Skip to content

Commit f306a7f

Browse files
authored
deployment 2025-03-13 (#405)
* Merge pull request #400 from outerbase/polyfill-random-uuid-http refactor: polyfill for random uuid for insecure http * make the dashboard header responsive (#401) * refactor: remove unneccessary file * feat: make the driver more composite (#402) * make the driver more composite * move everything to queryable interface * add support int for sqlite * supporting starbase hyperdrive * fixing starbase * fixing build error
2 parents e9eca9c + 55231dd commit f306a7f

49 files changed

Lines changed: 697 additions & 691 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

src/app/(outerbase)/local/edit-base/[baseId]/page.tsx

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -41,12 +41,11 @@ export default function LocalEditBasePage() {
4141
setValidateErrors(errors);
4242
if (Object.keys(errors).length > 0) return;
4343

44-
setLoading(true);
4544
const tmp = await updateLocalConnection(baseId, template.localTo(value));
4645
router.push(
4746
tmp?.content.driver === "sqlite-filehandler"
4847
? `/playground/client?s=${tmp?.content.id}`
49-
: `/client/s/${tmp?.content.driver ?? "turso"}?p=${tmp?.content.id}`
48+
: `/client/s/${tmp?.content.driver ?? "turso"}?p=${baseId}`
5049
);
5150
}, [template, value, router, baseId]);
5251

src/app/(outerbase)/local/hooks.tsx

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import { SavedConnectionRawLocalStorage } from "@/app/(theme)/connect/saved-connection-storage";
22
import { LocalConnectionData, LocalDashboardData, localDb } from "@/indexdb";
3+
import { generateId } from "@/lib/generate-id";
34
import parseSafeJson from "@/lib/json-safe";
45
import useSWR, { mutate } from "swr";
56

@@ -18,7 +19,7 @@ export function useLocalDashboardList() {
1819
}
1920

2021
export async function createLocalDashboard(boardName: string) {
21-
const id = crypto.randomUUID();
22+
const id = generateId();
2223
const now = Date.now();
2324

2425
const data: LocalDashboardData = {
@@ -103,7 +104,7 @@ export async function removeLocalConnection(id: string) {
103104
export async function createLocalConnection(
104105
config: SavedConnectionRawLocalStorage
105106
): Promise<LocalConnectionData> {
106-
const id = crypto.randomUUID();
107+
const id = generateId();
107108

108109
const data = {
109110
id,
@@ -133,7 +134,12 @@ export async function updateLocalConnection(
133134
};
134135

135136
await localDb.connection.put(data);
137+
136138
mutate("/connections/local");
139+
mutate("/connections/local/" + id, data, {
140+
optimisticData: data,
141+
revalidate: false,
142+
});
137143

138144
return data;
139145
}

src/app/(outerbase)/nav-layout.tsx

Lines changed: 85 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -4,86 +4,112 @@ import {
44
SidebarMenuItem,
55
SidebarMenuLoadingItem,
66
} from "@/components/sidebar-menu";
7-
import { Database, Plus } from "@phosphor-icons/react";
7+
import { cn } from "@/lib/utils";
8+
import { Database, List, Plus } from "@phosphor-icons/react";
89
import { useParams, usePathname, useRouter } from "next/navigation";
9-
import { PropsWithChildren } from "react";
10+
import { PropsWithChildren, useState } from "react";
1011
import NavigationProfile from "./nav-profile";
1112
import NavigationSigninBanner from "./nav-signin-banner";
1213
import { useSession } from "./session-provider";
1314
import { useWorkspaces } from "./workspace-provider";
1415

1516
export default function NavigationLayout({ children }: PropsWithChildren) {
1617
const router = useRouter();
18+
const [mobileToggle, setMobileToggle] = useState(false);
1719
const { session } = useSession();
1820
const { workspaces, loading: workspaceLoading } = useWorkspaces();
1921
const pathname = usePathname();
2022
const { workspaceId } = useParams<{ workspaceId?: string }>();
2123

2224
return (
23-
<div className="flex h-screen w-screen">
24-
<div className="flex w-[250px] shrink-0 flex-col overflow-hidden border-r">
25-
<div className="px-2 py-2">
25+
<div className="flex w-screen flex-col lg:h-screen lg:flex-row">
26+
<div className="bg-background sticky top-0 z-25 flex w-full shrink-0 flex-col overflow-hidden border-r-0 border-b lg:w-[250px] lg:border-r lg:border-b-0">
27+
<div className="flex items-center justify-between px-2 py-2">
2628
<NavigationProfile />
27-
</div>
28-
29-
<div className="flex flex-1 flex-col overflow-scroll border-b pb-2">
30-
<SidebarMenuHeader text="Workspace" />
31-
<SidebarMenuItem
32-
selected={pathname === "/local" || pathname === "/local-setting"}
33-
text="Local Workspace"
34-
icon={Database}
35-
href="/local"
29+
<List
30+
className="mr-2 block h-6 w-6 cursor-pointer lg:hidden"
31+
onClick={() => {
32+
setMobileToggle(!mobileToggle);
33+
}}
3634
/>
35+
</div>
3736

38-
{workspaces.map((workspace) => {
39-
return (
40-
<SidebarMenuItem
41-
key={workspace.id}
42-
text={workspace.name}
43-
icon={Database}
44-
onClick={
45-
workspace.short_name === workspaceId
46-
? undefined
47-
: () => {
48-
router.push(`/w/${workspace.short_name}`);
49-
}
50-
}
51-
selected={workspace.short_name === workspaceId}
52-
badge={
53-
!workspace.is_enterprise &&
54-
workspace.subscription.plan === "starter" ? (
55-
<span className="mr-2 rounded border border-neutral-200 bg-white px-1.5 py-0.5 text-sm font-medium text-neutral-600 dark:border-neutral-700 dark:bg-neutral-800 dark:text-neutral-200">
56-
Free
57-
</span>
58-
) : undefined
59-
}
60-
/>
61-
);
62-
})}
37+
{mobileToggle && (
38+
<div
39+
className="fixed top-0 right-0 bottom-0 left-0 z-25 backdrop-blur-md lg:hidden"
40+
onClick={() => {
41+
setMobileToggle(false);
42+
}}
43+
></div>
44+
)}
6345

64-
{workspaceLoading && (
65-
<>
66-
<SidebarMenuLoadingItem />
67-
<SidebarMenuLoadingItem />
68-
<SidebarMenuLoadingItem />
69-
</>
46+
<div
47+
className={cn(
48+
"bg-background fixed right-0 z-50 flex hidden h-screen w-2/3 flex-1 overflow-scroll border-b border-l pb-2 md:w-1/2 lg:relative lg:z-0 lg:block lg:h-auto lg:w-auto",
49+
{
50+
block: mobileToggle,
51+
}
7052
)}
53+
>
54+
<div className="flex flex-1 flex-col">
55+
<SidebarMenuHeader text="Workspace" />
56+
<SidebarMenuItem
57+
selected={pathname === "/local" || pathname === "/local-setting"}
58+
text="Local Workspace"
59+
icon={Database}
60+
href="/local"
61+
/>
7162

72-
<SidebarMenuItem
73-
text={"New Workspace"}
74-
icon={Plus}
75-
onClick={() => {
76-
if (session?.user) {
77-
router.push("/new-workspace");
78-
} else {
79-
localStorage.setItem("continue-redirect", "/new-workspace");
80-
router.push("/signin");
81-
}
82-
}}
83-
/>
84-
</div>
63+
{workspaces.map((workspace) => {
64+
return (
65+
<SidebarMenuItem
66+
key={workspace.id}
67+
text={workspace.name}
68+
icon={Database}
69+
onClick={
70+
workspace.short_name === workspaceId
71+
? undefined
72+
: () => {
73+
router.push(`/w/${workspace.short_name}`);
74+
}
75+
}
76+
selected={workspace.short_name === workspaceId}
77+
badge={
78+
!workspace.is_enterprise &&
79+
workspace.subscription.plan === "starter" ? (
80+
<span className="mr-2 rounded border border-neutral-200 bg-white px-1.5 py-0.5 text-sm font-medium text-neutral-600 dark:border-neutral-700 dark:bg-neutral-800 dark:text-neutral-200">
81+
Free
82+
</span>
83+
) : undefined
84+
}
85+
/>
86+
);
87+
})}
8588

86-
<NavigationSigninBanner />
89+
{workspaceLoading && (
90+
<>
91+
<SidebarMenuLoadingItem />
92+
<SidebarMenuLoadingItem />
93+
<SidebarMenuLoadingItem />
94+
</>
95+
)}
96+
97+
<SidebarMenuItem
98+
text={"New Workspace"}
99+
icon={Plus}
100+
onClick={() => {
101+
if (session?.user) {
102+
router.push("/new-workspace");
103+
} else {
104+
localStorage.setItem("continue-redirect", "/new-workspace");
105+
router.push("/signin");
106+
}
107+
}}
108+
/>
109+
</div>
110+
111+
<NavigationSigninBanner />
112+
</div>
87113
</div>
88114
<div className="flex min-h-screen w-full flex-col overflow-y-auto bg-neutral-50 dark:bg-neutral-950">
89115
{children}

src/app/(outerbase)/w/[workspaceId]/[baseId]/page.tsx

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,9 @@ import {
88
createPostgreSQLExtensions,
99
createSQLiteExtensions,
1010
} from "@/core/standard-extension";
11+
import MySQLLikeDriver from "@/drivers/mysql/mysql-driver";
12+
import PostgresLikeDriver from "@/drivers/postgres/postgres-driver";
13+
import { SqliteLikeBaseDriver } from "@/drivers/sqlite-base-driver";
1114
import DataCatalogExtension from "@/extensions/data-catalog";
1215
import OuterbaseExtension from "@/extensions/outerbase";
1316
import {
@@ -17,9 +20,7 @@ import {
1720
import { OuterbaseAPIBaseCredential } from "@/outerbase-cloud/api-type";
1821
import { getOuterbaseBaseCredential } from "@/outerbase-cloud/api-workspace";
1922
import DataCatalogOuterbaseDriver from "@/outerbase-cloud/data-catalog-driver";
20-
import { OuterbaseMySQLDriver } from "@/outerbase-cloud/database/mysql";
21-
import { OuterbasePostgresDriver } from "@/outerbase-cloud/database/postgresql";
22-
import { OuterbaseSqliteDriver } from "@/outerbase-cloud/database/sqlite";
23+
import { OuterbaseQueryable } from "@/outerbase-cloud/database/query";
2324
import OuterbaseQueryDriver from "@/outerbase-cloud/query-driver";
2425
import { useParams } from "next/navigation";
2526
import { useEffect, useMemo, useState } from "react";
@@ -74,15 +75,18 @@ export default function OuterbaseSourcePage() {
7475

7576
if (dialect === "postgres") {
7677
return [
77-
new OuterbasePostgresDriver(outerbaseConfig),
78+
new PostgresLikeDriver(new OuterbaseQueryable(outerbaseConfig)),
7879
new StudioExtensionManager([
7980
...createPostgreSQLExtensions(),
8081
...outerbaseSpecifiedDrivers,
8182
]),
8283
];
8384
} else if (dialect === "mysql") {
8485
return [
85-
new OuterbaseMySQLDriver(outerbaseConfig, credential.database),
86+
new MySQLLikeDriver(
87+
new OuterbaseQueryable(outerbaseConfig),
88+
credential.database
89+
),
8690
new StudioExtensionManager([
8791
...createMySQLExtensions(),
8892
...outerbaseSpecifiedDrivers,
@@ -91,7 +95,7 @@ export default function OuterbaseSourcePage() {
9195
}
9296

9397
return [
94-
new OuterbaseSqliteDriver(outerbaseConfig),
98+
new SqliteLikeBaseDriver(new OuterbaseQueryable(outerbaseConfig)),
9599
new StudioExtensionManager([
96100
...createSQLiteExtensions(),
97101
...outerbaseSpecifiedDrivers,

0 commit comments

Comments
 (0)