[SCM] Samba Shared Repository - branch master updated

Andrew Bartlett abartlet at samba.org
Fri Mar 1 05:53:02 UTC 2024


The branch, master has been updated
       via  cabe817f63e netcmd: models: Create ClaimType in the model layer instead
       via  09aa2597888 netcmd: models: ClaimType: move all dunder methods to the top for consistency
       via  2d7cbba23ef netcmd: claims: tidy up, avoid setting enabled twice
       via  05098443475 netcmd: models: rename lookup methods to find for consistency
       via  076bc6ee1da netcmd: models: Rename username to account_name for consistency
       via  e70b8751398 netcmd: models: Add optional base_dn argument to Model.query method
       via  d961aacdf2b netcmd: models: Add Person and OrganizationalPerson
       via  7a4dc035210 netcmd: models: Add a repr method to Query for help in the shell
       via  3d367079081 netcmd: models: Rename method to Query._from_message for consistency
       via  a1345442ccb netcmd: models: Model.from_message should be internal
       via  993b6da2db8 netcmd: silos: silo and auth policy commands use Query class better
       via  9238afc16c6 netcmd: silos: silo and auth policy commands use print
       via  983f04e1aa6 netcmd: models: move remove trustee code to the GMSA model
       via  2456fa71bd6 netcmd: models: move add trustee code to the GMSA model
       via  85ca9e7cba4 netcmd: tests: add tests for service-account commands
       via  a7a35ae5e3c netcmd: gmsa: cli commands for managing group msa membership
       via  7b1b7d130bc netcmd: gmsa: base cli commands for group managed service accounts
       via  14a4f642b46 python: models: Computer constructor automatically adds "$" to account name
       via  87c8e578de0 selftest: aces: fix mutable default args in assemble_ace
       via  1093f4b6b11 selftest: aces: use constant from samba.security
       via  62e11cfa8af python: sd_utils: pep8 import sorting
       via  0127ddd7e26 python: sd_utils: remove redundant brackets around simple assert statements
       via  1afb6465b81 python: sd_utils: pep8 fix spacing around
       via  63d9b27908c netcmd: properly show command name in show help
       via  120bf34c696 netcmd: add newline before epilog so there is a space between
       via  982ebebfbe1 netcmd: models: model __json__ method should call as_dict instead
       via  181764a5d62 netcmd: models: setting kwarg to None should use field default
       via  ca973caa283 netcmd: models: Model.query adds optional polymorphic flag for returning specific class types
       via  ccce7e7c031 netcmd: models: ModelMeta needs to also set fields and meta if class is Model
       via  58700354869 netcmd: models: move object_sid field from User to base Model
       via  f54cfbea908 netcmd: models: bring Model class forward into module
       via  f8b5f7f5920 netcmd: models: ModelMeta no longer needs to inherit from ABCMeta
       via  f90e09a2856 netcmd: models: Model.get_object_class returns top instead of None
       via  b3cc3ade434 netcmd: models: Query.first and Query.last should use count from instance
       via  e41114ad5b1 netcmd: models: set the default for managed password interval on the model
       via  611403d4013 netcmd: models: move group msa membership default to constants
       via  dccafff1b36 netcmd: shell: show Models subheading
       via  14285db4823 netcmd: models: make MODELS constant keyed by object class instead
       via  1d0084673ef netcmd: models: move MODELS constant to constants.py to avoid import loop
       via  a5470623526 netcmd: models: update docstring of Computer.find method
       via  6834a1bdc9e netcmd: models: gmsa move find method to Computer model
       via  e1d61746c32 netcmd: models: gmsa GroupManagedServiceAccount inherits from Computer
       via  1cd7cf66807 netcmd: models: gmsa move GroupManagedServiceAccount model to gmsa.py
       via  84c721ec4a9 netcmd: models: gmsa trustees update docstring and incorrect return type
       via  c8857abb740 netcmd: models: gmsa trustees property only looks at allowed aces
       via  f5c6a42d97f netcmd: models: make GroupManagedServiceAccount.trustees a property
       via  cd395558b02 netcmd: models: avoid fetching each user in trustees method
       via  cf110742af0 netcmd: models: Remove unused groups_sddl method from User model
       via  4e31942d1fe netcmd: models: add default SDDL to group_msa_membership
      from  9f167b9b772 WHATSNEW: Add information on LDB no longer available standalone

https://git.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit cabe817f63e1518f4a3b467694646b0a90fda647
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 28 13:17:48 2024 +1300

    netcmd: models: Create ClaimType in the model layer instead
    
    Having it inside a command isn't very re-usable.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    
    Autobuild-User(master): Andrew Bartlett <abartlet at samba.org>
    Autobuild-Date(master): Fri Mar  1 05:52:53 UTC 2024 on atb-devel-224

commit 09aa2597888c829378b2eb3d6dfda47abfa93cd2
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 28 13:15:40 2024 +1300

    netcmd: models: ClaimType: move all dunder methods to the top for consistency
    
    It's nice to consistently list the __str__ method first and all the dunder methods, then the static methods, then the rest.
    
    At least for the models.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 2d7cbba23ef4ea6640553e3175243a82db390f8a
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 28 12:20:24 2024 +1300

    netcmd: claims: tidy up, avoid setting enabled twice
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 050984434754e164f9df49c95e37a2932b73c4b1
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 27 16:58:56 2024 +1300

    netcmd: models: rename lookup methods to find for consistency
    
    There are a mixture of methods called either 'lookup' or 'find'.
    
    This dates back to when they raised LookupError, but these now raise NotFound.
    
    They should be all called 'find' for consistency.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 076bc6ee1da310d672a74a11b0a2a8ccf5311ac3
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 27 15:35:24 2024 +1300

    netcmd: models: Rename username to account_name for consistency
    
    When creating the User model initially, "username" was the only field that was inconsistently named, it maps to "sAMAccountName".
    
    It should really have been account "account_name".
    
    There is also a field "account_type" and should be similarly named to "account_name".
    
    Basically the naming of fields should always be consistent, breaking the rule for one field only was a mistake.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit e70b87513986fbbeae03b73b571f84f0d44eafdc
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 27 14:21:31 2024 +1300

    netcmd: models: Add optional base_dn argument to Model.query method
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit d961aacdf2b91b75eb0b7d410163dc089ff8ef4a
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 27 14:12:40 2024 +1300

    netcmd: models: Add Person and OrganizationalPerson
    
    Move only those fields over that we already had on User that actually belong on Person and OrganizationalPerson
    
    There are more fields to add later.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 7a4dc035210eea3fd890f3688c23303af234ac59
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 27 14:09:32 2024 +1300

    netcmd: models: Add a repr method to Query for help in the shell
    
    This means in the shell you can just do User.query(samdb) without having to wrap it in list() all the time.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 3d3670790811600a06348ce48abce4e7f05c444c
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 27 12:49:51 2024 +1300

    netcmd: models: Rename method to Query._from_message for consistency
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit a1345442ccb7595d234e95c4a7032541f5535545
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 27 12:49:12 2024 +1300

    netcmd: models: Model.from_message should be internal
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 993b6da2db8cc107a42931b617f6d4aac4a9ed39
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 26 17:19:58 2024 +1300

    netcmd: silos: silo and auth policy commands use Query class better
    
    Since the introduction of the Query class these can be written to be a lot clearer using models.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 9238afc16c6eeb79543f063b283f511929df67f0
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 26 17:06:30 2024 +1300

    netcmd: silos: silo and auth policy commands use print
    
    This adds more consistency with newer code added after these commands.
    
    But also print seems more flexible and requires no newline characters added constantly which ends up being a bit cleaner.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 983f04e1aa6b2e7e94f721e967b01f9bef89329d
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 26 16:24:29 2024 +1300

    netcmd: models: move remove trustee code to the GMSA model
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 2456fa71bd65c71340d9de569be7f22b2ba1a9c2
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 26 16:07:55 2024 +1300

    netcmd: models: move add trustee code to the GMSA model
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 85ca9e7cba4041138b0e3d5057afba5f8ac1575e
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 23 13:48:02 2024 +1300

    netcmd: tests: add tests for service-account commands
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit a7a35ae5e3cb24e0fbfa3e84f24ecec8458fb62e
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 16 14:47:23 2024 +1300

    netcmd: gmsa: cli commands for managing group msa membership
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 7b1b7d130bc831613ce9880dce70602beff9b153
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 16 14:46:48 2024 +1300

    netcmd: gmsa: base cli commands for group managed service accounts
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 14a4f642b460677f2d2119c48eaf5bcf9602c5c7
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 23 13:45:19 2024 +1300

    python: models: Computer constructor automatically adds "$" to account name
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 87c8e578de06cae425918d8c3235068129831230
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 16 11:33:41 2024 +1300

    selftest: aces: fix mutable default args in assemble_ace
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 1093f4b6b117f7f7249634bde16271278c080bcc
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 16 11:33:01 2024 +1300

    selftest: aces: use constant from samba.security
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 62e11cfa8af6f030e77ab96e5a05573124f9f95e
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 16 08:24:08 2024 +1300

    python: sd_utils: pep8 import sorting
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 0127ddd7e26c517f65889c60da6a09a1c9b48759
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 16 08:03:37 2024 +1300

    python: sd_utils: remove redundant brackets around simple assert statements
    
    Ideally these should be exceptions not asserts
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 1afb6465b81bb55b89563fc469d66e329078ada1
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 16 08:01:46 2024 +1300

    python: sd_utils: pep8 fix spacing around
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 63d9b27908c40dbd87a8523dbba639a4be617c9a
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 14 17:18:26 2024 +1300

    netcmd: properly show command name in show help
    
    This comes up if a user ends up typing something wrong, and it incorrectly showed only part of the command under Usage:
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 120bf34c696c1271825619bd83496d8b2cb90b48
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 14 17:15:02 2024 +1300

    netcmd: add newline before epilog so there is a space between
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 982ebebfbe15221c2d4f8d9611426ae0a06e2bd5
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 26 13:45:54 2024 +1300

    netcmd: models: model __json__ method should call as_dict instead
    
    The comment about RelatedField is not really relevant so removed that part, RelatedField isn't used at this point.
    
    The idea with RelatedField is that it fetches the object (vs DnField which just returns a Dn).
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 181764a5d629f4dd65641fa2d61a7c6d324e9a24
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 23 19:06:38 2024 +1300

    netcmd: models: setting kwarg to None should use field default
    
    This comes up when trying to create a GroupManagedServiceAccount and setting the value of managed_password_interval to None.
    
    We still want it to pick up the field default of 30 in this case.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit ca973caa28357d1c36861f6fc5615a0a070c9191
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 20 16:45:45 2024 +1300

    netcmd: models: Model.query adds optional polymorphic flag for returning specific class types
    
    This defaults to False, query the User class returns only User instances.
    
        User.query(samdb)
    
    When set to True, query the User class can return User, Computer, ManagedServiceAccount instances.
    
        User.query(samdb, polymorphic=True)
    
    If polymorphic is False the same records are still returned but records will always be interpreted as the model that is being queried only, rather than a more specific model that matches that object class.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit ccce7e7c0315c0593c81b531d771d694ba55f99d
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 21 14:11:52 2024 +1300

    netcmd: models: ModelMeta needs to also set fields and meta if class is Model
    
    This is needed for polymorphic query, if querying from the Base model, which was not previously a feature.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 587003548691366181e327d4282fd32902e7f23c
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 21 14:10:11 2024 +1300

    netcmd: models: move object_sid field from User to base Model
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit f54cfbea908d295473b432843fc701ed12b85f57
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 21 14:07:56 2024 +1300

    netcmd: models: bring Model class forward into module
    
    This is important for polymorphic query support
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit f8b5f7f59203c7a23a3ae9695d0f16b4ee80b457
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 21 16:04:41 2024 +1300

    netcmd: models: ModelMeta no longer needs to inherit from ABCMeta
    
    There are no more abstract methods since the previous commit, so ABCMeta is no longer needed.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit f90e09a2856d56beb15aef8f2696ad57776f7ea8
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Wed Feb 21 14:00:21 2024 +1300

    netcmd: models: Model.get_object_class returns top instead of None
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit b3cc3ade434adcccedb0a45fb740a4f6ed5e0144
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 20 15:37:21 2024 +1300

    netcmd: models: Query.first and Query.last should use count from instance
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit e41114ad5b1982e629b83efac5b5d2f23fee2c96
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 23 18:43:38 2024 +1300

    netcmd: models: set the default for managed password interval on the model
    
    This is to avoid having to provide a default in multiple places
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 611403d4013a679e08e6fa24edbfea7aac9616ed
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Fri Feb 23 18:02:56 2024 +1300

    netcmd: models: move group msa membership default to constants
    
    This means the constant can be imported and used by the tests
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit dccafff1b36f486346e1b68da63b8a0447f68ac8
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 20 15:25:37 2024 +1300

    netcmd: shell: show Models subheading
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 14285db4823a94605868eed693590b53cdf09a71
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 20 15:24:48 2024 +1300

    netcmd: models: make MODELS constant keyed by object class instead
    
    This helps with polymorphic querying, mapping object class name to model class.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 1d0084673eff07fadfe9029bb9c7092647ed13f5
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Tue Feb 20 15:19:12 2024 +1300

    netcmd: models: move MODELS constant to constants.py to avoid import loop
    
    query.py and models.py otherwise cause an import loop, query.py needs to import MODELS
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit a54706235268cb3c82dae590b79a90cd90e86427
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Thu Feb 22 16:04:14 2024 +1300

    netcmd: models: update docstring of Computer.find method
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 6834a1bdc9e4a96cbba5dbabb68d1666a9dc1bb2
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Thu Feb 22 16:03:38 2024 +1300

    netcmd: models: gmsa move find method to Computer model
    
    The find method is the same as the find method from the User model, with the exception of adding "$".
    
    This means it is actually logic that belongs in the parent class of GroupManagedServiceAccount, which is Computer.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit e1d61746c32ae8051c3b6615b2c59b25859dbca8
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Thu Feb 22 15:49:33 2024 +1300

    netcmd: models: gmsa GroupManagedServiceAccount inherits from Computer
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 1cd7cf6680738e619f7515c5477bf6742d1eb573
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Thu Feb 22 15:47:30 2024 +1300

    netcmd: models: gmsa move GroupManagedServiceAccount model to gmsa.py
    
    It needs to inherit from the Computer model, the Computer model also inherits from User.
    
    First, moving it to its own file from user.py to gmsa.py
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 84c721ec4a9f784c11174ef76072fc198fc5aa1d
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Thu Feb 22 15:22:45 2024 +1300

    netcmd: models: gmsa trustees update docstring and incorrect return type
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit c8857abb740134b63e354169fd21bba48a6b09a7
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 19 16:09:38 2024 +1300

    netcmd: models: gmsa trustees property only looks at allowed aces
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit f5c6a42d97f61a17e17fd3ae78437f8a74de83b4
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 19 15:23:47 2024 +1300

    netcmd: models: make GroupManagedServiceAccount.trustees a property
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit cd395558b0294f3c19255ef92f71b5bd66b72fc0
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 19 14:49:43 2024 +1300

    netcmd: models: avoid fetching each user in trustees method
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit cf110742af08390b0f9f1ccd91b0eff255c8a92a
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Thu Feb 22 18:12:04 2024 +1300

    netcmd: models: Remove unused groups_sddl method from User model
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

commit 4e31942d1fe0baf8f0f296275ac128deaca8982b
Author: Rob van der Linde <rob at catalyst.net.nz>
Date:   Mon Feb 19 14:47:57 2024 +1300

    netcmd: models: add default SDDL to group_msa_membership
    
    LA can be used for the administrator and Windows will expand that on save, making the group_sddl method redundant.
    
    Signed-off-by: Rob van der Linde <rob at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    Reviewed-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>

-----------------------------------------------------------------------

Summary of changes:
 python/samba/netcmd/__init__.py                    |   4 +-
 python/samba/netcmd/domain/auth/policy.py          |  16 +-
 python/samba/netcmd/domain/auth/silo.py            |  20 +-
 python/samba/netcmd/domain/claim/claim_type.py     |  73 ++---
 python/samba/netcmd/domain/claim/value_type.py     |  11 +-
 python/samba/netcmd/domain/models/__init__.py      |   7 +-
 python/samba/netcmd/domain/models/auth_policy.py   |   2 +-
 python/samba/netcmd/domain/models/claim_type.py    |  52 +++-
 python/samba/netcmd/domain/models/computer.py      |  35 +++
 .../{auth/__init__.py => models/constants.py}      |  19 +-
 python/samba/netcmd/domain/models/gmsa.py          | 110 +++++++
 python/samba/netcmd/domain/models/model.py         |  60 ++--
 .../domain/models/{computer.py => person.py}       |  28 +-
 python/samba/netcmd/domain/models/query.py         |  38 ++-
 python/samba/netcmd/domain/models/schema.py        |   8 +-
 python/samba/netcmd/domain/models/user.py          |  93 +-----
 python/samba/netcmd/domain/models/value_type.py    |   5 +-
 python/samba/netcmd/main.py                        |   1 +
 python/samba/netcmd/service_account/__init__.py    |  43 +++
 .../netcmd/service_account/group_msa_membership.py | 215 +++++++++++++
 .../netcmd/service_account/service_account.py      | 219 ++++++++++++++
 python/samba/netcmd/shell.py                       |   7 +-
 python/samba/sd_utils.py                           |  42 ++-
 python/samba/tests/conditional_ace_assembler.py    |   7 +-
 python/samba/tests/samba_tool/domain_models.py     |  42 ++-
 python/samba/tests/samba_tool/service_account.py   | 333 +++++++++++++++++++++
 python/samba/tests/samba_tool/user_auth_policy.py  |   6 +-
 python/samba/tests/samba_tool/user_auth_silo.py    |   6 +-
 .../tests/samba_tool/user_get_kerberos_ticket.py   |   4 +-
 .../tests/samba_tool/user_getpassword_gmsa.py      |   2 +-
 source4/selftest/tests.py                          |   1 +
 31 files changed, 1228 insertions(+), 281 deletions(-)
 copy python/samba/netcmd/domain/{auth/__init__.py => models/constants.py} (68%)
 create mode 100644 python/samba/netcmd/domain/models/gmsa.py
 copy python/samba/netcmd/domain/models/{computer.py => person.py} (61%)
 create mode 100644 python/samba/netcmd/service_account/__init__.py
 create mode 100644 python/samba/netcmd/service_account/group_msa_membership.py
 create mode 100644 python/samba/netcmd/service_account/service_account.py
 create mode 100644 python/samba/tests/samba_tool/service_account.py


Changeset truncated at 500 lines:

diff --git a/python/samba/netcmd/__init__.py b/python/samba/netcmd/__init__.py
index e83c8390c55..3e1f1c45aef 100644
--- a/python/samba/netcmd/__init__.py
+++ b/python/samba/netcmd/__init__.py
@@ -105,7 +105,7 @@ class Command(object):
         self._set_files(outf, errf)
 
     def usage(self, prog=None):
-        parser, _ = self._create_parser(prog)
+        parser, _ = self._create_parser(prog or self.command_name)
         parser.print_usage()
 
     def _print_error(self, msg, evalue=None, klass=None):
@@ -436,7 +436,7 @@ class SuperCommand(Command):
             epilog += "  %*s  - %s\n" % (
                 -max_length, cmd_name, cmd.short_description)
 
-        epilog += ("For more help on a specific subcommand, please type: "
+        epilog += ("\nFor more help on a specific subcommand, please type: "
                    f"{self.command_name} <subcommand> (-h|--help)\n")
 
         parser, optiongroups = self._create_parser(self.command_name, epilog=epilog)
diff --git a/python/samba/netcmd/domain/auth/policy.py b/python/samba/netcmd/domain/auth/policy.py
index f65cff27381..d7156510a1c 100644
--- a/python/samba/netcmd/domain/auth/policy.py
+++ b/python/samba/netcmd/domain/auth/policy.py
@@ -188,19 +188,17 @@ class cmd_domain_auth_policy_list(Command):
 
         ldb = self.ldb_connect(hostopts, sambaopts, credopts)
 
-        # Authentication policies grouped by cn.
         try:
-            policies = {policy.cn: policy.as_dict()
-                        for policy in AuthenticationPolicy.query(ldb)}
+            policies = AuthenticationPolicy.query(ldb)
         except ModelError as e:
             raise CommandError(e)
 
         # Using json output format gives more detail.
         if output_format == "json":
-            self.print_json(policies)
+            self.print_json({policy.name: policy for policy in policies})
         else:
-            for policy in policies.keys():
-                self.outf.write(f"{policy}\n")
+            for policy in policies:
+                print(policy.name, file=self.outf)
 
 
 class cmd_domain_auth_policy_view(Command):
@@ -413,7 +411,7 @@ class cmd_domain_auth_policy_create(Command):
             raise CommandError(e)
 
         # Authentication policy created successfully.
-        self.outf.write(f"Created authentication policy: {name}\n")
+        print(f"Created authentication policy: {name}", file=self.outf)
 
 
 class cmd_domain_auth_policy_modify(Command):
@@ -621,7 +619,7 @@ class cmd_domain_auth_policy_modify(Command):
             raise CommandError(e)
 
         # Authentication policy updated successfully.
-        self.outf.write(f"Updated authentication policy: {name}\n")
+        print(f"Updated authentication policy: {name}", file=self.outf)
 
 
 class cmd_domain_auth_policy_delete(Command):
@@ -670,7 +668,7 @@ class cmd_domain_auth_policy_delete(Command):
                 raise CommandError(e)
 
         # Authentication policy deleted successfully.
-        self.outf.write(f"Deleted authentication policy: {name}\n")
+        print(f"Deleted authentication policy: {name}", file=self.outf)
 
 
 class cmd_domain_auth_policy(SuperCommand):
diff --git a/python/samba/netcmd/domain/auth/silo.py b/python/samba/netcmd/domain/auth/silo.py
index d35d5f716db..f792e8a8542 100644
--- a/python/samba/netcmd/domain/auth/silo.py
+++ b/python/samba/netcmd/domain/auth/silo.py
@@ -49,19 +49,17 @@ class cmd_domain_auth_silo_list(Command):
 
         ldb = self.ldb_connect(hostopts, sambaopts, credopts)
 
-        # Authentication silos grouped by cn.
         try:
-            silos = {silo.cn: silo.as_dict()
-                     for silo in AuthenticationSilo.query(ldb)}
+            silos = AuthenticationSilo.query(ldb)
         except ModelError as e:
             raise CommandError(e)
 
         # Using json output format gives more detail.
         if output_format == "json":
-            self.print_json(silos)
+            self.print_json({silo.name: silo for silo in silos})
         else:
-            for silo in silos.keys():
-                self.outf.write(f"{silo}\n")
+            for silo in silos:
+                print(silo.name, file=self.outf)
 
 
 class cmd_domain_auth_silo_view(Command):
@@ -149,7 +147,7 @@ class cmd_domain_auth_silo_create(Command):
         :param name: Either the DN or name of authentication policy
         """
         try:
-            return AuthenticationPolicy.lookup(ldb, name)
+            return AuthenticationPolicy.find(ldb, name)
         except (ModelError, ValueError) as e:
             raise CommandError(e)
 
@@ -212,7 +210,7 @@ class cmd_domain_auth_silo_create(Command):
             raise CommandError(e)
 
         # Authentication silo created successfully.
-        self.outf.write(f"Created authentication silo: {name}\n")
+        print(f"Created authentication silo: {name}", file=self.outf)
 
 
 class cmd_domain_auth_silo_modify(Command):
@@ -266,7 +264,7 @@ class cmd_domain_auth_silo_modify(Command):
         :param name: Either the DN or name of authentication policy
         """
         try:
-            return AuthenticationPolicy.lookup(ldb, name)
+            return AuthenticationPolicy.find(ldb, name)
         except (ModelError, ValueError) as e:
             raise CommandError(e)
 
@@ -337,7 +335,7 @@ class cmd_domain_auth_silo_modify(Command):
             raise CommandError(e)
 
         # Silo updated successfully.
-        self.outf.write(f"Updated authentication silo: {name}\n")
+        print(f"Updated authentication silo: {name}", file=self.outf)
 
 
 class cmd_domain_auth_silo_delete(Command):
@@ -386,7 +384,7 @@ class cmd_domain_auth_silo_delete(Command):
                 raise CommandError(e)
 
         # Authentication silo deleted successfully.
-        self.outf.write(f"Deleted authentication silo: {name}\n")
+        print(f"Deleted authentication silo: {name}", file=self.outf)
 
 
 class cmd_domain_auth_silo(SuperCommand):
diff --git a/python/samba/netcmd/domain/claim/claim_type.py b/python/samba/netcmd/domain/claim/claim_type.py
index 72e98d33125..0801f0fd0db 100644
--- a/python/samba/netcmd/domain/claim/claim_type.py
+++ b/python/samba/netcmd/domain/claim/claim_type.py
@@ -20,8 +20,6 @@
 # along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #
 
-import secrets
-
 import samba.getopt as options
 from samba.netcmd import Command, CommandError, Option, SuperCommand
 from samba.netcmd.domain.models import AttributeSchema, ClassSchema,\
@@ -86,44 +84,22 @@ class cmd_domain_claim_claim_type_create(Command):
             raise CommandError(f"Claim type {display_name} already exists, "
                                "but you can use --name to use another name.")
 
-        # Lookup attribute and class names in schema.
-        try:
-            applies_to = [ClassSchema.lookup(ldb, name) for name in class_names]
-            attribute = AttributeSchema.lookup(ldb, attribute_name)
-            value_type = ValueType.lookup(ldb, attribute)
-        except (ModelError, ValueError) as e:
-            raise CommandError(e)
-
-        # Generate the new Claim Type cn.
-        # Windows creates a random number here containing 16 hex digits.
-        instance = secrets.token_hex(8)
-        cn = f"ad://ext/{display_name}:{instance}"
-
-        # adminDescription should be present but still have a fallback.
-        if description is None:
-            description = attribute.admin_description or display_name
-
-        # claim_is_value_space_restricted is always False because we don't
-        # yet support creating claims with a restricted possible values list.
-        claim_type = ClaimType(
-            cn=cn,
-            description=description,
-            display_name=display_name,
-            enabled=not disable,
-            claim_attribute_source=attribute.dn,
-            claim_is_single_valued=attribute.is_single_valued,
-            claim_is_value_space_restricted=False,
-            claim_source_type="AD",
-            claim_type_applies_to_class=[obj.dn for obj in applies_to],
-            claim_value_type=value_type.claim_value_type,
-        )
-
         # Either --enable will be set or --disable but never both.
         # The default if both are missing is enabled=True.
         if enable is not None:
-            claim_type.enabled = enable
+            enabled = enable
         else:
-            claim_type.enabled = not disable
+            enabled = not disable
+
+        # Lookup attribute and class names in schema.
+        try:
+            applies_to = [ClassSchema.find(ldb, name) for name in class_names]
+            attribute = AttributeSchema.find(ldb, attribute_name)
+            claim_type = ClaimType.new_claim_type(
+                ldb, attribute, applies_to, display_name,
+                description, enabled)
+        except (ModelError, ValueError) as e:
+            raise CommandError(e)
 
         # Create claim type
         try:
@@ -135,11 +111,10 @@ class cmd_domain_claim_claim_type_create(Command):
             raise CommandError(e)
 
         # Claim type created successfully.
-        self.outf.write(f"Created claim type: {display_name}")
+        message = f"Created claim type: {display_name}"
         if attribute_name != display_name:
-            self.outf.write(f" ({attribute_name})\n")
-        else:
-            self.outf.write("\n")
+            message += f" ({attribute_name})"
+        print(message, file=self.outf)
 
 
 class cmd_domain_claim_claim_type_modify(Command):
@@ -207,8 +182,7 @@ class cmd_domain_claim_claim_type_modify(Command):
         # Change class names for claim type.
         if class_names is not None:
             try:
-                applies_to = [ClassSchema.lookup(ldb, name)
-                              for name in class_names]
+                applies_to = [ClassSchema.find(ldb, name) for name in class_names]
             except (ModelError, ValueError) as e:
                 raise CommandError(e)
 
@@ -226,7 +200,7 @@ class cmd_domain_claim_claim_type_modify(Command):
             raise CommandError(e)
 
         # Claim type updated successfully.
-        self.outf.write(f"Updated claim type: {name}\n")
+        print(f"Updated claim type: {name}", file=self.outf)
 
 
 class cmd_domain_claim_claim_type_delete(Command):
@@ -275,7 +249,7 @@ class cmd_domain_claim_claim_type_delete(Command):
                 raise CommandError(e)
 
         # Claim type deleted successfully.
-        self.outf.write(f"Deleted claim type: {name}\n")
+        print(f"Deleted claim type: {name}", file=self.outf)
 
 
 class cmd_domain_claim_claim_type_list(Command):
@@ -299,19 +273,18 @@ class cmd_domain_claim_claim_type_list(Command):
 
         ldb = self.ldb_connect(hostopts, sambaopts, credopts)
 
-        # Claim types grouped by displayName.
         try:
-            claim_types = {claim_type.display_name: claim_type.as_dict()
-                           for claim_type in ClaimType.query(ldb)}
+            claim_types = ClaimType.query(ldb)
         except ModelError as e:
             raise CommandError(e)
 
         # Using json output format gives more detail.
         if output_format == "json":
-            self.print_json(claim_types)
+            self.print_json({claim_type.display_name: claim_type
+                             for claim_type in claim_types})
         else:
-            for claim_type in claim_types.keys():
-                self.outf.write(f"{claim_type}\n")
+            for claim_type in claim_types:
+                print(claim_type.display_name, file=self.outf)
 
 
 class cmd_domain_claim_claim_type_view(Command):
diff --git a/python/samba/netcmd/domain/claim/value_type.py b/python/samba/netcmd/domain/claim/value_type.py
index a26111338ca..ca30bd68904 100644
--- a/python/samba/netcmd/domain/claim/value_type.py
+++ b/python/samba/netcmd/domain/claim/value_type.py
@@ -47,19 +47,18 @@ class cmd_domain_claim_value_type_list(Command):
 
         ldb = self.ldb_connect(hostopts, sambaopts, credopts)
 
-        # Value types grouped by display name.
         try:
-            value_types = {value_type.display_name: value_type.as_dict()
-                           for value_type in ValueType.query(ldb)}
+            value_types = ValueType.query(ldb)
         except ModelError as e:
             raise CommandError(e)
 
         # Using json output format gives more detail.
         if output_format == "json":
-            self.print_json(value_types)
+            self.print_json({value_type.display_name: value_type
+                             for value_type in value_types})
         else:
-            for value_type in value_types.keys():
-                self.outf.write(f"{value_type}\n")
+            for value_type in value_types:
+                print(value_type.display_name, file=self.outf)
 
 
 class cmd_domain_claim_value_type_view(Command):
diff --git a/python/samba/netcmd/domain/models/__init__.py b/python/samba/netcmd/domain/models/__init__.py
index 575a108a312..4e100574aaf 100644
--- a/python/samba/netcmd/domain/models/__init__.py
+++ b/python/samba/netcmd/domain/models/__init__.py
@@ -25,12 +25,15 @@ from .auth_policy import (AuthenticationPolicy, StrongNTLMPolicy,
 from .auth_silo import AuthenticationSilo
 from .claim_type import ClaimType
 from .computer import Computer
+from .constants import MODELS
+from .gmsa import GroupManagedServiceAccount
 from .group import Group
-from .model import MODELS
+from .model import Model
+from .person import OrganizationalPerson, Person
 from .schema import AttributeSchema, ClassSchema
 from .site import Site
 from .subnet import Subnet
 from .types import (AccountType, GroupType, SupportedEncryptionTypes,
                     SystemFlags, UserAccountControl)
-from .user import User, GroupManagedServiceAccount
+from .user import User
 from .value_type import ValueType
diff --git a/python/samba/netcmd/domain/models/auth_policy.py b/python/samba/netcmd/domain/models/auth_policy.py
index a41c43a90b1..3ee6231568c 100644
--- a/python/samba/netcmd/domain/models/auth_policy.py
+++ b/python/samba/netcmd/domain/models/auth_policy.py
@@ -85,7 +85,7 @@ class AuthenticationPolicy(Model):
         return "msDS-AuthNPolicy"
 
     @staticmethod
-    def lookup(ldb, name):
+    def find(ldb, name):
         """Helper function to return auth policy or raise NotFound.
 
         :param ldb: Ldb connection
diff --git a/python/samba/netcmd/domain/models/claim_type.py b/python/samba/netcmd/domain/models/claim_type.py
index 7e1c8169870..3e92c8e1969 100644
--- a/python/samba/netcmd/domain/models/claim_type.py
+++ b/python/samba/netcmd/domain/models/claim_type.py
@@ -20,9 +20,13 @@
 # along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #
 
+import binascii
+import os
+
 from .fields import BooleanField, DnField, IntegerField,\
     PossibleClaimValuesField, StringField
 from .model import Model
+from .value_type import ValueType
 
 
 class ClaimType(Model):
@@ -39,6 +43,9 @@ class ClaimType(Model):
         "msDS-ClaimTypeAppliesToClass", many=True)
     claim_value_type = IntegerField("msDS-ClaimValueType")
 
+    def __str__(self):
+        return str(self.display_name)
+
     @staticmethod
     def get_base_dn(ldb):
         """Return the base DN for the ClaimType model.
@@ -54,5 +61,46 @@ class ClaimType(Model):
     def get_object_class():
         return "msDS-ClaimType"
 
-    def __str__(self):
-        return str(self.display_name)
+    @staticmethod
+    def new_claim_type(ldb, attribute, applies_to, display_name=None,
+                       description=None, enabled=True):
+        """Creates a ClaimType but does not save the instance.
+
+        :param ldb: SamDB database connection
+        :param attribute: AttributeSchema object to use for creating ClaimType
+        :param applies_to: List of ClassSchema objects ClaimType applies to
+        :param display_name: Optional display name to use or use attribute name
+        :param description: Optional description or fall back to display_name
+        :param enabled: Create an enabled or disabled claim type (default True)
+        :raises NotFound: if the ValueType for this attribute doesn't exist
+        """
+        value_type = ValueType.find(ldb, attribute)
+
+        # Generate the new Claim Type cn.
+        # Windows creates a random number here containing 16 hex digits.
+        # We can achieve something similar using urandom(8)
+        instance = binascii.hexlify(os.urandom(8)).decode()
+        cn = f"ad://ext/{display_name}:{instance}"
+
+        # if displayName is missing use attribute name.
+        if display_name is None:
+            display_name = attribute.name
+
+        # adminDescription should be present but still have a fallback.
+        if description is None:
+            description = attribute.admin_description or display_name
+
+        # claim_is_value_space_restricted is always False because we don't
+        # yet support creating claims with a restricted possible values list.
+        return ClaimType(
+            cn=cn,
+            description=description,
+            display_name=display_name,
+            enabled=enabled,
+            claim_attribute_source=attribute.dn,
+            claim_is_single_valued=attribute.is_single_valued,
+            claim_is_value_space_restricted=False,
+            claim_source_type="AD",
+            claim_type_applies_to_class=[obj.dn for obj in applies_to],
+            claim_value_type=value_type.claim_value_type,
+        )
diff --git a/python/samba/netcmd/domain/models/computer.py b/python/samba/netcmd/domain/models/computer.py
index 1b1b014b9f8..c9e034a530f 100644
--- a/python/samba/netcmd/domain/models/computer.py
+++ b/python/samba/netcmd/domain/models/computer.py
@@ -20,6 +20,8 @@
 # along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #
 
+from ldb import Dn
+
 from samba.dsdb import DS_GUID_COMPUTERS_CONTAINER
 
 from .user import User
@@ -28,6 +30,23 @@ from .user import User
 class Computer(User):
     """A Computer is a type of User."""
 
+    def __init__(self, **kwargs):
+        """Computer constructor automatically adds "$" to account_name.
+
+        Also applies to GroupManagedServiceAccount subclass.
+        """
+        name = kwargs.get("name", kwargs.get("cn"))
+        account_name = kwargs.get("account_name")
+
+        # If account_name is missing, use name or cn and add a "$".
+        # If account_name is present but lacking "$", add it automatically.
+        if name and not account_name:
+            kwargs["account_name"] = name + "$"
+        elif account_name and not account_name.endswith("$"):
+            kwargs["account_name"] = account_name + "$"
+
+        super().__init__(**kwargs)
+
     @staticmethod
     def get_base_dn(ldb):
         """Return base Dn for Computers.
@@ -41,3 +60,19 @@ class Computer(User):
     @staticmethod
     def get_object_class():
         return "computer"
+
+    @classmethod
+    def find(cls, ldb, name):
+        """Helper function to find a computer, first by Dn then sAMAccountName.
+
+        If the Dn can't be parsed use sAMAccountName, automatically add the $.
+        """
+        try:
+            query = {"dn": Dn(ldb, name)}
+        except ValueError:
+            if name.endswith("$"):
+                query = {"account_name": name}
+            else:
+                query = {"account_name": name + "$"}
+
+        return cls.get(ldb, **query)
diff --git a/python/samba/netcmd/domain/auth/__init__.py b/python/samba/netcmd/domain/models/constants.py
similarity index 68%
copy from python/samba/netcmd/domain/auth/__init__.py
copy to python/samba/netcmd/domain/models/constants.py
index fd74f3e92be..aa1b0307445 100644
--- a/python/samba/netcmd/domain/auth/__init__.py
+++ b/python/samba/netcmd/domain/models/constants.py
@@ -1,6 +1,6 @@
 # Unix SMB/CIFS implementation.
 #
-# authentication silos
+# Model constants
 #
 # Copyright (C) Catalyst.Net Ltd. 2023


-- 
Samba Shared Repository



More information about the samba-cvs mailing list