Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

xScheduledTask: Cannot create task to run as NetworkService #130

Closed
jpuskar opened this issue Dec 30, 2017 · 18 comments
Closed

xScheduledTask: Cannot create task to run as NetworkService #130

jpuskar opened this issue Dec 30, 2017 · 18 comments
Labels
bug The issue is a bug.

Comments

@jpuskar
Copy link

jpuskar commented Dec 30, 2017

This logic would need changed such that if logontype is 'serviceaccount' and the password is null or empty, don't set the password.

        if ($PSBoundParameters.ContainsKey('ExecuteAsCredential'))
        {
            $username = $ExecuteAsCredential.UserName
            $registerArguments.Add('User', $username)

            # If the LogonType is not specified then set it to password
            if ([System.String]::IsNullOrEmpty($LogonType))
            {
                $LogonType = 'Password'
            }

            if ($LogonType -notin ('Interactive', 'S4U'))
            {
                # Only set the password if the LogonType is not interactive or S4U
                $registerArguments.Add('Password', $ExecuteAsCredential.GetNetworkCredential().Password)
            }
        }
        else
        {
            $username = 'NT AUTHORITY\SYSTEM'
            $registerArguments.Add('User', $username)
            $LogonType = 'ServiceAccount'
        }

Example resource which should work, but fails with a 'password is null' error due to the logic above.:

$network_service_cred = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList ("NT AUTHORITY\NETWORK SERVICE", (new-object System.Security.SecureString))

xScheduledTask 'sql_backups_daily'
    {
        TaskName            = 'my_task'
        TaskPath            = '\CustomTasks'
        ActionExecutable    = 'C:\windows\system32\WindowsPowerShell\v1.0\powershell.exe'
        ActionArguments     = "-File `"C:\scripts\my_script.ps1`""
        ScheduleType        = 'Daily'
        DaysInterval        = 1
        RepetitionDuration  = 'Indefinitely'
        ExecuteAsCredential = $network_service_cred
        LogonType           = 'ServiceAccount'
        Enable              = $true
    }
@PlagueHO PlagueHO added bug The issue is a bug. help wanted The issue is up for grabs for anyone in the community. labels Jan 12, 2018
@PlagueHO
Copy link
Member

Great info @jpuskar - thanks for raising this! Should be enough for me to get onto fixing ASAP! Awesome stuff!

@ketjap
Copy link

ketjap commented Feb 12, 2018

The same would apply if you use the BUILTIN\Administrators group.

@PlagueHO
Copy link
Member

I've been a bit (a lot) snowed under lately, but hopefully things will slow down by this weekend and I'll get some DSC work done. Again - sorry this has all been taking so long.

@PlagueHO PlagueHO added in progress The issue is being actively worked on by someone. and removed help wanted The issue is up for grabs for anyone in the community. labels Mar 6, 2018
@PlagueHO
Copy link
Member

PlagueHO commented Mar 6, 2018

Unfortunately I can't resolve this issue without a change to DSC itself. There is a user voice issue open to enable blank passwords to be passed to a DSC Resource: https://windowsserver.uservoice.com/forums/301869-powershell/suggestions/13447689-dsc-should-allow-credentials-with-blank-passwords

But there is no ETA on when this will be fixed.

@PlagueHO PlagueHO added on hold The issue or pull request has been put on hold by a maintainer. discussion The issue is a discussion. and removed in progress The issue is being actively worked on by someone. on hold The issue or pull request has been put on hold by a maintainer. labels Mar 6, 2018
@PlagueHO
Copy link
Member

PlagueHO commented Mar 6, 2018

There are two other possibilities of solving this problem (neither are ideal), but until this limitation in DSC is addressed then they should be considered:

  1. Split the ExecuteAsCredential into two parameters: ExecuteAsUsername and ExecuteAsPassword and deprecate the ExecuteAsCredential parameter. This would be a breaking change to the resource, so would be nice to avoid.
  2. Make the resource ignore the password in a credential IF the Username is BUILTIN* or NT AUTHORITY\NETWORK SERVICE. This would require clear documentation/examples showing this to make it clear how this should be used.

e.g.

$network_service_cred = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList ("NT AUTHORITY\NETWORK SERVICE", (ConvertTo-SecureString -String 'WhoCares' -AsPlainText -Force))

xScheduledTask 'sql_backups_daily'
    {
        TaskName            = 'my_task'
        TaskPath            = '\CustomTasks'
        ActionExecutable    = 'C:\windows\system32\WindowsPowerShell\v1.0\powershell.exe'
        ActionArguments     = "-File `"C:\scripts\my_script.ps1`""
        ScheduleType        = 'Daily'
        DaysInterval        = 1
        RepetitionDuration  = 'Indefinitely'
        ExecuteAsCredential = $network_service_cred
        LogonType           = 'ServiceAccount'
        Enable              = $true
    }

@jpuskar , @ketjap, @johlju - do you have any opinion on this one?

@johlju
Copy link
Member

johlju commented Mar 6, 2018

I would go for option 2 because it is not a breaking change (?) and it is easy to reverse without another breaking change when the limitation is resolved, which would not be the case with option 1.
Option 1 would be a breaking change and go against what you normally would expect to use to set credential (a credential object), and as said before, it would be a breaking change when reversing the change.

So option 2 seems to me as the best option.

@briantist
Copy link

Ignoring the password might also allow it to work for (g)MSAs, which is currently doesn't. But in that case you can't use BUILTIN to determine that. LogonType also, confusingly, needs to be password for an MSA.

@johlju
Copy link
Member

johlju commented Jun 28, 2018

I think (g)MSA is ending with $, so if a username match regex '\$$' then we could assume it's a (g)MSA. Unless we could use computer accounts, they end with '$' as well.

@briantist
Copy link

@johlju true, though gMSAs are subclassed from computers anyway, so it would make sense to use the same rules for a computer or a gMSA, since their mechanism should basically be the same.

It's an odd use case to have a scheduled task on a machine run as a computer other than itself (which would be achieved with SYSTEM or NETWORK SERVICE) but still, in theory it should work the same way I think?

@johlju
Copy link
Member

johlju commented Jun 29, 2018

Never tried running a schedule task as the computer account, but in theory I think you could assign permission using the computer account those allowing a job to access resources 🤔 But that must be an edge case.

@johlju johlju added help wanted The issue is up for grabs for anyone in the community. and removed discussion The issue is a discussion. labels Jun 29, 2018
@PlagueHO
Copy link
Member

PlagueHO commented Jul 2, 2018

Might be worth putting together a table of all possible username/password and how they should be treated? I'll see if I can put something together this week.

@MatthewGM
Copy link

xWebAdministration's xWebAppPool also has this issue with gMSAs. It would be good (IMO) if both modules handled special accounts in the same manner.
xWebAppPool has a field for identityType to handle ApplicationPoolIdentity, LocalService, LocalSystem, NetworkService, and SpecificUser

See dsccommunity/WebAdministrationDsc#80 for the gMSA issue

@djwork
Copy link
Contributor

djwork commented Aug 21, 2018

Maybe the solution should bring ScheduledTask resource into alignment with the Service resource which has a separate property BuiltInAccount?

Service
[String] BuiltInAccount (Write): Indicates the sign-in account to use for the service. { LocalService | LocalSystem | NetworkService }.

@djwork
Copy link
Contributor

djwork commented Oct 1, 2018

See my pull request
#187

@djwork
Copy link
Contributor

djwork commented Oct 3, 2018

New pull request:
#192

@djwork
Copy link
Contributor

djwork commented Oct 4, 2018

Verbose Change Log for pull request, putting it here so there is a record of the design decisions when implementing fix.

Added BuiltInAccount Property to allow running task as one of the build in service accounts
Used for running the Scheduled Task as one of the built in service accounts.
Valid Values: 'SYSTEM', 'LOCAL SERVICE', 'NETWORK SERVICE'.
If set ExecuteAsCredential will be ignored and LogonType will be overwritten to 'ServiceAccount'.
Added Example 16-CreateScheduledTasksAsBuiltinServiceAccount.ps1
The name BuiltInAccount and it's pattern of use is based on the property of the same name in the Service DSCR.
The reason for defining a new property and not using the alternative eg:

`ExecuteAsCredential = ([pscredential]::new(
  'NT AUTHORITY\NETWORK SERVICE',
  (ConvertTo-SecureString -String 'TEST' -AsPlainText -Force)))`

was the above requires either; the configuration to be compiled with PSDscAllowPlainTextPassword = $true (not secure) or the resultant MOF file to be encrytpted (additional complexity that may not otherwise be required for a specific environment)

PlagueHO added a commit that referenced this issue Apr 5, 2019
ScheduledTask: Added BuiltInUser (Issue #130) & Fixed IdleWaitTimeout…
@djwork
Copy link
Contributor

djwork commented Apr 8, 2019

@PlagueHO Can we closes this now the fix is merged into dev?

@PlagueHO
Copy link
Member

PlagueHO commented Apr 8, 2019

Yep. Good point. Thank you for your hard work!!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug The issue is a bug.
Projects
None yet
Development

No branches or pull requests

8 participants