Skip to content

Commit 142575b

Browse files
committed
Illustrative demo changes.
1 parent 85d7955 commit 142575b

File tree

4 files changed

+86
-46
lines changed

4 files changed

+86
-46
lines changed

demos/react-supabase-todolist/src/app/views/todo-lists/page.tsx

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -13,11 +13,14 @@ import {
1313
} from '@mui/material';
1414
import Fab from '@mui/material/Fab';
1515
import React from 'react';
16-
import { useSupabase } from '@/components/providers/SystemProvider';
16+
import { drizzleDb, useSupabase } from '@/components/providers/SystemProvider';
1717
import { LISTS_TABLE } from '@/library/powersync/AppSchema';
1818
import { NavigationPage } from '@/components/navigation/NavigationPage';
1919
import { SearchBarWidget } from '@/components/widgets/SearchBarWidget';
2020
import { TodoListsWidget } from '@/components/widgets/TodoListsWidget';
21+
import { lists } from '@/library/powersync/DrizzleSchema';
22+
23+
import { sql } from 'drizzle-orm';
2124

2225
export default function TodoListsPage() {
2326
const powerSync = usePowerSync();
@@ -33,16 +36,13 @@ export default function TodoListsPage() {
3336
if (!userID) {
3437
throw new Error(`Could not create new lists, no userID found`);
3538
}
39+
await drizzleDb.insert(lists).values({
40+
id: sql`uuid()`,
41+
created_at: sql`datetime()`,
42+
name,
43+
owner_id: userID
44+
});
3645

37-
const res = await powerSync.execute(
38-
`INSERT INTO ${LISTS_TABLE} (id, created_at, name, owner_id) VALUES (uuid(), datetime(), ?, ?) RETURNING *`,
39-
[name, userID]
40-
);
41-
42-
const resultRecord = res.rows?.item(0);
43-
if (!resultRecord) {
44-
throw new Error('Could not create list');
45-
}
4646
};
4747

4848
return (

demos/react-supabase-todolist/src/components/providers/SystemProvider.tsx

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@ import { PowerSyncDatabase } from '@powersync/web';
77
import Logger from 'js-logger';
88
import React, { Suspense } from 'react';
99
import { NavigationPanelContextProvider } from '../navigation/NavigationPanelContext';
10+
import { wrapPowerSyncWithDrizzle } from "@powersync/drizzle-driver";
11+
import { drizzleSchema } from '@/library/powersync/DrizzleSchema';
1012

1113
const SupabaseContext = React.createContext<SupabaseConnector | null>(null);
1214
export const useSupabase = () => React.useContext(SupabaseContext);
@@ -18,6 +20,9 @@ export const db = new PowerSyncDatabase({
1820
}
1921
});
2022

23+
24+
export const drizzleDb = wrapPowerSyncWithDrizzle(db, { schema: drizzleSchema });
25+
2126
export const SystemProvider = ({ children }: { children: React.ReactNode }) => {
2227
const [connector] = React.useState(new SupabaseConnector());
2328
const [powerSync] = React.useState(db);

demos/react-supabase-todolist/src/components/widgets/TodoListsWidget.tsx

Lines changed: 23 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,13 @@ import { useNavigate } from 'react-router-dom';
44
import { ListItemWidget } from './ListItemWidget';
55
import { LISTS_TABLE, ListRecord, TODOS_TABLE } from '@/library/powersync/AppSchema';
66
import { TODO_LISTS_ROUTE } from '@/app/router';
7+
import { drizzleDb } from '../providers/SystemProvider';
8+
import { lists } from '@/library/powersync/DrizzleSchema';
9+
import { useEffect, useState } from 'react';
10+
import { CompilableQuery } from '@powersync/web';
11+
import { Query, sql } from 'drizzle-orm';
12+
import { toCompilableQuery } from '@powersync/drizzle-driver';
13+
714

815
export type TodoListsWidgetProps = {
916
selectedId?: string;
@@ -13,48 +20,28 @@ const description = (total: number, completed: number = 0) => {
1320
return `${total - completed} pending, ${completed} completed`;
1421
};
1522

23+
24+
1625
export function TodoListsWidget(props: TodoListsWidgetProps) {
17-
const powerSync = usePowerSync();
18-
const navigate = useNavigate();
19-
20-
const { data: listRecords, isLoading } = useQuery<ListRecord & { total_tasks: number; completed_tasks: number }>(`
21-
SELECT
22-
${LISTS_TABLE}.*, COUNT(${TODOS_TABLE}.id) AS total_tasks, SUM(CASE WHEN ${TODOS_TABLE}.completed = true THEN 1 ELSE 0 END) as completed_tasks
23-
FROM
24-
${LISTS_TABLE}
25-
LEFT JOIN ${TODOS_TABLE}
26-
ON ${LISTS_TABLE}.id = ${TODOS_TABLE}.list_id
27-
GROUP BY
28-
${LISTS_TABLE}.id;
29-
`);
30-
31-
const deleteList = async (id: string) => {
32-
await powerSync.writeTransaction(async (tx) => {
33-
// Delete associated todos
34-
await tx.execute(`DELETE FROM ${TODOS_TABLE} WHERE list_id = ?`, [id]);
35-
// Delete list record
36-
await tx.execute(`DELETE FROM ${LISTS_TABLE} WHERE id = ?`, [id]);
37-
});
38-
};
26+
const query = drizzleDb.select().from(lists);
27+
// const query = drizzleDb.query.lists.findMany();
28+
29+
30+
const { data: listRecords, isLoading } = useQuery(toCompilableQuery(query));
31+
3932

4033
if (isLoading) {
4134
return <div>Loading...</div>;
4235
}
4336

4437
return (
45-
<List dense={false}>
46-
{listRecords.map((r) => (
47-
<ListItemWidget
48-
key={r.id}
49-
title={r.name ?? ''}
50-
description={description(r.total_tasks, r.completed_tasks)}
51-
selected={r.id == props.selectedId}
52-
onDelete={() => deleteList(r.id)}
53-
onPress={() => {
54-
navigate(TODO_LISTS_ROUTE + '/' + r.id);
55-
}}
56-
/>
57-
))}
58-
</List>
38+
<div>
39+
<List dense={false}>
40+
{listRecords.map((r) => (
41+
<div key={r.id}>{r.id}-{r.name}</div>
42+
))}
43+
</List>
44+
</div>
45+
5946
);
6047
}
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
import { relations } from 'drizzle-orm';
2+
import { index, integer, sqliteTable, text } from 'drizzle-orm/sqlite-core';
3+
4+
export const lists = sqliteTable('lists', {
5+
id: text('id').primaryKey().notNull(),
6+
created_at: text('created_at'),
7+
name: text('name').notNull(),
8+
owner_id: text('owner_id')
9+
});
10+
11+
export const todos = sqliteTable(
12+
'todos',
13+
{
14+
id: text('id').primaryKey().notNull(),
15+
list_id: text('list_id')
16+
.notNull()
17+
.references(() => lists.id),
18+
created_at: text('created_at'),
19+
completed_at: text('completed_at'),
20+
description: text('description').notNull(),
21+
created_by: text('created_by'),
22+
completed_by: text('completed_by'),
23+
completed: integer('completed')
24+
},
25+
(todos) => ({
26+
listIdx: index('listIdx').on(todos.list_id)
27+
})
28+
);
29+
30+
// Define relations for 'lists' (one-to-many with 'todos')
31+
export const listsRelations = relations(lists, ({ many }) => ({
32+
todos: many(todos)
33+
}));
34+
35+
// Define relations for 'todos' (many-to-one with 'lists')
36+
const todosRelations = relations(todos, ({ one }) => ({
37+
list: one(lists, {
38+
fields: [todos.list_id],
39+
references: [lists.id]
40+
})
41+
}));
42+
43+
export const drizzleSchema = {
44+
lists,
45+
todos,
46+
listsRelations,
47+
todosRelations
48+
};

0 commit comments

Comments
 (0)