mirror of
https://github.com/SrIzan10/hctv.git
synced 2026-06-06 00:56:56 +00:00
fix: chat stuff
This commit is contained in:
@@ -1,8 +1,9 @@
|
||||
import { lucia } from '@/lib/auth';
|
||||
import { resolveUserPersonalChannel } from '@/lib/db/resolve';
|
||||
import type { WebSocket } from 'ws';
|
||||
|
||||
export async function SOCKET(
|
||||
client: import('ws').WebSocket,
|
||||
client: ExtendedWebSocket,
|
||||
request: import('http').IncomingMessage,
|
||||
server: import('ws').WebSocketServer
|
||||
) {
|
||||
@@ -19,11 +20,16 @@ export async function SOCKET(
|
||||
return;
|
||||
}
|
||||
|
||||
const url = new URL(request.url!, `http://${request.headers.host}`);
|
||||
const username = url.pathname.split('/').at(-1);
|
||||
client.targetUsername = username!;
|
||||
|
||||
client.on('message', (message) => {
|
||||
const msg = message.toString();
|
||||
server.clients.forEach((client) => {
|
||||
if (client.readyState === client.OPEN) {
|
||||
client.send(
|
||||
server.clients.forEach((c) => {
|
||||
const client = c as ExtendedWebSocket;
|
||||
if (client.readyState === client.OPEN && client.targetUsername === username) {
|
||||
c.send(
|
||||
JSON.stringify({
|
||||
user: {
|
||||
id: user.id,
|
||||
@@ -35,7 +41,7 @@ export async function SOCKET(
|
||||
);
|
||||
/* if (msg === 'BOMB') {
|
||||
for (let i = 0; i < 10000; i++) {
|
||||
client.send(JSON.stringify({
|
||||
c.send(JSON.stringify({
|
||||
user: {
|
||||
id: user.id,
|
||||
username: personalChannel.name,
|
||||
@@ -57,3 +63,7 @@ function parseCookieString(cookie: string) {
|
||||
return acc;
|
||||
}, {} as Record<string, string>);
|
||||
}
|
||||
|
||||
interface ExtendedWebSocket extends WebSocket {
|
||||
targetUsername: string;
|
||||
}
|
||||
@@ -1,71 +0,0 @@
|
||||
'use client';
|
||||
|
||||
import { useState, useRef, useEffect } from 'react';
|
||||
import { Send } from 'lucide-react';
|
||||
import { Input } from '@/components/ui/input';
|
||||
import { Button } from '@/components/ui/button';
|
||||
import { useChat } from '@livekit/components-react';
|
||||
|
||||
export default function ChatPanel() {
|
||||
const [message, setMessage] = useState('');
|
||||
const chat = useChat();
|
||||
const scrollRef = useRef<HTMLDivElement>(null);
|
||||
|
||||
// auto scroll to bottom when messages change
|
||||
useEffect(() => {
|
||||
if (scrollRef.current) {
|
||||
scrollRef.current.scrollTop = scrollRef.current.scrollHeight;
|
||||
}
|
||||
}, [chat.chatMessages]);
|
||||
|
||||
return (
|
||||
<div className="border-l flex flex-col w-[350px] min-w-[350px] h-full">
|
||||
<div ref={scrollRef} className="flex-1 p-4 overflow-y-auto flex flex-col">
|
||||
<div className="space-y-4 flex-1">
|
||||
{chat.chatMessages.map((msg, i) => {
|
||||
const splitName = msg.from?.name?.split('-');
|
||||
const name = splitName?.slice(0, -1).join('-');
|
||||
return (
|
||||
// jank asf, but works (thanks claude)
|
||||
<div key={i} className="flex space-x-2">
|
||||
<div className="font-bold shrink-0">{name}</div>
|
||||
<div
|
||||
lang="en"
|
||||
className="max-w-[calc(100%-4rem)] break-all whitespace-pre-wrap hyphens-auto"
|
||||
>
|
||||
{msg.message}
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
})}
|
||||
</div>
|
||||
</div>
|
||||
<div className="p-4 border-t">
|
||||
<div className="flex space-x-2">
|
||||
<Input
|
||||
value={message}
|
||||
onChange={(e) => setMessage(e.target.value)}
|
||||
onKeyDown={(e) => {
|
||||
if (e.key === 'Enter') {
|
||||
chat.send(message);
|
||||
setMessage('');
|
||||
}
|
||||
}}
|
||||
placeholder="Type a message"
|
||||
className="flex-1 bg-transparent focus-visible:ring-offset-0"
|
||||
/>
|
||||
<Button
|
||||
size="icon"
|
||||
className="text-black transition-colors"
|
||||
onClick={() => {
|
||||
chat.send(message);
|
||||
setMessage('');
|
||||
}}
|
||||
>
|
||||
<Send className="h-4 w-4" />
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
@@ -4,6 +4,7 @@ import { useState, useRef, useEffect } from 'react';
|
||||
import { Send } from 'lucide-react';
|
||||
import { Input } from '@/components/ui/input';
|
||||
import { Button } from '@/components/ui/button';
|
||||
import { useParams } from 'next/navigation';
|
||||
|
||||
interface User {
|
||||
id: string;
|
||||
@@ -17,13 +18,14 @@ interface ChatMessage {
|
||||
}
|
||||
|
||||
export default function ChatPanel() {
|
||||
const { username } = useParams();
|
||||
const [message, setMessage] = useState('');
|
||||
const [chatMessages, setChatMessages] = useState<ChatMessage[]>([]);
|
||||
const scrollRef = useRef<HTMLDivElement>(null);
|
||||
const socketRef = useRef<WebSocket | null>(null);
|
||||
|
||||
useEffect(() => {
|
||||
const socket = new WebSocket('ws://localhost:3000/api/stream/chat');
|
||||
const socket = new WebSocket(`/api/stream/chat/${username}`);
|
||||
socketRef.current = socket;
|
||||
|
||||
socket.onopen = () => {
|
||||
|
||||
Reference in New Issue
Block a user