This commit is contained in:
Dobromir Popov
2024-10-02 14:26:42 +03:00
22 changed files with 911 additions and 641 deletions

View File

@ -1,15 +1,18 @@
const express = require('express')
const bodyParser = require('body-parser')
const WebSocket = require('ws')
const storage = require('node-persist')
const request = require('request')
const fs = require('fs')
const path = require('path')
const dotenv = require('dotenv')
const ollama = require('ollama')
const axios = require('axios')
const OpenAI = require('openai')
const Groq = require('groq-sdk')
const express = require('express');
const bodyParser = require('body-parser');
const WebSocket = require('ws');
const storage = require('node-persist');
const request = require('request');
const fs = require('fs');
const path = require('path');
const dotenv = require('dotenv');
const ollama = require('ollama');
const axios = require('axios');
const OpenAI = require('openai');
const Groq = require('groq-sdk');
const { PrismaClient } = require('@prisma/client');
const prisma = new PrismaClient();
// Load environment variables
dotenv.config({
@ -44,21 +47,51 @@ let queueCounter = 0
const sessions = new Map()
const chats = new Map() // Store chat rooms
// Initialize storage and load initial values
async function initStorage () {
await storage.init()
language = (await storage.getItem('language')) || language
storeRecordings =
(await storage.getItem('storeRecordings')) || storeRecordings
const storedChats = (await storage.getItem('chats')) || []
storedChats.forEach(chat => chats.set(chat.id, chat))
const storedSessions = (await storage.getItem('sessions')) || []
storedSessions.forEach(session => sessions.set(session.sessionId, session))
}
// User registration
app.post('/register', async (req, res) => {
const { username, password } = req.body;
try {
const user = await prisma.user.create({
data: { username, password: hashPassword(password) },
});
res.status(201).json({ message: 'User registered successfully', userId: user.id });
} catch (error) {
res.status(400).json({ error: 'Username already exists' });
}
});
// User login
app.post('/login', async (req, res) => {
const { username, password } = req.body;
const user = await prisma.user.findUnique({ where: { username } });
if (user && verifyPassword(password, user.password)) {
const session = await prisma.session.create({
data: { userId: user.id, lastLogin: new Date() },
});
res.json({ sessionId: session.id, userId: user.id });
} else {
res.status(401).json({ error: 'Invalid credentials' });
}
});
initStorage()
// // Initialize storage and load initial values
// async function initStorage () {
// await storage.init()
// language = (await storage.getItem('language')) || language
// storeRecordings =
// (await storage.getItem('storeRecordings')) || storeRecordings
// const storedChats = (await storage.getItem('chats')) || []
// storedChats.forEach(chat => chats.set(chat.id, chat))
// const storedSessions = (await storage.getItem('sessions')) || []
// storedSessions.forEach(session => sessions.set(session.sessionId, session))
// }
// initStorage()
// WebSocket Server
const wss = new WebSocket.Server({ port: PORT_WS })
@ -113,43 +146,56 @@ async function handleSessionId (ws) {
await storage.setItem('sessions', Array.from(sessions.values()))
}
async function handleJoin (ws, { username, language }) {
sessions.set(ws.sessionId, { username, sessionId: ws.sessionId, language })
ws.send(
JSON.stringify({
type: 'sessionId',
sessionId: ws.sessionId,
language,
storeRecordings
})
)
// Modified handleJoin function
async function handleJoin(ws, { username, language, sessionId }) {
const session = await prisma.session.update({
where: { id: sessionId },
data: { language },
include: { user: true },
});
ws.sessionId = sessionId;
ws.userId = session.userId;
ws.send(JSON.stringify({ type: 'sessionId', sessionId, language, storeRecordings }));
const userChats = await prisma.chat.findMany({
where: { participants: { some: { userId: session.userId } } },
include: { participants: true },
});
ws.send(JSON.stringify({ type: 'chats', chats: userChats }));
broadcastUserList();
}
const userChats = Array.from(chats.values()).filter(chat =>
chat.participants.includes(ws.sessionId)
)
ws.send(JSON.stringify({ type: 'chats', chats: userChats }))
broadcastUserList()
}
async function handleStartChat (ws, { users }) {
const chatId = generateChatId()
let participants = [ws.sessionId, ...users]
participants = [...new Set(participants)]
chats.set(chatId, { participants, messages: [] })
await storage.setItem('chats', Array.from(chats.values()))
notifyParticipants(participants)
broadcastUserList()
}
async function handleEnterChat (ws, { chatId }) {
const enteredChat = chats.get(chatId)
const currentSession = sessions.get(ws.sessionId)
currentSession.currentChat = chatId
if (enteredChat && enteredChat.participants.includes(ws.sessionId)) {
ws.send(JSON.stringify({ type: 'chat', chat: enteredChat }))
async function handleStartChat(ws, { users }) {
const chatId = generateChatId();
let participants = [ws.userId, ...users];
participants = [...new Set(participants)];
const chat = await prisma.chat.create({
data: {
id: chatId,
participants: {
connect: participants.map(userId => ({ id: userId })),
},
},
include: { participants: true },
});
notifyParticipants(participants);
broadcastUserList();
}
async function handleEnterChat(ws, { chatId }) {
const enteredChat = await prisma.chat.findUnique({
where: { id: chatId },
include: { participants: true, messages: true },
});
if (enteredChat && enteredChat.participants.some(p => p.id === ws.userId)) {
await prisma.session.update({
where: { id: ws.sessionId },
data: { currentChatId: chatId },
});
ws.send(JSON.stringify({ type: 'chat', chat: enteredChat }));
}
}
@ -177,35 +223,34 @@ function generateChatId () {
return Math.random().toString(36).substring(2)
}
function broadcastUserList () {
const userList = Array.from(sessions.values()).map(user => ({
username: user.username,
sessionId: user.sessionId,
currentChat: user.currentChat,
language: user.language
}))
wss.clients.forEach(client => {
if (client.readyState === WebSocket.OPEN) {
client.send(JSON.stringify({ type: 'userList', users: userList }))
}
})
}
function notifyParticipants (participants) {
participants.forEach(sessionId => {
const participantSocket = Array.from(wss.clients).find(
client => client.sessionId === sessionId
)
if (participantSocket && participantSocket.readyState === WebSocket.OPEN) {
const userChats = Array.from(chats.entries())
.filter(([id, chat]) => chat.participants.includes(sessionId))
.map(([id, chat]) => ({ id, participants: chat.participants }))
participantSocket.send(
JSON.stringify({ type: 'chats', chats: userChats })
)
}
})
async function broadcastUserList() {
const users = await prisma.session.findMany({
include: { user: true },
});
const userList = users.map(session => ({
username: session.user.username,
sessionId: session.id,
currentChat: session.currentChatId,
language: session.language,
}));
wss.clients.forEach(client => {
if (client.readyState === WebSocket.OPEN) {
client.send(JSON.stringify({ type: 'userList', users: userList }));
}
});
}
function notifyParticipants(participants) {
participants.forEach(sessionId => {
const participantSocket = Array.from(wss.clients).find(client => client.sessionId === sessionId);
if (participantSocket && participantSocket.readyState === WebSocket.OPEN) {
const userChats = Array.from(chats.entries())
.filter(([id, chat]) => chat.participants.includes(sessionId))
.map(([id, chat]) => ({ id, participants: chat.participants }));
participantSocket.send(JSON.stringify({ type: 'chats', chats: userChats }));
}
});
}
async function handleAudioData (ws, data) {