diff --git a/api/graph.js b/api/graph.js index 9f8ea80..2b27ddf 100644 --- a/api/graph.js +++ b/api/graph.js @@ -17,19 +17,19 @@ graphApi.get( const finishes = sqlite.prepare( ` - SELECT DISTINCT(a.map), a.timestamp, b.points + SELECT DISTINCT(a.map), a.date, b.points FROM race AS a INNER JOIN maps AS b ON a.map = b.map - WHERE a.NAME = ? + WHERE a.player = ? GROUP BY a.map - ORDER BY a.timestamp; + ORDER BY a.date; `) let array = [] for (const finish of finishes.iterate(player)) { - currentPoints += finish.Points - array.push({ t: new Date(finish.Timestamp), y: currentPoints }) + currentPoints += finish.points + array.push({ t: new Date(finish.date), y: currentPoints }) } return res.json({ @@ -49,11 +49,11 @@ graphApi.get( response: "No query ('host/path?q=query') provided!" }) } - const finishes = sqlite.prepare(`SELECT * FROM graphRecordCache WHERE map = ? ORDER BY Timestamp`) + const finishes = sqlite.prepare(`SELECT * FROM graphRecordCache WHERE map = ? ORDER BY date`) let array = [] for (const record of finishes.iterate(req.query.q)) - array.push({ t: new Date(record.timestamp), y: record.time, player: record.player}) + array.push({ t: new Date(record.date), y: record.time, player: record.player}) return res.json({ success: true, diff --git a/api/maps.js b/api/maps.js index d80d193..b3582f9 100644 --- a/api/maps.js +++ b/api/maps.js @@ -6,11 +6,11 @@ const mapApi = Router() mapApi.get( '/count', (req, res) => { - const totalMaps = sqlite.prepare(`SELECT COUNT(*) as amount FROM maps`).get() + const totalMaps = sqlite.prepare(`SELECT COUNT(*) as count FROM maps`).get() return res.json({ success: true, - response: totalMaps.amount, + response: totalMaps.count, }) } ) @@ -28,25 +28,19 @@ mapApi.get( response: "No map found!", }) } - const info = sqlite.prepare(`SELECT * FROM maps WHERE map = ?`).get(map) /* TODO: Generate a table with this as a cache */ - /* Also generate indexes */ - const avgTime = sqlite.prepare(`SELECT avg(Time) as 'averageTime' FROM race WHERE map = ?`).get(map) - const total = sqlite.prepare(`SELECT COUNT(*) as 'total' FROM race WHERE map = ?`).get(map) - const unique = sqlite.prepare(`SELECT COUNT(distinct(name)) as 'unique' FROM race WHERE map = ?`).get(map) - const teams = sqlite.prepare(`SELECT COUNT(distinct(ID)) as 'teams' FROM teamrace WHERE map = ?`).get(map) + const avgTime = sqlite.prepare(`SELECT avg(time) AS 'averageTime' FROM race WHERE map = ?`).get(map) + const total = sqlite.prepare(`SELECT COUNT(*) AS 'total' FROM race WHERE map = ?`).get(map) + const unique = sqlite.prepare(`SELECT COUNT(distinct(player)) AS 'unique' FROM race WHERE map = ?`).get(map) + const teams = sqlite.prepare(`SELECT COUNT(distinct(id)) AS 'teams' FROM teamrace WHERE map = ?`).get(map) return res.json({ success: true, response: { - name: info.Map, - category: info.Server, - awardPoints: info.Points, - rating: info.Stars, - mapper: info.Mapper, - release: info.Timestamp, + info, + /* TODO Get median time*/ averageTime: avgTime.averageTime, finishes: { @@ -62,16 +56,7 @@ mapApi.get( mapApi.get( '/getAll', (req, res) => { - - const allMaps = sqlite.prepare( - `SELECT - map as name, - server as category, - points as awardPoints, - stars as rating, - mapper as mapper, - timestamp as release - FROM maps`).all() + const allMaps = sqlite.prepare(`SELECT * FROM maps`).all() return res.json({ success: true, @@ -86,7 +71,7 @@ mapApi.get( let category = req.params.category /* Check if category exists */ - const check = sqlite.prepare(`SELECT server FROM maps WHERE server = ? LIMIT 1`).get(category) + const check = sqlite.prepare(`SELECT category FROM maps WHERE server = ? LIMIT 1`).get(category) if (!check) { return res.json({ success: false, @@ -94,15 +79,7 @@ mapApi.get( }) } - const allMaps = sqlite.prepare( - `SELECT - map as name, - server as category, - points as awardPoints, - stars as rating, - mapper as mapper, - timestamp as release - FROM maps WHERE server = ?`).all(category) + const allMaps = sqlite.prepare(`SELECT * FROM maps WHERE category = ?`).all(category) return res.json({ success: true, @@ -111,64 +88,17 @@ mapApi.get( } ) -/* Searching allows you to attach sql LIKE % - * Example to search for maps beginning with Kobra - * You can do search for Kobra% - - * This thing is a complete mess, send help. BUT it does work <3 */ mapApi.get( '/search', async (req, res) => { /* Check if a query was provided */ - if (!req.query.q || !req.query.byMapper) { + if (!req.query.q) { return res.json({ success: false, response: "No query ('host/path?q=query') provided!" }) } - - let query = req.query.q - - /* Set defaults */ - let limit = 20 - let offset = 0 - let sortBy = "timestamp" - let order = "asc" - let column = "map" - let startsWith = "" - - if (req.query.limit) - limit = req.query.limit - - if (req.query.sortBy) - sortBy = req.query.sortBy - - if (req.query.order) - order = req.query.order - - if (req.query.byMapper) - column = "mapper" - - /* TODO: do this in one query? */ - const amount = sqlite.prepare( - `SELECT COUNT(*) as amount FROM maps WHERE ${column} LIKE "${query}"`).get() - - let pages = Math.floor(amount.amount / limit) - - if (req.query.page) - offset = (req.query.page * limit) - - const maps = sqlite.prepare( - `SELECT * FROM maps WHERE ${column} LIKE "${query}" ORDER BY ${sortBy} ${order} LIMIT ? OFFSET ?`).all(limit, offset) - - return res.json({ - success: true, - response: { - amount: amount.amount, - pages, - maps, - } - }) + /* TODO: Use the searcher function */ } ) diff --git a/api/players.js b/api/players.js index 3dd337a..cc9b511 100644 --- a/api/players.js +++ b/api/players.js @@ -10,7 +10,7 @@ playerApi.get( let player = req.params.player /* Misc */ - const firstFinish = sqlite.prepare(`SELECT server as server, map as map, time as time, Timestamp as date FROM race WHERE name = ? ORDER BY Timestamp ASC LIMIT 1`).get(player) + const firstFinish = sqlite.prepare(`SELECT * FROM race WHERE player = ? ORDER BY date ASC LIMIT 1`).get(player) /* Points */ let points = {} @@ -30,10 +30,6 @@ playerApi.get( } ) -/* Searching allows you to attach sql LIKE % - * Example to search for players beginning with Test - * You can do search for %Test - */ playerApi.get( '/search', async (req, res) => { @@ -44,40 +40,7 @@ playerApi.get( response: "No query ('host/path?q=query') provided!" }) } - 1 - let name = req.query.q - - /* Set defaults */ - let limit = 20 - let offset = 0 - - if (req.query.limit) { - limit = req.query.limit - } - - const amount = sqlite.prepare( - `SELECT COUNT(*) as amount FROM points - WHERE name LIKE "${name}" - `).get() - - let pages = Math.floor(amount.amount / limit) - - if (req.query.page) - offset = (req.query.page * limit) - - const players = sqlite.prepare( - `SELECT Rank, Name, Points FROM points - WHERE name LIKE "${name}" LIMIT ? OFFSET ? - `).all(limit, offset) - - return res.json({ - success: true, - response: { - amount: amount.amount, - pages: pages, - players: players, - } - }) + /* TODO: Use the searcher function */ } ) diff --git a/index.js b/index.js index 28a1025..5efdcc6 100644 --- a/index.js +++ b/index.js @@ -1,9 +1,8 @@ import express from 'express' import dotenv from 'dotenv' import api from './api/api.js' -import { generateDB } from "./libs/database/generate.js" -import { dbInit } from "./libs/database/init.js" - +import { generateDB } from './libs/database/generate.js' +import { dbInit } from './libs/database/init.js' dotenv.config() diff --git a/libs/database/generate.js b/libs/database/generate.js index 7007755..e3214a3 100644 --- a/libs/database/generate.js +++ b/libs/database/generate.js @@ -10,40 +10,63 @@ const log = initLog("DB Generation") * @module db/generateDB */ export function generateDB() { - /* TODO: Clean this up as it is a mess */ - /* TODO: Remove useless ones */ - if (process.env.GENERATE_DB !== "true") return log("Won't generate the database since 'GENERATE_DB' is not set to \"true\" in '.env'!") const exists = sqlite.prepare(`SELECT count(*) as a FROM sqlite_master WHERE type='table' AND name='points'`).get() - if(!exists.a) + if(!exists.a === 0) return log("Database already generated!") + /* Check if columns are already renamed */ + const renamed = sqlite.prepare(`SELECT COUNT(*) AS CNTREC FROM pragma_table_info('race') WHERE name='date'`).get() + + if(!renamed.a === 0) { + log("Renaming columns...") + execMany([ + `ALTER TABLE race RENAME COLUMN Map TO map`, + `ALTER TABLE race RENAME COLUMN Name TO player`, + `ALTER TABLE race RENAME COLUMN Time TO time`, + `ALTER TABLE race RENAME COLUMN Timestamp TO date`, + `ALTER TABLE race RENAME COLUMN Server TO server`, + + `ALTER TABLE teamrace RENAME COLUMN Map TO map`, + `ALTER TABLE teamrace RENAME COLUMN Name TO player`, + `ALTER TABLE teamrace RENAME COLUMN Time TO time`, + `ALTER TABLE teamrace RENAME COLUMN ID TO id`, + `ALTER TABLE teamrace RENAME COLUMN Timestamp TO date`, + + `ALTER TABLE maps RENAME COLUMN Map TO map`, + `ALTER TABLE maps RENAME COLUMN Server TO category`, + `ALTER TABLE maps RENAME COLUMN Points TO points`, + `ALTER TABLE maps RENAME COLUMN Stars TO stars`, + `ALTER TABLE maps RENAME COLUMN Mapper TO mapper`, + `ALTER TABLE maps RENAME COLUMN Timestamp TO release` + ]) + } log("Generating map index...") execMany([ `CREATE INDEX IF NOT EXISTS "idx_maps_map" ON "maps" ("map")`, - `CREATE INDEX IF NOT EXISTS "idx_maps_category" ON "maps" ("server");` + `CREATE INDEX IF NOT EXISTS "idx_maps_category" ON "maps" ("category")` ]) log("Generating race index...") execMany([ - `CREATE INDEX IF NOT EXISTS "idx_race_player" ON "race" ("Name")`, - `CREATE INDEX IF NOT EXISTS "idx_race_name" ON "race" ("Name","Timestamp")`, - `CREATE INDEX IF NOT EXISTS "idx_race_server" ON "race" ("Server")`, - `CREATE INDEX IF NOT EXISTS "idx_race_mapTimestamp" ON "race" ("Map","Timestamp")`, - `CREATE INDEX IF NOT EXISTS "idx_race_timestamp" ON "race" ("Timestamp")`, - `CREATE INDEX IF NOT EXISTS "idx_race_mapNameTime" ON "race" ("Map", "Name", "Time")` + `CREATE INDEX IF NOT EXISTS "idx_race_player" ON "race" ("player")`, + `CREATE INDEX IF NOT EXISTS "idx_race_name" ON "race" ("player", "date")`, + `CREATE INDEX IF NOT EXISTS "idx_race_server" ON "race" ("server")`, + `CREATE INDEX IF NOT EXISTS "idx_race_mapTimestamp" ON "race" ("map", "date")`, + `CREATE INDEX IF NOT EXISTS "idx_race_timestamp" ON "race" ("date")`, + `CREATE INDEX IF NOT EXISTS "idx_race_mapNameTime" ON "race" ("map", "player", "time")` ]) log("Creating rankings table...") sqlite.exec(` CREATE TABLE IF NOT EXISTS "rankings" ( - "Map" varchar(128) NOT NULL, - "Name" varchar(16) NOT NULL, - "Time" float NOT NULL DEFAULT 0, - "Timestamp" timestamp NOT NULL DEFAULT current_timestamp, - "Server" char(4) NOT NULL DEFAULT '', + "map" varchar(128) NOT NULL, + "player" varchar(16) NOT NULL, + "time" float NOT NULL DEFAULT 0, + "date" timestamp NOT NULL DEFAULT current_timestamp, + "server" char(4) NOT NULL DEFAULT '', "rank" INTEGER NOT NULL); `) @@ -52,27 +75,27 @@ export function generateDB() { log("Generating rankings index...") execMany([ - `CREATE INDEX IF NOT EXISTS "idx_rankings_map" ON "rankings" ("Map")`, + `CREATE INDEX IF NOT EXISTS "idx_rankings_map" ON "rankings" ("map")`, `CREATE INDEX IF NOT EXISTS "idx_rankings_rank" ON "rankings" ("rank")`, `CREATE INDEX IF NOT EXISTS "idx_rankings_player" ON "rankings" ("Name")` ]) log("Generating teamrace index...") execMany([ - `CREATE INDEX IF NOT EXISTS "idx_teamrace_map" ON "teamrace" ("Map")`, - `CREATE INDEX IF NOT EXISTS "idx_teamrace_ID" ON "teamrace" ("ID")`, - `CREATE INDEX IF NOT EXISTS "idx_teamrace_mapID" ON "teamrace" ("Map", "ID")` + `CREATE INDEX IF NOT EXISTS "idx_teamrace_map" ON "teamrace" ("map")`, + `CREATE INDEX IF NOT EXISTS "idx_teamrace_id" ON "teamrace" ("id")`, + `CREATE INDEX IF NOT EXISTS "idx_teamrace_mapID" ON "teamrace" ("map", "id")` ]) log("Creating teamrankings table...") sqlite.exec(` CREATE TABLE IF NOT EXISTS "teamrankings" ( - "Map" varchar(128) NOT NULL, - "ID" varbinary(16) NOT NULL, - "Name" varchar(16) NOT NULL, - "Time" float NOT NULL DEFAULT 0, - "Timestamp" timestamp NOT NULL DEFAULT current_timestamp, - "Server" char(4) NOT NULL DEFAULT '', + "map" varchar(128) NOT NULL, + "id" varbinary(16) NOT NULL, + "player" varchar(16) NOT NULL, + "time" float NOT NULL DEFAULT 0, + "date" timestamp NOT NULL DEFAULT current_timestamp, + "server" char(4) NOT NULL DEFAULT '', "teamrank" INTEGER NOT NULL); `) @@ -81,15 +104,15 @@ export function generateDB() { log("Generating teamrankings index...") execMany([ - `CREATE INDEX IF NOT EXISTS "idx_teamrankings_map" ON "teamrankings" ("Map")`, + `CREATE INDEX IF NOT EXISTS "idx_teamrankings_map" ON "teamrankings" ("map")`, `CREATE INDEX IF NOT EXISTS "idx_teamrankings_rank" ON "teamrankings" ("teamrank")`, - `CREATE INDEX IF NOT EXISTS "idx_teamrankings_player" ON "teamrankings" ("name")` + `CREATE INDEX IF NOT EXISTS "idx_teamrankings_player" ON "teamrankings" ("player")` ]) sqlite.exec(` CREATE TABLE IF NOT EXISTS "points" ( "rank" INTEGER NOT NULL, - "name" varchar(16) NOT NULL, + "player" varchar(16) NOT NULL, "points" INTEGER NOT NULL); `) @@ -99,8 +122,8 @@ export function generateDB() { "map" varchar(128) NOT NULL, "player" varchar(16) NOT NULL, "time" float NOT NULL DEFAULT 0, - "timestamp" timestamp NOT NULL DEFAULT current_timestamp, - "Server" char(4) NOT NULL DEFAULT ''); + "date" timestamp NOT NULL DEFAULT current_timestamp, + "server" char(4) NOT NULL DEFAULT ''); `) tasks.processTimeGraph() diff --git a/libs/database/tasks.js b/libs/database/tasks.js index 97a47fd..47ac4fe 100644 --- a/libs/database/tasks.js +++ b/libs/database/tasks.js @@ -34,19 +34,19 @@ export function processRankings() { .prepare(` INSERT INTO rankings ( - map, name, time, timestamp, rank, server + map, player, time, date, rank, server ) - SELECT map, name, time, timestamp, rank, server + SELECT map, player, time, date, rank, server FROM ( SELECT rank() OVER w AS rank, map, - timestamp, - NAME, + date, + player, min(time) AS time, server FROM race WHERE map = ? - GROUP BY NAME window w AS (ORDER BY time) ) AS a + GROUP BY player window w AS (ORDER BY time) ) AS a ORDER BY rank `) .run(map.Map) @@ -64,10 +64,10 @@ export function processTeamRankings() { .prepare(` INSERT INTO teamrankings ( - name, map, id, time, timestamp, server, teamrank + player, map, id, time, date, server, teamrank ) - SELECT DISTINCT(r.NAME), - r.map, r.id, r.time, r.timestamp, + SELECT DISTINCT(r.player), + r.map, r.id, r.time, r.date, Substring(n.server, 1, 3), dense_rank() OVER w AS rank FROM (( @@ -80,10 +80,10 @@ export function processTeamRankings() { ON l.id = r.id INNER JOIN race AS n ON r.map = n.map - AND r.NAME = n.NAME + AND r.player = n.player AND r.time = n.time window w AS (ORDER BY r.time) `) - .run(map.Map) + .run(map.map) } /** @@ -96,12 +96,12 @@ export function processTimeGraph() { let currentBest = 0; const maps = sqlite.prepare(`SELECT map FROM maps`); - const finishes = sqlite.prepare(`SELECT * FROM race WHERE map = ? ORDER BY Timestamp`) + const finishes = sqlite.prepare(`SELECT * FROM race WHERE map = ? ORDER BY date`) for (const map of maps.iterate()) { let currentFinish let currentBest = 0; - for (const record of finishes.iterate(map.Map)) { + for (const record of finishes.iterate(map.map)) { currentFinish = record.Time if (currentFinish <= currentBest || currentBest == 0) { currentBest = currentFinish @@ -109,14 +109,14 @@ export function processTimeGraph() { sqlite.prepare(` INSERT INTO "graphRecordCache" ( - map, player, time, timestamp, server + map, player, time, date, server ) VALUES (?, ?, ?, ?, ?) `).run( map.Map, - record.Name, - record.Time, - record.Timestamp, - record.Server + record.name, + record.time, + record.timestamp, + record.server ) } } @@ -144,7 +144,7 @@ export function processAllPoints() { ( "type" varchar(16) NOT NULL, "rank" INTEGER NOT NULL, - "name" varchar(16) NOT NULL, + "player" varchar(16) NOT NULL, "points" INTEGER NOT NULL ); `) @@ -158,7 +158,7 @@ export function processAllPoints() { .prepare(` INSERT INTO "points" ( - type, rank, name, points + type, rank, player, points ) VALUES (?, ?, ?, ?) `) .run( @@ -176,7 +176,7 @@ export function processAllPoints() { execMany([ `CREATE INDEX IF NOT EXISTS "idx_points_type" ON "points" ("type")`, `CREATE INDEX IF NOT EXISTS "Idx_points_rank" on "points" ("rank")`, - `CREATE INDEX IF NOT EXISTS "Idx_points_name" on "points" ("name")` + `CREATE INDEX IF NOT EXISTS "Idx_points_name" on "points" ("player")` ]) }