Funktionierender Prototyp des Serious Games zur Vermittlung von Wissen zu Software-Engineering-Arbeitsmodellen.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

search.py 4.1KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. import pythoncom
  2. import pywintypes
  3. import win32security
  4. from win32com.adsi import adsi, adsicon
  5. from win32com.adsi.adsicon import *
  6. options = None # set to optparse options object
  7. ADsTypeNameMap = {}
  8. def getADsTypeName(type_val):
  9. # convert integer type to the 'typename' as known in the headerfiles.
  10. if not ADsTypeNameMap:
  11. for n, v in adsicon.__dict__.items():
  12. if n.startswith("ADSTYPE_"):
  13. ADsTypeNameMap[v] = n
  14. return ADsTypeNameMap.get(type_val, hex(type_val))
  15. def _guid_from_buffer(b):
  16. return pywintypes.IID(b, True)
  17. def _sid_from_buffer(b):
  18. return str(pywintypes.SID(b))
  19. _null_converter = lambda x: x
  20. converters = {
  21. "objectGUID": _guid_from_buffer,
  22. "objectSid": _sid_from_buffer,
  23. "instanceType": getADsTypeName,
  24. }
  25. def log(level, msg, *args):
  26. if options.verbose >= level:
  27. print("log:", msg % args)
  28. def getGC():
  29. cont = adsi.ADsOpenObject(
  30. "GC:", options.user, options.password, 0, adsi.IID_IADsContainer
  31. )
  32. enum = adsi.ADsBuildEnumerator(cont)
  33. # Only 1 child of the global catalog.
  34. for e in enum:
  35. gc = e.QueryInterface(adsi.IID_IDirectorySearch)
  36. return gc
  37. return None
  38. def print_attribute(col_data):
  39. prop_name, prop_type, values = col_data
  40. if values is not None:
  41. log(2, "property '%s' has type '%s'", prop_name, getADsTypeName(prop_type))
  42. value = [converters.get(prop_name, _null_converter)(v[0]) for v in values]
  43. if len(value) == 1:
  44. value = value[0]
  45. print(" %s=%r" % (prop_name, value))
  46. else:
  47. print(" %s is None" % (prop_name,))
  48. def search():
  49. gc = getGC()
  50. if gc is None:
  51. log(0, "Can't find the global catalog")
  52. return
  53. prefs = [(ADS_SEARCHPREF_SEARCH_SCOPE, (ADS_SCOPE_SUBTREE,))]
  54. hr, statuses = gc.SetSearchPreference(prefs)
  55. log(3, "SetSearchPreference returned %d/%r", hr, statuses)
  56. if options.attributes:
  57. attributes = options.attributes.split(",")
  58. else:
  59. attributes = None
  60. h = gc.ExecuteSearch(options.filter, attributes)
  61. hr = gc.GetNextRow(h)
  62. while hr != S_ADS_NOMORE_ROWS:
  63. print("-- new row --")
  64. if attributes is None:
  65. # Loop over all columns returned
  66. while 1:
  67. col_name = gc.GetNextColumnName(h)
  68. if col_name is None:
  69. break
  70. data = gc.GetColumn(h, col_name)
  71. print_attribute(data)
  72. else:
  73. # loop over attributes specified.
  74. for a in attributes:
  75. try:
  76. data = gc.GetColumn(h, a)
  77. print_attribute(data)
  78. except adsi.error as details:
  79. if details[0] != E_ADS_COLUMN_NOT_SET:
  80. raise
  81. print_attribute((a, None, None))
  82. hr = gc.GetNextRow(h)
  83. gc.CloseSearchHandle(h)
  84. def main():
  85. global options
  86. from optparse import OptionParser
  87. parser = OptionParser()
  88. parser.add_option(
  89. "-f", "--file", dest="filename", help="write report to FILE", metavar="FILE"
  90. )
  91. parser.add_option(
  92. "-v",
  93. "--verbose",
  94. action="count",
  95. default=1,
  96. help="increase verbosity of output",
  97. )
  98. parser.add_option(
  99. "-q", "--quiet", action="store_true", help="suppress output messages"
  100. )
  101. parser.add_option("-U", "--user", help="specify the username used to connect")
  102. parser.add_option("-P", "--password", help="specify the password used to connect")
  103. parser.add_option(
  104. "",
  105. "--filter",
  106. default="(&(objectCategory=person)(objectClass=User))",
  107. help="specify the search filter",
  108. )
  109. parser.add_option(
  110. "", "--attributes", help="comma sep'd list of attribute names to print"
  111. )
  112. options, args = parser.parse_args()
  113. if options.quiet:
  114. if options.verbose != 1:
  115. parser.error("Can not use '--verbose' and '--quiet'")
  116. options.verbose = 0
  117. if args:
  118. parser.error("You need not specify args")
  119. search()
  120. if __name__ == "__main__":
  121. main()