graph-crawler 5.2.0__tar.gz → 5.2.1__tar.gz

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 (953) hide show
  1. graph_crawler-5.2.1/CHANGELOG.md +244 -0
  2. graph_crawler-5.2.1/CODE_STYLE.md +1473 -0
  3. graph_crawler-5.2.1/LICENSE +21 -0
  4. graph_crawler-5.2.1/MANIFEST.in +19 -0
  5. graph_crawler-5.2.1/PKG-INFO +370 -0
  6. graph_crawler-5.2.1/README.md +249 -0
  7. graph_crawler-5.2.1/graph_crawler/__init__.py +478 -0
  8. graph_crawler-5.2.1/graph_crawler/__version__.py +7 -0
  9. graph_crawler-5.2.1/graph_crawler/ai/__init__.py +49 -0
  10. graph_crawler-5.2.1/graph_crawler/api/__init__.py +24 -0
  11. graph_crawler-5.2.1/graph_crawler/api/_core.py +281 -0
  12. graph_crawler-5.2.1/graph_crawler/api/_distributed.py +174 -0
  13. graph_crawler-5.2.1/graph_crawler/api/_shared.py +120 -0
  14. graph_crawler-5.2.1/graph_crawler/api/_sitemap_distributed.py +244 -0
  15. graph_crawler-5.2.1/graph_crawler/api/async_.py +325 -0
  16. graph_crawler-5.2.1/graph_crawler/api/cli.py +440 -0
  17. graph_crawler-5.2.1/graph_crawler/api/client/__init__.py +8 -0
  18. graph_crawler-5.2.1/graph_crawler/api/client/client.py +498 -0
  19. graph_crawler-5.2.1/graph_crawler/api/history_manager.py +82 -0
  20. graph_crawler-5.2.1/graph_crawler/api/project_init.py +194 -0
  21. graph_crawler-5.2.1/graph_crawler/api/server/__init__.py +18 -0
  22. graph_crawler-5.2.1/graph_crawler/api/server/crawl_monitor.py +145 -0
  23. graph_crawler-5.2.1/graph_crawler/api/server/dashboard.py +221 -0
  24. graph_crawler-5.2.1/graph_crawler/api/server/rest_api.py +704 -0
  25. graph_crawler-5.2.1/graph_crawler/api/server/webhooks.py +421 -0
  26. graph_crawler-5.2.1/graph_crawler/api/server/websocket_manager.py +89 -0
  27. graph_crawler-5.2.1/graph_crawler/api/stats_collector.py +115 -0
  28. graph_crawler-5.2.1/graph_crawler/api/sync.py +491 -0
  29. graph_crawler-5.2.1/graph_crawler/application/__init__.py +38 -0
  30. graph_crawler-5.2.1/graph_crawler/application/bootstrap.py +209 -0
  31. graph_crawler-5.2.1/graph_crawler/application/context/__init__.py +31 -0
  32. graph_crawler-5.2.1/graph_crawler/application/context/dependency_registry.py +354 -0
  33. graph_crawler-5.2.1/graph_crawler/application/context/graph_context.py +217 -0
  34. graph_crawler-5.2.1/graph_crawler/application/context/merge_context.py +221 -0
  35. graph_crawler-5.2.1/graph_crawler/application/dto/__init__.py +67 -0
  36. graph_crawler-5.2.1/graph_crawler/application/dto/edge_dto.py +25 -0
  37. graph_crawler-5.2.1/graph_crawler/application/dto/graph_dto.py +27 -0
  38. graph_crawler-5.2.1/graph_crawler/application/dto/mappers/__init__.py +14 -0
  39. graph_crawler-5.2.1/graph_crawler/application/dto/mappers/edge_mapper.py +149 -0
  40. graph_crawler-5.2.1/graph_crawler/application/dto/mappers/graph_mapper.py +614 -0
  41. graph_crawler-5.2.1/graph_crawler/application/dto/mappers/node_data_codec.py +190 -0
  42. graph_crawler-5.2.1/graph_crawler/application/dto/mappers/node_mapper.py +387 -0
  43. graph_crawler-5.2.1/graph_crawler/application/dto/node_dto.py +27 -0
  44. graph_crawler-5.2.1/graph_crawler/application/dto/utils.py +272 -0
  45. graph_crawler-5.2.1/graph_crawler/application/services/__init__.py +60 -0
  46. graph_crawler-5.2.1/graph_crawler/application/services/application_container.py +208 -0
  47. graph_crawler-5.2.1/graph_crawler/application/services/driver_factory.py +147 -0
  48. graph_crawler-5.2.1/graph_crawler/application/services/exporters/__init__.py +26 -0
  49. graph_crawler-5.2.1/graph_crawler/application/services/exporters/base_exporter.py +150 -0
  50. graph_crawler-5.2.1/graph_crawler/application/services/exporters/csv_exporter.py +318 -0
  51. graph_crawler-5.2.1/graph_crawler/application/services/exporters/edge_exporter.py +432 -0
  52. graph_crawler-5.2.1/graph_crawler/application/services/exporters/excel_exporter.py +301 -0
  53. graph_crawler-5.2.1/graph_crawler/application/services/exporters/jsonl_exporter.py +290 -0
  54. graph_crawler-5.2.1/graph_crawler/application/services/exporters/node_exporter.py +283 -0
  55. graph_crawler-5.2.1/graph_crawler/application/services/exporters/parquet_exporter.py +248 -0
  56. graph_crawler-5.2.1/graph_crawler/application/services/exporters/sql_exporter.py +267 -0
  57. graph_crawler-5.2.1/graph_crawler/application/services/finalize.py +115 -0
  58. graph_crawler-5.2.1/graph_crawler/application/services/low_memory_graph_saver.py +339 -0
  59. graph_crawler-5.2.1/graph_crawler/application/services/resource_budget.py +179 -0
  60. graph_crawler-5.2.1/graph_crawler/application/services/scheduling/__init__.py +12 -0
  61. graph_crawler-5.2.1/graph_crawler/application/services/scheduling/rule_based_scheduler.py +113 -0
  62. graph_crawler-5.2.1/graph_crawler/application/services/storage_factory.py +195 -0
  63. graph_crawler-5.2.1/graph_crawler/application/use_cases/__init__.py +11 -0
  64. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/__init__.py +81 -0
  65. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/adaptive_throttler.py +374 -0
  66. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/async_bridge.py +45 -0
  67. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/base_spider.py +156 -0
  68. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/celery_batch_spider.py +658 -0
  69. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/celery_spider.py +448 -0
  70. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/checkpoint.py +421 -0
  71. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/crawl_coordinator.py +1044 -0
  72. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/dead_letter_queue.py +413 -0
  73. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/domain_rate_limiter.py +262 -0
  74. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/filters/__init__.py +10 -0
  75. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/filters/base.py +74 -0
  76. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/filters/domain_filter.py +195 -0
  77. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/filters/domain_patterns.py +30 -0
  78. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/filters/path_filter.py +95 -0
  79. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/incremental_strategy.py +239 -0
  80. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/link_processor.py +908 -0
  81. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/multiprocess_spider.py +511 -0
  82. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/node_scanner.py +808 -0
  83. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/parsers/__init__.py +6 -0
  84. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/parsers/base.py +73 -0
  85. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/parsers/html_parser.py +154 -0
  86. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/progress_tracker.py +235 -0
  87. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/scheduler.py +747 -0
  88. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/serialization_mixin.py +218 -0
  89. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/sitemap_parser.py +662 -0
  90. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/sitemap_processor.py +401 -0
  91. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/sitemap_spider.py +608 -0
  92. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/spider.py +811 -0
  93. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/spider_lifecycle.py +108 -0
  94. graph_crawler-5.2.1/graph_crawler/application/use_cases/crawling/worker_pool.py +154 -0
  95. graph_crawler-5.2.1/graph_crawler/application/use_cases/graph_export.py +504 -0
  96. graph_crawler-5.2.1/graph_crawler/application/use_cases/graph_merge/__init__.py +33 -0
  97. graph_crawler-5.2.1/graph_crawler/application/use_cases/graph_merge/graph_operations.py +632 -0
  98. graph_crawler-5.2.1/graph_crawler/application/use_cases/graph_merge/merge_strategies.py +348 -0
  99. graph_crawler-5.2.1/graph_crawler/data/__init__.py +28 -0
  100. graph_crawler-5.2.1/graph_crawler/data/backends/__init__.py +21 -0
  101. graph_crawler-5.2.1/graph_crawler/data/backends/memory.py +486 -0
  102. graph_crawler-5.2.1/graph_crawler/data/backends/sqlite.py +1866 -0
  103. graph_crawler-5.2.1/graph_crawler/data/interfaces.py +575 -0
  104. graph_crawler-5.2.1/graph_crawler/domain/__init__.py +62 -0
  105. graph_crawler-5.2.1/graph_crawler/domain/context/__init__.py +14 -0
  106. graph_crawler-5.2.1/graph_crawler/domain/context/crawl_context.py +531 -0
  107. graph_crawler-5.2.1/graph_crawler/domain/entities/__init__.py +32 -0
  108. graph_crawler-5.2.1/graph_crawler/domain/entities/edge.py +345 -0
  109. graph_crawler-5.2.1/graph_crawler/domain/entities/edge_analysis.py +223 -0
  110. graph_crawler-5.2.1/graph_crawler/domain/entities/graph.py +4120 -0
  111. graph_crawler-5.2.1/graph_crawler/domain/entities/graph_operations.py +33 -0
  112. graph_crawler-5.2.1/graph_crawler/domain/entities/graph_statistics.py +13 -0
  113. graph_crawler-5.2.1/graph_crawler/domain/entities/merge_strategies.py +36 -0
  114. graph_crawler-5.2.1/graph_crawler/domain/entities/node.py +692 -0
  115. graph_crawler-5.2.1/graph_crawler/domain/entities/redirect_mode.py +23 -0
  116. graph_crawler-5.2.1/graph_crawler/domain/entities/registries.py +237 -0
  117. graph_crawler-5.2.1/graph_crawler/domain/entities/sitemap_node.py +74 -0
  118. graph_crawler-5.2.1/graph_crawler/domain/entities/strategies.py +202 -0
  119. graph_crawler-5.2.1/graph_crawler/domain/events/__init__.py +163 -0
  120. graph_crawler-5.2.1/graph_crawler/domain/events/base.py +58 -0
  121. graph_crawler-5.2.1/graph_crawler/domain/events/crawl.py +123 -0
  122. graph_crawler-5.2.1/graph_crawler/domain/events/edge.py +46 -0
  123. graph_crawler-5.2.1/graph_crawler/domain/events/event_bus.py +251 -0
  124. graph_crawler-5.2.1/graph_crawler/domain/events/events.py +313 -0
  125. graph_crawler-5.2.1/graph_crawler/domain/events/fetch.py +123 -0
  126. graph_crawler-5.2.1/graph_crawler/domain/events/idempotent_subscriber.py +120 -0
  127. graph_crawler-5.2.1/graph_crawler/domain/events/legacy_type_map.py +45 -0
  128. graph_crawler-5.2.1/graph_crawler/domain/events/llm.py +158 -0
  129. graph_crawler-5.2.1/graph_crawler/domain/events/node.py +124 -0
  130. graph_crawler-5.2.1/graph_crawler/domain/events/plugin.py +96 -0
  131. graph_crawler-5.2.1/graph_crawler/domain/events/scheduler.py +102 -0
  132. graph_crawler-5.2.1/graph_crawler/domain/events/storage.py +168 -0
  133. graph_crawler-5.2.1/graph_crawler/domain/interfaces/__init__.py +111 -0
  134. graph_crawler-5.2.1/graph_crawler/domain/interfaces/adapter.py +29 -0
  135. graph_crawler-5.2.1/graph_crawler/domain/interfaces/control_channel.py +371 -0
  136. graph_crawler-5.2.1/graph_crawler/domain/interfaces/crawl_context.py +49 -0
  137. graph_crawler-5.2.1/graph_crawler/domain/interfaces/distributed_spider.py +63 -0
  138. graph_crawler-5.2.1/graph_crawler/domain/interfaces/driver.py +88 -0
  139. graph_crawler-5.2.1/graph_crawler/domain/interfaces/event_bus.py +61 -0
  140. graph_crawler-5.2.1/graph_crawler/domain/interfaces/exporters.py +83 -0
  141. graph_crawler-5.2.1/graph_crawler/domain/interfaces/filter.py +19 -0
  142. graph_crawler-5.2.1/graph_crawler/domain/interfaces/merge_context.py +58 -0
  143. graph_crawler-5.2.1/graph_crawler/domain/interfaces/node_interfaces.py +376 -0
  144. graph_crawler-5.2.1/graph_crawler/domain/interfaces/parser.py +110 -0
  145. graph_crawler-5.2.1/graph_crawler/domain/interfaces/plugin_manager.py +53 -0
  146. graph_crawler-5.2.1/graph_crawler/domain/interfaces/processor.py +11 -0
  147. graph_crawler-5.2.1/graph_crawler/domain/interfaces/scanner.py +57 -0
  148. graph_crawler-5.2.1/graph_crawler/domain/interfaces/scheduler.py +43 -0
  149. graph_crawler-5.2.1/graph_crawler/domain/interfaces/scheduling/__init__.py +40 -0
  150. graph_crawler-5.2.1/graph_crawler/domain/interfaces/scheduling/frontier.py +97 -0
  151. graph_crawler-5.2.1/graph_crawler/domain/interfaces/scheduling/scheduler.py +107 -0
  152. graph_crawler-5.2.1/graph_crawler/domain/interfaces/spider.py +63 -0
  153. graph_crawler-5.2.1/graph_crawler/domain/interfaces/stop_condition.py +211 -0
  154. graph_crawler-5.2.1/graph_crawler/domain/interfaces/storage/__init__.py +43 -0
  155. graph_crawler-5.2.1/graph_crawler/domain/interfaces/storage/base.py +70 -0
  156. graph_crawler-5.2.1/graph_crawler/domain/interfaces/storage/eviction.py +102 -0
  157. graph_crawler-5.2.1/graph_crawler/domain/interfaces/storage/queue.py +234 -0
  158. graph_crawler-5.2.1/graph_crawler/domain/services/__init__.py +216 -0
  159. graph_crawler-5.2.1/graph_crawler/domain/services/adjacency_maintenance.py +95 -0
  160. graph_crawler-5.2.1/graph_crawler/domain/services/cycle_detection.py +92 -0
  161. graph_crawler-5.2.1/graph_crawler/domain/services/degree_ranking.py +47 -0
  162. graph_crawler-5.2.1/graph_crawler/domain/services/depth_context.py +123 -0
  163. graph_crawler-5.2.1/graph_crawler/domain/services/display_title.py +47 -0
  164. graph_crawler-5.2.1/graph_crawler/domain/services/duplicate_detection.py +141 -0
  165. graph_crawler-5.2.1/graph_crawler/domain/services/duplicate_selector.py +127 -0
  166. graph_crawler-5.2.1/graph_crawler/domain/services/duplicate_stats.py +63 -0
  167. graph_crawler-5.2.1/graph_crawler/domain/services/edge_filter.py +82 -0
  168. graph_crawler-5.2.1/graph_crawler/domain/services/edge_statistics.py +110 -0
  169. graph_crawler-5.2.1/graph_crawler/domain/services/eviction_policy.py +83 -0
  170. graph_crawler-5.2.1/graph_crawler/domain/services/graph_query_cascade.py +178 -0
  171. graph_crawler-5.2.1/graph_crawler/domain/services/graph_statistics.py +186 -0
  172. graph_crawler-5.2.1/graph_crawler/domain/services/graph_traversal.py +150 -0
  173. graph_crawler-5.2.1/graph_crawler/domain/services/language_versions.py +73 -0
  174. graph_crawler-5.2.1/graph_crawler/domain/services/lsh_index.py +99 -0
  175. graph_crawler-5.2.1/graph_crawler/domain/services/minimap_builder.py +147 -0
  176. graph_crawler-5.2.1/graph_crawler/domain/services/node_content_resolver.py +128 -0
  177. graph_crawler-5.2.1/graph_crawler/domain/services/node_view_builder.py +163 -0
  178. graph_crawler-5.2.1/graph_crawler/domain/services/pagination_guards.py +136 -0
  179. graph_crawler-5.2.1/graph_crawler/domain/services/predicate_ops.py +77 -0
  180. graph_crawler-5.2.1/graph_crawler/domain/services/schema_filter.py +138 -0
  181. graph_crawler-5.2.1/graph_crawler/domain/services/search_haystack.py +102 -0
  182. graph_crawler-5.2.1/graph_crawler/domain/services/simhash_clustering.py +96 -0
  183. graph_crawler-5.2.1/graph_crawler/domain/services/simhash_fallback.py +59 -0
  184. graph_crawler-5.2.1/graph_crawler/domain/services/similarity_ranking.py +62 -0
  185. graph_crawler-5.2.1/graph_crawler/domain/services/text_search.py +157 -0
  186. graph_crawler-5.2.1/graph_crawler/domain/services/url_clustering.py +88 -0
  187. graph_crawler-5.2.1/graph_crawler/domain/services/url_deduplication.py +101 -0
  188. graph_crawler-5.2.1/graph_crawler/domain/services/url_normalizer.py +108 -0
  189. graph_crawler-5.2.1/graph_crawler/domain/services/url_rule_matcher.py +103 -0
  190. graph_crawler-5.2.1/graph_crawler/domain/services/url_tree_builder.py +197 -0
  191. graph_crawler-5.2.1/graph_crawler/domain/value_objects/__init__.py +88 -0
  192. graph_crawler-5.2.1/graph_crawler/domain/value_objects/configs.py +884 -0
  193. graph_crawler-5.2.1/graph_crawler/domain/value_objects/domain_patterns.py +71 -0
  194. graph_crawler-5.2.1/graph_crawler/domain/value_objects/fetch_options.py +57 -0
  195. graph_crawler-5.2.1/graph_crawler/domain/value_objects/html_document.py +59 -0
  196. graph_crawler-5.2.1/graph_crawler/domain/value_objects/lifecycle.py +30 -0
  197. graph_crawler-5.2.1/graph_crawler/domain/value_objects/models.py +1316 -0
  198. graph_crawler-5.2.1/graph_crawler/domain/value_objects/redirect_hop.py +49 -0
  199. graph_crawler-5.2.1/graph_crawler/domain/value_objects/scheduling/__init__.py +23 -0
  200. graph_crawler-5.2.1/graph_crawler/domain/value_objects/scheduling/crawl_request.py +153 -0
  201. graph_crawler-5.2.1/graph_crawler/domain/value_objects/scheduling/retry_policy.py +109 -0
  202. graph_crawler-5.2.1/graph_crawler/domain/value_objects/settings.py +350 -0
  203. graph_crawler-5.2.1/graph_crawler/domain/value_objects/url_normalization.py +496 -0
  204. graph_crawler-5.2.1/graph_crawler/domain/value_objects/views.py +293 -0
  205. graph_crawler-5.2.1/graph_crawler/extensions/__init__.py +1 -0
  206. graph_crawler-5.2.1/graph_crawler/extensions/middleware/__init__.py +65 -0
  207. graph_crawler-5.2.1/graph_crawler/extensions/middleware/base.py +147 -0
  208. graph_crawler-5.2.1/graph_crawler/extensions/middleware/cache_middleware.py +277 -0
  209. graph_crawler-5.2.1/graph_crawler/extensions/middleware/chain.py +159 -0
  210. graph_crawler-5.2.1/graph_crawler/extensions/middleware/error_recovery_middleware.py +442 -0
  211. graph_crawler-5.2.1/graph_crawler/extensions/middleware/logging_middleware.py +108 -0
  212. graph_crawler-5.2.1/graph_crawler/extensions/middleware/proxy_health.py +144 -0
  213. graph_crawler-5.2.1/graph_crawler/extensions/middleware/proxy_middleware.py +208 -0
  214. graph_crawler-5.2.1/graph_crawler/extensions/middleware/proxy_models.py +84 -0
  215. graph_crawler-5.2.1/graph_crawler/extensions/middleware/proxy_selection.py +87 -0
  216. graph_crawler-5.2.1/graph_crawler/extensions/middleware/rate_limit_middleware.py +262 -0
  217. graph_crawler-5.2.1/graph_crawler/extensions/middleware/request_response_middleware.py +476 -0
  218. graph_crawler-5.2.1/graph_crawler/extensions/middleware/retry_middleware.py +279 -0
  219. graph_crawler-5.2.1/graph_crawler/extensions/middleware/robots_cache.py +85 -0
  220. graph_crawler-5.2.1/graph_crawler/extensions/middleware/robots_middleware.py +110 -0
  221. graph_crawler-5.2.1/graph_crawler/extensions/middleware/robots_validator.py +60 -0
  222. graph_crawler-5.2.1/graph_crawler/extensions/middleware/user_agent_middleware.py +251 -0
  223. graph_crawler-5.2.1/graph_crawler/extensions/plugins/__init__.py +57 -0
  224. graph_crawler-5.2.1/graph_crawler/extensions/plugins/builtin/__init__.py +7 -0
  225. graph_crawler-5.2.1/graph_crawler/extensions/plugins/builtin/stats_export_plugin.py +98 -0
  226. graph_crawler-5.2.1/graph_crawler/extensions/plugins/crawl_engine/__init__.py +24 -0
  227. graph_crawler-5.2.1/graph_crawler/extensions/plugins/crawl_engine/base.py +155 -0
  228. graph_crawler-5.2.1/graph_crawler/extensions/plugins/crawl_engine/priority_provider.py +247 -0
  229. graph_crawler-5.2.1/graph_crawler/extensions/plugins/crawl_engine/smart_crawl.py +306 -0
  230. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/__init__.py +128 -0
  231. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/anti_bot_detection.py +52 -0
  232. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/anti_bot_playwright.py +85 -0
  233. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/anti_bot_scripts.py +133 -0
  234. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/anti_bot_stealth.py +177 -0
  235. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/base.py +121 -0
  236. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/captcha/__init__.py +22 -0
  237. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/captcha/detector.py +94 -0
  238. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/captcha/models.py +74 -0
  239. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/captcha/plugin.py +228 -0
  240. graph_crawler-5.2.1/graph_crawler/extensions/plugins/engine/captcha/services.py +389 -0
  241. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/__init__.py +86 -0
  242. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/base.py +432 -0
  243. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/content_extractors/__init__.py +15 -0
  244. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/content_extractors/base.py +82 -0
  245. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/content_extractors/goose3_extractor.py +80 -0
  246. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/content_extractors/newspaper_extractor.py +93 -0
  247. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/content_extractors/plugin.py +132 -0
  248. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/content_extractors/readability_extractor.py +91 -0
  249. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/defaults.py +32 -0
  250. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/extractors/__init__.py +30 -0
  251. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/extractors/email_extractor.py +146 -0
  252. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/extractors/phone_extractor.py +136 -0
  253. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/extractors/price_extractor.py +137 -0
  254. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/links.py +184 -0
  255. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/markdown_plugin.py +249 -0
  256. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/metadata.py +391 -0
  257. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/smart_page_finder.py +749 -0
  258. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/__init__.py +51 -0
  259. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/constants.py +27 -0
  260. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/exceptions.py +18 -0
  261. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/extractor.py +361 -0
  262. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/options.py +62 -0
  263. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/parsers/__init__.py +25 -0
  264. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/parsers/base.py +43 -0
  265. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/parsers/jsonld.py +331 -0
  266. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/parsers/microdata.py +117 -0
  267. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/parsers/opengraph.py +66 -0
  268. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/parsers/rdfa.py +122 -0
  269. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/parsers/twitter.py +66 -0
  270. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/plugin.py +132 -0
  271. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/structured_data/result.py +233 -0
  272. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/text.py +76 -0
  273. graph_crawler-5.2.1/graph_crawler/extensions/plugins/node/url_normalizer.py +363 -0
  274. graph_crawler-5.2.1/graph_crawler/extensions/plugins/registry.py +97 -0
  275. graph_crawler-5.2.1/graph_crawler/infrastructure/__init__.py +1 -0
  276. graph_crawler-5.2.1/graph_crawler/infrastructure/adapters/__init__.py +60 -0
  277. graph_crawler-5.2.1/graph_crawler/infrastructure/adapters/base.py +498 -0
  278. graph_crawler-5.2.1/graph_crawler/infrastructure/adapters/selectolax_adapter.py +234 -0
  279. graph_crawler-5.2.1/graph_crawler/infrastructure/messaging/__init__.py +37 -0
  280. graph_crawler-5.2.1/graph_crawler/infrastructure/messaging/celery_app.py +202 -0
  281. graph_crawler-5.2.1/graph_crawler/infrastructure/messaging/celery_batch.py +284 -0
  282. graph_crawler-5.2.1/graph_crawler/infrastructure/messaging/celery_job_task.py +415 -0
  283. graph_crawler-5.2.1/graph_crawler/infrastructure/messaging/celery_unified.py +419 -0
  284. graph_crawler-5.2.1/graph_crawler/infrastructure/messaging/config.py +201 -0
  285. graph_crawler-5.2.1/graph_crawler/infrastructure/messaging/easy_crawler.py +279 -0
  286. graph_crawler-5.2.1/graph_crawler/infrastructure/messaging/worker_api.py +607 -0
  287. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/__init__.py +135 -0
  288. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/auto_storage.py +336 -0
  289. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/base.py +111 -0
  290. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/eviction.py +100 -0
  291. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/graph_repository.py +401 -0
  292. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/json/__init__.py +10 -0
  293. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/json_storage.py +375 -0
  294. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/lmdb_eviction_storage.py +403 -0
  295. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/memory/__init__.py +1 -0
  296. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/memory_dedup_store.py +91 -0
  297. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/memory_frontier.py +180 -0
  298. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/memory_politeness_store.py +88 -0
  299. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/memory_storage.py +166 -0
  300. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/mongodb_storage.py +383 -0
  301. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/naming_strategy.py +174 -0
  302. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/postgresql_storage.py +449 -0
  303. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/protocols/__init__.py +1 -0
  304. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/redis_dedup_store.py +119 -0
  305. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/redis_politeness_store.py +122 -0
  306. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/repository.py +130 -0
  307. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/sqlite/__init__.py +10 -0
  308. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/sqlite_eviction_storage.py +918 -0
  309. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/sqlite_storage.py +775 -0
  310. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/unified/__init__.py +47 -0
  311. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/unified/file_job_storage.py +245 -0
  312. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/unified/file_queue_storage.py +248 -0
  313. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/unified/memory_job_storage.py +94 -0
  314. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/unified/memory_queue_storage.py +117 -0
  315. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/unified/postgresql_job_storage.py +317 -0
  316. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/unified/postgresql_queue_storage.py +364 -0
  317. graph_crawler-5.2.1/graph_crawler/infrastructure/persistence/unified/unified_storage.py +244 -0
  318. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/__init__.py +135 -0
  319. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/__init__.py +38 -0
  320. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/config.py +47 -0
  321. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/context.py +55 -0
  322. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/driver.py +724 -0
  323. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/driver_curl_cffi.py +407 -0
  324. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/plugins/__init__.py +48 -0
  325. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/plugins/autothrottle.py +484 -0
  326. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/plugins/autothrottle_adaptive.py +1435 -0
  327. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/plugins/headers.py +69 -0
  328. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/plugins/http_cache.py +321 -0
  329. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/plugins/rate_limiter.py +96 -0
  330. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/plugins/retry.py +316 -0
  331. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/async_http/stages.py +33 -0
  332. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/base.py +324 -0
  333. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/base_plugin.py +151 -0
  334. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/compression/__init__.py +23 -0
  335. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/compression/strategy.py +219 -0
  336. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/connection_pool.py +349 -0
  337. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/context.py +114 -0
  338. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/core/__init__.py +15 -0
  339. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/core/base_async.py +378 -0
  340. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/core/body_decoder.py +26 -0
  341. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/core/mixins.py +258 -0
  342. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/core/redirect_utils.py +168 -0
  343. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/escalation.py +937 -0
  344. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/factory.py +210 -0
  345. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/__init__.py +19 -0
  346. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/adaptive_semaphore.py +65 -0
  347. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/batch_scheduler.py +764 -0
  348. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/browser_factory.py +576 -0
  349. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/browser_profile.py +718 -0
  350. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/config.py +84 -0
  351. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/context.py +46 -0
  352. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/driver.py +80 -0
  353. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/engine.py +465 -0
  354. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/fetch_metrics.py +115 -0
  355. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/net/__init__.py +41 -0
  356. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/net/geoip.py +136 -0
  357. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/net/proxy_pool.py +225 -0
  358. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/net/rate_limiter.py +139 -0
  359. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/page_fetch.py +896 -0
  360. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/__init__.py +71 -0
  361. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/_network_record.py +66 -0
  362. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/captcha_detector.py +315 -0
  363. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/captcha_solver.py +108 -0
  364. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/cookie_consent.py +565 -0
  365. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/form_filler.py +177 -0
  366. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/human_bezier.py +297 -0
  367. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/network_log.py +366 -0
  368. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/ram_adaptive.py +208 -0
  369. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/screenshot.py +169 -0
  370. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/plugins/user_profile.py +556 -0
  371. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/pool_lifecycle.py +658 -0
  372. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/pooled_driver.py +698 -0
  373. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/stages.py +35 -0
  374. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/playwright/stealth_hints.py +153 -0
  375. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/plugin_manager.py +316 -0
  376. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/protocols.py +118 -0
  377. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/undetected/__init__.py +8 -0
  378. graph_crawler-5.2.1/graph_crawler/infrastructure/transport/undetected/async_driver.py +465 -0
  379. graph_crawler-5.2.1/graph_crawler/native/README.md +110 -0
  380. graph_crawler-5.2.1/graph_crawler/native/__init__.py +200 -0
  381. graph_crawler-5.2.1/graph_crawler/native/bloom_filter.pyx +255 -0
  382. graph_crawler-5.2.1/graph_crawler/native/html_parser.pyx +262 -0
  383. graph_crawler-5.2.1/graph_crawler/native/setup.py +101 -0
  384. graph_crawler-5.2.1/graph_crawler/native/url_utils.pyx +209 -0
  385. graph_crawler-5.2.1/graph_crawler/observability/__init__.py +62 -0
  386. graph_crawler-5.2.1/graph_crawler/observability/decorators/__init__.py +11 -0
  387. graph_crawler-5.2.1/graph_crawler/observability/decorators/cache.py +126 -0
  388. graph_crawler-5.2.1/graph_crawler/observability/decorators/log.py +56 -0
  389. graph_crawler-5.2.1/graph_crawler/observability/decorators/retry.py +121 -0
  390. graph_crawler-5.2.1/graph_crawler/observability/decorators/timing.py +43 -0
  391. graph_crawler-5.2.1/graph_crawler/observability/error_tracing.py +363 -0
  392. graph_crawler-5.2.1/graph_crawler/observability/extensions/__init__.py +18 -0
  393. graph_crawler-5.2.1/graph_crawler/observability/extensions/memory_guard.py +237 -0
  394. graph_crawler-5.2.1/graph_crawler/observability/extensions/state_manager.py +319 -0
  395. graph_crawler-5.2.1/graph_crawler/observability/listeners/__init__.py +33 -0
  396. graph_crawler-5.2.1/graph_crawler/observability/listeners/base.py +82 -0
  397. graph_crawler-5.2.1/graph_crawler/observability/listeners/base_metrics_listener.py +18 -0
  398. graph_crawler-5.2.1/graph_crawler/observability/listeners/crawl_listener.py +28 -0
  399. graph_crawler-5.2.1/graph_crawler/observability/listeners/dlq_listener.py +215 -0
  400. graph_crawler-5.2.1/graph_crawler/observability/listeners/error_listener.py +18 -0
  401. graph_crawler-5.2.1/graph_crawler/observability/listeners/logging_listener.py +88 -0
  402. graph_crawler-5.2.1/graph_crawler/observability/listeners/metrics_listener.py +109 -0
  403. graph_crawler-5.2.1/graph_crawler/observability/listeners/node_listener.py +33 -0
  404. graph_crawler-5.2.1/graph_crawler/observability/listeners/plugin_listener.py +28 -0
  405. graph_crawler-5.2.1/graph_crawler/observability/listeners/storage_listener.py +21 -0
  406. graph_crawler-5.2.1/graph_crawler/observability/listeners/url_listener.py +29 -0
  407. graph_crawler-5.2.1/graph_crawler/observability/metrics/__init__.py +23 -0
  408. graph_crawler-5.2.1/graph_crawler/observability/metrics/memory_profiler.py +508 -0
  409. graph_crawler-5.2.1/graph_crawler/observability/metrics/metrics_collector.py +408 -0
  410. graph_crawler-5.2.1/graph_crawler/observability/metrics/prometheus_metrics.py +293 -0
  411. graph_crawler-5.2.1/graph_crawler/observability/metrics_core.py +395 -0
  412. graph_crawler-5.2.1/graph_crawler/observability/structured_logging.py +240 -0
  413. graph_crawler-5.2.1/graph_crawler/observability/tracing.py +291 -0
  414. graph_crawler-5.2.1/graph_crawler/optimizations/__init__.py +89 -0
  415. graph_crawler-5.2.1/graph_crawler/optimizations/generators.py +477 -0
  416. graph_crawler-5.2.1/graph_crawler/optimizations/memory_slots.py +641 -0
  417. graph_crawler-5.2.1/graph_crawler/optimizations/simhash_numba.py +284 -0
  418. graph_crawler-5.2.1/graph_crawler/shared/__init__.py +25 -0
  419. graph_crawler-5.2.1/graph_crawler/shared/constants.py +938 -0
  420. graph_crawler-5.2.1/graph_crawler/shared/dto/__init__.py +38 -0
  421. graph_crawler-5.2.1/graph_crawler/shared/dto/edge_dto.py +52 -0
  422. graph_crawler-5.2.1/graph_crawler/shared/dto/graph_dto.py +97 -0
  423. graph_crawler-5.2.1/graph_crawler/shared/dto/node_dto.py +193 -0
  424. graph_crawler-5.2.1/graph_crawler/shared/error_handling/__init__.py +15 -0
  425. graph_crawler-5.2.1/graph_crawler/shared/error_handling/error_handler.py +333 -0
  426. graph_crawler-5.2.1/graph_crawler/shared/exceptions.py +394 -0
  427. graph_crawler-5.2.1/graph_crawler/shared/platform/__init__.py +125 -0
  428. graph_crawler-5.2.1/graph_crawler/shared/platform/adaptive_resolver.py +414 -0
  429. graph_crawler-5.2.1/graph_crawler/shared/platform/config.py +635 -0
  430. graph_crawler-5.2.1/graph_crawler/shared/platform/detector.py +334 -0
  431. graph_crawler-5.2.1/graph_crawler/shared/platform/diagnostics.py +660 -0
  432. graph_crawler-5.2.1/graph_crawler/shared/platform/metrics.py +299 -0
  433. graph_crawler-5.2.1/graph_crawler/shared/security/__init__.py +22 -0
  434. graph_crawler-5.2.1/graph_crawler/shared/security/url_sanitizer.py +100 -0
  435. graph_crawler-5.2.1/graph_crawler/shared/security/url_validator.py +299 -0
  436. graph_crawler-5.2.1/graph_crawler/shared/utils/__init__.py +212 -0
  437. graph_crawler-5.2.1/graph_crawler/shared/utils/async_compat.py +140 -0
  438. graph_crawler-5.2.1/graph_crawler/shared/utils/bloom_filter.py +373 -0
  439. graph_crawler-5.2.1/graph_crawler/shared/utils/captcha/__init__.py +36 -0
  440. graph_crawler-5.2.1/graph_crawler/shared/utils/captcha/base.py +92 -0
  441. graph_crawler-5.2.1/graph_crawler/shared/utils/captcha/manager.py +474 -0
  442. graph_crawler-5.2.1/graph_crawler/shared/utils/celery_config.py +332 -0
  443. graph_crawler-5.2.1/graph_crawler/shared/utils/celery_helpers.py +153 -0
  444. graph_crawler-5.2.1/graph_crawler/shared/utils/cgroup_limits.py +227 -0
  445. graph_crawler-5.2.1/graph_crawler/shared/utils/content_decoder.py +150 -0
  446. graph_crawler-5.2.1/graph_crawler/shared/utils/distributed_rate_limiter.py +265 -0
  447. graph_crawler-5.2.1/graph_crawler/shared/utils/distributed_rate_limiter_backends.py +284 -0
  448. graph_crawler-5.2.1/graph_crawler/shared/utils/dns_cache.py +370 -0
  449. graph_crawler-5.2.1/graph_crawler/shared/utils/enterprise_ua_generator.py +294 -0
  450. graph_crawler-5.2.1/graph_crawler/shared/utils/event_publisher_mixin.py +188 -0
  451. graph_crawler-5.2.1/graph_crawler/shared/utils/fast_json.py +240 -0
  452. graph_crawler-5.2.1/graph_crawler/shared/utils/fingerprint.py +36 -0
  453. graph_crawler-5.2.1/graph_crawler/shared/utils/fingerprint_data.py +99 -0
  454. graph_crawler-5.2.1/graph_crawler/shared/utils/fingerprint_generators.py +128 -0
  455. graph_crawler-5.2.1/graph_crawler/shared/utils/fingerprint_profile.py +121 -0
  456. graph_crawler-5.2.1/graph_crawler/shared/utils/fingerprint_stealth.py +105 -0
  457. graph_crawler-5.2.1/graph_crawler/shared/utils/html_utils.py +118 -0
  458. graph_crawler-5.2.1/graph_crawler/shared/utils/id_generator.py +195 -0
  459. graph_crawler-5.2.1/graph_crawler/shared/utils/memory_optimizer.py +536 -0
  460. graph_crawler-5.2.1/graph_crawler/shared/utils/rate_limiter.py +185 -0
  461. graph_crawler-5.2.1/graph_crawler/shared/utils/regex_validator.py +966 -0
  462. graph_crawler-5.2.1/graph_crawler/shared/utils/shadow_dom.py +36 -0
  463. graph_crawler-5.2.1/graph_crawler/shared/utils/text_utils.py +387 -0
  464. graph_crawler-5.2.1/graph_crawler/shared/utils/url_patterns.py +135 -0
  465. graph_crawler-5.2.1/graph_crawler/shared/utils/url_utils.py +595 -0
  466. graph_crawler-5.2.1/graph_crawler/shared/utils/user_agent_rotator.py +333 -0
  467. graph_crawler-5.2.1/graph_crawler/shared/utils/validation_helpers.py +225 -0
  468. graph_crawler-5.2.1/graph_crawler/shared/utils/visualization.py +134 -0
  469. graph_crawler-5.2.1/graph_crawler/shared/utils/visualization_core.py +566 -0
  470. graph_crawler-5.2.1/graph_crawler/tools/__init__.py +1 -0
  471. graph_crawler-5.2.1/graph_crawler/tools/db_cleanup.py +263 -0
  472. graph_crawler-5.2.1/graph_crawler.egg-info/PKG-INFO +370 -0
  473. graph_crawler-5.2.1/graph_crawler.egg-info/SOURCES.txt +477 -0
  474. graph_crawler-5.2.1/pyproject.toml +301 -0
  475. graph_crawler-5.2.1/setup.cfg +4 -0
  476. graph_crawler-5.2.0/CHANGELOG.md +0 -3
  477. graph_crawler-5.2.0/CODE_STYLE.md +0 -1473
  478. graph_crawler-5.2.0/LICENSE +0 -21
  479. graph_crawler-5.2.0/MANIFEST.in +0 -19
  480. graph_crawler-5.2.0/PKG-INFO +0 -366
  481. graph_crawler-5.2.0/README.md +0 -245
  482. graph_crawler-5.2.0/graph_crawler/__init__.py +0 -478
  483. graph_crawler-5.2.0/graph_crawler/__version__.py +0 -7
  484. graph_crawler-5.2.0/graph_crawler/ai/__init__.py +0 -49
  485. graph_crawler-5.2.0/graph_crawler/api/__init__.py +0 -24
  486. graph_crawler-5.2.0/graph_crawler/api/_core.py +0 -281
  487. graph_crawler-5.2.0/graph_crawler/api/_distributed.py +0 -174
  488. graph_crawler-5.2.0/graph_crawler/api/_shared.py +0 -120
  489. graph_crawler-5.2.0/graph_crawler/api/_sitemap_distributed.py +0 -244
  490. graph_crawler-5.2.0/graph_crawler/api/async_.py +0 -325
  491. graph_crawler-5.2.0/graph_crawler/api/cli.py +0 -440
  492. graph_crawler-5.2.0/graph_crawler/api/client/__init__.py +0 -8
  493. graph_crawler-5.2.0/graph_crawler/api/client/client.py +0 -498
  494. graph_crawler-5.2.0/graph_crawler/api/history_manager.py +0 -82
  495. graph_crawler-5.2.0/graph_crawler/api/project_init.py +0 -194
  496. graph_crawler-5.2.0/graph_crawler/api/server/__init__.py +0 -18
  497. graph_crawler-5.2.0/graph_crawler/api/server/crawl_monitor.py +0 -145
  498. graph_crawler-5.2.0/graph_crawler/api/server/dashboard.py +0 -221
  499. graph_crawler-5.2.0/graph_crawler/api/server/rest_api.py +0 -704
  500. graph_crawler-5.2.0/graph_crawler/api/server/webhooks.py +0 -421
  501. graph_crawler-5.2.0/graph_crawler/api/server/websocket_manager.py +0 -89
  502. graph_crawler-5.2.0/graph_crawler/api/stats_collector.py +0 -115
  503. graph_crawler-5.2.0/graph_crawler/api/sync.py +0 -491
  504. graph_crawler-5.2.0/graph_crawler/application/__init__.py +0 -38
  505. graph_crawler-5.2.0/graph_crawler/application/bootstrap.py +0 -209
  506. graph_crawler-5.2.0/graph_crawler/application/context/__init__.py +0 -31
  507. graph_crawler-5.2.0/graph_crawler/application/context/dependency_registry.py +0 -354
  508. graph_crawler-5.2.0/graph_crawler/application/context/graph_context.py +0 -217
  509. graph_crawler-5.2.0/graph_crawler/application/context/merge_context.py +0 -221
  510. graph_crawler-5.2.0/graph_crawler/application/dto/__init__.py +0 -67
  511. graph_crawler-5.2.0/graph_crawler/application/dto/edge_dto.py +0 -25
  512. graph_crawler-5.2.0/graph_crawler/application/dto/graph_dto.py +0 -27
  513. graph_crawler-5.2.0/graph_crawler/application/dto/mappers/__init__.py +0 -14
  514. graph_crawler-5.2.0/graph_crawler/application/dto/mappers/edge_mapper.py +0 -149
  515. graph_crawler-5.2.0/graph_crawler/application/dto/mappers/graph_mapper.py +0 -614
  516. graph_crawler-5.2.0/graph_crawler/application/dto/mappers/node_data_codec.py +0 -190
  517. graph_crawler-5.2.0/graph_crawler/application/dto/mappers/node_mapper.py +0 -387
  518. graph_crawler-5.2.0/graph_crawler/application/dto/node_dto.py +0 -27
  519. graph_crawler-5.2.0/graph_crawler/application/dto/utils.py +0 -272
  520. graph_crawler-5.2.0/graph_crawler/application/services/__init__.py +0 -60
  521. graph_crawler-5.2.0/graph_crawler/application/services/application_container.py +0 -208
  522. graph_crawler-5.2.0/graph_crawler/application/services/driver_factory.py +0 -147
  523. graph_crawler-5.2.0/graph_crawler/application/services/exporters/__init__.py +0 -26
  524. graph_crawler-5.2.0/graph_crawler/application/services/exporters/base_exporter.py +0 -150
  525. graph_crawler-5.2.0/graph_crawler/application/services/exporters/csv_exporter.py +0 -318
  526. graph_crawler-5.2.0/graph_crawler/application/services/exporters/edge_exporter.py +0 -432
  527. graph_crawler-5.2.0/graph_crawler/application/services/exporters/excel_exporter.py +0 -301
  528. graph_crawler-5.2.0/graph_crawler/application/services/exporters/jsonl_exporter.py +0 -290
  529. graph_crawler-5.2.0/graph_crawler/application/services/exporters/node_exporter.py +0 -283
  530. graph_crawler-5.2.0/graph_crawler/application/services/exporters/parquet_exporter.py +0 -248
  531. graph_crawler-5.2.0/graph_crawler/application/services/exporters/sql_exporter.py +0 -267
  532. graph_crawler-5.2.0/graph_crawler/application/services/finalize.py +0 -115
  533. graph_crawler-5.2.0/graph_crawler/application/services/low_memory_graph_saver.py +0 -339
  534. graph_crawler-5.2.0/graph_crawler/application/services/resource_budget.py +0 -179
  535. graph_crawler-5.2.0/graph_crawler/application/services/scheduling/__init__.py +0 -12
  536. graph_crawler-5.2.0/graph_crawler/application/services/scheduling/rule_based_scheduler.py +0 -113
  537. graph_crawler-5.2.0/graph_crawler/application/services/storage_factory.py +0 -195
  538. graph_crawler-5.2.0/graph_crawler/application/use_cases/__init__.py +0 -11
  539. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/__init__.py +0 -81
  540. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/adaptive_throttler.py +0 -374
  541. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/async_bridge.py +0 -45
  542. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/base_spider.py +0 -156
  543. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/celery_batch_spider.py +0 -658
  544. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/celery_spider.py +0 -448
  545. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/checkpoint.py +0 -421
  546. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/crawl_coordinator.py +0 -1044
  547. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/dead_letter_queue.py +0 -413
  548. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/domain_rate_limiter.py +0 -262
  549. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/filters/__init__.py +0 -10
  550. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/filters/base.py +0 -74
  551. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/filters/domain_filter.py +0 -195
  552. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/filters/domain_patterns.py +0 -30
  553. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/filters/path_filter.py +0 -95
  554. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/incremental_strategy.py +0 -239
  555. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/link_processor.py +0 -908
  556. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/multiprocess_spider.py +0 -511
  557. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/node_scanner.py +0 -808
  558. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/parsers/__init__.py +0 -6
  559. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/parsers/base.py +0 -73
  560. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/parsers/html_parser.py +0 -154
  561. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/progress_tracker.py +0 -235
  562. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/scheduler.py +0 -747
  563. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/serialization_mixin.py +0 -218
  564. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/sitemap_parser.py +0 -662
  565. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/sitemap_processor.py +0 -401
  566. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/sitemap_spider.py +0 -608
  567. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/spider.py +0 -811
  568. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/spider_lifecycle.py +0 -108
  569. graph_crawler-5.2.0/graph_crawler/application/use_cases/crawling/worker_pool.py +0 -154
  570. graph_crawler-5.2.0/graph_crawler/application/use_cases/graph_export.py +0 -504
  571. graph_crawler-5.2.0/graph_crawler/application/use_cases/graph_merge/__init__.py +0 -33
  572. graph_crawler-5.2.0/graph_crawler/application/use_cases/graph_merge/graph_operations.py +0 -632
  573. graph_crawler-5.2.0/graph_crawler/application/use_cases/graph_merge/merge_strategies.py +0 -348
  574. graph_crawler-5.2.0/graph_crawler/data/__init__.py +0 -28
  575. graph_crawler-5.2.0/graph_crawler/data/backends/__init__.py +0 -21
  576. graph_crawler-5.2.0/graph_crawler/data/backends/memory.py +0 -486
  577. graph_crawler-5.2.0/graph_crawler/data/backends/sqlite.py +0 -1866
  578. graph_crawler-5.2.0/graph_crawler/data/interfaces.py +0 -575
  579. graph_crawler-5.2.0/graph_crawler/domain/__init__.py +0 -62
  580. graph_crawler-5.2.0/graph_crawler/domain/context/__init__.py +0 -14
  581. graph_crawler-5.2.0/graph_crawler/domain/context/crawl_context.py +0 -531
  582. graph_crawler-5.2.0/graph_crawler/domain/entities/__init__.py +0 -32
  583. graph_crawler-5.2.0/graph_crawler/domain/entities/edge.py +0 -345
  584. graph_crawler-5.2.0/graph_crawler/domain/entities/edge_analysis.py +0 -223
  585. graph_crawler-5.2.0/graph_crawler/domain/entities/graph.py +0 -4120
  586. graph_crawler-5.2.0/graph_crawler/domain/entities/graph_operations.py +0 -33
  587. graph_crawler-5.2.0/graph_crawler/domain/entities/graph_statistics.py +0 -13
  588. graph_crawler-5.2.0/graph_crawler/domain/entities/merge_strategies.py +0 -36
  589. graph_crawler-5.2.0/graph_crawler/domain/entities/node.py +0 -692
  590. graph_crawler-5.2.0/graph_crawler/domain/entities/redirect_mode.py +0 -23
  591. graph_crawler-5.2.0/graph_crawler/domain/entities/registries.py +0 -237
  592. graph_crawler-5.2.0/graph_crawler/domain/entities/sitemap_node.py +0 -74
  593. graph_crawler-5.2.0/graph_crawler/domain/entities/strategies.py +0 -202
  594. graph_crawler-5.2.0/graph_crawler/domain/events/__init__.py +0 -163
  595. graph_crawler-5.2.0/graph_crawler/domain/events/base.py +0 -58
  596. graph_crawler-5.2.0/graph_crawler/domain/events/crawl.py +0 -123
  597. graph_crawler-5.2.0/graph_crawler/domain/events/edge.py +0 -46
  598. graph_crawler-5.2.0/graph_crawler/domain/events/event_bus.py +0 -251
  599. graph_crawler-5.2.0/graph_crawler/domain/events/events.py +0 -313
  600. graph_crawler-5.2.0/graph_crawler/domain/events/fetch.py +0 -123
  601. graph_crawler-5.2.0/graph_crawler/domain/events/idempotent_subscriber.py +0 -120
  602. graph_crawler-5.2.0/graph_crawler/domain/events/legacy_type_map.py +0 -45
  603. graph_crawler-5.2.0/graph_crawler/domain/events/llm.py +0 -158
  604. graph_crawler-5.2.0/graph_crawler/domain/events/node.py +0 -124
  605. graph_crawler-5.2.0/graph_crawler/domain/events/plugin.py +0 -96
  606. graph_crawler-5.2.0/graph_crawler/domain/events/scheduler.py +0 -102
  607. graph_crawler-5.2.0/graph_crawler/domain/events/storage.py +0 -168
  608. graph_crawler-5.2.0/graph_crawler/domain/interfaces/__init__.py +0 -111
  609. graph_crawler-5.2.0/graph_crawler/domain/interfaces/adapter.py +0 -29
  610. graph_crawler-5.2.0/graph_crawler/domain/interfaces/control_channel.py +0 -371
  611. graph_crawler-5.2.0/graph_crawler/domain/interfaces/crawl_context.py +0 -49
  612. graph_crawler-5.2.0/graph_crawler/domain/interfaces/distributed_spider.py +0 -63
  613. graph_crawler-5.2.0/graph_crawler/domain/interfaces/driver.py +0 -88
  614. graph_crawler-5.2.0/graph_crawler/domain/interfaces/event_bus.py +0 -61
  615. graph_crawler-5.2.0/graph_crawler/domain/interfaces/exporters.py +0 -83
  616. graph_crawler-5.2.0/graph_crawler/domain/interfaces/filter.py +0 -19
  617. graph_crawler-5.2.0/graph_crawler/domain/interfaces/merge_context.py +0 -58
  618. graph_crawler-5.2.0/graph_crawler/domain/interfaces/node_interfaces.py +0 -376
  619. graph_crawler-5.2.0/graph_crawler/domain/interfaces/parser.py +0 -110
  620. graph_crawler-5.2.0/graph_crawler/domain/interfaces/plugin_manager.py +0 -53
  621. graph_crawler-5.2.0/graph_crawler/domain/interfaces/processor.py +0 -11
  622. graph_crawler-5.2.0/graph_crawler/domain/interfaces/scanner.py +0 -57
  623. graph_crawler-5.2.0/graph_crawler/domain/interfaces/scheduler.py +0 -43
  624. graph_crawler-5.2.0/graph_crawler/domain/interfaces/scheduling/__init__.py +0 -40
  625. graph_crawler-5.2.0/graph_crawler/domain/interfaces/scheduling/frontier.py +0 -97
  626. graph_crawler-5.2.0/graph_crawler/domain/interfaces/scheduling/scheduler.py +0 -107
  627. graph_crawler-5.2.0/graph_crawler/domain/interfaces/spider.py +0 -63
  628. graph_crawler-5.2.0/graph_crawler/domain/interfaces/stop_condition.py +0 -211
  629. graph_crawler-5.2.0/graph_crawler/domain/interfaces/storage/__init__.py +0 -43
  630. graph_crawler-5.2.0/graph_crawler/domain/interfaces/storage/base.py +0 -70
  631. graph_crawler-5.2.0/graph_crawler/domain/interfaces/storage/eviction.py +0 -102
  632. graph_crawler-5.2.0/graph_crawler/domain/interfaces/storage/queue.py +0 -234
  633. graph_crawler-5.2.0/graph_crawler/domain/services/__init__.py +0 -216
  634. graph_crawler-5.2.0/graph_crawler/domain/services/adjacency_maintenance.py +0 -95
  635. graph_crawler-5.2.0/graph_crawler/domain/services/cycle_detection.py +0 -92
  636. graph_crawler-5.2.0/graph_crawler/domain/services/degree_ranking.py +0 -47
  637. graph_crawler-5.2.0/graph_crawler/domain/services/depth_context.py +0 -123
  638. graph_crawler-5.2.0/graph_crawler/domain/services/display_title.py +0 -47
  639. graph_crawler-5.2.0/graph_crawler/domain/services/duplicate_detection.py +0 -141
  640. graph_crawler-5.2.0/graph_crawler/domain/services/duplicate_selector.py +0 -127
  641. graph_crawler-5.2.0/graph_crawler/domain/services/duplicate_stats.py +0 -63
  642. graph_crawler-5.2.0/graph_crawler/domain/services/edge_filter.py +0 -82
  643. graph_crawler-5.2.0/graph_crawler/domain/services/edge_statistics.py +0 -110
  644. graph_crawler-5.2.0/graph_crawler/domain/services/eviction_policy.py +0 -83
  645. graph_crawler-5.2.0/graph_crawler/domain/services/graph_query_cascade.py +0 -178
  646. graph_crawler-5.2.0/graph_crawler/domain/services/graph_statistics.py +0 -186
  647. graph_crawler-5.2.0/graph_crawler/domain/services/graph_traversal.py +0 -150
  648. graph_crawler-5.2.0/graph_crawler/domain/services/language_versions.py +0 -73
  649. graph_crawler-5.2.0/graph_crawler/domain/services/lsh_index.py +0 -99
  650. graph_crawler-5.2.0/graph_crawler/domain/services/minimap_builder.py +0 -147
  651. graph_crawler-5.2.0/graph_crawler/domain/services/node_content_resolver.py +0 -128
  652. graph_crawler-5.2.0/graph_crawler/domain/services/node_view_builder.py +0 -163
  653. graph_crawler-5.2.0/graph_crawler/domain/services/pagination_guards.py +0 -136
  654. graph_crawler-5.2.0/graph_crawler/domain/services/predicate_ops.py +0 -77
  655. graph_crawler-5.2.0/graph_crawler/domain/services/schema_filter.py +0 -138
  656. graph_crawler-5.2.0/graph_crawler/domain/services/search_haystack.py +0 -102
  657. graph_crawler-5.2.0/graph_crawler/domain/services/simhash_clustering.py +0 -96
  658. graph_crawler-5.2.0/graph_crawler/domain/services/simhash_fallback.py +0 -59
  659. graph_crawler-5.2.0/graph_crawler/domain/services/similarity_ranking.py +0 -62
  660. graph_crawler-5.2.0/graph_crawler/domain/services/text_search.py +0 -157
  661. graph_crawler-5.2.0/graph_crawler/domain/services/url_clustering.py +0 -88
  662. graph_crawler-5.2.0/graph_crawler/domain/services/url_deduplication.py +0 -101
  663. graph_crawler-5.2.0/graph_crawler/domain/services/url_normalizer.py +0 -108
  664. graph_crawler-5.2.0/graph_crawler/domain/services/url_rule_matcher.py +0 -103
  665. graph_crawler-5.2.0/graph_crawler/domain/services/url_tree_builder.py +0 -197
  666. graph_crawler-5.2.0/graph_crawler/domain/value_objects/__init__.py +0 -88
  667. graph_crawler-5.2.0/graph_crawler/domain/value_objects/configs.py +0 -884
  668. graph_crawler-5.2.0/graph_crawler/domain/value_objects/domain_patterns.py +0 -71
  669. graph_crawler-5.2.0/graph_crawler/domain/value_objects/fetch_options.py +0 -57
  670. graph_crawler-5.2.0/graph_crawler/domain/value_objects/html_document.py +0 -59
  671. graph_crawler-5.2.0/graph_crawler/domain/value_objects/lifecycle.py +0 -30
  672. graph_crawler-5.2.0/graph_crawler/domain/value_objects/models.py +0 -1316
  673. graph_crawler-5.2.0/graph_crawler/domain/value_objects/redirect_hop.py +0 -49
  674. graph_crawler-5.2.0/graph_crawler/domain/value_objects/scheduling/__init__.py +0 -23
  675. graph_crawler-5.2.0/graph_crawler/domain/value_objects/scheduling/crawl_request.py +0 -153
  676. graph_crawler-5.2.0/graph_crawler/domain/value_objects/scheduling/retry_policy.py +0 -109
  677. graph_crawler-5.2.0/graph_crawler/domain/value_objects/settings.py +0 -350
  678. graph_crawler-5.2.0/graph_crawler/domain/value_objects/url_normalization.py +0 -496
  679. graph_crawler-5.2.0/graph_crawler/domain/value_objects/views.py +0 -293
  680. graph_crawler-5.2.0/graph_crawler/extensions/__init__.py +0 -1
  681. graph_crawler-5.2.0/graph_crawler/extensions/middleware/__init__.py +0 -65
  682. graph_crawler-5.2.0/graph_crawler/extensions/middleware/base.py +0 -147
  683. graph_crawler-5.2.0/graph_crawler/extensions/middleware/cache_middleware.py +0 -277
  684. graph_crawler-5.2.0/graph_crawler/extensions/middleware/chain.py +0 -159
  685. graph_crawler-5.2.0/graph_crawler/extensions/middleware/error_recovery_middleware.py +0 -442
  686. graph_crawler-5.2.0/graph_crawler/extensions/middleware/logging_middleware.py +0 -108
  687. graph_crawler-5.2.0/graph_crawler/extensions/middleware/proxy_health.py +0 -144
  688. graph_crawler-5.2.0/graph_crawler/extensions/middleware/proxy_middleware.py +0 -208
  689. graph_crawler-5.2.0/graph_crawler/extensions/middleware/proxy_models.py +0 -84
  690. graph_crawler-5.2.0/graph_crawler/extensions/middleware/proxy_selection.py +0 -87
  691. graph_crawler-5.2.0/graph_crawler/extensions/middleware/rate_limit_middleware.py +0 -262
  692. graph_crawler-5.2.0/graph_crawler/extensions/middleware/request_response_middleware.py +0 -476
  693. graph_crawler-5.2.0/graph_crawler/extensions/middleware/retry_middleware.py +0 -279
  694. graph_crawler-5.2.0/graph_crawler/extensions/middleware/robots_cache.py +0 -85
  695. graph_crawler-5.2.0/graph_crawler/extensions/middleware/robots_middleware.py +0 -110
  696. graph_crawler-5.2.0/graph_crawler/extensions/middleware/robots_validator.py +0 -60
  697. graph_crawler-5.2.0/graph_crawler/extensions/middleware/user_agent_middleware.py +0 -251
  698. graph_crawler-5.2.0/graph_crawler/extensions/plugins/__init__.py +0 -57
  699. graph_crawler-5.2.0/graph_crawler/extensions/plugins/builtin/__init__.py +0 -7
  700. graph_crawler-5.2.0/graph_crawler/extensions/plugins/builtin/stats_export_plugin.py +0 -98
  701. graph_crawler-5.2.0/graph_crawler/extensions/plugins/crawl_engine/__init__.py +0 -24
  702. graph_crawler-5.2.0/graph_crawler/extensions/plugins/crawl_engine/base.py +0 -155
  703. graph_crawler-5.2.0/graph_crawler/extensions/plugins/crawl_engine/priority_provider.py +0 -247
  704. graph_crawler-5.2.0/graph_crawler/extensions/plugins/crawl_engine/smart_crawl.py +0 -306
  705. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/__init__.py +0 -128
  706. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/anti_bot_detection.py +0 -52
  707. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/anti_bot_playwright.py +0 -85
  708. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/anti_bot_scripts.py +0 -133
  709. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/anti_bot_stealth.py +0 -177
  710. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/base.py +0 -121
  711. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/captcha/__init__.py +0 -22
  712. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/captcha/detector.py +0 -94
  713. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/captcha/models.py +0 -74
  714. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/captcha/plugin.py +0 -228
  715. graph_crawler-5.2.0/graph_crawler/extensions/plugins/engine/captcha/services.py +0 -389
  716. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/__init__.py +0 -86
  717. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/base.py +0 -432
  718. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/content_extractors/__init__.py +0 -15
  719. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/content_extractors/base.py +0 -82
  720. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/content_extractors/goose3_extractor.py +0 -80
  721. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/content_extractors/newspaper_extractor.py +0 -93
  722. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/content_extractors/plugin.py +0 -132
  723. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/content_extractors/readability_extractor.py +0 -91
  724. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/defaults.py +0 -32
  725. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/extractors/__init__.py +0 -30
  726. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/extractors/email_extractor.py +0 -146
  727. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/extractors/phone_extractor.py +0 -136
  728. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/extractors/price_extractor.py +0 -137
  729. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/links.py +0 -184
  730. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/markdown_plugin.py +0 -249
  731. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/metadata.py +0 -391
  732. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/smart_page_finder.py +0 -749
  733. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/__init__.py +0 -51
  734. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/constants.py +0 -27
  735. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/exceptions.py +0 -18
  736. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/extractor.py +0 -361
  737. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/options.py +0 -62
  738. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/parsers/__init__.py +0 -25
  739. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/parsers/base.py +0 -43
  740. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/parsers/jsonld.py +0 -331
  741. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/parsers/microdata.py +0 -117
  742. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/parsers/opengraph.py +0 -66
  743. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/parsers/rdfa.py +0 -122
  744. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/parsers/twitter.py +0 -66
  745. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/plugin.py +0 -132
  746. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/structured_data/result.py +0 -233
  747. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/text.py +0 -76
  748. graph_crawler-5.2.0/graph_crawler/extensions/plugins/node/url_normalizer.py +0 -363
  749. graph_crawler-5.2.0/graph_crawler/extensions/plugins/registry.py +0 -97
  750. graph_crawler-5.2.0/graph_crawler/infrastructure/__init__.py +0 -1
  751. graph_crawler-5.2.0/graph_crawler/infrastructure/adapters/__init__.py +0 -60
  752. graph_crawler-5.2.0/graph_crawler/infrastructure/adapters/base.py +0 -498
  753. graph_crawler-5.2.0/graph_crawler/infrastructure/adapters/selectolax_adapter.py +0 -234
  754. graph_crawler-5.2.0/graph_crawler/infrastructure/messaging/__init__.py +0 -37
  755. graph_crawler-5.2.0/graph_crawler/infrastructure/messaging/celery_app.py +0 -202
  756. graph_crawler-5.2.0/graph_crawler/infrastructure/messaging/celery_batch.py +0 -284
  757. graph_crawler-5.2.0/graph_crawler/infrastructure/messaging/celery_job_task.py +0 -415
  758. graph_crawler-5.2.0/graph_crawler/infrastructure/messaging/celery_unified.py +0 -419
  759. graph_crawler-5.2.0/graph_crawler/infrastructure/messaging/config.py +0 -201
  760. graph_crawler-5.2.0/graph_crawler/infrastructure/messaging/easy_crawler.py +0 -279
  761. graph_crawler-5.2.0/graph_crawler/infrastructure/messaging/worker_api.py +0 -607
  762. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/__init__.py +0 -135
  763. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/auto_storage.py +0 -336
  764. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/base.py +0 -111
  765. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/eviction.py +0 -100
  766. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/graph_repository.py +0 -401
  767. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/json/__init__.py +0 -10
  768. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/json_storage.py +0 -375
  769. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/lmdb_eviction_storage.py +0 -403
  770. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/memory/__init__.py +0 -1
  771. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/memory_dedup_store.py +0 -91
  772. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/memory_frontier.py +0 -180
  773. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/memory_politeness_store.py +0 -88
  774. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/memory_storage.py +0 -166
  775. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/mongodb_storage.py +0 -383
  776. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/naming_strategy.py +0 -174
  777. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/postgresql_storage.py +0 -449
  778. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/protocols/__init__.py +0 -1
  779. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/redis_dedup_store.py +0 -119
  780. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/redis_politeness_store.py +0 -122
  781. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/repository.py +0 -130
  782. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/sqlite/__init__.py +0 -10
  783. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/sqlite_eviction_storage.py +0 -918
  784. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/sqlite_storage.py +0 -775
  785. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/unified/__init__.py +0 -47
  786. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/unified/file_job_storage.py +0 -245
  787. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/unified/file_queue_storage.py +0 -248
  788. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/unified/memory_job_storage.py +0 -94
  789. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/unified/memory_queue_storage.py +0 -117
  790. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/unified/postgresql_job_storage.py +0 -317
  791. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/unified/postgresql_queue_storage.py +0 -364
  792. graph_crawler-5.2.0/graph_crawler/infrastructure/persistence/unified/unified_storage.py +0 -244
  793. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/__init__.py +0 -135
  794. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/__init__.py +0 -38
  795. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/config.py +0 -47
  796. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/context.py +0 -55
  797. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/driver.py +0 -724
  798. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/driver_curl_cffi.py +0 -407
  799. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/plugins/__init__.py +0 -48
  800. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/plugins/autothrottle.py +0 -484
  801. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/plugins/autothrottle_adaptive.py +0 -1435
  802. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/plugins/headers.py +0 -69
  803. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/plugins/http_cache.py +0 -321
  804. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/plugins/rate_limiter.py +0 -96
  805. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/plugins/retry.py +0 -316
  806. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/async_http/stages.py +0 -33
  807. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/base.py +0 -324
  808. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/base_plugin.py +0 -151
  809. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/compression/__init__.py +0 -23
  810. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/compression/strategy.py +0 -219
  811. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/connection_pool.py +0 -349
  812. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/context.py +0 -114
  813. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/core/__init__.py +0 -15
  814. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/core/base_async.py +0 -378
  815. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/core/body_decoder.py +0 -26
  816. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/core/mixins.py +0 -258
  817. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/core/redirect_utils.py +0 -168
  818. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/escalation.py +0 -937
  819. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/factory.py +0 -210
  820. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/__init__.py +0 -19
  821. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/adaptive_semaphore.py +0 -65
  822. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/batch_scheduler.py +0 -764
  823. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/browser_factory.py +0 -576
  824. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/browser_profile.py +0 -718
  825. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/config.py +0 -84
  826. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/context.py +0 -46
  827. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/driver.py +0 -80
  828. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/engine.py +0 -465
  829. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/fetch_metrics.py +0 -115
  830. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/net/__init__.py +0 -41
  831. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/net/geoip.py +0 -136
  832. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/net/proxy_pool.py +0 -225
  833. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/net/rate_limiter.py +0 -139
  834. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/page_fetch.py +0 -864
  835. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/__init__.py +0 -67
  836. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/_network_record.py +0 -59
  837. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/captcha_detector.py +0 -315
  838. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/captcha_solver.py +0 -108
  839. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/cookie_consent.py +0 -565
  840. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/form_filler.py +0 -177
  841. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/human_bezier.py +0 -297
  842. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/network_log.py +0 -348
  843. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/ram_adaptive.py +0 -208
  844. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/screenshot.py +0 -169
  845. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/plugins/user_profile.py +0 -556
  846. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/pool_lifecycle.py +0 -658
  847. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/pooled_driver.py +0 -698
  848. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/stages.py +0 -35
  849. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/playwright/stealth_hints.py +0 -153
  850. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/plugin_manager.py +0 -316
  851. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/protocols.py +0 -118
  852. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/undetected/__init__.py +0 -8
  853. graph_crawler-5.2.0/graph_crawler/infrastructure/transport/undetected/async_driver.py +0 -465
  854. graph_crawler-5.2.0/graph_crawler/native/README.md +0 -110
  855. graph_crawler-5.2.0/graph_crawler/native/__init__.py +0 -200
  856. graph_crawler-5.2.0/graph_crawler/native/bloom_filter.pyx +0 -255
  857. graph_crawler-5.2.0/graph_crawler/native/html_parser.pyx +0 -262
  858. graph_crawler-5.2.0/graph_crawler/native/setup.py +0 -101
  859. graph_crawler-5.2.0/graph_crawler/native/url_utils.pyx +0 -209
  860. graph_crawler-5.2.0/graph_crawler/observability/__init__.py +0 -62
  861. graph_crawler-5.2.0/graph_crawler/observability/decorators/__init__.py +0 -11
  862. graph_crawler-5.2.0/graph_crawler/observability/decorators/cache.py +0 -126
  863. graph_crawler-5.2.0/graph_crawler/observability/decorators/log.py +0 -56
  864. graph_crawler-5.2.0/graph_crawler/observability/decorators/retry.py +0 -121
  865. graph_crawler-5.2.0/graph_crawler/observability/decorators/timing.py +0 -43
  866. graph_crawler-5.2.0/graph_crawler/observability/error_tracing.py +0 -363
  867. graph_crawler-5.2.0/graph_crawler/observability/extensions/__init__.py +0 -18
  868. graph_crawler-5.2.0/graph_crawler/observability/extensions/memory_guard.py +0 -237
  869. graph_crawler-5.2.0/graph_crawler/observability/extensions/state_manager.py +0 -319
  870. graph_crawler-5.2.0/graph_crawler/observability/listeners/__init__.py +0 -33
  871. graph_crawler-5.2.0/graph_crawler/observability/listeners/base.py +0 -82
  872. graph_crawler-5.2.0/graph_crawler/observability/listeners/base_metrics_listener.py +0 -18
  873. graph_crawler-5.2.0/graph_crawler/observability/listeners/crawl_listener.py +0 -28
  874. graph_crawler-5.2.0/graph_crawler/observability/listeners/dlq_listener.py +0 -215
  875. graph_crawler-5.2.0/graph_crawler/observability/listeners/error_listener.py +0 -18
  876. graph_crawler-5.2.0/graph_crawler/observability/listeners/logging_listener.py +0 -88
  877. graph_crawler-5.2.0/graph_crawler/observability/listeners/metrics_listener.py +0 -109
  878. graph_crawler-5.2.0/graph_crawler/observability/listeners/node_listener.py +0 -33
  879. graph_crawler-5.2.0/graph_crawler/observability/listeners/plugin_listener.py +0 -28
  880. graph_crawler-5.2.0/graph_crawler/observability/listeners/storage_listener.py +0 -21
  881. graph_crawler-5.2.0/graph_crawler/observability/listeners/url_listener.py +0 -29
  882. graph_crawler-5.2.0/graph_crawler/observability/metrics/__init__.py +0 -23
  883. graph_crawler-5.2.0/graph_crawler/observability/metrics/memory_profiler.py +0 -508
  884. graph_crawler-5.2.0/graph_crawler/observability/metrics/metrics_collector.py +0 -408
  885. graph_crawler-5.2.0/graph_crawler/observability/metrics/prometheus_metrics.py +0 -293
  886. graph_crawler-5.2.0/graph_crawler/observability/metrics_core.py +0 -395
  887. graph_crawler-5.2.0/graph_crawler/observability/structured_logging.py +0 -240
  888. graph_crawler-5.2.0/graph_crawler/observability/tracing.py +0 -291
  889. graph_crawler-5.2.0/graph_crawler/optimizations/__init__.py +0 -89
  890. graph_crawler-5.2.0/graph_crawler/optimizations/generators.py +0 -477
  891. graph_crawler-5.2.0/graph_crawler/optimizations/memory_slots.py +0 -641
  892. graph_crawler-5.2.0/graph_crawler/optimizations/simhash_numba.py +0 -284
  893. graph_crawler-5.2.0/graph_crawler/shared/__init__.py +0 -25
  894. graph_crawler-5.2.0/graph_crawler/shared/constants.py +0 -938
  895. graph_crawler-5.2.0/graph_crawler/shared/dto/__init__.py +0 -38
  896. graph_crawler-5.2.0/graph_crawler/shared/dto/edge_dto.py +0 -52
  897. graph_crawler-5.2.0/graph_crawler/shared/dto/graph_dto.py +0 -97
  898. graph_crawler-5.2.0/graph_crawler/shared/dto/node_dto.py +0 -193
  899. graph_crawler-5.2.0/graph_crawler/shared/error_handling/__init__.py +0 -15
  900. graph_crawler-5.2.0/graph_crawler/shared/error_handling/error_handler.py +0 -333
  901. graph_crawler-5.2.0/graph_crawler/shared/exceptions.py +0 -394
  902. graph_crawler-5.2.0/graph_crawler/shared/platform/__init__.py +0 -125
  903. graph_crawler-5.2.0/graph_crawler/shared/platform/adaptive_resolver.py +0 -414
  904. graph_crawler-5.2.0/graph_crawler/shared/platform/config.py +0 -635
  905. graph_crawler-5.2.0/graph_crawler/shared/platform/detector.py +0 -334
  906. graph_crawler-5.2.0/graph_crawler/shared/platform/diagnostics.py +0 -660
  907. graph_crawler-5.2.0/graph_crawler/shared/platform/metrics.py +0 -299
  908. graph_crawler-5.2.0/graph_crawler/shared/security/__init__.py +0 -22
  909. graph_crawler-5.2.0/graph_crawler/shared/security/url_sanitizer.py +0 -100
  910. graph_crawler-5.2.0/graph_crawler/shared/security/url_validator.py +0 -299
  911. graph_crawler-5.2.0/graph_crawler/shared/utils/__init__.py +0 -212
  912. graph_crawler-5.2.0/graph_crawler/shared/utils/async_compat.py +0 -140
  913. graph_crawler-5.2.0/graph_crawler/shared/utils/bloom_filter.py +0 -373
  914. graph_crawler-5.2.0/graph_crawler/shared/utils/captcha/__init__.py +0 -36
  915. graph_crawler-5.2.0/graph_crawler/shared/utils/captcha/base.py +0 -92
  916. graph_crawler-5.2.0/graph_crawler/shared/utils/captcha/manager.py +0 -474
  917. graph_crawler-5.2.0/graph_crawler/shared/utils/celery_config.py +0 -332
  918. graph_crawler-5.2.0/graph_crawler/shared/utils/celery_helpers.py +0 -153
  919. graph_crawler-5.2.0/graph_crawler/shared/utils/cgroup_limits.py +0 -227
  920. graph_crawler-5.2.0/graph_crawler/shared/utils/content_decoder.py +0 -150
  921. graph_crawler-5.2.0/graph_crawler/shared/utils/distributed_rate_limiter.py +0 -265
  922. graph_crawler-5.2.0/graph_crawler/shared/utils/distributed_rate_limiter_backends.py +0 -284
  923. graph_crawler-5.2.0/graph_crawler/shared/utils/dns_cache.py +0 -370
  924. graph_crawler-5.2.0/graph_crawler/shared/utils/enterprise_ua_generator.py +0 -294
  925. graph_crawler-5.2.0/graph_crawler/shared/utils/event_publisher_mixin.py +0 -188
  926. graph_crawler-5.2.0/graph_crawler/shared/utils/fast_json.py +0 -240
  927. graph_crawler-5.2.0/graph_crawler/shared/utils/fingerprint.py +0 -36
  928. graph_crawler-5.2.0/graph_crawler/shared/utils/fingerprint_data.py +0 -99
  929. graph_crawler-5.2.0/graph_crawler/shared/utils/fingerprint_generators.py +0 -128
  930. graph_crawler-5.2.0/graph_crawler/shared/utils/fingerprint_profile.py +0 -121
  931. graph_crawler-5.2.0/graph_crawler/shared/utils/fingerprint_stealth.py +0 -105
  932. graph_crawler-5.2.0/graph_crawler/shared/utils/html_utils.py +0 -118
  933. graph_crawler-5.2.0/graph_crawler/shared/utils/id_generator.py +0 -195
  934. graph_crawler-5.2.0/graph_crawler/shared/utils/memory_optimizer.py +0 -536
  935. graph_crawler-5.2.0/graph_crawler/shared/utils/rate_limiter.py +0 -185
  936. graph_crawler-5.2.0/graph_crawler/shared/utils/regex_validator.py +0 -966
  937. graph_crawler-5.2.0/graph_crawler/shared/utils/text_utils.py +0 -387
  938. graph_crawler-5.2.0/graph_crawler/shared/utils/url_patterns.py +0 -135
  939. graph_crawler-5.2.0/graph_crawler/shared/utils/url_utils.py +0 -595
  940. graph_crawler-5.2.0/graph_crawler/shared/utils/user_agent_rotator.py +0 -333
  941. graph_crawler-5.2.0/graph_crawler/shared/utils/validation_helpers.py +0 -225
  942. graph_crawler-5.2.0/graph_crawler/shared/utils/visualization.py +0 -134
  943. graph_crawler-5.2.0/graph_crawler/shared/utils/visualization_core.py +0 -566
  944. graph_crawler-5.2.0/graph_crawler/tools/__init__.py +0 -1
  945. graph_crawler-5.2.0/graph_crawler/tools/db_cleanup.py +0 -263
  946. graph_crawler-5.2.0/graph_crawler.egg-info/PKG-INFO +0 -366
  947. graph_crawler-5.2.0/graph_crawler.egg-info/SOURCES.txt +0 -476
  948. graph_crawler-5.2.0/pyproject.toml +0 -301
  949. graph_crawler-5.2.0/setup.cfg +0 -4
  950. {graph_crawler-5.2.0 → graph_crawler-5.2.1}/graph_crawler.egg-info/dependency_links.txt +0 -0
  951. {graph_crawler-5.2.0 → graph_crawler-5.2.1}/graph_crawler.egg-info/entry_points.txt +0 -0
  952. {graph_crawler-5.2.0 → graph_crawler-5.2.1}/graph_crawler.egg-info/requires.txt +0 -0
  953. {graph_crawler-5.2.0 → graph_crawler-5.2.1}/graph_crawler.egg-info/top_level.txt +0 -0
@@ -0,0 +1,244 @@
1
+ # Changelog
2
+
3
+ ## 5.2.1 — 2026-06
4
+
5
+ ### Fixed (freelance cases 33/34 — `ai-graph-crawler/docs/FREELANCE_CASES.md`)
6
+ - **Captured XHR/fetch traffic could not be replayed outside the browser.** `NetworkLogPlugin` recorded the
7
+ URL and method of a request but not its body, so every POST/GraphQL endpoint (robota.ua lists vacancies via
8
+ `POST dracula.robota.ua/?q=getPublishedVacanciesList`) was unusable: a GET of the same URL returns 400.
9
+ Records now carry `post_data` and (on `response`) `request_headers`.
10
+ - **GraphQL responses overwrote each other.** `body_ref` was `sha1(url|status|content-type)` — all operations
11
+ POSTed to one `/graphql` URL shared a key and only the last body survived. The key now includes method and
12
+ request body.
13
+ - **JSON family by default.** The capture allow-list matched exact MIME types only; `application/graphql-
14
+ response+json`, `problem+json`, `vnd.api+json`, `text/json` were dropped. Without an explicit
15
+ `capture_content_types` every `*/json` and `*+json` type is captured (RFC 6839). Default `max_body_kb` 64 → 256
16
+ (listing APIs routinely exceed 64 KB).
17
+ - **Shadow DOM was invisible.** `page.content()` serializes only light DOM: content of open shadow roots (web
18
+ components, embedded price widgets) never reached the node. When a page has open shadow roots, the browser
19
+ driver serializes it with `Element.getHTML({shadowRoots})` and expands the declarative shadow roots into their
20
+ hosts (`shared/utils/shadow_dom.expose_shadow_roots`) — Lexbor, like the HTML spec, does not descend into
21
+ `<template>` content, so a plain declarative-shadow-DOM serialization would still hide it from selectors and link
22
+ extraction. Pages without shadow roots are untouched.
23
+ - `tests/unit/domain/entities/test_graph_new_features.py` still expected the `DeprecationWarning` that
24
+ `export_nodes()` stopped emitting in 4aab7525; it now asserts the opposite.
25
+
26
+ ### Fixed (real-site audit, round 2 — `docs/REAL_SITE_TESTS.md` §1.2)
27
+ - **Ctrl+C during `crawl()` hung until the crawl-level timeout** (28 s with `timeout=25`; forever without
28
+ one). `asyncio.wait_for` in Python 3.11 swallows the outer cancellation when the awaited coroutine finishes
29
+ at the same moment, so some workers survived `KeyboardInterrupt` and kept crawling. `NodeScanner` and the
30
+ escalation tier budget now use `asyncio.timeout()`; `CrawlCoordinator` cancels its workers on
31
+ `CancelledError`. Ctrl+C now returns in ~0.3 s.
32
+ - **`same_domain=False` was ignored** — without `allowed_domains` the `DomainFilter` default
33
+ (`domain+subdomains`) still applied and external links never entered the graph. Now maps to `allowed_domains=["*"]`.
34
+ - **`graph.metadata["stop_reason"]` was `None` after `timeout=` / `max_pages`** — only stop conditions were
35
+ recorded. Now `"timeout"`, `"max_pages"` or `"limit"`.
36
+ - **Network errors were invisible on the node**: a DNS/connection failure left `response_status=None`,
37
+ `scanned=True` and no message; `get_failed_nodes()` returned `[]`. The error text is now in
38
+ `node.metadata["error"]`, the HTTP status (if any) is kept, and `get_failed_nodes()` with default
39
+ arguments includes network-error nodes.
40
+ - **`storage="json", storage_config={"path": "site.json"}` was silently ignored** (file written to
41
+ `crawler_data/json/graph.json`). `path` is now honoured, like for sqlite (`JSONStorage(file_name=)`).
42
+ - `Graph.export_nodes()` / `Graph.export_edges()` are no longer deprecated: they are the public one-liners the
43
+ README shows and now delegate to `GraphExportUseCase` silently (no `DeprecationWarning`).
44
+ - `tests/manual/real_sites/run_all.py -j N` runs scenarios in parallel; `tests/manual/real_sites/test_user_cases.py`
45
+ — 23 pytest user scenarios on Wikipedia / robota.ua / GitHub / example.com, each hard-capped at 40 s.
46
+
47
+ ### Changed
48
+ - **Engine contract verified end-to-end** (audit `06_browser_engine.md` §4, now closed). `tests/transport/
49
+ test_engine_contract.py` drives the real `PlaywrightDriver.fetch()` through three engines registered via the
50
+ public `register_engine()` on a recording fake SDK: the call sequence is byte-for-byte identical across
51
+ engines, stealth is injected iff `provides_stealth is False`, and `executable_path`/`ignore_default_args`/
52
+ launch args come only from the engine. No runtime code changed.
53
+ - **`LexborDocument.clean_text()` no longer re-parses the page** (audit `01_parser_audit.md` §4 "parse once",
54
+ `00_interim_analysis.md` §3.4). To strip `script/style/noscript/svg/head` without mutating the shared tree it
55
+ serialised the document and built a second `LexborHTMLParser` — i.e. every page with the default
56
+ `TextExtractorPlugin` was parsed twice (`count_parses.py`: 2.0 → **1.0** per page; with `MarkdownPlugin`
57
+ 1 parse + 1 clone). It now uses `tree.clone()`. `docs/audit/benchmarks/count_parses.py` works without
58
+ bs4/lxml and counts `generate_from_tree` clones.
59
+ - **One `ContentDecoder` for every HTTP tier** (audit `docs/audit/01_parser_audit.md` §5 "no parser accepts
60
+ bytes"). `AsyncDriver` (aiohttp) and `AsyncCurlCffiDriver` (curl_cffi) no longer rely on the client's own
61
+ `response.text`/`.text()`: they read the raw body and decode it through `ContentDecoder`
62
+ (`Content-Type` charset → `<meta charset>` → BOM → chardet → strict utf-8). Pages whose charset is only
63
+ declared in `<meta>` (e.g. windows-1251 without a header) were previously decoded as utf-8 by aiohttp,
64
+ failed, and silently became `html=None` with a "successful" 200. An undecodable body is now reported as
65
+ `FetchResponse.error` (`"ContentDecoder: cannot decode body …"`) with the status code preserved;
66
+ `ConnectionPoolManager.fetch_text()` goes through the same decoder. `FetchResponse.html` is a strict
67
+ `str` field — passing `bytes` raises `ValidationError` instead of being coerced. Browser tiers
68
+ (Playwright `page.content()`, nodriver `tab.get_content()`) already return `str`. Contract test:
69
+ `tests/transport/test_html_is_str_contract.py` (driver matrix returns `str`; cp1251 via meta/header;
70
+ binary → error).
71
+ - **Lazy public facade** (audit `docs/audit/04_dependency_map.md` §5 п.3). `graph_crawler/__init__.py` now
72
+ eagerly imports only `crawl`, `async_crawl`, `Graph`, `Node`, `save_graph`, `load_graph`,
73
+ `BaseStopCondition`; every other name in `__all__` (drivers, storages, exceptions, settings, views,
74
+ celery tasks, …) resolves on first access via module `__getattr__` and is cached. `aiohttp` is no longer
75
+ loaded by `import graph_crawler`. `bootstrap()` no longer calls `collect_system_metrics()`
76
+ (`psutil.cpu_percent(interval=0.1)` blocked import for 100 ms for a DEBUG line). Import time here:
77
+ 470 ms → 228 ms. Optional names (`PlaywrightDriver`, `celery`, `EasyDistributedCrawler`, …) still return
78
+ `None` without their extra.
79
+ - **Escalation re-probe replays the solving tier's User-Agent** (audit `03_escalation.md` §3/§6).
80
+ Playwright and nodriver now export `navigator.userAgent` as `extras["user_agent"]`;
81
+ `SessionState.absorb` records it (pinned once the session is solved, like `impersonate`/`proxy`) and
82
+ `EscalatingDriver._fetch_tier` sends it as `extra_headers={"User-Agent": …}` to HTTP/TLS tiers together
83
+ with the stored cookies. `cf_clearance` is bound to UA+IP+JA4, so a re-probe on Tier 1 with aiohttp's
84
+ default UA was rejected and the host never descended from the browser tier.
85
+
86
+ ### Removed
87
+ - **`NodePluginContext.parser`** (audit `01_parser_audit.md` §4 "parse once"). Node plugins now read the
88
+ single Lexbor tree through the `HTMLDocument`/`HTMLNode` protocols: `LinkExtractorPlugin`
89
+ (`doc.css("a[href]")`, `doc.base_href()`), `MetadataExtractorPlugin`, `TextExtractorPlugin`
90
+ (`doc.clean_text()`, new in the protocol), `StructuredDataPlugin` (OG/Twitter/Microdata/RDFa parsers take
91
+ an `HTMLDocument`; `StructuredDataExtractor.extract(html=, doc=)`), `Email`/`PhoneExtractorPlugin`.
92
+ Migration: `context.parser.find_all(sel)` → `context.html_tree.css(sel)`, `.find()` → `.css_first()`,
93
+ `el.get_attribute()` → `el.attr()`. Fixed along the way in `LexborNode`: `attr()` returns `""` (not
94
+ `None`) for valueless boolean attributes such as `itemscope`, so nested Microdata/RDFa items are now
95
+ detected; `css()`/`css_first()` return descendants only (selectolax included the node itself, which made
96
+ Microdata recurse to `max_nesting_depth`).
97
+ - **`PooledPlaywrightDriver` legacy batch path** (audit `06_browser_engine.md` §3): `batch_legacy.py`
98
+ (`LegacyBatch._fetch_batch_legacy`, `_fetch_chain`) is gone. `persistent_browser=False` keeps its
99
+ "launch/stop per batch" semantics through the pool path: after a batch, once no fetch is in flight, the
100
+ pool and the engine session are closed (`_close_pool()` + `_stop_persistent_session()`, shared with
101
+ `close()`). Dead `self.playwright`/`self.browsers` cleanup removed from `close()`.
102
+ - **Escalation 6.0 (audit `docs/audit/03_escalation.md`, Vector 2).** `classify_block()` rewritten to the
103
+ 6.0 decision table: challenge/captcha vendor headers first, then unambiguous body captcha/challenge
104
+ markers (ahead of vendor hard-block headers), then short/blocking-page widgets, status-based verdicts
105
+ and empty-2xx. A bare `401/403/405` with no vendor markers is no longer a block. The classifier corpus
106
+ (`docs/audit/benchmarks/classifier_corpus.py`) goes 25/37 → **37/37**.
107
+ - `needs_browser` heuristic (SPA shell: little visible text + SPA root / `<noscript>` JS hint / no
108
+ `<a href>`) is now the default `EscalationPolicy.needs_browser`; on a clean HTTP/TLS response it jumps
109
+ straight to the first browser tier (`escalation_reason="needs_browser"`).
110
+ - Per-tier `TierTimeouts` + `escalation_deadline_s` (60s) budget: a tier is skipped (last response
111
+ returned, browser never started) when the remaining budget is below its `min_budget`; each tier fetch
112
+ is wrapped in `asyncio.wait_for`. New `PER_NODE_FETCH_TIMEOUT` constant with a validator warning.
113
+ - Cross-tier session: `SessionState` / `HostSessionStore` carry solved cookies (`cf_clearance`, `__cf_bm`,
114
+ `datadome`, …) forward and back down to cheaper tiers on re-probe; `impersonate`/`proxy` are pinned once
115
+ a session is solved. curl_cffi pins the impersonate fingerprint; Playwright/nodriver export context
116
+ cookies via `extras["cookies"]`.
117
+ - `extras` contract: every driver stamps `channel`/`driver`/`engine` (via `BaseDriver`/`BaseAsyncDriver`
118
+ `_stamp_extras` + `_finalize_response`) even outside escalation.
119
+ - New Prometheus metrics `crawl_fetch_duration_seconds{channel,engine}`, `crawl_escalations_total`,
120
+ `crawl_escalation_deadline_hits_total`.
121
+
122
+ - **HTML parsing: Lexbor (selectolax) is the only core parser** (audit `docs/audit/01_parser_audit.md`).
123
+ `beautifulsoup4`, `lxml`, `lxml_html_clean` removed from `[project].dependencies`;
124
+ `BeautifulSoupAdapter`, `LxmlAdapter`, `ScrapyAdapter` deleted. New `HTMLDocument` / `HTMLNode`
125
+ protocols in `domain/value_objects/html_document.py`, implemented by `LexborDocument` in
126
+ `infrastructure/adapters/selectolax_adapter.py`. `<template>` is renamed to `gc-template` before
127
+ parsing so Vue/React SSR links inside templates are not lost. `IParser.parse()` returns `HTMLDocument`;
128
+ `NodePluginContext.html_tree` is now a `LexborDocument`. `get_parser()` accepts `auto|selectolax|lexbor`.
129
+ - `HTMLUtils.extract_links/extract_text/extract_metadata` accept an `HTMLDocument` (string input still
130
+ works but is deprecated).
131
+ - `SitemapParser.parse_large_sitemap_streaming()` uses stdlib `iterparse` by default; lxml is an
132
+ optional fast-path via the new extra `sitemap-fast`.
133
+
134
+ - **`html2md-clean` moved to the optional extra `markdown`** (`pip install "graph-crawler[markdown]"`);
135
+ `MarkdownGenerator/MarkdownOptions/MarkdownResult` re-exports in `graph_crawler.shared.utils` are lazy.
136
+ `MarkdownPlugin` feeds the already-parsed Lexbor tree to html2md-clean 0.5 (`generate_from_tree`) —
137
+ one parse per page instead of 2–4. `import graph_crawler` no longer loads bs4/lxml.
138
+
139
+ - **Dependency map 6.0** (audit `docs/audit/04_dependency_map.md`). Core is now 10 packages: `requests`,
140
+ `httpx`, `pydantic-settings`, `pybloom-live`, `fastapi`, `tenacity`, `stop-words`, `tiktoken`,
141
+ `markdown-it-py` removed from `[project].dependencies`. New extras: `browser` (`playwright` kept as alias),
142
+ `server` (fastapi/uvicorn/websockets), `text` (tiktoken/stop-words), `captcha`; `markdown` also pulls
143
+ `markdown-it-py`; `all` is recursive. Extras `cloudscraper` and `undetected-sync` dropped.
144
+ Extra-gated imports are lazy and fail fast with `requires extra '<name>'`; `transport.PlaywrightDriver/
145
+ RequestsDriver/CloudscraperDriver/RequestsSessionAdapter` are lazy re-exports (ImportError instead of `None`).
146
+ `CrawlerSettings` keeps `GC_*`/`__`/`.env` without pydantic-settings; `CrawlerConfig` is a plain `BaseModel`.
147
+
148
+ - **Transport eradication 6.0** (audit `docs/audit/02_codebase_audit.md`). Deleted: sync drivers
149
+ (`RequestsDriver`, `CloudscraperDriver`, `UndetectedChromeDriver`, `BotasaurusDriver`, `BaseSyncDriver`),
150
+ `AsyncDriverHTTP2` (httpx), `AsyncCloudscraperDriver`, `tls_client.py`, `StealthHTTPDriver`,
151
+ `session_manager/session_adapters/session_protocol`, `shared/utils/captcha_bypass.py`,
152
+ `shared/utils/proxy_manager.py`, packages `transport/http` and `transport/browser`.
153
+ `DriverType` is now `aiohttp | tls | playwright | nodriver | escalating` (+ `asyncio` alias);
154
+ strings `http`/`async`/`asyncio` → `aiohttp` and `stealth`/`curl_cffi` → `tls` are accepted for one
155
+ release with `DeprecationWarning`. One `AsyncDriver` (former `driver_adaptive.py` is now
156
+ `async_http/driver.py`); request hints (`referer`, `extra_headers`, `cookies`) are honoured.
157
+ `requests` is gone from the package: proxy health-check, CAPTCHA solvers/bypass and `SitemapParser`
158
+ use aiohttp (`SitemapParser.parse_sitemap/parse_from_robots` are `asyncio.run` wrappers,
159
+ `http_client=` is deprecated and ignored). `BloomFilter` is pure-python (xxhash) — `pybloom-live`
160
+ no longer needed.
161
+ `import graph_crawler` no longer loads any extra (guarded by `tests/unit/test_import_surface.py`), 3.8 s → 1.7 s here.
162
+ Follow-up (02 §6 close-out): `shared/constants.py` no longer imports aiohttp — `br`/`zstd` are advertised
163
+ by `transport.compression.runtime_browser_headers()` only when the runtime can decode them;
164
+ one driver registry — `application.services.driver_factory` delegates to
165
+ `transport.factory.DriverFactory` (`register_factory`, `registered_names`); `SitemapParser(driver=)`
166
+ fetches robots.txt/sitemaps through the crawl `IDriver` (same tier chain), `SitemapSpider` passes its
167
+ driver, aiohttp is used directly only for binary `.gz`; `tests/transport/test_all_drivers_report_redirects.py`
168
+ is an `IDriver` acceptance matrix (aiohttp / tls / fake playwright / fake nodriver / escalating).
169
+
170
+ - **Escalation (audit `docs/audit/03_escalation.md` §6/§7)**: `EscalationPolicy.reprobe_interval` (5 min) —
171
+ one request per interval re-probes tier 0 for a host remembered on a higher tier (no herd of browser
172
+ re-escalations after TTL); `EscalationPolicy.max_hosts` (10k) — `HostTierMemory` is an LRU and drops
173
+ per-host locks together with entries. In strict mode (`GC_ENGINE_STRICT`) an `ImportError` raised *during*
174
+ `fetch` (lazy browser start without the SDK) now propagates instead of being turned into a network error.
175
+
176
+ - **`extras` contract persisted (audit `docs/audit/05_migration_guide.md` §4).** New
177
+ `FetchResponse.fetch_provenance()` / `FETCH_EXTRAS_KEYS`: a JSON-safe slice
178
+ (`bot_block_status, channel, driver, engine, escalations` + `escalation_reason`; cookies/impersonate dropped).
179
+ `NodeScanner` stores it in `node.metadata["fetch"]` for every response, including blocked/error ones, so it
180
+ survives JSON/SQLite/MongoDB/PostgreSQL storage. Contract test `tests/transport/test_extras_contract.py`.
181
+ - `docs/audit/05_migration_guide.md` — 5.2 → 6.0 migration guide (extras, drivers, parser, settings, sitemap, checklist).
182
+
183
+ ### Fixed
184
+ - Transport `extras` (`bot_block_status`, tier, escalations) were dropped after fetch and never reached the
185
+ node or storage; for blocked pages nothing was transferred at all.
186
+ - `SmartPageFinder` read `html_tree.text` as a property; with Lexbor it is a method — page text was
187
+ silently dropped.
188
+ - `AsyncUndetectedDriver` accepts a plain `dict` config (`AsyncUndetectedConfig.from_mapping`) — building
189
+ the `nodriver` tier through `DriverFactory.create(DriverType.NODRIVER, config={...})` (as `EscalatingDriver`
190
+ does) raised `AttributeError`.
191
+
192
+ ## 5.2.0 — 2026-06
193
+
194
+ ### Added
195
+ - `infrastructure/transport/escalation.py`: `classify_block()` (Cloudflare / Akamai / DataDome /
196
+ PerimeterX / Incapsula markers, 403/429/503, empty 200), `EscalationPolicy`, `EscalationTier`,
197
+ `EscalatingDriver` — chain http → tls → browser → undetected with `max_tier`.
198
+ `driver="escalating"` works in `crawl()` / `async_crawl()` / `Crawler` / CLI.
199
+ - `HostTierMemory`: adaptive per-host tier memory — TTL from the moment of decision
200
+ (`GC_TIER_TTL`, default 1200 s), invalidation when the remembered tier gets blocked,
201
+ one escalation per host at a time (per-host lock). Per process.
202
+ - Strict engine mode: `GC_ENGINE_STRICT=1`, `{"browser_engine": {"strict": True}}` or
203
+ `driver_config={"engine_strict": True}` — `ImportError` instead of a silent fallback
204
+ `cloakbrowser → patchright → playwright` or a skipped escalation tier.
205
+ - Browser engine registry in `playwright/engine.py`: `register_engine()`, `resolve_engine()`,
206
+ `registered_engines()`. Built-in engines `cloakbrowser` → `patchright` → `playwright` with
207
+ automatic fail-open. `GC_BROWSER_ENGINE` env selects the engine when config has none.
208
+ `PlaywrightBrowserEngine.effective_name` / `fallback_reason`.
209
+ - `FetchResponse.extras` contract: `bot_block_status`, `channel`, `driver`, `engine`, `escalations`.
210
+ - `DriverType.TLS`, `NODRIVER`, `UNDETECTED`, `BOTASAURUS`, `ESCALATING`; `DriverFactory.create()`
211
+ accepts extra constructor kwargs (`policy=`).
212
+ - Extras: `tls`, `stealth`, `cloak`, `undetected`, `undetected-sync`, `antidetect`, `cloudscraper`, `system`.
213
+ - `README.md`, `CHANGELOG.md`.
214
+
215
+ ### Changed
216
+ - `normalize_protocol` defaults to `False`: `http://` and `https://` are different URLs.
217
+ The crawler follows the real redirect instead of rewriting the scheme itself, so
218
+ http-only hosts stay reachable. Enable it explicitly to merge both schemes on dedup.
219
+ - `Graph.handle_redirect()` stores the alias as the real `Location` the server sent
220
+ (provenance); the normalized form is used only to find and merge nodes.
221
+ - Single `DriverType` enum (`transport/base.py`); `factory.py` re-exports it.
222
+ - `cloudscraper` moved from required dependencies to extra `cloudscraper`.
223
+ - `psutil` is optional (`system` extra); `MemoryGuard` imports it lazily.
224
+ - `requires-python = ">=3.11"` (upper bound removed; classifiers 3.11–3.14).
225
+ - `pytest` runs offline by default (`-m 'not manual'`, no coverage in `addopts`).
226
+ Network / real-site tests live in `tests/manual/` and run with `pytest -m manual tests/manual`.
227
+ - Project URLs point to the GitLab repository.
228
+
229
+ ### Fixed
230
+ - `pooled_driver`: bounded walk over `redirected_from` (infinite loop on objects without a
231
+ `None` terminator); cookies are no longer added twice to a fresh browser.
232
+ - Tests synced with the code: redirect aliases, `html2md-clean` 0.4.0 API, `crawl_coordinator`
233
+ `per_host_max_in_flight`, `.gitignore` lookup at the repository root, `tools/db_cleanup.py`
234
+ CLI allow-listed for `print`. Playwright fake tests skip when `playwright` is not installed.
235
+
236
+ ### Removed
237
+ - `tests/345.py`, `tests/ДОДАТКОВІ_ТЕСТИ.py`, `tests/manual_4a_games_test.py`, `tests/google_maps_results.json`.
238
+ - `EXTRACTION_AUDIT.md` and other analysis / plan documents that described work, not the code.
239
+ - `graph_crawler/data/ARCHITECTURE.md`, `MIGRATION_50_STEPS.md`, `REFACTORING_PLAN.md`, `mkdocs.yml`
240
+ (finished plans / config without content).
241
+
242
+ ## 5.1.0
243
+
244
+ Previous release (sync-first API, Playwright pool, adaptive HTTP drivers, storage backends).