Loading plugin/ad/ad.cpp +4 −1 Changes for plugin/ad/ad.cpp: 4 added lines, 1 removed line. Original line number Diff line number Diff line Loading @@ -852,7 +852,8 @@ bool ActiveDirectory::dirRemoveMember(const std::string &domain, const uuid::uui } bool ActiveDirectory::dirImportNative(const std::string &domain, int &migrated, std::string &err) { std::string &err, std::map<std::string, std::string> *groupMap) { if (g_Replication && g_Replication->isSlave()) { err = "this node is a replication slave (read-only); make changes on the master"; return false; Loading Loading @@ -931,6 +932,8 @@ bool ActiveDirectory::dirImportNative(const std::string &domain, int &migrated, continue; } } if (groupMap) (*groupMap)[gid.c_str()] = groupGuid.c_str(); /* add each native member (resolved by username) to the directory * group — member + memberOf, duplicate-safe so a re-import is a no-op */ Loading plugin/ad/ad.h +2 −1 Changes for plugin/ad/ad.h: 2 added lines, 1 removed line. Original line number Diff line number Diff line Loading @@ -280,7 +280,8 @@ namespace fenrirds { /* unified directory CRUD (see AdPlugin for the contract) */ void reloadDomains() override { loadDomains(); } bool dirImportNative(const std::string &domain, int &migrated, std::string &err) override; std::string &err, std::map<std::string, std::string> *groupMap = nullptr) override; bool dirList(const std::string &domain, int kind, std::vector<dsdb::Entry> &out, std::string &err) override; bool dirGet(const std::string &domain, const uuid::uuid &guid, Loading src/admin.cpp +29 −1 Changes for src/admin.cpp: 29 added lines, 1 removed line. Original line number Diff line number Diff line Loading @@ -2077,9 +2077,37 @@ namespace fenrirds { if (strcmp(cdid, "admin") != 0 && g_AdPlugin) { std::string domain = domainNameFor(cdid); std::string err; if (!domain.empty() && !g_AdPlugin->dirImportNative(domain, migrated, err)) std::map<std::string, std::string> groupMap; if (!domain.empty() && !g_AdPlugin->dirImportNative(domain, migrated, err, &groupMap)) std::cerr << "import: dirImportNative failed: " << err << std::endl; /* imported GPOs still allow the native group uuids: point them * at the directory groups those were migrated to */ if (!groupMap.empty()) { AuthBackend::Guard g(*backend); Gpo gpo; std::vector<uuid::uuid> gpoids; gpo.list(*backend, gpoids); for (const auto &gpoid : gpoids) { class GpoData gd(gpoid); size_t gp = sizeof(AuthHeader); try { gpo.info(*backend, gd, gp); } catch (...) { continue; } std::vector<uuid::uuid> allow; gd.getAlowed(allow); bool changed = false; for (auto &a : allow) { auto it = groupMap.find(a.c_str()); if (it != groupMap.end() && it->second != a.c_str()) { a = uuid::uuid(it->second.c_str()); changed = true; } } if (!changed) continue; gd.setAllowed(allow); try { gpo.edit(*backend, gd); } catch (...) {} } } /* ensure the domain has the default policies (so the Policies * view is populated), with allowed pointing at the directory * "Domain Admins" group — matching session memberships */ Loading src/plugin.h +6 −3 Changes for src/plugin.h: 6 added lines, 3 removed lines. Original line number Diff line number Diff line Loading @@ -189,10 +189,13 @@ namespace fenrirds { * @webHash (so web login keeps working via dirAuthenticate without the * clear password); native groups become directory groups with their * members. Objects already present in the directory are skipped. Fills * `migrated` with the count. Default: unsupported. */ * `migrated` with the count. If groupMap is given, it receives native * group uuid -> directory group objectGUID for every native group, so * references (GPO allowed lists) can be remapped. Default: unsupported. */ virtual bool dirImportNative(const std::string &domain, int &migrated, std::string &err) { (void)domain; (void)migrated; std::string &err, std::map<std::string, std::string> *groupMap = nullptr) { (void)domain; (void)migrated; (void)groupMap; err = "directory service unavailable"; return false; } Loading Loading
plugin/ad/ad.cpp +4 −1 Changes for plugin/ad/ad.cpp: 4 added lines, 1 removed line. Original line number Diff line number Diff line Loading @@ -852,7 +852,8 @@ bool ActiveDirectory::dirRemoveMember(const std::string &domain, const uuid::uui } bool ActiveDirectory::dirImportNative(const std::string &domain, int &migrated, std::string &err) { std::string &err, std::map<std::string, std::string> *groupMap) { if (g_Replication && g_Replication->isSlave()) { err = "this node is a replication slave (read-only); make changes on the master"; return false; Loading Loading @@ -931,6 +932,8 @@ bool ActiveDirectory::dirImportNative(const std::string &domain, int &migrated, continue; } } if (groupMap) (*groupMap)[gid.c_str()] = groupGuid.c_str(); /* add each native member (resolved by username) to the directory * group — member + memberOf, duplicate-safe so a re-import is a no-op */ Loading
plugin/ad/ad.h +2 −1 Changes for plugin/ad/ad.h: 2 added lines, 1 removed line. Original line number Diff line number Diff line Loading @@ -280,7 +280,8 @@ namespace fenrirds { /* unified directory CRUD (see AdPlugin for the contract) */ void reloadDomains() override { loadDomains(); } bool dirImportNative(const std::string &domain, int &migrated, std::string &err) override; std::string &err, std::map<std::string, std::string> *groupMap = nullptr) override; bool dirList(const std::string &domain, int kind, std::vector<dsdb::Entry> &out, std::string &err) override; bool dirGet(const std::string &domain, const uuid::uuid &guid, Loading
src/admin.cpp +29 −1 Changes for src/admin.cpp: 29 added lines, 1 removed line. Original line number Diff line number Diff line Loading @@ -2077,9 +2077,37 @@ namespace fenrirds { if (strcmp(cdid, "admin") != 0 && g_AdPlugin) { std::string domain = domainNameFor(cdid); std::string err; if (!domain.empty() && !g_AdPlugin->dirImportNative(domain, migrated, err)) std::map<std::string, std::string> groupMap; if (!domain.empty() && !g_AdPlugin->dirImportNative(domain, migrated, err, &groupMap)) std::cerr << "import: dirImportNative failed: " << err << std::endl; /* imported GPOs still allow the native group uuids: point them * at the directory groups those were migrated to */ if (!groupMap.empty()) { AuthBackend::Guard g(*backend); Gpo gpo; std::vector<uuid::uuid> gpoids; gpo.list(*backend, gpoids); for (const auto &gpoid : gpoids) { class GpoData gd(gpoid); size_t gp = sizeof(AuthHeader); try { gpo.info(*backend, gd, gp); } catch (...) { continue; } std::vector<uuid::uuid> allow; gd.getAlowed(allow); bool changed = false; for (auto &a : allow) { auto it = groupMap.find(a.c_str()); if (it != groupMap.end() && it->second != a.c_str()) { a = uuid::uuid(it->second.c_str()); changed = true; } } if (!changed) continue; gd.setAllowed(allow); try { gpo.edit(*backend, gd); } catch (...) {} } } /* ensure the domain has the default policies (so the Policies * view is populated), with allowed pointing at the directory * "Domain Admins" group — matching session memberships */ Loading
src/plugin.h +6 −3 Changes for src/plugin.h: 6 added lines, 3 removed lines. Original line number Diff line number Diff line Loading @@ -189,10 +189,13 @@ namespace fenrirds { * @webHash (so web login keeps working via dirAuthenticate without the * clear password); native groups become directory groups with their * members. Objects already present in the directory are skipped. Fills * `migrated` with the count. Default: unsupported. */ * `migrated` with the count. If groupMap is given, it receives native * group uuid -> directory group objectGUID for every native group, so * references (GPO allowed lists) can be remapped. Default: unsupported. */ virtual bool dirImportNative(const std::string &domain, int &migrated, std::string &err) { (void)domain; (void)migrated; std::string &err, std::map<std::string, std::string> *groupMap = nullptr) { (void)domain; (void)migrated; (void)groupMap; err = "directory service unavailable"; return false; } Loading