forked from geolba/tethys.backend
Arno Kaimbacher
68928b5e07
- adapted command ValidateChecksum.ts: on published files are checked. better information logging - better LineChart.vue component: showing real statistics - start/routes/apu.ts: added Route.get('/statistic/:year', 'HomeController.findPublicationsPerMonth');
82 lines
3.0 KiB
TypeScript
82 lines
3.0 KiB
TypeScript
import { BaseCommand } from '@adonisjs/core/build/standalone';
|
|
import crypto from 'crypto';
|
|
import fs from 'fs';
|
|
// import Config from '@ioc:Adonis/Core/Config';
|
|
import Logger from '@ioc:Adonis/Core/Logger';
|
|
|
|
export default class ValidateChecksum extends BaseCommand {
|
|
/**
|
|
* Command name is used to run the command
|
|
*/
|
|
public static commandName = 'validate:checksum';
|
|
|
|
/**
|
|
* Command description is displayed in the "help" output
|
|
*/
|
|
public static description = '';
|
|
|
|
public static settings = {
|
|
/**
|
|
* Set the following value to true, if you want to load the application
|
|
* before running the command. Don't forget to call `node ace generate:manifest`
|
|
* afterwards.
|
|
*/
|
|
loadApp: true,
|
|
|
|
/**
|
|
* Set the following value to true, if you want this command to keep running until
|
|
* you manually decide to exit the process. Don't forget to call
|
|
* `node ace generate:manifest` afterwards.
|
|
*/
|
|
stayAlive: false,
|
|
};
|
|
|
|
public async run() {
|
|
// this.logger.info('Hello world!')
|
|
const { default: File } = await import('App/Models/File');
|
|
// const { default: HashValue } = await (await (import ('App/Models/HashValue')));
|
|
|
|
// query all published files from database:
|
|
const files = await File.query()
|
|
.whereHas('dataset', (dQuery) => {
|
|
dQuery.where('server_state', 'published');
|
|
})
|
|
.preload('hashvalues');
|
|
|
|
// const logLevel = Config.get('app.logger.level', 'info');
|
|
// console.log(this.logger.)
|
|
|
|
for (var file of files) {
|
|
let hashValue = await file.related('hashvalues').query().pluck('value', 'type');
|
|
|
|
const filePath = '/storage/app/public/' + file.pathName;
|
|
let calculatedMd5FileHash;
|
|
try {
|
|
calculatedMd5FileHash = await this.checksumFile(filePath, 'md5');
|
|
} catch (exception) {
|
|
// this.logger.error(exception.message);
|
|
Logger.error(exception.message);
|
|
continue;
|
|
}
|
|
|
|
if (hashValue['md5'] === calculatedMd5FileHash) {
|
|
Logger.info(`File id ${file.id} OK: stored md5 checksum: ${calculatedMd5FileHash}, same control md5 checksum: ${hashValue['md5']}`);
|
|
} else {
|
|
Logger.error(
|
|
`File id ${file.id}: stored md5 checksum: ${calculatedMd5FileHash}, control md5 checksum: ${hashValue['md5']}`,
|
|
);
|
|
}
|
|
}
|
|
}
|
|
|
|
private async checksumFile(path, hashName = 'md5'): Promise<string> {
|
|
return new Promise((resolve, reject) => {
|
|
const hash = crypto.createHash(hashName);
|
|
const stream = fs.createReadStream(path);
|
|
stream.on('error', (err) => reject(err));
|
|
stream.on('data', (chunk) => hash.update(chunk));
|
|
stream.on('end', () => resolve(hash.digest('hex')));
|
|
});
|
|
}
|
|
}
|