Skip to content

Commit a94bba5

Browse files
authored
Merge pull request #17 from SilverCore-Git/new/ws
New/ws
2 parents 1988da3 + 482019e commit a94bba5

9 files changed

Lines changed: 269 additions & 27 deletions

File tree

.env.example

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ GOOGLE_API_KEY=key
1818

1919
CLERK_PUBLISHABLE_KEY=key
2020
CLERK_SECRET_KEY=key
21+
CLERK_JWT_KEY=key
2122

2223
MCP_SERVER_PATH=./src/mcp-server/index.js
2324

src/app.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,2 @@
11
import './express.js';
2-
import './ws.js';
2+
import './wsocket/ws.js';

src/routes/api.ai.ts

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,17 @@ router.post('/create', verify_auth, async (req: Request, res: Response) => {
4141
const mcpService = getMCPService();
4242
await mcpService.ensureConnected();
4343

44+
const existingSession = chats.find(chat => chat.userID === user.id);
45+
46+
if (existingSession)
47+
{
48+
res.json({
49+
success: true,
50+
session: existingSession,
51+
mcpConnected: mcpService.isConnected()
52+
});
53+
}
54+
4455
const session: Chat = {
4556
uuid: randomUUID(),
4657
userID: user.id,

src/ws.ts renamed to src/wsocket/routes/collaboration.ts

Lines changed: 8 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,11 @@
1-
import { Server } from "socket.io";
2-
import { createServer } from 'http';
1+
import { Server, Socket } from "socket.io";
2+
import notes from "../../assets/ts/notes.js";
3+
import { Note } from "../../assets/ts/types.js";
34
import * as Y from "yjs";
45
import * as awarenessProtocol from "y-protocols/awareness";
5-
import fs from 'fs';
6-
import path from 'path';
7-
import __dirname from "./assets/ts/_dirname.js";
8-
const config = JSON.parse(fs.readFileSync(path.join(__dirname, '../../config.json'), 'utf-8'))
9-
import notes from "./assets/ts/notes.js";
10-
import { Note } from "./assets/ts/types.js";
11-
import Share from "./assets/ts/db/share/Share.js";
6+
import Share from "../../assets/ts/db/share/Share.js";
7+
128

13-
const httpServer = createServer();
149

1510
const save_note = async (note: Note): Promise<void> => {
1611
await notes.updateNote({
@@ -26,12 +21,6 @@ const get_note = async (uuid: string): Promise<Note | undefined> => {
2621
}
2722

2823

29-
const io = new Server(httpServer, {
30-
cors: { origin: config.corsOptions.origin },
31-
path: "/socket.io/share",
32-
transports: ["websocket", "polling"]
33-
});
34-
3524
const docs = new Map<string, {
3625
ydoc: Y.Doc,
3726
awareness: awarenessProtocol.Awareness,
@@ -40,11 +29,10 @@ const docs = new Map<string, {
4029
icon: string
4130
}>();
4231

43-
io.on("connection", (socket) => {
4432

45-
console.log("Client connected :", socket.id);
4633

47-
// Stocker la room du socket pour l'utiliser dans les autres événements
34+
export default (io: Server, socket: Socket) => {
35+
4836
let currentRoom: string | null = null;
4937

5038
socket.on("join-room", async ({ room, userId }: { room: string, userId: string }) => {
@@ -263,10 +251,4 @@ io.on("connection", (socket) => {
263251
console.log("Client disconnected:", socket.id);
264252
});
265253

266-
});
267-
268-
console.log("Socket.IO server running...");
269-
270-
httpServer.listen('3434', () => {
271-
console.log(`Serveur WebSocket sur le port 3434`);
272-
});
254+
};

src/wsocket/routes/index.ts

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
import collaboration from "./collaboration.js";
2+
import user from "./user.js";
3+
import notes from "./notes.js";
4+
import tags from "./tags.js";
5+
6+
7+
export default [
8+
collaboration,
9+
user,
10+
notes,
11+
tags
12+
]

src/wsocket/routes/notes.ts

Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
import { Server, Socket } from "socket.io";
2+
import type { Note } from "../../assets/ts/types.js";
3+
import notes from "../../assets/ts/notes.js";
4+
5+
6+
export default (io: Server, socket: Socket) => {
7+
8+
socket.on('note:create', async (note: Note) => {
9+
10+
const userId = socket.data.userId;
11+
12+
if (note.user_id !== userId)
13+
{
14+
socket.emit('error', 'Unauthorized');
15+
return;
16+
}
17+
18+
const res = await notes.createNote(note);
19+
20+
if (res.error)
21+
{
22+
socket.emit('error', res.error);
23+
return;
24+
}
25+
26+
socket.to(`user:${userId}`).emit('note:create', res.note);
27+
28+
})
29+
30+
socket.on('note:update', async (note: Note) => {
31+
32+
const userId = socket.data.userId;
33+
34+
if (note.user_id !== userId)
35+
{
36+
socket.emit('error', 'Unauthorized');
37+
return;
38+
}
39+
40+
const res = await notes.updateNote(note);
41+
42+
if (res.error)
43+
{
44+
socket.emit('error', res.error);
45+
return;
46+
}
47+
48+
socket.to(`user:${userId}`).emit('note:update', note);
49+
50+
})
51+
52+
socket.on('note:delete', async (note: Note) => {
53+
54+
const userId = socket.data.userId;
55+
56+
if (note.user_id !== userId)
57+
{
58+
socket.emit('error', 'Unauthorized');
59+
return;
60+
}
61+
62+
const res = await notes.deleteNoteByUUID(note.user_id, note.uuid!);
63+
64+
if (res.error)
65+
{
66+
socket.emit('error', res.error);
67+
return;
68+
}
69+
70+
socket.to(`user:${userId}`).emit('note:delete', note);
71+
72+
})
73+
74+
};

src/wsocket/routes/tags.ts

Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
import { Server, Socket } from "socket.io";
2+
import type { Tag } from "../../assets/ts/types.js";
3+
import tags from "../../assets/ts/tags.js";
4+
5+
6+
export default (io: Server, socket: Socket) => {
7+
8+
socket.on('tag:create', async (tag: Tag) => {
9+
10+
const userId = socket.data.userId;
11+
12+
if (tag.user_id !== userId)
13+
{
14+
socket.emit('error', 'Unauthorized');
15+
return;
16+
}
17+
18+
const res = await tags.createTag(tag);
19+
20+
if (res.error)
21+
{
22+
socket.emit('error', res.error);
23+
return;
24+
}
25+
26+
socket.to(`user:${userId}`).emit('tag:create', res.tag);
27+
28+
})
29+
30+
socket.on('tag:update', async (tag: Tag) => {
31+
32+
const userId = socket.data.userId;
33+
34+
if (tag.user_id !== userId)
35+
{
36+
socket.emit('error', 'Unauthorized');
37+
return;
38+
}
39+
40+
const res = await tags.updateTag(tag);
41+
42+
if (res.error)
43+
{
44+
socket.emit('error', res.error);
45+
return;
46+
}
47+
48+
socket.to(`user:${userId}`).emit('tag:update', res.tag);
49+
50+
})
51+
52+
socket.on('tag:delete', async (tag: Tag) => {
53+
54+
const userId = socket.data.userId;
55+
56+
if (tag.user_id !== userId)
57+
{
58+
socket.emit('error', 'Unauthorized');
59+
return;
60+
}
61+
62+
const res = await tags.deleteTagByUUID(tag.user_id!, tag.uuid!);
63+
64+
if (res.error)
65+
{
66+
socket.emit('error', res.error);
67+
return;
68+
}
69+
70+
socket.to(`user:${userId}`).emit('tag:delete', tag);
71+
72+
})
73+
74+
};

src/wsocket/routes/user.ts

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
import { Server, Socket } from "socket.io";
2+
3+
4+
export default (io: Server, socket: Socket) => {
5+
6+
socket.on('user-connect', () => {
7+
8+
const userId = socket.data.userId;
9+
10+
socket.join(`user:${userId}`);
11+
12+
console.log(`[WS] User ${userId} joined silvernote socket.`);
13+
14+
})
15+
16+
socket.on('disconnect', () => {
17+
18+
const userId = socket.data.userId;
19+
20+
socket.leave(`user:${userId}`);
21+
22+
console.log(`[WS] User ${userId} left silvernote socket.`);
23+
24+
})
25+
26+
};

src/wsocket/ws.ts

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
import { Server } from "socket.io";
2+
import { createServer } from 'http';
3+
import fs from 'fs';
4+
import path from 'path';
5+
import __dirname from "../assets/ts/_dirname.js";
6+
const config = JSON.parse(fs.readFileSync(path.join(__dirname, '../../config.json'), 'utf-8'))
7+
import routes from "./routes/index.js";
8+
import { verifyToken } from "@clerk/express";
9+
10+
const httpServer = createServer();
11+
12+
13+
const io = new Server(httpServer, {
14+
cors: { origin: config.corsOptions.origin },
15+
path: "/socket",
16+
transports: ["websocket", "polling"]
17+
});
18+
19+
20+
io.use(async (socket, next) => {
21+
22+
const token = socket.handshake.auth.token; // on client in socket init
23+
24+
if (!token)
25+
{
26+
return next(new Error("Unauthorized: No token provided"));
27+
}
28+
29+
try {
30+
31+
const sessionClaims = await verifyToken(token, {
32+
jwtKey: process.env.CLERK_JWT_KEY as string
33+
});
34+
35+
socket.data.userId = sessionClaims.sub;
36+
37+
next();
38+
39+
}
40+
catch (error)
41+
{
42+
console.error("Erreur d'auth Socket.io :", error);
43+
next(new Error("Unauthorized: Invalid token"));
44+
}
45+
46+
});
47+
48+
io.on("connection", (socket) => {
49+
50+
routes.forEach((registerRoutes) => {
51+
registerRoutes(io, socket);
52+
});
53+
54+
});
55+
56+
57+
58+
console.log("Socket.IO server running...");
59+
60+
httpServer.listen('3434', () => {
61+
console.log(`Serveur WebSocket sur le port 3434`);
62+
});

0 commit comments

Comments
 (0)