Commit
•
0bfcf81
1
Parent(s):
c878a7d
✨ Can chat in shared convo (#55)
Browse files- package-lock.json +10 -1
- package.json +2 -1
- src/lib/types/Conversation.ts +4 -0
- src/routes/conversation/+server.ts +31 -3
- src/routes/conversation/[id]/+page.svelte +1 -3
- src/routes/r/[id]/+page.svelte +37 -1
package-lock.json
CHANGED
@@ -18,7 +18,8 @@
|
|
18 |
"nanoid": "^4.0.2",
|
19 |
"postcss": "^8.4.21",
|
20 |
"tailwind-scrollbar": "^3.0.0",
|
21 |
-
"tailwindcss": "^3.3.1"
|
|
|
22 |
},
|
23 |
"devDependencies": {
|
24 |
"@iconify-json/carbon": "^1.1.16",
|
@@ -4138,6 +4139,14 @@
|
|
4138 |
"funding": {
|
4139 |
"url": "https://github.com/sponsors/sindresorhus"
|
4140 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
4141 |
}
|
4142 |
}
|
4143 |
}
|
|
|
18 |
"nanoid": "^4.0.2",
|
19 |
"postcss": "^8.4.21",
|
20 |
"tailwind-scrollbar": "^3.0.0",
|
21 |
+
"tailwindcss": "^3.3.1",
|
22 |
+
"zod": "^3.21.4"
|
23 |
},
|
24 |
"devDependencies": {
|
25 |
"@iconify-json/carbon": "^1.1.16",
|
|
|
4139 |
"funding": {
|
4140 |
"url": "https://github.com/sponsors/sindresorhus"
|
4141 |
}
|
4142 |
+
},
|
4143 |
+
"node_modules/zod": {
|
4144 |
+
"version": "3.21.4",
|
4145 |
+
"resolved": "https://registry.npmjs.org/zod/-/zod-3.21.4.tgz",
|
4146 |
+
"integrity": "sha512-m46AKbrzKVzOzs/DZgVnG5H55N1sv1M8qZU3A8RIKbs3mrACDNeIOeilDymVb2HdmP8uwshOCF4uJ8uM9rCqJw==",
|
4147 |
+
"funding": {
|
4148 |
+
"url": "https://github.com/sponsors/colinhacks"
|
4149 |
+
}
|
4150 |
}
|
4151 |
}
|
4152 |
}
|
package.json
CHANGED
@@ -43,6 +43,7 @@
|
|
43 |
"nanoid": "^4.0.2",
|
44 |
"postcss": "^8.4.21",
|
45 |
"tailwind-scrollbar": "^3.0.0",
|
46 |
-
"tailwindcss": "^3.3.1"
|
|
|
47 |
}
|
48 |
}
|
|
|
43 |
"nanoid": "^4.0.2",
|
44 |
"postcss": "^8.4.21",
|
45 |
"tailwind-scrollbar": "^3.0.0",
|
46 |
+
"tailwindcss": "^3.3.1",
|
47 |
+
"zod": "^3.21.4"
|
48 |
}
|
49 |
}
|
src/lib/types/Conversation.ts
CHANGED
@@ -12,4 +12,8 @@ export interface Conversation {
|
|
12 |
|
13 |
createdAt: Date;
|
14 |
updatedAt: Date;
|
|
|
|
|
|
|
|
|
15 |
}
|
|
|
12 |
|
13 |
createdAt: Date;
|
14 |
updatedAt: Date;
|
15 |
+
|
16 |
+
meta?: {
|
17 |
+
fromShareId?: string;
|
18 |
+
};
|
19 |
}
|
src/routes/conversation/+server.ts
CHANGED
@@ -1,19 +1,47 @@
|
|
1 |
import type { RequestHandler } from "./$types";
|
2 |
import { collections } from "$lib/server/database";
|
3 |
import { ObjectId } from "mongodb";
|
4 |
-
import { redirect } from "@sveltejs/kit";
|
5 |
import { base } from "$app/paths";
|
|
|
|
|
6 |
|
7 |
export const POST: RequestHandler = async (input) => {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
8 |
const res = await collections.conversations.insertOne({
|
9 |
_id: new ObjectId(),
|
10 |
title:
|
|
|
11 |
"Untitled " +
|
12 |
-
|
13 |
-
|
|
|
14 |
createdAt: new Date(),
|
15 |
updatedAt: new Date(),
|
16 |
sessionId: input.locals.sessionId,
|
|
|
17 |
});
|
18 |
|
19 |
return new Response(
|
|
|
1 |
import type { RequestHandler } from "./$types";
|
2 |
import { collections } from "$lib/server/database";
|
3 |
import { ObjectId } from "mongodb";
|
4 |
+
import { error, redirect } from "@sveltejs/kit";
|
5 |
import { base } from "$app/paths";
|
6 |
+
import { z } from "zod";
|
7 |
+
import type { Message } from "$lib/types/Message";
|
8 |
|
9 |
export const POST: RequestHandler = async (input) => {
|
10 |
+
const body = await input.request.text();
|
11 |
+
|
12 |
+
let title = "";
|
13 |
+
let messages: Message[] = [];
|
14 |
+
let fromShareId: string | undefined;
|
15 |
+
|
16 |
+
if (body) {
|
17 |
+
fromShareId = z.object({ fromShare: z.string().optional() }).parse(JSON.parse(body)).fromShare;
|
18 |
+
|
19 |
+
if (fromShareId) {
|
20 |
+
const conversation = await collections.sharedConversations.findOne({
|
21 |
+
_id: fromShareId,
|
22 |
+
});
|
23 |
+
|
24 |
+
if (!conversation) {
|
25 |
+
throw error(404, "Conversation not found");
|
26 |
+
}
|
27 |
+
|
28 |
+
title = conversation.title;
|
29 |
+
messages = conversation.messages;
|
30 |
+
}
|
31 |
+
}
|
32 |
+
|
33 |
const res = await collections.conversations.insertOne({
|
34 |
_id: new ObjectId(),
|
35 |
title:
|
36 |
+
title ||
|
37 |
"Untitled " +
|
38 |
+
((await collections.conversations.countDocuments({ sessionId: input.locals.sessionId })) +
|
39 |
+
1),
|
40 |
+
messages,
|
41 |
createdAt: new Date(),
|
42 |
updatedAt: new Date(),
|
43 |
sessionId: input.locals.sessionId,
|
44 |
+
...(fromShareId ? { meta: { fromShareId } } : {}),
|
45 |
});
|
46 |
|
47 |
return new Response(
|
src/routes/conversation/[id]/+page.svelte
CHANGED
@@ -81,9 +81,7 @@
|
|
81 |
const val = $pendingMessage;
|
82 |
$pendingMessage = "";
|
83 |
|
84 |
-
|
85 |
-
writeMessage(val);
|
86 |
-
}
|
87 |
}
|
88 |
});
|
89 |
</script>
|
|
|
81 |
const val = $pendingMessage;
|
82 |
$pendingMessage = "";
|
83 |
|
84 |
+
writeMessage(val);
|
|
|
|
|
85 |
}
|
86 |
});
|
87 |
</script>
|
src/routes/r/[id]/+page.svelte
CHANGED
@@ -1,8 +1,44 @@
|
|
1 |
<script lang="ts">
|
|
|
|
|
|
|
2 |
import ChatWindow from "$lib/components/chat/ChatWindow.svelte";
|
|
|
3 |
import type { PageData } from "./$types";
|
4 |
|
5 |
export let data: PageData;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
6 |
</script>
|
7 |
|
8 |
-
<ChatWindow
|
|
|
1 |
<script lang="ts">
|
2 |
+
import { goto } from "$app/navigation";
|
3 |
+
import { base } from "$app/paths";
|
4 |
+
import { page } from "$app/stores";
|
5 |
import ChatWindow from "$lib/components/chat/ChatWindow.svelte";
|
6 |
+
import { pendingMessage } from "$lib/stores/pendingMessage";
|
7 |
import type { PageData } from "./$types";
|
8 |
|
9 |
export let data: PageData;
|
10 |
+
|
11 |
+
let loading = false;
|
12 |
+
|
13 |
+
async function createConversation(message: string) {
|
14 |
+
try {
|
15 |
+
loading = true;
|
16 |
+
const res = await fetch(`${base}/conversation`, {
|
17 |
+
method: "POST",
|
18 |
+
headers: {
|
19 |
+
"Content-Type": "application/json",
|
20 |
+
},
|
21 |
+
body: JSON.stringify({
|
22 |
+
fromShare: $page.params.id,
|
23 |
+
}),
|
24 |
+
});
|
25 |
+
|
26 |
+
if (!res.ok) {
|
27 |
+
alert("Error while creating conversation: " + (await res.text()));
|
28 |
+
return;
|
29 |
+
}
|
30 |
+
|
31 |
+
const { conversationId } = await res.json();
|
32 |
+
|
33 |
+
// Ugly hack to use a store as temp storage, feel free to improve ^^
|
34 |
+
pendingMessage.set(message);
|
35 |
+
|
36 |
+
// invalidateAll to update list of conversations
|
37 |
+
await goto(`${base}/conversation/${conversationId}`, { invalidateAll: true });
|
38 |
+
} finally {
|
39 |
+
loading = false;
|
40 |
+
}
|
41 |
+
}
|
42 |
</script>
|
43 |
|
44 |
+
<ChatWindow on:message={(ev) => createConversation(ev.detail)} messages={data.messages} {loading} />
|