Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
96 commits
Select commit Hold shift + click to select a range
f5f3614
refactor: rename Supabase environment variables for clarity and mark …
surajair Feb 12, 2026
9c5c4c7
refactor: enhance publish dropdown with icons, labels, and conditiona…
amitdhiman5086 Feb 13, 2026
ca1508b
refactor: rename hasUnpublishedTranslationsPages to hasLanguagePages …
amitdhiman5086 Feb 13, 2026
bd5b7fe
Merge pull request #746 from chaibuilder/some-ui-tweaks
surajair Feb 13, 2026
7597362
refactor: add showDesignTokenSuggestions prop to ManualClasses
amitdhiman5086 Feb 13, 2026
cd03d77
refactor: conditionally display design tokens in manual classes place…
amitdhiman5086 Feb 13, 2026
367a180
refactor: disable dark mode flag by default in theme configuration panel
amitdhiman5086 Feb 13, 2026
ca0b47f
Merge pull request #751 from chaibuilder/dark-mode-toggle
surajair Feb 13, 2026
4d6e18b
Merge branch 'dev' into design-token-tweaks
surajair Feb 13, 2026
1768cac
Merge pull request #749 from chaibuilder/design-token-tweaks
surajair Feb 13, 2026
b10aba7
fix: 748 added support for expressions in data bindings
surajair Feb 13, 2026
50a5586
chore: replace eta with eta/core
surajair Feb 13, 2026
288b367
Initial plan
Copilot Feb 13, 2026
2a41c53
Merge check_user_access and get_role_and_permissions APIs
Copilot Feb 13, 2026
adbe23b
Remove deprecated get-role-and-permissions files
Copilot Feb 13, 2026
46b6124
Fix type inconsistencies in roleAndPermissions prop
Copilot Feb 13, 2026
0a97605
Document behavior change and improve backward compatibility
Copilot Feb 13, 2026
73ca1c7
Fix syntax error and enhance documentation
Copilot Feb 13, 2026
5ea6331
refactor: increase image picker thumbnail size from 56px to 72px
surajair Feb 13, 2026
2c8d420
fix: fetch actual role and permissions from database and parse API re…
Copilot Feb 13, 2026
a7a70a3
refactor: remove useUserRoleAndPermissions hook, use fetchAPI with ex…
Copilot Feb 13, 2026
99e771b
refactor: eliminate duplicate code in CheckUserAccessAction by reusin…
Copilot Feb 13, 2026
f240421
Merge pull request #756 from chaibuilder/copilot/merge-user-access-ro…
surajair Feb 13, 2026
96ea03f
Update src/render/binding-engine.ts
surajair Feb 13, 2026
3b8b8b0
Merge branch 'dev' into 748-expressions-support-in-data-binding
surajair Feb 13, 2026
a17299f
refactor: add ShowSetting component to block settings panel
surajair Feb 13, 2026
84569f2
Initial plan
Copilot Feb 13, 2026
53e9241
feat: remove publish with translation pages menu item
Copilot Feb 13, 2026
1e64493
chore: clean up extra blank lines
Copilot Feb 13, 2026
6237f0a
Merge pull request #758 from chaibuilder/copilot/remove-publish-trans…
surajair Feb 13, 2026
85729f5
Merge branch 'dev' into 748-expressions-support-in-data-binding
surajair Feb 13, 2026
7b994b3
Merge pull request #750 from chaibuilder/748-expressions-support-in-d…
surajair Feb 13, 2026
5413a74
Merge branch 'main' into dev
surajair Feb 13, 2026
ac27a51
refactor: consolidate website data fetching into single GET_WEBSITE_D…
amitdhiman5086 Feb 13, 2026
ceb565e
Merge branch 'dev' of github.com:chaibuilder/sdk into 752-combine-mul…
amitdhiman5086 Feb 13, 2026
e24d2cd
refactor: simplify website pages fetching to only retrieve primary la…
amitdhiman5086 Feb 13, 2026
601ab5b
Merge pull request #759 from chaibuilder/752-combine-multiple-api-cal…
surajair Feb 13, 2026
ce42823
Initial plan
Copilot Feb 13, 2026
f763031
feat: implement GET_PAGE_ALL_DATA to consolidate page data API calls
Copilot Feb 13, 2026
b4f7ddd
refactor: optimize hook architecture for page data consolidation
Copilot Feb 13, 2026
b5bf9ca
refactor: rely on React Query's built-in cache management
Copilot Feb 13, 2026
9b1ed8d
refactor: consolidate page data fetching in ChaiBuilderInner component
surajair Feb 13, 2026
1046463
Initial plan
Copilot Feb 13, 2026
6f89a00
Remove mark as template feature and related code
Copilot Feb 13, 2026
6faf30b
refactor: remove unused hooks and simplify page data fetching
surajair Feb 13, 2026
75306ab
refactor: rename useChaiCurrentPage to useChaiPrimaryPage for clarity
surajair Feb 13, 2026
ecd75c2
refactor: rename useWebsitePages to useWebsitePrimaryPages for clarity
surajair Feb 13, 2026
892ce20
refactor: rename useActivePage to useCurrentActivePage for clarity
surajair Feb 13, 2026
c453771
Restore mark as template code and hide UI elements only
Copilot Feb 15, 2026
d9ad9e1
Merge pull request #762 from chaibuilder/copilot/remove-mark-as-templ…
surajair Feb 15, 2026
c9653c8
refactor: update UI styling and layout for top bar and sidebar compon…
surajair Feb 15, 2026
6b08e85
refactor: rename currentPage to primaryPage in usePrimaryPage hook usage
surajair Feb 15, 2026
9006349
Merge branch 'dev' into copilot/merge-api-calls-page-data
surajair Feb 15, 2026
b217c46
refactor: remove mark as template props and related code from page co…
surajair Feb 15, 2026
14d200f
refactor: remove usePageDraftBlocks hook and merge functionality into…
surajair Feb 15, 2026
241ec5f
Merge pull request #760 from chaibuilder/copilot/merge-api-calls-page…
surajair Feb 15, 2026
0b8ee68
Merge remote-tracking branch 'origin/dev' into new-ui-design
surajair Feb 15, 2026
34a7631
refactor: move PagesManagerTrigger from TopbarLeft to AddressBar comp…
surajair Feb 15, 2026
08fb3a9
refactor: update topbar address bar layout and icon changes
surajair Feb 15, 2026
7e0f130
Merge remote-tracking branch 'origin/dev' into remove-dependency-on-s…
surajair Feb 15, 2026
c18b43d
refactor: update UI styling with lighter color scheme and replace icons
surajair Feb 15, 2026
28a890e
refactor: update topbar icons and remove text labels for cleaner UI
surajair Feb 15, 2026
7e7366b
refactor: replace isNull with falsy check and remove unused import
surajair Feb 15, 2026
9390fff
refactor: reorder canvas topbar elements and update dropdown icon sizing
surajair Feb 16, 2026
a621298
refactor: simplify PageDropdownInHeader and move LanguageSwitcher to …
surajair Feb 16, 2026
0e95496
refactor: add tooltips to topbar buttons and remove unused EmptyCanva…
surajair Feb 16, 2026
94b89e3
refactor: remove variant prop from LanguageSwitcher component
surajair Feb 16, 2026
8ded9af
Merge pull request #763 from chaibuilder/new-ui-design
surajair Feb 16, 2026
ead0f35
refactor: remove derived data from GetWebsiteDataAction and compute c…
amitdhiman5086 Feb 16, 2026
e1e7d2f
Update src/pages/chaibuilder-pages.tsx
amitdhiman5086 Feb 16, 2026
d296099
refactor: replace useWebsiteData with useWebsitePages in useSiteWideU…
amitdhiman5086 Feb 16, 2026
8aa9b49
Merge pull request #764 from chaibuilder/client-hooks
surajair Feb 16, 2026
b6ac850
refactor: add design token tracking and realtime query sync for page …
amitdhiman5086 Feb 17, 2026
57e96f1
Merge pull request #767 from chaibuilder/realtime-changes
surajair Feb 17, 2026
8997e0f
refactor: update topbar styling and add CanvasTopBar to demo
surajair Feb 17, 2026
c8593bc
refactor: rename ShowSetting to VisibilitySettings and add conditiona…
surajair Feb 17, 2026
98bbecf
refactor: add conditional visibility support with data binding expres…
surajair Feb 17, 2026
6d224f3
Merge branch 'dev' into conditional-visibilitu
surajair Feb 17, 2026
2990505
Merge pull request #769 from chaibuilder/conditional-visibilitu
surajair Feb 17, 2026
a2076d1
refactor: add success toast notifications for theme, design token, an…
amitdhiman5086 Feb 17, 2026
7279900
refactor: add user attribution to realtime sync toast notifications
amitdhiman5086 Feb 17, 2026
2147349
refactor: simplify theme and design token update toast messages
amitdhiman5086 Feb 17, 2026
e43743f
fix: add i18n translation support to realtime sync toast notifications
amitdhiman5086 Feb 17, 2026
d88ed89
Initial plan
Copilot Feb 17, 2026
5f0e2c4
feat: show pages using partial in delete confirmation dialog
Copilot Feb 17, 2026
2c8a1ce
refactor: update useSiteWideUsage hook to return object and remove op…
amitdhiman5086 Feb 17, 2026
924b38a
Remove toast notification for published changes
surajair Feb 17, 2026
76e22d5
refactor: remove unused parameters from handlePublishChanges function
surajair Feb 17, 2026
c3bd5b3
Merge pull request #770 from chaibuilder/toast-for-realtime
surajair Feb 17, 2026
49e4486
Merge branch 'dev' into copilot/update-delete-partial-confirmation
surajair Feb 17, 2026
7fd1936
Merge pull request #766 from chaibuilder/copilot/update-delete-partia…
surajair Feb 17, 2026
7051860
refactor: optimize currentPage lookup by checking language pages first
amitdhiman5086 Feb 18, 2026
c05c4c8
refactor: added dep
amitdhiman5086 Feb 18, 2026
4295529
Merge pull request #771 from chaibuilder/create-new-page-issue
surajair Feb 18, 2026
f16b593
refactor: update currentPage lookup to use primaryPage field for non-…
amitdhiman5086 Feb 18, 2026
92e6ccf
Merge pull request #772 from chaibuilder/lan-fix
surajair Feb 18, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions .env.sample
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
VITE_SUPABASE_URL=supabase url
VITE_SUPABASE_ANON_KEY=supabase anon key
SUPABASE_SERVICE_KEY=supabase service key
VITE_SUPABASE_PUBLISHABLE_DEFAULT_KEY=supabase anon key
SUPABASE_SECRET_KEY=supabase service key

CHAIBUILDER_APP_KEY=chai builder app id
CHAIBUILDER_DATABASE_URL=postgres database url
AI_GATEWAY_API_KEY=Vercel AI Gateway API Key
AI_GATEWAY_API_KEY=#optional Vercel AI Gateway API Key
4 changes: 2 additions & 2 deletions frameworks/nextjs/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,13 @@
"build": "npx tailwindcss -c tailwind.config.ts -i './app/(public)/public.css' -o ./public/chaistyles.css --minify && next build",
"start": "next start",
"lint": "eslint",
"preview": "opennextjs-cloudflare build && opennextjs-cloudflare preview",
"preview": "opennextjs-cloudflare preview",
"cf-build": "npx tailwindcss -c tailwind.config.ts -i './app/(public)/public.css' -o ./public/chaistyles.css --minify && opennextjs-cloudflare build",
"deploy": "opennextjs-cloudflare build && opennextjs-cloudflare deploy",
"cf-typegen": "wrangler types --env-interface CloudflareEnv cloudflare-env.d.ts"
},
"dependencies": {
"@chaibuilder/sdk": "4.0.0-beta.32",
"@chaibuilder/sdk": "link:../../",
"@opennextjs/cloudflare": "^1.16.4",
"@supabase/ssr": "^0.8.0",
"@supabase/supabase-js": "^2.90.1",
Expand Down
6,331 changes: 379 additions & 5,952 deletions frameworks/nextjs/pnpm-lock.yaml

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -185,6 +185,7 @@
"compressorjs": "^1.2.1",
"culori": "^4.0.2",
"date-fns": "^4.1.0",
"eta": "^4.5.1",
"flagged": "3.0.0",
"framer-motion": "12.23.20",
"fuse.js": "7.1.0",
Expand Down
9 changes: 9 additions & 0 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 4 additions & 2 deletions src/actions/builder/actions-registery.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@ import { GetLibraryItemsAction } from "./get-library-items";
import { GetPageRevisionsAction } from "./get-page-revisions";
import { GetPageTypesAction } from "./get-page-types";
import { GetRevisionPageAction } from "./get-revision-page";
import { GetRoleAndPermissionsAction } from "./get-role-and-permissions";
import { GetSiteWideDataAction } from "./get-site-wide-data";
import { GetTemplatesByTypeAction } from "./get-templates-by-type";
import { GetWebsitePagesAction } from "./get-website-pages";
Expand All @@ -42,6 +41,8 @@ import { UpdatePageAction } from "./update-page";
import { UpdatePageMetadataAction } from "./update-page-metadata";
import { UpdateWebsiteFieldsAction } from "./update-website-fields";
import { UpsertLibraryItemAction } from "./upsert-library-item";
import { GetWebsiteDataAction } from "./get-website-data";
import { GetPageAllDataAction } from "./get-page-all-data";

/**
* Registry of all available actions
Expand Down Expand Up @@ -102,7 +103,8 @@ class ChaiActionsRegistry {
this.register("GET_PAGE_TYPES", new GetPageTypesAction());
this.register("SEARCH_PAGE_TYPE_ITEMS", new SearchPageTypeItemsAction());
this.register("GET_DYNAMIC_PAGES", new GetDynamicPagesAction());
this.register("GET_ROLE_AND_PERMISSIONS", new GetRoleAndPermissionsAction());
this.register("GET_WEBSITE_DATA", new GetWebsiteDataAction());
this.register("GET_PAGE_ALL_DATA", new GetPageAllDataAction());
// Add more actions here as they are created
}

Expand Down
13 changes: 12 additions & 1 deletion src/actions/builder/base-action.ts
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,12 @@ export abstract class ChaiBaseAction<T = any, K = any> implements ChaiAction<T,
* Verify if the user has access to the app
* @throws ActionError if the user does not have access
*/
protected async verifyAccess(): Promise<void> {
/**
* Get user access data from the database
* @returns The user access record
* @throws ActionError if access check fails
*/
protected async getUserAccess(): Promise<any> {
if (!this.context) {
throw new ActionError("Context not set", "CONTEXT_NOT_SET", 500);
}
Expand Down Expand Up @@ -100,6 +105,12 @@ export abstract class ChaiBaseAction<T = any, K = any> implements ChaiAction<T,
if (!userAccess || userAccess.length === 0) {
throw new ActionError("User does not have access to this app", "UNAUTHORIZED", 401);
}

return userAccess[0];
}

protected async verifyAccess(): Promise<void> {
await this.getUserAccess();
}

/**
Expand Down
18 changes: 14 additions & 4 deletions src/actions/builder/check-user-access.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,23 @@
import { z } from "zod";
import { ChaiBaseAction } from "./base-action";

export class CheckUserAccessAction extends ChaiBaseAction<any, { access: boolean }> {
type CheckUserAccessResponse = {
access: boolean;
role: string;
permissions: string[] | null;
};

export class CheckUserAccessAction extends ChaiBaseAction<any, CheckUserAccessResponse> {
protected getValidationSchema() {
return z.any();
}

async execute(): Promise<{ access: boolean }> {
await this.verifyAccess();
return { access: true };
async execute(): Promise<CheckUserAccessResponse> {
const user = await this.getUserAccess();
return {
access: true,
role: user.role || "user",
permissions: (user.permissions as string[]) || null,
};
}
}
69 changes: 69 additions & 0 deletions src/actions/builder/get-page-all-data.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
import { z } from "zod";
import { ChaiBaseAction } from "./base-action";
import { GetBuilderPageDataAction } from "./get-builder-page-data";
import { GetDraftPageAction } from "./get-draft-page";
import { GetLanguagePagesAction } from "./get-language-pages";

type GetPageAllDataActionData = {
id: string;
lang: string;
pageType?: string;
pageProps?: any;
};

type GetPageAllDataActionResponse = {
draftPage: any;
builderPageData: any;
languagePages: any[];
};

/**
* Get Page All Data Action
* Consolidates GET_DRAFT_PAGE, GET_BUILDER_PAGE_DATA, and GET_LANGUAGE_PAGES into a single API call
* This reduces the number of HTTP requests and improves page load performance
*/
export class GetPageAllDataAction extends ChaiBaseAction<GetPageAllDataActionData, GetPageAllDataActionResponse> {
protected getValidationSchema() {
return z.object({
id: z.string(),
lang: z.string(),
pageType: z.string().optional(),
pageProps: z.any().optional().default({}),
});
}

async execute(data: GetPageAllDataActionData): Promise<GetPageAllDataActionResponse> {
const { id, lang, pageType, pageProps = {} } = data;

// Initialize sub-actions
const draftPageAction = new GetDraftPageAction();
const builderPageDataAction = new GetBuilderPageDataAction();
const languagePagesAction = new GetLanguagePagesAction();

// Set context on all sub-actions
if (this.context) {
draftPageAction.setContext(this.context);
builderPageDataAction.setContext(this.context);
languagePagesAction.setContext(this.context);
}

try {
// Execute all actions in parallel for optimal performance
const [draftPage, builderPageData, languagePages] = await Promise.all([
draftPageAction.execute({ id }),
builderPageDataAction.execute({ lang, pageType, pageProps }),
languagePagesAction.execute({ id }),
]);

return {
draftPage,
builderPageData,
languagePages,
};
} catch (error) {
// Re-throw with more context about which action failed
const errorMessage = error instanceof Error ? error.message : String(error);
throw new Error(`Failed to fetch page data: ${errorMessage}`);
}
}
}
29 changes: 0 additions & 29 deletions src/actions/builder/get-role-and-permissions.ts

This file was deleted.

58 changes: 58 additions & 0 deletions src/actions/builder/get-website-data.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
import { z } from "zod";
import { ChaiBaseAction } from "./base-action";
import { GetCollectionsAction } from "./get-collections";
import { GetLibrariesAction } from "./get-libraries";
import { GetPageTypesAction } from "./get-page-types";
import { GetWebsitePagesAction } from "./get-website-pages";
import { GetWebsiteSettingsAction } from "./get-website-settings";

type GetWebsiteDataActionData = Record<string, never>;

type GetWebsiteDataActionResponse = {
websiteSettings: any;
websitePages: any;
pageTypes: any;
libraries: any;
collections: any;
};

export class GetWebsiteDataAction extends ChaiBaseAction<GetWebsiteDataActionData, GetWebsiteDataActionResponse> {
protected getValidationSchema() {
return z.object({}).optional().default({});
}

async execute(): Promise<GetWebsiteDataActionResponse> {
const websiteSettingsAction = new GetWebsiteSettingsAction();
const websitePagesAction = new GetWebsitePagesAction();
const pageTypesAction = new GetPageTypesAction();
const librariesAction = new GetLibrariesAction();
const collectionsAction = new GetCollectionsAction();

// Set context on all sub-actions
if (this.context) {
websiteSettingsAction.setContext(this.context);
websitePagesAction.setContext(this.context);
pageTypesAction.setContext(this.context);
librariesAction.setContext(this.context);
collectionsAction.setContext(this.context);
}

// Execute remaining actions in parallel
// NOTE: websitePagesAction fetches only primary pages (lang = "")
const [websiteSettings, websitePages, pageTypes, libraries, collections] = await Promise.all([
websiteSettingsAction.execute({ draft: true }),
websitePagesAction.execute({ lang: "" }),
pageTypesAction.execute(),
librariesAction.execute(),
collectionsAction.execute(),
]);

return {
websiteSettings,
websitePages,
pageTypes,
libraries,
collections,
};
}
}
12 changes: 12 additions & 0 deletions src/actions/builder/get-website-pages.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,10 @@ type GetWebsitePagesActionResponse = Array<{
primaryPage?: string | null;
isTemplate: boolean;
changes: string[] | null;
lang: string;
designTokens: unknown;
links: string | null;
partialBlocks: string | null;
}>;

export class GetWebsitePagesAction extends ChaiBaseAction<GetWebsitePagesActionData, GetWebsitePagesActionResponse> {
Expand Down Expand Up @@ -59,6 +63,10 @@ export class GetWebsitePagesAction extends ChaiBaseAction<GetWebsitePagesActionD
dynamicSlugCustom: schema.appPages.dynamicSlugCustom,
primaryPage: schema.appPages.primaryPage,
changes: schema.appPages.changes,
lang: schema.appPages.lang,
designTokens: schema.appPages.designTokens,
links: schema.appPages.links,
partialBlocks: schema.appPages.partialBlocks,
})
.from(schema.appPages)
.where(and(eq(schema.appPages.app, appId), eq(schema.appPages.lang, lang))),
Expand Down Expand Up @@ -97,6 +105,10 @@ export class GetWebsitePagesAction extends ChaiBaseAction<GetWebsitePagesActionD
pageType: page.pageType ?? "page",
isTemplate: templatePageIds.has(page.id),
changes: page.changes as string[] | null,
lang: page.lang,
designTokens: page.designTokens,
links: page.links,
partialBlocks: page.partialBlocks,
}));
}
}
5 changes: 5 additions & 0 deletions src/actions/builder/get-website-settings.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ type GetWebsiteSettingsActionResponse = {
theme: any; // Making it more flexible to match database schema
appKey: string;
designTokens?: any;
appChanges?: string[];
};

export class GetWebsiteSettingsAction extends ChaiBaseAction<
Expand Down Expand Up @@ -47,6 +48,7 @@ export class GetWebsiteSettingsAction extends ChaiBaseAction<
languages: targetTable.languages,
settings: targetTable.settings,
designTokens: targetTable.designTokens,
changes: targetTable.changes,
})
.from(targetTable)
.where(eq(targetTable.id, appId))
Expand All @@ -63,6 +65,8 @@ export class GetWebsiteSettingsAction extends ChaiBaseAction<

const settings = first(config);

const appChanges = ((settings as any)?.changes ?? []) as string[];

return {
...this.getDefaultSettings(),
...settings,
Expand All @@ -72,6 +76,7 @@ export class GetWebsiteSettingsAction extends ChaiBaseAction<
theme: settings?.theme || this.getDefaultSettings().theme,
// Generate deterministic app key like the original implementation
appKey: this.generateDeterministicUuid(appId),
appChanges,
};
}

Expand Down
10 changes: 0 additions & 10 deletions src/core/components/canvas/empty-canvas.tsx

This file was deleted.

Loading
Loading