@etcsec-com/etc-collector 1.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (617) hide show
  1. package/.env.example +60 -0
  2. package/.env.test.example +33 -0
  3. package/.github/workflows/ci.yml +83 -0
  4. package/.github/workflows/release.yml +246 -0
  5. package/.prettierrc.json +10 -0
  6. package/CHANGELOG.md +15 -0
  7. package/Dockerfile +57 -0
  8. package/LICENSE +190 -0
  9. package/README.md +194 -0
  10. package/dist/api/controllers/audit.controller.d.ts +21 -0
  11. package/dist/api/controllers/audit.controller.d.ts.map +1 -0
  12. package/dist/api/controllers/audit.controller.js +179 -0
  13. package/dist/api/controllers/audit.controller.js.map +1 -0
  14. package/dist/api/controllers/auth.controller.d.ts +16 -0
  15. package/dist/api/controllers/auth.controller.d.ts.map +1 -0
  16. package/dist/api/controllers/auth.controller.js +146 -0
  17. package/dist/api/controllers/auth.controller.js.map +1 -0
  18. package/dist/api/controllers/export.controller.d.ts +27 -0
  19. package/dist/api/controllers/export.controller.d.ts.map +1 -0
  20. package/dist/api/controllers/export.controller.js +80 -0
  21. package/dist/api/controllers/export.controller.js.map +1 -0
  22. package/dist/api/controllers/health.controller.d.ts +5 -0
  23. package/dist/api/controllers/health.controller.d.ts.map +1 -0
  24. package/dist/api/controllers/health.controller.js +16 -0
  25. package/dist/api/controllers/health.controller.js.map +1 -0
  26. package/dist/api/controllers/jobs.controller.d.ts +13 -0
  27. package/dist/api/controllers/jobs.controller.d.ts.map +1 -0
  28. package/dist/api/controllers/jobs.controller.js +125 -0
  29. package/dist/api/controllers/jobs.controller.js.map +1 -0
  30. package/dist/api/controllers/providers.controller.d.ts +15 -0
  31. package/dist/api/controllers/providers.controller.d.ts.map +1 -0
  32. package/dist/api/controllers/providers.controller.js +112 -0
  33. package/dist/api/controllers/providers.controller.js.map +1 -0
  34. package/dist/api/dto/AuditRequest.dto.d.ts +6 -0
  35. package/dist/api/dto/AuditRequest.dto.d.ts.map +1 -0
  36. package/dist/api/dto/AuditRequest.dto.js +3 -0
  37. package/dist/api/dto/AuditRequest.dto.js.map +1 -0
  38. package/dist/api/dto/AuditResponse.dto.d.ts +17 -0
  39. package/dist/api/dto/AuditResponse.dto.d.ts.map +1 -0
  40. package/dist/api/dto/AuditResponse.dto.js +3 -0
  41. package/dist/api/dto/AuditResponse.dto.js.map +1 -0
  42. package/dist/api/dto/TokenRequest.dto.d.ts +6 -0
  43. package/dist/api/dto/TokenRequest.dto.d.ts.map +1 -0
  44. package/dist/api/dto/TokenRequest.dto.js +3 -0
  45. package/dist/api/dto/TokenRequest.dto.js.map +1 -0
  46. package/dist/api/dto/TokenResponse.dto.d.ts +12 -0
  47. package/dist/api/dto/TokenResponse.dto.d.ts.map +1 -0
  48. package/dist/api/dto/TokenResponse.dto.js +3 -0
  49. package/dist/api/dto/TokenResponse.dto.js.map +1 -0
  50. package/dist/api/middlewares/authenticate.d.ts +12 -0
  51. package/dist/api/middlewares/authenticate.d.ts.map +1 -0
  52. package/dist/api/middlewares/authenticate.js +141 -0
  53. package/dist/api/middlewares/authenticate.js.map +1 -0
  54. package/dist/api/middlewares/errorHandler.d.ts +3 -0
  55. package/dist/api/middlewares/errorHandler.d.ts.map +1 -0
  56. package/dist/api/middlewares/errorHandler.js +30 -0
  57. package/dist/api/middlewares/errorHandler.js.map +1 -0
  58. package/dist/api/middlewares/rateLimit.d.ts +3 -0
  59. package/dist/api/middlewares/rateLimit.d.ts.map +1 -0
  60. package/dist/api/middlewares/rateLimit.js +34 -0
  61. package/dist/api/middlewares/rateLimit.js.map +1 -0
  62. package/dist/api/middlewares/validate.d.ts +4 -0
  63. package/dist/api/middlewares/validate.d.ts.map +1 -0
  64. package/dist/api/middlewares/validate.js +31 -0
  65. package/dist/api/middlewares/validate.js.map +1 -0
  66. package/dist/api/routes/audit.routes.d.ts +5 -0
  67. package/dist/api/routes/audit.routes.d.ts.map +1 -0
  68. package/dist/api/routes/audit.routes.js +24 -0
  69. package/dist/api/routes/audit.routes.js.map +1 -0
  70. package/dist/api/routes/auth.routes.d.ts +6 -0
  71. package/dist/api/routes/auth.routes.d.ts.map +1 -0
  72. package/dist/api/routes/auth.routes.js +22 -0
  73. package/dist/api/routes/auth.routes.js.map +1 -0
  74. package/dist/api/routes/export.routes.d.ts +5 -0
  75. package/dist/api/routes/export.routes.d.ts.map +1 -0
  76. package/dist/api/routes/export.routes.js +16 -0
  77. package/dist/api/routes/export.routes.js.map +1 -0
  78. package/dist/api/routes/health.routes.d.ts +4 -0
  79. package/dist/api/routes/health.routes.d.ts.map +1 -0
  80. package/dist/api/routes/health.routes.js +11 -0
  81. package/dist/api/routes/health.routes.js.map +1 -0
  82. package/dist/api/routes/index.d.ts +10 -0
  83. package/dist/api/routes/index.d.ts.map +1 -0
  84. package/dist/api/routes/index.js +20 -0
  85. package/dist/api/routes/index.js.map +1 -0
  86. package/dist/api/routes/providers.routes.d.ts +5 -0
  87. package/dist/api/routes/providers.routes.d.ts.map +1 -0
  88. package/dist/api/routes/providers.routes.js +13 -0
  89. package/dist/api/routes/providers.routes.js.map +1 -0
  90. package/dist/api/validators/audit.schemas.d.ts +60 -0
  91. package/dist/api/validators/audit.schemas.d.ts.map +1 -0
  92. package/dist/api/validators/audit.schemas.js +55 -0
  93. package/dist/api/validators/audit.schemas.js.map +1 -0
  94. package/dist/api/validators/auth.schemas.d.ts +17 -0
  95. package/dist/api/validators/auth.schemas.d.ts.map +1 -0
  96. package/dist/api/validators/auth.schemas.js +21 -0
  97. package/dist/api/validators/auth.schemas.js.map +1 -0
  98. package/dist/app.d.ts +3 -0
  99. package/dist/app.d.ts.map +1 -0
  100. package/dist/app.js +62 -0
  101. package/dist/app.js.map +1 -0
  102. package/dist/config/config.schema.d.ts +65 -0
  103. package/dist/config/config.schema.d.ts.map +1 -0
  104. package/dist/config/config.schema.js +95 -0
  105. package/dist/config/config.schema.js.map +1 -0
  106. package/dist/config/index.d.ts +4 -0
  107. package/dist/config/index.d.ts.map +1 -0
  108. package/dist/config/index.js +75 -0
  109. package/dist/config/index.js.map +1 -0
  110. package/dist/container.d.ts +47 -0
  111. package/dist/container.d.ts.map +1 -0
  112. package/dist/container.js +137 -0
  113. package/dist/container.js.map +1 -0
  114. package/dist/data/database.d.ts +13 -0
  115. package/dist/data/database.d.ts.map +1 -0
  116. package/dist/data/database.js +68 -0
  117. package/dist/data/database.js.map +1 -0
  118. package/dist/data/jobs/token-cleanup.job.d.ts +23 -0
  119. package/dist/data/jobs/token-cleanup.job.d.ts.map +1 -0
  120. package/dist/data/jobs/token-cleanup.job.js +96 -0
  121. package/dist/data/jobs/token-cleanup.job.js.map +1 -0
  122. package/dist/data/migrations/migration.runner.d.ts +13 -0
  123. package/dist/data/migrations/migration.runner.d.ts.map +1 -0
  124. package/dist/data/migrations/migration.runner.js +136 -0
  125. package/dist/data/migrations/migration.runner.js.map +1 -0
  126. package/dist/data/models/Token.model.d.ts +30 -0
  127. package/dist/data/models/Token.model.d.ts.map +1 -0
  128. package/dist/data/models/Token.model.js +3 -0
  129. package/dist/data/models/Token.model.js.map +1 -0
  130. package/dist/data/repositories/token.repository.d.ts +16 -0
  131. package/dist/data/repositories/token.repository.d.ts.map +1 -0
  132. package/dist/data/repositories/token.repository.js +97 -0
  133. package/dist/data/repositories/token.repository.js.map +1 -0
  134. package/dist/providers/azure/auth.provider.d.ts +5 -0
  135. package/dist/providers/azure/auth.provider.d.ts.map +1 -0
  136. package/dist/providers/azure/auth.provider.js +13 -0
  137. package/dist/providers/azure/auth.provider.js.map +1 -0
  138. package/dist/providers/azure/azure-errors.d.ts +40 -0
  139. package/dist/providers/azure/azure-errors.d.ts.map +1 -0
  140. package/dist/providers/azure/azure-errors.js +121 -0
  141. package/dist/providers/azure/azure-errors.js.map +1 -0
  142. package/dist/providers/azure/azure-retry.d.ts +41 -0
  143. package/dist/providers/azure/azure-retry.d.ts.map +1 -0
  144. package/dist/providers/azure/azure-retry.js +85 -0
  145. package/dist/providers/azure/azure-retry.js.map +1 -0
  146. package/dist/providers/azure/graph-client.d.ts +26 -0
  147. package/dist/providers/azure/graph-client.d.ts.map +1 -0
  148. package/dist/providers/azure/graph-client.js +146 -0
  149. package/dist/providers/azure/graph-client.js.map +1 -0
  150. package/dist/providers/azure/graph.provider.d.ts +23 -0
  151. package/dist/providers/azure/graph.provider.d.ts.map +1 -0
  152. package/dist/providers/azure/graph.provider.js +161 -0
  153. package/dist/providers/azure/graph.provider.js.map +1 -0
  154. package/dist/providers/azure/queries/app.queries.d.ts +6 -0
  155. package/dist/providers/azure/queries/app.queries.d.ts.map +1 -0
  156. package/dist/providers/azure/queries/app.queries.js +9 -0
  157. package/dist/providers/azure/queries/app.queries.js.map +1 -0
  158. package/dist/providers/azure/queries/policy.queries.d.ts +6 -0
  159. package/dist/providers/azure/queries/policy.queries.d.ts.map +1 -0
  160. package/dist/providers/azure/queries/policy.queries.js +9 -0
  161. package/dist/providers/azure/queries/policy.queries.js.map +1 -0
  162. package/dist/providers/azure/queries/user.queries.d.ts +7 -0
  163. package/dist/providers/azure/queries/user.queries.d.ts.map +1 -0
  164. package/dist/providers/azure/queries/user.queries.js +10 -0
  165. package/dist/providers/azure/queries/user.queries.js.map +1 -0
  166. package/dist/providers/interfaces/IGraphProvider.d.ts +31 -0
  167. package/dist/providers/interfaces/IGraphProvider.d.ts.map +1 -0
  168. package/dist/providers/interfaces/IGraphProvider.js +3 -0
  169. package/dist/providers/interfaces/IGraphProvider.js.map +1 -0
  170. package/dist/providers/interfaces/ILDAPProvider.d.ts +37 -0
  171. package/dist/providers/interfaces/ILDAPProvider.d.ts.map +1 -0
  172. package/dist/providers/interfaces/ILDAPProvider.js +3 -0
  173. package/dist/providers/interfaces/ILDAPProvider.js.map +1 -0
  174. package/dist/providers/ldap/acl-parser.d.ts +8 -0
  175. package/dist/providers/ldap/acl-parser.d.ts.map +1 -0
  176. package/dist/providers/ldap/acl-parser.js +157 -0
  177. package/dist/providers/ldap/acl-parser.js.map +1 -0
  178. package/dist/providers/ldap/ad-mappers.d.ts +8 -0
  179. package/dist/providers/ldap/ad-mappers.d.ts.map +1 -0
  180. package/dist/providers/ldap/ad-mappers.js +162 -0
  181. package/dist/providers/ldap/ad-mappers.js.map +1 -0
  182. package/dist/providers/ldap/ldap-client.d.ts +33 -0
  183. package/dist/providers/ldap/ldap-client.d.ts.map +1 -0
  184. package/dist/providers/ldap/ldap-client.js +195 -0
  185. package/dist/providers/ldap/ldap-client.js.map +1 -0
  186. package/dist/providers/ldap/ldap-errors.d.ts +48 -0
  187. package/dist/providers/ldap/ldap-errors.d.ts.map +1 -0
  188. package/dist/providers/ldap/ldap-errors.js +120 -0
  189. package/dist/providers/ldap/ldap-errors.js.map +1 -0
  190. package/dist/providers/ldap/ldap-retry.d.ts +14 -0
  191. package/dist/providers/ldap/ldap-retry.d.ts.map +1 -0
  192. package/dist/providers/ldap/ldap-retry.js +102 -0
  193. package/dist/providers/ldap/ldap-retry.js.map +1 -0
  194. package/dist/providers/ldap/ldap-sanitizer.d.ts +12 -0
  195. package/dist/providers/ldap/ldap-sanitizer.d.ts.map +1 -0
  196. package/dist/providers/ldap/ldap-sanitizer.js +104 -0
  197. package/dist/providers/ldap/ldap-sanitizer.js.map +1 -0
  198. package/dist/providers/ldap/ldap.provider.d.ts +21 -0
  199. package/dist/providers/ldap/ldap.provider.d.ts.map +1 -0
  200. package/dist/providers/ldap/ldap.provider.js +165 -0
  201. package/dist/providers/ldap/ldap.provider.js.map +1 -0
  202. package/dist/providers/ldap/queries/computer.queries.d.ts +6 -0
  203. package/dist/providers/ldap/queries/computer.queries.d.ts.map +1 -0
  204. package/dist/providers/ldap/queries/computer.queries.js +9 -0
  205. package/dist/providers/ldap/queries/computer.queries.js.map +1 -0
  206. package/dist/providers/ldap/queries/group.queries.d.ts +6 -0
  207. package/dist/providers/ldap/queries/group.queries.d.ts.map +1 -0
  208. package/dist/providers/ldap/queries/group.queries.js +9 -0
  209. package/dist/providers/ldap/queries/group.queries.js.map +1 -0
  210. package/dist/providers/ldap/queries/user.queries.d.ts +7 -0
  211. package/dist/providers/ldap/queries/user.queries.d.ts.map +1 -0
  212. package/dist/providers/ldap/queries/user.queries.js +10 -0
  213. package/dist/providers/ldap/queries/user.queries.js.map +1 -0
  214. package/dist/providers/smb/smb.provider.d.ts +68 -0
  215. package/dist/providers/smb/smb.provider.d.ts.map +1 -0
  216. package/dist/providers/smb/smb.provider.js +382 -0
  217. package/dist/providers/smb/smb.provider.js.map +1 -0
  218. package/dist/server.d.ts +2 -0
  219. package/dist/server.d.ts.map +1 -0
  220. package/dist/server.js +44 -0
  221. package/dist/server.js.map +1 -0
  222. package/dist/services/audit/ad-audit.service.d.ts +70 -0
  223. package/dist/services/audit/ad-audit.service.d.ts.map +1 -0
  224. package/dist/services/audit/ad-audit.service.js +1019 -0
  225. package/dist/services/audit/ad-audit.service.js.map +1 -0
  226. package/dist/services/audit/attack-graph.service.d.ts +62 -0
  227. package/dist/services/audit/attack-graph.service.d.ts.map +1 -0
  228. package/dist/services/audit/attack-graph.service.js +702 -0
  229. package/dist/services/audit/attack-graph.service.js.map +1 -0
  230. package/dist/services/audit/audit.service.d.ts +4 -0
  231. package/dist/services/audit/audit.service.d.ts.map +1 -0
  232. package/dist/services/audit/audit.service.js +10 -0
  233. package/dist/services/audit/audit.service.js.map +1 -0
  234. package/dist/services/audit/azure-audit.service.d.ts +37 -0
  235. package/dist/services/audit/azure-audit.service.d.ts.map +1 -0
  236. package/dist/services/audit/azure-audit.service.js +153 -0
  237. package/dist/services/audit/azure-audit.service.js.map +1 -0
  238. package/dist/services/audit/detectors/ad/accounts.detector.d.ts +37 -0
  239. package/dist/services/audit/detectors/ad/accounts.detector.d.ts.map +1 -0
  240. package/dist/services/audit/detectors/ad/accounts.detector.js +881 -0
  241. package/dist/services/audit/detectors/ad/accounts.detector.js.map +1 -0
  242. package/dist/services/audit/detectors/ad/adcs.detector.d.ts +21 -0
  243. package/dist/services/audit/detectors/ad/adcs.detector.d.ts.map +1 -0
  244. package/dist/services/audit/detectors/ad/adcs.detector.js +227 -0
  245. package/dist/services/audit/detectors/ad/adcs.detector.js.map +1 -0
  246. package/dist/services/audit/detectors/ad/advanced.detector.d.ts +63 -0
  247. package/dist/services/audit/detectors/ad/advanced.detector.d.ts.map +1 -0
  248. package/dist/services/audit/detectors/ad/advanced.detector.js +867 -0
  249. package/dist/services/audit/detectors/ad/advanced.detector.js.map +1 -0
  250. package/dist/services/audit/detectors/ad/attack-paths.detector.d.ts +16 -0
  251. package/dist/services/audit/detectors/ad/attack-paths.detector.d.ts.map +1 -0
  252. package/dist/services/audit/detectors/ad/attack-paths.detector.js +369 -0
  253. package/dist/services/audit/detectors/ad/attack-paths.detector.js.map +1 -0
  254. package/dist/services/audit/detectors/ad/compliance.detector.d.ts +28 -0
  255. package/dist/services/audit/detectors/ad/compliance.detector.d.ts.map +1 -0
  256. package/dist/services/audit/detectors/ad/compliance.detector.js +896 -0
  257. package/dist/services/audit/detectors/ad/compliance.detector.js.map +1 -0
  258. package/dist/services/audit/detectors/ad/computers.detector.d.ts +30 -0
  259. package/dist/services/audit/detectors/ad/computers.detector.d.ts.map +1 -0
  260. package/dist/services/audit/detectors/ad/computers.detector.js +799 -0
  261. package/dist/services/audit/detectors/ad/computers.detector.js.map +1 -0
  262. package/dist/services/audit/detectors/ad/gpo.detector.d.ts +17 -0
  263. package/dist/services/audit/detectors/ad/gpo.detector.d.ts.map +1 -0
  264. package/dist/services/audit/detectors/ad/gpo.detector.js +257 -0
  265. package/dist/services/audit/detectors/ad/gpo.detector.js.map +1 -0
  266. package/dist/services/audit/detectors/ad/groups.detector.d.ts +19 -0
  267. package/dist/services/audit/detectors/ad/groups.detector.d.ts.map +1 -0
  268. package/dist/services/audit/detectors/ad/groups.detector.js +488 -0
  269. package/dist/services/audit/detectors/ad/groups.detector.js.map +1 -0
  270. package/dist/services/audit/detectors/ad/index.d.ts +15 -0
  271. package/dist/services/audit/detectors/ad/index.d.ts.map +1 -0
  272. package/dist/services/audit/detectors/ad/index.js +51 -0
  273. package/dist/services/audit/detectors/ad/index.js.map +1 -0
  274. package/dist/services/audit/detectors/ad/kerberos.detector.d.ts +17 -0
  275. package/dist/services/audit/detectors/ad/kerberos.detector.d.ts.map +1 -0
  276. package/dist/services/audit/detectors/ad/kerberos.detector.js +293 -0
  277. package/dist/services/audit/detectors/ad/kerberos.detector.js.map +1 -0
  278. package/dist/services/audit/detectors/ad/monitoring.detector.d.ts +23 -0
  279. package/dist/services/audit/detectors/ad/monitoring.detector.d.ts.map +1 -0
  280. package/dist/services/audit/detectors/ad/monitoring.detector.js +328 -0
  281. package/dist/services/audit/detectors/ad/monitoring.detector.js.map +1 -0
  282. package/dist/services/audit/detectors/ad/network.detector.d.ts +39 -0
  283. package/dist/services/audit/detectors/ad/network.detector.d.ts.map +1 -0
  284. package/dist/services/audit/detectors/ad/network.detector.js +257 -0
  285. package/dist/services/audit/detectors/ad/network.detector.js.map +1 -0
  286. package/dist/services/audit/detectors/ad/password.detector.d.ts +14 -0
  287. package/dist/services/audit/detectors/ad/password.detector.d.ts.map +1 -0
  288. package/dist/services/audit/detectors/ad/password.detector.js +235 -0
  289. package/dist/services/audit/detectors/ad/password.detector.js.map +1 -0
  290. package/dist/services/audit/detectors/ad/permissions.detector.d.ts +20 -0
  291. package/dist/services/audit/detectors/ad/permissions.detector.d.ts.map +1 -0
  292. package/dist/services/audit/detectors/ad/permissions.detector.js +392 -0
  293. package/dist/services/audit/detectors/ad/permissions.detector.js.map +1 -0
  294. package/dist/services/audit/detectors/ad/trusts.detector.d.ts +11 -0
  295. package/dist/services/audit/detectors/ad/trusts.detector.d.ts.map +1 -0
  296. package/dist/services/audit/detectors/ad/trusts.detector.js +186 -0
  297. package/dist/services/audit/detectors/ad/trusts.detector.js.map +1 -0
  298. package/dist/services/audit/detectors/azure/app-security.detector.d.ts +11 -0
  299. package/dist/services/audit/detectors/azure/app-security.detector.d.ts.map +1 -0
  300. package/dist/services/audit/detectors/azure/app-security.detector.js +184 -0
  301. package/dist/services/audit/detectors/azure/app-security.detector.js.map +1 -0
  302. package/dist/services/audit/detectors/azure/conditional-access.detector.d.ts +10 -0
  303. package/dist/services/audit/detectors/azure/conditional-access.detector.d.ts.map +1 -0
  304. package/dist/services/audit/detectors/azure/conditional-access.detector.js +130 -0
  305. package/dist/services/audit/detectors/azure/conditional-access.detector.js.map +1 -0
  306. package/dist/services/audit/detectors/azure/privilege-security.detector.d.ts +8 -0
  307. package/dist/services/audit/detectors/azure/privilege-security.detector.d.ts.map +1 -0
  308. package/dist/services/audit/detectors/azure/privilege-security.detector.js +113 -0
  309. package/dist/services/audit/detectors/azure/privilege-security.detector.js.map +1 -0
  310. package/dist/services/audit/detectors/azure/user-security.detector.d.ts +14 -0
  311. package/dist/services/audit/detectors/azure/user-security.detector.d.ts.map +1 -0
  312. package/dist/services/audit/detectors/azure/user-security.detector.js +198 -0
  313. package/dist/services/audit/detectors/azure/user-security.detector.js.map +1 -0
  314. package/dist/services/audit/detectors/index.d.ts +2 -0
  315. package/dist/services/audit/detectors/index.d.ts.map +1 -0
  316. package/dist/services/audit/detectors/index.js +38 -0
  317. package/dist/services/audit/detectors/index.js.map +1 -0
  318. package/dist/services/audit/response-formatter.d.ts +176 -0
  319. package/dist/services/audit/response-formatter.d.ts.map +1 -0
  320. package/dist/services/audit/response-formatter.js +240 -0
  321. package/dist/services/audit/response-formatter.js.map +1 -0
  322. package/dist/services/audit/scoring.service.d.ts +15 -0
  323. package/dist/services/audit/scoring.service.d.ts.map +1 -0
  324. package/dist/services/audit/scoring.service.js +139 -0
  325. package/dist/services/audit/scoring.service.js.map +1 -0
  326. package/dist/services/auth/crypto.service.d.ts +19 -0
  327. package/dist/services/auth/crypto.service.d.ts.map +1 -0
  328. package/dist/services/auth/crypto.service.js +135 -0
  329. package/dist/services/auth/crypto.service.js.map +1 -0
  330. package/dist/services/auth/errors.d.ts +19 -0
  331. package/dist/services/auth/errors.d.ts.map +1 -0
  332. package/dist/services/auth/errors.js +46 -0
  333. package/dist/services/auth/errors.js.map +1 -0
  334. package/dist/services/auth/token.service.d.ts +41 -0
  335. package/dist/services/auth/token.service.d.ts.map +1 -0
  336. package/dist/services/auth/token.service.js +208 -0
  337. package/dist/services/auth/token.service.js.map +1 -0
  338. package/dist/services/config/config.service.d.ts +6 -0
  339. package/dist/services/config/config.service.d.ts.map +1 -0
  340. package/dist/services/config/config.service.js +64 -0
  341. package/dist/services/config/config.service.js.map +1 -0
  342. package/dist/services/export/export.service.d.ts +28 -0
  343. package/dist/services/export/export.service.d.ts.map +1 -0
  344. package/dist/services/export/export.service.js +28 -0
  345. package/dist/services/export/export.service.js.map +1 -0
  346. package/dist/services/export/formatters/csv.formatter.d.ts +8 -0
  347. package/dist/services/export/formatters/csv.formatter.d.ts.map +1 -0
  348. package/dist/services/export/formatters/csv.formatter.js +46 -0
  349. package/dist/services/export/formatters/csv.formatter.js.map +1 -0
  350. package/dist/services/export/formatters/json.formatter.d.ts +40 -0
  351. package/dist/services/export/formatters/json.formatter.d.ts.map +1 -0
  352. package/dist/services/export/formatters/json.formatter.js +58 -0
  353. package/dist/services/export/formatters/json.formatter.js.map +1 -0
  354. package/dist/services/jobs/azure-job-runner.d.ts +38 -0
  355. package/dist/services/jobs/azure-job-runner.d.ts.map +1 -0
  356. package/dist/services/jobs/azure-job-runner.js +199 -0
  357. package/dist/services/jobs/azure-job-runner.js.map +1 -0
  358. package/dist/services/jobs/index.d.ts +4 -0
  359. package/dist/services/jobs/index.d.ts.map +1 -0
  360. package/dist/services/jobs/index.js +20 -0
  361. package/dist/services/jobs/index.js.map +1 -0
  362. package/dist/services/jobs/job-runner.d.ts +64 -0
  363. package/dist/services/jobs/job-runner.d.ts.map +1 -0
  364. package/dist/services/jobs/job-runner.js +952 -0
  365. package/dist/services/jobs/job-runner.js.map +1 -0
  366. package/dist/services/jobs/job-store.d.ts +27 -0
  367. package/dist/services/jobs/job-store.d.ts.map +1 -0
  368. package/dist/services/jobs/job-store.js +261 -0
  369. package/dist/services/jobs/job-store.js.map +1 -0
  370. package/dist/services/jobs/job.types.d.ts +67 -0
  371. package/dist/services/jobs/job.types.d.ts.map +1 -0
  372. package/dist/services/jobs/job.types.js +36 -0
  373. package/dist/services/jobs/job.types.js.map +1 -0
  374. package/dist/types/ad.types.d.ts +74 -0
  375. package/dist/types/ad.types.d.ts.map +1 -0
  376. package/dist/types/ad.types.js +3 -0
  377. package/dist/types/ad.types.js.map +1 -0
  378. package/dist/types/adcs.types.d.ts +58 -0
  379. package/dist/types/adcs.types.d.ts.map +1 -0
  380. package/dist/types/adcs.types.js +38 -0
  381. package/dist/types/adcs.types.js.map +1 -0
  382. package/dist/types/attack-graph.types.d.ts +135 -0
  383. package/dist/types/attack-graph.types.d.ts.map +1 -0
  384. package/dist/types/attack-graph.types.js +58 -0
  385. package/dist/types/attack-graph.types.js.map +1 -0
  386. package/dist/types/audit.types.d.ts +34 -0
  387. package/dist/types/audit.types.d.ts.map +1 -0
  388. package/dist/types/audit.types.js +3 -0
  389. package/dist/types/audit.types.js.map +1 -0
  390. package/dist/types/azure.types.d.ts +61 -0
  391. package/dist/types/azure.types.d.ts.map +1 -0
  392. package/dist/types/azure.types.js +3 -0
  393. package/dist/types/azure.types.js.map +1 -0
  394. package/dist/types/config.types.d.ts +63 -0
  395. package/dist/types/config.types.d.ts.map +1 -0
  396. package/dist/types/config.types.js +3 -0
  397. package/dist/types/config.types.js.map +1 -0
  398. package/dist/types/error.types.d.ts +33 -0
  399. package/dist/types/error.types.d.ts.map +1 -0
  400. package/dist/types/error.types.js +70 -0
  401. package/dist/types/error.types.js.map +1 -0
  402. package/dist/types/finding.types.d.ts +133 -0
  403. package/dist/types/finding.types.d.ts.map +1 -0
  404. package/dist/types/finding.types.js +3 -0
  405. package/dist/types/finding.types.js.map +1 -0
  406. package/dist/types/gpo.types.d.ts +39 -0
  407. package/dist/types/gpo.types.d.ts.map +1 -0
  408. package/dist/types/gpo.types.js +15 -0
  409. package/dist/types/gpo.types.js.map +1 -0
  410. package/dist/types/token.types.d.ts +26 -0
  411. package/dist/types/token.types.d.ts.map +1 -0
  412. package/dist/types/token.types.js +3 -0
  413. package/dist/types/token.types.js.map +1 -0
  414. package/dist/types/trust.types.d.ts +45 -0
  415. package/dist/types/trust.types.d.ts.map +1 -0
  416. package/dist/types/trust.types.js +71 -0
  417. package/dist/types/trust.types.js.map +1 -0
  418. package/dist/utils/entity-converter.d.ts +17 -0
  419. package/dist/utils/entity-converter.d.ts.map +1 -0
  420. package/dist/utils/entity-converter.js +285 -0
  421. package/dist/utils/entity-converter.js.map +1 -0
  422. package/dist/utils/graph.util.d.ts +66 -0
  423. package/dist/utils/graph.util.d.ts.map +1 -0
  424. package/dist/utils/graph.util.js +382 -0
  425. package/dist/utils/graph.util.js.map +1 -0
  426. package/dist/utils/logger.d.ts +7 -0
  427. package/dist/utils/logger.d.ts.map +1 -0
  428. package/dist/utils/logger.js +86 -0
  429. package/dist/utils/logger.js.map +1 -0
  430. package/dist/utils/type-name-normalizer.d.ts +5 -0
  431. package/dist/utils/type-name-normalizer.d.ts.map +1 -0
  432. package/dist/utils/type-name-normalizer.js +218 -0
  433. package/dist/utils/type-name-normalizer.js.map +1 -0
  434. package/docker-compose.yml +26 -0
  435. package/docs/api/README.md +178 -0
  436. package/docs/api/openapi.yaml +1524 -0
  437. package/eslint.config.js +54 -0
  438. package/jest.config.js +38 -0
  439. package/package.json +97 -0
  440. package/scripts/fetch-ad-cert.sh +142 -0
  441. package/src/.gitkeep +0 -0
  442. package/src/api/.gitkeep +0 -0
  443. package/src/api/controllers/.gitkeep +0 -0
  444. package/src/api/controllers/audit.controller.ts +313 -0
  445. package/src/api/controllers/auth.controller.ts +258 -0
  446. package/src/api/controllers/export.controller.ts +153 -0
  447. package/src/api/controllers/health.controller.ts +16 -0
  448. package/src/api/controllers/jobs.controller.ts +187 -0
  449. package/src/api/controllers/providers.controller.ts +165 -0
  450. package/src/api/dto/.gitkeep +0 -0
  451. package/src/api/dto/AuditRequest.dto.ts +8 -0
  452. package/src/api/dto/AuditResponse.dto.ts +19 -0
  453. package/src/api/dto/TokenRequest.dto.ts +8 -0
  454. package/src/api/dto/TokenResponse.dto.ts +14 -0
  455. package/src/api/middlewares/.gitkeep +0 -0
  456. package/src/api/middlewares/authenticate.ts +203 -0
  457. package/src/api/middlewares/errorHandler.ts +54 -0
  458. package/src/api/middlewares/rateLimit.ts +35 -0
  459. package/src/api/middlewares/validate.ts +32 -0
  460. package/src/api/routes/.gitkeep +0 -0
  461. package/src/api/routes/audit.routes.ts +77 -0
  462. package/src/api/routes/auth.routes.ts +71 -0
  463. package/src/api/routes/export.routes.ts +34 -0
  464. package/src/api/routes/health.routes.ts +14 -0
  465. package/src/api/routes/index.ts +40 -0
  466. package/src/api/routes/providers.routes.ts +24 -0
  467. package/src/api/validators/.gitkeep +0 -0
  468. package/src/api/validators/audit.schemas.ts +59 -0
  469. package/src/api/validators/auth.schemas.ts +59 -0
  470. package/src/app.ts +87 -0
  471. package/src/config/.gitkeep +0 -0
  472. package/src/config/config.schema.ts +108 -0
  473. package/src/config/index.ts +82 -0
  474. package/src/container.ts +221 -0
  475. package/src/data/.gitkeep +0 -0
  476. package/src/data/database.ts +78 -0
  477. package/src/data/jobs/token-cleanup.job.ts +166 -0
  478. package/src/data/migrations/.gitkeep +0 -0
  479. package/src/data/migrations/001_initial_schema.sql +47 -0
  480. package/src/data/migrations/migration.runner.ts +125 -0
  481. package/src/data/models/.gitkeep +0 -0
  482. package/src/data/models/Token.model.ts +35 -0
  483. package/src/data/repositories/.gitkeep +0 -0
  484. package/src/data/repositories/token.repository.ts +160 -0
  485. package/src/providers/.gitkeep +0 -0
  486. package/src/providers/azure/.gitkeep +0 -0
  487. package/src/providers/azure/auth.provider.ts +14 -0
  488. package/src/providers/azure/azure-errors.ts +189 -0
  489. package/src/providers/azure/azure-retry.ts +168 -0
  490. package/src/providers/azure/graph-client.ts +315 -0
  491. package/src/providers/azure/graph.provider.ts +294 -0
  492. package/src/providers/azure/queries/app.queries.ts +9 -0
  493. package/src/providers/azure/queries/policy.queries.ts +9 -0
  494. package/src/providers/azure/queries/user.queries.ts +10 -0
  495. package/src/providers/interfaces/.gitkeep +0 -0
  496. package/src/providers/interfaces/IGraphProvider.ts +117 -0
  497. package/src/providers/interfaces/ILDAPProvider.ts +142 -0
  498. package/src/providers/ldap/.gitkeep +0 -0
  499. package/src/providers/ldap/acl-parser.ts +231 -0
  500. package/src/providers/ldap/ad-mappers.ts +280 -0
  501. package/src/providers/ldap/ldap-client.ts +259 -0
  502. package/src/providers/ldap/ldap-errors.ts +188 -0
  503. package/src/providers/ldap/ldap-retry.ts +267 -0
  504. package/src/providers/ldap/ldap-sanitizer.ts +273 -0
  505. package/src/providers/ldap/ldap.provider.ts +293 -0
  506. package/src/providers/ldap/queries/computer.queries.ts +9 -0
  507. package/src/providers/ldap/queries/group.queries.ts +9 -0
  508. package/src/providers/ldap/queries/user.queries.ts +10 -0
  509. package/src/providers/smb/smb.provider.ts +653 -0
  510. package/src/server.ts +60 -0
  511. package/src/services/.gitkeep +0 -0
  512. package/src/services/audit/.gitkeep +0 -0
  513. package/src/services/audit/ad-audit.service.ts +1481 -0
  514. package/src/services/audit/attack-graph.service.ts +1104 -0
  515. package/src/services/audit/audit.service.ts +12 -0
  516. package/src/services/audit/azure-audit.service.ts +286 -0
  517. package/src/services/audit/detectors/ad/accounts.detector.ts +1232 -0
  518. package/src/services/audit/detectors/ad/adcs.detector.ts +449 -0
  519. package/src/services/audit/detectors/ad/advanced.detector.ts +1270 -0
  520. package/src/services/audit/detectors/ad/attack-paths.detector.ts +600 -0
  521. package/src/services/audit/detectors/ad/compliance.detector.ts +1421 -0
  522. package/src/services/audit/detectors/ad/computers.detector.ts +1188 -0
  523. package/src/services/audit/detectors/ad/gpo.detector.ts +485 -0
  524. package/src/services/audit/detectors/ad/groups.detector.ts +685 -0
  525. package/src/services/audit/detectors/ad/index.ts +84 -0
  526. package/src/services/audit/detectors/ad/kerberos.detector.ts +424 -0
  527. package/src/services/audit/detectors/ad/monitoring.detector.ts +501 -0
  528. package/src/services/audit/detectors/ad/network.detector.ts +538 -0
  529. package/src/services/audit/detectors/ad/password.detector.ts +324 -0
  530. package/src/services/audit/detectors/ad/permissions.detector.ts +637 -0
  531. package/src/services/audit/detectors/ad/trusts.detector.ts +315 -0
  532. package/src/services/audit/detectors/azure/app-security.detector.ts +246 -0
  533. package/src/services/audit/detectors/azure/conditional-access.detector.ts +186 -0
  534. package/src/services/audit/detectors/azure/privilege-security.detector.ts +176 -0
  535. package/src/services/audit/detectors/azure/user-security.detector.ts +280 -0
  536. package/src/services/audit/detectors/index.ts +18 -0
  537. package/src/services/audit/response-formatter.ts +604 -0
  538. package/src/services/audit/scoring.service.ts +234 -0
  539. package/src/services/auth/.gitkeep +0 -0
  540. package/src/services/auth/crypto.service.ts +230 -0
  541. package/src/services/auth/errors.ts +47 -0
  542. package/src/services/auth/token.service.ts +420 -0
  543. package/src/services/config/.gitkeep +0 -0
  544. package/src/services/config/config.service.ts +75 -0
  545. package/src/services/export/.gitkeep +0 -0
  546. package/src/services/export/export.service.ts +99 -0
  547. package/src/services/export/formatters/csv.formatter.ts +124 -0
  548. package/src/services/export/formatters/json.formatter.ts +160 -0
  549. package/src/services/jobs/azure-job-runner.ts +312 -0
  550. package/src/services/jobs/index.ts +9 -0
  551. package/src/services/jobs/job-runner.ts +1280 -0
  552. package/src/services/jobs/job-store.ts +384 -0
  553. package/src/services/jobs/job.types.ts +182 -0
  554. package/src/types/.gitkeep +0 -0
  555. package/src/types/ad.types.ts +91 -0
  556. package/src/types/adcs.types.ts +107 -0
  557. package/src/types/attack-graph.types.ts +260 -0
  558. package/src/types/audit.types.ts +42 -0
  559. package/src/types/azure.types.ts +68 -0
  560. package/src/types/config.types.ts +79 -0
  561. package/src/types/error.types.ts +69 -0
  562. package/src/types/finding.types.ts +284 -0
  563. package/src/types/gpo.types.ts +72 -0
  564. package/src/types/smb2.d.ts +73 -0
  565. package/src/types/token.types.ts +32 -0
  566. package/src/types/trust.types.ts +140 -0
  567. package/src/utils/.gitkeep +0 -0
  568. package/src/utils/entity-converter.ts +453 -0
  569. package/src/utils/graph.util.ts +609 -0
  570. package/src/utils/logger.ts +111 -0
  571. package/src/utils/type-name-normalizer.ts +302 -0
  572. package/tests/.gitkeep +0 -0
  573. package/tests/e2e/.gitkeep +0 -0
  574. package/tests/fixtures/.gitkeep +0 -0
  575. package/tests/integration/.gitkeep +0 -0
  576. package/tests/integration/README.md +156 -0
  577. package/tests/integration/ad-audit.integration.test.ts +216 -0
  578. package/tests/integration/api/.gitkeep +0 -0
  579. package/tests/integration/api/endpoints.integration.test.ts +431 -0
  580. package/tests/integration/auth/jwt-authentication.integration.test.ts +358 -0
  581. package/tests/integration/providers/.gitkeep +0 -0
  582. package/tests/integration/providers/azure-basic.integration.test.ts +167 -0
  583. package/tests/integration/providers/ldap-basic.integration.test.ts +152 -0
  584. package/tests/integration/providers/ldap-connectivity.test.ts +44 -0
  585. package/tests/integration/providers/ldap-provider.integration.test.ts +347 -0
  586. package/tests/mocks/.gitkeep +0 -0
  587. package/tests/setup.ts +16 -0
  588. package/tests/unit/.gitkeep +0 -0
  589. package/tests/unit/api/middlewares/authenticate.test.ts +446 -0
  590. package/tests/unit/providers/.gitkeep +0 -0
  591. package/tests/unit/providers/azure/azure-errors.test.ts +193 -0
  592. package/tests/unit/providers/azure/azure-retry.test.ts +254 -0
  593. package/tests/unit/providers/azure/graph-provider.test.ts +313 -0
  594. package/tests/unit/providers/ldap/ad-mappers.test.ts +392 -0
  595. package/tests/unit/providers/ldap/ldap-provider.test.ts +376 -0
  596. package/tests/unit/providers/ldap/ldap-retry.test.ts +377 -0
  597. package/tests/unit/providers/ldap/ldap-sanitizer.test.ts +301 -0
  598. package/tests/unit/sample.test.ts +19 -0
  599. package/tests/unit/services/.gitkeep +0 -0
  600. package/tests/unit/services/audit/detectors/ad/accounts.detector.test.ts +393 -0
  601. package/tests/unit/services/audit/detectors/ad/advanced.detector.test.ts +380 -0
  602. package/tests/unit/services/audit/detectors/ad/computers.detector.test.ts +440 -0
  603. package/tests/unit/services/audit/detectors/ad/groups.detector.test.ts +276 -0
  604. package/tests/unit/services/audit/detectors/ad/kerberos.detector.test.ts +215 -0
  605. package/tests/unit/services/audit/detectors/ad/password.detector.test.ts +226 -0
  606. package/tests/unit/services/audit/detectors/ad/permissions.detector.test.ts +244 -0
  607. package/tests/unit/services/audit/detectors/azure/app-security.detector.test.ts +349 -0
  608. package/tests/unit/services/audit/detectors/azure/conditional-access.detector.test.ts +374 -0
  609. package/tests/unit/services/audit/detectors/azure/privilege-security.detector.test.ts +374 -0
  610. package/tests/unit/services/audit/detectors/azure/user-security.detector.test.ts +297 -0
  611. package/tests/unit/services/auth/crypto.service.test.ts +296 -0
  612. package/tests/unit/services/auth/token.service.test.ts +579 -0
  613. package/tests/unit/services/export/export.service.test.ts +241 -0
  614. package/tests/unit/services/export/formatters/csv.formatter.test.ts +270 -0
  615. package/tests/unit/services/export/formatters/json.formatter.test.ts +258 -0
  616. package/tests/unit/utils/.gitkeep +0 -0
  617. package/tsconfig.json +50 -0
@@ -0,0 +1,653 @@
1
+ /**
2
+ * SMB Provider
3
+ *
4
+ * Provides SMB2/3 access to Windows shares (SYSVOL, etc.)
5
+ * Used to read Group Policy files like GptTmpl.inf for Kerberos policy.
6
+ *
7
+ * Uses smbclient CLI tool for better compatibility with Windows servers.
8
+ */
9
+
10
+ import { exec } from 'child_process';
11
+ import { promisify } from 'util';
12
+ import { readFile as fsReadFile, unlink } from 'fs/promises';
13
+ import { tmpdir } from 'os';
14
+ import { join } from 'path';
15
+ import { logger } from '../../utils/logger';
16
+
17
+ const execAsync = promisify(exec);
18
+
19
+ /**
20
+ * SMB connection configuration
21
+ */
22
+ export interface SMBConfig {
23
+ /** Domain controller hostname or IP */
24
+ host: string;
25
+ /** SMB share name (e.g., 'SYSVOL') */
26
+ share: string;
27
+ /** Domain name */
28
+ domain: string;
29
+ /** Username for authentication */
30
+ username: string;
31
+ /** Password for authentication */
32
+ password: string;
33
+ /** Connection timeout in ms (default: 10000) */
34
+ timeout?: number;
35
+ }
36
+
37
+ /**
38
+ * Kerberos policy from GptTmpl.inf
39
+ */
40
+ export interface KerberosPolicy {
41
+ maxTicketAge: number; // hours
42
+ maxRenewAge: number; // days
43
+ maxServiceAge: number; // minutes
44
+ maxClockSkew: number; // minutes
45
+ ticketValidateClient: boolean;
46
+ }
47
+
48
+ /**
49
+ * Security settings extracted from GPO files
50
+ */
51
+ export interface GpoSecuritySettings {
52
+ /** LDAP server signing requirement: 0=none, 1=negotiate, 2=require */
53
+ ldapServerIntegrity?: number;
54
+ /** LDAP channel binding: 0=never, 1=when supported, 2=always */
55
+ ldapChannelBinding?: number;
56
+ /** SMBv1 server enabled */
57
+ smbv1ServerEnabled?: boolean;
58
+ /** SMBv1 client enabled */
59
+ smbv1ClientEnabled?: boolean;
60
+ /** SMB Server signing required (RequireSecuritySignature) */
61
+ smbSigningRequired?: boolean;
62
+ /** SMB Client signing required */
63
+ smbClientSigningRequired?: boolean;
64
+ /** Audit policies configured */
65
+ auditPolicies?: {
66
+ category: string;
67
+ subcategory?: string;
68
+ success: boolean;
69
+ failure: boolean;
70
+ }[];
71
+ /** PowerShell logging settings */
72
+ powershellLogging?: {
73
+ moduleLogging: boolean;
74
+ scriptBlockLogging: boolean;
75
+ transcription: boolean;
76
+ };
77
+ }
78
+
79
+ /**
80
+ * Default Domain Policy GUID (well-known)
81
+ */
82
+ const DEFAULT_DOMAIN_POLICY_GUID = '{31B2F340-016D-11D2-945F-00C04FB984F9}';
83
+
84
+ /**
85
+ * SMB Provider for reading Windows shares using smbclient
86
+ */
87
+ export class SMBProvider {
88
+ private config: SMBConfig;
89
+
90
+ constructor(config: SMBConfig) {
91
+ this.config = {
92
+ timeout: 15000,
93
+ ...config,
94
+ };
95
+ }
96
+
97
+ /**
98
+ * Connect to SMB share (no-op for smbclient - stateless)
99
+ */
100
+ async connect(): Promise<void> {
101
+ logger.debug('SMB provider ready (using smbclient)', { host: this.config.host, share: this.config.share });
102
+ }
103
+
104
+ /**
105
+ * Disconnect from SMB share (no-op for smbclient - stateless)
106
+ */
107
+ async disconnect(): Promise<void> {
108
+ // No-op for smbclient
109
+ }
110
+
111
+ /**
112
+ * Build smbclient command base (without the -c command part)
113
+ */
114
+ private buildSmbCommand(): string {
115
+ const { host, share, domain, username, password } = this.config;
116
+ // smbclient //server/share -U domain\user%password -c "command"
117
+ // Escape special characters in password
118
+ const escapedPassword = password.replace(/'/g, "'\\''");
119
+ return `smbclient '//${host}/${share}' -U '${domain}\\${username}%${escapedPassword}' -c`;
120
+ }
121
+
122
+ /**
123
+ * Read a file from the SMB share using smbclient
124
+ */
125
+ async readFile(path: string): Promise<string> {
126
+ const timeout = this.config.timeout || 15000;
127
+ const tempFile = join(tmpdir(), `smb_${Date.now()}_${Math.random().toString(36).substring(7)}`);
128
+
129
+ // Convert Windows path to SMB path format
130
+ const smbPath = path.replace(/\\/g, '/');
131
+
132
+ const cmd = `${this.buildSmbCommand()} 'get "${smbPath}" "${tempFile}"'`;
133
+
134
+ try {
135
+ logger.debug('SMB readFile', { path: smbPath, tempFile });
136
+
137
+ await execAsync(cmd, { timeout });
138
+
139
+ const content = await fsReadFile(tempFile, 'utf8');
140
+
141
+ // Cleanup temp file
142
+ try {
143
+ await unlink(tempFile);
144
+ } catch {
145
+ // Ignore cleanup errors
146
+ }
147
+
148
+ return content;
149
+ } catch (error) {
150
+ // Cleanup temp file on error
151
+ try {
152
+ await unlink(tempFile);
153
+ } catch {
154
+ // Ignore cleanup errors
155
+ }
156
+
157
+ const message = error instanceof Error ? error.message : 'Unknown error';
158
+ logger.debug('SMB readFile failed', { path: smbPath, error: message });
159
+ throw new Error(`SMB readFile failed: ${message}`);
160
+ }
161
+ }
162
+
163
+ /**
164
+ * Read a binary file from the SMB share
165
+ */
166
+ async readBinaryFile(path: string): Promise<Buffer> {
167
+ const timeout = this.config.timeout || 15000;
168
+ const tempFile = join(tmpdir(), `smb_${Date.now()}_${Math.random().toString(36).substring(7)}`);
169
+
170
+ // Convert Windows path to SMB path format
171
+ const smbPath = path.replace(/\\/g, '/');
172
+
173
+ const cmd = `${this.buildSmbCommand()} 'get "${smbPath}" "${tempFile}"'`;
174
+
175
+ try {
176
+ await execAsync(cmd, { timeout });
177
+ const content = await fsReadFile(tempFile);
178
+
179
+ // Cleanup temp file
180
+ try {
181
+ await unlink(tempFile);
182
+ } catch {
183
+ // Ignore cleanup errors
184
+ }
185
+
186
+ return content;
187
+ } catch (error) {
188
+ // Cleanup temp file on error
189
+ try {
190
+ await unlink(tempFile);
191
+ } catch {
192
+ // Ignore cleanup errors
193
+ }
194
+
195
+ throw error;
196
+ }
197
+ }
198
+
199
+ /**
200
+ * Check if a file exists on the SMB share
201
+ */
202
+ async exists(path: string): Promise<boolean> {
203
+ const timeout = this.config.timeout || 15000;
204
+
205
+ // Convert Windows path to SMB path format
206
+ const smbPath = path.replace(/\\/g, '/');
207
+
208
+ // Use 'ls' command to check if file exists
209
+ // Extract directory and filename
210
+ const lastSlash = smbPath.lastIndexOf('/');
211
+ const dir = lastSlash > 0 ? smbPath.substring(0, lastSlash) : '';
212
+ const filename = lastSlash > 0 ? smbPath.substring(lastSlash + 1) : smbPath;
213
+
214
+ const cmd = `${this.buildSmbCommand()} 'cd "${dir}"; ls "${filename}"'`;
215
+
216
+ try {
217
+ logger.debug('SMB exists check', { path: smbPath, dir, filename });
218
+
219
+ const { stdout } = await execAsync(cmd, { timeout });
220
+
221
+ // If we get output and it contains the filename, the file exists
222
+ const exists = stdout.includes(filename);
223
+ logger.debug('SMB exists result', { path: smbPath, exists });
224
+
225
+ return exists;
226
+ } catch (error) {
227
+ const message = error instanceof Error ? error.message : 'Unknown error';
228
+ logger.debug('SMB exists check failed (file likely does not exist)', { path: smbPath, error: message });
229
+ return false;
230
+ }
231
+ }
232
+
233
+ /**
234
+ * Read Kerberos policy from Default Domain Policy GPO
235
+ */
236
+ async readKerberosPolicy(domainDnsName: string): Promise<KerberosPolicy | null> {
237
+ const gptTmplPath = `${domainDnsName}/Policies/${DEFAULT_DOMAIN_POLICY_GUID}/Machine/Microsoft/Windows NT/SecEdit/GptTmpl.inf`;
238
+
239
+ try {
240
+ logger.debug('Reading GptTmpl.inf for Kerberos policy', { path: gptTmplPath });
241
+
242
+ const exists = await this.exists(gptTmplPath);
243
+ if (!exists) {
244
+ logger.warn('GptTmpl.inf not found', { path: gptTmplPath });
245
+ return null;
246
+ }
247
+
248
+ const content = await this.readFile(gptTmplPath);
249
+ return this.parseKerberosPolicy(content);
250
+ } catch (error) {
251
+ logger.warn('Failed to read Kerberos policy from SYSVOL', { error, path: gptTmplPath });
252
+ return null;
253
+ }
254
+ }
255
+
256
+ /**
257
+ * Parse Kerberos policy from GptTmpl.inf content
258
+ */
259
+ private parseKerberosPolicy(content: string): KerberosPolicy {
260
+ const policy: KerberosPolicy = {
261
+ maxTicketAge: 10, // Default: 10 hours
262
+ maxRenewAge: 7, // Default: 7 days
263
+ maxServiceAge: 600, // Default: 600 minutes
264
+ maxClockSkew: 5, // Default: 5 minutes
265
+ ticketValidateClient: true,
266
+ };
267
+
268
+ // Find [Kerberos Policy] section
269
+ const lines = content.split(/\r?\n/);
270
+ let inKerberosSection = false;
271
+
272
+ for (const line of lines) {
273
+ const trimmedLine = line.trim();
274
+
275
+ // Check for section headers
276
+ if (trimmedLine.startsWith('[')) {
277
+ inKerberosSection = trimmedLine.toLowerCase() === '[kerberos policy]';
278
+ continue;
279
+ }
280
+
281
+ if (!inKerberosSection) continue;
282
+
283
+ // Parse key=value pairs
284
+ const match = trimmedLine.match(/^(\w+)\s*=\s*(.+)$/);
285
+ if (!match || !match[1] || !match[2]) continue;
286
+
287
+ const key = match[1];
288
+ const value = match[2];
289
+ const numValue = parseInt(value, 10);
290
+
291
+ switch (key.toLowerCase()) {
292
+ case 'maxticketage':
293
+ policy.maxTicketAge = numValue;
294
+ break;
295
+ case 'maxrenewage':
296
+ policy.maxRenewAge = numValue;
297
+ break;
298
+ case 'maxserviceage':
299
+ policy.maxServiceAge = numValue;
300
+ break;
301
+ case 'maxclockskew':
302
+ policy.maxClockSkew = numValue;
303
+ break;
304
+ case 'ticketvalidateclient':
305
+ policy.ticketValidateClient = numValue === 1;
306
+ break;
307
+ }
308
+ }
309
+
310
+ return policy;
311
+ }
312
+
313
+ /**
314
+ * Read GPO security settings from Default Domain Controllers Policy
315
+ * Reads GptTmpl.inf [Registry Values] section for LDAP signing, SMBv1, etc.
316
+ */
317
+ async readGpoSecuritySettings(domainDnsName: string): Promise<GpoSecuritySettings | null> {
318
+ // Default Domain Controllers Policy GUID
319
+ const DC_POLICY_GUID = '{6AC1786C-016F-11D2-945F-00C04FB984F9}';
320
+ const gptTmplPath = `${domainDnsName}/Policies/${DC_POLICY_GUID}/Machine/Microsoft/Windows NT/SecEdit/GptTmpl.inf`;
321
+
322
+ const settings: GpoSecuritySettings = {};
323
+
324
+ try {
325
+ // Read GptTmpl.inf for registry values from DC Policy
326
+ logger.debug('Reading GPO security settings', { path: gptTmplPath });
327
+
328
+ const dcPolicyExists = await this.exists(gptTmplPath);
329
+ if (dcPolicyExists) {
330
+ const content = await this.readFile(gptTmplPath);
331
+ this.parseRegistryValues(content, settings);
332
+ logger.debug('Parsed DC Policy GptTmpl.inf', { settings });
333
+ }
334
+
335
+ // Also check Default Domain Policy for additional settings
336
+ const domainPolicyPath = `${domainDnsName}/Policies/${DEFAULT_DOMAIN_POLICY_GUID}/Machine/Microsoft/Windows NT/SecEdit/GptTmpl.inf`;
337
+ const domainPolicyExists = await this.exists(domainPolicyPath);
338
+ if (domainPolicyExists) {
339
+ const domainContent = await this.readFile(domainPolicyPath);
340
+ this.parseRegistryValues(domainContent, settings);
341
+ logger.debug('Parsed Domain Policy GptTmpl.inf', { settings });
342
+ }
343
+
344
+ // Try to read audit.csv for audit policy
345
+ await this.readAuditPolicy(domainDnsName, DC_POLICY_GUID, settings);
346
+
347
+ // Try to read registry.pol for PowerShell logging
348
+ await this.readPowerShellLogging(domainDnsName, DC_POLICY_GUID, settings);
349
+
350
+ logger.info('Successfully fetched GPO security settings', {
351
+ hasLdapSigning: settings.ldapServerIntegrity !== undefined,
352
+ hasSmbSigning: settings.smbSigningRequired !== undefined,
353
+ hasAuditPolicy: settings.auditPolicies !== undefined,
354
+ hasPsLogging: settings.powershellLogging !== undefined,
355
+ });
356
+
357
+ return settings;
358
+ } catch (error) {
359
+ logger.warn('Failed to read GPO security settings', { error });
360
+ return null;
361
+ }
362
+ }
363
+
364
+ /**
365
+ * Parse [Registry Values] section from GptTmpl.inf
366
+ */
367
+ private parseRegistryValues(content: string, settings: GpoSecuritySettings): void {
368
+ const lines = content.split(/\r?\n/);
369
+ let inRegistrySection = false;
370
+
371
+ for (const line of lines) {
372
+ const trimmedLine = line.trim();
373
+
374
+ // Check for section headers
375
+ if (trimmedLine.startsWith('[')) {
376
+ inRegistrySection = trimmedLine.toLowerCase() === '[registry values]';
377
+ continue;
378
+ }
379
+
380
+ if (!inRegistrySection) continue;
381
+
382
+ // Registry format: MACHINE\path\to\key=type,value
383
+ // Example: MACHINE\System\CurrentControlSet\Services\NTDS\Parameters\LDAPServerIntegrity=4,2
384
+ const match = trimmedLine.match(/^MACHINE\\(.+?)=(\d+),(.+)$/i);
385
+ if (!match || !match[1] || !match[3]) continue;
386
+
387
+ const keyPath = match[1].toLowerCase();
388
+ const value = match[3];
389
+
390
+ // LDAP Server Signing
391
+ if (keyPath.includes('ntds\\parameters\\ldapserverintegrity')) {
392
+ settings.ldapServerIntegrity = parseInt(value, 10);
393
+ }
394
+
395
+ // LDAP Channel Binding
396
+ if (keyPath.includes('ntds\\parameters\\ldapenforcechannelbinding')) {
397
+ settings.ldapChannelBinding = parseInt(value, 10);
398
+ }
399
+
400
+ // SMBv1 Server
401
+ if (keyPath.includes('lanmanserver\\parameters\\smb1')) {
402
+ settings.smbv1ServerEnabled = value === '1';
403
+ }
404
+
405
+ // SMBv1 Client (LanmanWorkstation)
406
+ if (keyPath.includes('lanmanworkstation\\parameters\\smb1')) {
407
+ settings.smbv1ClientEnabled = value === '1';
408
+ }
409
+
410
+ // Alternative SMBv1 check via MrxSmb10
411
+ if (keyPath.includes('mrxsmb10\\start')) {
412
+ // Start=4 means disabled, anything else means enabled
413
+ settings.smbv1ClientEnabled = value !== '4';
414
+ }
415
+
416
+ // SMB Server Signing (RequireSecuritySignature)
417
+ // MACHINE\System\CurrentControlSet\Services\LanManServer\Parameters\RequireSecuritySignature=4,1
418
+ if (keyPath.includes('lanmanserver\\parameters\\requiresecuritysignature')) {
419
+ settings.smbSigningRequired = value === '1';
420
+ }
421
+
422
+ // SMB Client Signing (RequireSecuritySignature)
423
+ // MACHINE\System\CurrentControlSet\Services\LanManWorkstation\Parameters\RequireSecuritySignature=4,1
424
+ if (keyPath.includes('lanmanworkstation\\parameters\\requiresecuritysignature')) {
425
+ settings.smbClientSigningRequired = value === '1';
426
+ }
427
+ }
428
+ }
429
+
430
+ /**
431
+ * Read audit policy from audit.csv
432
+ */
433
+ private async readAuditPolicy(
434
+ domainDnsName: string,
435
+ gpoGuid: string,
436
+ settings: GpoSecuritySettings
437
+ ): Promise<void> {
438
+ const auditPath = `${domainDnsName}/Policies/${gpoGuid}/Machine/Microsoft/Windows NT/Audit/audit.csv`;
439
+
440
+ try {
441
+ const exists = await this.exists(auditPath);
442
+ if (!exists) return;
443
+
444
+ const content = await this.readFile(auditPath);
445
+ settings.auditPolicies = this.parseAuditCsv(content);
446
+ } catch (error) {
447
+ logger.debug('Failed to read audit.csv', { error });
448
+ }
449
+ }
450
+
451
+ /**
452
+ * Parse audit.csv content
453
+ * Format: Machine Name,Policy Target,Subcategory,Subcategory GUID,Inclusion Setting,Exclusion Setting,Setting Value
454
+ */
455
+ private parseAuditCsv(content: string): GpoSecuritySettings['auditPolicies'] {
456
+ const policies: NonNullable<GpoSecuritySettings['auditPolicies']> = [];
457
+ const lines = content.split(/\r?\n/);
458
+
459
+ // Skip header line
460
+ for (let i = 1; i < lines.length; i++) {
461
+ const line = lines[i];
462
+ if (!line) continue;
463
+
464
+ const trimmedLine = line.trim();
465
+ if (!trimmedLine) continue;
466
+
467
+ // CSV parsing (simple - assumes no commas in values)
468
+ const parts = trimmedLine.split(',');
469
+ if (parts.length < 7) continue;
470
+
471
+ const subcategory = parts[2];
472
+ const settingValue = parts[6];
473
+
474
+ if (!subcategory || !settingValue) continue;
475
+
476
+ // Setting values: 0=No Auditing, 1=Success, 2=Failure, 3=Success and Failure
477
+ const value = parseInt(settingValue, 10);
478
+
479
+ // Map subcategories to categories
480
+ const category = this.getAuditCategory(subcategory);
481
+
482
+ policies.push({
483
+ category,
484
+ subcategory,
485
+ success: (value & 1) !== 0,
486
+ failure: (value & 2) !== 0,
487
+ });
488
+ }
489
+
490
+ return policies;
491
+ }
492
+
493
+ /**
494
+ * Map audit subcategory to category
495
+ */
496
+ private getAuditCategory(subcategory: string): string {
497
+ const categoryMap: Record<string, string> = {
498
+ 'Credential Validation': 'Account Logon',
499
+ 'Kerberos Authentication Service': 'Account Logon',
500
+ 'Kerberos Service Ticket Operations': 'Account Logon',
501
+ 'Computer Account Management': 'Account Management',
502
+ 'Security Group Management': 'Account Management',
503
+ 'User Account Management': 'Account Management',
504
+ 'Logon': 'Logon/Logoff',
505
+ 'Logoff': 'Logon/Logoff',
506
+ 'Special Logon': 'Logon/Logoff',
507
+ 'File System': 'Object Access',
508
+ 'Registry': 'Object Access',
509
+ 'Kernel Object': 'Object Access',
510
+ 'Audit Policy Change': 'Policy Change',
511
+ 'Authentication Policy Change': 'Policy Change',
512
+ 'Sensitive Privilege Use': 'Privilege Use',
513
+ 'Security State Change': 'System',
514
+ 'Security System Extension': 'System',
515
+ 'System Integrity': 'System',
516
+ };
517
+
518
+ for (const [sub, cat] of Object.entries(categoryMap)) {
519
+ if (subcategory.toLowerCase().includes(sub.toLowerCase())) {
520
+ return cat;
521
+ }
522
+ }
523
+ return 'Other';
524
+ }
525
+
526
+ /**
527
+ * Read PowerShell logging settings from registry.pol
528
+ * Note: registry.pol is a binary format, this is a simplified implementation
529
+ */
530
+ private async readPowerShellLogging(
531
+ domainDnsName: string,
532
+ gpoGuid: string,
533
+ settings: GpoSecuritySettings
534
+ ): Promise<void> {
535
+ const registryPolPath = `${domainDnsName}/Policies/${gpoGuid}/Machine/Registry.pol`;
536
+
537
+ try {
538
+ const exists = await this.exists(registryPolPath);
539
+ if (!exists) return;
540
+
541
+ // Registry.pol is a binary format
542
+ // For simplicity, we read as buffer and search for known strings
543
+ const content = await this.readBinaryFile(registryPolPath);
544
+ settings.powershellLogging = this.parsePowerShellLogging(content);
545
+ } catch (error) {
546
+ logger.debug('Failed to read registry.pol', { error });
547
+ }
548
+ }
549
+
550
+ /**
551
+ * Parse PowerShell logging settings from registry.pol binary content
552
+ * Registry.pol format: PReg header + entries
553
+ * Each entry: [key;value;type;size;data]
554
+ */
555
+ private parsePowerShellLogging(content: Buffer): GpoSecuritySettings['powershellLogging'] {
556
+ const result = {
557
+ moduleLogging: false,
558
+ scriptBlockLogging: false,
559
+ transcription: false,
560
+ };
561
+
562
+ try {
563
+ // Convert to string for simple pattern matching
564
+ // This is a simplified approach - proper parsing would use the binary format
565
+ const textContent = content.toString('utf16le');
566
+
567
+ // Look for PowerShell logging registry keys
568
+ // ScriptBlockLogging: Software\Policies\Microsoft\Windows\PowerShell\ScriptBlockLogging\EnableScriptBlockLogging
569
+ // ModuleLogging: Software\Policies\Microsoft\Windows\PowerShell\ModuleLogging\EnableModuleLogging
570
+ // Transcription: Software\Policies\Microsoft\Windows\PowerShell\Transcription\EnableTranscripting
571
+
572
+ if (textContent.includes('EnableScriptBlockLogging') && textContent.includes('\x01\x00\x00\x00')) {
573
+ result.scriptBlockLogging = true;
574
+ }
575
+
576
+ if (textContent.includes('EnableModuleLogging') && textContent.includes('\x01\x00\x00\x00')) {
577
+ result.moduleLogging = true;
578
+ }
579
+
580
+ if (textContent.includes('EnableTranscripting') && textContent.includes('\x01\x00\x00\x00')) {
581
+ result.transcription = true;
582
+ }
583
+ } catch (error) {
584
+ logger.debug('Failed to parse registry.pol', { error });
585
+ }
586
+
587
+ return result;
588
+ }
589
+
590
+ /**
591
+ * Test SMB connection using smbclient
592
+ */
593
+ async testConnection(): Promise<{ success: boolean; message: string }> {
594
+ const timeout = this.config.timeout || 15000;
595
+
596
+ const cmd = `${this.buildSmbCommand()} 'ls'`;
597
+
598
+ try {
599
+ await execAsync(cmd, { timeout });
600
+ return {
601
+ success: true,
602
+ message: 'SMB connection successful',
603
+ };
604
+ } catch (error) {
605
+ const message = error instanceof Error ? error.message : 'Unknown error';
606
+ return {
607
+ success: false,
608
+ message: `SMB connection failed: ${message}`,
609
+ };
610
+ }
611
+ }
612
+ }
613
+
614
+ /**
615
+ * Formatted Kerberos policy with isDefault flag
616
+ */
617
+ export interface FormattedKerberosPolicy {
618
+ maxTicketAge: string;
619
+ maxRenewAge: string;
620
+ maxServiceAge: string;
621
+ maxClockSkew: string;
622
+ ticketValidateClient: boolean;
623
+ isDefault: boolean;
624
+ }
625
+
626
+ /**
627
+ * Format Kerberos policy values to human-readable strings
628
+ */
629
+ export function formatKerberosPolicy(policy: KerberosPolicy, isDefault = false): FormattedKerberosPolicy {
630
+ return {
631
+ maxTicketAge: `${policy.maxTicketAge} hours`,
632
+ maxRenewAge: `${policy.maxRenewAge} days`,
633
+ maxServiceAge: `${policy.maxServiceAge} min`,
634
+ maxClockSkew: `${policy.maxClockSkew} min`,
635
+ ticketValidateClient: policy.ticketValidateClient,
636
+ isDefault,
637
+ };
638
+ }
639
+
640
+ /**
641
+ * Get Windows default Kerberos policy values
642
+ * These are the defaults when no GPO customization is applied
643
+ */
644
+ export function getDefaultKerberosPolicy(): FormattedKerberosPolicy {
645
+ return {
646
+ maxTicketAge: '10 hours',
647
+ maxRenewAge: '7 days',
648
+ maxServiceAge: '600 min',
649
+ maxClockSkew: '5 min',
650
+ ticketValidateClient: true,
651
+ isDefault: true,
652
+ };
653
+ }
package/src/server.ts ADDED
@@ -0,0 +1,60 @@
1
+ import { createApp } from './app';
2
+ import { getConfig } from './config';
3
+ import { logInfo, logError } from './utils/logger';
4
+ import { MigrationRunner } from './data/migrations/migration.runner';
5
+ import { DIContainer } from './container';
6
+ import { version } from '../package.json';
7
+
8
+ /**
9
+ * Server Entry Point
10
+ * Bootstraps the application and starts the HTTP server
11
+ */
12
+
13
+ async function startServer(): Promise<void> {
14
+ try {
15
+ // Load configuration
16
+ const config = getConfig();
17
+ logInfo('Configuration loaded successfully', {
18
+ port: config.server.port,
19
+ nodeEnv: config.server.nodeEnv,
20
+ });
21
+
22
+ // Run database migrations
23
+ await MigrationRunner.runMigrations(config.database.path);
24
+ logInfo('Database migrations completed');
25
+
26
+ // Initialize dependency injection container
27
+ await DIContainer.initialize();
28
+ logInfo('DI container initialized');
29
+
30
+ // Create Express app
31
+ const app = createApp();
32
+
33
+ // Start HTTP server
34
+ const server = app.listen(config.server.port, () => {
35
+ logInfo('Server started successfully', {
36
+ port: config.server.port,
37
+ nodeEnv: config.server.nodeEnv,
38
+ version,
39
+ });
40
+ });
41
+
42
+ // Graceful shutdown
43
+ const shutdown = (): void => {
44
+ logInfo('Shutdown signal received, closing server...');
45
+ server.close(() => {
46
+ logInfo('Server closed successfully');
47
+ process.exit(0);
48
+ });
49
+ };
50
+
51
+ process.on('SIGTERM', shutdown);
52
+ process.on('SIGINT', shutdown);
53
+ } catch (error) {
54
+ logError('Failed to start server', error as Error);
55
+ process.exit(1);
56
+ }
57
+ }
58
+
59
+ // Start the server
60
+ void startServer();
File without changes