moriarty-project 0.1.6__py3-none-any.whl

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 (416) hide show
  1. moriarty/__init__.py +5 -0
  2. moriarty/adapters/__init__.py +0 -0
  3. moriarty/agent/__init__.py +0 -0
  4. moriarty/assets/modules/.gitkeep +0 -0
  5. moriarty/assets/modules/asia/douban.yaml +19 -0
  6. moriarty/assets/modules/asia/kakao.yaml +19 -0
  7. moriarty/assets/modules/asia/line.yaml +19 -0
  8. moriarty/assets/modules/asia/mixi.yaml +19 -0
  9. moriarty/assets/modules/asia/naver.yaml +19 -0
  10. moriarty/assets/modules/asia/qq.yaml +19 -0
  11. moriarty/assets/modules/asia/vk.yaml +19 -0
  12. moriarty/assets/modules/asia/wechat.yaml +19 -0
  13. moriarty/assets/modules/asia/weibo.yaml +19 -0
  14. moriarty/assets/modules/asia/xiaohongshu.yaml +19 -0
  15. moriarty/assets/modules/behance.yaml +47 -0
  16. moriarty/assets/modules/business/crunchbase.yaml +27 -0
  17. moriarty/assets/modules/business/fiverr.yaml +32 -0
  18. moriarty/assets/modules/business/freelancer.yaml +27 -0
  19. moriarty/assets/modules/business/glassdoor.yaml +27 -0
  20. moriarty/assets/modules/business/guru.yaml +26 -0
  21. moriarty/assets/modules/business/indeed.yaml +25 -0
  22. moriarty/assets/modules/business/monster.yaml +25 -0
  23. moriarty/assets/modules/business/peopleperhour.yaml +26 -0
  24. moriarty/assets/modules/business/toptal.yaml +28 -0
  25. moriarty/assets/modules/business/upwork.yaml +27 -0
  26. moriarty/assets/modules/business/ziprecruiter.yaml +25 -0
  27. moriarty/assets/modules/content/buymeacoffee.yaml +27 -0
  28. moriarty/assets/modules/content/gumroad.yaml +27 -0
  29. moriarty/assets/modules/content/ko-fi.yaml +32 -0
  30. moriarty/assets/modules/content/onlyfans.yaml +27 -0
  31. moriarty/assets/modules/content/patreon.yaml +33 -0
  32. moriarty/assets/modules/content/substack.yaml +32 -0
  33. moriarty/assets/modules/creative/500px.yaml +31 -0
  34. moriarty/assets/modules/creative/artstation.yaml +33 -0
  35. moriarty/assets/modules/creative/deviantart.yaml +32 -0
  36. moriarty/assets/modules/creative/flickr.yaml +31 -0
  37. moriarty/assets/modules/creative/pexels.yaml +26 -0
  38. moriarty/assets/modules/creative/unsplash.yaml +26 -0
  39. moriarty/assets/modules/creative/vimeo.yaml +31 -0
  40. moriarty/assets/modules/crypto/binance.yaml +27 -0
  41. moriarty/assets/modules/crypto/bitcointalk.yaml +33 -0
  42. moriarty/assets/modules/crypto/coinbase.yaml +26 -0
  43. moriarty/assets/modules/crypto/etherscan.yaml +32 -0
  44. moriarty/assets/modules/crypto/foundation.yaml +28 -0
  45. moriarty/assets/modules/crypto/kraken.yaml +27 -0
  46. moriarty/assets/modules/crypto/mirror.yaml +27 -0
  47. moriarty/assets/modules/crypto/niftygateway.yaml +26 -0
  48. moriarty/assets/modules/crypto/opensea.yaml +32 -0
  49. moriarty/assets/modules/crypto/rarible.yaml +27 -0
  50. moriarty/assets/modules/crypto/superrare.yaml +29 -0
  51. moriarty/assets/modules/dating/bumble.yaml +25 -0
  52. moriarty/assets/modules/dating/grindr.yaml +27 -0
  53. moriarty/assets/modules/dating/happn.yaml +25 -0
  54. moriarty/assets/modules/dating/her.yaml +27 -0
  55. moriarty/assets/modules/dating/hinge.yaml +25 -0
  56. moriarty/assets/modules/dating/match.yaml +25 -0
  57. moriarty/assets/modules/dating/meetme.yaml +27 -0
  58. moriarty/assets/modules/dating/okcupid.yaml +25 -0
  59. moriarty/assets/modules/dating/pof.yaml +25 -0
  60. moriarty/assets/modules/dating/tinder.yaml +25 -0
  61. moriarty/assets/modules/dating-nsfw/adultfriendfinder.yaml +28 -0
  62. moriarty/assets/modules/dating-nsfw/ashley-madison.yaml +26 -0
  63. moriarty/assets/modules/design/adobe-portfolio.yaml +27 -0
  64. moriarty/assets/modules/design/carbonmade.yaml +27 -0
  65. moriarty/assets/modules/design/cgsociety.yaml +27 -0
  66. moriarty/assets/modules/design/coroflot.yaml +27 -0
  67. moriarty/assets/modules/design/figma.yaml +27 -0
  68. moriarty/assets/modules/design/sketch.yaml +26 -0
  69. moriarty/assets/modules/dev/bitbucket.yaml +35 -0
  70. moriarty/assets/modules/dev/codeforces.yaml +32 -0
  71. moriarty/assets/modules/dev/codepen.yaml +34 -0
  72. moriarty/assets/modules/dev/hackerone.yaml +32 -0
  73. moriarty/assets/modules/dev/hackthebox.yaml +27 -0
  74. moriarty/assets/modules/dev/huggingface.yaml +27 -0
  75. moriarty/assets/modules/dev/kaggle.yaml +32 -0
  76. moriarty/assets/modules/dev/leetcode.yaml +32 -0
  77. moriarty/assets/modules/dev/replit.yaml +31 -0
  78. moriarty/assets/modules/dribbble.yaml +53 -0
  79. moriarty/assets/modules/ecommerce/etsy.yaml +32 -0
  80. moriarty/assets/modules/education/duolingo.yaml +32 -0
  81. moriarty/assets/modules/education/edx.yaml +26 -0
  82. moriarty/assets/modules/education/khanacademy.yaml +26 -0
  83. moriarty/assets/modules/education/lynda.yaml +27 -0
  84. moriarty/assets/modules/education/memrise.yaml +27 -0
  85. moriarty/assets/modules/education/pluralsight.yaml +27 -0
  86. moriarty/assets/modules/education/skillshare.yaml +27 -0
  87. moriarty/assets/modules/education/udacity.yaml +27 -0
  88. moriarty/assets/modules/email/github_email.yaml +40 -0
  89. moriarty/assets/modules/email/gravatar.yaml +23 -0
  90. moriarty/assets/modules/europe/badoo.yaml +19 -0
  91. moriarty/assets/modules/europe/lovoo.yaml +19 -0
  92. moriarty/assets/modules/europe/myspace.yaml +19 -0
  93. moriarty/assets/modules/europe/netlog.yaml +19 -0
  94. moriarty/assets/modules/europe/ok.yaml +19 -0
  95. moriarty/assets/modules/europe/skyrock.yaml +19 -0
  96. moriarty/assets/modules/europe/studivz.yaml +19 -0
  97. moriarty/assets/modules/europe/tuenti.yaml +19 -0
  98. moriarty/assets/modules/europe/viadeo.yaml +19 -0
  99. moriarty/assets/modules/europe/xing.yaml +19 -0
  100. moriarty/assets/modules/fitness/fitbit.yaml +27 -0
  101. moriarty/assets/modules/fitness/garmin.yaml +27 -0
  102. moriarty/assets/modules/fitness/myfitnesspal.yaml +27 -0
  103. moriarty/assets/modules/fitness/strava.yaml +33 -0
  104. moriarty/assets/modules/fitness/zwift.yaml +28 -0
  105. moriarty/assets/modules/food/allrecipes.yaml +27 -0
  106. moriarty/assets/modules/food/tasty.yaml +27 -0
  107. moriarty/assets/modules/food/yelp.yaml +32 -0
  108. moriarty/assets/modules/food/zomato.yaml +28 -0
  109. moriarty/assets/modules/forums/4chan.yaml +26 -0
  110. moriarty/assets/modules/forums/8kun.yaml +26 -0
  111. moriarty/assets/modules/forums/9gag.yaml +26 -0
  112. moriarty/assets/modules/forums/discourse.yaml +26 -0
  113. moriarty/assets/modules/forums/disqus.yaml +31 -0
  114. moriarty/assets/modules/forums/hackernews.yaml +32 -0
  115. moriarty/assets/modules/forums/launchpad.yaml +27 -0
  116. moriarty/assets/modules/forums/phpbb.yaml +25 -0
  117. moriarty/assets/modules/forums/quora.yaml +32 -0
  118. moriarty/assets/modules/forums/serverfault.yaml +27 -0
  119. moriarty/assets/modules/forums/slashdot.yaml +28 -0
  120. moriarty/assets/modules/forums/stackexchange.yaml +32 -0
  121. moriarty/assets/modules/forums/superuser.yaml +27 -0
  122. moriarty/assets/modules/forums/vbulletin.yaml +25 -0
  123. moriarty/assets/modules/forums/xenforo.yaml +25 -0
  124. moriarty/assets/modules/forums-nsfw/kiwifarms.yaml +25 -0
  125. moriarty/assets/modules/forums-nsfw/lolcow.yaml +26 -0
  126. moriarty/assets/modules/gaming/apextracker.yaml +27 -0
  127. moriarty/assets/modules/gaming/battlenet.yaml +26 -0
  128. moriarty/assets/modules/gaming/chess.yaml +30 -0
  129. moriarty/assets/modules/gaming/discord-public.yaml +27 -0
  130. moriarty/assets/modules/gaming/dotabuff.yaml +32 -0
  131. moriarty/assets/modules/gaming/epicgames.yaml +25 -0
  132. moriarty/assets/modules/gaming/faceit.yaml +33 -0
  133. moriarty/assets/modules/gaming/fortnitetracker.yaml +32 -0
  134. moriarty/assets/modules/gaming/gog.yaml +26 -0
  135. moriarty/assets/modules/gaming/itch.yaml +32 -0
  136. moriarty/assets/modules/gaming/kongregate.yaml +25 -0
  137. moriarty/assets/modules/gaming/minecraft.yaml +31 -0
  138. moriarty/assets/modules/gaming/opgg.yaml +32 -0
  139. moriarty/assets/modules/gaming/origin.yaml +26 -0
  140. moriarty/assets/modules/gaming/playstation.yaml +30 -0
  141. moriarty/assets/modules/gaming/roblox.yaml +31 -0
  142. moriarty/assets/modules/gaming/xbox.yaml +25 -0
  143. moriarty/assets/modules/github.yaml +68 -0
  144. moriarty/assets/modules/gitlab.yaml +60 -0
  145. moriarty/assets/modules/instagram.yaml +48 -0
  146. moriarty/assets/modules/latam/fotolog.yaml +27 -0
  147. moriarty/assets/modules/latam/orkut.yaml +26 -0
  148. moriarty/assets/modules/latam/taringa.yaml +27 -0
  149. moriarty/assets/modules/learning/coursera.yaml +26 -0
  150. moriarty/assets/modules/learning/udemy.yaml +26 -0
  151. moriarty/assets/modules/linkedin.yaml +40 -0
  152. moriarty/assets/modules/marketplaces/depop.yaml +28 -0
  153. moriarty/assets/modules/marketplaces/ebay.yaml +32 -0
  154. moriarty/assets/modules/marketplaces/grailed.yaml +27 -0
  155. moriarty/assets/modules/marketplaces/mercari.yaml +26 -0
  156. moriarty/assets/modules/marketplaces/poshmark.yaml +27 -0
  157. moriarty/assets/modules/marketplaces/reverb.yaml +27 -0
  158. moriarty/assets/modules/marketplaces/vinted.yaml +28 -0
  159. moriarty/assets/modules/medium.yaml +44 -0
  160. moriarty/assets/modules/music/audiomack.yaml +26 -0
  161. moriarty/assets/modules/music/bandcamp.yaml +30 -0
  162. moriarty/assets/modules/music/beatport.yaml +28 -0
  163. moriarty/assets/modules/music/deezer.yaml +26 -0
  164. moriarty/assets/modules/music/discogs.yaml +32 -0
  165. moriarty/assets/modules/music/genius.yaml +26 -0
  166. moriarty/assets/modules/music/lastfm.yaml +30 -0
  167. moriarty/assets/modules/music/mixcloud.yaml +26 -0
  168. moriarty/assets/modules/music/reverbnation.yaml +31 -0
  169. moriarty/assets/modules/music/soundcloud.yaml +31 -0
  170. moriarty/assets/modules/music/spotify.yaml +26 -0
  171. moriarty/assets/modules/music/tidal.yaml +26 -0
  172. moriarty/assets/modules/nsfw/adultwork.yaml +27 -0
  173. moriarty/assets/modules/nsfw/bongacams.yaml +28 -0
  174. moriarty/assets/modules/nsfw/cam4.yaml +28 -0
  175. moriarty/assets/modules/nsfw/chaturbate.yaml +28 -0
  176. moriarty/assets/modules/nsfw/clips4sale.yaml +27 -0
  177. moriarty/assets/modules/nsfw/extralunchmoney.yaml +27 -0
  178. moriarty/assets/modules/nsfw/fansly.yaml +28 -0
  179. moriarty/assets/modules/nsfw/fetlife.yaml +28 -0
  180. moriarty/assets/modules/nsfw/iwantclips.yaml +27 -0
  181. moriarty/assets/modules/nsfw/justforfans.yaml +28 -0
  182. moriarty/assets/modules/nsfw/loyalfans.yaml +28 -0
  183. moriarty/assets/modules/nsfw/manyvids.yaml +27 -0
  184. moriarty/assets/modules/nsfw/myfreecams.yaml +28 -0
  185. moriarty/assets/modules/nsfw/niteflirt.yaml +26 -0
  186. moriarty/assets/modules/nsfw/pornhub.yaml +32 -0
  187. moriarty/assets/modules/nsfw/redtube.yaml +27 -0
  188. moriarty/assets/modules/nsfw/stripchat.yaml +28 -0
  189. moriarty/assets/modules/nsfw/xhamster.yaml +27 -0
  190. moriarty/assets/modules/nsfw/xvideos.yaml +27 -0
  191. moriarty/assets/modules/nsfw/youporn.yaml +27 -0
  192. moriarty/assets/modules/photography/eyeem.yaml +25 -0
  193. moriarty/assets/modules/photography/fotki.yaml +25 -0
  194. moriarty/assets/modules/photography/photobucket.yaml +26 -0
  195. moriarty/assets/modules/photography/smugmug.yaml +25 -0
  196. moriarty/assets/modules/photography/vsco.yaml +27 -0
  197. moriarty/assets/modules/pinterest.yaml +40 -0
  198. moriarty/assets/modules/podcasts/anchor.yaml +26 -0
  199. moriarty/assets/modules/podcasts/castbox.yaml +26 -0
  200. moriarty/assets/modules/podcasts/podbean.yaml +26 -0
  201. moriarty/assets/modules/professional/about.yaml +31 -0
  202. moriarty/assets/modules/professional/academia.yaml +27 -0
  203. moriarty/assets/modules/professional/angellist.yaml +27 -0
  204. moriarty/assets/modules/professional/calendly.yaml +26 -0
  205. moriarty/assets/modules/professional/issuu.yaml +27 -0
  206. moriarty/assets/modules/professional/mendeley.yaml +27 -0
  207. moriarty/assets/modules/professional/notion.yaml +27 -0
  208. moriarty/assets/modules/professional/orcid.yaml +27 -0
  209. moriarty/assets/modules/professional/producthunt.yaml +31 -0
  210. moriarty/assets/modules/professional/researchgate.yaml +32 -0
  211. moriarty/assets/modules/professional/scribd.yaml +27 -0
  212. moriarty/assets/modules/professional/slideshare.yaml +31 -0
  213. moriarty/assets/modules/professional/trello.yaml +26 -0
  214. moriarty/assets/modules/professional/typeform.yaml +27 -0
  215. moriarty/assets/modules/reddit.yaml +46 -0
  216. moriarty/assets/modules/regional/amino.yaml +27 -0
  217. moriarty/assets/modules/regional/ask-fm.yaml +32 -0
  218. moriarty/assets/modules/regional/babycenter.yaml +26 -0
  219. moriarty/assets/modules/regional/cafemom.yaml +27 -0
  220. moriarty/assets/modules/regional/care2.yaml +27 -0
  221. moriarty/assets/modules/regional/diaspora.yaml +26 -0
  222. moriarty/assets/modules/regional/ello.yaml +27 -0
  223. moriarty/assets/modules/regional/gaia.yaml +27 -0
  224. moriarty/assets/modules/regional/habbo.yaml +27 -0
  225. moriarty/assets/modules/regional/imvu.yaml +27 -0
  226. moriarty/assets/modules/regional/lemmy.yaml +27 -0
  227. moriarty/assets/modules/regional/peertube.yaml +26 -0
  228. moriarty/assets/modules/regional/pixelfed.yaml +27 -0
  229. moriarty/assets/modules/regional/plurk.yaml +26 -0
  230. moriarty/assets/modules/regional/recroom.yaml +27 -0
  231. moriarty/assets/modules/regional/secondlife.yaml +26 -0
  232. moriarty/assets/modules/regional/vine-archive.yaml +27 -0
  233. moriarty/assets/modules/regional/vrchat.yaml +27 -0
  234. moriarty/assets/modules/regional/weheartit.yaml +27 -0
  235. moriarty/assets/modules/social/anilist.yaml +27 -0
  236. moriarty/assets/modules/social/beacons.yaml +26 -0
  237. moriarty/assets/modules/social/blogger.yaml +27 -0
  238. moriarty/assets/modules/social/crunchyroll.yaml +27 -0
  239. moriarty/assets/modules/social/discord.yaml +27 -0
  240. moriarty/assets/modules/social/dreamwidth.yaml +26 -0
  241. moriarty/assets/modules/social/facebook.yaml +34 -0
  242. moriarty/assets/modules/social/goodreads.yaml +32 -0
  243. moriarty/assets/modules/social/imdb.yaml +27 -0
  244. moriarty/assets/modules/social/kitsu.yaml +27 -0
  245. moriarty/assets/modules/social/letterboxd.yaml +32 -0
  246. moriarty/assets/modules/social/linktree.yaml +26 -0
  247. moriarty/assets/modules/social/livejournal.yaml +27 -0
  248. moriarty/assets/modules/social/mastodon.yaml +30 -0
  249. moriarty/assets/modules/social/minds.yaml +25 -0
  250. moriarty/assets/modules/social/myanimelist.yaml +32 -0
  251. moriarty/assets/modules/social/ravelry.yaml +27 -0
  252. moriarty/assets/modules/social/snapchat.yaml +25 -0
  253. moriarty/assets/modules/social/telegram.yaml +35 -0
  254. moriarty/assets/modules/social/tiktok.yaml +35 -0
  255. moriarty/assets/modules/social/trakt.yaml +28 -0
  256. moriarty/assets/modules/social/wattpad.yaml +32 -0
  257. moriarty/assets/modules/social/wordpress-com.yaml +26 -0
  258. moriarty/assets/modules/sports/espn.yaml +26 -0
  259. moriarty/assets/modules/sports/untappd.yaml +32 -0
  260. moriarty/assets/modules/stackoverflow.yaml +47 -0
  261. moriarty/assets/modules/steam.yaml +47 -0
  262. moriarty/assets/modules/streaming/caffeine.yaml +25 -0
  263. moriarty/assets/modules/streaming/dlive.yaml +27 -0
  264. moriarty/assets/modules/streaming/trovo.yaml +25 -0
  265. moriarty/assets/modules/travel/airbnb.yaml +26 -0
  266. moriarty/assets/modules/travel/booking.yaml +26 -0
  267. moriarty/assets/modules/travel/couchsurfing.yaml +27 -0
  268. moriarty/assets/modules/travel/tripadvisor.yaml +32 -0
  269. moriarty/assets/modules/tumblr.yaml +40 -0
  270. moriarty/assets/modules/twitch.yaml +48 -0
  271. moriarty/assets/modules/twitter.yaml +39 -0
  272. moriarty/assets/modules/youtube.yaml +42 -0
  273. moriarty/assets/templates/cves/CVE-2017-5638.yaml +27 -0
  274. moriarty/assets/templates/cves/CVE-2018-7600.yaml +30 -0
  275. moriarty/assets/templates/cves/CVE-2019-11510.yaml +27 -0
  276. moriarty/assets/templates/cves/CVE-2019-19781.yaml +28 -0
  277. moriarty/assets/templates/cves/CVE-2020-14882.yaml +28 -0
  278. moriarty/assets/templates/cves/CVE-2020-14883.yaml +29 -0
  279. moriarty/assets/templates/cves/CVE-2020-3452.yaml +28 -0
  280. moriarty/assets/templates/cves/CVE-2020-5902.yaml +28 -0
  281. moriarty/assets/templates/cves/CVE-2021-21972.yaml +31 -0
  282. moriarty/assets/templates/cves/CVE-2021-21985.yaml +28 -0
  283. moriarty/assets/templates/cves/CVE-2021-26084.yaml +30 -0
  284. moriarty/assets/templates/cves/CVE-2021-41773.yaml +25 -0
  285. moriarty/assets/templates/cves/CVE-2021-42013.yaml +28 -0
  286. moriarty/assets/templates/cves/CVE-2021-44228.yaml +27 -0
  287. moriarty/assets/templates/cves/CVE-2022-0185.yaml +21 -0
  288. moriarty/assets/templates/cves/CVE-2022-1388.yaml +36 -0
  289. moriarty/assets/templates/cves/CVE-2022-22954.yaml +28 -0
  290. moriarty/assets/templates/cves/CVE-2022-22965.yaml +31 -0
  291. moriarty/assets/templates/cves/CVE-2022-26134.yaml +27 -0
  292. moriarty/assets/templates/cves/CVE-2023-22515.yaml +27 -0
  293. moriarty/assets/templates/cves/CVE-2023-22527.yaml +29 -0
  294. moriarty/assets/templates/cves/CVE-2023-23752.yaml +33 -0
  295. moriarty/assets/templates/cves/CVE-2023-27350.yaml +27 -0
  296. moriarty/assets/templates/cves/CVE-2023-2868.yaml +27 -0
  297. moriarty/assets/templates/cves/CVE-2023-34362.yaml +27 -0
  298. moriarty/assets/templates/cves/CVE-2023-3519.yaml +28 -0
  299. moriarty/assets/templates/cves/CVE-2023-4966.yaml +27 -0
  300. moriarty/assets/templates/default-logins/admin-weak.yaml +40 -0
  301. moriarty/assets/templates/default-logins/wordpress-default.yaml +38 -0
  302. moriarty/assets/templates/exposures/aws-credentials.yaml +35 -0
  303. moriarty/assets/templates/exposures/backup-files.yaml +36 -0
  304. moriarty/assets/templates/exposures/database-files.yaml +34 -0
  305. moriarty/assets/templates/exposures/docker-exposed.yaml +31 -0
  306. moriarty/assets/templates/exposures/env-exposed.yaml +41 -0
  307. moriarty/assets/templates/exposures/git-exposed.yaml +41 -0
  308. moriarty/assets/templates/exposures/phpinfo.yaml +36 -0
  309. moriarty/assets/templates/exposures/svn-exposed.yaml +28 -0
  310. moriarty/assets/templates/fuzzing/api-endpoints.yaml +39 -0
  311. moriarty/assets/templates/fuzzing/common-files.yaml +37 -0
  312. moriarty/assets/templates/fuzzing/open-redirect-fuzz.yaml +35 -0
  313. moriarty/assets/templates/fuzzing/xss-search-fuzz.yaml +29 -0
  314. moriarty/assets/templates/git-config.yaml +18 -0
  315. moriarty/assets/templates/misconfigurations/cors-misconfiguration.yaml +30 -0
  316. moriarty/assets/templates/misconfigurations/debug-enabled.yaml +29 -0
  317. moriarty/assets/templates/misconfigurations/directory-listing.yaml +33 -0
  318. moriarty/assets/templates/misconfigurations/jwt-none-algo.yaml +30 -0
  319. moriarty/assets/templates/misconfigurations/ssl-tls-weak.yaml +23 -0
  320. moriarty/assets/templates/vulnerabilities/lfi-basic.yaml +31 -0
  321. moriarty/assets/templates/vulnerabilities/open-redirect.yaml +31 -0
  322. moriarty/assets/templates/vulnerabilities/rce-basic.yaml +34 -0
  323. moriarty/assets/templates/vulnerabilities/sqli-error.yaml +39 -0
  324. moriarty/assets/templates/vulnerabilities/ssrf-basic.yaml +31 -0
  325. moriarty/assets/templates/vulnerabilities/xss-reflected.yaml +38 -0
  326. moriarty/assets/templates/vulnerabilities/xxe-basic.yaml +30 -0
  327. moriarty/assets/wordlists/subdomains-1000.txt +1063 -0
  328. moriarty/cli/__init__.py +3 -0
  329. moriarty/cli/app.py +120 -0
  330. moriarty/cli/async_utils.py +19 -0
  331. moriarty/cli/dns.py +83 -0
  332. moriarty/cli/domain_cmd.py +572 -0
  333. moriarty/cli/email.py +383 -0
  334. moriarty/cli/email_investigate.py +224 -0
  335. moriarty/cli/intelligence.py +329 -0
  336. moriarty/cli/output.py +62 -0
  337. moriarty/cli/rdap.py +94 -0
  338. moriarty/cli/state.py +38 -0
  339. moriarty/cli/tls.py +91 -0
  340. moriarty/cli/user.py +227 -0
  341. moriarty/core/cache_backend.py +223 -0
  342. moriarty/core/config_manager.py +303 -0
  343. moriarty/correlator/__init__.py +0 -0
  344. moriarty/data/__init__.py +81 -0
  345. moriarty/data/ioc/__init__.py +142 -0
  346. moriarty/data/ioc/matcher.py +254 -0
  347. moriarty/data/ioc/types.py +267 -0
  348. moriarty/data/local_intelligence.py +507 -0
  349. moriarty/data/signature_loaders/__init__.py +103 -0
  350. moriarty/data/signature_loaders/base.py +54 -0
  351. moriarty/data/signature_loaders/ioc_feed.py +356 -0
  352. moriarty/data/signature_loaders/wappalyzer.py +112 -0
  353. moriarty/dsl/__init__.py +0 -0
  354. moriarty/dsl/loader.py +99 -0
  355. moriarty/dsl/schema.py +47 -0
  356. moriarty/export/__init__.py +0 -0
  357. moriarty/intelligence/__init__.py +27 -0
  358. moriarty/intelligence/__main__.py +150 -0
  359. moriarty/intelligence/config.py +395 -0
  360. moriarty/intelligence/ioc.py +267 -0
  361. moriarty/intelligence/signatures.py +550 -0
  362. moriarty/intelligence/storage.py +501 -0
  363. moriarty/interop/__init__.py +0 -0
  364. moriarty/logging/__init__.py +0 -0
  365. moriarty/logging/config.py +47 -0
  366. moriarty/models/__init__.py +16 -0
  367. moriarty/models/assertion.py +24 -0
  368. moriarty/models/entity.py +22 -0
  369. moriarty/models/evidence.py +37 -0
  370. moriarty/models/relation.py +24 -0
  371. moriarty/models/types.py +28 -0
  372. moriarty/modules/__init__.py +0 -0
  373. moriarty/modules/avatar_hash.py +184 -0
  374. moriarty/modules/directory_fuzzer.py +322 -0
  375. moriarty/modules/dns_scan.py +40 -0
  376. moriarty/modules/domain_scanner.py +620 -0
  377. moriarty/modules/email_check.py +98 -0
  378. moriarty/modules/email_investigate.py +267 -0
  379. moriarty/modules/email_security.py +274 -0
  380. moriarty/modules/googlemaps_lookup.py +106 -0
  381. moriarty/modules/headless_executor.py +201 -0
  382. moriarty/modules/orchestrator.py +60 -0
  383. moriarty/modules/passive_recon.py +444 -0
  384. moriarty/modules/phone_extractor.py +151 -0
  385. moriarty/modules/pipeline_orchestrator.py +726 -0
  386. moriarty/modules/port_scanner.py +129 -0
  387. moriarty/modules/rdap.py +61 -0
  388. moriarty/modules/rdap_extended.py +188 -0
  389. moriarty/modules/stealth_mode.py +610 -0
  390. moriarty/modules/subdomain_discovery.py +595 -0
  391. moriarty/modules/technology_profiler.py +361 -0
  392. moriarty/modules/template_executor.py +239 -0
  393. moriarty/modules/template_scanner.py +1048 -0
  394. moriarty/modules/tls_scan.py +46 -0
  395. moriarty/modules/tls_validator.py +188 -0
  396. moriarty/modules/vuln_scanner.py +483 -0
  397. moriarty/modules/waf_detector.py +585 -0
  398. moriarty/modules/wayback_discovery.py +234 -0
  399. moriarty/modules/web_crawler.py +163 -0
  400. moriarty/net/__init__.py +0 -0
  401. moriarty/net/dns_cache.py +175 -0
  402. moriarty/net/dns_client.py +188 -0
  403. moriarty/net/rdap_client.py +52 -0
  404. moriarty/net/smtp_client.py +114 -0
  405. moriarty/net/tls_client.py +111 -0
  406. moriarty/parsers/__init__.py +0 -0
  407. moriarty/parsers/html_parser.py +136 -0
  408. moriarty/tests/__init__.py +0 -0
  409. moriarty/tests/test_email_service.py +17 -0
  410. moriarty/tests/test_models.py +46 -0
  411. moriarty/tests/test_orchestrator.py +30 -0
  412. moriarty/tests/test_tls_client.py +18 -0
  413. moriarty_project-0.1.6.dist-info/METADATA +388 -0
  414. moriarty_project-0.1.6.dist-info/RECORD +418 -0
  415. moriarty_project-0.1.6.dist-info/WHEEL +4 -0
  416. moriarty_project-0.1.6.dist-info/entry_points.txt +2 -0
@@ -0,0 +1,329 @@
1
+ """Comandos para gerenciamento de inteligência local."""
2
+ from pathlib import Path
3
+ from typing import List, Optional, Dict, Any
4
+
5
+ import typer
6
+ from rich.console import Console
7
+ from rich.table import Table
8
+ from rich.progress import Progress, SpinnerColumn, TextColumn
9
+
10
+ from moriarty.data import (
11
+ get_local_intelligence,
12
+ IOC, IOCType, ThreatType,
13
+ load_iocs_from_file, save_iocs_to_file
14
+ )
15
+
16
+ app = typer.Typer(name="intel", help="🔍 Gerenciamento de inteligência local")
17
+ console = Console()
18
+
19
+ # Tipos de IOC suportados para autocompletar
20
+ IOC_TYPES = [t.value for t in IOCType]
21
+ THREAT_TYPES = [t.value for t in ThreatType]
22
+
23
+ # Configuração
24
+ DEFAULT_DATA_DIR = Path("~/.moriarty/data").expanduser()
25
+
26
+ def _get_intel():
27
+ """Retorna uma instância de LocalIntelligence."""
28
+ return get_local_intelligence()
29
+
30
+ @app.command("add")
31
+ def add_ioc(
32
+ value: str = typer.Argument(..., help="Valor do IOC"),
33
+ ioc_type: str = typer.Argument(..., help=f"Tipo do IOC: {', '.join(IOC_TYPES)}",
34
+ autocompletion=lambda: IOC_TYPES),
35
+ threat_type: str = typer.Option("unknown", "--threat", "-t",
36
+ help=f"Tipo de ameaça: {', '.join(THREAT_TYPES)}",
37
+ autocompletion=lambda: THREAT_TYPES),
38
+ source: str = typer.Option("manual", "--source", "-s",
39
+ help="Fonte da informação"),
40
+ confidence: int = typer.Option(50, "--confidence", "-c",
41
+ min=0, max=100,
42
+ help="Nível de confiança (0-100)"),
43
+ tags: str = typer.Option("", "--tags", help="Tags separadas por vírgula"),
44
+ notes: str = typer.Option("", "--notes", "-n", help="Notas adicionais"),
45
+ ):
46
+ """Adiciona um novo IOC à base de inteligência local."""
47
+ try:
48
+ # Valida o tipo de IOC
49
+ ioc_type_enum = IOCType(ioc_type.lower())
50
+ threat_type_enum = ThreatType(threat_type.lower())
51
+
52
+ # Cria o IOC
53
+ ioc = IOC(
54
+ value=value,
55
+ ioc_type=ioc_type_enum,
56
+ threat_type=threat_type_enum,
57
+ source=source,
58
+ confidence=confidence,
59
+ tags=[t.strip() for t in tags.split(",") if t.strip()],
60
+ metadata={"notes": notes} if notes else {}
61
+ )
62
+
63
+ # Adiciona ao sistema
64
+ intel = _get_intel()
65
+ if intel.add_ioc(ioc):
66
+ console.print(f"✅ [green]IOC adicionado com sucesso![/green]")
67
+ _display_ioc(ioc)
68
+ else:
69
+ console.print("[red]❌ Falha ao adicionar IOC.[/red]")
70
+
71
+ except ValueError as e:
72
+ console.print(f"[red]❌ Erro: {str(e)}[/red]")
73
+ raise typer.Exit(1)
74
+
75
+ @app.command("search")
76
+ def search_iocs(
77
+ query: str = typer.Argument(..., help="Termo de busca"),
78
+ limit: int = typer.Option(20, "--limit", "-l", help="Número máximo de resultados"),
79
+ output: Optional[Path] = typer.Option(None, "--output", "-o", help="Arquivo de saída"),
80
+ format: str = typer.Option("table", "--format", "-f",
81
+ help="Formato de saída: table, json, yaml, csv")
82
+ ):
83
+ """Busca IOCs na base de inteligência local."""
84
+ intel = _get_intel()
85
+
86
+ with Progress(
87
+ SpinnerColumn(),
88
+ TextColumn("[progress.description]{task.description}"),
89
+ transient=True,
90
+ ) as progress:
91
+ progress.add_task(description="Buscando IOCs...", total=None)
92
+ results = intel.search_iocs(query, limit=limit)
93
+
94
+ if not results:
95
+ console.print("[yellow]Nenhum IOC encontrado.[/yellow]")
96
+ return
97
+
98
+ # Formata a saída
99
+ if output:
100
+ _export_results(results, output, format)
101
+ console.print(f"✅ Resultados exportados para [cyan]{output}[/cyan]")
102
+ else:
103
+ if format == "table":
104
+ _display_iocs_table(results)
105
+ else:
106
+ _export_results(results, None, format)
107
+
108
+ @app.command("get")
109
+ def get_ioc(
110
+ ioc_type: str = typer.Argument(..., help=f"Tipo do IOC: {', '.join(IOC_TYPES)}",
111
+ autocompletion=lambda: IOC_TYPES),
112
+ value: str = typer.Argument(..., help="Valor do IOC"),
113
+ ):
114
+ """Obtém detalhes de um IOC específico."""
115
+ intel = _get_intel()
116
+
117
+ try:
118
+ ioc = intel.get_ioc(ioc_type, value)
119
+ if not ioc:
120
+ console.print("[yellow]IOC não encontrado.[/yellow]")
121
+ return
122
+
123
+ _display_ioc(ioc)
124
+
125
+ # Mostra IOCs relacionados
126
+ related = intel.get_related_iocs(ioc)
127
+ if any(related.values()):
128
+ console.print("\n[bold]Relacionados:[/bold]")
129
+ for rel_type, items in related.items():
130
+ if items:
131
+ console.print(f" [cyan]{rel_type.title()}:[/cyan]")
132
+ for item in items[:3]: # Mostra no máximo 3 itens por categoria
133
+ console.print(f" • {item.value} ([yellow]{item.threat_type.value}[/yellow])")
134
+ except ValueError as e:
135
+ console.print(f"[red]❌ Erro: {str(e)}[/red]")
136
+ raise typer.Exit(1)
137
+
138
+ @app.command("import")
139
+ def import_iocs(
140
+ file_path: Path = typer.Argument(..., help="Arquivo para importar"),
141
+ format: str = typer.Option("auto", "--format", "-f",
142
+ help="Formato do arquivo: auto, json, yaml, csv"),
143
+ ):
144
+ """Importa IOCs de um arquivo."""
145
+ if not file_path.exists():
146
+ console.print(f"[red]❌ Arquivo não encontrado: {file_path}[/red]")
147
+ raise typer.Exit(1)
148
+
149
+ try:
150
+ intel = _get_intel()
151
+ count = intel.import_iocs(file_path, format)
152
+ console.print(f"✅ [green]Importados {count} IOCs com sucesso![/green]")
153
+ except Exception as e:
154
+ console.print(f"[red]❌ Erro ao importar IOCs: {str(e)}[/red]")
155
+ raise typer.Exit(1)
156
+
157
+ @app.command("export")
158
+ def export_iocs(
159
+ output_file: Path = typer.Argument(..., help="Arquivo de saída"),
160
+ format: str = typer.Option("json", "--format", "-f",
161
+ help="Formato de saída: json, yaml, csv"),
162
+ query: Optional[str] = typer.Option(None, "--query", "-q",
163
+ help="Filtrar IOCs por termo"),
164
+ ):
165
+ """Exporta IOCs para um arquivo."""
166
+ try:
167
+ intel = _get_intel()
168
+
169
+ if query:
170
+ # Exporta apenas os IOCs que correspondem à consulta
171
+ iocs = intel.search_iocs(query, limit=1000) # Limite razoável
172
+ if not iocs:
173
+ console.print("[yellow]Nenhum IOC encontrado para exportar.[/yellow]")
174
+ return
175
+
176
+ # Converte para dicionários
177
+ ioc_dicts = [ioc.to_dict() for ioc in iocs]
178
+
179
+ # Salva no formato especificado
180
+ save_iocs_to_file(ioc_dicts, output_file, format)
181
+ else:
182
+ # Exporta todos os IOCs
183
+ intel.export_iocs(output_file, format)
184
+
185
+ console.print(f"✅ [green]IOCs exportados para [cyan]{output_file}[/cyan] no formato {format.upper()}[/green]")
186
+
187
+ except Exception as e:
188
+ console.print(f"[red]❌ Erro ao exportar IOCs: {str(e)}[/red]")
189
+ raise typer.Exit(1)
190
+
191
+ @app.command("update")
192
+ def update_signatures(
193
+ force: bool = typer.Option(False, "--force", "-f",
194
+ help="Forçar atualização mesmo se não for necessário")
195
+ ):
196
+ """Atualiza as assinaturas de ameaças a partir das fontes configuradas."""
197
+ with Progress(
198
+ SpinnerColumn(),
199
+ TextColumn("[progress.description]{task.description}"),
200
+ transient=True,
201
+ ) as progress:
202
+ progress.add_task(description="Atualizando assinaturas...", total=None)
203
+
204
+ try:
205
+ intel = _get_intel()
206
+ updated = intel.update_signatures(force=force)
207
+
208
+ if updated:
209
+ console.print("✅ [green]Assinaturas atualizadas com sucesso![/green]")
210
+ else:
211
+ console.print("ℹ️ [yellow]As assinaturas já estão atualizadas.[/yellow]")
212
+
213
+ except Exception as e:
214
+ console.print(f"[red]❌ Erro ao atualizar assinaturas: {str(e)}[/red]")
215
+ raise typer.Exit(1)
216
+
217
+ def _display_ioc(ioc: IOC):
218
+ """Exibe os detalhes de um IOC formatado."""
219
+ from rich.panel import Panel
220
+ from rich.text import Text
221
+ from rich.syntax import Syntax
222
+
223
+ # Cabeçalho com tipo e valor
224
+ header = Text()
225
+ header.append(f"{ioc.ioc_type.value.upper()}: ", style="bold")
226
+ header.append(ioc.value, style="bold green")
227
+
228
+ # Detalhes
229
+ details = []
230
+ details.append(f"[cyan]Ameaça:[/cyan] [yellow]{ioc.threat_type.value}[/yellow]")
231
+ details.append(f"[cyan]Fonte:[/cyan] {ioc.source}")
232
+ details.append(f"[cyan]Confiança:[/cyan] {ioc.confidence}/100")
233
+
234
+ if ioc.tags:
235
+ tags = ", ".join(f"[yellow]{t}[/yellow]" for t in ioc.tags)
236
+ details.append(f"[cyan]Tags:[/cyan] {tags}")
237
+
238
+ if ioc.first_seen:
239
+ details.append(f"[cyan]Primeira vez visto:[/cyan] {ioc.first_seen}")
240
+
241
+ if ioc.last_seen:
242
+ details.append(f"[cyan]Última vez visto:[/cyan] {ioc.last_seen}")
243
+
244
+ # Metadados adicionais
245
+ if ioc.metadata:
246
+ details.append("\n[bold]Metadados:[/bold]")
247
+ for k, v in ioc.metadata.items():
248
+ details.append(f" [cyan]{k}:[/cyan] {v}")
249
+
250
+ # Cria o painel
251
+ panel = Panel(
252
+ "\n".join(details),
253
+ title=header,
254
+ border_style="blue",
255
+ expand=False
256
+ )
257
+
258
+ console.print(panel)
259
+
260
+ def _display_iocs_table(iocs: List[IOC]):
261
+ """Exibe uma tabela com múltiplos IOCs."""
262
+ from rich.table import Table
263
+
264
+ table = Table(show_header=True, header_style="bold magenta")
265
+ table.add_column("Tipo", style="cyan")
266
+ table.add_column("Valor", style="green")
267
+ table.add_column("Ameaça", style="yellow")
268
+ table.add_column("Fonte")
269
+ table.add_column("Confiança", justify="right")
270
+ table.add_column("Tags")
271
+
272
+ for ioc in iocs:
273
+ table.add_row(
274
+ ioc.ioc_type.value.upper(),
275
+ ioc.value,
276
+ ioc.threat_type.value,
277
+ ioc.source,
278
+ str(ioc.confidence),
279
+ ", ".join(ioc.tags) if ioc.tags else ""
280
+ )
281
+
282
+ console.print(table)
283
+
284
+ def _export_results(iocs: List[IOC], output: Optional[Path] = None,
285
+ format: str = "table") -> str:
286
+ """Exporta os resultados para o formato especificado."""
287
+ import json
288
+ import yaml
289
+ import csv
290
+ from io import StringIO
291
+
292
+ # Converte para dicionários
293
+ ioc_dicts = [ioc.to_dict() for ioc in iocs]
294
+
295
+ if format == "json":
296
+ result = json.dumps({"iocs": ioc_dicts}, indent=2, ensure_ascii=False)
297
+ elif format in ("yaml", "yml"):
298
+ result = yaml.safe_dump({"iocs": ioc_dicts}, allow_unicode=True)
299
+ elif format == "csv":
300
+ if not ioc_dicts:
301
+ return ""
302
+
303
+ # Extrai todos os campos possíveis
304
+ all_fields = set()
305
+ for ioc in ioc_dicts:
306
+ all_fields.update(ioc.keys())
307
+
308
+ fieldnames = sorted(all_fields)
309
+
310
+ # Escreve para uma string
311
+ output = StringIO()
312
+ writer = csv.DictWriter(output, fieldnames=fieldnames)
313
+ writer.writeheader()
314
+ writer.writerows(ioc_dicts)
315
+ result = output.getvalue()
316
+ else:
317
+ raise ValueError(f"Formato não suportado: {format}")
318
+
319
+ # Se um arquivo de saída for especificado, salva nele
320
+ if output:
321
+ with open(output, 'w', encoding='utf-8') as f:
322
+ f.write(result)
323
+
324
+ return result
325
+
326
+ # Adiciona o comando ao grupo principal
327
+ def register_app(main_app):
328
+ """Registra os comandos de inteligência na aplicação principal."""
329
+ main_app.add_typer(app, name="intel", help="🔍 Comandos de inteligência local")
moriarty/cli/output.py ADDED
@@ -0,0 +1,62 @@
1
+ from __future__ import annotations
2
+
3
+ from pathlib import Path
4
+ from typing import Any, Dict, Optional
5
+
6
+ import typer
7
+ from rich.console import Console
8
+
9
+ from .state import CLIState, GlobalOptions
10
+
11
+ console = Console()
12
+
13
+ try:
14
+ import orjson # type: ignore
15
+ except ModuleNotFoundError: # pragma: no cover
16
+ import json
17
+
18
+ def _dumps(data: Any) -> bytes:
19
+ return json.dumps(data, ensure_ascii=False, separators=(",", ":")).encode("utf-8")
20
+ else:
21
+ def _dumps(data: Any) -> bytes:
22
+ return orjson.dumps(data, option=orjson.OPT_INDENT_2) # type: ignore[attr-defined]
23
+
24
+
25
+ try:
26
+ import yaml
27
+ except ModuleNotFoundError: # pragma: no cover
28
+ yaml = None # type: ignore
29
+
30
+
31
+ def ensure_state(ctx: typer.Context) -> CLIState:
32
+ obj = ctx.obj
33
+ if isinstance(obj, CLIState):
34
+ return obj
35
+ state = CLIState(options=GlobalOptions())
36
+ ctx.obj = state
37
+ return state
38
+
39
+
40
+ def emit_json(payload: Dict[str, Any], target: Optional[str], fallback: Optional[str]) -> None:
41
+ destination = target or fallback
42
+ data = _dumps(payload)
43
+ if destination in (None, "-"):
44
+ console.print_json(data=data.decode("utf-8"))
45
+ else:
46
+ Path(destination).write_bytes(data)
47
+ console.print(f"[success]JSON escrito em {destination}")
48
+
49
+
50
+ def emit_yaml(payload: Dict[str, Any], target: Optional[str], fallback: Optional[str]) -> None:
51
+ if yaml is None:
52
+ raise typer.BadParameter("PyYAML é necessário para saída YAML, instale a dependência.")
53
+ destination = target or fallback
54
+ data = yaml.safe_dump(payload, sort_keys=False)
55
+ if destination in (None, "-"):
56
+ console.print(data)
57
+ else:
58
+ Path(destination).write_text(data, encoding="utf-8")
59
+ console.print(f"[success]YAML escrito em {destination}")
60
+
61
+
62
+ __all__ = ["console", "ensure_state", "emit_json", "emit_yaml"]
moriarty/cli/rdap.py ADDED
@@ -0,0 +1,94 @@
1
+ from __future__ import annotations
2
+
3
+ from typing import Any, Dict, Optional
4
+
5
+ import typer
6
+ from rich import box
7
+ from rich.table import Table
8
+
9
+ from .async_utils import run_async
10
+ from .output import console, emit_json, emit_yaml, ensure_state
11
+ from ..modules.orchestrator import Orchestrator
12
+ from ..modules.rdap import RDAPResult, RDAPService
13
+ from ..net.rdap_client import RDAPClient
14
+
15
+ app = typer.Typer(add_completion=False, help="Consultas RDAP.")
16
+
17
+
18
+ @app.command("domain")
19
+ def domain(
20
+ ctx: typer.Context,
21
+ domain: str = typer.Option(..., "--domain", "-d", help="Domínio a consultar."),
22
+ json_output: Optional[str] = typer.Option(None, "--json", help="Escreve saída JSON no caminho ou '-'"),
23
+ ) -> None:
24
+ _execute_rdap(ctx, query=domain, path="domain", json_output=json_output)
25
+
26
+
27
+ @app.command("ip")
28
+ def ip(
29
+ ctx: typer.Context,
30
+ ip_value: str = typer.Option(..., "--ip", "-i", help="Endereço IP ou prefixo."),
31
+ json_output: Optional[str] = typer.Option(None, "--json", help="Escreve saída JSON no caminho ou '-'"),
32
+ ) -> None:
33
+ _execute_rdap(ctx, query=ip_value, path="ip", json_output=json_output)
34
+
35
+
36
+ def _execute_rdap(ctx: typer.Context, query: str, path: str, json_output: Optional[str]) -> None:
37
+ state = ensure_state(ctx)
38
+ orchestrator: Orchestrator = Orchestrator(
39
+ concurrency=state.options.concurrency,
40
+ timeout=state.options.timeout,
41
+ )
42
+ service = RDAPService(
43
+ client=RDAPClient(timeout=state.options.timeout, http2=True),
44
+ orchestrator=orchestrator,
45
+ )
46
+
47
+ if path == "domain":
48
+ result = run_async(service.domain(query))
49
+ else:
50
+ result = run_async(service.ip(query))
51
+
52
+ payload = _result_to_dict(result)
53
+ output_format = ("json" if json_output else state.options.format).lower()
54
+
55
+ if output_format == "json":
56
+ emit_json(payload, json_output, state.options.output)
57
+ elif output_format == "yaml":
58
+ emit_yaml(payload, json_output, state.options.output)
59
+ else:
60
+ _render_table(result)
61
+
62
+
63
+ def _render_table(result: RDAPResult) -> None:
64
+ table = Table(title=f"RDAP · {result.query}", box=box.SIMPLE_HEAVY)
65
+ table.add_column("Campo", style="cyan", no_wrap=True)
66
+ table.add_column("Valor", style="white")
67
+
68
+ table.add_row("URL", result.url)
69
+ table.add_row("Status", str(result.status))
70
+ table.add_row("Latência (ms)", f"{result.latency_ms:.2f}")
71
+ handle = result.response.get("handle")
72
+ if handle:
73
+ table.add_row("Handle", str(handle))
74
+ entity_type = result.response.get("objectClassName")
75
+ if entity_type:
76
+ table.add_row("Objeto", str(entity_type))
77
+ events = result.response.get("events", [])
78
+ if events:
79
+ table.add_row("Eventos", "\n".join(f"{e.get('eventAction')}: {e.get('eventDate')}" for e in events))
80
+
81
+ console.print(table)
82
+
83
+
84
+ def _result_to_dict(result: RDAPResult) -> Dict[str, Any]:
85
+ return {
86
+ "query": result.query,
87
+ "url": result.url,
88
+ "status": result.status,
89
+ "latency_ms": result.latency_ms,
90
+ "response": result.response,
91
+ }
92
+
93
+
94
+ __all__ = ["app"]
moriarty/cli/state.py ADDED
@@ -0,0 +1,38 @@
1
+ from __future__ import annotations
2
+
3
+ from dataclasses import dataclass
4
+ from typing import Optional
5
+
6
+ from ..logging.config import LogStyle
7
+
8
+
9
+ @dataclass
10
+ class GlobalOptions:
11
+ concurrency: int = 50
12
+ timeout: float = 8.0
13
+ proxy: Optional[str] = None
14
+ headless: str = "auto"
15
+ allowlist_domain: Optional[str] = None
16
+ output: Optional[str] = None
17
+ format: str = "table"
18
+ redact: bool = True
19
+ verbose: bool = False
20
+ quiet: bool = False
21
+ professional_mode: bool = False
22
+ seed: Optional[int] = None
23
+ dry_run: bool = False
24
+ plan_only: bool = False
25
+ sign: bool = False
26
+ resume_path: Optional[str] = None
27
+ http3: bool = False
28
+ doh: Optional[str] = None
29
+ dot: Optional[str] = None
30
+ logs: LogStyle = "structured"
31
+
32
+
33
+ @dataclass
34
+ class CLIState:
35
+ options: GlobalOptions
36
+
37
+
38
+ __all__ = ["CLIState", "GlobalOptions"]
moriarty/cli/tls.py ADDED
@@ -0,0 +1,91 @@
1
+ from __future__ import annotations
2
+
3
+ from typing import Any, Dict, Optional
4
+
5
+ import typer
6
+ from rich import box
7
+ from rich.table import Table
8
+
9
+ from .async_utils import run_async
10
+ from .output import console, emit_json, emit_yaml, ensure_state
11
+ from ..modules.orchestrator import Orchestrator
12
+ from ..modules.tls_scan import TLSScanService
13
+ from ..net.tls_client import TLSClient, TLSInspection
14
+
15
+ app = typer.Typer(add_completion=False, help="Inspeção de certificados TLS.")
16
+
17
+
18
+ @app.command("certs")
19
+ def certs(
20
+ ctx: typer.Context,
21
+ domain: str = typer.Option(..., "--domain", "-d", help="Host a ser inspecionado."),
22
+ port: int = typer.Option(443, help="Porta TLS."),
23
+ json_output: Optional[str] = typer.Option(None, "--json", help="Escreve saída JSON no caminho ou '-'"),
24
+ ) -> None:
25
+ state = ensure_state(ctx)
26
+ orchestrator: Orchestrator[TLSInspection] = Orchestrator(
27
+ concurrency=state.options.concurrency,
28
+ timeout=state.options.timeout,
29
+ )
30
+
31
+ service = TLSScanService(
32
+ client=TLSClient(timeout=state.options.timeout),
33
+ orchestrator=orchestrator,
34
+ host=domain,
35
+ port=port,
36
+ )
37
+
38
+ result = run_async(service.run())
39
+ payload = _result_to_dict(result.inspection)
40
+
41
+ output_format = ("json" if json_output else state.options.format).lower()
42
+ if output_format == "json":
43
+ emit_json(payload, json_output, state.options.output)
44
+ elif output_format == "yaml":
45
+ emit_yaml(payload, json_output, state.options.output)
46
+ else:
47
+ _render_table(result.inspection)
48
+
49
+
50
+ def _render_table(inspection: TLSInspection) -> None:
51
+ table = Table(title=f"TLS Certs · {inspection.host}:{inspection.port}", box=box.SIMPLE_HEAVY)
52
+ table.add_column("Campo", style="cyan", no_wrap=True)
53
+ table.add_column("Valor", style="white")
54
+
55
+ table.add_row("Protocolo", inspection.protocol or "—")
56
+ table.add_row("Cipher", inspection.cipher or "—")
57
+ table.add_row("Latência (ms)", f"{inspection.latency_ms:.2f}")
58
+
59
+ for idx, cert in enumerate(inspection.certificates, start=1):
60
+ table.add_row(f"Certificado {idx} - Subject", cert.subject or "—")
61
+ table.add_row(f"Certificado {idx} - Issuer", cert.issuer or "—")
62
+ table.add_row(f"Certificado {idx} - Validade", f"{cert.not_before} → {cert.not_after}")
63
+ table.add_row(f"Certificado {idx} - SHA256", cert.fingerprint_sha256)
64
+ if cert.subject_alt_names:
65
+ table.add_row(f"Certificado {idx} - SANs", ", ".join(cert.subject_alt_names))
66
+
67
+ console.print(table)
68
+
69
+
70
+ def _result_to_dict(inspection: TLSInspection) -> Dict[str, Any]:
71
+ return {
72
+ "host": inspection.host,
73
+ "port": inspection.port,
74
+ "protocol": inspection.protocol,
75
+ "cipher": inspection.cipher,
76
+ "latency_ms": inspection.latency_ms,
77
+ "certificates": [
78
+ {
79
+ "subject": cert.subject,
80
+ "issuer": cert.issuer,
81
+ "not_before": cert.not_before.isoformat(),
82
+ "not_after": cert.not_after.isoformat(),
83
+ "fingerprint_sha256": cert.fingerprint_sha256,
84
+ "subject_alt_names": cert.subject_alt_names,
85
+ }
86
+ for cert in inspection.certificates
87
+ ],
88
+ }
89
+
90
+
91
+ __all__ = ["app"]