Use tasks api for external ldap syncer
This commit is contained in:
+68
-59
@@ -4,6 +4,7 @@ exports = module.exports = {
|
||||
ExternalLdapError: ExternalLdapError,
|
||||
|
||||
testConfig: testConfig,
|
||||
startSyncer: startSyncer,
|
||||
|
||||
sync: sync
|
||||
};
|
||||
@@ -12,6 +13,7 @@ var assert = require('assert'),
|
||||
debug = require('debug')('box:ldapclient'),
|
||||
ldap = require('ldapjs'),
|
||||
settings = require('./settings.js'),
|
||||
tasks = require('./tasks.js'),
|
||||
util = require('util');
|
||||
|
||||
function ExternalLdapError(reason, errorOrMessage) {
|
||||
@@ -41,30 +43,24 @@ ExternalLdapError.BAD_FIELD = 'bad field';
|
||||
ExternalLdapError.NOT_FOUND = 'not found';
|
||||
|
||||
// performs service bind if required
|
||||
function getClientAndConfig(callback) {
|
||||
function getClient(externalLdapConfig, callback) {
|
||||
assert.strictEqual(typeof callback, 'function');
|
||||
|
||||
settings.getExternalLdapConfig(function (error, externalLdapConfig) {
|
||||
if (error) return callback(new ExternalLdapError(ExternalLdapError.INTERNAL_ERROR, error));
|
||||
var client;
|
||||
try {
|
||||
client = ldap.createClient({ url: externalLdapConfig.url });
|
||||
} catch (e) {
|
||||
if (e instanceof ldap.ProtocolError) return callback(new ExternalLdapError(ExternalLdapError.BAD_FIELD, 'url protocol is invalid'));
|
||||
return callback(new ExternalLdapError(ExternalLdapError.INTERNAL_ERROR, e));
|
||||
}
|
||||
|
||||
var client;
|
||||
try {
|
||||
client = ldap.createClient({ url: externalLdapConfig.url });
|
||||
} catch (e) {
|
||||
if (e instanceof ldap.ProtocolError) return callback(new ExternalLdapError(ExternalLdapError.BAD_FIELD, 'url protocol is invalid'));
|
||||
return callback(new ExternalLdapError(ExternalLdapError.INTERNAL_ERROR, e));
|
||||
}
|
||||
if (!externalLdapConfig.bindDn) return callback(null, client);
|
||||
|
||||
if (!externalLdapConfig.bindDn) return callback(null, client);
|
||||
client.bind(externalLdapConfig.bindDn, externalLdapConfig.bindPassword, function (error) {
|
||||
if (error instanceof ldap.InvalidCredentialsError) return callback(new ExternalLdapError(ExternalLdapError.INVALID_CREDENTIALS));
|
||||
if (error) return callback(new ExternalLdapError(ExternalLdapError.EXTERNAL_ERROR, error));
|
||||
|
||||
client.bind(externalLdapConfig.bindDn, externalLdapConfig.bindPassword, function (error) {
|
||||
if (error instanceof ldap.InvalidCredentialsError) return callback(new ExternalLdapError(ExternalLdapError.INVALID_CREDENTIALS));
|
||||
if (error) return callback(new ExternalLdapError(ExternalLdapError.EXTERNAL_ERROR, error));
|
||||
|
||||
debug('getClient: successful');
|
||||
|
||||
callback(null, client, externalLdapConfig);
|
||||
});
|
||||
callback(null, client, externalLdapConfig);
|
||||
});
|
||||
}
|
||||
|
||||
@@ -83,26 +79,7 @@ function testConfig(config, callback) {
|
||||
try { ldap.parseFilter(config.filter); } catch (e) { return callback(new ExternalLdapError(ExternalLdapError.BAD_FIELD, 'invalid filter')); }
|
||||
if (config.bindDn) try { ldap.parseFilter(config.bindDn); } catch (e) { return callback(new ExternalLdapError(ExternalLdapError.INVALID_CREDENTIALS)); }
|
||||
|
||||
var client;
|
||||
try {
|
||||
client = ldap.createClient({ url: config.url });
|
||||
} catch (e) {
|
||||
if (e instanceof ldap.ProtocolError) return callback(new ExternalLdapError(ExternalLdapError.BAD_FIELD, 'url protocol is invalid'));
|
||||
return callback(new ExternalLdapError(ExternalLdapError.EXTERNAL_ERROR, e));
|
||||
}
|
||||
|
||||
function bindIfNeeded(callback) {
|
||||
if (!config.bindDn) return callback();
|
||||
|
||||
client.bind(config.bindDn, config.bindPassword, function (error) {
|
||||
if (error instanceof ldap.InvalidCredentialsError) return callback(new ExternalLdapError(ExternalLdapError.INVALID_CREDENTIALS));
|
||||
if (error) return callback(new ExternalLdapError(ExternalLdapError.EXTERNAL_ERROR, error));
|
||||
|
||||
callback();
|
||||
});
|
||||
}
|
||||
|
||||
bindIfNeeded(function (error) {
|
||||
getClient(config, function (error, client) {
|
||||
if (error) return callback(error);
|
||||
|
||||
var opts = {
|
||||
@@ -120,31 +97,63 @@ function testConfig(config, callback) {
|
||||
});
|
||||
}
|
||||
|
||||
function sync(callback) {
|
||||
function startSyncer(callback) {
|
||||
assert.strictEqual(typeof callback, 'function');
|
||||
|
||||
getClientAndConfig(function (error, client, externalLdapConfig) {
|
||||
if (error) return callback(error);
|
||||
settings.getExternalLdapConfig(function (error, externalLdapConfig) {
|
||||
if (error) return callback(new ExternalLdapError(ExternalLdapError.INTERNAL_ERROR, error));
|
||||
if (!externalLdapConfig.enabled) return callback(new ExternalLdapError(ExternalLdapError.BAD_STATE, 'not enabled'));
|
||||
|
||||
var opts = {
|
||||
filter: externalLdapConfig.filter,
|
||||
scope: 'sub'
|
||||
};
|
||||
tasks.add(tasks.TASK_SYNC_EXTERNAL_LDAP, [], function (error, taskId) {
|
||||
if (error) return callback(new ExternalLdapError(ExternalLdapError.INTERNAL_ERROR, error));
|
||||
|
||||
client.search(externalLdapConfig.baseDn, opts, function(err, res) {
|
||||
assert.ifError(err);
|
||||
tasks.startTask(taskId, {}, function (error, result) {
|
||||
debug('sync: done', error, result);
|
||||
});
|
||||
|
||||
res.on('searchEntry', function(entry) {
|
||||
console.log('entry: ' + JSON.stringify(entry.object));
|
||||
});
|
||||
res.on('searchReference', function(referral) {
|
||||
console.log('referral: ' + referral.uris.join());
|
||||
});
|
||||
res.on('error', function(err) {
|
||||
console.error('error: ' + err.message);
|
||||
});
|
||||
res.on('end', function(result) {
|
||||
console.log('status: ' + result.status);
|
||||
callback(null, taskId);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function sync(progressCallback, callback) {
|
||||
assert.strictEqual(typeof progressCallback, 'function');
|
||||
assert.strictEqual(typeof callback, 'function');
|
||||
|
||||
settings.getExternalLdapConfig(function (error, externalLdapConfig) {
|
||||
if (error) return callback(new ExternalLdapError(ExternalLdapError.INTERNAL_ERROR, error));
|
||||
if (!externalLdapConfig.enabled) return callback(new ExternalLdapError(ExternalLdapError.BAD_STATE, 'not enabled'));
|
||||
|
||||
// basic validation to not crash
|
||||
try { ldap.parseDN(externalLdapConfig.baseDn); } catch (e) { return callback(new ExternalLdapError(ExternalLdapError.BAD_FIELD, 'invalid baseDn')); }
|
||||
try { ldap.parseFilter(externalLdapConfig.filter); } catch (e) { return callback(new ExternalLdapError(ExternalLdapError.BAD_FIELD, 'invalid filter')); }
|
||||
if (externalLdapConfig.bindDn) try { ldap.parseFilter(externalLdapConfig.bindDn); } catch (e) { return callback(new ExternalLdapError(ExternalLdapError.INVALID_CREDENTIALS)); }
|
||||
|
||||
getClient(externalLdapConfig, function (error, client) {
|
||||
if (error) return callback(error);
|
||||
|
||||
var opts = {
|
||||
filter: externalLdapConfig.filter,
|
||||
scope: 'sub'
|
||||
};
|
||||
|
||||
client.search(externalLdapConfig.baseDn, opts, function (error, result) {
|
||||
if (error) return callback(new ExternalLdapError(ExternalLdapError.EXTERNAL_ERROR, error));
|
||||
|
||||
result.on('searchEntry', function(entry) {
|
||||
console.log('entry: ' + JSON.stringify(entry.object));
|
||||
|
||||
// TODO ensure db record for user
|
||||
});
|
||||
|
||||
result.on('error', function (error) {
|
||||
callback(new ExternalLdapError(ExternalLdapError.EXTERNAL_ERROR, error));
|
||||
});
|
||||
|
||||
result.on('end', function(result) {
|
||||
console.log('status: ' + result.status);
|
||||
callback();
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user