UNPKG

regedit

Version:

Read, Write, List and do all sorts of funky stuff to the windows registry using node.js and windows script host

897 lines (712 loc) 21.6 kB
/* eslint-disable no-unused-expressions */ // TODO need to find a better way to test the 32bit/64bit specific scenarios var index = require('../index') var should = require('should') function toLowerCase(str) { return str.toLowerCase() } describe('regedit', function() { describe('list keys and values in a sub key', function() { this.timeout(5000) var target = 'HKLM\\software\\microsoft\\windows\\CurrentVersion' it(target, function(done) { index.list(target, function(err, result) { if (err) { return done(err) } result.should.have.property(target) var key = result[target] key.should.have.property('exists') key.exists.should.eql(true) key.should.have.property('keys') key.keys.map(toLowerCase).should.containEql('policies') key.should.have.property('values') key.values.should.have.property('ProgramFilesDir') key.values.ProgramFilesDir.should.have.property('value') key.values.ProgramFilesDir.value.indexOf('C:\\Program Files').should.eql(0) key.values.ProgramFilesDir.should.have.property('type', 'REG_SZ') done() }) }) it(target + ' 32bit', function(done) { this.timeout(5000) index.arch.list32(target, function(err, result) { if (err) { return done(err) } result.should.have.property(target) var key = result[target] key.should.have.property('exists') key.exists.should.eql(true) key.should.have.property('keys') key.keys.map(toLowerCase).should.containEql('policies') key.should.have.property('values') key.values.should.have.property('ProgramFilesDir') key.values.ProgramFilesDir.should.have.property('value') key.values.ProgramFilesDir.value.indexOf('C:\\Program Files').should.eql(0) key.values.ProgramFilesDir.should.have.property('type', 'REG_SZ') done() }) }) it(target + ' 64bit', function(done) { index.arch.list64(target, function(err, result) { if (err) { return done(err) } result.should.have.property(target) var key = result[target] key.should.have.property('exists') key.exists.should.eql(true) key.should.have.property('keys') key.keys.map(toLowerCase).should.containEql('policies') key.should.have.property('values') key.values.should.have.property('ProgramFilesDir') key.values.ProgramFilesDir.should.have.property('value', 'C:\\Program Files') key.values.ProgramFilesDir.should.have.property('type', 'REG_SZ') done() }) }) it(target + ' arch auto pick', function(done) { index.arch.list(target, function(err, result) { if (err) { return done(err) } result.should.have.property(target) var key = result[target] key.should.have.property('exists') key.exists.should.eql(true) key.should.have.property('keys') key.keys.map(toLowerCase).should.containEql('policies') key.should.have.property('values') key.values.should.have.property('ProgramFilesDir') key.values.ProgramFilesDir.should.have.property('value', 'C:\\Program Files') key.values.ProgramFilesDir.should.have.property('type', 'REG_SZ') done() }) }) it('can be applied to several independant keys at once', function(done) { index.list(['hklm', 'hkcu'], function(err, result) { if (err) { return done(err) } result.should.have.property('hklm') result.hklm.should.have.property('exists') result.hklm.exists.should.eql(true) result.hklm.should.have.property('keys') result.hklm.keys.map(toLowerCase).should.containEql('software') result.should.have.property('hkcu') result.hkcu.should.have.property('exists') result.hkcu.exists.should.eql(true) result.hkcu.should.have.property('keys') result.hkcu.keys.map(toLowerCase).should.containEql('software') done() }) }) it('handle spaces in registry keys', function(done) { var key = 'HKCU\\Keyboard Layout' index.list([key], function(err, result) { if (err) { return done(err) } result[key].should.have.property('exists') result[key].exists.should.eql(true) result[key].should.have.property('keys') result[key].keys.map(toLowerCase).should.containEql('preload') result[key].keys.map(toLowerCase).should.containEql('substitutes') result[key].keys.map(toLowerCase).should.containEql('toggle') done() }) }) it.skip('reads unicode characters from the registry - need to manually create', function(done) { var key = 'HKCU\\software\\ironsource\\' index.list(key, function(err, result) { if (err) { return done(err) } result[key].should.have.property('exists') result[key].exists.should.eql(true) result[key].should.have.property('keys') result[key].keys.should.containEql('测试') done() }) }) it('will fail for unknown hives', function(done) { index.list('lala\\software', function(err) { should(err).not.be.null err.message.should.eql('unsupported hive') done() }) }) it('lists default values', function(done) { index.list('HKCR\\Directory\\shell\\cmd\\command', function(err, results) { if (err) { return done(err) } results['HKCR\\Directory\\shell\\cmd\\command'].should.have.property('exists') results['HKCR\\Directory\\shell\\cmd\\command'].exists.should.eql(true) results['HKCR\\Directory\\shell\\cmd\\command'].should.have.property('values') results['HKCR\\Directory\\shell\\cmd\\command'].values.should.have.property('') done() }) }) }) describe('create keys', function() { var key = 'HKCU\\software\\ironSource\\regedit\\test\\' var now = Date.now().toString() it('will throw an error if we dont have permission', function(done) { index.createKey('HKLM\\SECURITY\\unauthorized', function(err) { err.should.be.an.Error err.message.should.eql('access is denied') done() }) }) it(key + now, function(done) { index.createKey(key + now, function(err) { if (err) { return done(err) } // testing using the module itself is not the best idea... index.list(key, function(err, result) { if (err) { return done(err) } result[key].keys.should.containEql(now) done() }) }) }) it(key + now + '测试', function(done) { index.createKey(key + now + '测试', function(err) { if (err) { return done(err) } index.list(key, function(err, results) { if (err) { return done(err) } results[key].should.have.property('keys') results[key].keys.should.containEql(now + '测试') done() }) }) }) it(key + now + ' S', function(done) { index.arch.createKey(key + now, function(err) { if (err) { return done(err) } // testing using the module itself is not the best idea... index.arch.list(key, function(err, result) { if (err) { return done(err) } result[key].keys.should.containEql(now) done() }) }) }) it(key + now + ' 32bit', function(done) { index.arch.createKey32(key + now, function(err) { if (err) { return done(err) } // testing using the module itself is not the best idea... index.arch.list32(key, function(err, result) { if (err) { return done(err) } result[key].keys.should.containEql(now) done() }) }) }) it(key + now + ' 64bit', function(done) { index.arch.createKey64(key + now, function(err) { if (err) { return done(err) } // testing using the module itself is not the best idea... index.arch.list64(key, function(err, result) { if (err) { return done(err) } result[key].keys.should.containEql(now) done() }) }) }) afterEach(function() { now = Date.now().toString() }) }) describe('delete keys', function() { var key = 'HKCU\\software\\ironSource\\regedit\\test\\' var now = Date.now().toString() it('will throw an error if we attempt to delete a key without permission', function(done) { index.deleteKey('HKLM\\SECURITY', function(err) { err.should.be.an.Error err.message.should.eql('access is denied') done() }) }) it(key + now, function(done) { index.createKey(key + now, function(err) { if (err) { return done(err) } index.list(key, function(err, result) { if (err) { return done(err) } result[key].keys.should.containEql(now) index.deleteKey(key + now, function(err) { if (err) { return done(err) } index.list(key, function(err, result1) { if (err) { return done(err) } result1[key].keys.should.not.containEql(now) done() }) }) }) }) }) it(key + now + ' S', function(done) { index.arch.createKey(key + now, function(err) { if (err) { return done(err) } index.arch.list(key, function(err, result) { if (err) { return done(err) } result[key].keys.should.containEql(now) index.arch.deleteKey(key + now, function(err) { if (err) { return done(err) } index.list(key, function(err, result1) { if (err) { return done(err) } result1[key].keys.should.not.containEql(now) done() }) }) }) }) }) it(key + now + ' 32bit', function(done) { index.arch.createKey32(key + now, function(err) { if (err) { return done(err) } index.arch.list32(key, function(err, result) { if (err) { return done(err) } result[key].keys.should.containEql(now) index.arch.deleteKey32(key + now, function(err) { if (err) { return done(err) } index.list(key, function(err, result1) { if (err) { return done(err) } result1[key].keys.should.not.containEql(now) done() }) }) }) }) }) it(key + now + ' 64bit', function(done) { index.arch.createKey64(key + now, function(err) { if (err) { return done(err) } index.arch.list64(key, function(err, result) { if (err) { return done(err) } result[key].keys.should.containEql(now) index.arch.deleteKey64(key + now, function(err) { if (err) { return done(err) } index.list(key, function(err, result1) { if (err) { return done(err) } result1[key].keys.should.not.containEql(now) done() }) }) }) }) }) afterEach(function() { now = Date.now().toString() }) }) describe('put values', function() { var key = 'HKCU\\software\\ironSource\\regedit\\test\\' var now = Date.now().toString() var map = {} it('in ' + key + now, function(done) { index.putValue(map, function(err) { if (err) { return done(err) } index.list(key + now, function(err, result) { if (err) { console.error(result) return done(err) } var values = result[key + now].values values.should.have.property('a key') values['a key'].type.should.eql('REG_SZ') values['a key'].value.should.eql('some string') values.should.have.property('b') values.b.type.should.eql('REG_BINARY') values.b.value.should.eql([1, 2, 3]) values.should.have.property('c') values.c.type.should.eql('REG_DWORD') values.c.value.should.eql(10) values.should.have.property('d') values.d.type.should.eql('REG_QWORD') values.d.value.should.eql(100) values.should.have.property('e') values.e.type.should.eql('REG_EXPAND_SZ') values.e.value.should.eql('expand_string') values.should.have.property('f') values.f.type.should.eql('REG_MULTI_SZ') values.f.value.should.eql(['a', 'b', 'c']) values.should.have.property('测试') values['测试'].type.should.eql('REG_SZ') values['测试'].value.should.eql('值 test for non-English environment') values.should.have.property('newline') values.newline.type.should.eql('REG_SZ') values.newline.value.should.eql('new\\nline') done() }) }) }) it('default value in ' + key + now, function(done) { var values = {} values[key + now] = { 'default': { type: 'reg_default', value: 'default', }, } index.putValue(values, function(err) { if (err) { return done(err) } index.list(key + now, function(err, results) { if (err) { return done(err) } results[key + now].should.have.property('values') results[key + now].values.should.have.property('', { type: 'REG_SZ', value: 'default', }) done() }) }) }) it('in ' + key + now + ' S', function(done) { index.arch.putValue(map, function(err) { if (err) { return done(err) } index.arch.list(key + now, function(err, result) { if (err) { return done(err) } var values = result[key + now].values values.should.have.property('a key') values['a key'].type.should.eql('REG_SZ') values['a key'].value.should.eql('some string') values.should.have.property('b') values.b.type.should.eql('REG_BINARY') values.b.value.should.eql([1, 2, 3]) values.should.have.property('c') values.c.type.should.eql('REG_DWORD') values.c.value.should.eql(10) values.should.have.property('d') values.d.type.should.eql('REG_QWORD') values.d.value.should.eql(100) values.should.have.property('e') values.e.type.should.eql('REG_EXPAND_SZ') values.e.value.should.eql('expand_string') values.should.have.property('f') values.f.type.should.eql('REG_MULTI_SZ') values.f.value.should.eql(['a', 'b', 'c']) values.should.have.property('测试') values['测试'].type.should.eql('REG_SZ') values['测试'].value.should.eql('值 test for non-English environment') values.should.have.property('newline') values.newline.type.should.eql('REG_SZ') values.newline.value.should.eql('new\\nline') done() }) }) }) it('in ' + key + now + ' 32bit', function(done) { index.arch.putValue32(map, function(err) { if (err) { return done(err) } index.arch.list32(key + now, function(err, result) { if (err) { return done(err) } var values = result[key + now].values values.should.have.property('a key') values['a key'].type.should.eql('REG_SZ') values['a key'].value.should.eql('some string') values.should.have.property('b') values.b.type.should.eql('REG_BINARY') values.b.value.should.eql([1, 2, 3]) values.should.have.property('c') values.c.type.should.eql('REG_DWORD') values.c.value.should.eql(10) values.should.have.property('d') values.d.type.should.eql('REG_QWORD') values.d.value.should.eql(100) values.should.have.property('e') values.e.type.should.eql('REG_EXPAND_SZ') values.e.value.should.eql('expand_string') values.should.have.property('f') values.f.type.should.eql('REG_MULTI_SZ') values.f.value.should.eql(['a', 'b', 'c']) values.should.have.property('测试') values['测试'].type.should.eql('REG_SZ') values['测试'].value.should.eql('值 test for non-English environment') values.should.have.property('newline') values.newline.type.should.eql('REG_SZ') values.newline.value.should.eql('new\\nline') done() }) }) }) it('in ' + key + now + '64bit', function(done) { index.arch.putValue64(map, function(err) { if (err) { return done(err) } index.arch.list64(key + now, function(err, result) { if (err) { return done(err) } var values = result[key + now].values values.should.have.property('a key') values['a key'].type.should.eql('REG_SZ') values['a key'].value.should.eql('some string') values.should.have.property('b') values.b.type.should.eql('REG_BINARY') values.b.value.should.eql([1, 2, 3]) values.should.have.property('c') values.c.type.should.eql('REG_DWORD') values.c.value.should.eql(10) values.should.have.property('d') values.d.type.should.eql('REG_QWORD') values.d.value.should.eql(100) values.should.have.property('e') values.e.type.should.eql('REG_EXPAND_SZ') values.e.value.should.eql('expand_string') values.should.have.property('f') values.f.type.should.eql('REG_MULTI_SZ') values.f.value.should.eql(['a', 'b', 'c']) values.should.have.property('测试') values['测试'].type.should.eql('REG_SZ') values['测试'].value.should.eql('值 test for non-English environment') values.should.have.property('newline') values.newline.type.should.eql('REG_SZ') values.newline.value.should.eql('new\\nline') done() }) }) }) beforeEach(function(done) { index.createKey(key + now, done) map[key + now] = { 'a key': { type: 'reg_sz', value: 'some string', }, 'b': { type: 'reg_binary', value: [1, 2, 3], }, 'c': { type: 'reg_dword', value: 10, }, 'd': { type: 'reg_qword', value: 100, }, 'e': { type: 'reg_expand_sz', value: 'expand_string', }, 'f': { type: 'reg_multi_sz', value: ['a', 'b', 'c'], }, '测试': { type: 'reg_sz', value: '值 test for non-English environment', }, 'newline': { type: 'reg_sz', value: 'new\nline', }, } }) afterEach(function() { now = Date.now().toString() }) }) describe('delete values', function() { var key = 'HKCU\\SOFTWARE\\ironSource\\regedit\\test\\' var now = '' var map = {} function genericTest(arch, done) { index.arch['putValue' + arch](map, function(err) { if (err) { return done(err) } index.arch['list' + arch](key + now, function(err, result) { if (err) { return done(err) } var values = result[key + now].values values.should.have.property('DeleteMe') index.arch['deleteValue' + arch](key + now + '\\DeleteMe', function(err) { if (err) { return done(err) } index.arch['list' + arch](key + now, function(err, result) { if (err) { return done(err) } result[key + now].should.not.have.property('DeleteMe') done() }) }) }) }) } beforeEach(function(done) { now = Date.now().toString() map[key + now] = { 'DeleteMe': { type: 'reg_sz', value: 'some string', }, } this.currentTest.title = 'Key: ' + key + now + ' ' + this.currentTest.title index.createKey(key + now, done) }) it('Agnostic', function(done) { index.putValue(map, function(err) { if (err) { return done(err) } index.list(key + now, function(err, result) { if (err) { return done(err) } var values = result[key + now].values values.should.have.property('DeleteMe') index.deleteValue(key + now + '\\DeleteMe', function(err) { if (err) { return done(err) } index.list(key + now, function(err, result) { if (err) { return done(err) } result[key + now].values.should.not.have.property('DeleteMe') done() }) }) }) }) }) it('Specific', function(done) { genericTest('', done) }) it('32bit', function(done) { genericTest('32', done) }) it('64bit', function(done) { genericTest('64', done) }) }) describe('listUnexpandedValues', function () { it('reads values without expanding environment variables embedded in them', function(done) { const key = 'HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders\\AppData' index.listUnexpandedValues(key, function(err, result) { if (err) { return done(err) } result.should.deepEqual([{ path: 'HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders\\AppData', exists: true, value: '%USERPROFILE%\\AppData\\Roaming', }]) done() }) }) it('does not fail for values that dont exist', function(done) { index.listUnexpandedValues('HKCU\\Software\\Microsoft\\blabla', function(err, result) { if (err) { return done(err) } result.should.deepEqual([{ path: 'HKCU\\Software\\Microsoft\\blabla', exists: false, value: '', }]) done() }) }) it('has a streaming interface', function(done) { const results = [] const stream = index.listUnexpandedValues([ 'HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders\\AppData', 'HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders\\AppData', 'HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders\\AppData', ]).on('data', function (result) { results.push(result) }).on('end', function () { results.should.deepEqual([{ path: 'HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders\\AppData', exists: true, value: '%USERPROFILE%\\AppData\\Roaming', }, { path: 'HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders\\AppData', exists: true, value: '%USERPROFILE%\\AppData\\Roaming', }, { path: 'HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders\\AppData', exists: true, value: '%USERPROFILE%\\AppData\\Roaming', }]) done() }) }) }) })