migrate crypto key from config file to database
MODIFY
src/migration/MigrationHandler.ts
src/migration/MigrationHandler.ts
@@ -25,6 +25,7 @@ import LockingManager from '../locking/LockingManager';
import Logging from '../utils/Logging';
import LogicallyDeleteTagsOfDeletedUsersTask from './tasks/LogicallyDeleteTagsOfDeletedUsersTask';
import MigrateCoordinatesTask from './tasks/MigrateCoordinatesTask';
+import MigrateCryptoSettingsFromConfigToDBTask from './tasks/MigrateCryptoSettingsFromConfigToDBTask';
import MigrateOcpiSettingTask from './tasks/MigrateOcpiSettingTask';
import MigrateOcpiTransactionsTask from './tasks/MigrateOcpiTransactionsTask';
import MigrationStorage from '../storage/mongodb/MigrationStorage';
@@ -101,6 +102,7 @@ export default class MigrationHandler {
currentMigrationTasks.push(new SetDefaultTagToUserTask());
currentMigrationTasks.push(new DeleteChargingStationPropertiesTask());
currentMigrationTasks.push(new FixedConsumptionRoundedPriceTask());
+ currentMigrationTasks.push(new MigrateCryptoSettingsFromConfigToDBTask());
// Get the already done migrations from the DB
const migrationTasksDone = await MigrationStorage.getMigrations();
// Check

ADD
src/migration/tasks/MigrateCryptoSettingsFromConfigToDBTask.ts
+import { CryptoKeyProperties, CryptoSettingsType, KeySetting } from '../../types/Setting';
+
+import Configuration from '../../utils/Configuration';
+import Constants from '../../utils/Constants';
+import MigrationTask from '../MigrationTask';
+import SettingStorage from '../../storage/mongodb/SettingStorage';
+import Tenant from '../../types/Tenant';
+import TenantComponents from '../../types/TenantComponents';
+import TenantStorage from '../../storage/mongodb/TenantStorage';
+import Utils from '../../utils/Utils';
+
+export default class MigrateCryptoSettingsFromConfigToDBTask extends MigrationTask {
+ public async migrate(): Promise<void> {
+ const tenants = await TenantStorage.getTenants({}, Constants.DB_PARAMS_MAX_LIMIT);
+
+ for (const tenant of tenants.result) {
+ await this.migrateTenant(tenant);
+ }
+ }
+
+ public async migrateTenant(tenant: Tenant): Promise<void> {
+ // Crypto Key from config file
+ const configCryptoKey: string = Configuration.getCryptoConfig().key;
+ // Crypto Key Properties from config file
+ const confiCryptoKeyProperties: CryptoKeyProperties = Utils.separateCryptoAlgo(Configuration.getCryptoConfig().algorithm);
+ // Crypto Key Setting from db
+ const keySettings = await SettingStorage.getCryptoSettings(tenant.id);
+ // If no Crypto Key Setting exist, initialize them with Crypto Key from config file
+ if (!keySettings) {
+ // Create New Crypto Key in Tenant Settings
+ const keySettingToSave = {
+ identifier: TenantComponents.CRYPTO,
+ type: CryptoSettingsType.CRYPTO,
+ crypto: {
+ key: configCryptoKey,
+ keyProperties: confiCryptoKeyProperties,
+ }
+ } as KeySetting;
+ await SettingStorage.saveCryptoSettings(tenant.id, keySettingToSave);
+ }
+ }
+
+ public getVersion(): string {
+ return '1.0';
+ }
+
+ public getName(): string {
+ return 'MigrateCryptoSettingsFromConfigToDB';
+ }
+}

MODIFY
src/storage/mongodb/SettingStorage.ts
src/storage/mongodb/SettingStorage.ts
-import { AnalyticsSettings, AnalyticsSettingsType, AssetSettings, AssetSettingsType, BillingSettings, BillingSettingsType, PricingSettings, PricingSettingsType, RefundSettings, RefundSettingsType, RoamingSettings, SettingDB, SmartChargingSettings, SmartChargingSettingsType } from '../../types/Setting';
+import { AnalyticsSettings, AnalyticsSettingsType, AssetSettings, AssetSettingsType, BillingSettings, BillingSettingsType, CryptoSetting, CryptoSettingsType, KeySetting, PricingSettings, PricingSettingsType, RefundSettings, RefundSettingsType, RoamingSettings, SettingDB, SmartChargingSettings, SmartChargingSettingsType } from '../../types/Setting';
import global, { FilterParams } from '../../types/GlobalType';
import BackendError from '../../exception/BackendError';
@@ -304,6 +304,50 @@ export default class SettingStorage {
}
}
+ public static async saveCryptoSettings(tenantID: string, cryptoSettingToSave: KeySetting): Promise<void> {
+ // Build internal structure
+ const settingsToSave = {
+ id: cryptoSettingToSave.id,
+ identifier: 'crypto',
+ lastChangedOn: new Date(),
+ content: {
+ crypto: cryptoSettingToSave.crypto
+ },
+ } as SettingDB;
+ // Save
+ await this.saveSettings(tenantID, settingsToSave);
+ }
+
+ public static async getCryptoSettings(tenantID: string): Promise<KeySetting> {
+ // Get the Crypto Key settings
+ const settings = await SettingStorage.getSettings(tenantID,
+ { identifier: TenantComponents.CRYPTO },
+ Constants.DB_PARAMS_MAX_LIMIT);
+ if (settings.count > 0) {
+ const cryptoSetting = {
+ formerKey: settings.result[0].content.crypto.formerKey,
+ formerKeyProperties: {
+ blockCypher: settings.result[0].content.crypto.formerKeyProperties?.blockCypher,
+ keySize: settings.result[0].content.crypto.formerKeyProperties?.keySize,
+ operationMode: settings.result[0].content.crypto.formerKeyProperties?.operationMode,
+ },
+ key: settings.result[0].content.crypto.key,
+ keyProperties: {
+ blockCypher: settings.result[0].content.crypto.keyProperties.blockCypher,
+ keySize: settings.result[0].content.crypto.keyProperties.keySize,
+ operationMode: settings.result[0].content.crypto.keyProperties.operationMode,
+ }
+ } as CryptoSetting;
+ const keySetting = {
+ id: settings.result[0].id,
+ identifier: settings.result[0].identifier,
+ type: CryptoSettingsType.CRYPTO,
+ crypto: cryptoSetting
+ } as KeySetting;
+ return keySetting;
+ }
+ }
+
public static async getSettings(tenantID: string,
params: {identifier?: string; settingID?: string, dateFrom?: Date, dateTo?: Date},
dbParams: DbParams, projectFields?: string[]): Promise<DataResult<SettingDB>> {

MODIFY
src/types/Setting.ts
src/types/Setting.ts
@@ -21,7 +21,7 @@ export interface SettingLink {
}
export interface SettingDBContent {
- type: RoamingSettingsType | AnalyticsSettingsType | RefundSettingsType | PricingSettingsType | BillingSettingsType | SmartChargingSettingsType | AssetSettingsType | SmartChargingContentType;
+ type: RoamingSettingsType | AnalyticsSettingsType | RefundSettingsType | PricingSettingsType | BillingSettingsType | SmartChargingSettingsType | AssetSettingsType | SmartChargingContentType | CryptoSettingsType;
ocpi?: OcpiSetting;
simple?: SimplePricingSetting;
convergentCharging?: ConvergentChargingPricingSetting;
@@ -31,6 +31,7 @@ export interface SettingDBContent {
concur?: ConcurRefundSetting;
sapSmartCharging?: SapSmartChargingSetting;
asset?: AssetSetting;
+ crypto?: CryptoSetting;
}
export enum PricingSettingsType {
@@ -238,3 +239,26 @@ export interface AssetUserPasswordConnectionType {
// eslint-disable-next-line @typescript-eslint/no-empty-interface
export interface AssetSchneiderConnectionType extends AssetUserPasswordConnectionType {
}
+
+export enum CryptoSettingsType {
+ CRYPTO = 'crypto'
+}
+
+export interface KeySetting extends Setting {
+ identifier: TenantComponents.CRYPTO;
+ type: CryptoSettingsType;
+ crypto: CryptoSetting;
+}
+
+export interface CryptoKeyProperties {
+ blockCypher: string;
+ keySize: number;
+ operationMode: string;
+}
+
+export interface CryptoSetting {
+ key: string;
+ keyProperties: CryptoKeyProperties;
+ formerKey?: string;
+ formerKeyProperties?: CryptoKeyProperties;
+}

MODIFY
src/types/TenantComponents.ts
src/types/TenantComponents.ts
@@ -9,5 +9,6 @@ enum TenantComponents {
ASSET = 'asset',
SMART_CHARGING = 'smartCharging',
CAR = 'car',
+ CRYPTO = 'crypto'
}
export default TenantComponents;

MODIFY
src/utils/Utils.ts
src/utils/Utils.ts
-import { AnalyticsSettingsType, AssetSettingsType, BillingSettingsType, PricingSettingsType, RefundSettingsType, RoamingSettingsType, SettingDBContent, SmartChargingContentType } from '../types/Setting';
+import { AnalyticsSettingsType, AssetSettingsType, BillingSettingsType, CryptoKeyProperties, PricingSettingsType, RefundSettingsType, RoamingSettingsType, SettingDBContent, SmartChargingContentType } from '../types/Setting';
import { Car, CarCatalog } from '../types/Car';
import { ChargePointStatus, OCPPProtocol, OCPPVersion } from '../types/ocpp/OCPPServer';
import ChargingStation, { ChargePoint, ChargingStationEndpoint, Connector, ConnectorCurrentLimitSource, CurrentType } from '../types/ChargingStation';
@@ -1345,4 +1345,14 @@ export default class Utils {
public static isPlateIDValid(plateID): boolean {
return /^[A-Z0-9- ]*$/.test(plateID);
}
+
+ public static separateCryptoAlgo(algo: string): CryptoKeyProperties {
+ const regExp = /(.*?)-(.*?)-(.*)/.exec(algo);
+ return {
+ blockCypher: regExp[1].toUpperCase(),
+ keySize: parseInt(regExp[2]),
+ operationMode: regExp[3].toUpperCase()
+ };
+
+ }
}

migrate crypto key from config file to database