From c255e8882448c2f1349f69a3b7f68f7778923e56 Mon Sep 17 00:00:00 2001 From: Aldrik Ramaekers Date: Wed, 13 Mar 2024 22:43:19 +0100 Subject: csv file import --- src/export.cpp | 10 ++-- src/export.h | 3 +- src/import.cpp | 118 +++++++++++++++++++++++++++++++++++++++++++ src/import.h | 5 ++ src/main.cpp | 3 +- src/mutex.h | 1 + src/search.cpp | 3 ++ src/windows/main_windows.cpp | 4 +- 8 files changed, 138 insertions(+), 9 deletions(-) create mode 100644 src/import.cpp create mode 100644 src/import.h (limited to 'src') diff --git a/src/export.cpp b/src/export.cpp index 5bd29b4..6991c94 100644 --- a/src/export.cpp +++ b/src/export.cpp @@ -5,7 +5,7 @@ #ifndef _WIN32 #include -static int fopen_s(FILE **f, const char *name, const char *mode) { +int fopen_s(FILE **f, const char *name, const char *mode) { int ret = 0; assert(f); *f = fopen(name, mode); @@ -16,7 +16,7 @@ static int fopen_s(FILE **f, const char *name, const char *mode) { } #endif -static bool _str_has_extension(const utf8_int8_t *str, const utf8_int8_t *suffix) +bool ts_str_has_extension(const utf8_int8_t *str, const utf8_int8_t *suffix) { if (!str || !suffix) return 0; @@ -245,13 +245,13 @@ struct t_export_thread_args { static void* _ts_export_thread(void* args) { struct t_export_thread_args* arg = (struct t_export_thread_args*)args; - if (_str_has_extension(arg->path, ".json")) { + if (ts_str_has_extension(arg->path, ".json")) { _ts_export_json(arg->result, arg->path); } - if (_str_has_extension(arg->path, ".csv")) { + if (ts_str_has_extension(arg->path, ".csv")) { _ts_export_csv(arg->result, arg->path); } - if (_str_has_extension(arg->path, ".xml")) { + if (ts_str_has_extension(arg->path, ".xml")) { _ts_export_xml(arg->result, arg->path); } diff --git a/src/export.h b/src/export.h index ad83c77..0a320f8 100644 --- a/src/export.h +++ b/src/export.h @@ -10,4 +10,5 @@ typedef enum ts_export_result { EXPORT_SAVE_PENDING, } export_result; -export_result ts_export_result(ts_search_result* result, const utf8_int8_t* path); \ No newline at end of file +bool ts_str_has_extension(const utf8_int8_t *str, const utf8_int8_t *suffix); +export_result ts_export_result(ts_search_result* result, const utf8_int8_t* path); \ No newline at end of file diff --git a/src/import.cpp b/src/import.cpp new file mode 100644 index 0000000..545320e --- /dev/null +++ b/src/import.cpp @@ -0,0 +1,118 @@ +#include "import.h" +#include "search.h" +#include "export.h" + +#include +#include + +#ifndef _WIN32 +int fopen_s(FILE **f, const char *name, const char *mode); // defined in export.cpp +#endif + +static utf8_int8_t* _ts_str_find(utf8_int8_t* text, utf8_int8_t token) { + utf8_int32_t ch; + while ((text = utf8codepoint(text, &ch)) && ch) { + if (ch == token) return text; + } + return NULL; +} + +#define fscanf_required(_file, _format, _expect, ...) \ + if (fscanf(_file, _format, __VA_ARGS__) != _expect) { return false; } + +static bool _ts_import_csv_v1(ts_search_result* result, FILE *read_file) { + // Read setup info. + fscanf_required(read_file, "PATH,%s\n", 1, (char*)result->directory_to_search); + fscanf_required(read_file, "FILTER,%s\n", 1, (char*)result->file_filter); + fscanf_required(read_file, "QUERY,%s\n", 1, (char*)result->search_text); + fscanf_required(read_file, "CASESENSITIVE,%d\n", 1, (int*)&result->respect_capitalization); + fscanf_required(read_file, "MATCH_COUNT,%d\n", 1, &result->match_count); + fscanf_required(read_file, "FILE_COUNT,%d\n", 1, &result->file_count); + fscanf_required(read_file, "TIMESTAMP,%llu\n", 1, &result->timestamp); + + utf8ncpy(path_buffer, result->directory_to_search, MAX_INPUT_LENGTH); + utf8ncpy(filter_buffer, result->file_filter, MAX_INPUT_LENGTH); + utf8ncpy(query_buffer, result->search_text, MAX_INPUT_LENGTH); + + result->filters = ts_get_filters(result->file_filter); + if (utf8len(result->search_text) == 0) { + result->search_text = nullptr; + } + + // Read results + ts_found_file* current_file = 0; + ts_found_file* next_file = (ts_found_file*)ts_memory_bucket_reserve(&result->memory, sizeof(ts_found_file)); + next_file->path = (utf8_int8_t*)ts_memory_bucket_reserve(&result->memory, MAX_INPUT_LENGTH); + + ts_file_match match; + match.line_info = (char *)ts_memory_bucket_reserve(&result->memory, MAX_INPUT_LENGTH); + memset(match.line_info, 0, MAX_INPUT_LENGTH); + + utf8_int8_t line_buffer[MAX_INPUT_LENGTH]; + while(fgets(line_buffer, MAX_INPUT_LENGTH, read_file)) { + + // New file start. + if (sscanf(line_buffer, "FILE,%s", (char*)next_file->path) == 1) { + current_file = next_file; + current_file->match_count = 0; + current_file->error = 0; + current_file->collapsed = false; + + next_file = (ts_found_file*)ts_memory_bucket_reserve(&result->memory, sizeof(ts_found_file)); + next_file->path = (utf8_int8_t*)ts_memory_bucket_reserve(&result->memory, MAX_INPUT_LENGTH); + + ts_array_push_size(&result->files, ¤t_file, sizeof(ts_found_file*)); + } + + // New match within current_file + if (current_file && sscanf(line_buffer, "MATCH,%d,%zu,%zu\n", &match.line_nr, &match.word_match_length, &match.word_match_offset) == 3) { + match.file = current_file; + + utf8_int8_t* iter = line_buffer; + int count = 0; + while ((iter = _ts_str_find(iter, ',')) && iter) { + count++; + + if (count == 4) { // Copy string from here + utf8ncpy(match.line_info, iter, MAX_INPUT_LENGTH); + break; + } + } + + ts_array_push_size(&result->matches, &match, sizeof(ts_file_match)); + match.line_info = (char *)ts_memory_bucket_reserve(&result->memory, MAX_INPUT_LENGTH); + memset(match.line_info, 0, MAX_INPUT_LENGTH); + } + } + + return true; +} + +static bool _ts_import_csv(ts_search_result* result, const utf8_int8_t* path) { + FILE *read_file; + fopen_s(&read_file, path, "rb"); + if (read_file == NULL) return false; + + int version = -1; + fscanf(read_file, "VERSION,%d\n", &version); + switch(version) { + case 1: return _ts_import_csv_v1(result, read_file); + default: return false; + } +} + +ts_search_result* ts_import_result(const utf8_int8_t* path) { + ts_search_result* res = ts_create_empty_search_result(); + res->done_finding_files = false; + res->search_completed = false; + res->cancel_search = false; + + if (ts_str_has_extension(path, ".csv")) { + _ts_import_csv(res, path); + } + + res->done_finding_files = true; + res->search_completed = true; + + return res; +} \ No newline at end of file diff --git a/src/import.h b/src/import.h new file mode 100644 index 0000000..979cf84 --- /dev/null +++ b/src/import.h @@ -0,0 +1,5 @@ +#pragma once + +#include "search.h" + +ts_search_result* ts_import_result(const utf8_int8_t* path); \ No newline at end of file diff --git a/src/main.cpp b/src/main.cpp index 4d28a3c..9b6e599 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -10,6 +10,7 @@ #include "image.h" #include "config.h" #include "export.h" +#include "import.h" #include @@ -547,7 +548,7 @@ void ts_create_gui(int window_w, int window_h) { pos_y += _ts_create_textbox_area(window_w, window_h, textbox_area_height, pos_y); if (dragdrop_data.did_drop) { - printf("Do loading..\n"); + current_search_result = ts_import_result(dragdrop_data.path); dragdrop_data.did_drop = false; } diff --git a/src/mutex.h b/src/mutex.h index 2ee6316..323b277 100644 --- a/src/mutex.h +++ b/src/mutex.h @@ -2,6 +2,7 @@ #define INCLUDE_MUTEX #if defined(_WIN32) +#define _CRT_SECURE_NO_WARNINGS #include #include /* _beginthread, _endthread */ #include diff --git a/src/search.cpp b/src/search.cpp index 9eb3ca4..de5b608 100644 --- a/src/search.cpp +++ b/src/search.cpp @@ -105,6 +105,9 @@ ts_search_result *ts_create_empty_search_result() new_result_buffer->directory_to_search = (char *)ts_memory_bucket_reserve(&new_result_buffer->memory, MAX_INPUT_LENGTH); new_result_buffer->search_text = (char *)ts_memory_bucket_reserve(&new_result_buffer->memory, MAX_INPUT_LENGTH); new_result_buffer->file_filter = (char *)ts_memory_bucket_reserve(&new_result_buffer->memory, MAX_INPUT_LENGTH); + memset(new_result_buffer->directory_to_search, 0, MAX_INPUT_LENGTH); + memset(new_result_buffer->search_text, 0, MAX_INPUT_LENGTH); + memset(new_result_buffer->file_filter, 0, MAX_INPUT_LENGTH); return new_result_buffer; } diff --git a/src/windows/main_windows.cpp b/src/windows/main_windows.cpp index 00a8bc2..948226f 100644 --- a/src/windows/main_windows.cpp +++ b/src/windows/main_windows.cpp @@ -14,6 +14,7 @@ #ifndef WIN32_LEAN_AND_MEAN #define WIN32_LEAN_AND_MEAN #endif +#define _CRT_SECURE_NO_WARNINGS #include #include #include @@ -424,8 +425,7 @@ void ts_platform_list_files_block(ts_search_result* result, wchar_t* start_dir) ts_mutex_lock(&result->files.mutex); ts_array_push_size(&result->files, &f, sizeof(ts_found_file*)); - ts_mutex_unlock(&result->files.mutex); - + ts_mutex_unlock(&result->files.mutex); } } while (FindNextFile(handle, (LPWIN32_FIND_DATAW)&file_info) != 0); -- cgit v1.2.3-70-g09d2