Skip to content
Snippets Groups Projects
Commit ee4e0094 authored by Xavier Jouslin de Noray's avatar Xavier Jouslin de Noray
Browse files

Watcher: avoid doubles in plugins

Change-Id: I08975a409e7e182df3e9726de35e0ef11d8ac818
parent 01d8d386
No related branches found
No related tags found
No related merge requests found
......@@ -25,4 +25,5 @@ export interface Plugins {
arches: string[];
timestamp: string;
author: string;
signature: Buffer;
}
......@@ -62,6 +62,10 @@ export class CertificateManager {
return await this.readCRL(process.env.DATA_DIRECTORY + '/' + 'sfl.crl');
}
verifySignature(signature: Buffer, checkSignature: Buffer): boolean {
return Buffer.compare(signature, checkSignature) === 0;
}
private async readCertificate(
path: string,
file: string
......
......@@ -44,18 +44,31 @@ export class PluginsManager {
return;
}
// eslint-disable-next-line
watcher.on('change', () => {
watcher.on('change', (_, filename: string | Buffer) => {
const filePath =
// eslint-disable-next-line
__dirname +
'/../..' +
process.env.DATA_DIRECTORY +
'/' +
filename.toString();
// check if the file signature is valid and not in the list
this.checkPluginAlreadyPull(filePath).then(isValid => {
if (!isValid) {
return;
}
this.setPlugins().catch(e => {
console.log(e);
});
});
});
}
// need eslint disable because of the refactoring
async getPlugins(
arch: string,
lang: string
): Promise<Array<Omit<Plugins, 'arches'>>> {
): Promise<Array<Omit<Omit<Plugins, 'arches'>, 'signature'>>> {
if (this.plugins.length === 0) {
await this.setPlugins();
}
......@@ -206,6 +219,7 @@ export class PluginsManager {
timestamp,
author: issuer.CN,
background: plugin.background,
signature: await this.fileManager.readArchive(path, 'signatures.sig'),
};
} catch (e) {
console.error(e);
......@@ -296,4 +310,26 @@ export class PluginsManager {
}
this.plugins = plugins;
}
private async checkPluginAlreadyPull(pluginPath: string): Promise<boolean> {
const id = pluginPath.split('/').at(-1)?.split('.').at(0);
const arches = await this.architectureManager.getAllPluginArches(
pluginPath
);
if (id === undefined || arches === undefined) {
return false;
}
const pluginAlreadyInstalled = await this.findPlugin(id, arches[0]);
if (pluginAlreadyInstalled === undefined) {
return true;
}
const signature = await this.fileManager.readArchive(
pluginPath,
'signatures.sig'
);
return !this.certificateManager.verifySignature(
pluginAlreadyInstalled.signature,
signature
);
}
}
......@@ -57,7 +57,8 @@ describe('Plugins manager service tests', function () {
arches: ['test'],
timestamp: '',
author: '',
background: ''
background: '',
signature: Buffer.from(''),
}];
const expectedPlugin = [
......@@ -89,6 +90,7 @@ describe('Plugins manager service tests', function () {
background: 'test',
timestamp: 'test',
author: 'test',
signature: Buffer.from(''),
}
const expected = [{
......@@ -99,8 +101,16 @@ describe('Plugins manager service tests', function () {
pluginsManagerService['plugins'] = expected;
transaltionStub.formatText.resolves(plugin.name);
const actual = await pluginsManagerService.getPlugin("test", 'en');
expect(actual).toEqual(plugin);
expect(actual).toEqual({
id: plugin.id,
name: plugin.name,
version: plugin.version,
description: plugin.description,
icon: plugin.icon,
background: plugin.background,
timestamp: plugin.timestamp,
author: plugin.author,
});
});
it('should return undefined if plugin not found', async () => {
......@@ -118,6 +128,7 @@ describe('Plugins manager service tests', function () {
background: 'test',
timestamp: 'test',
author: 'test',
signature: Buffer.from(''),
};
const expected = [{
......@@ -214,6 +225,7 @@ describe('Plugins manager service tests', function () {
background: 'test',
timestamp: 'test',
author: 'test',
signature: Buffer.from(''),
};
const expected = [{
......@@ -270,6 +282,7 @@ describe('Plugins manager service tests', function () {
arches: ['x64'],
timestamp: 'timestamp1',
author: 'author1',
signature: Buffer.from(''),
},
{
id: 'plugin2',
......@@ -281,6 +294,7 @@ describe('Plugins manager service tests', function () {
arches: ['x86', 'x64'],
timestamp: 'timestamp2',
author: 'author2',
signature: Buffer.from(''),
},
{
id: 'plugin3',
......@@ -292,6 +306,7 @@ describe('Plugins manager service tests', function () {
arches: ['x64'],
timestamp: 'timestamp3',
author: 'author3',
signature: Buffer.from(''),
},
];
......@@ -335,6 +350,28 @@ describe('Plugins manager service tests', function () {
// Restore the original getNewPlugin method
getNewPluginStub.restore();
});
it('should return true if plugin is not already installed and signature is valid', async () => {
const pluginPath = 'path/to/plugin';
const signature = Buffer.from('valid-signature');
architectureService.getAllPluginArches.resolves(['arch1', 'arch2']);
fileManager.readArchive.resolves(signature);
pluginsManagerService['plugins'] = [];
const result = await pluginsManagerService['checkPluginAlreadyPull'](pluginPath);
expect(result).toBe(true);
});
it('should return true if plugin is not already installed and signature is invalid', async () => {
const pluginPath = 'path/to/plugin';
const signature = Buffer.from('invalid-signature');
architectureService.getAllPluginArches.resolves(['arch1', 'arch2']);
fileManager.readArchive.resolves(signature);
pluginsManagerService['plugins'] = [];
const result = await pluginsManagerService['checkPluginAlreadyPull'](pluginPath);
expect(result).toBe(true);
});
});
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment