Hey the chat works now a bit.
This commit is contained in:
parent
03c51e7dbe
commit
9e1ecbbe1f
@ -1,14 +0,0 @@
|
|||||||
import m from "mithril";
|
|
||||||
import { MessageBox } from "./MessageBox";
|
|
||||||
import { LoginForm } from "./Login";
|
|
||||||
|
|
||||||
export function createChatApp({ ws, session }) {
|
|
||||||
return {
|
|
||||||
view: function () {
|
|
||||||
return m("div", { class: "container" }, [
|
|
||||||
m("h1", "A Stupid Chat Application"),
|
|
||||||
m(LoginForm)
|
|
||||||
]);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
}
|
|
@ -1,37 +0,0 @@
|
|||||||
import m from "mithril";
|
|
||||||
import Cookies from "js-cookie";
|
|
||||||
|
|
||||||
export function LoginForm() {
|
|
||||||
let loggedIn = false;
|
|
||||||
|
|
||||||
async function login(e) {
|
|
||||||
e.preventDefault();
|
|
||||||
|
|
||||||
const formData = new FormData(e.target);
|
|
||||||
|
|
||||||
const res = await m.request({
|
|
||||||
method: "POST",
|
|
||||||
url: "/login",
|
|
||||||
body: formData
|
|
||||||
});
|
|
||||||
|
|
||||||
if (res.success) {
|
|
||||||
Cookies.set('logged-in', true);
|
|
||||||
} else {
|
|
||||||
Cookies.remove('logged-in');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return {
|
|
||||||
oninit: function() {
|
|
||||||
loggedIn = !!Cookies.get('logged-in');
|
|
||||||
},
|
|
||||||
view: function() {
|
|
||||||
return m("form", { action: "/login", method: "post", onsubmit: login }, [
|
|
||||||
m("label", { for: "username" }, "Username"),
|
|
||||||
m("input", { type: "text", name: "username" }),
|
|
||||||
m("input", { type: "submit", value: "Login" })
|
|
||||||
]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,7 +0,0 @@
|
|||||||
import m from "mithril";
|
|
||||||
|
|
||||||
export const MessageBox = {
|
|
||||||
view: function () {
|
|
||||||
return m("div", { id: "message-box" }, "Do Something");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,10 +1,62 @@
|
|||||||
import m from "mithril";
|
import m from "mithril";
|
||||||
import { createChatApp } from "./components/ChatApp";
|
|
||||||
import { createWebSocket } from "./websocket";
|
import { createWebSocket } from "./websocket";
|
||||||
import { Sessions } from "./session";
|
|
||||||
|
|
||||||
// open the WS to the server
|
// on new message event, call m.redraw();
|
||||||
const ws = createWebSocket();
|
const messages = [];
|
||||||
const session = new Sessions();
|
const socket = createWebSocket();
|
||||||
const ChatApp = createChatApp({ ws, session });
|
|
||||||
m.mount(document.getElementById("app"), ChatApp);
|
socket.onmessage = function (event) {
|
||||||
|
if (event.type === "message") {
|
||||||
|
const message = JSON.parse(event.data);
|
||||||
|
messages.push(message);
|
||||||
|
m.redraw();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function newMessageText(name, message) {
|
||||||
|
return `${name}: ${message}`;
|
||||||
|
}
|
||||||
|
|
||||||
|
const MessageBox = {
|
||||||
|
view: function () {
|
||||||
|
return m(".messages", messages.map(function(message) {
|
||||||
|
return m(".message", newMessageText(message.chatter, message.message));
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
function sendMessage(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
const form = new FormData(e.target);
|
||||||
|
|
||||||
|
const message = {};
|
||||||
|
|
||||||
|
for (const [key, value] of form.entries()) {
|
||||||
|
message[key] = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
socket.send(JSON.stringify(message));
|
||||||
|
}
|
||||||
|
|
||||||
|
const MessageInput = {
|
||||||
|
view: function () {
|
||||||
|
return m("div", [
|
||||||
|
m("form", { method: "post", onsubmit: sendMessage }, [
|
||||||
|
m("input", { name: "chatter", placeholder: "Name" }),
|
||||||
|
m("input", { name: "message", placeholder: "Message" }),
|
||||||
|
m("input", { type: "submit", value: "Send" })
|
||||||
|
])
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
const Chat = {
|
||||||
|
view: function(vnode) {
|
||||||
|
return m("div", [
|
||||||
|
m(MessageBox),
|
||||||
|
m(MessageInput)
|
||||||
|
])
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
m.mount(document.getElementById("app"), Chat);
|
||||||
|
14
chat-app/frontend/login.js
Normal file
14
chat-app/frontend/login.js
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
import m from 'mithril';
|
||||||
|
|
||||||
|
// login to the server
|
||||||
|
function login(e) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
export const Login = {
|
||||||
|
return m("form", { action: "/login", method: "post", onsubmit: login }, [
|
||||||
|
m("label", { for: "username" }, "Username"),
|
||||||
|
m("input", { type: "text", name: "username" }),
|
||||||
|
m("input", { type: "submit", value: "Login" })
|
||||||
|
]);
|
||||||
|
};
|
@ -1,31 +0,0 @@
|
|||||||
export class Sessions extends EventManager {
|
|
||||||
constructor() {
|
|
||||||
this.users = [];
|
|
||||||
}
|
|
||||||
|
|
||||||
userExists(user) {
|
|
||||||
return !!this.findUser(user);
|
|
||||||
}
|
|
||||||
|
|
||||||
findUser(user) {
|
|
||||||
return this.users.find(u => u.username === user.username);
|
|
||||||
}
|
|
||||||
|
|
||||||
addUser(user) {
|
|
||||||
if (!this.userExists(user)) {
|
|
||||||
this.users.push(user);
|
|
||||||
this.emit('user-logged-in', user);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
clearUser(user) {
|
|
||||||
if (this.userExists(user)) {
|
|
||||||
const index = this.users.indexOf(user);
|
|
||||||
|
|
||||||
if (index > -1) {
|
|
||||||
this.users.splice(index - 1, 1);
|
|
||||||
this.emit('user-removed', user);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
2
chat-app/frontend/state.js
Normal file
2
chat-app/frontend/state.js
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
const state = {};
|
||||||
|
|
@ -2,7 +2,7 @@
|
|||||||
"name": "chat-app",
|
"name": "chat-app",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"dev": "bun run --hot src/index.ts",
|
"dev": "bun run --hot src/index.ts",
|
||||||
"build": "rm -r static/js && bun build.ts"
|
"build": "rm -r static/js; bun build.ts"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@types/mithril": "^2.2.7",
|
"@types/mithril": "^2.2.7",
|
||||||
|
@ -8,8 +8,8 @@ export const chatters = new Array<Chatter>();
|
|||||||
|
|
||||||
export type Message = {
|
export type Message = {
|
||||||
message: string,
|
message: string,
|
||||||
timestamp: Date
|
timestamp: Date,
|
||||||
chatter: Chatter
|
chatter: string,
|
||||||
};
|
};
|
||||||
|
|
||||||
export function createMessageString(message: Message): string {
|
export function createMessageString(message: Message): string {
|
||||||
@ -21,7 +21,7 @@ export class ChatRoom extends EventEmitter {
|
|||||||
|
|
||||||
public constructor() {
|
public constructor() {
|
||||||
super();
|
super();
|
||||||
this.message = new Array<Message>();
|
this.messages = new Array<Message>();
|
||||||
}
|
}
|
||||||
|
|
||||||
public getMessages(): Message[] {
|
public getMessages(): Message[] {
|
||||||
|
@ -4,12 +4,10 @@ import type { ServerWebSocket } from "hono";
|
|||||||
import {
|
import {
|
||||||
chatRoom,
|
chatRoom,
|
||||||
createMessageString,
|
createMessageString,
|
||||||
type Chatter,
|
|
||||||
type Message
|
type Message
|
||||||
} from "./chat-room.ts";
|
} from "./chat-room.ts";
|
||||||
|
|
||||||
const app = new Hono();
|
const app = new Hono();
|
||||||
const users: string[] = [];
|
|
||||||
|
|
||||||
// Set up the chat socket
|
// Set up the chat socket
|
||||||
const { upgradeWebSocket, websocket } = createBunWebSocket<ServerWebSocket>();
|
const { upgradeWebSocket, websocket } = createBunWebSocket<ServerWebSocket>();
|
||||||
@ -19,22 +17,15 @@ app.get("/chat-service", upgradeWebSocket((c) => {
|
|||||||
chatRoom.addListener('message-added', function (e) {
|
chatRoom.addListener('message-added', function (e) {
|
||||||
ws.send(JSON.stringify({
|
ws.send(JSON.stringify({
|
||||||
message: e.message.message,
|
message: e.message.message,
|
||||||
chatter: e.message.chatter
|
chatter: e.message.chatter,
|
||||||
|
timestamp: e.message.timestamp
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
onMessage(event, ws) {
|
onMessage(event, ws) {
|
||||||
const data = JSON.parse(event.data);
|
const { data } = event;
|
||||||
|
const message = JSON.parse(data);
|
||||||
if (!chatters.find(c => c.name == data.chatter.name)) {
|
message.timestamp = Date.now() as string;
|
||||||
chatters.push(data.chatter);
|
|
||||||
}
|
|
||||||
|
|
||||||
const message: Message = {
|
|
||||||
chatter: data.chatter,
|
|
||||||
message: data.message,
|
|
||||||
timestamp: Date.now() as string
|
|
||||||
};
|
|
||||||
|
|
||||||
chatRoom.addMessage(message);
|
chatRoom.addMessage(message);
|
||||||
},
|
},
|
||||||
@ -42,7 +33,7 @@ app.get("/chat-service", upgradeWebSocket((c) => {
|
|||||||
console.log("Connection closed.");
|
console.log("Connection closed.");
|
||||||
},
|
},
|
||||||
onError(event) {
|
onError(event) {
|
||||||
console.log(event);
|
console.error(event);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
|
1775
chat-app/static/js/index.js
Normal file
1775
chat-app/static/js/index.js
Normal file
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user