Update user authentication and sidebar config
This commit involves improving the user authentication process in the billing and accounts pages for better reliability. It also changes the name of 'organization-account-sidebar.config' to 'team-account-sidebar.config' for improved clarity and consistency.
This commit is contained in:
@@ -1,5 +1,3 @@
|
||||
import { redirect } from 'next/navigation';
|
||||
|
||||
import { SupabaseClient } from '@supabase/supabase-js';
|
||||
|
||||
import {
|
||||
@@ -14,23 +12,15 @@ import { Trans } from '@kit/ui/trans';
|
||||
|
||||
import { createPersonalAccountBillingPortalSession } from '~/(dashboard)/home/(user)/billing/server-actions';
|
||||
import billingConfig from '~/config/billing.config';
|
||||
import pathsConfig from '~/config/paths.config';
|
||||
import { withI18n } from '~/lib/i18n/with-i18n';
|
||||
|
||||
import { loadUserWorkspace } from '../../_lib/load-user-workspace';
|
||||
import { PersonalAccountCheckoutForm } from './_components/personal-account-checkout-form';
|
||||
|
||||
type Subscription = Database['public']['Tables']['subscriptions']['Row'];
|
||||
|
||||
async function PersonalAccountBillingPage() {
|
||||
const client = getSupabaseServerComponentClient();
|
||||
const { session } = await loadUserWorkspace();
|
||||
|
||||
if (!session?.user) {
|
||||
redirect(pathsConfig.auth.signIn);
|
||||
}
|
||||
|
||||
const [subscription, customerId] = await loadData(client, session.user.id);
|
||||
const [subscription, customerId] = await loadData(client);
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -68,18 +58,26 @@ async function PersonalAccountBillingPage() {
|
||||
|
||||
export default withI18n(PersonalAccountBillingPage);
|
||||
|
||||
function loadData(client: SupabaseClient<Database>, userId: string) {
|
||||
async function loadData(client: SupabaseClient<Database>) {
|
||||
const { data, error } = await client.auth.getUser();
|
||||
|
||||
if (error ?? !data?.user) {
|
||||
throw new Error('Authentication required');
|
||||
}
|
||||
|
||||
const user = data.user;
|
||||
|
||||
const subscription = client
|
||||
.from('subscriptions')
|
||||
.select<string, Subscription>('*')
|
||||
.eq('account_id', userId)
|
||||
.eq('account_id', user.id)
|
||||
.maybeSingle()
|
||||
.then(({ data }) => data);
|
||||
|
||||
const customer = client
|
||||
.from('billing_customers')
|
||||
.select('customer_id')
|
||||
.eq('account_id', userId)
|
||||
.eq('account_id', user.id)
|
||||
.maybeSingle()
|
||||
.then(({ data }) => data?.customer_id);
|
||||
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
import { SidebarDivider, SidebarGroup, SidebarItem } from '@kit/ui/sidebar';
|
||||
import { Trans } from '@kit/ui/trans';
|
||||
|
||||
import { getOrganizationAccountSidebarConfig } from '~/config/organization-account-sidebar.config';
|
||||
import { getOrganizationAccountSidebarConfig } from '~/config/team-account-sidebar.config';
|
||||
|
||||
export function AppSidebarNavigation({
|
||||
account,
|
||||
|
||||
@@ -24,8 +24,8 @@ import {
|
||||
import { Trans } from '@kit/ui/trans';
|
||||
|
||||
import featureFlagsConfig from '~/config/feature-flags.config';
|
||||
import { getOrganizationAccountSidebarConfig } from '~/config/organization-account-sidebar.config';
|
||||
import pathsConfig from '~/config/paths.config';
|
||||
import { getOrganizationAccountSidebarConfig } from '~/config/team-account-sidebar.config';
|
||||
|
||||
const features = {
|
||||
enableTeamAccounts: featureFlagsConfig.enableTeamAccounts,
|
||||
|
||||
@@ -1,5 +1,8 @@
|
||||
import { SupabaseClient } from '@supabase/supabase-js';
|
||||
|
||||
import { PlusCircle } from 'lucide-react';
|
||||
|
||||
import { Database } from '@kit/supabase/database';
|
||||
import { getSupabaseServerComponentClient } from '@kit/supabase/server-component-client';
|
||||
import {
|
||||
AccountInvitationsTable,
|
||||
@@ -26,9 +29,20 @@ interface Params {
|
||||
};
|
||||
}
|
||||
|
||||
async function loadAccountMembers(account: string) {
|
||||
const client = getSupabaseServerComponentClient();
|
||||
async function loadUser(client: SupabaseClient<Database>) {
|
||||
const { data, error } = await client.auth.getUser();
|
||||
|
||||
if (error) {
|
||||
throw error;
|
||||
}
|
||||
|
||||
return data.user;
|
||||
}
|
||||
|
||||
async function loadAccountMembers(
|
||||
client: SupabaseClient<Database>,
|
||||
account: string,
|
||||
) {
|
||||
const { data, error } = await client.rpc('get_account_members', {
|
||||
account_slug: account,
|
||||
});
|
||||
@@ -41,9 +55,10 @@ async function loadAccountMembers(account: string) {
|
||||
return data ?? [];
|
||||
}
|
||||
|
||||
async function loadInvitations(account: string) {
|
||||
const client = getSupabaseServerComponentClient();
|
||||
|
||||
async function loadInvitations(
|
||||
client: SupabaseClient<Database>,
|
||||
account: string,
|
||||
) {
|
||||
const { data, error } = await client.rpc('get_account_invitations', {
|
||||
account_slug: account,
|
||||
});
|
||||
@@ -56,14 +71,22 @@ async function loadInvitations(account: string) {
|
||||
return data ?? [];
|
||||
}
|
||||
|
||||
async function TeamAccountMembersPage({ params }: Params) {
|
||||
const slug = params.account;
|
||||
|
||||
const [{ account, user }, members, invitations] = await Promise.all([
|
||||
async function loadData(client: SupabaseClient<Database>, slug: string) {
|
||||
return Promise.all([
|
||||
loadTeamWorkspace(slug),
|
||||
loadAccountMembers(slug),
|
||||
loadInvitations(slug),
|
||||
loadAccountMembers(client, slug),
|
||||
loadInvitations(client, slug),
|
||||
loadUser(client),
|
||||
]);
|
||||
}
|
||||
|
||||
async function TeamAccountMembersPage({ params }: Params) {
|
||||
const client = getSupabaseServerComponentClient();
|
||||
|
||||
const [{ account }, members, invitations, user] = await loadData(
|
||||
client,
|
||||
params.account,
|
||||
);
|
||||
|
||||
const canManageRoles = account.permissions.includes('roles.manage');
|
||||
const isPrimaryOwner = account.primary_owner_user_id === user.id;
|
||||
|
||||
@@ -7,7 +7,7 @@ import pathsConfig from '~/config/paths.config';
|
||||
|
||||
const iconClasses = 'w-4';
|
||||
|
||||
const routes = (account: string) => [
|
||||
const getRoutes = (account: string) => [
|
||||
{
|
||||
label: 'common:dashboardTabLabel',
|
||||
path: pathsConfig.app.accountHome.replace('[account]', account),
|
||||
@@ -41,7 +41,7 @@ const routes = (account: string) => [
|
||||
|
||||
export function getOrganizationAccountSidebarConfig(account: string) {
|
||||
return SidebarConfigSchema.parse({
|
||||
routes: routes(account),
|
||||
routes: getRoutes(account),
|
||||
});
|
||||
}
|
||||
|
||||
@@ -9,8 +9,10 @@
|
||||
"dangerZone": "Danger Zone",
|
||||
"dangerZoneDescription": "This section contains actions that are irreversible"
|
||||
},
|
||||
"yourTeam": "Your Teams",
|
||||
"createTeam": "Create Team",
|
||||
"yourTeams": "Your Teams",
|
||||
"createTeam": "Create a Team",
|
||||
"personalAccount": "Personal Account",
|
||||
"searchAccount": "Search Account...",
|
||||
"membersTabLabel": "Members",
|
||||
"memberName": "Name",
|
||||
"youLabel": "You",
|
||||
|
||||
Reference in New Issue
Block a user