puppetlabs/puppet · error · Puppet::Error
OS X version #{self.class.get_os_version} does not allow cha
Error message
OS X version #{self.class.get_os_version} does not allow changing #{setter_method} using puppet What it means
Raised by Puppet's macOS DirectoryService user provider when the manifest tries to change `home` or `uid` on an existing user. The provider defines setters for home/uid/gid/comment/shell, but for home and uid on a user that already has a value it refuses outright — Apple's DirectoryService semantics make these changes unsafe/unsupported from Puppet.
Source
Thrown at lib/puppet/provider/user/directoryservice.rb:455
# that property and it needs changed (true here since all of these values
# have a default that is set in the create method). We don't want to merge
# in additional values if an incorrect value is set, we want to CHANGE it.
# When using the -change argument in dscl, the old value needs to be passed
# first (followed by the new value). Because of this, we get the current
# value from the @property_hash variable and then use the value passed as
# the new value. Because we're prefetching instances of the provider, it's
# possible that the value determined at the start of the run may be stale
# (i.e. someone changed the value by hand during a Puppet run) - if that's
# the case we rescue the error from dscl and alert the user.
#
# In the event that the user doesn't HAVE a value for the attribute, the
# provider should use the -create option with dscl to add the attribute value
# for the user record
%w[home uid gid comment shell].each do |setter_method|
define_method("#{setter_method}=") do |value|
if @property_hash[setter_method.intern]
if %w[home uid].include?(setter_method)
raise Puppet::Error, "OS X version #{self.class.get_os_version} does not allow changing #{setter_method} using puppet"
end
begin
dscl '.', '-change', "/Users/#{resource.name}", self.class.ns_to_ds_attribute_map[setter_method.intern], @property_hash[setter_method.intern], value
rescue Puppet::ExecutionFailure => e
raise Puppet::Error, "Cannot set the #{setter_method} value of '#{value}' for user " \
"#{@resource.name} due to the following error: #{e.inspect}", e.backtrace
end
else
begin
dscl '.', '-create', "/Users/#{resource.name}", self.class.ns_to_ds_attribute_map[setter_method.intern], value
rescue Puppet::ExecutionFailure => e
raise Puppet::Error, "Cannot set the #{setter_method} value of '#{value}' for user " \
"#{@resource.name} due to the following error: #{e.inspect}", e.backtrace
end
end
end
endView on GitHub (pinned to e227c27540)
Solutions
- Do not manage home/uid changes with Puppet on macOS — set them only at creation time and keep them stable afterwards.
- For a one-time migration, perform it out-of-band with `dscl . -change /Users/<name> UniqueID <old> <new>` plus the matching chown, then update the manifest to the new values.
- If the user record was created outside Puppet with wrong values, delete/recreate the record so Puppet's `create` path sets home/uid once.
- Scope the properties by OS: put home/uid inside a conditional so only non-Darwin platforms manage changes.
Example fix
# before
user { 'alice': ensure => present, home => '/Users/alice-new', uid => 2001 }
# after - create-time only on Darwin, migrate out-of-band
darwin_home_change = false # handle via dscl + chown migration script
user { 'alice':
ensure => present,
uid => darwin_home_change ? { true => 2001, default => undef },
} Defensive patterns
Strategy: validation
Validate before calling
# manifest-side guard: only set home/uid at creation on Darwin existing = `dscl . -read /Users/alice UniqueID 2>/dev/null` # node-side: avoid changing these values at all # dscl . -change requires a manual migration
Type guard
def darwin_safe_properties?(current_uid, desired_uid, current_home, desired_home)
(current_uid.nil? || current_uid == desired_uid) &&
(current_home.nil? || current_home == desired_home)
end Prevention
- Treat home/uid as immutable on macOS; plan migrations as out-of-band dscl+chown scripts.
- Pre-create users via Puppet (not imaging tools) so creation-time values stick.
- Scope home/uid properties to non-Darwin platforms in shared profiles.
When it happens
Trigger: A `user` resource with a changed `home` or `uid` that already exists in the local directory (the @property_hash has a current value, so the '-change' branch runs and hits the guard). Also triggers if the provider's prefetch saw a value even though you expected creation.
Common situations: Renumbering UIDs during a migration; repointing home directories after storage changes; manifests reused from Linux where home/uid changes are routine; users pre-created by imaging/MDM so Puppet treats them as modifications rather than creations.
Related errors
- Invalid #{field} given for user #{user_name}
- OS X 10.7 requires a Salted SHA512 hash password of 136 char
- OS X versions > 10.7 require a Salted SHA512 PBKDF2 password
- puppet.plans/invalid-name
- Invalid value %{value}: %{property} must be an Integer!
AI-assisted analysis of puppetlabs/puppet@e227c27540 (2026-08-21).
Data as JSON: /api/errors/e467ee39296d5aa1.
Report an issue: GitHub.