Skip to content
This repository was archived by the owner on Oct 23, 2024. It is now read-only.

Commit 1f631e4

Browse files
authored
Update key settings and scripts (#1282)
* Update key settings and scripts * Handle error when missing file
1 parent 97ea467 commit 1f631e4

File tree

6 files changed

+129
-20
lines changed

6 files changed

+129
-20
lines changed

scripts/release/initauth.js

Lines changed: 91 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,14 @@ const saveAuth = (obj, filename) => new Promise((resolve, reject) => {
5959
}
6060
});
6161

62-
const updateRabbit = () => new Promise((resolve, reject) => {
62+
const updateRabbit = (cleanup) => new Promise((resolve, reject) => {
63+
if (cleanup) {
64+
console.log('Cleanup RabbitMQ account...');
65+
saveAuth({rabbit: null}, authStore)
66+
.then(resolve)
67+
.catch(reject);
68+
return;
69+
}
6370
question('Update RabbitMQ account?[yes/no]')
6471
.then((answer) => {
6572
answer = answer.toLowerCase();
@@ -81,7 +88,14 @@ const updateRabbit = () => new Promise((resolve, reject) => {
8188
});
8289
});
8390

84-
const updateMongo = () => new Promise((resolve, reject) => {
91+
const updateMongo = (cleanup) => new Promise((resolve, reject) => {
92+
if (cleanup) {
93+
console.log('Cleanup MongoDB account...');
94+
saveAuth({mongo: null}, authStore)
95+
.then(resolve)
96+
.catch(reject);
97+
return;
98+
}
8599
question('Update MongoDB account?[yes/no]')
86100
.then((answer) => {
87101
answer = answer.toLowerCase();
@@ -103,7 +117,14 @@ const updateMongo = () => new Promise((resolve, reject) => {
103117
});
104118
});
105119

106-
const updateInternal = () => new Promise((resolve, reject) => {
120+
const updateInternal = (cleanup) => new Promise((resolve, reject) => {
121+
if (cleanup) {
122+
console.log('Cleanup internal passphrase...');
123+
saveAuth({internalPass: null}, authStore)
124+
.then(resolve)
125+
.catch(reject);
126+
return;
127+
}
107128
question('Update internal passphrase?[yes/no]')
108129
.then((answer) => {
109130
answer = answer.toLowerCase();
@@ -122,7 +143,14 @@ const updateInternal = () => new Promise((resolve, reject) => {
122143
});
123144
});
124145

125-
const updateGKeyPass = () => new Promise((resolve, reject) => {
146+
const updateGKeyPass = (cleanup) => new Promise((resolve, reject) => {
147+
if (cleanup) {
148+
console.log('Cleanup gRPC TLS key...');
149+
saveAuth({grpc: null}, authStore)
150+
.then(resolve)
151+
.catch(reject);
152+
return;
153+
}
126154
question('Update passphrase for gRPC TLS key?[yes/no]')
127155
.then((answer) => {
128156
answer = answer.toLowerCase();
@@ -146,8 +174,47 @@ const updateGKeyPass = () => new Promise((resolve, reject) => {
146174
});
147175
});
148176

177+
const generateServiceProtectionKey = (cleanup) => new Promise((resolve, reject) => {
178+
if (cleanup) {
179+
console.log('Cleanup service protection key...');
180+
saveAuth({spk: null}, authStore)
181+
.then(resolve)
182+
.catch(reject);
183+
return;
184+
}
185+
question('Generate service protection key?[yes/no]')
186+
.then((answer) => {
187+
answer = answer.toLowerCase();
188+
if (answer === 'y' || answer === 'yes') {
189+
const spk = require('crypto').randomBytes(64).toString('hex');
190+
saveAuth({spk: spk}, authStore)
191+
.then(() => {
192+
console.log(`Service protection key generated: ${spk}`);
193+
resolve();
194+
})
195+
.catch(reject);
196+
} else {
197+
resolve();
198+
}
199+
});
200+
});
201+
202+
const printUsage = () => {
203+
let usage = 'Usage:\n';
204+
usage += ' --rabbitmq Update RabbitMQ account(default)\n';
205+
usage += ' --mongodb Update MongoDB account(default)\n';
206+
usage += ' --internal Update internal TLS key passphrase\n';
207+
usage += ' --grpc Update gRPC TLS key passphrase\n';
208+
usage += ' --spk Generate service protection key\n';
209+
usage += ' --cleanup Clean up selected credentials\n';
210+
console.log(usage);
211+
}
149212
const options = {};
150213
const parseArgs = () => {
214+
if (process.argv.includes('--help')) {
215+
printUsage();
216+
process.exit(0);
217+
}
151218
if (process.argv.includes('--rabbitmq')) {
152219
options.rabbit = true;
153220
}
@@ -160,7 +227,17 @@ const parseArgs = () => {
160227
if (process.argv.includes('--grpc')) {
161228
options.grpc = true;
162229
}
163-
if (Object.keys(options).length === 0) {
230+
if (process.argv.includes('--spk')) {
231+
options.spk = true;
232+
}
233+
if (process.argv.includes('--cleanup')) {
234+
options.cleanup = true;
235+
}
236+
let selectedUpdate = Object.keys(options).length;
237+
if (options.cleanup) {
238+
selectedUpdate -= 1;
239+
}
240+
if (selectedUpdate === 0) {
164241
options.rabbit = true;
165242
options.mongo = true;
166243
}
@@ -170,22 +247,27 @@ const parseArgs = () => {
170247
parseArgs()
171248
.then(() => {
172249
if (options.rabbit) {
173-
return updateRabbit();
250+
return updateRabbit(options.cleanup);
174251
}
175252
})
176253
.then(() => {
177254
if (options.mongo) {
178-
return updateMongo();
255+
return updateMongo(options.cleanup);
179256
}
180257
})
181258
.then(() => {
182259
if (options.internal) {
183-
return updateInternal();
260+
return updateInternal(options.cleanup);
184261
}
185262
})
186263
.then(() => {
187264
if (options.grpc) {
188-
return updateGKeyPass();
265+
return updateGKeyPass(options.cleanup);
266+
}
267+
})
268+
.then(() => {
269+
if (options.spk) {
270+
return generateServiceProtectionKey(options.cleanup);
189271
}
190272
})
191273
.finally(() => readline.close());

source/common/cipher.js

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -80,11 +80,26 @@ function unlockSync (password, filename) {
8080
return JSON.parse(data.toString());
8181
}
8282

83+
const defaultK =
84+
Buffer.from('3d84a1efc77268c98bc6ca2921eb35a6d82a40a38696d25fbb64ff1733cd2523', 'hex');
85+
let csk = null;
86+
// Set credPass with your own pass
87+
if (global.config?.credPass) {
88+
const defaultSalt =
89+
Buffer.from('1a7bb4a4f56f15eb875c7a66d8fe893bc9458acd414319d431f6a6dfaef69fa6', 'hex');
90+
// crypto.randomBytes(32).toString('hex');
91+
// Set credSalt with your own salt
92+
const salt = global.config.credSalt || defaultSalt;
93+
csk = crypto.pbkdf2Sync(global.config.credPass, salt, 4000, 128, 'sha256');
94+
delete global.config.credPass;
95+
delete global.config.credSalt;
96+
}
97+
8398
module.exports = {
8499
encrypt: encrypt,
85100
decrypt: decrypt,
86-
// Replace k with your key generator
87-
k: Buffer.from('3d84a1efc77268c98bc6ca2921eb35a6d82a40a38696d25fbb64ff1733cd2523', 'hex'),
101+
k: (csk || defaultK),
102+
dk: defaultK,
88103
astore: '.owt.authstore',
89104
kstore: '.owt.keystore',
90105
lock: lock,

source/management_api/api.js

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -258,6 +258,13 @@ if (cluster.isMaster) {
258258
} else {
259259
// Worker Process
260260
rpc.connect(global.config.rabbit);
261+
// Load spk
262+
try {
263+
const aconfig = cipher.unlockSync(cipher.k, cipher.astore);
264+
global.config.spk = aconfig.spk ? Buffer.from(aconfig.spk, 'hex') : cipher.dk;
265+
} catch (e) {
266+
global.config.spk = cipher.dk;
267+
}
261268

262269
if (serverConfig.ssl === true) {
263270
var cipher = require('./cipher');
@@ -266,12 +273,13 @@ if (cluster.isMaster) {
266273
cipher.unlock(cipher.k, keystore, function cb (err, passphrase) {
267274
if (!err) {
268275
try {
269-
require('https').createServer({
270-
pfx: require('fs').readFileSync(serverConfig.keystorePath),
271-
passphrase: passphrase
272-
}, app).listen(serverPort);
276+
require('https').createServer({
277+
pfx: require('fs').readFileSync(serverConfig.keystorePath),
278+
passphrase: passphrase
279+
}, app).listen(serverPort);
273280
} catch (e) {
274-
err = e;
281+
log.warn('Failed to start secured server:', e);
282+
return process.exit(1);
275283
}
276284
} else {
277285
log.warn('Failed to setup secured server:', err);

source/management_api/auth/serverAuthenticator.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ exports.authenticate = function (req, res, next) {
110110

111111
var key = serv.key;
112112
if (serv.encrypted === true) {
113-
key = cipher.decrypt(cipher.k, key);
113+
key = cipher.decrypt(global.config.spk, key);
114114
}
115115

116116
// Check if timestamp and cnonce are valids in order to avoid duplicate requests.

source/management_api/initdb.js

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ var configFile = path.resolve(dirName, CONFIG_NAME);
3232
var samplePackageJson = path.resolve(dirName, SAMPLE_RELATED_PATH, 'package.json');
3333
var sampleEntryName = (require(samplePackageJson).main || DEFAULT_SAMPLE_ENTRY);
3434
var sampleServiceFile = path.resolve(dirName, SAMPLE_RELATED_PATH, sampleEntryName);
35+
var spk = cipher.dk;
3536

3637
function prepareDB(next) {
3738
if (dbURL.indexOf('mongodb://') !== 0) {
@@ -40,6 +41,9 @@ function prepareDB(next) {
4041
if (fs.existsSync(cipher.astore)) {
4142
cipher.unlock(cipher.k, cipher.astore, function cb (err, authConfig) {
4243
if (!err) {
44+
if (authConfig.spk) {
45+
spk = Buffer.from(authConfig.spk, 'hex');
46+
}
4347
if (authConfig.mongo && !dbURL.includes('@')) {
4448
dbURL = "mongodb://" + authConfig.mongo.username
4549
+ ':' + authConfig.mongo.password
@@ -188,7 +192,7 @@ function prepareService (serviceName, next) {
188192
if (err || !service) {
189193
var crypto = require('crypto');
190194
var key = crypto.pbkdf2Sync(crypto.randomBytes(64).toString('hex'), crypto.randomBytes(32).toString('hex'), 4000, 128, 'sha256').toString('base64');
191-
service = {name: serviceName, key: cipher.encrypt(cipher.k, key), encrypted: true, rooms: [], __v: 0};
195+
service = {name: serviceName, key: cipher.encrypt(spk, key), encrypted: true, rooms: [], __v: 0};
192196
db.collection('services').insertOne(service, function cb (err, result) {
193197
if (err) {
194198
console.log('mongodb: error in adding', serviceName);
@@ -199,7 +203,7 @@ function prepareService (serviceName, next) {
199203
});
200204
} else {
201205
if (service.encrypted === true) {
202-
service.key = cipher.decrypt(cipher.k, service.key);
206+
service.key = cipher.decrypt(spk, service.key);
203207
}
204208
next(service);
205209
}

source/management_api/resource/servicesResource.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ exports.create = function (req, res, next) {
6969
}
7070

7171
service.encrypted = true;
72-
service.key = cipher.encrypt(cipher.k, service.key);
72+
service.key = cipher.encrypt(global.config.spk, service.key);
7373
dataAccess.service.create(service, function(err, result) {
7474
if (err) {
7575
log.warn('Failed to create service:', err.message);

0 commit comments

Comments
 (0)