Skip to content

Commit

Permalink
working but changed websockets
Browse files Browse the repository at this point in the history
  • Loading branch information
Bit-Barron committed Nov 2, 2024
1 parent 43f949f commit bf22a81
Show file tree
Hide file tree
Showing 6 changed files with 119 additions and 79 deletions.
9 changes: 9 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -21,10 +21,19 @@ services:
- proxy
labels:
- 'traefik.enable=true'
# Main application route
- 'traefik.http.routers.youtubepedia.rule=Host(`youtubepedia.barron.agency`)'
- 'traefik.http.routers.youtubepedia.entrypoints=websecure'
- 'traefik.http.routers.youtubepedia.tls.certresolver=letsencrypt'
- 'traefik.http.services.youtubepedia.loadbalancer.server.port=3000'
# WebSocket route
- 'traefik.http.routers.youtubepedia-ws.rule=Host(`youtubepedia.barron.agency`) && PathPrefix(`/socket.io`)'
- 'traefik.http.routers.youtubepedia-ws.entrypoints=websecure'
- 'traefik.http.routers.youtubepedia-ws.tls.certresolver=letsencrypt'
- 'traefik.http.services.youtubepedia-ws.loadbalancer.server.port=3000'
# Enable WebSocket protocol
- 'traefik.http.middlewares.sio.headers.customrequestheaders.X-Forwarded-Proto=https'
- 'traefik.http.routers.youtubepedia-ws.middlewares=sio'

networks:
proxy:
Expand Down
26 changes: 14 additions & 12 deletions src/hooks.server.ts
Original file line number Diff line number Diff line change
@@ -1,22 +1,24 @@
/* eslint-disable no-var */
/* eslint-disable @typescript-eslint/no-explicit-any */
import type { Handle } from '@sveltejs/kit';
import { locale } from 'svelte-i18n';
import { lucia } from '$lib/server/auth';
import { initSocketIO } from '@/server/socket';
import { createServer } from 'http';

const httpServer = createServer();
initSocketIO(httpServer);

httpServer.listen(3001, () => {
console.log('Socket.IO server listening on port 3001');
});

let isSocketInitialized = false;
declare global {
var __socketio: import('socket.io').Server<import('socket.io').DefaultEventsMap, import('socket.io').DefaultEventsMap, import('socket.io').DefaultEventsMap, any> | null;
}

export const handle: Handle = async ({ event, resolve }) => {
if (!isSocketInitialized && event.platform?.server) {
isSocketInitialized = true;
initSocketIO(event.platform.server);
// Initialize socket.io if not already initialized
if (!global.__socketio && event.platform?.server) {
try {
console.log('Initializing Socket.IO from hooks...');
initSocketIO(event.platform.server);
console.log('Socket.IO initialization from hooks completed');
} catch (error) {
console.error('Failed to initialize Socket.IO from hooks:', error);
}
}

const lang =
Expand Down
81 changes: 44 additions & 37 deletions src/lib/server/socket.ts
Original file line number Diff line number Diff line change
@@ -1,50 +1,57 @@
/* eslint-disable no-var */
import { Server } from 'socket.io';
import type { Server as HTTPServer } from 'http';
import { dev } from '$app/environment';

let io: Server | null = null;
let initializationPromise: Promise<Server> | null = null;
// Access the global io instance
declare global {
var __socketio: Server | null;
}

export const initSocketIO = (httpServer: HTTPServer): Promise<Server> => {
if (!initializationPromise) {
initializationPromise = new Promise((resolve) => {
if (!io) {
console.log('Initializing Socket.IO server...');
io = new Server(httpServer, {
path: '/socket.io',
cors: {
origin: dev ? ['http://localhost:3000'] : ['https://youtubepedia.barron.agency'],
methods: ['GET', 'POST'],
credentials: true
},
transports: ['websocket', 'polling']
});

io.on('connection', (socket) => {
console.log('Client connected', socket.id);
export const getIO = (): Server => {
if (dev) {
// In development, use the Vite-initialized socket
if (!global.__socketio) {
throw new Error('Socket.IO not initialized yet');
}
return global.__socketio;
} else {
// In production, initialize normally
if (!global.__socketio) {
throw new Error('Socket.IO not initialized yet');
}
return global.__socketio;
}
};

const userId = socket.handshake.auth.userId;
if (userId) {
socket.join(userId);
console.log(`User ${userId} joined their room`);
}
export const initSocketIO = (httpServer: HTTPServer): void => {
if (!global.__socketio) {
console.log('Initializing Socket.IO server...');
const io = new Server(httpServer, {
path: '/socket.io',
cors: {
origin: dev ? ['http://localhost:3000'] : ['https://youtubepedia.barron.agency'],
methods: ['GET', 'POST'],
credentials: true
},
transports: ['websocket', 'polling']
});

socket.on('disconnect', () => {
console.log('Client disconnected', socket.id);
});
});
io.on('connection', (socket) => {
console.log('Client connected', socket.id);

console.log('Socket.IO server initialized successfully');
const userId = socket.handshake.auth.userId;
if (userId) {
socket.join(userId);
console.log(`User ${userId} joined their room`);
}
resolve(io);

socket.on('disconnect', () => {
console.log('Client disconnected', socket.id);
});
});
}
return initializationPromise;
};

export const getIO = (): Server => {
if (!io) {
throw new Error('Socket.IO has not been initialized');
global.__socketio = io;
console.log('Socket.IO server initialized successfully');
}
return io;
};
10 changes: 5 additions & 5 deletions src/lib/socket.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,13 @@ import { io, type Socket } from 'socket.io-client';

export const initSocket = (userId: string): Socket | null => {
if (browser) {
const socketUrl = `${window.location.protocol}//${window.location.hostname}:3001`;

const socket = io(socketUrl, {
const socket = io(window.location.origin, {
path: '/socket.io',
auth: { userId },
reconnection: true,
reconnectionDelay: 1000,
reconnectionAttempts: 5
reconnectionAttempts: 5,
transports: ['websocket', 'polling']
});

socket.on('connect', () => {
Expand All @@ -23,4 +23,4 @@ export const initSocket = (userId: string): Socket | null => {
return socket;
}
return null;
};
};
21 changes: 16 additions & 5 deletions src/routes/(main)/dashboard/chat/[id]/+page.server.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { error, fail, type Actions } from '@sveltejs/kit';
import { error, fail } from '@sveltejs/kit';
import type { PageServerLoad } from './$types';
import prisma from '@/utils/prisma';
import { getIO } from '@/server/socket';
Expand Down Expand Up @@ -67,8 +67,13 @@ export const actions = {
}
});

const io = getIO();
io.to(userId).emit('new-question', questionChat);
// Emit the question event
try {
const io = getIO();
io.to(userId).emit('new-question', questionChat);
} catch (socketError) {
console.error('Socket error (non-fatal):', socketError);
}

const response = await fetch('/api/ask', {
method: 'POST',
Expand Down Expand Up @@ -108,7 +113,13 @@ export const actions = {
}
});

io.to(userId).emit('new-answer', answerChat);
// Emit the answer event
try {
const io = getIO();
io.to(userId).emit('new-answer', answerChat);
} catch (socketError) {
console.error('Socket error for answer (non-fatal):', socketError);
}

return {
success: true,
Expand All @@ -123,4 +134,4 @@ export const actions = {
});
}
}
} satisfies Actions;
};
51 changes: 31 additions & 20 deletions vite.config.ts
Original file line number Diff line number Diff line change
@@ -1,35 +1,46 @@
/* eslint-disable @typescript-eslint/no-explicit-any */
import { sveltekit } from '@sveltejs/kit/vite';
import { defineConfig } from 'vite';
import type { ViteDevServer } from 'vite';
import { Server } from 'socket.io';
import type { ServerOptions } from 'socket.io';

let io: Server | null = null;

const webSocketServer = {
name: 'webSocketServer',
configureServer(server: ViteDevServer) {
if (!server.httpServer) return;

const io = new Server(server.httpServer, {
cors: {
origin: '*',
methods: ['GET', 'POST'],
credentials: true
}
} as Partial<ServerOptions>);

io.on('connection', (socket) => {
console.log('Client connected', socket.id);

const userId = socket.handshake.auth.userId;
if (userId) {
socket.join(userId);
console.log(`User ${userId} joined their room`);
}

socket.on('disconnect', () => {
console.log('Client disconnected', socket.id);
if (!io) {
console.log('Initializing Socket.IO server in Vite...');
io = new Server(server.httpServer, {
cors: {
origin: '*',
methods: ['GET', 'POST'],
credentials: true
}
} as Partial<ServerOptions>);

// Store the io instance on the global object for access from other files
(global as any).__socketio = io;

io.on('connection', (socket) => {
console.log('Client connected', socket.id);

const userId = socket.handshake.auth.userId;
if (userId) {
socket.join(userId);
console.log(`User ${userId} joined their room`);
}

socket.on('disconnect', () => {
console.log('Client disconnected', socket.id);
});
});
});

console.log('Socket.IO server initialized successfully in Vite');
}
}
};

Expand Down

0 comments on commit bf22a81

Please sign in to comment.