Implement database versioning and migration. It could not possibly be any simpler or easier to break, but it works. And it can be used to automatically migrate to a better system for migration later.

For now, the way it works is by creating a new migration script with the name of the version (increment by one, whole numbers) in the src/db folder
On start up, it will compare version numbers and run new scripts. The user can also manually check for migrations and skip the automatic checking.
Added a bit of additional logging to see what's happening in the startup process as well.
merge-requests/24/head
knotteye 4 years ago
parent a36a49b70e
commit ee3527f292
  1. 8
      README.md
  2. 3
      package.json
  3. 34
      src/cleanup.ts
  4. 1
      src/config.ts
  5. 1
      src/database.ts
  6. 8
      src/db/0.ts
  7. 2
      src/index.ts
  8. 9
      src/migrate.ts

@ -13,7 +13,13 @@ Follow the instructions after setup runs.
### Run the server
```bash
npm start
npm run start
```
You can also run this to skip checking the database version on startup.
```bash
npm run start -- --skip-migrate
# don't forget to migrate manually when you update
npm run migrate
```
## Contributing

@ -7,7 +7,8 @@
"scripts": {
"start": "ts-node src/index.ts",
"user": "ts-node src/cli.ts",
"setup": "sh install/setup.sh"
"setup": "sh install/setup.sh",
"migrate": "ts-node src/migrate.ts"
},
"repository": {
"type": "git",

@ -1,10 +1,42 @@
import * as db from "./database";
import {readdirSync} from "fs";
async function init() {
async function init(m?: boolean) {
if(!m){
console.log('Checking database version.');
var tmp: string[] = await db.query('show tables like \"db_meta\"');
if(tmp.length === 0){
console.log('No database version info, running initial migration.');
await require('./db/0').run();
await bringUpToDate();
}
else {
await bringUpToDate();
}
}
else {
console.log('Skipping database version check.');
}
//If satyr is restarted in the middle of a stream
//it causes problems
//Live flags in the database stay live
await db.query('update user_meta set live=false');
}
async function bringUpToDate(): Promise<void>{
var versions: Object[] = await db.query('select * from db_meta');
var scripts: Buffer[] | string[] = readdirSync('./src/db/', {withFileTypes: false});
var diff: number = scripts.length - versions.length
if(diff === 0){
console.log('No migration needed.');
} else {
console.log('Versions differ, migrating now.');
for(let i=0;i<diff;i++){
console.log('Migration to version '+Math.floor(scripts.length-(diff-i)));
await require('./db/'+scripts[Math.floor(scripts.length-(diff-i))]).run();
}
console.log('Done migrating database.');
}
}
export { init };

@ -2,6 +2,7 @@ import {parseAsYaml as parse} from "parse-yaml";
import {readFileSync as read} from "fs";
try {
var localconfig: Object = parse(read('config/config.yml'));
console.log('Config file found.');
} catch (e) {
console.log('No config file found. Exiting.');
process.exit();

@ -9,6 +9,7 @@ var cryptoconfig: Object;
function init (){
raw = mysql.createPool(config['database']);
cryptoconfig = config['crypto'];
console.log('Connected to database.');
}
async function addUser(name: string, password: string){

@ -0,0 +1,8 @@
import * as db from "../database";
async function run () {
await db.query('CREATE TABLE IF NOT EXISTS db_meta(version SMALLINT)');
await db.query('INSERT INTO db_meta (version) VALUES (0)');
}
export { run }

@ -7,7 +7,7 @@ import { config } from "./config";
async function run() {
await initDB();
await clean();
await clean(process.argv.indexOf('--skip-migrate') !== -1);
await initHTTP();
await initRTMP();
await initChat();

@ -0,0 +1,9 @@
import {init as initDB} from "./database";
import {init as clean} from "./cleanup";
import { config } from "./config";
async function run() {
await initDB();
await clean(false);
}
run().then(() => {process.exit()});