From fc5af2468f36b75e29941b8ec72abc556d44c7ae Mon Sep 17 00:00:00 2001 From: rasmus Date: Tue, 6 May 2025 23:11:20 +0200 Subject: [PATCH] Added sending css file. Broke up some pieces of code, so now the ServerUtil is a bit more clean now. --- content/style.css | 57 ++++++++++++++++++ include/DataType.h | 10 ++++ include/FileUtils.h | 1 - include/ServerUtils.h | 65 ++++++++++++++++++++- include/WordUtils.h | 10 ++-- src/ServerUtils.cpp | 113 ++++++++++++++++++++++++++++-------- src/WordUtils.cpp | 130 +++++++++++++++++++----------------------- src/main.cpp | 5 +- 8 files changed, 287 insertions(+), 104 deletions(-) create mode 100644 content/style.css create mode 100644 include/DataType.h diff --git a/content/style.css b/content/style.css new file mode 100644 index 0000000..7146f01 --- /dev/null +++ b/content/style.css @@ -0,0 +1,57 @@ +.flex { + display: flex; +} + +.flex-col { + flex-direction: column; +} + +.min-h-screen { + min-height: 100vh; +} + +.justify-center { + justify-content: center; +} + +.grow { + flex-grow: 1; +} + +.pt-10 { + padding-top: 2.5rem /* 40px */; +} + +.px-4 { + padding-left: 1rem /* 16px */; + padding-right: 1rem /* 16px */; +} + +.text-2xl { + font-size: 1.5rem /* 24px */; + line-height: 2rem /* 32px */; +} + +.place-items-center { + place-items: center; +} + +.w-full { + width: 100%; +} + +.max-w-screen-lg { + max-width: 1024px; +} + +.mt-10 { + margin-top: 2.5rem /* 40px */; +} + +.pb-2 { + padding-bottom: 0.5rem /* 8px */; +} + +.underline { + text-decoration-line: underline; +} \ No newline at end of file diff --git a/include/DataType.h b/include/DataType.h new file mode 100644 index 0000000..822fd5e --- /dev/null +++ b/include/DataType.h @@ -0,0 +1,10 @@ +#ifndef DATATYPE_H +#define DATATYPE_H + +enum data_type { + HTML, + CSS, + IMAGE +}; + +#endif \ No newline at end of file diff --git a/include/FileUtils.h b/include/FileUtils.h index c1e854c..415a225 100644 --- a/include/FileUtils.h +++ b/include/FileUtils.h @@ -8,7 +8,6 @@ using namespace std; struct FileUtils { static bool fileExists(const char *path); - static char* getFiles(const char *path); }; #endif \ No newline at end of file diff --git a/include/ServerUtils.h b/include/ServerUtils.h index 8e84994..33721d8 100644 --- a/include/ServerUtils.h +++ b/include/ServerUtils.h @@ -12,12 +12,71 @@ #include #include #include +#include "../include/DataType.h" using namespace std; -struct ServerUtils { - static void serve(map> wordwordFrequencies); - static void process_request(int client_fd, map> wordwordFrequencies); +class ServerUtils { + public: + static void serve(); + private: + static void process_request(int client_fd); + static void send_header(int client_fd, data_type type); + static void send_chunked_html(int client_fd, unsigned int hash); + static void send_chunked_css(int client_fd); + static void send_data(int client_fd, string data); }; +const string HTML_RESPONSE_HEADER = + "HTTP/1.1 200 OK\r\n" + "Content-Type: text/html; charset=utf-8\r\n" + "Transfer-Encoding: chunked\r\n" + "Cache-control: max-age=12000\r\n" + "Connection: close\r\n\r\n"; + +const string CSS_RESPONSE_HEADER = + "HTTP/1.1 200 OK\r\n" + "Content-Type: text/css; charset=utf-8\r\n" + "Transfer-Encoding: chunked\r\n" + "Cache-control: max-age=12000\r\n" + "Connection: close\r\n\r\n"; + +const string PNG_RESPONSE_HEADER = + "HTTP/1.1 200 OK\r\n" + "Content-Type: text/png; charset=utf-8\r\n" + "Transfer-Encoding: chunked\r\n" + "Cache-control: max-age=12000\r\n" + "Connection: close\r\n\r\n"; + +const string HTML_BEGINNING = + "\n\r\n" + "Drip\r\n" + "\r\n" + "\r\n"; + +const string HTML_END = "\r\n"; + +const string HTML_NAV = + "
\r\n" + "
\r\n" + "\r\n" + "
\r\n"; + +const string HTML_MAIN_1 = + "
\r\n" + "
\r\n"; + +const string HTML_MAIN_2 = + "
\r\n" + "
\r\n"; + +const string HTML_FOOTER = + "\r\n" + "
\r\n"; + #endif \ No newline at end of file diff --git a/include/WordUtils.h b/include/WordUtils.h index 5048904..4c5a92f 100644 --- a/include/WordUtils.h +++ b/include/WordUtils.h @@ -6,16 +6,18 @@ #include #include #include +#include "../include/DataType.h" using namespace std; struct WordUtils { - static map> load_data(const char *path); + static map> load_data(const string& path); + static vector load_css(const string& path); static vector predict_next_word(const string& input, const map>& word_frequencies, size_t count); - static string load_file(const char *path); - static vector split_string(const string& input, const char *delimiters); + static string load_file(const string& path); + static vector split_string(const string& input, data_type type); static string extract_url(const string& input); - static vector create_tag(const map>& word_frequencies, unsigned int hash); + static string create_tag(const map>& word_frequencies, const char& hash); static unsigned int hash_url(const string& input); }; diff --git a/src/ServerUtils.cpp b/src/ServerUtils.cpp index c08ab4a..b743fa9 100644 --- a/src/ServerUtils.cpp +++ b/src/ServerUtils.cpp @@ -1,5 +1,6 @@ #include "../include/ServerUtils.h" #include "../include/WordUtils.h" +#include "../include/DataType.h" #include #include @@ -11,9 +12,13 @@ #include #include -using namespace std; +vector _css; +map> _word_frequencies; + +void ServerUtils::serve() { + _word_frequencies = WordUtils::load_data("/home/skingging/Documents/Projects/CPP/AI-Tarpit-Reimagined/wordlist/wordlist-Food.txt"); + _css = WordUtils::load_css("/home/skingging/Documents/Projects/CPP/AI-Tarpit-Reimagined/content/style.css"); -void ServerUtils::serve(map> word_frequencies) { // server_fd is a file descriptor. int server_fd = socket(AF_INET, SOCK_STREAM, 0); @@ -30,15 +35,14 @@ void ServerUtils::serve(map> word_frequencies) { while (true) { int client_fd = accept(server_fd, nullptr, nullptr); - thread(process_request, client_fd, word_frequencies).detach(); + thread(process_request, client_fd).detach(); } close(server_fd); } -void ServerUtils::process_request(int client_fd, map> word_frequencies) { +void ServerUtils::process_request(int client_fd) { char buffer[1024]; - int bytes_received = recv(client_fd, buffer, sizeof(buffer) - 1, 0); string url; @@ -52,25 +56,21 @@ void ServerUtils::process_request(int client_fd, map> w cerr << "AAAA \n"; } - unsigned int hash = WordUtils::hash_url(url); - - string headers = - "HTTP/1.1 200 OK\r\n" - "Content-Type: text/html; charset=utf-8\r\n" - "Transfer-Encoding: chunked\r\n" - "Connection: close\r\n\r\n"; - - send(client_fd, headers.c_str(), headers.size(), 0); - - const vector html_chunks = WordUtils::create_tag(word_frequencies, hash); - - for (const auto& chunk : html_chunks) { - ostringstream oss; - oss << hex << chunk.size() << "\r\n" << chunk << "\r\n"; - string to_send = oss.str(); - - send(client_fd, to_send.c_str(), to_send.size(), 0); - this_thread::sleep_for(chrono::milliseconds(5)); + if (url == "/style.css") { + // This sends the header, that instructs how the browser should interpret the data. + send_header(client_fd, data_type::CSS); + send_chunked_css(client_fd); + } + + else if (url == "/favicon.png") { + // This sends the header, that instructs how the browser should interpret the data. + //send_header(client_fd, data_type::IMAGE); + } + + else { + unsigned int hash = WordUtils::hash_url(url); + send_header(client_fd, data_type::HTML); + send_chunked_html(client_fd, hash); } // Send final zero-length chunk to end the response @@ -78,3 +78,68 @@ void ServerUtils::process_request(int client_fd, map> w close(client_fd); } + +void ServerUtils::send_header(int client_fd, data_type type) { + if (type == data_type::HTML) { + send(client_fd, HTML_RESPONSE_HEADER.c_str(), HTML_RESPONSE_HEADER.size(), 0); + } + + else if (type == data_type::CSS) { + send(client_fd, CSS_RESPONSE_HEADER.c_str(), CSS_RESPONSE_HEADER.size(), 0); + } + + else { + send(client_fd, PNG_RESPONSE_HEADER.c_str(), PNG_RESPONSE_HEADER.size(), 0); + } +} + +void ServerUtils::send_chunked_html(int client_fd, unsigned int hash) { + string chunk; + const string hashes = to_string(hash); + + unsigned short itr = 0; + unsigned short end = hashes.size(); + + send_data(client_fd, HTML_BEGINNING); + send_data(client_fd, HTML_NAV); + send_data(client_fd, HTML_MAIN_1); + + while (itr < end) { + ostringstream oss; + + chunk = WordUtils::create_tag(_word_frequencies, hashes[itr]); + + oss << hex << chunk.size() << "\r\n" << chunk << "\r\n"; + + string to_send = oss.str(); + + send(client_fd, to_send.c_str(), to_send.size(), 0); + //this_thread::sleep_for(chrono::milliseconds(0)); + + itr++; + } + + send_data(client_fd, HTML_MAIN_2); + send_data(client_fd, HTML_FOOTER); + send_data(client_fd, HTML_END); +} + +void ServerUtils::send_chunked_css(int client_fd) { + for (size_t i = 0; i < _css.size(); i++) { + ostringstream oss; + + oss << hex << _css[i].size() << "\r\n" << _css[i] << "\r\n"; + + string to_send = oss.str(); + + send(client_fd, to_send.c_str(), to_send.size(), 0); + } +} + +void ServerUtils::send_data(int client_fd, string data) { + ostringstream oss; + + oss << hex << data.size() << "\r\n" << data << "\r\n"; + + send(client_fd, oss.str().c_str(), oss.str().size(), 0); +} \ No newline at end of file diff --git a/src/WordUtils.cpp b/src/WordUtils.cpp index ba29a53..a675073 100644 --- a/src/WordUtils.cpp +++ b/src/WordUtils.cpp @@ -1,6 +1,6 @@ +#include "../include/WordUtils.h" #include #include -#include "../include/WordUtils.h" #include #include #include @@ -8,10 +8,8 @@ #include #include -map> WordUtils::load_data(const char *path) { - const char del[] = {' ', '.', ',', '!', '?', ';', ':', '(', ')', '\n', '\r', '\t'}; - - vector data = split_string(load_file(path), del); +map> WordUtils::load_data(const string& path) { + vector data = split_string(load_file(path), data_type::HTML); map> word_frequencies = {}; @@ -24,6 +22,10 @@ map> WordUtils::load_data(const char *path) { return word_frequencies; } +vector WordUtils::load_css(const string& path) { + return split_string(load_file(path), data_type::CSS); +} + vector WordUtils::predict_next_word(const string& input, const map>& word_frequencies, size_t count) { auto it = word_frequencies.find(input); @@ -40,7 +42,7 @@ vector WordUtils::predict_next_word(const string& input, const map results; - // Take up to `count` most common words + // Take up to "count" most common words for (size_t i = 0; i < min(count, sortedWords.size()); ++i) { results.push_back(sortedWords[i].first); } @@ -48,79 +50,65 @@ vector WordUtils::predict_next_word(const string& input, const map WordUtils::create_tag(const map>& word_frequencies, unsigned int hash) { - const vector beginning_sequences = {"the", "but", "with"}; - const string start = "\nDrip\n"; - const string end = "\n"; +string WordUtils::create_tag(const map>& word_frequencies, const char& hash) { + unsigned char predict_num = 5; + + const string start_words[3] = {"the", "but", "with"}; + vector tags; - const string hashes = to_string(hash); + minstd_rand generator(hash); - tags.push_back(start); - - int predict_num = 5; - - // Tags - for (int i = 0; i < hashes.size(); i++) - { - vector inner_tags; - - minstd_rand generator((int)hashes[i]); - - uniform_int_distribution outer_distribution(0, beginning_sequences.size() - 1); - vector temp_words = predict_next_word(beginning_sequences[outer_distribution(generator)], word_frequencies, predict_num); - - uniform_int_distribution outer_2_distribution(0, temp_words.size() - 1); - - inner_tags.push_back(temp_words[outer_2_distribution(generator)]); - - // Words per tag - for (int j = 0; j < 25; j++) - { - temp_words = predict_next_word(inner_tags[j], word_frequencies, predict_num); - - uniform_int_distribution inner_distribution(0, temp_words.size() - 1); - - if (temp_words.size() != 0) - { - temp_words = predict_next_word(inner_tags[j], word_frequencies, predict_num); - - uniform_int_distribution inner_2_distribution(0, temp_words.size() - 1); - - inner_tags.push_back(temp_words[inner_2_distribution(generator)]); - } else { - temp_words = predict_next_word(beginning_sequences[outer_distribution(generator)], word_frequencies, predict_num); - - uniform_int_distribution inner_3_distribution(0, temp_words.size() - 1); - - inner_tags.push_back(temp_words[inner_3_distribution(generator)]); - } - } - - string temp_string = "

"; - for (int l = 0; l < inner_tags.size(); l++) - { - temp_string += inner_tags[l] + " "; - } - - temp_string += ".

"; - - tags.push_back(temp_string); - } + uniform_int_distribution outer_distribution(0, start_words->length() - 1); + vector temp_words = predict_next_word(start_words[outer_distribution(generator)], word_frequencies, predict_num); - return tags; + uniform_int_distribution outer_2_distribution(0, temp_words.size() - 1); + + tags.push_back(temp_words[outer_2_distribution(generator)]); + + // Words inside the

tag + for (unsigned short j = 0; j < 25; j++) + { + temp_words = predict_next_word(tags[j], word_frequencies, predict_num); + + uniform_int_distribution inner_distribution(0, temp_words.size() - 1); + + tags.push_back(temp_words[inner_distribution(generator)]); + } + + string temp_string = "

"; + + for (unsigned short l = 0; l < tags.size(); l++) { + temp_string += tags[l]; + temp_string += " "; + } + + temp_string += ".

\n"; + + return temp_string; } -vector WordUtils::split_string(const string& input, const char *delimiters) { +vector WordUtils::split_string(const string& input, data_type type) { vector data; size_t start = 0; size_t end = 0; // Create a string from the delimiters array - string delimiter_string = " .,!?;:()\n\r\t"; + string delimiter_string; + if (type == data_type::HTML) + { + delimiter_string = " .,!?;:()\n\r\t"; + } + + else if (type == data_type::CSS) + { + delimiter_string = "}\n\r\t"; + } + + while ((end = input.find_first_of(delimiter_string, start)) != string::npos) { if (end > start) { data.push_back(input.substr(start, end - start)); @@ -137,7 +125,7 @@ vector WordUtils::split_string(const string& input, const char *delimite return data; } -string WordUtils::load_file(const char *path) { +string WordUtils::load_file(const string& path) { ifstream file(path); string temp; string data; @@ -152,15 +140,15 @@ string WordUtils::load_file(const char *path) { } string WordUtils::extract_url(const string& input) { - int first_line_end = input.find("\n"); + unsigned short first_line_end = input.find("\n"); if (first_line_end == string::npos) return ""; string first_line = input.substr(0, first_line_end); - int method_end = first_line.find(' '); + unsigned short method_end = first_line.find(' '); if (method_end == string::npos) return ""; - int path_end = first_line.find(' ', method_end + 1); + unsigned short path_end = first_line.find(' ', method_end + 1); if (path_end == string::npos) return ""; return first_line.substr(method_end + 1, path_end - method_end - 1); @@ -168,8 +156,10 @@ string WordUtils::extract_url(const string& input) { unsigned int WordUtils::hash_url(const string& input) { unsigned int hash = 0; + for (char c : input) { - hash += static_cast(c); + hash += static_cast(c) * 597301; } + return hash; } \ No newline at end of file diff --git a/src/main.cpp b/src/main.cpp index 5ec161e..426febe 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -4,7 +4,7 @@ using namespace std; -int main(int argc, char* argv[]) { +int main(int argc, const char* argv[]) { /*if (argc > 2) { cout << "Too many arguments"; @@ -36,7 +36,8 @@ int main(int argc, char* argv[]) { //argv[1] - ServerUtils::serve(WordUtils::load_data("/home/skingging/Documents/Projects/CPP/AI-Tarpit-Reimagined/wordlist/wordlist-Food.txt")); + ServerUtils server; + server.serve(); return 0; } \ No newline at end of file