Setting permissions on NTFS Fileshare with PowerShell - windows

My script in a nutshell should create 5 Folders, 1 root level folder, 3 2nd level folders, and 1 3rd level folder.
Permissions are granted at the 2nd level, either ReadWrite or ReadOnly. No user should be able to create anything within the second level or delete a second level.
I seem to be having issues with Set-Acl and permissions. I'm wondering if there's a better way to script this out that I don't need elevated privileges for. Our DA's can run the script fine, and I can do the folder and security group creation manually but its tedious and prone to errors. Any insight into what I'm doing wrong or how I could do it better would be appreciated.
Import-Module ActiveDirectory
$path = "\\earth\data\group\"
$newFolderName = Read-Host -Prompt "Enter Name of New Folder"
$newFolderFull = $path + $newFolderName
Write-Output "New Folder will be: $newFolderFull"
$confirm = Read-Host "Confirm? Y/N"
if (!(($confirm) -ne "y")) {
Write-Output "Create AD Groups"
$groupNamePGroup = "P_$newFolderName"
$groupNameAdminRW = "EG-$newFolderName-Admin-RW"
$groupNameAdminRF = "EG-$newFolderName-Admin-RF"
$groupNameEveryoneRW = "EG-$newFolderName-Everyone-RW"
$groupNameEveryoneRF = "EG-$newFolderName-Everyone-RF"
$groupNameScannedDocsRW = "EG-$newFolderName-ScannedDocs-RW"
New-ADGroup $groupNamePGroup -samAccountName $groupNamePGroup -GroupScope DomainLocal -path "OU=SecurityGroups,OU=Metro,DC=metrogr,DC=org"
New-ADGroup $groupNameAdminRW -samAccountName $groupNameAdminRW -GroupScope DomainLocal -path "OU=SecurityGroups,OU=Metro,DC=metrogr,DC=org"
New-ADGroup $groupNameAdminRF -samAccountName $groupNameAdminRF -GroupScope DomainLocal -path "OU=SecurityGroups,OU=Metro,DC=metrogr,DC=org"
New-ADGroup $groupNameEveryoneRW -samAccountName $groupNameEveryoneRW -GroupScope DomainLocal -path "OU=SecurityGroups,OU=Metro,DC=metrogr,DC=org"
New-ADGroup $groupNameEveryoneRF -samAccountName $groupNameEveryoneRF -GroupScope DomainLocal -path "OU=SecurityGroups,OU=Metro,DC=metrogr,DC=org"
New-ADGroup $groupNameScannedDocsRW -samAccountName $groupNameScannedDocsRW -GroupScope DomainLocal -path "OU=SecurityGroups,OU=Metro,DC=metrogr,DC=org"
Write-Output "Add Folder.."
New-Item $newFolderFull -ItemType Directory
New-Item $newFolderFull\Admin -ItemType Directory
New-Item $newFolderFull\Everyone -ItemType Directory
New-Item $newFolderFull\ScannedDocs -ItemType Directory
New-Item $newFolderFull\Everyone\ScannedDocs -ItemType Directory
Write-Output "Remove Inheritance.."
icacls $newFolderFull /inheritance:d
icacls $newFolderFull\Admin /inheritance:d
icacls $newFolderFull\Everyone /inheritance:d
icacls $newFolderFull\Everyone\ScannedDocs /inheritance:d
#icacls $newFolderFull\ScannedDocs /inheritance:d
# Rights
$readOnly = [Security.AccessControl.FileSystemRights]"ReadAndExecute"
$readWrite = [Security.AccessControl.FileSystemRights]"Write, DeleteSubdirectoriesAndFiles,ReadAndExecute"
# Inheritance
$inheritanceFlag = [Security.AccessControl.InheritanceFlags]"ContainerInherit, ObjectInherit"
# Propagation
$propagationFlag = [Security.AccessControl.PropagationFlags]::None
# User
$PUserRF = New-Object System.Security.Principal.NTAccount($groupNamePGroup)
$AdminUserRW = New-Object System.Security.Principal.NTAccount($groupnameAdminRW)
$AdminUserRF = New-Object System.Security.Principal.NTAccount($groupnameAdminRF)
$EveryoneUserRW = New-Object System.Security.Principal.NTAccount($groupnameEveryoneRW)
$EveryoneUserRF = New-Object System.Security.Principal.NTAccount($groupnameEveryoneRF)
$ScannedDocsUserRW = New-Object System.Security.Principal.NTAccount($groupnameScannedDocsRW)
# Type
$type = [Security.AccessControl.AccessControlType]::Allow
#Add Group membership
Add-ADGroupMember -Identity $groupNamePGroup -Members $groupNameAdminRW,$groupNameAdminRF,$groupNameEveryoneRW,$groupNameEveryoneRF,$groupNameScannedDocsRW
Add-ADGroupMember -Identity $groupNameEveryoneRW -Members NDPSSCAN
Add-ADGroupMember -Identity $groupNameScannedDocsRW -Members NDPSSCAN
# ACL
$accessControlEntryDefault = New-Object System.Security.AccessControl.FileSystemAccessRule #("Domain Users", $readOnly, $inheritanceFlag, $propagationFlag, $type)
$accessControlRootEntryRF = New-Object System.Security.AccessControl.FileSystemAccessRule #($PUserRF, $readOnly, $inheritanceFlag, $propagationFlag, $type)
$accessControlAdminEntryRW = New-Object System.Security.AccessControl.FileSystemAccessRule #($AdminUserRW, $readWrite, $inheritanceFlag, $propagationFlag, $type)
$accessControlAdminEntryRF = New-Object System.Security.AccessControl.FileSystemAccessRule #($AdminUserRF, $readOnly, $inheritanceFlag, $propagationFlag, $type)
$accessControlEveryoneEntryRW = New-Object System.Security.AccessControl.FileSystemAccessRule #($EveryoneUserRW, $readWrite, $inheritanceFlag, $propagationFlag, $type)
$accessControlEveryoneEntryRF = New-Object System.Security.AccessControl.FileSystemAccessRule #($EveryoneUserRF, $readOnly, $inheritanceFlag, $propagationFlag, $type)
$accessControlScannedDocsEntryRW = New-Object System.Security.AccessControl.FileSystemAccessRule #($ScannedDocsUserRW, $readWrite, $inheritanceFlag, $propagationFlag, $type)
$objACL = Get-Acl $newFolderFull
$objACL.RemoveAccessRuleAll($accessControlEntryDefault)
$objACL.AddAccessRule($accessControlRootEntryRF)
Set-Acl $newFolderFull $objACL
$objACL = Get-Acl $newFolderFull\Admin
$objACL.RemoveAccessRuleAll($accessControlEntryDefault)
$objACL.AddAccessRule($accessControlAdminEntryRW)
$objACL.AddAccessRule($accessControlAdminEntryRF)
Set-Acl $newFolderFull\Admin $objACL
$objACL = Get-Acl $newFolderFull\Everyone
$objACL.RemoveAccessRuleAll($accessControlEntryDefault)
$objACL.AddAccessRule($accessControlEveryoneEntryRW)
$objACL.AddAccessRule($accessControlEveryoneEntryRF)
Set-Acl $newFolderFull\Everyone $objACL
$objACL = Get-Acl $newFolderFull\ScannedDocs
$objACL.RemoveAccessRuleAll($accessControlEntryDefault)
$objACL.AddAccessRule($accessControlScannedDocsEntryRW)
Set-Acl $newFolderFull\ScannedDocs $objACL
}

SetAccessControl($objACL) worked for me.
Set-ACL didn't work as my account didn't have elevated permissions.

Related

how to "replace all child object permission entries with inheritable permission entries from this object" using PowerShell for ACL folder access

I am trying to enable "replace all child object permission entries with inheritable permission entries from this object" method using PowerShell, below is my Script
$ProfileDir = 'C:\Users\'
$Profiles = Get-ChildItem $ProfileDir \ Select-Object -ExpandProperty Name
ForEach ($X in $Profiles)
{
$Profile = $ProfileDir + $X
Write-Host "Starting $Profile"
$Acl = Get-Acl $Profile
$Acl.SetAccessRuleProtection($false, $true)
(Get-Item $Profile).SetAccessControl($Acl)
$Permissions = (Get-Acl $Profile).Access | Where-Object
{
(-not $_.isInherited) -and $_.IdentityReference -like "domain\*"
}
ForEach ($Y in $Permissions)
{
$Acl.AddAccessRule($Y)
}
(Get-Item $Profile).SetAccessRule($Acl)
(Get-Acl $Profile).Access
}
Below is the script I have created and it worked as expected.
Thank you for your suggestions and help. To replace all child objects, I have used Get-ChildItem with -recurse and it worked.
$objName = (Get-CimInstance -ClassName Win32_ComputerSystem).UserName.Split("\")[1]
$objDir = "C:\Users\$objName\"
$objUser = (Get-CimInstance -ClassName Win32_ComputerSystem).UserName
$objAccount = New-Object System.Security.Principal.NTAccount($objUser)
$objRule = $objUser,"FullControl","ContainerInherit,ObjectInherit","None","Allow"
$objFileSec = New-Object System.Security.AccessControl.FileSecurity
$objAccessRule = New-Object System.Security.AccessControl.FileSystemAccessRule($objRule)
$objFileSec.SetOwner($objAccount)
$objAclSec = Get-Acl $objDir
$objAclSec.SetAccessRuleProtection($true,$true)
$objAclSec.PurgeAccessRules($objAccount)
$objAclSec.SetAccessRule($objAccessRule)
Get-ChildItem -Path $objDir | Set-Acl -AclObject $objAclSec
$objAclSec.Access | Format-Table
Pause

Home folders created in powershell won't work: Access Denied

I'm having some trouble creating home folders with powershell, I create the folder
New-Item -Path "C:\Homes\" -name $username -ItemType Directory
Then I copy the ACL and disable the inheritance and add the new permissions
$Rights = [System.Security.AccessControl.FileSystemRights]"FullControl"
$Inheritance = [System.Security.AccessControl.InheritanceFlags]::"ContainerInherit", "ObjectInherit"
$Propagation = [System.Security.AccessControl.PropagationFlags]::None
$AC =[System.Security.AccessControl.AccessControlType]::Allow
$NewACL = New-Object System.Security.AccessControl.FileSystemAccessRule ($username, $Rights, $Inheritance, $Propagation, $AC)
$ACL = Get-Acl -Path "C:\Homes\$username"
$ACL.SetAccessRuleProtection($True, $False)
$ACL.SetAccessRule($NewACL)
$NewACL = New-Object System.Security.AccessControl.FileSystemAccessRule ("SYSTEM", $Rights, $Inheritance, $Propagation, $AC)
$ACL.SetAccessRule($NewACL)
$NewACL = New-Object System.Security.AccessControl.FileSystemAccessRule ("Administrators", $Rights, $Inheritance, $Propagation, $AC)
$ACL.SetAccessRule($NewACL)
Set-Acl -Path "C:\Homes\$username" -AclObject $ACL
Finally I mount the folders as H: and set it as home dir
Set-ADUser -Identity $username -Replace #{HomeDirectory=$homeDir}
Set-ADUser -Identity $username -Replace #{HomeDrive=$homeDrive}
When I login to a user and try to add a file/folder I recieve permission denied.
The Root Folder (C:\Homes) is shared and has configured permissions
#Louis J. Are you sure permissions have been set properly? I mean you should try to get ACL of the created folder using command like :
(Get-Acl H:...).Access
Then check user's rights over this directory.
By the way, do you execute your script with elevated rights?

How can I use powershell 4.0 set-acl to allow the user to have the same security settings in newly created subdirectories?

When I set user access via set-acl I can loop through all existing subfolders. How do I set it to include future subfolders created under the main folder?
Also... Once the access is set it only displays in 'Advanced' settings for the folders. The first security screen shows the user but shows no access rights.
This is in Windows Server 2012 R2.
$SubFolder = "name"
$UserName = "domain\" + $SubFolder
$Folder = "R:\User Files\" + $SubFolder + "\"
$Acl = Get-Acl $Folder
$Ar = New-Object system.security.accesscontrol.filesystemaccessrule($UserName,"FullControl","Allow")
$Acl.SetAccessRule($Ar)
#Get-Variable
Set-Acl -Path $Folder -AclObject $Acl
$Folder = Get-childItem $Folder
foreach ($TempFolder in $Folder)
{
$Folder = $TempFolder.FullName
$Acl = Get-Acl $Folder
$Ar = New-Object system.security.accesscontrol.filesystemaccessrule($UserName,"FullControl","Allow")
$Acl.SetAccessRule($Ar)
#Get-Variable
Set-Acl -Path $Folder -AclObject $Acl
}
You will need to set your Inheritance and Propagation flags in order for it to affect files and folders within your target. Here's my typical template that I use when I'm working on setting up new ACLs for users:
$Rights = [System.Security.AccessControl.FileSystemRights]"FullControl"
$InheritanceFlag = [System.Security.AccessControl.InheritanceFlags]"ObjectInherit,ContainerInherit"
$PropagationFlag = [System.Security.AccessControl.PropagationFlags]::None
$objType =[System.Security.AccessControl.AccessControlType]::Allow
#Define the user's account using their samAccountName
$objUser = New-Object System.Security.Principal.NTAccount("samAccountName")
$objACE = New-Object System.Security.AccessControl.FileSystemAccessRule($objUser, $Rights, $InheritanceFlag, $PropagationFlag, $objType)
$objACL = Get-ACL "C:\Temp"
$objACL.AddAccessRule($objACE)
Set-ACL "C:\Temp" $objACL
The settings here will make future things inherit the settings that you define for the target folder.

How to set permission on folder using powershell

i am trying to write a script which adds"CreatorOwner" permission to profile$ folders on all file servers;
i.e , add "CreatorOwner" permissions to "\FileServer\Profile$"
can anybody tell me whats the command and syntax for it?
Please do ask if any questions.
One way of doing this is using WMI and UNC paths.
$AccessRule = New-Object system.security.accesscontrol.filesystemaccessrule("CREATOR OWNER","FullControl","ContainerInherit, ObjectInherit","InheritOnly","Allow")
$profileshare = Get-WmiObject Win32_Share -ComputerName fileserver -Filter "name = 'profile$'"
$driveletter, $path = $profileshare.path
$path = $path.TrimStart("\")
$ACL = Get-Acl "\\fileserver\$driveletter`$\$path"
$ACL.SetAccessRule($AccessRule)
Set-Acl \\fileserver\$driveletter`$\$path -AclObject $ACL
Now if you have a list of server names you could do the following:
$servers = #("fileserver1","fileserver2","fileserver3")
$AccessRule = New-Object system.security.accesscontrol.filesystemaccessrule("CREATOR OWNER","FullControl","ContainerInherit, ObjectInherit","InheritOnly","Allow")
$servers | % {
$profileshare = Get-WmiObject Win32_Share -ComputerName $_ -Filter "name = 'profile$'"
$driveletter, $path = $profileshare.path
$path = $path.TrimStart("\")
$ACL = Get-Acl "\\$_\$driveletter`$\$path"
$ACL.SetAccessRule($AccessRule)
Set-Acl \\$_\$driveletter`$\$path -AclObject $ACL
}
This will do it:
#Change the CSV file path
$Permissions = Import-Csv C:\Test.CSV -delimiter '|'
ForEach ($line in $Permissions)
$inherit = [system.security.accesscontrol.InheritanceFlags]"ContainerInherit,
ObjectInherit"
$propagation = [system.security.accesscontrol.PropagationFlags]"None"
$acl = Get-Acl $line.Path
$acl.SetAccessRuleProtection($True, $False)
$accessrule = New-Object system.security.AccessControl.FileSystemAccessRule("domain users", "Read", $inherit, $propagation, "Allow")
#Adding the Rule
$acl.AddAccessRule($accessrule)
#Setting the Change
Set-Acl $line.Path $acl
What the CSV file looks Like
\SRV01\Folder1\Folder2 etc.

Removing all ACL on folder with powershell

I'm pretty new to powershell scripting (nearly 1 month since I started learning powershell.)
I'm currently working on a script with powershell 2.0 to clean folder NTFS ACL. I want to delete every acl except the administrator one.
My problem is that I can't find a way to delete every acl that are not administrator, without knowing them.
So I came here to sought for powershell pro.
This code remove acl :
$acl = Get-Acl \\remote_server\share_folder\HAL.9000
$acl.Access | %{$acl.RemoveAccessRule($_)}
This code add administrator acl :
#BUILTIN administrator
$acl = Get-Acl \\remote_server\share_folder\HAL.9000
$permission = "BUILTIN\Administrators","FullControl", "ContainerInherit,ObjectInherit","None","Allow"
$accessRule = New-Object System.Security.AccessControl.FileSystemAccessRule $permission
$acl.SetAccessRule($accessRule)
Set-Acl \\remote_server\share_folder\HAL.9000 $acl
#Domain controller administrator
$acl = Get-Acl \\remote_server\share_folder\HAL.9000
$permission = "DOMAINCONTROLLER\Administrators","FullControl", "ContainerInherit,ObjectInherit","None","Allow"
$accessRule = New-Object System.Security.AccessControl.FileSystemAccessRule $permission
$acl.SetAccessRule($accessRule)
Set-Acl \\remote_server\share_folder\HAL.9000 $acl
Hope this will help someone :)
For convenience I've copy/pasted all this stuff together in a function. If it can be of use to anyone, here it is:
Function Remove-ACL {
[CmdletBinding(SupportsShouldProcess=$True)]
Param(
[parameter(Mandatory=$true,ValueFromPipeline=$true,Position=0)]
[ValidateNotNullOrEmpty()]
[ValidateScript({Test-Path $_ -PathType Container})]
[String[]]$Folder,
[Switch]$Recurse
)
Process {
foreach ($f in $Folder) {
if ($Recurse) {$Folders = $(Get-ChildItem $f -Recurse -Directory).FullName} else {$Folders = $f}
if ($Folders -ne $null) {
$Folders | ForEach-Object {
# Remove inheritance
$acl = Get-Acl $_
$acl.SetAccessRuleProtection($true,$true)
Set-Acl $_ $acl
# Remove ACL
$acl = Get-Acl $_
$acl.Access | %{$acl.RemoveAccessRule($_)} | Out-Null
# Add local admin
$permission = "BUILTIN\Administrators","FullControl", "ContainerInherit,ObjectInherit","None","Allow"
$rule = New-Object System.Security.AccessControl.FileSystemAccessRule $permission
$acl.SetAccessRule($rule)
Set-Acl $_ $acl
Write-Verbose "Remove-HCacl: Inheritance disabled and permissions removed from $_"
}
}
else {
Write-Verbose "Remove-HCacl: No subfolders found for $f"
}
}
}
}
Usage:
# For only one folder:
Remove-ACL 'C:\Folder' -Verbose
# For all subfolders:
Remove-ACL 'C:\Folder' -Recurse -Verbose
# Pipe stuff
'C:\Folder 1', 'C:\Folder 2' | Remove-ACL -Verbose
This code remove acl : $acl = Get-Acl
\remote_server\share_folder\HAL.9000 $acl.Access |
%{$acl.RemoveAccessRule($_)}
it does not work until you do
Set-Acl \\remote_server\share_folder\HAL.9000 $acl
Why not create a new list. For example:
$identity = New-Object System.Security.Principal.NTAccount('NT AUTHORITY\SYSTEM')
$acl = New-Object System.Security.AccessControl.DirectorySecurity
$acl.SetOwner($identity)
$acl.SetGroup($identity)
$rule = New-Object System.Security.AccessControl.FileSystemAccessRule('NT AUTHORITY\SYSTEM', ’FullControl’, ’ContainerInherit, ObjectInherit’, ’None’,’Allow’)
$acl.AddAccessRule($rule)
$rule = New-Object System.Security.AccessControl.FileSystemAccessRule('BUILTIN\Administrators', ’FullControl’, ’ContainerInherit, ObjectInherit’, ’None’, ’Allow’)
$acl.AddAccessRule($rule)
Set-Acl -LiteralPath "C:\MyFolder" -AclObject $acl
Get-Acl -LiteralPath "C:\MyFolder" | Format-List

Resources