Compare commits

...

2 Commits

29 changed files with 352 additions and 113 deletions

View File

@ -1,4 +1,4 @@
{% ELDEF main JSON pres JSON userinfo %}
{% ELDEF main JSON pres JSON userinfo JSON errors %}
<!DOCTYPE html>
<html lang="{% WRITE pres.lang %}">
<head>
@ -6,11 +6,15 @@
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>{% WRITE pres.phr.decl.page-login %}</title>
<link rel="stylesheet" href="/assets/css/login.css">
</head>
<body>
{% PUT pass-pres-userinfo pres userinfo %}
{% FOR msg IN errors %}
<div class="error-msg">
{% WRITE msg %}
</div>
{% ENDFOR %}
<div class="form-container">
<h1 class="hide-cursor no-select">{% WRITE pres.phr.decl.enter %}</h1>
<form action="/login" method="post" enctype="application/x-www-form-urlencoded">

View File

@ -1,4 +1,5 @@
dy {
/* I have no idea what is going on here */
body {
font-family: Arial, sans-serif;
display: flex;
justify-content: center;
@ -50,28 +51,9 @@ button {
transition: background-color 0.3s;
}
button:hover,
button:focus-visible {
background-color: #007bb5;
}
.hide-cursor::placeholder {
color: #000;
}
.hide-cursor {
caret-color: transparent;
}
.no-select {
-webkit-user-select: none; /* Для Safari */
-moz-user-select: none; /* Для Firefox */
user-select: none; /* Для всех остальных браузеров */
}
div {
.error-msg {
color: red;
font-size: 15px;
margin-top: 10px;
display: none;
background-color: #ffc0c0;
border-color: red;
border-radius: 5px;
}

View File

@ -153,13 +153,19 @@ struct CAWebChat {
"backend_logic/when_login.cpp",
"backend_logic/when_chat.cpp",
"backend_logic/when_user.cpp",
"backend_logic/when_api_pollevents.cpp",
"backend_logic/when_api_getchatlist.cpp",
"backend_logic/when_api_getchatinfo.cpp",
"backend_logic/when_api_getchatmemberlist.cpp",
"backend_logic/when_api_getuserinfo.cpp",
"backend_logic/when_api_getmessageinfo.cpp",
"backend_logic/when_api_getmessageneighbours.cpp",
"backend_logic/api_pollevents.cpp",
"backend_logic/api_getchatlist.cpp",
"backend_logic/api_getchatinfo.cpp",
"backend_logic/api_getchatmemberlist.cpp",
"backend_logic/api_getuserinfo.cpp",
"backend_logic/api_getmessageinfo.cpp",
"backend_logic/api_getmessageneighbours.cpp",
"backend_logic/api_sendmessage.cpp",
"backend_logic/api_deletemessage.cpp",
"backend_logic/api_addmembertochat.cpp",
"backend_logic/api_removememberfromchat.cpp",
"backend_logic/api_createchat.cpp",
"backend_logic/api_removechat.cpp",
};
for (std::string& u: T.units)
u = "web_chat/iu9_ca_web_chat_lib/" + u;

View File

@ -12,7 +12,9 @@
"page-login": "Вход",
"list-of-chat-rooms": "Список Чат-Коsмнат",
"name-of-room": "Название комнаты",
"create-room": "Создать комнату"
"create-room": "Создать комнату",
"incorrect-nickname-or-password": "Неправильный никнейм или пароль"
},
"ask" : {
"select-chat-room": "Выберете чат комнату"

View File

@ -0,0 +1,15 @@
#include "server_data_interact.h"
#include <engine_engine_number_9/baza_throw.h>
namespace iu9cawebchat {
json::JSON internalapi_addMemberToChat(SqliteConnection& conn, int64_t uid, const json::JSON& Sent) {
int64_t chatId = Sent["chatId"].g().asInteger().get_int();
int64_t my_role_here = get_role_of_user_in_chat(conn, uid, chatId);
if (my_role_here == user_chat_role_deleted)
een9_THROW("Unauthorized user tries to access internalapi_getChatInfo");
json::JSON Recv;
Recv["status"] = json::JSON(0l);
// todo: WRITE THIS MORBID THING
return Recv;
}
}

View File

@ -0,0 +1,11 @@
#include "server_data_interact.h"
#include <engine_engine_number_9/baza_throw.h>
namespace iu9cawebchat {
json::JSON internalapi_createChat(SqliteConnection& conn, int64_t uid, const json::JSON& Sent) {
json::JSON Recv;
Recv["status"] = json::JSON(0l);
// todo: WRITE THIS MORBID THING
return Recv;
}
}

View File

@ -0,0 +1,15 @@
#include "server_data_interact.h"
#include <engine_engine_number_9/baza_throw.h>
namespace iu9cawebchat {
json::JSON internalapi_deleteMessage(SqliteConnection& conn, int64_t uid, const json::JSON& Sent) {
int64_t chatId = Sent["chatId"].g().asInteger().get_int();
int64_t my_role_here = get_role_of_user_in_chat(conn, uid, chatId);
if (my_role_here == user_chat_role_deleted)
een9_THROW("Unauthorized user tries to access internalapi_getChatInfo");
json::JSON Recv;
Recv["status"] = json::JSON(0l);
// todo: WRITE THIS MORBID THING
return Recv;
}
}

View File

@ -2,7 +2,7 @@
#include <engine_engine_number_9/baza_throw.h>
namespace iu9cawebchat {
json::JSON internalapi_getChatList(SqliteConnection& conn, int64_t uid) {
json::JSON internalapi_getChatList(SqliteConnection& conn, int64_t uid, const json::JSON& Sent) {
json::JSON Recv;
Recv["status"] = json::JSON(0l);
Recv["chats"] = json::JSON(json::array);

View File

@ -97,6 +97,37 @@ namespace iu9cawebchat {
}
}
int64_t event_polling_fill_chat_hist_entity_response(SqliteConnection& conn, json::JSON& hist_entity_response,
int64_t uid, int64_t chatId, int64_t LocalHistoryId) {
hist_entity_response["type"] = json::JSON("chat");
if (get_role_of_user_in_chat(conn, uid, chatId) == user_chat_role_deleted)
een9_THROW("internalapi/pollEvents: trying to access chat that user does not belong to");
hist_entity_response["chatId"] = json::JSON(chatId);
int64_t NewHistoryId = get_current_history_id_of_chat(conn, chatId);
hist_entity_response["HistoryId"] = json::JSON(NewHistoryId);
hist_entity_response["events"] = json::JSON(json::array);
std::vector<json::JSON>& events = hist_entity_response["events"].g().asArray();
/* Two classes of 'real events' can happen to chat: membership table change, message table change */
/* Here, I collect membership changes (related to this chat) */
internalapi_pollEvents_in_chat_collect_membership_events(conn, events, chatId, LocalHistoryId);
/* Here, I collect message changes (related to this chat) */
internalapi_pollEvents_in_chat_collect_messages_events(conn, events, chatId, LocalHistoryId);
return NewHistoryId;
}
int64_t event_polling_fill_chatlist_hist_entity_response(SqliteConnection& conn, json::JSON& hist_entity_response,
int64_t uid, int64_t LocalHistoryId) {
hist_entity_response["type"] = json::JSON("chatlist");
int64_t NewHistoryId = get_current_history_id_of_user_chatList(conn, uid);
hist_entity_response["HistotyId"] = json::JSON(NewHistoryId);
hist_entity_response["events"] = json::JSON(json::array);
std::vector<json::JSON>& events = hist_entity_response["events"].g().asArray();
internalapi_pollEvents_in_user_chatList_collect_events(conn, events, uid, LocalHistoryId);
return NewHistoryId;
}
json::JSON internalapi_pollEvents(SqliteConnection& conn, int64_t uid, const json::JSON& Sent) {
json::JSON Recv;
Recv["status"] = json::JSON(0l);
@ -106,24 +137,12 @@ namespace iu9cawebchat {
for (const json::JSON& hist_entity_request: req_scope) {
updated.emplace_back();
json::JSON& hist_entity_response = updated.back();
hist_entity_response["type"] = hist_entity_request["type"].g();
hist_entity_response["events"] = json::JSON(json::array);
std::vector<json::JSON>& events = hist_entity_response["events"].g().asArray();
const int64_t LocalHistoryId = hist_entity_request["LocalHistoryId"].g().asInteger().get_int();
if (hist_entity_request["type"].g().asString() == "chat") {
int64_t chatId = hist_entity_request["chatId"].g().asInteger().get_int();
if (get_role_of_user_in_chat(conn, uid, chatId) == user_chat_role_deleted)
een9_THROW("internalapi/pollEvents: trying to access chat that user does not belong to");
hist_entity_response["chatId"] = json::JSON(chatId);
hist_entity_response["HistoryId"] = json::JSON(get_current_history_id_of_chat(conn, chatId));
/* Two classes of 'real events' can happen to chat: membership table change, message table change */
/* Here, I collect membership changes (related to this chat) */
internalapi_pollEvents_in_chat_collect_membership_events(conn, events, chatId, LocalHistoryId);
/* Here, I collect message changes (related to this chat) */
internalapi_pollEvents_in_chat_collect_messages_events(conn, events, chatId, LocalHistoryId);
event_polling_fill_chat_hist_entity_response(conn, hist_entity_response, uid, chatId, LocalHistoryId);
} else if (hist_entity_request["type"].g().asString() == "chatlist") {
hist_entity_response["HistotyId"] = json::JSON(get_current_history_id_of_user_chatList(conn, uid));
internalapi_pollEvents_in_user_chatList_collect_events(conn, events, uid, LocalHistoryId);
event_polling_fill_chatlist_hist_entity_response(conn, hist_entity_response, uid, LocalHistoryId);
} else
een9_THROW("Bad request");
}

View File

@ -0,0 +1,11 @@
#include "server_data_interact.h"
#include <engine_engine_number_9/baza_throw.h>
namespace iu9cawebchat {
json::JSON internalapi_removeChat(SqliteConnection& conn, int64_t uid, const json::JSON& Sent) {
json::JSON Recv;
Recv["status"] = json::JSON(0l);
// todo: WRITE THIS MORBID THING
return Recv;
}
}

View File

@ -0,0 +1,15 @@
#include "server_data_interact.h"
#include <engine_engine_number_9/baza_throw.h>
namespace iu9cawebchat {
json::JSON internalapi_removeMemberFromChat(SqliteConnection& conn, int64_t uid, const json::JSON& Sent) {
int64_t chatId = Sent["chatId"].g().asInteger().get_int();
int64_t my_role_here = get_role_of_user_in_chat(conn, uid, chatId);
if (my_role_here == user_chat_role_deleted)
een9_THROW("Unauthorized user tries to access internalapi_getChatInfo");
json::JSON Recv;
Recv["status"] = json::JSON(0l);
// todo: WRITE THIS MORBID THING
return Recv;
}
}

View File

@ -0,0 +1,48 @@
#include "server_data_interact.h"
#include <engine_engine_number_9/baza_throw.h>
#include "../str_fields.h"
namespace iu9cawebchat {
/* Throws excetion on failure
* Chat's HistoryId will increment after this operation, incremented
* if adding system message, uid is ignored
*/
int64_t insert_new_message(SqliteConnection& conn, int64_t uid, int64_t chatId,
const std::string& text, bool isSystem) {
int64_t chat_HistoryId_BEFORE_MSG = get_current_history_id_of_chat(conn, chatId);
if (chat_HistoryId_BEFORE_MSG > INT64_MAX - 100)
een9_THROW("please no");
SqliteStatement req(conn,
"INSERT INTO `message` (`chatId`, `previous`, `senderUserId`, `exists`, `isSystem`, `text`,"
"`chat_IncHistoryId`) VALUES (?1, ?2, ?3, 1, ?4, ?5, ?6)",
{{1, chatId}, {4, (int64_t)isSystem}, {6, chat_HistoryId_BEFORE_MSG + 1}}, {{5, text}});
int64_t chat_cur_last_msg_id = get_lastMsgId_of_chat(conn, chatId);
if (chat_cur_last_msg_id >= 0)
sqlite_stmt_bind_int64(req, 2, chat_cur_last_msg_id);
if (!isSystem)
sqlite_stmt_bind_int64(req, 3, uid);
int64_t MSG_ID = sqlite_trsess_last_insert_rowid(conn);
sqlite_nooutput(conn, "UPDATE `chat` SET `lastMsgId` = ?1, `it_HistoryId` = ?2 WHERE `id` = ?3",
{{1, MSG_ID}, {2, chat_HistoryId_BEFORE_MSG + 1}, {3, chatId}}, {});
return MSG_ID;
}
json::JSON internalapi_sendMessage(SqliteConnection& conn, int64_t uid, const json::JSON& Sent) {
int64_t chatId = Sent["chatId"].g().asInteger().get_int();
int64_t my_role_here = get_role_of_user_in_chat(conn, uid, chatId);
if (my_role_here == user_chat_role_deleted)
een9_THROW("Unauthorized user tries to access internalapi_getChatInfo");
if (my_role_here == user_chat_role_read_only)
een9_THROW("read-only user can't send messages");
const int64_t LocalHistoryId = Sent["LocalHistoryId"].g().asInteger().get_int();
std::string text = Sent["content"]["text"].g().asString();
if (!is_orthodox_string(text) || text.empty())
een9_THROW("Bad input text");
int64_t MSG_ID = insert_new_message(conn, uid, chatId, text, false);
json::JSON Recv;
Recv["status"] = json::JSON(0l);
json::JSON hist_ent_response = Recv["update"][0].g();
event_polling_fill_chat_hist_entity_response(conn, hist_ent_response, uid, chatId, LocalHistoryId);
return Recv;
}
}

View File

@ -1,5 +1,6 @@
#include "client_server_interact.h"
#include <engine_engine_number_9/http_structures/cookies.h>
#include <functional>
namespace iu9cawebchat {
void initial_extraction_of_all_the_useful_info_from_cookies(
@ -24,55 +25,86 @@ namespace iu9cawebchat {
}
}
std::string RTEE(const std::string& el_name,
const json::JSON& config_presentation, WorkerGuestData& wgd,
std::string R200_pres_uinfo(const std::string& el_name, WorkerGuestData& wgd,
const json::JSON& config_presentation,
const json::JSON& userinfo) {
std::string page = wgd.templater->render(el_name, {&config_presentation, &userinfo});
return een9::form_http_server_response_200("text/html", page);
}
std::string R200_pres_uinfo_msges(const std::string& el_name, WorkerGuestData& wgd,
const json::JSON& config_presentation,
const json::JSON& userinfo, const std::vector<HtmlMsgBox>& messages) {
json::JSON jmessages;
// todo: optimize
for (size_t i = 0; i < messages.size(); i++) {
jmessages[i]["class"] = json::JSON(messages[i].class_);
jmessages[i]["text"] = json::JSON(messages[i].text);
}
std::string page = wgd.templater->render(el_name, {&config_presentation, &userinfo, &jmessages});
return een9::form_http_server_response_200("text/html", page);
}
/* ========================= API =========================*/
std::string when_internalapi_pollevents(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid) {
std::string when_internalapi(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid,
const std::function<json::JSON(SqliteConnection&, int64_t, const json::JSON&)>& F) {
const json::JSON& Sent = json::parse_str_flawless(req.body);
std::string result = json::generate_str(internalapi_pollEvents(*wgd.db, uid, Sent), json::print_pretty);
std::string result = json::generate_str(F(*wgd.db, uid, Sent), json::print_pretty);
return een9::form_http_server_response_200("text/json", result);
}
std::string when_internalapi_getchatlist(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid) {
const json::JSON& Sent = json::parse_str_flawless(req.body);
std::string result = json::generate_str(internalapi_getChatList(*wgd.db, uid), json::print_pretty);
return een9::form_http_server_response_200("text/json", result);
std::string when_internalapi_pollevents(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_pollEvents);
}
std::string when_internalapi_getchatinfo(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid) {
const json::JSON& Sent = json::parse_str_flawless(req.body);
std::string result = json::generate_str(internalapi_getChatInfo(*wgd.db, uid, Sent), json::print_pretty);
return een9::form_http_server_response_200("text/json", result);
std::string when_internalapi_getchatlist(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_getChatList);
}
std::string when_internalapi_getchatmemberlist(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid) {
const json::JSON& Sent = json::parse_str_flawless(req.body);
std::string result = json::generate_str(internalapi_getChatMemberList(*wgd.db, uid, Sent), json::print_pretty);
return een9::form_http_server_response_200("text/json", result);
std::string when_internalapi_getchatinfo(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_getChatInfo);
}
std::string when_internalapi_getuserinfo(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid) {
const json::JSON& Sent = json::parse_str_flawless(req.body);
std::string result = json::generate_str(internalapi_getUserInfo(*wgd.db, uid, Sent), json::print_pretty);
return een9::form_http_server_response_200("text/json", result);
std::string when_internalapi_getchatmemberlist(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_getChatMemberList);
}
std::string when_internalapi_getmessageinfo(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid) {
const json::JSON& Sent = json::parse_str_flawless(req.body);
std::string result = json::generate_str(internalapi_getMessageInfo(*wgd.db, uid, Sent), json::print_pretty);
return een9::form_http_server_response_200("text/json", result);
std::string when_internalapi_getuserinfo(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_getUserInfo);
}
std::string when_internalapi_getmessageinfo(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_getMessageInfo);
}
std::string when_internalapi_getmessageneighbours(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_getMessageNeighbours);
}
std::string when_internalapi_sendmessage(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_sendMessage);
}
std::string when_internalapi_deletemessage(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_deleteMessage);
}
std::string when_internalapi_addmembertochat(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_addMemberToChat);
}
std::string when_internalapi_removememberfromchat(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_removeMemberFromChat);
}
std::string when_internalapi_createchat(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_createChat);
}
std::string when_internalapi_removechat(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid) {
return when_internalapi(wgd, req, uid, internalapi_removeChat);
}
}

View File

@ -27,10 +27,19 @@ namespace iu9cawebchat {
int64_t& ret_logged_in_user
);
std::string RTEE(const std::string& el_name,
const json::JSON& config_presentation, WorkerGuestData& wgd,
std::string R200_pres_uinfo(const std::string& el_name, WorkerGuestData& wgd,
const json::JSON& config_presentation,
const json::JSON& userinfo);
struct HtmlMsgBox {
std::string class_;
std::string text;
};
std::string R200_pres_uinfo_msges(const std::string& el_name, WorkerGuestData& wgd,
const json::JSON& config_presentation,
const json::JSON& userinfo, const std::vector<HtmlMsgBox>& messages);
/* ========================== PAGES ================================== */
std::string when_page_list_rooms(WorkerGuestData& wgd, const json::JSON& config_presentation,
@ -48,23 +57,31 @@ namespace iu9cawebchat {
/* ======================== API ============================== */
std::string when_internalapi_pollevents(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_pollevents(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getchatlist(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getchatlist(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getchatinfo(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getchatinfo(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getchatmemberlist(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getchatmemberlist(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getuserinfo(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getuserinfo(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getmessageinfo(WorkerGuestData& wgd,
const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getmessageinfo(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_getmessageneighbours(WorkerGuestData& wgd, const een9::ClientRequest& req, int64_t uid);
std::string when_internalapi_sendmessage(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid);
std::string when_internalapi_deletemessage(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid);
std::string when_internalapi_addmembertochat(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid);
std::string when_internalapi_removememberfromchat(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid);
std::string when_internalapi_createchat(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid);
std::string when_internalapi_removechat(WorkerGuestData &wgd, const een9::ClientRequest &req, int64_t uid);
}
#endif

View File

@ -118,5 +118,18 @@ namespace iu9cawebchat {
return user_chat_role_deleted;
}
/* All the api calls processing is done in dedicated files */
int64_t get_lastMsgId_of_chat(SqliteConnection &conn, int64_t chatId) {
een9_ASSERT(chatId >= 0, "Are you crazy?");
SqliteStatement sql_req(conn,
"SELECT `lastMsgId` FROM `chat` WHERE `id` = ?1", {{1, chatId}}, {});
fsql_integer_or_null last_msg_id_col;
int status = sqlite_stmt_step(sql_req, {{0, &last_msg_id_col}}, {});
if (status == SQLITE_ROW) {
return last_msg_id_col.exist ? last_msg_id_col.value : -1;
}
een9_THROW("No such chat");
}
/* All the api calls processing is done in dedicated files.
* All functions related to polling are defined in api_pollevents.cpp */
}

View File

@ -30,6 +30,7 @@ namespace iu9cawebchat {
};
RowUser_Content lookup_user_content(SqliteConnection& conn, int64_t uid);
/* Does not make authorization check */
RowChat_Content lookup_chat_content(SqliteConnection& conn, int64_t chatId);
struct RowMessage_Content {
@ -44,17 +45,33 @@ namespace iu9cawebchat {
/* If prevMsgId is id of the last message in chat, and there is no message ahead of it, .first = -1 */
std::pair<int64_t, RowMessage_Content> lookup_message_content_rev_side(SqliteConnection& conn, int64_t chatId, int64_t prevMsgId);
/* Does not make authorization check */
int64_t get_role_of_user_in_chat(SqliteConnection& conn, int64_t userId, int64_t chatId);
/* Does not make authorization check */
int64_t get_lastMsgId_of_chat(SqliteConnection& conn, int64_t chatId);
/* ============================= API ====================================*/
int64_t get_current_history_id_of_chat(SqliteConnection& conn, int64_t chatId);
int64_t get_current_history_id_of_user_chatList(SqliteConnection& conn, int64_t userId);
/* Returns HistoryId of chat (latest) */
int64_t event_polling_fill_chat_hist_entity_response(SqliteConnection& conn, json::JSON& hist_entity_response,
int64_t uid, int64_t chatId, int64_t LocalHistoryId);
/* Returns HistoryId of chat list (latest) */
int64_t event_polling_fill_chatlist_hist_entity_response(SqliteConnection& conn, json::JSON& hist_entity_response,
int64_t uid, int64_t LocalHistoryId);
json::JSON internalapi_pollEvents(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_getChatList(SqliteConnection& conn, int64_t uid);
json::JSON internalapi_getChatList(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_getChatInfo(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_getChatMemberList(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_getUserInfo(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_getMessageInfo(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_getMessageNeighbours(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
// todo: complete the list
json::JSON internalapi_sendMessage(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_deleteMessage(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_addMemberToChat(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_removeMemberFromChat(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_createChat(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
json::JSON internalapi_removeChat(SqliteConnection& conn, int64_t uid, const json::JSON& Sent);
}
#endif

View File

@ -3,6 +3,6 @@
namespace iu9cawebchat {
std::string when_page_chat(WorkerGuestData& wgd, const json::JSON& config_presentation,
const een9::ClientRequest& req, const json::JSON& userinfo) {
return RTEE("chat", config_presentation, wgd, userinfo);
return R200_pres_uinfo("chat", config_presentation, wgd, userinfo);
}
}

View File

@ -6,6 +6,6 @@ namespace iu9cawebchat {
if (userinfo.isNull()) {
return een9::form_http_server_response_303("/login");
}
return RTEE("list-rooms", config_presentation, wgd, userinfo);
return R200_pres_uinfo("list-rooms", config_presentation, wgd, userinfo);
}
}

View File

@ -25,14 +25,15 @@ namespace iu9cawebchat {
} catch(const std::exception& e){}
if (uid < 0) {
printf("Redirecting back to /login because of incorrect credentials\n");
/* todo: Here I need to tell somehow to user (through fancy red box, maybe), that login was incorrect */
return RTEE("login", config_presentation, wgd, userinfo);
// class will be successfully ignored
return R200_pres_uinfo_msges("login", wgd, config_presentation, userinfo, {{"",
config_presentation["phr"]["decl"]["incorrect-nickname-or-password"].g().asString()}});
}
std::vector<std::pair<std::string, std::string>> response_hlines;
LoginCookie new_login_cookie = create_login_cookie(nickname, password);
add_set_cookie_headers_to_login(login_cookies, response_hlines, new_login_cookie);
return een9::form_http_server_response_303_spec_head("/", response_hlines);
}
return RTEE("login", config_presentation, wgd, userinfo);
return R200_pres_uinfo_msges("login", wgd, config_presentation, userinfo, {});
}
}

View File

@ -3,6 +3,6 @@
namespace iu9cawebchat {
std::string when_page_user(WorkerGuestData& wgd, const json::JSON& config_presentation,
const een9::ClientRequest& req, const json::JSON& userinfo) {
return RTEE("profile", config_presentation, wgd, userinfo);
return R200_pres_uinfo("profile", config_presentation, wgd, userinfo);
}
}

View File

@ -64,7 +64,7 @@ namespace iu9cawebchat {
"`id` INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,"
"`chatId` INTEGER REFERENCES `chat` NOT NULL,"
"`previous` INTEGER REFERENCES `message`,"
"`senderUserId` INTEGER REFERENCES `user` NOT NULL,"
"`senderUserId` INTEGER REFERENCES `user`,"
"`exists` BOOLEAN NOT NULL,"
"`isSystem` BOOLEAN NOT NULL,"
"`text` TEXT NOT NULL,"

View File

@ -96,10 +96,27 @@ namespace iu9cawebchat {
if (req.uri_path == "/internalapi/getMessageInfo") {
return when_internalapi_getmessageinfo(wgd, req, logged_in_user);
}
// if (req.uri_path == "/internalapi/getMessageNeighbours") {
// return when
// }
// todo: write all the other interfaces
if (req.uri_path == "/internalapi/getMessageNeighbours") {
return when_internalapi_getmessageneighbours(wgd, req, logged_in_user);
}
if (req.uri_path == "/internalapi/sendMessage") {
return when_internalapi_sendmessage(wgd, req, logged_in_user);
}
if (req.uri_path == "/internalapi/deleteMessage") {
return when_internalapi_deletemessage(wgd, req, logged_in_user);
}
if (req.uri_path == "/internalapi/addMemberToChat") {
return when_internalapi_addmembertochat(wgd, req, logged_in_user);
}
if (req.uri_path == "/internalapi/removeMemberFromChat") {
return when_internalapi_removememberfromchat(wgd, req, logged_in_user);
}
if (req.uri_path == "/internalapi/createChat") {
return when_internalapi_createchat(wgd, req, logged_in_user);
}
if (req.uri_path == "/internalapi/removeChat") {
return when_internalapi_removechat(wgd, req, logged_in_user);
}
} catch (const std::exception& e) {
guard_.rollback = true;
throw;

View File

@ -101,6 +101,11 @@ namespace iu9cawebchat {
sqlite3_finalize(stmt_obj);
}
void sqlite_stmt_bind_int64(SqliteStatement &stmt, int paramId, int64_t value) {
int ret = sqlite3_bind_int64(stmt.stmt_obj, paramId, value);
een9_ASSERT(ret == 0, "sqlite3_bind_int64");
}
int sqlite_stmt_step(SqliteStatement &stmt,
const std::vector<std::pair<int, fsql_integer_or_null *>> &ret_of_integer_or_null,
const std::vector<std::pair<int, fsql_text8_or_null *>> &ret_of_text8_or_null) {
@ -137,4 +142,9 @@ namespace iu9cawebchat {
}
return SQLITE_ROW;
}
int64_t sqlite_trsess_last_insert_rowid(SqliteConnection& conn) {
int64_t res = sqlite3_last_insert_rowid(conn.hand);
return res;
}
}

View File

@ -41,9 +41,13 @@ namespace iu9cawebchat {
~SqliteStatement();
};
void sqlite_stmt_bind_int64(SqliteStatement& stmt, int paramId, int64_t value);
int sqlite_stmt_step(SqliteStatement& stmt,
const std::vector<std::pair<int, fsql_integer_or_null*>>& ret_of_integer_or_null,
const std::vector<std::pair<int, fsql_text8_or_null*>>& ret_of_text8_or_null);
int64_t sqlite_trsess_last_insert_rowid(SqliteConnection& conn);
}
#endif