commit 3c6a816942dd26fbe950062a1135b20df1e5283a Author: serversdwn Date: Sun Jan 25 08:34:42 2026 +0000 Initial OnlyScavs: keys, ratings, grid icons diff --git a/README.md b/README.md new file mode 100644 index 0000000..fa1b6ec --- /dev/null +++ b/README.md @@ -0,0 +1,14 @@ +##Place hoder, for this here personalized tarkov DB im building. + + +##Items to be tracked = ## +**Weight Management Mostly** +--Weapons and weapons parts +--helmets + armor and rigs +--backpacks + +**Keys** +--full list w/ locations and whats behind the lock +-- vendor price +-- My personal 0-4 priority scale. +-- Flag useless keys. \ No newline at end of file diff --git a/app.py b/app.py new file mode 100644 index 0000000..e13115b --- /dev/null +++ b/app.py @@ -0,0 +1,110 @@ +from flask import Flask, render_template, request, redirect, url_for +import sqlite3 + +app = Flask(__name__) +DB_PATH = "tarkov.db" + + +def get_db(): + conn = sqlite3.connect(DB_PATH) + conn.row_factory = sqlite3.Row + return conn + + +@app.route("/") +def index(): + conn = get_db() + maps = conn.execute(""" + SELECT id, name + FROM maps + ORDER BY name + """).fetchall() + map_filter = request.args.get("map_id", type=int) + key_map_rows = conn.execute(""" + SELECT key_id, map_id + FROM key_maps + """).fetchall() + key_maps = {} + for row in key_map_rows: + key_maps.setdefault(row["key_id"], set()).add(row["map_id"]) + + key_query = """ + SELECT + k.id, + k.name, + k.icon_url, + k.grid_image_url, + k.wiki_url, + r.priority, + r.reason, + COALESCE(r.used_in_quest, 0) AS used_in_quest + FROM keys k + """ + params = [] + if map_filter: + key_query += """ + JOIN key_maps kmf + ON k.id = kmf.key_id + AND kmf.map_id = ? + """ + params.append(map_filter) + key_query += """ + LEFT JOIN key_ratings r ON k.id = r.key_id + ORDER BY + CASE WHEN r.priority IS NULL THEN 1 ELSE 0 END, + r.priority DESC, + k.name + """ + keys = conn.execute(key_query, params).fetchall() + conn.close() + + key_maps = {k: sorted(v) for k, v in key_maps.items()} + return render_template( + "index.html", + keys=keys, + maps=maps, + key_maps=key_maps, + map_filter=map_filter, + ) + + +@app.route("/rate", methods=["POST"]) +def rate_key(): + key_id = request.form["key_id"] + priority = request.form["priority"] + reason = request.form.get("reason", "") + used_in_quest = 1 if request.form.get("used_in_quest") == "on" else 0 + map_filter = request.form.get("map_id") + map_ids = [] + for value in request.form.getlist("map_ids"): + try: + map_ids.append(int(value)) + except ValueError: + continue + + conn = get_db() + conn.execute(""" + INSERT INTO key_ratings (key_id, priority, reason, used_in_quest) + VALUES (?, ?, ?, ?) + ON CONFLICT(key_id) DO UPDATE SET + priority = excluded.priority, + reason = excluded.reason, + used_in_quest = excluded.used_in_quest, + updated_at = CURRENT_TIMESTAMP + """, (key_id, priority, reason, used_in_quest)) + conn.execute("DELETE FROM key_maps WHERE key_id = ?", (key_id,)) + if map_ids: + conn.executemany( + "INSERT OR IGNORE INTO key_maps (key_id, map_id) VALUES (?, ?)", + [(key_id, map_id) for map_id in map_ids], + ) + conn.commit() + conn.close() + + if map_filter: + return redirect(url_for("index", map_id=map_filter)) + return redirect(url_for("index")) + + +if __name__ == "__main__": + app.run(host="0.0.0.0", port=5000, debug=True) diff --git a/import_keys.py b/import_keys.py new file mode 100644 index 0000000..8f00f70 --- /dev/null +++ b/import_keys.py @@ -0,0 +1,125 @@ +import requests +import sqlite3 +import sys + +DB_PATH = "tarkov.db" +API_URL = "https://api.tarkov.dev/graphql" + +GRAPHQL_QUERY = """ +query { + items(types: [keys]) { + id + name + shortName + weight + wikiLink + gridImageLink + properties { + ... on ItemPropertiesKey { + uses + } + } + } +} +""" + +def fetch_keys(): + response = requests.post( + API_URL, + json={"query": GRAPHQL_QUERY}, + timeout=30 + ) + response.raise_for_status() + data = response.json() + + if "errors" in data: + raise RuntimeError(data["errors"]) + + return data["data"]["items"] + +def upsert_keys(conn, keys): + inserted = 0 + updated = 0 + skipped = 0 + + cursor = conn.cursor() + + for k in keys: + api_id = k.get("id") + name = k.get("name") + short_name = k.get("shortName") + weight = k.get("weight") + wiki_url = k.get("wikiLink") + grid_image_url = k.get("gridImageLink") + uses = None + + props = k.get("properties") + if props and "uses" in props: + uses = props["uses"] + + if not api_id or not name: + skipped += 1 + continue + + cursor.execute( + """ + SELECT id FROM keys WHERE api_id = ? + """, + (api_id,) + ) + row = cursor.fetchone() + + if row: + cursor.execute( + """ + UPDATE keys + SET name = ?, short_name = ?, weight_kg = ?, uses = ?, wiki_url = ?, grid_image_url = ? + WHERE api_id = ? + """, + (name, short_name, weight, uses, wiki_url, grid_image_url, api_id) + ) + updated += 1 + else: + cursor.execute( + """ + INSERT INTO keys (api_id, name, short_name, weight_kg, uses) + VALUES (?, ?, ?, ?, ?) + """, + (api_id, name, short_name, weight, uses, icon_url, wiki_url) + ) + inserted += 1 + + conn.commit() + return inserted, updated, skipped + +def main(): + print("Fetching keys from Tarkov.dev...") + try: + keys = fetch_keys() + except Exception as e: + print("ERROR: Failed to fetch keys") + print(e) + sys.exit(1) + + print(f"Fetched {len(keys)} keys") + + conn = sqlite3.connect(DB_PATH) + conn.execute("PRAGMA foreign_keys = ON") + + try: + inserted, updated, skipped = upsert_keys(conn, keys) + except Exception as e: + conn.rollback() + print("ERROR: Database operation failed") + print(e) + sys.exit(1) + finally: + conn.close() + + print("Import complete") + print(f"Inserted: {inserted}") + print(f"Updated: {updated}") + print(f"Skipped: {skipped}") + +if __name__ == "__main__": + main() diff --git a/migrations_v1.sql b/migrations_v1.sql new file mode 100644 index 0000000..4c9bfb7 --- /dev/null +++ b/migrations_v1.sql @@ -0,0 +1,27 @@ +-- V1: maps tagging + used_in_quest flag +PRAGMA foreign_keys = ON; + +CREATE TABLE IF NOT EXISTS maps ( + id INTEGER PRIMARY KEY, + name TEXT UNIQUE +); + +CREATE TABLE IF NOT EXISTS key_maps ( + key_id INTEGER NOT NULL, + map_id INTEGER NOT NULL, + PRIMARY KEY (key_id, map_id), + FOREIGN KEY (key_id) REFERENCES keys(id), + FOREIGN KEY (map_id) REFERENCES maps(id) +); + +ALTER TABLE key_ratings ADD COLUMN used_in_quest INTEGER DEFAULT 0; + +INSERT OR IGNORE INTO maps (name) VALUES + ('Customs'), + ('Factory'), + ('Shoreline'), + ('Interchange'), + ('Reserve'), + ('Woods'), + ('Labs'), + ('Streets'); diff --git a/tarkov.db b/tarkov.db new file mode 100644 index 0000000..145d928 Binary files /dev/null and b/tarkov.db differ diff --git a/templates/index.html b/templates/index.html new file mode 100644 index 0000000..bb30b50 --- /dev/null +++ b/templates/index.html @@ -0,0 +1,237 @@ + + + + OnlyScavs – Key Ratings + + + + + +
+

OnlyScavs – Keys

+ +
+ + + +
+ +{% for key in keys %} +
+ +
+ {{ key.name }} + {% if key.wiki_url %} + wiki + {% endif %} + {% set selected_maps = key_maps.get(key.id, []) %} + {% if selected_maps %} +
+ {% for map in maps %} + {% if map.id in selected_maps %} + {{ map.name }} + {% endif %} + {% endfor %} +
+ {% endif %} +
+ +
+ + {% if map_filter %} + + {% endif %} + + + +
+ {% for map in maps %} + + {% endfor %} +
+ +
+
+{% endfor %} + +
+ +