Chat history.
This commit is contained in:
@@ -31,8 +31,8 @@
|
|||||||
<div id="bottom_text">
|
<div id="bottom_text">
|
||||||
<i>COMS</i> by Jacob Signorovitch.
|
<i>COMS</i> by Jacob Signorovitch.
|
||||||
<a href="#" id="help">Help</a> |
|
<a href="#" id="help">Help</a> |
|
||||||
<a href="//signorovitch.org">Code</a> |
|
<a href="//git.signorovitch.org/jacob/coms">Code</a> |
|
||||||
<a href="//signorovitch.org">API</a>
|
<a href="#">API</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ import {
|
|||||||
updateUser,
|
updateUser,
|
||||||
getGroupedUsers,
|
getGroupedUsers,
|
||||||
setMyId,
|
setMyId,
|
||||||
|
clearData,
|
||||||
users,
|
users,
|
||||||
setFocused,
|
setFocused,
|
||||||
setReplyTo,
|
setReplyTo,
|
||||||
@@ -49,11 +50,25 @@ export function initWebSocket(username, chatEl, inputContainer, usersListEl) {
|
|||||||
case "welcome": {
|
case "welcome": {
|
||||||
// Initial user list.
|
// Initial user list.
|
||||||
const myId = packet.data.you;
|
const myId = packet.data.you;
|
||||||
|
clearData();
|
||||||
setMyId(myId);
|
setMyId(myId);
|
||||||
const users = packet.data.users || [];
|
const users = packet.data.users || [];
|
||||||
users.forEach(({ id, username }) => addUser(id, username));
|
users.forEach(({ id, username }) => addUser(id, username));
|
||||||
const groups = getGroupedUsers();
|
const groups = getGroupedUsers();
|
||||||
usersListEl.innerHTML = "Online: " + groups.join(", ");
|
usersListEl.innerHTML = "Online: " + groups.join(", ");
|
||||||
|
// Replay chat history.
|
||||||
|
const history = packet.data.history || [];
|
||||||
|
history.forEach((raw) => {
|
||||||
|
try {
|
||||||
|
const histPkt = JSON.parse(raw);
|
||||||
|
if (histPkt.type === "msg-event") {
|
||||||
|
const { id, username: u, content, ts, parent } = histPkt.data;
|
||||||
|
addMessage({ id, username: u, content, ts, parent });
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
console.error("Invalid history entry", raw);
|
||||||
|
}
|
||||||
|
});
|
||||||
//addNotice(`<i>Users online: ${groups.join(", ")}</i>`);
|
//addNotice(`<i>Users online: ${groups.join(", ")}</i>`);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -12,6 +12,13 @@
|
|||||||
|
|
||||||
static size_t next_msg_id = 1;
|
static size_t next_msg_id = 1;
|
||||||
|
|
||||||
|
// History buffer for last 100 messages.
|
||||||
|
#define HISTORY_SIZE 100
|
||||||
|
static char* history[HISTORY_SIZE];
|
||||||
|
static size_t history_len[HISTORY_SIZE];
|
||||||
|
static size_t history_pos = 0;
|
||||||
|
static size_t history_count = 0;
|
||||||
|
|
||||||
#define CHAT_BUF_SIZE SESSION_CHAT_BUF_SIZE
|
#define CHAT_BUF_SIZE SESSION_CHAT_BUF_SIZE
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -92,6 +99,7 @@ int cb_chat(
|
|||||||
if (session_has_username(s)) {
|
if (session_has_username(s)) {
|
||||||
yyjson_mut_val* uobj = yyjson_mut_obj(wdoc);
|
yyjson_mut_val* uobj = yyjson_mut_obj(wdoc);
|
||||||
yyjson_mut_arr_add_val(wusers, uobj);
|
yyjson_mut_arr_add_val(wusers, uobj);
|
||||||
|
yyjson_mut_arr_add_val(wusers, uobj);
|
||||||
yyjson_mut_obj_add_uint(
|
yyjson_mut_obj_add_uint(
|
||||||
wdoc, uobj, "id", session_get_id(s)
|
wdoc, uobj, "id", session_get_id(s)
|
||||||
);
|
);
|
||||||
@@ -100,6 +108,19 @@ int cb_chat(
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// Include last 100 messages in the welcome history array.
|
||||||
|
yyjson_mut_val* whist = yyjson_mut_arr(wdoc);
|
||||||
|
yyjson_mut_obj_add_val(wdoc, wdata, "history", whist);
|
||||||
|
for (size_t i = 0; i < history_count; ++i) {
|
||||||
|
size_t idx =
|
||||||
|
(history_pos + HISTORY_SIZE - history_count + i) %
|
||||||
|
HISTORY_SIZE;
|
||||||
|
// Append raw JSON string into history array.
|
||||||
|
yyjson_mut_val* raw = yyjson_mut_strn(
|
||||||
|
wdoc, history[idx], history_len[idx]
|
||||||
|
);
|
||||||
|
yyjson_mut_arr_add_val(whist, raw);
|
||||||
|
}
|
||||||
|
|
||||||
size_t out_len;
|
size_t out_len;
|
||||||
char* out = yyjson_mut_write(wdoc, 0, &out_len);
|
char* out = yyjson_mut_write(wdoc, 0, &out_len);
|
||||||
@@ -291,6 +312,15 @@ int cb_chat(
|
|||||||
|
|
||||||
size_t out_len;
|
size_t out_len;
|
||||||
char* out = yyjson_mut_write(mdoc, 0, &out_len);
|
char* out = yyjson_mut_write(mdoc, 0, &out_len);
|
||||||
|
/* Store this msg-event JSON in the circular history buffer */
|
||||||
|
if (history_count == HISTORY_SIZE) {
|
||||||
|
free(history[history_pos]);
|
||||||
|
} else {
|
||||||
|
history_count++;
|
||||||
|
}
|
||||||
|
history[history_pos] = strdup(out);
|
||||||
|
history_len[history_pos] = out_len;
|
||||||
|
history_pos = (history_pos + 1) % HISTORY_SIZE;
|
||||||
size_t copy_len = out_len < SESSION_CHAT_BUF_SIZE
|
size_t copy_len = out_len < SESSION_CHAT_BUF_SIZE
|
||||||
? out_len
|
? out_len
|
||||||
: SESSION_CHAT_BUF_SIZE;
|
: SESSION_CHAT_BUF_SIZE;
|
||||||
|
|||||||
Reference in New Issue
Block a user