diff --git a/src/nsls2api/api/models/person_model.py b/src/nsls2api/api/models/person_model.py index 9b45078e..5d8ebce8 100644 --- a/src/nsls2api/api/models/person_model.py +++ b/src/nsls2api/api/models/person_model.py @@ -117,19 +117,22 @@ class AccountInfo(pydantic.BaseModel): badPwdCount: int = 0 pwdLastSet: Optional[str] = None lastLogon: Optional[str] = None - userAccountControlFlags: List[str] = [] + userAccountControlFlags: List[str] = pydantic.Field(default_factory=list) userPrincipalName: Optional[str] = None logonCount: int = 0 sAMAccountName: Optional[str] = None sAMAccountType: Optional[str] = None - lastLogoff: Optional[int] = None - uSNCreated: int = 0 + lastLogoff: Optional[str] = None + uSNCreated: Optional[int] = None + uSNChanged: Optional[int] = None class DirectoryInfo(pydantic.BaseModel): objectGUID: Optional[str] = None objectSid: Optional[str] = None primaryGroupID: Optional[str] = None distinguishedName: Optional[str] = None + whenCreated: Optional[str] = None + whenChanged: Optional[str] = None class AttributesInfo(pydantic.BaseModel): sn: Optional[str] = None @@ -140,7 +143,7 @@ class AttributesInfo(pydantic.BaseModel): codePage: Optional[str] = None countryCode: Optional[str] = None instanceType: Optional[str] = None - objectClass: List[str] = [] + objectClass: List[str] = pydantic.Field(default_factory=list) class LDAPUserResponse(pydantic.BaseModel): """Complete LDAP user data from direct LDAP query""" @@ -150,5 +153,5 @@ class LDAPUserResponse(pydantic.BaseModel): identity: Optional[IdentityInfo] = None account: Optional[AccountInfo] = None directory: Optional[DirectoryInfo] = None - groups: List[str] = [] + groups: List[str] = pydantic.Field(default_factory=list) attributes: Optional[AttributesInfo] = None \ No newline at end of file diff --git a/src/nsls2api/api/v1/user_api.py b/src/nsls2api/api/v1/user_api.py index 90ad9bf6..a9bc8e2a 100644 --- a/src/nsls2api/api/v1/user_api.py +++ b/src/nsls2api/api/v1/user_api.py @@ -83,8 +83,8 @@ async def get_myself(request: Request, upn: str= None): ldap_info = await asyncio.to_thread(get_user_info, upn, settings.ldap_server, - settings.base_dn, - settings.bind_user, + settings.ldap_base_dn, + settings.ldap_bind_user, settings.ldap_bind_password ) if not ldap_info: diff --git a/src/nsls2api/infrastructure/config.py b/src/nsls2api/infrastructure/config.py index 7189682e..d6d0eb55 100644 --- a/src/nsls2api/infrastructure/config.py +++ b/src/nsls2api/infrastructure/config.py @@ -73,8 +73,8 @@ class Settings(BaseSettings): #Whoami LDAP settings ldap_server: str = Field(default="ldaps://ldapproxy.nsls2.bnl.gov", alias="LDAP_SERVER") - base_dn: str = Field(default="dc=bnl,dc=gov", alias="BASE_DN") - bind_user: str = Field(default="", alias="BIND_USER") + ldap_base_dn: str = Field(default="dc=bnl,dc=gov", alias="LDAP_BASE_DN") + ldap_bind_user: str = Field(default="", alias="LDAP_BIND_USER") ldap_bind_password: str = Field(default="", alias="LDAP_BIND_PASSWORD") diff --git a/src/nsls2api/services/ldap_service.py b/src/nsls2api/services/ldap_service.py index f496c270..fcd93981 100644 --- a/src/nsls2api/services/ldap_service.py +++ b/src/nsls2api/services/ldap_service.py @@ -12,13 +12,13 @@ def to_hex(val): return binascii.hexlify(val).decode() return None -def get_user_info(upn, ldap_server, base_dn, bind_user, bind_password): +def get_user_info(upn, ldap_server, ldap_base_dn, ldap_bind_user, bind_password): conn = None try: server = Server(ldap_server) - conn = Connection(server, user=bind_user, password=bind_password, auto_bind=True) + conn = Connection(server, user=ldap_bind_user, password=bind_password, auto_bind=True) search_filter = f"(&(objectclass=person)(userPrincipalName={upn}))" - conn.search(base_dn, search_filter, attributes=['sAMAccountName']) + conn.search(ldap_base_dn, search_filter, attributes=['sAMAccountName']) if not conn.entries: logger.warning("No entries found for the given UPN.") @@ -30,7 +30,7 @@ def get_user_info(upn, ldap_server, base_dn, bind_user, bind_password): return None search_filter = f"(&(objectclass=posixaccount)(sAMAccountName={username}))" - conn.search(base_dn, search_filter, attributes=['*']) + conn.search(ldap_base_dn, search_filter, attributes=['*']) if not conn.entries: logger.warning("no posix entries found for the given username.") @@ -120,14 +120,17 @@ def clean_groups(groups_val): "logonCount": int(user_info.get("logonCount") or 0), "sAMAccountName": user_info.get("sAMAccountName"), "sAMAccountType": user_info.get("sAMAccountType"), - "lastLogoff": user_info.get("lastLogoff"), + "lastLogoff": filetime_to_str(user_info.get("lastLogoff")), "uSNCreated": int(user_info.get("uSNCreated") or 0), + "uSNChanged": int(user_info.get("uSNChanged") or 0), }, "directory": { "objectGUID": to_hex(user_info.get("objectGUID")), "objectSid": to_hex(user_info.get("objectSid")), "primaryGroupID": user_info.get("primaryGroupID"), "distinguishedName": user_info.get("distinguishedName"), + "whenCreated": generalized_time_to_str(user_info.get("whenCreated")), + "whenChanged": generalized_time_to_str(user_info.get("whenChanged")), }, "groups": clean_groups(user_info.get("memberOf")), "attributes": {