Merge remote-tracking branch 'origin/main' into cloudflare

This commit is contained in:
javayhu 2025-09-03 00:08:21 +08:00
commit b0a065ced9
7 changed files with 30 additions and 46 deletions

View File

@ -592,7 +592,7 @@
}, },
"price": "Price:", "price": "Price:",
"periodStartDate": "Period start date:", "periodStartDate": "Period start date:",
"nextBillingDate": "Next billing date:", "periodEndDate": "Period end date:",
"trialEnds": "Trial ends:", "trialEnds": "Trial ends:",
"freePlanMessage": "You are currently on the free plan with limited features", "freePlanMessage": "You are currently on the free plan with limited features",
"lifetimeMessage": "You have lifetime access to all premium features", "lifetimeMessage": "You have lifetime access to all premium features",

View File

@ -592,7 +592,7 @@
}, },
"price": "价格:", "price": "价格:",
"periodStartDate": "周期开始日期:", "periodStartDate": "周期开始日期:",
"nextBillingDate": "下次账单日期:", "periodEndDate": "周期结束日期:",
"trialEnds": "试用结束日期:", "trialEnds": "试用结束日期:",
"freePlanMessage": "您当前使用的是功能有限的免费方案", "freePlanMessage": "您当前使用的是功能有限的免费方案",
"lifetimeMessage": "您拥有所有高级功能的终身使用权限", "lifetimeMessage": "您拥有所有高级功能的终身使用权限",

View File

@ -17,7 +17,7 @@ import { Input } from '@/components/ui/input';
import { websiteConfig } from '@/config/website'; import { websiteConfig } from '@/config/website';
import { LocaleLink } from '@/i18n/navigation'; import { LocaleLink } from '@/i18n/navigation';
import { authClient } from '@/lib/auth-client'; import { authClient } from '@/lib/auth-client';
import { getUrlWithLocaleInCallbackUrl } from '@/lib/urls/urls'; import { getUrlWithLocale } from '@/lib/urls/urls';
import { cn } from '@/lib/utils'; import { cn } from '@/lib/utils';
import { DEFAULT_LOGIN_REDIRECT, Routes } from '@/routes'; import { DEFAULT_LOGIN_REDIRECT, Routes } from '@/routes';
import { zodResolver } from '@hookform/resolvers/zod'; import { zodResolver } from '@hookform/resolvers/zod';
@ -45,10 +45,10 @@ export const LoginForm = ({
const paramCallbackUrl = searchParams.get('callbackUrl'); const paramCallbackUrl = searchParams.get('callbackUrl');
// Use prop callback URL or param callback URL if provided, otherwise use the default login redirect // Use prop callback URL or param callback URL if provided, otherwise use the default login redirect
const locale = useLocale(); const locale = useLocale();
const defaultCallbackUrl = getUrlWithLocaleInCallbackUrl( const defaultCallbackUrl = getUrlWithLocale(DEFAULT_LOGIN_REDIRECT, locale);
DEFAULT_LOGIN_REDIRECT, // console.log('login form, propCallbackUrl', propCallbackUrl);
locale // console.log('login form, paramCallbackUrl', paramCallbackUrl);
); // console.log('login form, defaultCallbackUrl', defaultCallbackUrl);
const callbackUrl = propCallbackUrl || paramCallbackUrl || defaultCallbackUrl; const callbackUrl = propCallbackUrl || paramCallbackUrl || defaultCallbackUrl;
console.log('login form, callbackUrl', callbackUrl); console.log('login form, callbackUrl', callbackUrl);

View File

@ -16,7 +16,7 @@ import {
import { Input } from '@/components/ui/input'; import { Input } from '@/components/ui/input';
import { websiteConfig } from '@/config/website'; import { websiteConfig } from '@/config/website';
import { authClient } from '@/lib/auth-client'; import { authClient } from '@/lib/auth-client';
import { getUrlWithLocaleInCallbackUrl } from '@/lib/urls/urls'; import { getUrlWithLocale } from '@/lib/urls/urls';
import { DEFAULT_LOGIN_REDIRECT, Routes } from '@/routes'; import { DEFAULT_LOGIN_REDIRECT, Routes } from '@/routes';
import { zodResolver } from '@hookform/resolvers/zod'; import { zodResolver } from '@hookform/resolvers/zod';
import { EyeIcon, EyeOffIcon, Loader2Icon } from 'lucide-react'; import { EyeIcon, EyeOffIcon, Loader2Icon } from 'lucide-react';
@ -40,10 +40,10 @@ export const RegisterForm = ({
const paramCallbackUrl = searchParams.get('callbackUrl'); const paramCallbackUrl = searchParams.get('callbackUrl');
// Use prop callback URL or param callback URL if provided, otherwise use the default login redirect // Use prop callback URL or param callback URL if provided, otherwise use the default login redirect
const locale = useLocale(); const locale = useLocale();
const defaultCallbackUrl = getUrlWithLocaleInCallbackUrl( const defaultCallbackUrl = getUrlWithLocale(DEFAULT_LOGIN_REDIRECT, locale);
DEFAULT_LOGIN_REDIRECT, // console.log('register form, propCallbackUrl', propCallbackUrl);
locale // console.log('register form, paramCallbackUrl', paramCallbackUrl);
); // console.log('register form, defaultCallbackUrl', defaultCallbackUrl);
const callbackUrl = propCallbackUrl || paramCallbackUrl || defaultCallbackUrl; const callbackUrl = propCallbackUrl || paramCallbackUrl || defaultCallbackUrl;
console.log('register form, callbackUrl', callbackUrl); console.log('register form, callbackUrl', callbackUrl);

View File

@ -6,7 +6,7 @@ import { GoogleIcon } from '@/components/icons/google';
import { Button } from '@/components/ui/button'; import { Button } from '@/components/ui/button';
import { websiteConfig } from '@/config/website'; import { websiteConfig } from '@/config/website';
import { authClient } from '@/lib/auth-client'; import { authClient } from '@/lib/auth-client';
import { getUrlWithLocaleInCallbackUrl } from '@/lib/urls/urls'; import { getUrlWithLocale } from '@/lib/urls/urls';
import { DEFAULT_LOGIN_REDIRECT, Routes } from '@/routes'; import { DEFAULT_LOGIN_REDIRECT, Routes } from '@/routes';
import { Loader2Icon } from 'lucide-react'; import { Loader2Icon } from 'lucide-react';
import { useLocale, useTranslations } from 'next-intl'; import { useLocale, useTranslations } from 'next-intl';
@ -37,10 +37,7 @@ export const SocialLoginButton = ({
const paramCallbackUrl = searchParams.get('callbackUrl'); const paramCallbackUrl = searchParams.get('callbackUrl');
// Use prop callback URL or param callback URL if provided, otherwise use the default login redirect // Use prop callback URL or param callback URL if provided, otherwise use the default login redirect
const locale = useLocale(); const locale = useLocale();
const defaultCallbackUrl = getUrlWithLocaleInCallbackUrl( const defaultCallbackUrl = getUrlWithLocale(DEFAULT_LOGIN_REDIRECT, locale);
DEFAULT_LOGIN_REDIRECT,
locale
);
const callbackUrl = propCallbackUrl || paramCallbackUrl || defaultCallbackUrl; const callbackUrl = propCallbackUrl || paramCallbackUrl || defaultCallbackUrl;
const [isLoading, setIsLoading] = useState<'google' | 'github' | null>(null); const [isLoading, setIsLoading] = useState<'google' | 'github' | null>(null);
console.log('social login button, callbackUrl', callbackUrl); console.log('social login button, callbackUrl', callbackUrl);

View File

@ -60,23 +60,21 @@ export default function BillingCard() {
const isFreePlan = currentPlanWithTranslations?.isFree || false; const isFreePlan = currentPlanWithTranslations?.isFree || false;
const isLifetimeMember = currentPlanWithTranslations?.isLifetime || false; const isLifetimeMember = currentPlanWithTranslations?.isLifetime || false;
// Get subscription price details
const currentPrice =
subscription &&
currentPlanWithTranslations?.prices.find(
(price) => price.priceId === subscription?.priceId
);
// Get current period start date // Get current period start date
const currentPeriodStart = subscription?.currentPeriodStart const currentPeriodStart = subscription?.currentPeriodStart
? formatDate(subscription.currentPeriodStart) ? formatDate(subscription.currentPeriodStart)
: null; : null;
// Format next billing date if subscription is active // Get current period end date
const nextBillingDate = subscription?.currentPeriodEnd const currentPeriodEnd = subscription?.currentPeriodEnd
? formatDate(subscription.currentPeriodEnd) ? formatDate(subscription.currentPeriodEnd)
: null; : null;
// Get current trial end date
const trialEndDate = subscription?.trialEndDate
? formatDate(subscription.trialEndDate)
: null;
// Retry payment data fetching // Retry payment data fetching
const handleRetry = useCallback(() => { const handleRetry = useCallback(() => {
// console.log('handleRetry, refetch payment info'); // console.log('handleRetry, refetch payment info');
@ -229,36 +227,25 @@ export default function BillingCard() {
)} )}
{/* Subscription plan message */} {/* Subscription plan message */}
{subscription && currentPrice && ( {subscription && (
<div className="text-sm text-muted-foreground space-y-2"> <div className="text-sm text-muted-foreground space-y-2">
{/* <div>
{t('price')}{' '}
{formatPrice(currentPrice.amount, currentPrice.currency)} /{' '}
{currentPrice.interval === PlanIntervals.MONTH
? t('interval.month')
: currentPrice.interval === PlanIntervals.YEAR
? t('interval.year')
: t('interval.oneTime')}
</div> */}
{currentPeriodStart && ( {currentPeriodStart && (
<div className="text-muted-foreground"> <div className="text-muted-foreground">
{t('periodStartDate')} {currentPeriodStart} {t('periodStartDate')} {currentPeriodStart}
</div> </div>
)} )}
{nextBillingDate && ( {currentPeriodEnd && (
<div className="text-muted-foreground"> <div className="text-muted-foreground">
{t('nextBillingDate')} {nextBillingDate} {t('periodEndDate')} {currentPeriodEnd}
</div> </div>
)} )}
{subscription.status === 'trialing' && {subscription.status === 'trialing' && trialEndDate && (
subscription.currentPeriodEnd && ( <div className="text-amber-600">
<div className="text-amber-600"> {t('trialEnds')} {trialEndDate}
{t('trialEnds')} {formatDate(subscription.currentPeriodEnd)} </div>
</div> )}
)}
</div> </div>
)} )}
</CardContent> </CardContent>

View File

@ -35,7 +35,7 @@ export function getUrlWithLocale(url: string, locale?: Locale | null): string {
* Input: http://localhost:3000/api/auth/reset-password/token?callbackURL=/auth/reset-password * Input: http://localhost:3000/api/auth/reset-password/token?callbackURL=/auth/reset-password
* Output: http://localhost:3000/api/auth/reset-password/token?callbackURL=/zh/auth/reset-password * Output: http://localhost:3000/api/auth/reset-password/token?callbackURL=/zh/auth/reset-password
* *
* http://localhost:3000/api/auth/verify-email?token=eyJhbGciOiJIUzI1NiJ9&callbackURL=/dashboard * Input: http://localhost:3000/api/auth/verify-email?token=eyJhbGciOiJIUzI1NiJ9&callbackURL=/dashboard
* Output: http://localhost:3000/api/auth/verify-email?token=eyJhbGciOiJIUzI1NiJ9&callbackURL=/zh/dashboard * Output: http://localhost:3000/api/auth/verify-email?token=eyJhbGciOiJIUzI1NiJ9&callbackURL=/zh/dashboard
* *
* @param url - The original URL with callbackURL parameter * @param url - The original URL with callbackURL parameter