diff --git a/app/Http/Controllers/BtcPaymentController.php b/app/Http/Controllers/BtcPaymentController.php index ed8cc3da7..961cb6b5b 100644 --- a/app/Http/Controllers/BtcPaymentController.php +++ b/app/Http/Controllers/BtcPaymentController.php @@ -63,10 +63,19 @@ class BtcPaymentController extends BasePageController if ($checkOrder !== null) { $user = User::query()->where('email', '=', $checkOrder->email)->first(); if ($user) { - $roleName = $checkOrder->item_description; - User::updateUserRole($user->id, $roleName); + // Extract role name and addYears from item_description using regex + // Matches patterns like "User 1", "Admin ++ 2", "Friend 3" + if (preg_match('/(?P\w+(\s\+\+)?)[\s]+(?P\d+)/i', $checkOrder->item_description, $matches)) { + $roleName = $matches['role']; + $addYears = (int) $matches['addYears']; + } else { + $roleName = $checkOrder->item_description; + $addYears = null; + } + + User::updateUserRole($user->id, $roleName, addYears: $addYears); $checkOrder->update(['invoice_status' => 'Settled']); - Log::channel('btc_payment')->info('User: '.$user->username.' upgraded to '.$roleName.' for BTCPay webhook: '.$checkOrder->webhook_id); + Log::channel('btc_payment')->info('User: '.$user->username.' upgraded to '.$roleName.' (+'.$addYears.' years) for BTCPay webhook: '.$checkOrder->webhook_id); return response('OK', 200); } diff --git a/app/Models/User.php b/app/Models/User.php index e5db69352..b962b8a43 100644 --- a/app/Models/User.php +++ b/app/Models/User.php @@ -413,7 +413,7 @@ class User extends Authenticatable return self::whereEmail($email)->first(); } - public static function updateUserRole(int $uid, int|string $role, bool $applyPromotions = true, bool $stackRole = true, ?int $changedBy = null, ?string $originalExpiryBeforeEdits = null, bool $preserveCurrentExpiry = false): bool + public static function updateUserRole(int $uid, int|string $role, bool $applyPromotions = true, bool $stackRole = true, ?int $changedBy = null, ?string $originalExpiryBeforeEdits = null, bool $preserveCurrentExpiry = false, ?int $addYears = null): bool { // Handle role parameter - can be int, numeric string, or role name if (is_numeric($role)) { @@ -536,7 +536,8 @@ class User extends Authenticatable // Calculate a new expiry date for the pending role // Start with the role's base duration (addyears field converted to days) - $baseDays = $roleQuery->addyears * 365; + // Use the provided addYears parameter if available, otherwise use role's default + $baseDays = ($addYears !== null ? $addYears : $roleQuery->addyears) * 365; $promotionDays = 0; // Define roles that should not receive promotions @@ -607,7 +608,8 @@ class User extends Authenticatable // Apply the role change immediately // Calculate base days from role's addyears field - $baseDays = $roleQuery->addyears * 365; + // Use the provided addYears parameter if available, otherwise use role's default + $baseDays = ($addYears !== null ? $addYears : $roleQuery->addyears) * 365; $promotionDays = 0; // Define roles that should not receive promotions