const ldap = require('../../util/ldapjs-extra'); const ssh = require('node-ssh'); module.exports = Self => { Self.remoteMethod('syncAll', { description: 'Synchronizes user database with LDAP and Samba', http: { path: `/syncAll`, verb: 'PATCH' } }); Self.syncAll = async function() { let $ = Self.app.models; let usersToSync = new Set(); // Database let accounts = await $.UserAccount.find({ fields: ['id'], include: { relation: 'user', scope: { fields: ['name'], where: {active: true} } } }); for (let account of accounts) { let user = account.user(); if (!user) continue; usersToSync.add(user.name); } // LDAP let ldapConfig = await $.LdapConfig.findOne({ fields: ['host', 'rdn', 'password', 'baseDn'] }); if (ldapConfig) { let ldapClient = ldap.createClient({ url: `ldap://${ldapConfig.host}:389` }); let ldapPassword = Buffer .from(ldapConfig.password, 'base64') .toString('ascii'); await ldapClient.bind(ldapConfig.rdn, ldapPassword); res = await ldapClient.search(ldapConfig.baseDn, { scope: 'sub', attributes: ['uid'], filter: `uid=*` }); await new Promise((resolve, reject) => { res.on('error', reject); res.on('searchEntry', e => usersToSync.add(e.object.uid)); res.on('end', resolve); }); // FIXME: Cannot disconnect, hangs on undind() call // await ldapClient.unbind(); } // Samba let sambaConfig = await $.SambaConfig.findOne({ fields: ['host', 'sshUser', 'sshPass'] }); if (sambaConfig) { let sshPassword = Buffer .from(sambaConfig.sshPass, 'base64') .toString('ascii'); let sshClient = new ssh.NodeSSH(); await sshClient.connect({ host: sambaConfig.host, username: sambaConfig.sshUser, password: sshPassword }); let res = await sshClient.execCommand('samba-tool user list'); let users = res.stdout.split('\n'); for (let user of users) usersToSync.add(user.trim()); await sshClient.dispose(); } // Syncing $.RoleInherit.sync(); let sync = await Self.syncInit(); for (let user of usersToSync.values()) { try { await Self.doSync(sync, user); } catch (err) { console.error(`Cannot sync user '${user}':`, err); } } await Self.syncDeinit(sync); }; };