fix: remove lemon + paddle things
This commit is contained in:
parent
f557cd0933
commit
3ebb35a5cd
@ -3,7 +3,6 @@
|
|||||||
namespace App\Livewire\Subscription;
|
namespace App\Livewire\Subscription;
|
||||||
|
|
||||||
use App\Models\Team;
|
use App\Models\Team;
|
||||||
use Illuminate\Support\Facades\Http;
|
|
||||||
use Livewire\Component;
|
use Livewire\Component;
|
||||||
|
|
||||||
class Actions extends Component
|
class Actions extends Component
|
||||||
@ -15,70 +14,6 @@ public function mount()
|
|||||||
$this->server_limits = Team::serverLimit();
|
$this->server_limits = Team::serverLimit();
|
||||||
}
|
}
|
||||||
|
|
||||||
public function cancel()
|
|
||||||
{
|
|
||||||
try {
|
|
||||||
$subscription_id = currentTeam()->subscription->lemon_subscription_id;
|
|
||||||
if (! $subscription_id) {
|
|
||||||
throw new \Exception('No subscription found');
|
|
||||||
}
|
|
||||||
$response = Http::withHeaders([
|
|
||||||
'Accept' => 'application/vnd.api+json',
|
|
||||||
'Content-Type' => 'application/vnd.api+json',
|
|
||||||
'Authorization' => 'Bearer '.config('subscription.lemon_squeezy_api_key'),
|
|
||||||
])->delete('https://api.lemonsqueezy.com/v1/subscriptions/'.$subscription_id);
|
|
||||||
$json = $response->json();
|
|
||||||
if ($response->failed()) {
|
|
||||||
$error = data_get($json, 'errors.0.status');
|
|
||||||
if ($error === '404') {
|
|
||||||
throw new \Exception('Subscription not found.');
|
|
||||||
}
|
|
||||||
throw new \Exception(data_get($json, 'errors.0.title', 'Something went wrong. Please try again later.'));
|
|
||||||
} else {
|
|
||||||
$this->dispatch('success', 'Subscription cancelled successfully. Reloading in 5s.');
|
|
||||||
$this->dispatch('reloadWindow', 5000);
|
|
||||||
}
|
|
||||||
} catch (\Throwable $e) {
|
|
||||||
return handleError($e, $this);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public function resume()
|
|
||||||
{
|
|
||||||
try {
|
|
||||||
$subscription_id = currentTeam()->subscription->lemon_subscription_id;
|
|
||||||
if (! $subscription_id) {
|
|
||||||
throw new \Exception('No subscription found');
|
|
||||||
}
|
|
||||||
$response = Http::withHeaders([
|
|
||||||
'Accept' => 'application/vnd.api+json',
|
|
||||||
'Content-Type' => 'application/vnd.api+json',
|
|
||||||
'Authorization' => 'Bearer '.config('subscription.lemon_squeezy_api_key'),
|
|
||||||
])->patch('https://api.lemonsqueezy.com/v1/subscriptions/'.$subscription_id, [
|
|
||||||
'data' => [
|
|
||||||
'type' => 'subscriptions',
|
|
||||||
'id' => $subscription_id,
|
|
||||||
'attributes' => [
|
|
||||||
'cancelled' => false,
|
|
||||||
],
|
|
||||||
],
|
|
||||||
]);
|
|
||||||
$json = $response->json();
|
|
||||||
if ($response->failed()) {
|
|
||||||
$error = data_get($json, 'errors.0.status');
|
|
||||||
if ($error === '404') {
|
|
||||||
throw new \Exception('Subscription not found.');
|
|
||||||
}
|
|
||||||
throw new \Exception(data_get($json, 'errors.0.title', 'Something went wrong. Please try again later.'));
|
|
||||||
} else {
|
|
||||||
$this->dispatch('success', 'Subscription resumed successfully. Reloading in 5s.');
|
|
||||||
$this->dispatch('reloadWindow', 5000);
|
|
||||||
}
|
|
||||||
} catch (\Throwable $e) {
|
|
||||||
return handleError($e, $this);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public function stripeCustomerPortal()
|
public function stripeCustomerPortal()
|
||||||
{
|
{
|
||||||
$session = getStripeCustomerPortalSession(currentTeam());
|
$session = getStripeCustomerPortalSession(currentTeam());
|
||||||
|
@ -15,22 +15,7 @@ public function team()
|
|||||||
|
|
||||||
public function type()
|
public function type()
|
||||||
{
|
{
|
||||||
if (isLemon()) {
|
if (isStripe()) {
|
||||||
$basic = explode(',', config('subscription.lemon_squeezy_basic_plan_ids'));
|
|
||||||
$pro = explode(',', config('subscription.lemon_squeezy_pro_plan_ids'));
|
|
||||||
$ultimate = explode(',', config('subscription.lemon_squeezy_ultimate_plan_ids'));
|
|
||||||
|
|
||||||
$subscription = $this->lemon_variant_id;
|
|
||||||
if (in_array($subscription, $basic)) {
|
|
||||||
return 'basic';
|
|
||||||
}
|
|
||||||
if (in_array($subscription, $pro)) {
|
|
||||||
return 'pro';
|
|
||||||
}
|
|
||||||
if (in_array($subscription, $ultimate)) {
|
|
||||||
return 'ultimate';
|
|
||||||
}
|
|
||||||
} elseif (isStripe()) {
|
|
||||||
if (! $this->stripe_plan_id) {
|
if (! $this->stripe_plan_id) {
|
||||||
return 'zero';
|
return 'zero';
|
||||||
}
|
}
|
||||||
|
@ -1,51 +1,8 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
use App\Models\Team;
|
use App\Models\Team;
|
||||||
use Illuminate\Support\Carbon;
|
|
||||||
use Stripe\Stripe;
|
use Stripe\Stripe;
|
||||||
|
|
||||||
function getSubscriptionLink($type)
|
|
||||||
{
|
|
||||||
$checkout_id = config("subscription.lemon_squeezy_checkout_id_$type");
|
|
||||||
if (! $checkout_id) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
$user_id = auth()->user()->id;
|
|
||||||
$team_id = currentTeam()->id ?? null;
|
|
||||||
$email = auth()->user()->email ?? null;
|
|
||||||
$name = auth()->user()->name ?? null;
|
|
||||||
$url = "https://store.coollabs.io/checkout/buy/$checkout_id?";
|
|
||||||
if ($user_id) {
|
|
||||||
$url .= "&checkout[custom][user_id]={$user_id}";
|
|
||||||
}
|
|
||||||
if (isset($team_id)) {
|
|
||||||
$url .= "&checkout[custom][team_id]={$team_id}";
|
|
||||||
}
|
|
||||||
if ($email) {
|
|
||||||
$url .= "&checkout[email]={$email}";
|
|
||||||
}
|
|
||||||
if ($name) {
|
|
||||||
$url .= "&checkout[name]={$name}";
|
|
||||||
}
|
|
||||||
|
|
||||||
return $url;
|
|
||||||
}
|
|
||||||
|
|
||||||
function getPaymentLink()
|
|
||||||
{
|
|
||||||
return currentTeam()->subscription->lemon_update_payment_menthod_url;
|
|
||||||
}
|
|
||||||
|
|
||||||
function getRenewDate()
|
|
||||||
{
|
|
||||||
return Carbon::parse(currentTeam()->subscription->lemon_renews_at)->format('Y-M-d H:i:s');
|
|
||||||
}
|
|
||||||
|
|
||||||
function getEndDate()
|
|
||||||
{
|
|
||||||
return Carbon::parse(currentTeam()->subscription->lemon_renews_at)->format('Y-M-d H:i:s');
|
|
||||||
}
|
|
||||||
|
|
||||||
function isSubscriptionActive()
|
function isSubscriptionActive()
|
||||||
{
|
{
|
||||||
if (! isCloud()) {
|
if (! isCloud()) {
|
||||||
@ -60,12 +17,6 @@ function isSubscriptionActive()
|
|||||||
if (is_null($subscription)) {
|
if (is_null($subscription)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (isLemon()) {
|
|
||||||
return $subscription->lemon_status === 'active';
|
|
||||||
}
|
|
||||||
// if (isPaddle()) {
|
|
||||||
// return $subscription->paddle_status === 'active';
|
|
||||||
// }
|
|
||||||
if (isStripe()) {
|
if (isStripe()) {
|
||||||
return $subscription->stripe_invoice_paid === true;
|
return $subscription->stripe_invoice_paid === true;
|
||||||
}
|
}
|
||||||
@ -82,12 +33,6 @@ function isSubscriptionOnGracePeriod()
|
|||||||
if (! $subscription) {
|
if (! $subscription) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (isLemon()) {
|
|
||||||
$is_still_grace_period = $subscription->lemon_ends_at &&
|
|
||||||
Carbon::parse($subscription->lemon_ends_at) > Carbon::now();
|
|
||||||
|
|
||||||
return $is_still_grace_period;
|
|
||||||
}
|
|
||||||
if (isStripe()) {
|
if (isStripe()) {
|
||||||
return $subscription->stripe_cancel_at_period_end;
|
return $subscription->stripe_cancel_at_period_end;
|
||||||
}
|
}
|
||||||
@ -98,18 +43,10 @@ function subscriptionProvider()
|
|||||||
{
|
{
|
||||||
return config('subscription.provider');
|
return config('subscription.provider');
|
||||||
}
|
}
|
||||||
function isLemon()
|
|
||||||
{
|
|
||||||
return config('subscription.provider') === 'lemon';
|
|
||||||
}
|
|
||||||
function isStripe()
|
function isStripe()
|
||||||
{
|
{
|
||||||
return config('subscription.provider') === 'stripe';
|
return config('subscription.provider') === 'stripe';
|
||||||
}
|
}
|
||||||
function isPaddle()
|
|
||||||
{
|
|
||||||
return config('subscription.provider') === 'paddle';
|
|
||||||
}
|
|
||||||
function getStripeCustomerPortalSession(Team $team)
|
function getStripeCustomerPortalSession(Team $team)
|
||||||
{
|
{
|
||||||
Stripe::setApiKey(config('subscription.stripe_api_key'));
|
Stripe::setApiKey(config('subscription.stripe_api_key'));
|
||||||
|
@ -1,7 +1,8 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
return [
|
return [
|
||||||
'provider' => env('SUBSCRIPTION_PROVIDER', null), // stripe, paddle, lemon
|
'provider' => env('SUBSCRIPTION_PROVIDER', null), // stripe
|
||||||
|
|
||||||
// Stripe
|
// Stripe
|
||||||
'stripe_api_key' => env('STRIPE_API_KEY', null),
|
'stripe_api_key' => env('STRIPE_API_KEY', null),
|
||||||
'stripe_webhook_secret' => env('STRIPE_WEBHOOK_SECRET', null),
|
'stripe_webhook_secret' => env('STRIPE_WEBHOOK_SECRET', null),
|
||||||
@ -22,29 +23,4 @@
|
|||||||
|
|
||||||
'stripe_price_id_dynamic_monthly' => env('STRIPE_PRICE_ID_DYNAMIC_MONTHLY', null),
|
'stripe_price_id_dynamic_monthly' => env('STRIPE_PRICE_ID_DYNAMIC_MONTHLY', null),
|
||||||
'stripe_price_id_dynamic_yearly' => env('STRIPE_PRICE_ID_DYNAMIC_YEARLY', null),
|
'stripe_price_id_dynamic_yearly' => env('STRIPE_PRICE_ID_DYNAMIC_YEARLY', null),
|
||||||
|
|
||||||
// Paddle
|
|
||||||
'paddle_vendor_id' => env('PADDLE_VENDOR_ID', null),
|
|
||||||
'paddle_vendor_auth_code' => env('PADDLE_VENDOR_AUTH_CODE', null),
|
|
||||||
'paddle_webhook_secret' => env('PADDLE_WEBHOOK_SECRET', null),
|
|
||||||
'paddle_public_key' => env('PADDLE_PUBLIC_KEY', null),
|
|
||||||
'paddle_price_id_basic_monthly' => env('PADDLE_PRICE_ID_BASIC_MONTHLY', null),
|
|
||||||
'paddle_price_id_basic_yearly' => env('PADDLE_PRICE_ID_BASIC_YEARLY', null),
|
|
||||||
'paddle_price_id_pro_monthly' => env('PADDLE_PRICE_ID_PRO_MONTHLY', null),
|
|
||||||
'paddle_price_id_pro_yearly' => env('PADDLE_PRICE_ID_PRO_YEARLY', null),
|
|
||||||
'paddle_price_id_ultimate_monthly' => env('PADDLE_PRICE_ID_ULTIMATE_MONTHLY', null),
|
|
||||||
'paddle_price_id_ultimate_yearly' => env('PADDLE_PRICE_ID_ULTIMATE_YEARLY', null),
|
|
||||||
|
|
||||||
// Lemon
|
|
||||||
'lemon_squeezy_api_key' => env('LEMON_SQUEEZY_API_KEY', null),
|
|
||||||
'lemon_squeezy_webhook_secret' => env('LEMON_SQUEEZY_WEBHOOK_SECRET', null),
|
|
||||||
'lemon_squeezy_checkout_id_basic_monthly' => env('LEMON_SQUEEZY_CHECKOUT_ID_BASIC_MONTHLY', null),
|
|
||||||
'lemon_squeezy_checkout_id_basic_yearly' => env('LEMON_SQUEEZY_CHECKOUT_ID_BASIC_YEARLY', null),
|
|
||||||
'lemon_squeezy_checkout_id_pro_monthly' => env('LEMON_SQUEEZY_CHECKOUT_ID_PRO_MONTHLY', null),
|
|
||||||
'lemon_squeezy_checkout_id_pro_yearly' => env('LEMON_SQUEEZY_CHECKOUT_ID_PRO_YEARLY', null),
|
|
||||||
'lemon_squeezy_checkout_id_ultimate_monthly' => env('LEMON_SQUEEZY_CHECKOUT_ID_ULTIMATE_MONTHLY', null),
|
|
||||||
'lemon_squeezy_checkout_id_ultimate_yearly' => env('LEMON_SQUEEZY_CHECKOUT_ID_ULTIMATE_YEARLY', null),
|
|
||||||
'lemon_squeezy_basic_plan_ids' => env('LEMON_SQUEEZY_BASIC_PLAN_IDS', ''),
|
|
||||||
'lemon_squeezy_pro_plan_ids' => env('LEMON_SQUEEZY_PRO_PLAN_IDS', ''),
|
|
||||||
'lemon_squeezy_ultimate_plan_ids' => env('LEMON_SQUEEZY_ULTIMATE_PLAN_IDS', ''),
|
|
||||||
];
|
];
|
||||||
|
@ -69,27 +69,6 @@ services:
|
|||||||
- STRIPE_PRICE_ID_ULTIMATE_MONTHLY_OLD
|
- STRIPE_PRICE_ID_ULTIMATE_MONTHLY_OLD
|
||||||
- STRIPE_PRICE_ID_ULTIMATE_YEARLY_OLD
|
- STRIPE_PRICE_ID_ULTIMATE_YEARLY_OLD
|
||||||
- STRIPE_EXCLUDED_PLANS
|
- STRIPE_EXCLUDED_PLANS
|
||||||
- PADDLE_VENDOR_ID
|
|
||||||
- PADDLE_WEBHOOK_SECRET
|
|
||||||
- PADDLE_VENDOR_AUTH_CODE
|
|
||||||
- PADDLE_PUBLIC_KEY
|
|
||||||
- PADDLE_PRICE_ID_BASIC_MONTHLY
|
|
||||||
- PADDLE_PRICE_ID_BASIC_YEARLY
|
|
||||||
- PADDLE_PRICE_ID_PRO_MONTHLY
|
|
||||||
- PADDLE_PRICE_ID_PRO_YEARLY
|
|
||||||
- PADDLE_PRICE_ID_ULTIMATE_MONTHLY
|
|
||||||
- PADDLE_PRICE_ID_ULTIMATE_YEARLY
|
|
||||||
- LEMON_SQUEEZY_API_KEY
|
|
||||||
- LEMON_SQUEEZY_WEBHOOK_SECRET
|
|
||||||
- LEMON_SQUEEZY_CHECKOUT_ID_BASIC_MONTHLY
|
|
||||||
- LEMON_SQUEEZY_CHECKOUT_ID_BASIC_YEARLY
|
|
||||||
- LEMON_SQUEEZY_CHECKOUT_ID_PRO_MONTHLY
|
|
||||||
- LEMON_SQUEEZY_CHECKOUT_ID_PRO_YEARLY
|
|
||||||
- LEMON_SQUEEZY_CHECKOUT_ID_ULTIMATE_MONTHLY
|
|
||||||
- LEMON_SQUEEZY_CHECKOUT_ID_ULTIMATE_YEARLY
|
|
||||||
- LEMON_SQUEEZY_BASIC_PLAN_IDS
|
|
||||||
- LEMON_SQUEEZY_PRO_PLAN_IDS
|
|
||||||
- LEMON_SQUEEZY_ULTIMATE_PLAN_IDS
|
|
||||||
ports:
|
ports:
|
||||||
- "${APP_PORT:-8000}:80"
|
- "${APP_PORT:-8000}:80"
|
||||||
expose:
|
expose:
|
||||||
|
@ -1,80 +0,0 @@
|
|||||||
<x-slot:basic>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-basic" class="w-full h-10 buyme"
|
|
||||||
x-on:click="subscribe('basic-monthly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-basic" class="w-full h-10 buyme"
|
|
||||||
x-on:click="subscribe('basic-yearly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:basic>
|
|
||||||
<x-slot:pro>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-pro" class="w-full h-10 buyme"
|
|
||||||
x-on:click="subscribe('pro-monthly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-pro" class="w-full h-10 buyme"
|
|
||||||
x-on:click="subscribe('pro-yearly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:pro>
|
|
||||||
<x-slot:ultimate>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-ultimate" class="w-full h-10 buyme"
|
|
||||||
x-on:click="subscribe('ultimate-monthly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-ultimate" class="w-full h-10 buyme"
|
|
||||||
x-on:click="subscribe('ultimate-yearly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:ultimate>
|
|
||||||
<x-slot:other>
|
|
||||||
<script src="https://cdn.paddle.com/paddle/v2/paddle.js"></script>
|
|
||||||
<script type="text/javascript">
|
|
||||||
Paddle.Environment.set("{{ isDev() ? 'sandbox' : 'production' }}");
|
|
||||||
Paddle.Setup({
|
|
||||||
seller: {{ config('subscription.paddle_vendor_id') }},
|
|
||||||
checkout: {
|
|
||||||
settings: {
|
|
||||||
displayMode: "overlay",
|
|
||||||
theme: "light",
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
function subscribe(type) {
|
|
||||||
let priceId = null
|
|
||||||
switch (type) {
|
|
||||||
case 'basic-monthly':
|
|
||||||
priceId = "{{ config('subscription.paddle_price_id_basic_monthly') }}"
|
|
||||||
break;
|
|
||||||
case 'basic-yearly':
|
|
||||||
priceId = "{{ config('subscription.paddle_price_id_basic_yearly') }}"
|
|
||||||
break;
|
|
||||||
case 'pro-monthly':
|
|
||||||
priceId = "{{ config('subscription.paddle_price_id_pro_monthly') }}"
|
|
||||||
break;
|
|
||||||
case 'pro-yearly':
|
|
||||||
priceId = "{{ config('subscription.paddle_price_id_pro_yearly') }}"
|
|
||||||
break;
|
|
||||||
case 'ultimate-monthly':
|
|
||||||
priceId = "{{ config('subscription.paddle_price_id_ultimate_monthly') }}"
|
|
||||||
break;
|
|
||||||
case 'ultimate-yearly':
|
|
||||||
priceId = "{{ config('subscription.paddle_price_id_ultimate_yearly') }}"
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
Paddle.Checkout.open({
|
|
||||||
customer: {
|
|
||||||
email: '{{ auth()->user()->email }}',
|
|
||||||
},
|
|
||||||
customData: {
|
|
||||||
"team_id": "{{ currentTeam()->id }}",
|
|
||||||
},
|
|
||||||
items: [{
|
|
||||||
priceId,
|
|
||||||
quantity: 1
|
|
||||||
}],
|
|
||||||
});
|
|
||||||
}
|
|
||||||
</script>
|
|
||||||
</x-slot:other>
|
|
@ -34,15 +34,16 @@ class="font-bold dark:text-warning">{{ config('constants.limits.trial_period') }
|
|||||||
<div>
|
<div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{{-- <div class="p-4 rounded bg-coolgray-400">
|
<div class="p-4 rounded bg-coolgray-400">
|
||||||
<h2 id="tier-hobby" class="flex items-start gap-4 text-4xl font-bold tracking-tight">Unlimited Trial
|
<h2 id="tier-hobby" class="flex items-start gap-4 text-4xl font-bold tracking-tight">Unlimited Trial
|
||||||
<x-forms.button><a class="font-bold dark:text-white hover:no-underline"
|
<x-forms.button><a class="font-bold dark:text-white hover:no-underline"
|
||||||
href="https://github.com/coollabsio/coolify">Get Started</a></x-forms.button>
|
href="https://github.com/coollabsio/coolify">Get Started</a></x-forms.button>
|
||||||
</h2>
|
</h2>
|
||||||
<p class="mt-4 text-sm leading-6">Start self-hosting <span class="dark:text-warning">without limits</span> with
|
<p class="mt-4 text-sm leading-6">Start self-hosting <span class="dark:text-warning">without limits</span>
|
||||||
|
with
|
||||||
our
|
our
|
||||||
OSS version. Same features as the paid version, but you have to manage by yourself.</p>
|
OSS version. Same features as the paid version, but you have to manage by yourself.</p>
|
||||||
</div> --}}
|
</div>
|
||||||
|
|
||||||
<div class="flow-root mt-12">
|
<div class="flow-root mt-12">
|
||||||
<div class="pb-10 text-xl text-center">For the detailed list of features, please visit our landing page: <a
|
<div class="pb-10 text-xl text-center">For the detailed list of features, please visit our landing page: <a
|
||||||
@ -78,8 +79,8 @@ class="grid max-w-sm grid-cols-1 -mt-16 divide-y divide-neutral-200 dark:divide-
|
|||||||
</p>
|
</p>
|
||||||
<ul role="list" class="space-y-3 text-sm leading-6 ">
|
<ul role="list" class="space-y-3 text-sm leading-6 ">
|
||||||
<li class="flex">
|
<li class="flex">
|
||||||
<svg class="flex-none w-5 h-6 mr-3 dark:text-warning" viewBox="0 0 20 20" fill="currentColor"
|
<svg class="flex-none w-5 h-6 mr-3 dark:text-warning" viewBox="0 0 20 20"
|
||||||
aria-hidden="true">
|
fill="currentColor" aria-hidden="true">
|
||||||
<path fill-rule="evenodd"
|
<path fill-rule="evenodd"
|
||||||
d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.775 0 001.137-.089l4-5.5z"
|
d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.775 0 001.137-.089l4-5.5z"
|
||||||
clip-rule="evenodd" />
|
clip-rule="evenodd" />
|
||||||
@ -141,13 +142,14 @@ class="grid max-w-sm grid-cols-1 -mt-16 divide-y divide-neutral-200 dark:divide-
|
|||||||
{{ $pro }}
|
{{ $pro }}
|
||||||
@endisset
|
@endisset
|
||||||
@endif
|
@endif
|
||||||
<p class="h-20 mt-10 text-sm leading-6 dark:text-white">Expand your business or set up your own hosting
|
<p class="h-20 mt-10 text-sm leading-6 dark:text-white">Expand your business or set up your own
|
||||||
|
hosting
|
||||||
environment.
|
environment.
|
||||||
</p>
|
</p>
|
||||||
<ul role="list" class="mt-6 space-y-3 text-sm leading-6 ">
|
<ul role="list" class="mt-6 space-y-3 text-sm leading-6 ">
|
||||||
<li class="flex ">
|
<li class="flex ">
|
||||||
<svg class="flex-none w-5 h-6 mr-3 dark:text-warning" viewBox="0 0 20 20" fill="currentColor"
|
<svg class="flex-none w-5 h-6 mr-3 dark:text-warning" viewBox="0 0 20 20"
|
||||||
aria-hidden="true">
|
fill="currentColor" aria-hidden="true">
|
||||||
<path fill-rule="evenodd"
|
<path fill-rule="evenodd"
|
||||||
d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.75.75 0 001.137-.089l4-5.5z"
|
d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.75.75 0 001.137-.089l4-5.5z"
|
||||||
clip-rule="evenodd" />
|
clip-rule="evenodd" />
|
||||||
@ -213,8 +215,8 @@ class="grid max-w-sm grid-cols-1 -mt-16 divide-y divide-neutral-200 dark:divide-
|
|||||||
single location.</p>
|
single location.</p>
|
||||||
<ul role="list" class="mt-6 space-y-3 text-sm leading-6 ">
|
<ul role="list" class="mt-6 space-y-3 text-sm leading-6 ">
|
||||||
<li class="flex ">
|
<li class="flex ">
|
||||||
<svg class="flex-none w-5 h-6 mr-3 dark:text-warning" viewBox="0 0 20 20" fill="currentColor"
|
<svg class="flex-none w-5 h-6 mr-3 dark:text-warning" viewBox="0 0 20 20"
|
||||||
aria-hidden="true">
|
fill="currentColor" aria-hidden="true">
|
||||||
<path fill-rule="evenodd"
|
<path fill-rule="evenodd"
|
||||||
d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.75.75 0 001.137-.089l4-5.5z"
|
d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.75.75 0 001.137-.089l4-5.5z"
|
||||||
clip-rule="evenodd" />
|
clip-rule="evenodd" />
|
||||||
|
@ -2,8 +2,7 @@
|
|||||||
@if (subscriptionProvider() === 'stripe')
|
@if (subscriptionProvider() === 'stripe')
|
||||||
<div class="pt-4">
|
<div class="pt-4">
|
||||||
<h2>Your current plan</h2>
|
<h2>Your current plan</h2>
|
||||||
<div class="pb-4">Tier: <strong
|
<div class="pb-4">Tier: <strong class="dark:text-warning">
|
||||||
class="dark:text-warning">
|
|
||||||
@if (data_get(currentTeam(), 'subscription')->type() == 'dynamic')
|
@if (data_get(currentTeam(), 'subscription')->type() == 'dynamic')
|
||||||
Pay-as-you-go
|
Pay-as-you-go
|
||||||
@else
|
@else
|
||||||
@ -50,35 +49,4 @@ class="dark:text-warning">
|
|||||||
target="_blank">contact us.</a>
|
target="_blank">contact us.</a>
|
||||||
</div>
|
</div>
|
||||||
@endif
|
@endif
|
||||||
{{-- @if (subscriptionProvider() === 'lemon')
|
|
||||||
<div>Status: {{ currentTeam()->subscription->lemon_status }}</div>
|
|
||||||
<div>Type: {{ currentTeam()->subscription->lemon_variant_name }}</div>
|
|
||||||
@if (currentTeam()->subscription->lemon_status === 'cancelled')
|
|
||||||
<div class="pb-4">Subscriptions ends at: {{ getRenewDate() }}</div>
|
|
||||||
<div class="py-4">If you would like to change the subscription to a lower/higher plan, <a
|
|
||||||
class="underline dark:text-white" href="{{ config('coolify.contact') }}" target="_blank">please
|
|
||||||
contact
|
|
||||||
us.</a></div>
|
|
||||||
@else
|
|
||||||
<div class="pb-4">Renews at: {{ getRenewDate() }}</div>
|
|
||||||
@endif
|
|
||||||
<div class="flex flex-col gap-2">
|
|
||||||
<div class="flex gap-2">
|
|
||||||
@if (currentTeam()->subscription->lemon_status === 'cancelled')
|
|
||||||
<x-forms.button class="bg-coollabs-gradient" wire:click='resume'>Resume Subscription
|
|
||||||
</x-forms.button>
|
|
||||||
@else
|
|
||||||
<x-forms.button wire:click='cancel'>Cancel Subscription</x-forms.button>
|
|
||||||
@endif
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<x-forms.button><a class="dark:text-white hover:no-underline" href="{{ getPaymentLink() }}">Update Payment
|
|
||||||
Details</a>
|
|
||||||
</x-forms.button>
|
|
||||||
<a class="dark:text-white hover:no-underline"
|
|
||||||
href="https://app.lemonsqueezy.com/my-orders"><x-forms.button>Manage My
|
|
||||||
Subscription</x-forms.button></a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
@endif --}}
|
|
||||||
</div>
|
</div>
|
||||||
|
@ -1,67 +0,0 @@
|
|||||||
<x-pricing-plans>
|
|
||||||
@if (config('subscription.provider') === 'stripe')
|
|
||||||
<x-slot:basic>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-basic" class="w-full h-10 buyme"
|
|
||||||
wire:click="subscribeStripe('basic-monthly')">
|
|
||||||
{{ $isTrial ? 'Start Trial' : 'Subscribe' }}
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-basic" class="w-full h-10 buyme"
|
|
||||||
wire:click="subscribeStripe('basic-yearly')">
|
|
||||||
{{ $isTrial ? 'Start Trial' : 'Subscribe' }}
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:basic>
|
|
||||||
<x-slot:pro>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-pro" class="w-full h-10 buyme"
|
|
||||||
wire:click="subscribeStripe('pro-monthly')">
|
|
||||||
{{ $isTrial ? 'Start Trial' : 'Subscribe' }}
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-pro" class="w-full h-10 buyme"
|
|
||||||
wire:click="subscribeStripe('pro-yearly')"> {{ $isTrial ? 'Start Trial' : 'Subscribe' }}
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:pro>
|
|
||||||
<x-slot:ultimate>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-ultimate" class="w-full h-10 buyme"
|
|
||||||
wire:click="subscribeStripe('ultimate-monthly')">
|
|
||||||
{{ $isTrial ? 'Start Trial' : 'Subscribe' }}
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-ultimate" class="w-full h-10 buyme"
|
|
||||||
wire:click="subscribeStripe('ultimate-yearly')"> {{ $isTrial ? 'Start Trial' : 'Subscribe' }}
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:ultimate>
|
|
||||||
@endif
|
|
||||||
@if (config('subscription.provider') === 'paddle')
|
|
||||||
<x-paddle />
|
|
||||||
@endif
|
|
||||||
@if (config('subscription.provider') === 'lemon')
|
|
||||||
<x-slot:basic>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-basic"
|
|
||||||
class="w-full h-10 buyme" wire:click="getSubscriptionLink('basic-monthly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-basic"
|
|
||||||
class="w-full h-10 buyme" wire:click="getSubscriptionLink('basic-yearly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:basic>
|
|
||||||
<x-slot:pro>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-pro"
|
|
||||||
class="w-full h-10 buyme" wire:click="getSubscriptionLink('pro-monthly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-pro" class="w-full h-10 buyme"
|
|
||||||
wire:click="getSubscriptionLink('pro-yearly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:pro>
|
|
||||||
<x-slot:ultimate>
|
|
||||||
<x-forms.button x-show="selected === 'monthly'" x-cloak aria-describedby="tier-ultimate"
|
|
||||||
class="w-full h-10 buyme" wire:click="getSubscriptionLink('ultimate-monthly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
|
|
||||||
<x-forms.button x-show="selected === 'yearly'" x-cloak aria-describedby="tier-ultimate"
|
|
||||||
class="w-full h-10 buyme" wire:click="getSubscriptionLink('ultimate-yearly')"> Subscribe
|
|
||||||
</x-forms.button>
|
|
||||||
</x-slot:ultimate>
|
|
||||||
@endif
|
|
||||||
</x-pricing-plans>
|
|
@ -25,7 +25,7 @@
|
|||||||
<div>This is the default team. You can't delete it.</div>
|
<div>This is the default team. You can't delete it.</div>
|
||||||
@elseif(auth()->user()->teams()->get()->count() === 1 || auth()->user()->currentTeam()->personal_team)
|
@elseif(auth()->user()->teams()->get()->count() === 1 || auth()->user()->currentTeam()->personal_team)
|
||||||
<div>You can't delete your last / personal team.</div>
|
<div>You can't delete your last / personal team.</div>
|
||||||
@elseif(currentTeam()->subscription && currentTeam()->subscription?->lemon_status !== 'cancelled')
|
@elseif(currentTeam()->subscription)
|
||||||
<div>Please cancel your subscription <a class="underline dark:text-white"
|
<div>Please cancel your subscription <a class="underline dark:text-white"
|
||||||
href="{{ route('subscription.show') }}">here</a> before delete this team.</div>
|
href="{{ route('subscription.show') }}">here</a> before delete this team.</div>
|
||||||
@else
|
@else
|
||||||
|
@ -1,62 +0,0 @@
|
|||||||
<?php
|
|
||||||
|
|
||||||
use App\Actions\CoolifyTask\RunRemoteProcess;
|
|
||||||
use App\Actions\CoolifyTask\TidyOutput;
|
|
||||||
use App\Models\Server;
|
|
||||||
use App\Models\User;
|
|
||||||
use Database\Seeders\DatabaseSeeder;
|
|
||||||
use Illuminate\Foundation\Testing\DatabaseMigrations;
|
|
||||||
use Illuminate\Foundation\Testing\RefreshDatabase;
|
|
||||||
|
|
||||||
uses(RefreshDatabase::class);
|
|
||||||
uses(DatabaseMigrations::class);
|
|
||||||
|
|
||||||
beforeEach(function () {
|
|
||||||
$this->seed(DatabaseSeeder::class);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('starts a docker container correctly', function () {
|
|
||||||
|
|
||||||
|
|
||||||
test()->actingAs(User::factory([
|
|
||||||
'uuid' => Str::uuid(),
|
|
||||||
'email' => Str::uuid() . '@example.com',
|
|
||||||
])->create());
|
|
||||||
|
|
||||||
$coolifyNamePrefix = 'coolify_test_';
|
|
||||||
|
|
||||||
|
|
||||||
$format = '{"ID":"{{ .ID }}", "Image": "{{ .Image }}", "Names":"{{ .Names }}"}';
|
|
||||||
$areThereCoolifyTestContainers = "docker ps --filter=\"name={$coolifyNamePrefix}*\" --format '{$format}' ";
|
|
||||||
|
|
||||||
// Generate a known name
|
|
||||||
$containerName = 'coolify_test_' . now()->format('Ymd_his');
|
|
||||||
$host = Server::where('name', 'testing-local-docker-container')->first();
|
|
||||||
|
|
||||||
remote_process([
|
|
||||||
"docker rm -f $(docker ps --filter='name={$coolifyNamePrefix}*' -aq) > /dev/null 2>&1"
|
|
||||||
], $host);
|
|
||||||
|
|
||||||
// Assert there's no containers start with coolify_test_*
|
|
||||||
$activity = remote_process([$areThereCoolifyTestContainers], $host);
|
|
||||||
$tidyOutput = RunRemoteProcess::decodeOutput($activity);
|
|
||||||
$containers = format_docker_command_output_to_json($tidyOutput);
|
|
||||||
expect($containers)->toBeEmpty();
|
|
||||||
|
|
||||||
// start a container nginx -d --name = $containerName
|
|
||||||
$activity = remote_process(["docker run -d --rm --name {$containerName} nginx"], $host);
|
|
||||||
expect($activity->getExtraProperty('exitCode'))->toBe(0);
|
|
||||||
|
|
||||||
// docker ps name = $container
|
|
||||||
$activity = remote_process([$areThereCoolifyTestContainers], $host);
|
|
||||||
$tidyOutput = RunRemoteProcess::decodeOutput($activity);
|
|
||||||
$containers = format_docker_command_output_to_json($tidyOutput);
|
|
||||||
expect($containers->where('Names', $containerName)->count())->toBe(1);
|
|
||||||
|
|
||||||
// Stop testing containers
|
|
||||||
$activity = remote_process([
|
|
||||||
"docker ps --filter='name={$coolifyNamePrefix}*' -aq && " .
|
|
||||||
"docker rm -f $(docker ps --filter='name={$coolifyNamePrefix}*' -aq)"
|
|
||||||
], $host);
|
|
||||||
expect($activity->getExtraProperty('exitCode'))->toBe(0);
|
|
||||||
});
|
|
@ -1,32 +0,0 @@
|
|||||||
<?php
|
|
||||||
|
|
||||||
use App\Actions\CoolifyTask\RunRemoteProcess;
|
|
||||||
use App\Models\Server;
|
|
||||||
use Database\Seeders\DatabaseSeeder;
|
|
||||||
use Illuminate\Foundation\Testing\DatabaseMigrations;
|
|
||||||
use Illuminate\Foundation\Testing\RefreshDatabase;
|
|
||||||
|
|
||||||
uses(RefreshDatabase::class);
|
|
||||||
uses(DatabaseMigrations::class);
|
|
||||||
|
|
||||||
beforeEach(function () {
|
|
||||||
$this->seed(DatabaseSeeder::class);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('outputs correctly', function () {
|
|
||||||
|
|
||||||
$host = Server::where('name', 'testing-local-docker-container')->first();
|
|
||||||
|
|
||||||
$activity = remote_process([
|
|
||||||
'pwd',
|
|
||||||
'x=1; while [ $x -le 3 ]; do sleep 0.1 && echo "Welcome $x times" $(( x++ )); done',
|
|
||||||
], $host);
|
|
||||||
|
|
||||||
|
|
||||||
$tidyOutput = RunRemoteProcess::decodeOutput($activity);
|
|
||||||
|
|
||||||
expect($tidyOutput)
|
|
||||||
->toContain('Welcome 1 times')
|
|
||||||
->toContain('Welcome 3 times')
|
|
||||||
->not()->toBeJson();
|
|
||||||
});
|
|
Loading…
Reference in New Issue
Block a user