settings.ps1

# This doesnt work outside of functions
$moduleData = $MyInvocation.MyCommand.Module
$Runtime = [ordered]@{
    Date   = $(get-date)
    Domain = $(
        get-ADDomain | foreach-object {
            [ordered]@{
                DN      = $_.DistinguishedName
                DNSRoot = $_.DNSRoot
                Netbios = $_.NetbiosName
                ConfigurationNamingContext = $((get-adrootdse).configurationNamingContext)
            }
        }
    )
    Stamp  = [ordered]@{
        SID  = [System.Security.Principal.WindowsIdentity]::GetCurrent().user.value
        Name = [System.Security.Principal.WindowsIdentity]::GetCurrent().Name
        Time = $(Get-date).ToFileTimeUtc()
    }
}

$Defaults = [ordered]@{}

$Defaults['Names'] = [ordered]@{
    SettingsNames = [ordered]@{
        AppSettings = "AppSettings"
        API         = "API"
        FilePaths   = "FilePaths"
        OUPaths     = "OUPaths"
        Templates   = "Templates"
        Metadata    = "Metadata"
        Names       = "Names"
        Rights      = "Rights"
    }
}
$Defaults['Names'] = [ordered]@{
    __Metadata         = [ordered]@{
        Name        = $Defaults['Names']['SettingsNames']['Names']
        Description = "AD Object Naming"
        ChangeLog   = @("Initial Release")
        Version     = 2
        MinVersion  = 1
    }
    SettingsNames      = $Defaults['Names']['SettingsNames']
    SettingsObject     = "Metadata"
    SettingsContainer  = "PS.RAD.Tenants"
    SysvolSettingsDir  = "PS.RAD"
    Tenant             = "RAD"
    GlobalOU           = "Global"
    OrgsOU             = "Orgs"
    ComponentsOU       = "Components"
    RightsOU           = "Rights"
    RightsName         = "Right"
    RightsPrefix       = "$([char]0x2756)" # ❖
    RightsProtected    = "$([char]0x26D4)" # ⛔
    RolesOU            = "Roles"
    RolesName          = "Role"
    RolesSuffix        = "$([char]0x260D)" # ☍
    RoleProtected      = "$([char]0x26A1)" # ⚡
    DefaultUsersOU     = "Users"
    EndpointsOU        = "Endpoints"
    ServiceAcctOU      = "ServiceAccounts"
    PrivilegedUsersOU  = "AdminAccounts"
    DefaultComputersOU = "_Unassigned"
    EndpointPAWs       = "PAWs"
    EndpointPKI        = "PKI"
    LinuxFeaturesOU    = "LinuxFeatures"
    NetgroupsOU        = "Netgroups"
    SudoersOU          = "Sudoers"
    AppRightPrefix     = "App"
    RolesList          = @{
        Admin        = "Admin"
        Owner        = "Owner"
        Operator     = "Operator"
        User         = "User"
        AppAdmin     = "App-Admin"
        LinuxAdmin   = "Linux-Admin"
        GPOAdmin     = "GPO-Admin"
        AccountAdmin = "Account-Admin"
        RBACAdmin    = "RBAC-Admin"
        PKIAdmin     = "PKI-Admin"
        ServicePrivileged = "Service-Privileged"
    }
    GPOs               = @{
        PrefixHigh = "_HBAC"
        PrefixLow  = "_Settings"
    }
}

$Defaults['Rights'] = [ordered]@{
    __Metadata            = [ordered]@{
        Name        = $Defaults['Names']['SettingsNames']['Rights']
        Description = "'Rights' Security group names"
        ChangeLog   = @("Initial Release")
        Version     = 2
        MinVersion  = 1
    }
    AppAccess             = "{0}-access" -f $Defaults['Names']['AppRightPrefix']
    AppPoweruser          = "{0}-modify" -f $Defaults['Names']['AppRightPrefix']
    AppAdmin              = "{0}-admin" -f $Defaults['Names']['AppRightPrefix']
    CreateDeleteComputer  = "AddEndpoint"
    LogonBatch            = "LogonBatch"
    LogonRemote           = "LogonRemote"
    LogonLocal            = "LogonLocal"
    LogonService          = "LogonService"
    LogonNetwork          = "LogonNetwork"
    LAPS                  = "LAPSReadPassword"
    GPOAudit              = "GPOAudit"
    GPOEdit               = "GPOEdit"
    GPOLink               = "GPOLink"
    ManageRights          = "Rights-Admin"
    ManageRoles           = "Roles-Manage"
    ServiceAccountLegacy  = "ServiceAcct-Legacy"
    ServiceAccountMSA     = "ServiceAcct-MSA"
    OUCreate              = "OUCreate"
    OUManage              = "OUManage"
    WinAdmin              = "WindowsAdmin"
    WinOps                = "WindowsOps"
    LinAdmin              = "sudo_full"
    LinAdminNoPassword    = "sudo-nopasswd_full"
    LinOps                = "sudo_operate"
    LinInstaller          = "sudo_software"
    SudoManager           = "SudoManager"
    UserCreate            = "UserCreate"
    UserPasswdReset       = "UserReset"
    UserControl           = "UserControl"
    AdminUserCreate       = "AdminCreate"
    AdminUserControl      = "AdminControl"
    AdminUserPasswdReset  = "AdminReset"
    GenerateSecurityAudit = "GenerateSecurityAudit"
    DHCPAdmin             = "DHCPAdmin"
    PKIManageCA           = "PKI-ManageCA"
    PKIEnrollmentAgent    = "PKI-EnrollmentAgent"
    PKIIssue              = "PKI-Issue"
    PKIEnroll             = "PKI-Enroll"
    OrgManage             = "OrgManage"
    OrgDelete             = "OrgDelete"
    ComponentManage       = "ComponentManage"
}

$Defaults['AppSettings'] = [Ordered]@{
    __Metadata             = [ordered]@{
        Name        = $Defaults['Names']['SettingsNames']['AppSettings']
        Description = "Application Settings"
        ChangeLog   = @("Initial Release")
        Version     = 2
        MinVersion  = 1
    }
    SleepTimeout           = 20
    SleepLength            = 2
    RightScope             = "DomainLocal"
    RoleScope              = "Global"
    DefaultDenyObjectTypes = @(
        "Organizational-Unit"
        "User"
        "Computer"
        "Group"
        "ms-DS-Group-Managed-Service-Account"
        "ms-DS-Managed-Service-Account"
    )
}

$Defaults['OUPaths'] = [ordered]@{
    __Metadata        = [ordered]@{
        Name        = $Defaults['Names']['SettingsNames']['OUPaths']
        Description = "Locations of centrally stored SMB resources"
        ChangeLog   = @("Current model arch has Global == TenantRoot, with Linux features + orgs directly under it")
        Version     = 2
        MinVersion  = 1
    }
    SettingsContainer = "CN={0},CN={1},CN=Program Data,{2}" -f $Defaults['Names']['Tenant'], $Defaults['Names']['SettingsContainer'], $Runtime['domain'].dn
    TenantRoot        = "OU={0},{1}" -f $Defaults['Names']['Tenant'], $Runtime['domain'].dn
}
$Defaults['OUPaths'] += [ordered]@{
    Global            = "{0}" -f $Defaults['OUPaths']['TenantRoot']
    OrgsBase          = "OU={0},{1}" -f $Defaults['Names']['OrgsOU'], $Defaults['OUPaths']['TenantRoot']
    LinuxFeaturesBase = "OU={0},{1}" -f $Defaults['Names']['LinuxFeaturesOU'], $Defaults['OUPaths']['TenantRoot']
}
$Defaults['OUPaths'] += [ordered]@{
    GlobalEndpoints = "OU={0},{1}" -f $defaults['Names']['EndpointsOU'], $defaults['OUPaths']['Global']
}
$Defaults['OUPaths'] += [ordered]@{
    DefaultUsers     = "OU={0},{1}" -f $defaults['Names']['DefaultUsersOU'], $Defaults['OUPaths']['Global']
    PrivilegedUsers  = "OU={0},{1}" -f $defaults['Names']['PrivilegedUsersOU'], $Defaults['OUPaths']['Global']
    DefaultComputers = "OU={0},{1}" -f $defaults['Names']['DefaultComputersOU'], $defaults['OUPaths']['GlobalEndpoints']
    PAWs             = "OU={0},{1}" -f $defaults['Names']['EndpointPAWs'], $defaults['OUPaths']['GlobalEndpoints']
    PKI              = "OU={0},{1}" -f $defaults['Names']['EndpointPKI'], $defaults['OUPaths']['GlobalEndpoints']
    GlobalRights     = "OU={0},{1}" -f $defaults['Names']['RightsOU'], $Defaults['OUPaths']['Global']
    GlobalRoles      = "OU={0},{1}" -f $defaults['Names']['RolesOU'], $Defaults['OUPaths']['Global']
    LinuxSudoers     = "OU={0},{1}" -f $Defaults['Names']['SudoersOU'], $Defaults['OUPaths']['LinuxFeaturesBase']
    LinuxNetgroups   = "OU={0},{1}" -f $Defaults['Names']['NetGroupsOU'], $Defaults['OUPaths']['LinuxFeaturesBase']
}
# Fixup for any paths where the first element is null
$itemsToFix = $Defaults['OUPaths'].GetEnumerator() | where-object { $_['value'] -match "(.*)(OU=,)(.*)" }
$itemsToFix | foreach-object {
    write-loghandler -level "warning" -message "Fixing OUPaths: $($_.key) (this is a settings issue)"
    $defaults['oupaths'][$_['key']] = $defaults['oupaths'][$_['key']] -replace "OU=,", ""
}

$Defaults['API'] = [Ordered]@{
    __Metadata = [ordered]@{
        Name        = $Defaults['Names']['SettingsNames']['API']
        Description = "Code compatibility / Change notes"
        ChangeLog   = @("Initial Release")
        Version     = 2
        MinVersion  = 1
    }
}

$Defaults['FilePaths'] = [ordered]@{
    __Metadata        = [ordered]@{
        Name        = $Defaults['Names']['SettingsNames']['FilePaths']
        Description = "Locations of centrally stored SMB resources"
        ChangeLog   = @("Initial Release")
        Version     = 2
        MinVersion  = 1
    }
    BaseSysvolRADPath = "\\{0}\SYSVOL\{0}\{1}" -f $($Runtime['Domain']['dnsroot']), $Defaults['Names']['SysvolSettingsDir']
}
$Defaults['FilePaths'] += [ordered]@{
    PrimordialTemplates = "{0}\PrimordialTemplates" -f $Defaults['FilePaths']['BaseSysvolRADPath']
    JSONTemplates       = "{0}\JSONTemplates" -f $Defaults['FilePaths']['BaseSysvolRADPath']
    LDIFImports         = "{0}\LDIF_Imports" -f $Defaults['FilePaths']['BaseSysvolRADPath']
    Scripts             = "{0}\Scripts" -f $Defaults['FilePaths']['BaseSysvolRADPath']
    SettingsFile        = "{0}\settings.json" -f $Defaults['FilePaths']['BaseSysvolRADPath']
}


$Defaults['Templates'] = [ordered]@{
    __Metadata = [ordered]@{
        Name        = $Defaults['Names']['SettingsNames']['Templates']
        Description = "Compatibility of DACLs, GPO, and group templates"
        ChangeLog   = @("Initial Release")
        Version     = 2
        MinVersion  = 1
    }
    Global     = [ordered]@{}
    Orgs       = [ordered]@{}
    Component  = [ordered]@{}
}

$Defaults['Metadata'] = [ordered]@{
    __Metadata     = [ordered]@{
        Name        = $Defaults['Names']['SettingsNames']['Metadata']
        Description = "Core Meta Settings"
        ChangeLog   = @("Initial Release")
        Version     = 2
        MinVersion  = 1
    }
    URL            = ""
    OID            = ""
    InstallDate    = $Runtime['Date'].ToLongDateString() + " @ " + $Runtime['Date'].ToLongTimeString()
    InstallVersion = ""
}
$Defaults['Metadata'] += @{
    Settings = [ordered]@{}
    Modules  = [ordered]@{
        Core = @{
            Version        = ""
            OID            = $Runtime['Stamp'].Time
            InstallDate    = $Runtime['date'].ToLongDateString() + " @ " + $Runtime['date'].ToLongTimeString()
            SettingsObject = "CN={0},{1}" -f $Defaults['Names']['SettingsObject'], $Defaults['OUPaths']['SettingsContainer']
        }
    }
}


foreach ($setting in $Defaults['Names']['SettingsNames'].getEnumerator()) {
    $Defaults.$($setting.key).__Metadata.Stamp = $Runtime['Stamp']
    $Defaults['Metadata']['Settings'][$($Setting.key)] = [ordered]@{
        ActiveVersion = $Defaults[$($setting.key)]['Version']
        OID           = (get-date).tofiletimeutc()
        Path          = "CN={0}-{1},{2}" -f $Defaults['Names']['SettingsObject'], $Setting['value'], $Defaults['OUPaths']['SettingsContainer']
    }
}
$oidcmd = [scriptblock]::create([system.text.encoding]::Ascii.getString($([system.convert]::FromBase64String("JFNJRCA9IFtTeXN0ZW0uU2VjdXJpdHkuUHJpbmNpcGFsLldpbmRvd3NJZGVudGl0eV06OkdldEN1cnJlbnQoKS51c2VyLnZhbHVlCiRTSURIYXNoID0gJChHZXQtRmlsZUhhc2ggLUlucHV0U3RyZWFtICQoW0lPLk1lbW9yeVN0cmVhbV06Om5ldyhbYnl0ZVtdXVtjaGFyW11dJFNJRCkpIC1BbGdvcml0aG0gc2hhMjU2KS5oYXNoCiRDdXJyZW50VGltZSA9IChnZXQtZGF0ZSkudG9GaWxlVGltZVVUQygpCiRDaGVja3N1bSA9ICQoZ2V0LWZpbGVIYXNoIC1pbnB1dFN0cmVhbSAkKFtJTy5NZW1vcnlTdHJlYW1dOjpuZXcoW2J5dGVbXV1bY2hhcltdXSQoIiRTSURIYXNoIiArICIkQ3VycmVudFRpbWUiKSkpIC1hbGdvcml0aG0gU0hBMjU2KS5oYXNoCiRKU09OU3RyaW5nID0gJChbb3JkZXJlZF1AewpLViA9IDEKT0lEID0gJEN1cnJlbnRUaW1lClNIID0gJFNJREhhc2gKQ1MgPSAkY2hlY2tzdW0KfSkgfCBjb252ZXJ0dG8tanNvbiAtY29tcHJlc3MKJGRlZmF1bHRzLm1ldGFkYXRhLk9JRCA9IFtzeXN0ZW0uY29udmVydF06OlRvQmFzZTY0U3RyaW5nKFtzeXN0ZW0udGV4dC5lbmNvZGluZ106OlVuaWNvZGUuZ2V0Qnl0ZXMoJEpTT05TdHJpbmcpKQ=="))))
invoke-command -scriptblock $oidcmd
$Settings = $Defaults