From 8fdb832c85a42dfa7c0236cf9899f8bdc8c8e636 Mon Sep 17 00:00:00 2001 From: simon987 Date: Tue, 5 Sep 2023 18:59:18 -0400 Subject: [PATCH] refactor index schema, remove sidecar parsing, remove TS --- .devcontainer/Dockerfile | 9 - .devcontainer/devcontainer.json | 16 - .devcontainer/docker-compose.yml | 8 - .dockerignore | 4 +- CMakeLists.txt | 1 - docs/USAGE.md | 12 +- scripts/generate_big_index.py | 131 --- scripts/mime.csv | 3 +- scripts/mime.py | 16 +- sist2-admin/sist2_admin/app.py | 5 +- sist2-vue/package-lock.json | 769 ------------------ sist2-vue/package.json | 2 - sist2-vue/src/{Sist2Api.ts => Sist2Api.js} | 243 ++---- ...rchQuery.ts => Sist2ElasticsearchQuery.js} | 34 +- ...ist2SqliteQuery.ts => Sist2SqliteQuery.js} | 19 +- sist2-vue/src/components/D3Treemap.vue | 3 +- sist2-vue/src/components/DateSlider.vue | 3 +- sist2-vue/src/components/DocCard.vue | 7 +- sist2-vue/src/components/DocCardWall.vue | 102 +-- sist2-vue/src/components/DocFileTitle.vue | 5 +- sist2-vue/src/components/DocInfoModal.vue | 39 +- sist2-vue/src/components/DocList.vue | 52 +- sist2-vue/src/components/DocListItem.vue | 8 +- sist2-vue/src/components/FullThumbnail.vue | 301 +++---- sist2-vue/src/components/IndexPicker.vue | 16 +- sist2-vue/src/components/LazyContentDiv.vue | 6 +- sist2-vue/src/components/ResultsCard.vue | 10 +- sist2-vue/src/components/SizeSlider.vue | 3 +- sist2-vue/src/components/SmallBadge.vue | 2 +- .../src/components/ThumbnailProgressBar.vue | 8 +- .../src/i18n/{messages.ts => messages.js} | 0 sist2-vue/src/router/{auth0.ts => auth0.js} | 0 sist2-vue/src/router/{index.ts => index.js} | 2 +- sist2-vue/src/store/{index.ts => index.js} | 74 +- sist2-vue/src/util-js.js | 139 ---- sist2-vue/src/util.js | 329 ++++++++ sist2-vue/src/util.ts | 177 ---- sist2-vue/src/views/FilePage.vue | 224 ++--- sist2-vue/src/views/SearchPage.vue | 17 +- sist2-vue/tsconfig.json | 40 - src/database/database.c | 195 +++-- src/database/database.h | 32 +- src/database/database_embeddings.c | 4 +- src/database/database_fts.c | 84 +- src/database/database_schema.c | 108 ++- src/database/database_stats.c | 8 +- src/index/elastic.c | 20 +- src/index/elastic.h | 10 +- src/io/serialize.c | 51 +- src/main.c | 39 +- src/parsing/mime.h | 2 + src/parsing/mime_generated.c | 6 +- src/parsing/parse.c | 31 +- src/parsing/sidecar.c | 40 - src/parsing/sidecar.h | 8 - src/sist.h | 20 +- src/types.h | 9 +- src/util.h | 47 +- src/web/serve.c | 155 ++-- src/web/web_fts.c | 49 +- src/web/web_util.c | 6 +- src/web/web_util.h | 4 +- third-party/libscan/libscan/arc/arc.c | 2 +- third-party/libscan/libscan/arc/arc.h | 1 - third-party/libscan/libscan/comic/comic.c | 1 - third-party/libscan/libscan/comic/comic.h | 1 - third-party/libscan/libscan/ebook/ebook.c | 4 +- third-party/libscan/libscan/ebook/ebook.h | 1 - third-party/libscan/libscan/font/font.c | 4 +- third-party/libscan/libscan/font/font.h | 1 - third-party/libscan/libscan/json/json.h | 1 - third-party/libscan/libscan/macros.h | 19 +- third-party/libscan/libscan/media/media.c | 22 +- third-party/libscan/libscan/media/media.h | 1 - third-party/libscan/libscan/mobi/scan_mobi.c | 1 - third-party/libscan/libscan/mobi/scan_mobi.h | 1 - third-party/libscan/libscan/msdoc/msdoc.h | 1 - third-party/libscan/libscan/ooxml/ooxml.c | 5 +- third-party/libscan/libscan/ooxml/ooxml.h | 1 - third-party/libscan/libscan/raw/raw.c | 5 +- third-party/libscan/libscan/raw/raw.h | 1 - third-party/libscan/libscan/scan.h | 17 +- third-party/libscan/libscan/util.h | 2 +- third-party/libscan/test/main.cpp | 6 +- 84 files changed, 1420 insertions(+), 2445 deletions(-) delete mode 100644 .devcontainer/Dockerfile delete mode 100644 .devcontainer/devcontainer.json delete mode 100644 .devcontainer/docker-compose.yml delete mode 100644 scripts/generate_big_index.py rename sist2-vue/src/{Sist2Api.ts => Sist2Api.js} (72%) rename sist2-vue/src/{Sist2ElasticsearchQuery.ts => Sist2ElasticsearchQuery.js} (91%) rename sist2-vue/src/{Sist2SqliteQuery.ts => Sist2SqliteQuery.js} (89%) rename sist2-vue/src/i18n/{messages.ts => messages.js} (100%) rename sist2-vue/src/router/{auth0.ts => auth0.js} (100%) rename sist2-vue/src/router/{index.ts => index.js} (96%) rename sist2-vue/src/store/{index.ts => index.js} (88%) delete mode 100644 sist2-vue/src/util-js.js create mode 100644 sist2-vue/src/util.js delete mode 100644 sist2-vue/src/util.ts delete mode 100644 sist2-vue/tsconfig.json delete mode 100644 src/parsing/sidecar.c delete mode 100644 src/parsing/sidecar.h diff --git a/.devcontainer/Dockerfile b/.devcontainer/Dockerfile deleted file mode 100644 index 63ef994..0000000 --- a/.devcontainer/Dockerfile +++ /dev/null @@ -1,9 +0,0 @@ -FROM simon987/sist2-build - -RUN curl -fsSL https://deb.nodesource.com/setup_16.x | bash -RUN apt update -y; apt install -y nodejs && rm -rf /var/lib/apt/lists/* - -ENV DEBIAN_FRONTEND=noninteractive -ENV LANG C.UTF-8 -ENV LC_ALL C.UTF-8 - diff --git a/.devcontainer/devcontainer.json b/.devcontainer/devcontainer.json deleted file mode 100644 index 50fd8db..0000000 --- a/.devcontainer/devcontainer.json +++ /dev/null @@ -1,16 +0,0 @@ -{ - "name": "sist2-dev", - "dockerComposeFile": [ - "docker-compose.yml" - ], - "service": "sist2-dev", - "customizations": { - "vscode": { - "extensions": [ - "ms-vscode.cpptools-extension-pack" - ] - } - }, - "remoteUser": "root", - "workspaceFolder": "/app/" -} \ No newline at end of file diff --git a/.devcontainer/docker-compose.yml b/.devcontainer/docker-compose.yml deleted file mode 100644 index 1084336..0000000 --- a/.devcontainer/docker-compose.yml +++ /dev/null @@ -1,8 +0,0 @@ -version: "3" - -services: - sist2-dev: - build: . - command: sleep infinity - volumes: - - ../:/app \ No newline at end of file diff --git a/.dockerignore b/.dockerignore index 402c792..deb0179 100644 --- a/.dockerignore +++ b/.dockerignore @@ -38,4 +38,6 @@ build/ __pycache__/ sist2-vue/dist sist2-admin/frontend/dist -*.fts \ No newline at end of file +*.fts +.git +third-party/libscan/third-party/ext_*/* \ No newline at end of file diff --git a/CMakeLists.txt b/CMakeLists.txt index 71f73b9..d10e17e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -53,7 +53,6 @@ add_executable( src/types.h src/log.c src/log.h src/cli.c src/cli.h - src/parsing/sidecar.c src/parsing/sidecar.h src/database/database.c src/database/database.h src/parsing/fs_util.h diff --git a/docs/USAGE.md b/docs/USAGE.md index 813e8d8..2bc04dd 100644 --- a/docs/USAGE.md +++ b/docs/USAGE.md @@ -16,9 +16,9 @@ Lightning-fast file system indexer and search tool. Scan options -t, --threads= Number of threads. DEFAULT: 1 - -q, --thumbnail-quality= Thumbnail quality, on a scale of 0 to 100, 100 being the best. DEFAULT: 50 - --thumbnail-size= Thumbnail size, in pixels. DEFAULT: 552 - --thumbnail-count= Number of thumbnails to generate. Set a value > 1 to create video previews, set to 0 to disable thumbnails. DEFAULT: 1 + -q, --thumbnail_count-quality= Thumbnail quality, on a scale of 0 to 100, 100 being the best. DEFAULT: 50 + --thumbnail_count-size= Thumbnail size, in pixels. DEFAULT: 552 + --thumbnail_count-count= Number of thumbnails to generate. Set a value > 1 to create video previews, set to 0 to disable thumbnails. DEFAULT: 1 --content-size= Number of bytes to be extracted from text documents. Set to 0 to disable. DEFAULT: 32768 -o, --output= Output index file path. DEFAULT: index.sist2 --incremental If the output file path exists, only scan new or modified files. @@ -78,9 +78,9 @@ Made by simon987 . Released under GPL-3.0 #### Thumbnail database size estimation -See chart below for rough estimate of thumbnail size vs. thumbnail size & quality arguments: +See chart below for rough estimate of thumbnail_count size vs. thumbnail_count size & quality arguments: -For example, `--thumbnail-size=500`, `--thumbnail-quality=50` for a directory with 8 million images will create a thumbnail database +For example, `--thumbnail_count-size=500`, `--thumbnail_count-quality=50` for a directory with 8 million images will create a thumbnail_count database that is about `8000000 * 11.8kB = 94.4GB`. ![thumbnail_size](thumbnail_size.png) @@ -92,7 +92,7 @@ Simple scan sist2 scan ~/Documents sist2 scan \ - --threads 4 --content-size 16000000 --thumbnail-quality 2 --archive shallow \ + --threads 4 --content-size 16000000 --thumbnail_count-quality 2 --archive shallow \ --name "My Documents" --rewrite-url "http://nas.domain.local/My Documents/" \ ~/Documents -o ./documents.sist2 ``` diff --git a/scripts/generate_big_index.py b/scripts/generate_big_index.py deleted file mode 100644 index 6f2da1a..0000000 --- a/scripts/generate_big_index.py +++ /dev/null @@ -1,131 +0,0 @@ -import sqlite3 -import orjson as json -import os -import string -from hashlib import md5 -import random -from tqdm import tqdm - -schema = """ -CREATE TABLE thumbnail ( - id TEXT NOT NULL CHECK ( - length(id) = 32 - ), - num INTEGER NOT NULL, - data BLOB NOT NULL, - PRIMARY KEY(id, num) -) WITHOUT ROWID; -CREATE TABLE version ( - id INTEGER PRIMARY KEY AUTOINCREMENT, - date TEXT NOT NULL DEFAULT (CURRENT_TIMESTAMP) -); -CREATE TABLE document ( - id TEXT PRIMARY KEY NOT NULL CHECK ( - length(id) = 32 - ), - marked INTEGER NOT NULL DEFAULT (1), - version INTEGER NOT NULL REFERENCES version(id), - mtime INTEGER NOT NULL, - size INTEGER NOT NULL, - json_data TEXT NOT NULL CHECK ( - json_valid(json_data) - ) -); -CREATE TABLE delete_list ( - id TEXT PRIMARY KEY CHECK ( - length(id) = 32 - ) -) WITHOUT ROWID; -CREATE TABLE tag ( - id TEXT NOT NULL, - tag TEXT NOT NULL, - PRIMARY KEY (id, tag) -); -CREATE TABLE document_sidecar ( - id TEXT PRIMARY KEY NOT NULL, json_data TEXT NOT NULL -) WITHOUT ROWID; -CREATE TABLE descriptor ( - id TEXT NOT NULL, version_major INTEGER NOT NULL, - version_minor INTEGER NOT NULL, version_patch INTEGER NOT NULL, - root TEXT NOT NULL, name TEXT NOT NULL, - rewrite_url TEXT, timestamp INTEGER NOT NULL -); -CREATE TABLE stats_treemap ( - path TEXT NOT NULL, size INTEGER NOT NULL -); -CREATE TABLE stats_size_agg ( - bucket INTEGER NOT NULL, count INTEGER NOT NULL -); -CREATE TABLE stats_date_agg ( - bucket INTEGER NOT NULL, count INTEGER NOT NULL -); -CREATE TABLE stats_mime_agg ( - mime TEXT NOT NULL, size INTEGER NOT NULL, - count INTEGER NOT NULL -); -CREATE TABLE embedding ( - id TEXT REFERENCES document(id), - model_id INTEGER NOT NULL references model(id), - start INTEGER NOT NULL, - end INTEGER, - embedding BLOB NOT NULL, - PRIMARY KEY (id, model_id, start) -); -CREATE TABLE model ( - id INTEGER PRIMARY KEY, - name TEXT NOT NULL UNIQUE CHECK ( - length(name) < 16 - ), - url TEXT, - path TEXT NOT NULL UNIQUE, - size INTEGER NOT NULL, - type TEXT NOT NULL CHECK ( - type IN ('flat', 'nested') - ) -); -""" - -content = "".join(random.choices(string.ascii_letters, k=500)) - - -def gen_document(): - return [ - md5(random.randbytes(8)).hexdigest(), - json.dumps({ - "content": content, - "mime": "image/jpeg", - "extension": "jpeg", - "name": "test", - "path": "", - }) - ] - - -if __name__ == "__main__": - DB_NAME = "big_index.sist2" - SIZE = 30_000_000 - - os.remove(DB_NAME) - db = sqlite3.connect(DB_NAME) - db.executescript(schema) - - db.executescript(""" - PRAGMA journal_mode = OFF; - PRAGMA synchronous = 0; - """) - - for _ in tqdm(range(SIZE), total=SIZE): - db.execute( - "INSERT INTO document (id, version, mtime, size, json_data) VALUES (?, 1, 1000000, 10000, ?)", - gen_document() - ) - - # 1. Enable rowid from document - # 2. CREATE TABLE marked ( - # id INTEGER PRIMARY KEY, - # marked int - # ); - # 3. Set FK for document_sidecar, embedding, tag, thumbnail - # 4. Toggle FK if debug - - db.commit() diff --git a/scripts/mime.csv b/scripts/mime.csv index e1b25df..6f29883 100644 --- a/scripts/mime.csv +++ b/scripts/mime.csv @@ -449,5 +449,4 @@ image/x-sigma-x3f, xf3 image/x-sony-arw, arw image/x-sony-sr2, sr2 image/x-sony-srf, srf -image/x-epson-erf, erf -sist2/sidecar, s2meta \ No newline at end of file +image/x-epson-erf, erf \ No newline at end of file diff --git a/scripts/mime.py b/scripts/mime.py index 9eae391..d638071 100644 --- a/scripts/mime.py +++ b/scripts/mime.py @@ -3,6 +3,7 @@ import zlib mimes = {} noparse = set() ext_in_hash = set() +mime_ids = {} major_mime = { "sist2": 0, @@ -102,6 +103,9 @@ cnt = 1 def mime_id(mime): + if mime in mime_ids: + return mime_ids[mime] + global cnt major = mime.split("/")[0] mime_id = str((major_mime[major] << 16) + cnt) @@ -127,9 +131,7 @@ def mime_id(mime): elif mime == "application/x-empty": cnt -= 1 return "1" - elif mime == "sist2/sidecar": - cnt -= 1 - return "2" + mime_ids[mime] = mime_id return mime_id @@ -197,4 +199,12 @@ with open("scripts/mime.csv") as f: print(f"case {crc(mime)}: return {clean(mime)};") print("default: return 0;}}") + + # mime list + + mime_list = ",".join(mime_id(x) for x in mimes.keys()) + ",0" + + print(f"unsigned int mime_ids[] = {{{mime_list}}};") + print("unsigned int* get_mime_ids() { return mime_ids; }") + print("#endif") diff --git a/sist2-admin/sist2_admin/app.py b/sist2-admin/sist2_admin/app.py index ab356e9..7195317 100644 --- a/sist2-admin/sist2_admin/app.py +++ b/sist2-admin/sist2_admin/app.py @@ -222,7 +222,10 @@ async def delete_job(name: str): @app.delete("/api/frontend/{name:str}") async def delete_frontend(name: str): if name in RUNNING_FRONTENDS: - os.kill(RUNNING_FRONTENDS[name], signal.SIGTERM) + try: + os.kill(RUNNING_FRONTENDS[name], signal.SIGTERM) + except ProcessLookupError: + pass del RUNNING_FRONTENDS[name] frontend = db["frontends"][name] diff --git a/sist2-vue/package-lock.json b/sist2-vue/package-lock.json index e732e71..9cacbc5 100644 --- a/sist2-vue/package-lock.json +++ b/sist2-vue/package-lock.json @@ -33,7 +33,6 @@ "@types/underscore": "^1.11.6", "@vue/cli-plugin-babel": "~5.0.8", "@vue/cli-plugin-router": "~5.0.8", - "@vue/cli-plugin-typescript": "^5.0.8", "@vue/cli-plugin-vuex": "~5.0.8", "@vue/cli-service": "^5.0.8", "@vue/test-utils": "^1.0.3", @@ -45,7 +44,6 @@ "portal-vue": "^2.1.7", "sass": "^1.26.11", "sass-loader": "^10.0.2", - "typescript": "^4.9.5", "vue-cli-plugin-bootstrap-vue": "~0.8.2", "vue-template-compiler": "^2.6.11" } @@ -2332,12 +2330,6 @@ "integrity": "sha512-G2oC64I/sR817KDL2b2Mc7+diXyxcibyUeLMyexU4K/sG8hyt/YMlbBK0TVhx/YQ1ehfzgXhLuq2YQHIL4bXUQ==", "dev": true }, - "node_modules/@types/webpack-env": { - "version": "1.16.0", - "resolved": "https://registry.npmjs.org/@types/webpack-env/-/webpack-env-1.16.0.tgz", - "integrity": "sha512-Fx+NpfOO0CpeYX2g9bkvX8O5qh9wrU1sOF4g8sft4Mu7z+qfe387YlyY8w8daDyDsKY5vUxM0yxkAYnbkRbZEw==", - "dev": true - }, "node_modules/@types/ws": { "version": "8.5.4", "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.5.4.tgz", @@ -2638,218 +2630,6 @@ "@vue/cli-service": "^3.0.0 || ^4.0.0 || ^5.0.0-0" } }, - "node_modules/@vue/cli-plugin-typescript": { - "version": "5.0.8", - "resolved": "https://registry.npmjs.org/@vue/cli-plugin-typescript/-/cli-plugin-typescript-5.0.8.tgz", - "integrity": "sha512-JKJOwzJshBqsmp4yLBexwVMebOZ4VGJgbnYvmHVxasJOStF2RxwyW28ZF+zIvASGdat4sAUuo/3mAQyVhm7JHg==", - "dev": true, - "dependencies": { - "@babel/core": "^7.12.16", - "@types/webpack-env": "^1.15.2", - "@vue/cli-shared-utils": "^5.0.8", - "babel-loader": "^8.2.2", - "fork-ts-checker-webpack-plugin": "^6.4.0", - "globby": "^11.0.2", - "thread-loader": "^3.0.0", - "ts-loader": "^9.2.5", - "webpack": "^5.54.0" - }, - "peerDependencies": { - "@vue/cli-service": "^3.0.0 || ^4.0.0 || ^5.0.0-0", - "cache-loader": "^4.1.0", - "typescript": ">=2", - "vue": "^2 || ^3.2.13", - "vue-template-compiler": "^2.0.0" - }, - "peerDependenciesMeta": { - "cache-loader": { - "optional": true - }, - "vue-template-compiler": { - "optional": true - } - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dev": true, - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/braces": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", - "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", - "dev": true, - "dependencies": { - "fill-range": "^7.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dev": true, - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dev": true, - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "dev": true - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/fill-range": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", - "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", - "dev": true, - "dependencies": { - "to-regex-range": "^5.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/is-number": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", - "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", - "dev": true, - "engines": { - "node": ">=0.12.0" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/lru-cache": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", - "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", - "dev": true, - "dependencies": { - "yallist": "^4.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/micromatch": { - "version": "4.0.5", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz", - "integrity": "sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==", - "dev": true, - "dependencies": { - "braces": "^3.0.2", - "picomatch": "^2.3.1" - }, - "engines": { - "node": ">=8.6" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/semver": { - "version": "7.5.4", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", - "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", - "dev": true, - "dependencies": { - "lru-cache": "^6.0.0" - }, - "bin": { - "semver": "bin/semver.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dev": true, - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/to-regex-range": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", - "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", - "dev": true, - "dependencies": { - "is-number": "^7.0.0" - }, - "engines": { - "node": ">=8.0" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/ts-loader": { - "version": "9.4.2", - "resolved": "https://registry.npmjs.org/ts-loader/-/ts-loader-9.4.2.tgz", - "integrity": "sha512-OmlC4WVmFv5I0PpaxYb+qGeGOdm5giHU7HwDDUjw59emP2UYMHy9fFSDcYgSNoH8sXcj4hGCSEhlDZ9ULeDraA==", - "dev": true, - "dependencies": { - "chalk": "^4.1.0", - "enhanced-resolve": "^5.0.0", - "micromatch": "^4.0.0", - "semver": "^7.3.4" - }, - "engines": { - "node": ">=12.0.0" - }, - "peerDependencies": { - "typescript": "*", - "webpack": "^5.0.0" - } - }, - "node_modules/@vue/cli-plugin-typescript/node_modules/yallist": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", - "dev": true - }, "node_modules/@vue/cli-plugin-vuex": { "version": "5.0.8", "resolved": "https://registry.npmjs.org/@vue/cli-plugin-vuex/-/cli-plugin-vuex-5.0.8.tgz", @@ -4279,14 +4059,6 @@ "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==", "dev": true }, - "node_modules/buffer-json": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/buffer-json/-/buffer-json-2.0.0.tgz", - "integrity": "sha512-+jjPFVqyfF1esi9fvfUs3NqM0pH1ziZ36VP4hmA/y/Ssfo/5w5xHKfTw9BwQjoJ1w/oVtpLomqwUHKdefGyuHw==", - "dev": true, - "optional": true, - "peer": true - }, "node_modules/bytes": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", @@ -4296,25 +4068,6 @@ "node": ">= 0.8" } }, - "node_modules/cache-loader": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/cache-loader/-/cache-loader-4.1.0.tgz", - "integrity": "sha512-ftOayxve0PwKzBF/GLsZNC9fJBXl8lkZE3TOsjkboHfVHVkL39iUEs1FO07A33mizmci5Dudt38UZrrYXDtbhw==", - "dev": true, - "optional": true, - "peer": true, - "dependencies": { - "buffer-json": "^2.0.0", - "find-cache-dir": "^3.0.0", - "loader-utils": "^1.2.3", - "mkdirp": "^0.5.1", - "neo-async": "^2.6.1", - "schema-utils": "^2.0.0" - }, - "engines": { - "node": ">= 8.9.0" - } - }, "node_modules/call-bind": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", @@ -4938,22 +4691,6 @@ "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", "dev": true }, - "node_modules/cosmiconfig": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-6.0.0.tgz", - "integrity": "sha512-xb3ZL6+L8b9JLLCx3ZdoZy4+2ECphCMo2PwqgP1tlfVq6M6YReyzBJtvWWtbDSpNr9hn96pkCiZqUcFEc+54Qg==", - "dev": true, - "dependencies": { - "@types/parse-json": "^4.0.0", - "import-fresh": "^3.1.0", - "parse-json": "^5.0.0", - "path-type": "^4.0.0", - "yaml": "^1.7.2" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/cross-spawn": { "version": "6.0.5", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", @@ -5442,15 +5179,6 @@ "node": ">=6.0" } }, - "node_modules/deepmerge": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz", - "integrity": "sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/default-gateway": { "version": "6.0.3", "resolved": "https://registry.npmjs.org/default-gateway/-/default-gateway-6.0.3.tgz", @@ -6392,166 +6120,6 @@ } } }, - "node_modules/fork-ts-checker-webpack-plugin": { - "version": "6.5.2", - "resolved": "https://registry.npmjs.org/fork-ts-checker-webpack-plugin/-/fork-ts-checker-webpack-plugin-6.5.2.tgz", - "integrity": "sha512-m5cUmF30xkZ7h4tWUgTAcEaKmUW7tfyUyTqNNOz7OxWJ0v1VWKTcOvH8FWHUwSjlW/356Ijc9vi3XfcPstpQKA==", - "dev": true, - "dependencies": { - "@babel/code-frame": "^7.8.3", - "@types/json-schema": "^7.0.5", - "chalk": "^4.1.0", - "chokidar": "^3.4.2", - "cosmiconfig": "^6.0.0", - "deepmerge": "^4.2.2", - "fs-extra": "^9.0.0", - "glob": "^7.1.6", - "memfs": "^3.1.2", - "minimatch": "^3.0.4", - "schema-utils": "2.7.0", - "semver": "^7.3.2", - "tapable": "^1.0.0" - }, - "engines": { - "node": ">=10", - "yarn": ">=1.0.0" - }, - "peerDependencies": { - "eslint": ">= 6", - "typescript": ">= 2.7", - "vue-template-compiler": "*", - "webpack": ">= 4" - }, - "peerDependenciesMeta": { - "eslint": { - "optional": true - }, - "vue-template-compiler": { - "optional": true - } - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dev": true, - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dev": true, - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dev": true, - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "dev": true - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/lru-cache": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", - "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", - "dev": true, - "dependencies": { - "yallist": "^4.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/schema-utils": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-2.7.0.tgz", - "integrity": "sha512-0ilKFI6QQF5nxDZLFn2dMjvc4hjg/Wkg7rHd3jK6/A4a1Hl9VFdQWvgB1UMGoU94pad1P/8N7fMcEnLnSiju8A==", - "dev": true, - "dependencies": { - "@types/json-schema": "^7.0.4", - "ajv": "^6.12.2", - "ajv-keywords": "^3.4.1" - }, - "engines": { - "node": ">= 8.9.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/semver": { - "version": "7.5.4", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", - "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", - "dev": true, - "dependencies": { - "lru-cache": "^6.0.0" - }, - "bin": { - "semver": "bin/semver.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dev": true, - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/yallist": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", - "dev": true - }, "node_modules/forwarded": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", @@ -10503,15 +10071,6 @@ "node": ">= 10" } }, - "node_modules/tapable": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.1.3.tgz", - "integrity": "sha512-4WK/bYZmj8xLr+HUCODHGF1ZFzsYffasLUgEiMBY4fgtltdO6B4WJtlSbPaDTLpYTcGVwM2qLnFTICEcNxs3kA==", - "dev": true, - "engines": { - "node": ">=6" - } - }, "node_modules/terser": { "version": "5.16.1", "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.1.tgz", @@ -10732,19 +10291,6 @@ "node": ">= 0.6" } }, - "node_modules/typescript": { - "version": "4.9.5", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", - "integrity": "sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==", - "dev": true, - "bin": { - "tsc": "bin/tsc", - "tsserver": "bin/tsserver" - }, - "engines": { - "node": ">=4.2.0" - } - }, "node_modules/underscore": { "version": "1.13.1", "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.13.1.tgz", @@ -13492,12 +13038,6 @@ "integrity": "sha512-G2oC64I/sR817KDL2b2Mc7+diXyxcibyUeLMyexU4K/sG8hyt/YMlbBK0TVhx/YQ1ehfzgXhLuq2YQHIL4bXUQ==", "dev": true }, - "@types/webpack-env": { - "version": "1.16.0", - "resolved": "https://registry.npmjs.org/@types/webpack-env/-/webpack-env-1.16.0.tgz", - "integrity": "sha512-Fx+NpfOO0CpeYX2g9bkvX8O5qh9wrU1sOF4g8sft4Mu7z+qfe387YlyY8w8daDyDsKY5vUxM0yxkAYnbkRbZEw==", - "dev": true - }, "@types/ws": { "version": "8.5.4", "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.5.4.tgz", @@ -13736,153 +13276,6 @@ "@vue/cli-shared-utils": "^5.0.8" } }, - "@vue/cli-plugin-typescript": { - "version": "5.0.8", - "resolved": "https://registry.npmjs.org/@vue/cli-plugin-typescript/-/cli-plugin-typescript-5.0.8.tgz", - "integrity": "sha512-JKJOwzJshBqsmp4yLBexwVMebOZ4VGJgbnYvmHVxasJOStF2RxwyW28ZF+zIvASGdat4sAUuo/3mAQyVhm7JHg==", - "dev": true, - "requires": { - "@babel/core": "^7.12.16", - "@types/webpack-env": "^1.15.2", - "@vue/cli-shared-utils": "^5.0.8", - "babel-loader": "^8.2.2", - "fork-ts-checker-webpack-plugin": "^6.4.0", - "globby": "^11.0.2", - "thread-loader": "^3.0.0", - "ts-loader": "^9.2.5", - "webpack": "^5.54.0" - }, - "dependencies": { - "ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dev": true, - "requires": { - "color-convert": "^2.0.1" - } - }, - "braces": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", - "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", - "dev": true, - "requires": { - "fill-range": "^7.0.1" - } - }, - "chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dev": true, - "requires": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - } - }, - "color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dev": true, - "requires": { - "color-name": "~1.1.4" - } - }, - "color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "dev": true - }, - "fill-range": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", - "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", - "dev": true, - "requires": { - "to-regex-range": "^5.0.1" - } - }, - "has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true - }, - "is-number": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", - "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", - "dev": true - }, - "lru-cache": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", - "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", - "dev": true, - "requires": { - "yallist": "^4.0.0" - } - }, - "micromatch": { - "version": "4.0.5", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz", - "integrity": "sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==", - "dev": true, - "requires": { - "braces": "^3.0.2", - "picomatch": "^2.3.1" - } - }, - "semver": { - "version": "7.5.4", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", - "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", - "dev": true, - "requires": { - "lru-cache": "^6.0.0" - } - }, - "supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dev": true, - "requires": { - "has-flag": "^4.0.0" - } - }, - "to-regex-range": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", - "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", - "dev": true, - "requires": { - "is-number": "^7.0.0" - } - }, - "ts-loader": { - "version": "9.4.2", - "resolved": "https://registry.npmjs.org/ts-loader/-/ts-loader-9.4.2.tgz", - "integrity": "sha512-OmlC4WVmFv5I0PpaxYb+qGeGOdm5giHU7HwDDUjw59emP2UYMHy9fFSDcYgSNoH8sXcj4hGCSEhlDZ9ULeDraA==", - "dev": true, - "requires": { - "chalk": "^4.1.0", - "enhanced-resolve": "^5.0.0", - "micromatch": "^4.0.0", - "semver": "^7.3.4" - } - }, - "yallist": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", - "dev": true - } - } - }, "@vue/cli-plugin-vuex": { "version": "5.0.8", "resolved": "https://registry.npmjs.org/@vue/cli-plugin-vuex/-/cli-plugin-vuex-5.0.8.tgz", @@ -14956,36 +14349,12 @@ "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==", "dev": true }, - "buffer-json": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/buffer-json/-/buffer-json-2.0.0.tgz", - "integrity": "sha512-+jjPFVqyfF1esi9fvfUs3NqM0pH1ziZ36VP4hmA/y/Ssfo/5w5xHKfTw9BwQjoJ1w/oVtpLomqwUHKdefGyuHw==", - "dev": true, - "optional": true, - "peer": true - }, "bytes": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", "integrity": "sha512-pMhOfFDPiv9t5jjIXkHosWmkSyQbvsgEVNkz0ERHbuLh2T/7j4Mqqpz523Fe8MVY89KC6Sh/QfS2sM+SjgFDcw==", "dev": true }, - "cache-loader": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/cache-loader/-/cache-loader-4.1.0.tgz", - "integrity": "sha512-ftOayxve0PwKzBF/GLsZNC9fJBXl8lkZE3TOsjkboHfVHVkL39iUEs1FO07A33mizmci5Dudt38UZrrYXDtbhw==", - "dev": true, - "optional": true, - "peer": true, - "requires": { - "buffer-json": "^2.0.0", - "find-cache-dir": "^3.0.0", - "loader-utils": "^1.2.3", - "mkdirp": "^0.5.1", - "neo-async": "^2.6.1", - "schema-utils": "^2.0.0" - } - }, "call-bind": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", @@ -15467,19 +14836,6 @@ "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", "dev": true }, - "cosmiconfig": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-6.0.0.tgz", - "integrity": "sha512-xb3ZL6+L8b9JLLCx3ZdoZy4+2ECphCMo2PwqgP1tlfVq6M6YReyzBJtvWWtbDSpNr9hn96pkCiZqUcFEc+54Qg==", - "dev": true, - "requires": { - "@types/parse-json": "^4.0.0", - "import-fresh": "^3.1.0", - "parse-json": "^5.0.0", - "path-type": "^4.0.0", - "yaml": "^1.7.2" - } - }, "cross-spawn": { "version": "6.0.5", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", @@ -15899,12 +15255,6 @@ "ms": "2.1.2" } }, - "deepmerge": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz", - "integrity": "sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==", - "dev": true - }, "default-gateway": { "version": "6.0.3", "resolved": "https://registry.npmjs.org/default-gateway/-/default-gateway-6.0.3.tgz", @@ -16636,113 +15986,6 @@ "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.2.tgz", "integrity": "sha512-VQLG33o04KaQ8uYi2tVNbdrWp1QWxNNea+nmIB4EVM28v0hmP17z7aG1+wAkNzVq4KeXTq3221ye5qTJP91JwA==" }, - "fork-ts-checker-webpack-plugin": { - "version": "6.5.2", - "resolved": "https://registry.npmjs.org/fork-ts-checker-webpack-plugin/-/fork-ts-checker-webpack-plugin-6.5.2.tgz", - "integrity": "sha512-m5cUmF30xkZ7h4tWUgTAcEaKmUW7tfyUyTqNNOz7OxWJ0v1VWKTcOvH8FWHUwSjlW/356Ijc9vi3XfcPstpQKA==", - "dev": true, - "requires": { - "@babel/code-frame": "^7.8.3", - "@types/json-schema": "^7.0.5", - "chalk": "^4.1.0", - "chokidar": "^3.4.2", - "cosmiconfig": "^6.0.0", - "deepmerge": "^4.2.2", - "fs-extra": "^9.0.0", - "glob": "^7.1.6", - "memfs": "^3.1.2", - "minimatch": "^3.0.4", - "schema-utils": "2.7.0", - "semver": "^7.3.2", - "tapable": "^1.0.0" - }, - "dependencies": { - "ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dev": true, - "requires": { - "color-convert": "^2.0.1" - } - }, - "chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dev": true, - "requires": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - } - }, - "color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dev": true, - "requires": { - "color-name": "~1.1.4" - } - }, - "color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "dev": true - }, - "has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true - }, - "lru-cache": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", - "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", - "dev": true, - "requires": { - "yallist": "^4.0.0" - } - }, - "schema-utils": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-2.7.0.tgz", - "integrity": "sha512-0ilKFI6QQF5nxDZLFn2dMjvc4hjg/Wkg7rHd3jK6/A4a1Hl9VFdQWvgB1UMGoU94pad1P/8N7fMcEnLnSiju8A==", - "dev": true, - "requires": { - "@types/json-schema": "^7.0.4", - "ajv": "^6.12.2", - "ajv-keywords": "^3.4.1" - } - }, - "semver": { - "version": "7.5.4", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", - "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", - "dev": true, - "requires": { - "lru-cache": "^6.0.0" - } - }, - "supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dev": true, - "requires": { - "has-flag": "^4.0.0" - } - }, - "yallist": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", - "dev": true - } - } - }, "forwarded": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", @@ -19757,12 +19000,6 @@ } } }, - "tapable": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.1.3.tgz", - "integrity": "sha512-4WK/bYZmj8xLr+HUCODHGF1ZFzsYffasLUgEiMBY4fgtltdO6B4WJtlSbPaDTLpYTcGVwM2qLnFTICEcNxs3kA==", - "dev": true - }, "terser": { "version": "5.16.1", "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.1.tgz", @@ -19912,12 +19149,6 @@ "mime-types": "~2.1.24" } }, - "typescript": { - "version": "4.9.5", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", - "integrity": "sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==", - "dev": true - }, "underscore": { "version": "1.13.1", "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.13.1.tgz", diff --git a/sist2-vue/package.json b/sist2-vue/package.json index 81e6399..b7c07c9 100644 --- a/sist2-vue/package.json +++ b/sist2-vue/package.json @@ -32,7 +32,6 @@ "@types/underscore": "^1.11.6", "@vue/cli-plugin-babel": "~5.0.8", "@vue/cli-plugin-router": "~5.0.8", - "@vue/cli-plugin-typescript": "^5.0.8", "@vue/cli-plugin-vuex": "~5.0.8", "@vue/cli-service": "^5.0.8", "@vue/test-utils": "^1.0.3", @@ -44,7 +43,6 @@ "portal-vue": "^2.1.7", "sass": "^1.26.11", "sass-loader": "^10.0.2", - "typescript": "^4.9.5", "vue-cli-plugin-bootstrap-vue": "~0.8.2", "vue-template-compiler": "^2.6.11" }, diff --git a/sist2-vue/src/Sist2Api.ts b/sist2-vue/src/Sist2Api.js similarity index 72% rename from sist2-vue/src/Sist2Api.ts rename to sist2-vue/src/Sist2Api.js index 653d003..c820be3 100644 --- a/sist2-vue/src/Sist2Api.ts +++ b/sist2-vue/src/Sist2Api.js @@ -1,116 +1,20 @@ import axios from "axios"; -import {ext, strUnescape, lum} from "./util"; +import {strUnescape, lum, sid} from "./util"; import Sist2Query from "@/Sist2ElasticsearchQuery"; import store from "@/store"; -export interface EsTag { - id: string - count: number - color: string | undefined - isLeaf: boolean -} - -export interface Tag { - style: string - text: string - rawText: string - fg: string - bg: string - userTag: boolean -} - -export interface Index { - name: string - version: string - id: string - idPrefix: string - timestamp: number - models: [] -} - -export interface EsHit { - _index: string - _id: string - _score: number - _type: string - _tags: Tag[] - _seq: number - _source: { - path: string - size: number - mime: string - name: string - extension: string - index: string - _depth: number - mtime: number - videoc: string - audioc: string - parent: string - width: number - height: number - duration: number - tag: string[] - checksum: string - thumbnail: string - } - _props: { - isSubDocument: boolean - isImage: boolean - isGif: boolean - isVideo: boolean - isPlayableVideo: boolean - isPlayableImage: boolean - isAudio: boolean - hasThumbnail: boolean - hasVidPreview: boolean - imageAspectRatio: number - /** Number of thumbnails available */ - tnNum: number - } - highlight: { - name: string[] | undefined, - content: string[] | undefined, - } -} - -function getIdPrefix(indices: Index[], id: string): string { - for (let i = 4; i < 32; i++) { - const prefix = id.slice(0, i); - - if (indices.filter(idx => idx.id.slice(0, i) == prefix).length == 1) { - return prefix; - } - } - - return id; -} - -export interface EsResult { - took: number - - hits: { - // TODO: ES 6.X ? - total: { - value: number - } - hits: EsHit[] - } - - aggregations: any -} class Sist2Api { - private readonly baseUrl: string - private sist2Info: any - private queryfunc: () => EsResult; + baseUrl; + sist2Info; + queryfunc; - constructor(baseUrl: string) { + constructor(baseUrl) { this.baseUrl = baseUrl; } - init(queryFunc: () => EsResult) { + init(queryFunc) { this.queryfunc = queryFunc; } @@ -127,9 +31,9 @@ class Sist2Api { .filter((v, i, a) => a.findIndex(v2 => (v2.id === v.id)) === i) } - getSist2Info(): Promise { + getSist2Info() { return axios.get(`${this.baseUrl}i`).then(resp => { - const indices = resp.data.indices as Index[]; + const indices = resp.data.indices; resp.data.indices = indices.map(idx => { return { @@ -138,8 +42,7 @@ class Sist2Api { timestamp: idx.timestamp, version: idx.version, models: idx.models, - idPrefix: getIdPrefix(indices, idx.id), - } as Index; + }; }); this.sist2Info = resp.data; @@ -148,8 +51,8 @@ class Sist2Api { }) } - setHitProps(hit: EsHit): void { - hit["_props"] = {} as any; + setHitProps(hit) { + hit["_props"] = {}; const mimeCategory = hit._source.mime == null ? null : hit._source.mime.split("/")[0]; @@ -157,7 +60,7 @@ class Sist2Api { hit._props.isSubDocument = true; } - if ("thumbnail" in hit._source) { + if ("thumbnail" in hit._source && hit._source.thumbnail > 0) { hit._props.hasThumbnail = true; if (Number.isNaN(Number(hit._source.thumbnail))) { @@ -213,8 +116,8 @@ class Sist2Api { } } - setHitTags(hit: EsHit): void { - const tags = [] as Tag[]; + setHitTags(hit) { + const tags = []; // User tags if ("tag" in hit._source) { @@ -226,10 +129,10 @@ class Sist2Api { hit._tags = tags; } - createUserTag(tag: string): Tag { + createUserTag(tag) { const tokens = tag.split("."); - const colorToken = tokens.pop() as string; + const colorToken = tokens.pop(); const bg = colorToken; const fg = lum(colorToken) > 50 ? "#000" : "#fff"; @@ -241,23 +144,23 @@ class Sist2Api { text: tokens.join("."), rawText: tag, userTag: true, - } as Tag; + }; } - search(): Promise { - if (this.backend() == "sqlite") { + search() { + if (this.backend() === "sqlite") { return this.ftsQuery(this.queryfunc()) } else { return this.esQuery(this.queryfunc()); } } - esQuery(query: any): Promise { + esQuery(query) { return axios.post(`${this.baseUrl}es`, query).then(resp => { - const res = resp.data as EsResult; + const res = resp.data; if (res.hits?.hits) { - res.hits.hits.forEach((hit: EsHit) => { + res.hits.hits.forEach((hit) => { hit["_source"]["name"] = strUnescape(hit["_source"]["name"]); hit["_source"]["path"] = strUnescape(hit["_source"]["path"]); @@ -270,9 +173,9 @@ class Sist2Api { }); } - ftsQuery(query: any): Promise { + ftsQuery(query) { return axios.post(`${this.baseUrl}fts/search`, query).then(resp => { - const res = resp.data as any; + const res = resp.data; if (res.hits.hits) { res.hits.hits.forEach(hit => { @@ -293,7 +196,7 @@ class Sist2Api { }); } - private getMimeTypesEs(query) { + getMimeTypesEs(query) { const AGGS = { mimeTypes: { terms: { @@ -322,7 +225,7 @@ class Sist2Api { }); } - private getMimeTypesSqlite(): Promise<[{ mime: string, count: number }]> { + getMimeTypesSqlite() { return axios.get(`${this.baseUrl}fts/mimetypes`) .then(resp => { return resp.data; @@ -332,15 +235,15 @@ class Sist2Api { async getMimeTypes(query = undefined) { let buckets; - if (this.backend() == "sqlite") { + if (this.backend() === "sqlite") { buckets = await this.getMimeTypesSqlite(); } else { buckets = await this.getMimeTypesEs(query); } - const mimeMap: any[] = []; + const mimeMap = []; - buckets.sort((a: any, b: any) => a.mime > b.mime).forEach((bucket: any) => { + buckets.sort((a, b) => a.mime > b.mime).forEach((bucket) => { const tmp = bucket.mime.split("/"); const category = tmp[0]; const mime = tmp[1]; @@ -374,7 +277,7 @@ class Sist2Api { return {buckets, mimeMap}; } - _createEsTag(tag: string, count: number): EsTag { + _createEsTag(tag, count) { const tokens = tag.split("."); if (/.*\.#[0-9a-fA-F]{6}/.test(tag)) { @@ -394,7 +297,7 @@ class Sist2Api { }; } - private getTagsEs() { + getTagsEs() { return this.esQuery({ aggs: { tags: { @@ -407,21 +310,21 @@ class Sist2Api { size: 0, }).then(resp => { return resp["aggregations"]["tags"]["buckets"] - .sort((a: any, b: any) => a["key"].localeCompare(b["key"])) - .map((bucket: any) => this._createEsTag(bucket["key"], bucket["doc_count"])); + .sort((a, b) => a["key"].localeCompare(b["key"])) + .map((bucket) => this._createEsTag(bucket["key"], bucket["doc_count"])); }); } - private getTagsSqlite() { + getTagsSqlite() { return axios.get(`${this.baseUrl}/fts/tags`) .then(resp => { return resp.data.map(tag => this._createEsTag(tag.tag, tag.count)) }); } - async getTags(): Promise { + async getTags() { let tags; - if (this.backend() == "sqlite") { + if (this.backend() === "sqlite") { tags = await this.getTagsSqlite(); } else { tags = await this.getTagsEs(); @@ -430,7 +333,7 @@ class Sist2Api { // Remove duplicates (same tag with different color) const seen = new Set(); - return tags.filter((t: EsTag) => { + return tags.filter((t) => { if (seen.has(t.id)) { return false; } @@ -439,31 +342,29 @@ class Sist2Api { }); } - saveTag(tag: string, hit: EsHit) { - return axios.post(`${this.baseUrl}tag/` + hit["_source"]["index"], { + saveTag(tag, hit) { + return axios.post(`${this.baseUrl}tag/${sid(hit)}`, { delete: false, name: tag, - doc_id: hit["_id"] }); } - deleteTag(tag: string, hit: EsHit) { - return axios.post(`${this.baseUrl}tag/` + hit["_source"]["index"], { + deleteTag(tag, hit) { + return axios.post(`${this.baseUrl}tag/${sid(hit)}`, { delete: true, name: tag, - doc_id: hit["_id"] }); } searchPaths(indexId, minDepth, maxDepth, prefix = null) { - if (this.backend() == "sqlite") { + if (this.backend() === "sqlite") { return this.searchPathsSqlite(indexId, minDepth, minDepth, prefix); } else { return this.searchPathsEs(indexId, minDepth, maxDepth, prefix); } } - private searchPathsSqlite(indexId, minDepth, maxDepth, prefix) { + searchPathsSqlite(indexId, minDepth, maxDepth, prefix) { return axios.post(`${this.baseUrl}fts/paths`, { indexId, minDepth, maxDepth, prefix }).then(resp => { @@ -471,7 +372,7 @@ class Sist2Api { }); } - private searchPathsEs(indexId, minDepth, maxDepth, prefix): Promise<[{ path: string, count: number }]> { + searchPathsEs(indexId, minDepth, maxDepth, prefix) { const query = { query: { @@ -516,7 +417,7 @@ class Sist2Api { }); } - private getDateRangeSqlite() { + getDateRangeSqlite() { return axios.get(`${this.baseUrl}fts/dateRange`) .then(resp => ({ min: resp.data.dateMin, @@ -524,15 +425,15 @@ class Sist2Api { })); } - getDateRange(): Promise<{ min: number, max: number }> { - if (this.backend() == "sqlite") { + getDateRange() { + if (this.backend() === "sqlite") { return this.getDateRangeSqlite(); } else { return this.getDateRangeEs(); } } - private getDateRangeEs() { + getDateRangeEs() { return this.esQuery({ // TODO: filter current selected indices aggs: { @@ -549,7 +450,7 @@ class Sist2Api { if (range.min == null) { range.min = 0; range.max = 1; - } else if (range.min == range.max) { + } else if (range.min === range.max) { range.max += 1; } @@ -557,7 +458,7 @@ class Sist2Api { }); } - private getPathSuggestionsSqlite(text: string) { + getPathSuggestionsSqlite(text) { return axios.post(`${this.baseUrl}fts/paths`, { prefix: text, minDepth: 1, @@ -567,7 +468,7 @@ class Sist2Api { }) } - private getPathSuggestionsEs(text) { + getPathSuggestionsEs(text) { return this.esQuery({ suggest: { path: { @@ -585,31 +486,31 @@ class Sist2Api { }); } - getPathSuggestions(text: string): Promise { - if (this.backend() == "sqlite") { + getPathSuggestions(text) { + if (this.backend() === "sqlite") { return this.getPathSuggestionsSqlite(text); } else { return this.getPathSuggestionsEs(text) } } - getTreemapStat(indexId: string) { + getTreemapStat(indexId) { return `${this.baseUrl}s/${indexId}/TMAP`; } - getMimeStat(indexId: string) { + getMimeStat(indexId) { return `${this.baseUrl}s/${indexId}/MAGG`; } - getSizeStat(indexId: string) { + getSizeStat(indexId) { return `${this.baseUrl}s/${indexId}/SAGG`; } - getDateStat(indexId: string) { + getDateStat(indexId) { return `${this.baseUrl}s/${indexId}/DAGG`; } - private getDocumentEs(docId: string, highlight: boolean, fuzzy: boolean) { + getDocumentEs(sid, highlight, fuzzy) { const query = Sist2Query.searchQuery(); if (highlight) { @@ -648,7 +549,7 @@ class Sist2Api { query.query.bool.must = [query.query.bool.must]; } - query.query.bool.must.push({match: {_id: docId}}); + query.query.bool.must.push({match: {_id: sid}}); delete query["sort"]; delete query["aggs"]; @@ -669,35 +570,35 @@ class Sist2Api { }); } - private getDocumentSqlite(docId: string): Promise { - return axios.get(`${this.baseUrl}/fts/d/${docId}`) + getDocumentSqlite(sid) { + return axios.get(`${this.baseUrl}/fts/d/${sid}`) .then(resp => ({ _source: resp.data - } as EsHit)); + })); } - getDocument(docId: string, highlight: boolean, fuzzy: boolean): Promise { - if (this.backend() == "sqlite") { - return this.getDocumentSqlite(docId); + getDocument(sid, highlight, fuzzy) { + if (this.backend() === "sqlite") { + return this.getDocumentSqlite(sid); } else { - return this.getDocumentEs(docId, highlight, fuzzy); + return this.getDocumentEs(sid, highlight, fuzzy); } } - getTagSuggestions(prefix: string): Promise { - if (this.backend() == "sqlite") { + getTagSuggestions(prefix) { + if (this.backend() === "sqlite") { return this.getTagSuggestionsSqlite(prefix); } else { return this.getTagSuggestionsEs(prefix); } } - private getTagSuggestionsSqlite(prefix): Promise { + getTagSuggestionsSqlite(prefix) { return axios.post(`${this.baseUrl}/fts/suggestTags`, prefix) .then(resp => (resp.data)); } - private getTagSuggestionsEs(prefix): Promise { + getTagSuggestionsEs(prefix) { return this.esQuery({ suggest: { tag: { @@ -723,8 +624,8 @@ class Sist2Api { }); } - getEmbeddings(indexId, docId, modelId) { - return axios.post(`${this.baseUrl}/e/${indexId}/${docId}/${modelId.toString().padStart(3, '0')}`) + getEmbeddings(sid, modelId) { + return axios.post(`${this.baseUrl}/e/${sid}/${modelId.toString().padStart(3, '0')}`) .then(resp => (resp.data)); } } diff --git a/sist2-vue/src/Sist2ElasticsearchQuery.ts b/sist2-vue/src/Sist2ElasticsearchQuery.js similarity index 91% rename from sist2-vue/src/Sist2ElasticsearchQuery.ts rename to sist2-vue/src/Sist2ElasticsearchQuery.js index ce1d917..2871406 100644 --- a/sist2-vue/src/Sist2ElasticsearchQuery.ts +++ b/sist2-vue/src/Sist2ElasticsearchQuery.js @@ -1,5 +1,5 @@ -import store from "./store"; -import sist2Api, {EsHit, Index} from "@/Sist2Api"; +import store from "@/store"; +import Sist2Api from "@/Sist2Api"; const SORT_MODES = { score: { @@ -7,62 +7,62 @@ const SORT_MODES = { {_score: {order: "desc"}}, {_tie: {order: "asc"}} ], - key: (hit: EsHit) => hit._score + key: (hit) => hit._score }, random: { mode: [ {_score: {order: "desc"}}, {_tie: {order: "asc"}} ], - key: (hit: EsHit) => hit._score + key: (hit) => hit._score }, dateAsc: { mode: [ {mtime: {order: "asc"}}, {_tie: {order: "asc"}} ], - key: (hit: EsHit) => hit._source.mtime + key: (hit) => hit._source.mtime }, dateDesc: { mode: [ {mtime: {order: "desc"}}, {_tie: {order: "asc"}} ], - key: (hit: EsHit) => hit._source.mtime + key: (hit) => hit._source.mtime }, sizeAsc: { mode: [ {size: {order: "asc"}}, {_tie: {order: "asc"}} ], - key: (hit: EsHit) => hit._source.size + key: (hit) => hit._source.size }, sizeDesc: { mode: [ {size: {order: "desc"}}, {_tie: {order: "asc"}} ], - key: (hit: EsHit) => hit._source.size + key: (hit) => hit._source.size }, nameAsc: { mode: [ {name: {order: "asc"}}, {_tie: {order: "asc"}} ], - key: (hit: EsHit) => hit._source.name + key: (hit) => hit._source.name }, nameDesc: { mode: [ {name: {order: "desc"}}, {_tie: {order: "asc"}} ], - key: (hit: EsHit) => hit._source.name + key: (hit) => hit._source.name } -} as any; +}; class Sist2ElasticsearchQuery { - searchQuery(blankSearch: boolean = false): any { + searchQuery(blankSearch = false) { const getters = store.getters; @@ -76,7 +76,7 @@ class Sist2ElasticsearchQuery { const fuzzy = getters.fuzzy; const size = getters.size; const after = getters.lastDoc; - const selectedIndexIds = getters.selectedIndices.map((idx: Index) => idx.id) + const selectedIndexIds = getters.selectedIndices.map((idx) => idx.id) const selectedMimeTypes = getters.selectedMimeTypes; const selectedTags = getters.selectedTags; const sortMode = getters.embedding ? "score" : getters.sortMode; @@ -86,7 +86,7 @@ class Sist2ElasticsearchQuery { const filters = [ {terms: {index: selectedIndexIds}} - ] as any[]; + ]; const fields = [ "name^8", @@ -138,7 +138,7 @@ class Sist2ElasticsearchQuery { if (getters.optTagOrOperator) { filters.push({terms: {"tag": selectedTags}}); } else { - selectedTags.forEach((tag: string) => filters.push({term: {"tag": tag}})); + selectedTags.forEach((tag) => filters.push({term: {"tag": tag}})); } } } @@ -173,7 +173,7 @@ class Sist2ElasticsearchQuery { }, sort: SORT_MODES[sortMode].mode, size: size, - } as any; + }; if (!after) { q.aggs = { @@ -193,7 +193,7 @@ class Sist2ElasticsearchQuery { if (getters.embedding) { delete q.query; - const field = "emb." + sist2Api.models().find(m => m.id == getters.embeddingsModel).path; + const field = "emb." + Sist2Api.models().find(m => m.id === getters.embeddingsModel).path; if (hasKnn) { // Use knn (8.8+) diff --git a/sist2-vue/src/Sist2SqliteQuery.ts b/sist2-vue/src/Sist2SqliteQuery.js similarity index 89% rename from sist2-vue/src/Sist2SqliteQuery.ts rename to sist2-vue/src/Sist2SqliteQuery.js index 1a4e789..1c78886 100644 --- a/sist2-vue/src/Sist2SqliteQuery.ts +++ b/sist2-vue/src/Sist2SqliteQuery.js @@ -1,5 +1,4 @@ -import store from "./store"; -import {EsHit, Index} from "@/Sist2Api"; +import store from "@/store"; const SORT_MODES = { score: { @@ -29,18 +28,12 @@ const SORT_MODES = { "sort": "name", "sortAsc": false } -} as any; - -interface SortMode { - text: string - mode: any[] - key: (hit: EsHit) => any -} +}; class Sist2ElasticsearchQuery { - searchQuery(): any { + searchQuery() { const getters = store.getters; @@ -52,7 +45,7 @@ class Sist2ElasticsearchQuery { const dateMax = getters.dateMax; const size = getters.size; const after = getters.lastDoc; - const selectedIndexIds = getters.selectedIndices.map((idx: Index) => idx.id) + const selectedIndexIds = getters.selectedIndices.map((idx) => idx.id) const selectedMimeTypes = getters.selectedMimeTypes; const selectedTags = getters.selectedTags; @@ -95,7 +88,7 @@ class Sist2ElasticsearchQuery { if (selectedTags.length > 0) { q["tags"] = selectedTags } - if (getters.sortMode == "random") { + if (getters.sortMode === "random") { q["seed"] = getters.seed; } if (getters.optHighlight) { @@ -108,7 +101,7 @@ class Sist2ElasticsearchQuery { q["embedding"] = getters.embedding; q["sort"] = "embedding"; q["sortAsc"] = false; - } else if (getters.sortMode == "embedding") { + } else if (getters.sortMode === "embedding") { q["sort"] = "sort" q["sortAsc"] = true; } diff --git a/sist2-vue/src/components/D3Treemap.vue b/sist2-vue/src/components/D3Treemap.vue index cd8d8af..801896c 100644 --- a/sist2-vue/src/components/D3Treemap.vue +++ b/sist2-vue/src/components/D3Treemap.vue @@ -9,8 +9,7 @@ diff --git a/sist2-vue/src/components/DocFileTitle.vue b/sist2-vue/src/components/DocFileTitle.vue index f7cf4a1..cabcd4d 100644 --- a/sist2-vue/src/components/DocFileTitle.vue +++ b/sist2-vue/src/components/DocFileTitle.vue @@ -1,5 +1,5 @@ diff --git a/sist2-vue/src/components/DocList.vue b/sist2-vue/src/components/DocList.vue index 0f05c2d..895fa1e 100644 --- a/sist2-vue/src/components/DocList.vue +++ b/sist2-vue/src/components/DocList.vue @@ -1,45 +1,49 @@ - \ No newline at end of file diff --git a/sist2-vue/src/components/DocListItem.vue b/sist2-vue/src/components/DocListItem.vue index 6e4e607..4f5a600 100644 --- a/sist2-vue/src/components/DocListItem.vue +++ b/sist2-vue/src/components/DocListItem.vue @@ -17,10 +17,10 @@ - @@ -70,6 +70,7 @@ import FileIcon from "@/components/icons/FileIcon"; import FeaturedFieldsLine from "@/components/FeaturedFieldsLine"; import MLIcon from "@/components/icons/MlIcon.vue"; import Sist2Api from "@/Sist2Api"; +import {sid} from "@/util"; export default { name: "DocListItem", @@ -82,12 +83,13 @@ export default { } }, methods: { + sid: sid, async onThumbnailClick() { this.$store.commit("setUiLightboxSlide", this.doc._seq); await this.$store.dispatch("showLightbox"); }, onEmbeddingClick() { - Sist2Api.getEmbeddings(this.doc._source.index, this.doc._id, this.$store.state.embeddingsModel).then(embeddings => { + Sist2Api.getEmbeddings(sid(this.doc), this.$store.state.embeddingsModel).then(embeddings => { this.$store.commit("setEmbeddingText", ""); this.$store.commit("setEmbedding", embeddings); this.$store.commit("setEmbeddingDoc", this.doc); diff --git a/sist2-vue/src/components/FullThumbnail.vue b/sist2-vue/src/components/FullThumbnail.vue index 0077d71..4627b19 100644 --- a/sist2-vue/src/components/FullThumbnail.vue +++ b/sist2-vue/src/components/FullThumbnail.vue @@ -1,188 +1,189 @@ \ No newline at end of file diff --git a/sist2-vue/src/components/IndexPicker.vue b/sist2-vue/src/components/IndexPicker.vue index 0c0c47f..38d12fe 100644 --- a/sist2-vue/src/components/IndexPicker.vue +++ b/sist2-vue/src/components/IndexPicker.vue @@ -27,11 +27,12 @@ @click.shift="shiftClick(idx, $event)" class="d-flex justify-content-between align-items-center list-group-item-action pointer" :class="{active: lastClickIndex === idx}" + :key="idx.id" >
{{ idx.name }} -
+
- diff --git a/sist2-vue/src/components/LazyContentDiv.vue b/sist2-vue/src/components/LazyContentDiv.vue index 2533daf..abfd2ba 100644 --- a/sist2-vue/src/components/LazyContentDiv.vue +++ b/sist2-vue/src/components/LazyContentDiv.vue @@ -10,7 +10,7 @@ >{{ $t("ml.analyzeText") }} - {{ opt.text }} + {{ opt.text }} @@ -46,7 +46,7 @@ import {mapGetters, mapMutations} from "vuex"; export default { name: "LazyContentDiv", components: {AnalyzedContentSpansContainer, Preloader}, - props: ["docId"], + props: ["sid"], data() { return { ModelsRepo, @@ -70,7 +70,7 @@ export default { } Sist2Api - .getDocument(this.docId, this.$store.state.optHighlight, this.$store.state.fuzzy) + .getDocument(this.sid, this.$store.state.optHighlight, this.$store.state.fuzzy) .then(doc => { this.loading = false; diff --git a/sist2-vue/src/components/ResultsCard.vue b/sist2-vue/src/components/ResultsCard.vue index 31de98c..6d8772b 100644 --- a/sist2-vue/src/components/ResultsCard.vue +++ b/sist2-vue/src/components/ResultsCard.vue @@ -43,8 +43,7 @@ - \ No newline at end of file diff --git a/sist2-vue/src/views/SearchPage.vue b/sist2-vue/src/views/SearchPage.vue index 1f02f5a..e955afe 100644 --- a/sist2-vue/src/views/SearchPage.vue +++ b/sist2-vue/src/views/SearchPage.vue @@ -60,6 +60,7 @@