everyrow 0.1.0__tar.gz → 0.1.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 (221) hide show
  1. everyrow-0.1.1/.claude-plugin/marketplace.json +17 -0
  2. everyrow-0.1.1/PKG-INFO +275 -0
  3. everyrow-0.1.1/README.md +263 -0
  4. {everyrow-0.1.0 → everyrow-0.1.1}/case_studies/dedupe/case_01_crm_data.ipynb +3 -29
  5. everyrow-0.1.1/case_studies/screen/oil_price_margin_screen.ipynb +517 -0
  6. everyrow-0.1.1/case_studies/screen/oil_price_margin_screen_results.csv +151 -0
  7. {everyrow-0.1.0 → everyrow-0.1.1}/case_studies/screen/thematic_stock_screen.ipynb +4 -34
  8. everyrow-0.1.1/docs/DEDUPE.md +90 -0
  9. everyrow-0.1.1/docs/MERGE.md +79 -0
  10. everyrow-0.1.1/docs/RANK.md +86 -0
  11. everyrow-0.1.1/docs/SCREEN.md +104 -0
  12. everyrow-0.1.0/examples/clean_example.py → everyrow-0.1.1/examples/dedupe_example.py +2 -14
  13. everyrow-0.1.1/examples/derive_example.py +41 -0
  14. {everyrow-0.1.0 → everyrow-0.1.1}/examples/merge_example.py +2 -14
  15. everyrow-0.1.1/examples/rank_example.py +82 -0
  16. {everyrow-0.1.0 → everyrow-0.1.1}/examples/screen_example.py +6 -34
  17. everyrow-0.1.1/examples/simple_call.py +32 -0
  18. everyrow-0.1.1/images/future-search-logo-128.webp +0 -0
  19. everyrow-0.1.1/plugins/everyrow/.claude-plugin/plugin.json +9 -0
  20. everyrow-0.1.1/plugins/everyrow/skills/everyrow-sdk/SKILL.md +206 -0
  21. {everyrow-0.1.0 → everyrow-0.1.1}/pyproject.toml +1 -1
  22. everyrow-0.1.1/src/everyrow/__init__.py +5 -0
  23. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/citations.py +6 -2
  24. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/ops.py +154 -54
  25. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/session.py +33 -11
  26. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/task.py +99 -15
  27. {everyrow-0.1.0 → everyrow-0.1.1}/uv.lock +1 -1
  28. everyrow-0.1.0/PKG-INFO +0 -238
  29. everyrow-0.1.0/README.md +0 -226
  30. everyrow-0.1.0/examples/derive_example.py +0 -49
  31. everyrow-0.1.0/examples/rank_example.py +0 -144
  32. everyrow-0.1.0/examples/simple_call.py +0 -87
  33. everyrow-0.1.0/src/everyrow/__init__.py +0 -4
  34. everyrow-0.1.0/thematic_screen_results_20260114_172950.csv +0 -10
  35. {everyrow-0.1.0 → everyrow-0.1.1}/.env.example +0 -0
  36. {everyrow-0.1.0 → everyrow-0.1.1}/.github/workflows/ci.yaml +0 -0
  37. {everyrow-0.1.0 → everyrow-0.1.1}/.github/workflows/publish.yaml +0 -0
  38. {everyrow-0.1.0 → everyrow-0.1.1}/.gitignore +0 -0
  39. {everyrow-0.1.0 → everyrow-0.1.1}/LICENSE.txt +0 -0
  40. {everyrow-0.1.0 → everyrow-0.1.1}/case_studies/dedupe/case_01_crm_data.csv +0 -0
  41. {everyrow-0.1.0 → everyrow-0.1.1}/case_studies/screen/S&P 500 Companies.csv +0 -0
  42. {everyrow-0.1.0 → everyrow-0.1.1}/case_studies/screen/thematic_screen_results.csv +0 -0
  43. {everyrow-0.1.0 → everyrow-0.1.1}/generate_openapi.sh +0 -0
  44. {everyrow-0.1.0 → everyrow-0.1.1}/lefthook.yml +0 -0
  45. {everyrow-0.1.0 → everyrow-0.1.1}/openapi-python-client.yaml +0 -0
  46. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/api_utils.py +0 -0
  47. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/constants.py +0 -0
  48. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/__init__.py +0 -0
  49. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/__init__.py +0 -0
  50. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/__init__.py +0 -0
  51. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/continue_task_endpoint_tasks_continue_post.py +0 -0
  52. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/copy_artifacts_artifacts_copy_post.py +0 -0
  53. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/copy_workflow_endpoint_workflows_copy_post.py +0 -0
  54. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/create_api_key_endpoint_api_keys_create_post.py +0 -0
  55. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/create_session_endpoint_sessions_create_post.py +0 -0
  56. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/create_workflow_from_artifact_workflows_from_artifact_post.py +0 -0
  57. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/export_to_google_sheets_export_post.py +0 -0
  58. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/generate_feedback_endpoint_tasks_generate_feedback_post.py +0 -0
  59. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/get_artifacts_artifacts_get.py +0 -0
  60. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/get_default_timeout_seconds_models_default_timeout_seconds_get.py +0 -0
  61. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/get_job_progress_for_task_jobs_progress_get.py +0 -0
  62. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/get_metrics_metrics_get.py +0 -0
  63. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/get_queues_stats_jobs_queues_get.py +0 -0
  64. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/get_task_status_endpoint_tasks_task_id_status_get.py +0 -0
  65. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/get_user_usage_usage_get.py +0 -0
  66. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/healthz_healthz_get.py +0 -0
  67. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/import_from_google_sheets_import_post.py +0 -0
  68. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/interrupt_chat_task_tasks_chat_interrupt_post.py +0 -0
  69. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/list_api_keys_endpoint_api_keys_get.py +0 -0
  70. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/re_execute_task_endpoint_tasks_re_execute_post.py +0 -0
  71. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/revoke_api_key_endpoint_api_keys_key_id_revoke_post.py +0 -0
  72. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/revoke_jobs_for_task_jobs_revoke_post.py +0 -0
  73. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/rollback_to_message_endpoint_tasks_chat_rollback_post.py +0 -0
  74. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/submit_chat_task_tasks_chat_post.py +0 -0
  75. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/submit_task_tasks_post.py +0 -0
  76. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/task_resource_estimation_task_resource_estimation_post.py +0 -0
  77. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/trigger_workflow_execution_endpoint_workflows_trigger_post.py +0 -0
  78. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/api/default/whoami_whoami_get.py +0 -0
  79. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/client.py +0 -0
  80. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/errors.py +0 -0
  81. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/__init__.py +0 -0
  82. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/agent_improvement_instruction.py +0 -0
  83. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/agent_query_params.py +0 -0
  84. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/agent_query_params_system_prompt_kind_type_0.py +0 -0
  85. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/agent_task_args.py +0 -0
  86. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/agent_task_args_processing_mode.py +0 -0
  87. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/allowed_suggestions.py +0 -0
  88. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/api_key_info.py +0 -0
  89. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/artifact_changed_payload.py +0 -0
  90. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/artifact_group_record.py +0 -0
  91. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/artifact_group_record_metadata_type_0.py +0 -0
  92. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/artifact_group_record_trace_mapping_type_0.py +0 -0
  93. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/artifact_status.py +0 -0
  94. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/auto_cohort_conversation_message.py +0 -0
  95. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/aux_data.py +0 -0
  96. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/aux_data_source_bank.py +0 -0
  97. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/chat_completion_message_tool_call.py +0 -0
  98. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/chat_message_metadata.py +0 -0
  99. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/concatenate_query_params.py +0 -0
  100. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/concatenate_request.py +0 -0
  101. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/continue_reason.py +0 -0
  102. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/continue_task_request.py +0 -0
  103. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/controller_improvement_round.py +0 -0
  104. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/conversation_changed_payload.py +0 -0
  105. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/copy_artifacts_request.py +0 -0
  106. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/copy_artifacts_response.py +0 -0
  107. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/copy_workflow_request.py +0 -0
  108. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/copy_workflow_response.py +0 -0
  109. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_api_key_request.py +0 -0
  110. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_api_key_response.py +0 -0
  111. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_group_query_params.py +0 -0
  112. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_group_request.py +0 -0
  113. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_query_params.py +0 -0
  114. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_request.py +0 -0
  115. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_session_request.py +0 -0
  116. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_session_response.py +0 -0
  117. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_workflow_from_artifact_request.py +0 -0
  118. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/create_workflow_from_artifact_response.py +0 -0
  119. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/data_frame_method.py +0 -0
  120. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/date_cutoffs.py +0 -0
  121. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/dedupe_mode.py +0 -0
  122. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/dedupe_query_params.py +0 -0
  123. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/dedupe_request_params.py +0 -0
  124. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/deep_merge_public_params.py +0 -0
  125. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/deep_merge_request.py +0 -0
  126. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/deep_rank_public_params.py +0 -0
  127. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/deep_rank_request.py +0 -0
  128. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/deep_screen_public_params.py +0 -0
  129. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/deep_screen_request.py +0 -0
  130. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/derive_expression.py +0 -0
  131. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/derive_query_params.py +0 -0
  132. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/derive_request.py +0 -0
  133. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/document_query_tool.py +0 -0
  134. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/drop_columns_query_params.py +0 -0
  135. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/drop_columns_request.py +0 -0
  136. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/embedding_models.py +0 -0
  137. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/event_type.py +0 -0
  138. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/execution_metadata.py +0 -0
  139. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/export_request.py +0 -0
  140. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/export_request_token_data.py +0 -0
  141. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/export_to_google_sheets_export_post_response_export_to_google_sheets_export_post.py +0 -0
  142. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/filter_query_params.py +0 -0
  143. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/filter_request.py +0 -0
  144. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/flatten_query_params.py +0 -0
  145. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/flatten_request.py +0 -0
  146. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/generate_feedback_request.py +0 -0
  147. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/group_by_query_params.py +0 -0
  148. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/group_by_request.py +0 -0
  149. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/healthz_healthz_get_response_healthz_healthz_get.py +0 -0
  150. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/http_validation_error.py +0 -0
  151. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/image_chat_content_part.py +0 -0
  152. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/image_chat_content_part_image_url.py +0 -0
  153. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/import_from_google_sheets_import_post_response_import_from_google_sheets_import_post.py +0 -0
  154. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/import_request.py +0 -0
  155. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/import_request_token_data.py +0 -0
  156. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/insufficient_balance_error.py +0 -0
  157. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/join_query_params.py +0 -0
  158. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/join_request.py +0 -0
  159. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/llm_enum.py +0 -0
  160. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/map_agent_request_params.py +0 -0
  161. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/map_multi_agent_request_params.py +0 -0
  162. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/message_created_payload.py +0 -0
  163. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/multi_agent_effort_level.py +0 -0
  164. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/multi_agent_query_params.py +0 -0
  165. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/multi_modal_chat_message.py +0 -0
  166. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/multi_modal_chat_message_role.py +0 -0
  167. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/preview_metadata.py +0 -0
  168. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/processing_mode.py +0 -0
  169. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/progress_status.py +0 -0
  170. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/queue_stats.py +0 -0
  171. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/reduce_agent_request_params.py +0 -0
  172. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/reduce_multi_agent_request_params.py +0 -0
  173. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/resource_estimation_response.py +0 -0
  174. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/response_schema_type.py +0 -0
  175. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/revoke_api_key_response.py +0 -0
  176. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/rollback_to_message_request.py +0 -0
  177. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/rollback_to_message_response.py +0 -0
  178. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/session_changed_payload.py +0 -0
  179. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/simple_chat_message.py +0 -0
  180. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/simple_chat_message_role.py +0 -0
  181. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/simple_chat_message_with_tool_calls.py +0 -0
  182. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/source_database_entry.py +0 -0
  183. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/standalone_artifact_record.py +0 -0
  184. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/standalone_artifact_record_metadata_type_0.py +0 -0
  185. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/standalone_artifact_record_trace_mapping_type_0.py +0 -0
  186. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/status_count.py +0 -0
  187. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/status_count_status.py +0 -0
  188. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/submit_chat_task_body.py +0 -0
  189. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/submit_chat_task_body_selected_task_type_type_0.py +0 -0
  190. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/submit_task_body.py +0 -0
  191. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_changed_payload.py +0 -0
  192. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_effort.py +0 -0
  193. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_id_request.py +0 -0
  194. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_insert.py +0 -0
  195. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_insert_query_params.py +0 -0
  196. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_metadata.py +0 -0
  197. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_metadata_cols_to_rename_type_0.py +0 -0
  198. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_response.py +0 -0
  199. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_status.py +0 -0
  200. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_status_response.py +0 -0
  201. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/task_type.py +0 -0
  202. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/text_chat_content_part.py +0 -0
  203. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/tool_response_message.py +0 -0
  204. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/toolkit_constants.py +0 -0
  205. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/trace_changed_payload.py +0 -0
  206. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/trace_info.py +0 -0
  207. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/trigger_workflow_execution_request.py +0 -0
  208. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/trigger_workflow_execution_request_task_params.py +0 -0
  209. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/trigger_workflow_execution_request_task_params_additional_property.py +0 -0
  210. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/trigger_workflow_execution_response.py +0 -0
  211. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/upload_csv_payload.py +0 -0
  212. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/upload_csv_query_params.py +0 -0
  213. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/usage_response.py +0 -0
  214. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/validation_error.py +0 -0
  215. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/whoami_whoami_get_response_whoami_whoami_get.py +0 -0
  216. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/models/workflow_leaf_node_input.py +0 -0
  217. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/py.typed +0 -0
  218. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/generated/types.py +0 -0
  219. {everyrow-0.1.0 → everyrow-0.1.1}/src/everyrow/result.py +0 -0
  220. {everyrow-0.1.0 → everyrow-0.1.1}/tests/__init__.py +0 -0
  221. {everyrow-0.1.0 → everyrow-0.1.1}/tests/test_ops.py +0 -0
@@ -0,0 +1,17 @@
1
+ {
2
+ "name": "futuresearch",
3
+ "owner": {
4
+ "name": "FutureSearch"
5
+ },
6
+ "metadata": {
7
+ "description": "AI-powered data processing plugins from FutureSearch"
8
+ },
9
+ "plugins": [
10
+ {
11
+ "name": "everyrow",
12
+ "source": "./plugins/everyrow",
13
+ "description": "Claude Code plugin for the everyrow SDK - AI-powered data processing utilities for transforming, deduping, merging, ranking, and screening dataframes",
14
+ "version": "1.0.0"
15
+ }
16
+ ]
17
+ }
@@ -0,0 +1,275 @@
1
+ Metadata-Version: 2.4
2
+ Name: everyrow
3
+ Version: 0.1.1
4
+ Summary: An SDK for everyrow.io: agent ops at spreadsheet scale
5
+ License-File: LICENSE.txt
6
+ Requires-Python: >=3.12
7
+ Requires-Dist: attrs>=25.4.0
8
+ Requires-Dist: pandas>=2.3.3
9
+ Requires-Dist: pydantic>=2.12.5
10
+ Requires-Dist: python-dotenv>=1.2.1
11
+ Description-Content-Type: text/markdown
12
+
13
+ ![hero](https://github.com/user-attachments/assets/254fa2ed-c1f3-4ee8-b93d-d169edf32f27)
14
+
15
+ # <picture><img src="images/future-search-logo-128.webp" alt="FutureSearch" height="24" align="bottom"></picture> everyrow SDK
16
+
17
+ Python SDK for [everyrow.io](https://everyrow.io). Rank, dedupe, merge, and screen your dataframes using natural language—or run web agents to research every row.
18
+
19
+ ## Table of Contents
20
+
21
+ New to everyrow? Head to [Getting Started](#getting-started)
22
+
23
+ Looking to use our agent-backed utilities? Check out:
24
+ - [Rank](#rank)
25
+ - [Dedupe](#dedupe)
26
+ - [Merge](#merge)
27
+ - [Screen](#screen)
28
+ - [Agent Tasks](#agent-tasks)
29
+
30
+ ## Getting Started
31
+
32
+ Get an API key at [everyrow.io](https://everyrow.io).
33
+
34
+ ```bash
35
+ export EVERYROW_API_KEY=your_api_key_here
36
+ ```
37
+
38
+ ### Installation
39
+
40
+ ```bash
41
+ pip install everyrow
42
+ ```
43
+
44
+ For development:
45
+
46
+ ```bash
47
+ uv pip install -e .
48
+ uv sync
49
+ ```
50
+
51
+ Requires Python >= 3.12
52
+
53
+ ### Claude Code Plugin
54
+
55
+ There's a plugin for [Claude Code](https://code.claude.com/) that teaches Claude how to use the SDK:
56
+
57
+ ```sh
58
+ # from Claude Code
59
+ /plugin marketplace add futuresearch/everyrow-sdk
60
+ /plugin install everyrow@futuresearch
61
+
62
+ # from terminal
63
+ claude plugin marketplace add futuresearch/everyrow-sdk
64
+ claude plugin install everyrow@futuresearch
65
+ ```
66
+
67
+ ## Rank
68
+
69
+ Score rows based on criteria you can't put in a database field. The AI researches each row and assigns scores based on qualitative factors.
70
+
71
+ ```python
72
+ from everyrow.ops import rank
73
+
74
+ result = await rank(
75
+ task="Score by likelihood to need data integration solutions",
76
+ input=leads_dataframe,
77
+ field_name="integration_need_score",
78
+ )
79
+ ```
80
+
81
+ Say you want to rank leads by "likelihood to need data integration tools"—Ultramain Systems (sells software to airlines) looks similar to Ukraine International Airlines (is an airline) by industry code, but their actual needs are completely different. Traditional scoring can't tell them apart.
82
+
83
+ **Case studies:** [Lead Scoring with Data Fragmentation](https://futuresearch.ai/lead-scoring-data-fragmentation/) (1,000 leads, 7 min, $13) · [Lead Scoring Without CRM](https://futuresearch.ai/lead-scoring-without-crm/) ($28 vs $145 with Clay)
84
+
85
+ [Full documentation →](docs/RANK.md)
86
+
87
+ ### Dedupe
88
+
89
+ Deduplicate when fuzzy matching falls short. The AI understands that "AbbVie Inc", "Abbvie", and "AbbVie Pharmaceutical" are the same company, or that "Big Blue" means IBM.
90
+
91
+ ```python
92
+ from everyrow.ops import dedupe
93
+
94
+ result = await dedupe(
95
+ input=crm_data,
96
+ equivalence_relation="Two entries are duplicates if they represent the same legal entity",
97
+ )
98
+ ```
99
+
100
+ The `equivalence_relation` tells the AI what counts as a duplicate—natural language, not regex. Results include `equivalence_class_id` (groups duplicates), `equivalence_class_name` (human-readable cluster name), and `selected` (the canonical record in each cluster).
101
+
102
+ **Case studies:** [CRM Deduplication](https://futuresearch.ai/crm-deduplication/) (500→124 rows, 2 min, $1.67) · [Researcher Deduplication](https://futuresearch.ai/researcher-dedupe-case-study/) (98% accuracy with career changes)
103
+
104
+ [Full documentation →](docs/DEDUPE.md)
105
+
106
+ ### Merge
107
+
108
+ Join two tables when the keys don't match exactly—or at all. The AI knows "Photoshop" belongs to "Adobe" and "Genentech" is a Roche subsidiary, even with zero string similarity.
109
+
110
+ ```python
111
+ from everyrow.ops import merge
112
+
113
+ result = await merge(
114
+ task="Match each software product to its parent company",
115
+ left_table=software_products,
116
+ right_table=approved_suppliers,
117
+ merge_on_left="software_name",
118
+ merge_on_right="company_name",
119
+ )
120
+ ```
121
+
122
+ Handles subsidiaries, abbreviations (MSD → Merck), regional names, typos, and pseudonyms. Fuzzy matching thresholds always fail somewhere—0.9 misses "Colfi" ↔ "Dr. Ioana Colfescu", 0.7 false-positives on "John Smith" ↔ "Jane Smith".
123
+
124
+ **Case studies:** [Software Supplier Matching](https://futuresearch.ai/software-supplier-matching/) (2,000 products, 91% accuracy, $9) · [HubSpot Contact Merge](https://futuresearch.ai/merge-hubspot-contacts/) (99.9% recall) · [CRM Merge Workflow](https://futuresearch.ai/crm-merge-workflow/)
125
+
126
+ [Full documentation →](docs/MERGE.md)
127
+
128
+ ### Screen
129
+
130
+ Filter rows based on criteria that require research—things you can't express in SQL. The AI actually researches each row (10-Ks, earnings reports, news) before deciding pass/fail.
131
+
132
+ ```python
133
+ from everyrow.ops import screen
134
+ from pydantic import BaseModel, Field
135
+
136
+ class ScreenResult(BaseModel):
137
+ passes: bool = Field(description="True if company meets the criteria")
138
+
139
+ result = await screen(
140
+ task="""
141
+ Find companies with >75% recurring revenue that would benefit from
142
+ Taiwan tensions - CHIPS Act beneficiaries, defense contractors,
143
+ cybersecurity firms. Exclude companies dependent on Taiwan manufacturing.
144
+ """,
145
+ input=sp500_companies,
146
+ response_model=ScreenResult,
147
+ )
148
+ ```
149
+
150
+ Works for investment theses, geopolitical exposure, vendor risk assessment, job posting filtering, lead qualification—anything requiring judgment. Screening 500 S&P 500 companies takes ~12 min and $3 with >90% precision. Regex gets 68%.
151
+
152
+ **Case studies:** [Thematic Stock Screen](https://futuresearch.ai/thematic-stock-screening/) (63/502 passed, $3.29) · [Job Posting Screen](https://futuresearch.ai/job-posting-screening/) (>90% vs 68% regex) · [Lead Screening Workflow](https://futuresearch.ai/screening-workflow/)
153
+
154
+ [Full documentation →](docs/SCREEN.md)
155
+
156
+ ### Agent Tasks
157
+
158
+ For single-input tasks, use `single_agent`. For batch processing, use `agent_map`.
159
+
160
+ ```python
161
+ from everyrow.ops import single_agent, agent_map
162
+ from pandas import DataFrame
163
+
164
+ # Single input
165
+ result = await single_agent(
166
+ task="What is the capital of the given country?",
167
+ input={"country": "India"},
168
+ )
169
+
170
+ # Batch processing
171
+ result = await agent_map(
172
+ task="What is the capital of the given country?",
173
+ input=DataFrame([{"country": "India"}, {"country": "USA"}]),
174
+ )
175
+ ```
176
+
177
+ Our agents are tuned on [Deep Research Bench](https://arxiv.org/abs/2506.06287), a benchmark we built for evaluating web research on questions that require extensive searching and cross-referencing.
178
+
179
+ ## Advanced
180
+
181
+ ### Sessions
182
+
183
+ For quick one-off operations, sessions are created automatically:
184
+
185
+ ```python
186
+ from everyrow.ops import single_agent
187
+
188
+ result = await single_agent(
189
+ task="What is the capital of France?",
190
+ input={"country": "France"},
191
+ )
192
+ ```
193
+
194
+ For multiple operations, use an explicit session:
195
+
196
+ ```python
197
+ from everyrow import create_session
198
+
199
+ async with create_session(name="My Session") as session:
200
+ print(f"View session at: {session.get_url()}")
201
+ # All operations here share the same session
202
+ ```
203
+
204
+ If you want more explicit control over the client (for example, to reuse it across sessions or configure custom settings), you can create it directly:
205
+
206
+ ```python
207
+ from everyrow import create_client, create_session
208
+
209
+ async with create_client() as client:
210
+ async with create_session(client=client, name="My Session") as session:
211
+ # ...
212
+ ```
213
+
214
+ Sessions are visible on the [everyrow.io](https://everyrow.io) dashboard.
215
+
216
+ ### Async Operations
217
+
218
+ All utilities have async variants for background processing. These need an explicit session since the task persists beyond the function call:
219
+
220
+ ```python
221
+ from everyrow import create_session
222
+ from everyrow.ops import rank_async
223
+
224
+ async with create_session(name="Async Ranking") as session:
225
+ task = await rank_async(
226
+ session=session,
227
+ task="Score this organization",
228
+ input=dataframe,
229
+ field_name="score",
230
+ )
231
+
232
+ # Continue with other work...
233
+ result = await task.await_result()
234
+ ```
235
+
236
+ ## Case Studies
237
+
238
+ More at [futuresearch.ai/solutions](https://futuresearch.ai/solutions/).
239
+
240
+ **Notebooks:**
241
+ - [CRM Deduplication](case_studies/dedupe/case_01_crm_data.ipynb)
242
+ - [Thematic Stock Screen](case_studies/screen/thematic_stock_screen.ipynb)
243
+ - [Oil Price Margin Screen](case_studies/screen/oil_price_margin_screen.ipynb)
244
+
245
+ **On futuresearch.ai:**
246
+ - [Lead Scoring with Data Fragmentation](https://futuresearch.ai/lead-scoring-data-fragmentation/)
247
+ - [Software Supplier Matching](https://futuresearch.ai/software-supplier-matching/)
248
+ - [Researcher Deduplication](https://futuresearch.ai/researcher-dedupe-case-study/)
249
+
250
+ To run notebooks:
251
+
252
+ ```bash
253
+ uv sync --group case-studies
254
+ ```
255
+
256
+ ## Development
257
+
258
+ ```bash
259
+ uv sync
260
+ lefthook install
261
+ ```
262
+
263
+ ```bash
264
+ uv run pytest # tests
265
+ uv run ruff check . # lint
266
+ uv run ruff format . # format
267
+ uv run basedpyright # type check
268
+ ./generate_openapi.sh # regenerate client
269
+ ```
270
+
271
+ The `everyrow/generated/` directory is excluded from linting (auto-generated code).
272
+
273
+ ## License
274
+
275
+ This project is licensed under the MIT License - see LICENSE.txt file for details.
@@ -0,0 +1,263 @@
1
+ ![hero](https://github.com/user-attachments/assets/254fa2ed-c1f3-4ee8-b93d-d169edf32f27)
2
+
3
+ # <picture><img src="images/future-search-logo-128.webp" alt="FutureSearch" height="24" align="bottom"></picture> everyrow SDK
4
+
5
+ Python SDK for [everyrow.io](https://everyrow.io). Rank, dedupe, merge, and screen your dataframes using natural language—or run web agents to research every row.
6
+
7
+ ## Table of Contents
8
+
9
+ New to everyrow? Head to [Getting Started](#getting-started)
10
+
11
+ Looking to use our agent-backed utilities? Check out:
12
+ - [Rank](#rank)
13
+ - [Dedupe](#dedupe)
14
+ - [Merge](#merge)
15
+ - [Screen](#screen)
16
+ - [Agent Tasks](#agent-tasks)
17
+
18
+ ## Getting Started
19
+
20
+ Get an API key at [everyrow.io](https://everyrow.io).
21
+
22
+ ```bash
23
+ export EVERYROW_API_KEY=your_api_key_here
24
+ ```
25
+
26
+ ### Installation
27
+
28
+ ```bash
29
+ pip install everyrow
30
+ ```
31
+
32
+ For development:
33
+
34
+ ```bash
35
+ uv pip install -e .
36
+ uv sync
37
+ ```
38
+
39
+ Requires Python >= 3.12
40
+
41
+ ### Claude Code Plugin
42
+
43
+ There's a plugin for [Claude Code](https://code.claude.com/) that teaches Claude how to use the SDK:
44
+
45
+ ```sh
46
+ # from Claude Code
47
+ /plugin marketplace add futuresearch/everyrow-sdk
48
+ /plugin install everyrow@futuresearch
49
+
50
+ # from terminal
51
+ claude plugin marketplace add futuresearch/everyrow-sdk
52
+ claude plugin install everyrow@futuresearch
53
+ ```
54
+
55
+ ## Rank
56
+
57
+ Score rows based on criteria you can't put in a database field. The AI researches each row and assigns scores based on qualitative factors.
58
+
59
+ ```python
60
+ from everyrow.ops import rank
61
+
62
+ result = await rank(
63
+ task="Score by likelihood to need data integration solutions",
64
+ input=leads_dataframe,
65
+ field_name="integration_need_score",
66
+ )
67
+ ```
68
+
69
+ Say you want to rank leads by "likelihood to need data integration tools"—Ultramain Systems (sells software to airlines) looks similar to Ukraine International Airlines (is an airline) by industry code, but their actual needs are completely different. Traditional scoring can't tell them apart.
70
+
71
+ **Case studies:** [Lead Scoring with Data Fragmentation](https://futuresearch.ai/lead-scoring-data-fragmentation/) (1,000 leads, 7 min, $13) · [Lead Scoring Without CRM](https://futuresearch.ai/lead-scoring-without-crm/) ($28 vs $145 with Clay)
72
+
73
+ [Full documentation →](docs/RANK.md)
74
+
75
+ ### Dedupe
76
+
77
+ Deduplicate when fuzzy matching falls short. The AI understands that "AbbVie Inc", "Abbvie", and "AbbVie Pharmaceutical" are the same company, or that "Big Blue" means IBM.
78
+
79
+ ```python
80
+ from everyrow.ops import dedupe
81
+
82
+ result = await dedupe(
83
+ input=crm_data,
84
+ equivalence_relation="Two entries are duplicates if they represent the same legal entity",
85
+ )
86
+ ```
87
+
88
+ The `equivalence_relation` tells the AI what counts as a duplicate—natural language, not regex. Results include `equivalence_class_id` (groups duplicates), `equivalence_class_name` (human-readable cluster name), and `selected` (the canonical record in each cluster).
89
+
90
+ **Case studies:** [CRM Deduplication](https://futuresearch.ai/crm-deduplication/) (500→124 rows, 2 min, $1.67) · [Researcher Deduplication](https://futuresearch.ai/researcher-dedupe-case-study/) (98% accuracy with career changes)
91
+
92
+ [Full documentation →](docs/DEDUPE.md)
93
+
94
+ ### Merge
95
+
96
+ Join two tables when the keys don't match exactly—or at all. The AI knows "Photoshop" belongs to "Adobe" and "Genentech" is a Roche subsidiary, even with zero string similarity.
97
+
98
+ ```python
99
+ from everyrow.ops import merge
100
+
101
+ result = await merge(
102
+ task="Match each software product to its parent company",
103
+ left_table=software_products,
104
+ right_table=approved_suppliers,
105
+ merge_on_left="software_name",
106
+ merge_on_right="company_name",
107
+ )
108
+ ```
109
+
110
+ Handles subsidiaries, abbreviations (MSD → Merck), regional names, typos, and pseudonyms. Fuzzy matching thresholds always fail somewhere—0.9 misses "Colfi" ↔ "Dr. Ioana Colfescu", 0.7 false-positives on "John Smith" ↔ "Jane Smith".
111
+
112
+ **Case studies:** [Software Supplier Matching](https://futuresearch.ai/software-supplier-matching/) (2,000 products, 91% accuracy, $9) · [HubSpot Contact Merge](https://futuresearch.ai/merge-hubspot-contacts/) (99.9% recall) · [CRM Merge Workflow](https://futuresearch.ai/crm-merge-workflow/)
113
+
114
+ [Full documentation →](docs/MERGE.md)
115
+
116
+ ### Screen
117
+
118
+ Filter rows based on criteria that require research—things you can't express in SQL. The AI actually researches each row (10-Ks, earnings reports, news) before deciding pass/fail.
119
+
120
+ ```python
121
+ from everyrow.ops import screen
122
+ from pydantic import BaseModel, Field
123
+
124
+ class ScreenResult(BaseModel):
125
+ passes: bool = Field(description="True if company meets the criteria")
126
+
127
+ result = await screen(
128
+ task="""
129
+ Find companies with >75% recurring revenue that would benefit from
130
+ Taiwan tensions - CHIPS Act beneficiaries, defense contractors,
131
+ cybersecurity firms. Exclude companies dependent on Taiwan manufacturing.
132
+ """,
133
+ input=sp500_companies,
134
+ response_model=ScreenResult,
135
+ )
136
+ ```
137
+
138
+ Works for investment theses, geopolitical exposure, vendor risk assessment, job posting filtering, lead qualification—anything requiring judgment. Screening 500 S&P 500 companies takes ~12 min and $3 with >90% precision. Regex gets 68%.
139
+
140
+ **Case studies:** [Thematic Stock Screen](https://futuresearch.ai/thematic-stock-screening/) (63/502 passed, $3.29) · [Job Posting Screen](https://futuresearch.ai/job-posting-screening/) (>90% vs 68% regex) · [Lead Screening Workflow](https://futuresearch.ai/screening-workflow/)
141
+
142
+ [Full documentation →](docs/SCREEN.md)
143
+
144
+ ### Agent Tasks
145
+
146
+ For single-input tasks, use `single_agent`. For batch processing, use `agent_map`.
147
+
148
+ ```python
149
+ from everyrow.ops import single_agent, agent_map
150
+ from pandas import DataFrame
151
+
152
+ # Single input
153
+ result = await single_agent(
154
+ task="What is the capital of the given country?",
155
+ input={"country": "India"},
156
+ )
157
+
158
+ # Batch processing
159
+ result = await agent_map(
160
+ task="What is the capital of the given country?",
161
+ input=DataFrame([{"country": "India"}, {"country": "USA"}]),
162
+ )
163
+ ```
164
+
165
+ Our agents are tuned on [Deep Research Bench](https://arxiv.org/abs/2506.06287), a benchmark we built for evaluating web research on questions that require extensive searching and cross-referencing.
166
+
167
+ ## Advanced
168
+
169
+ ### Sessions
170
+
171
+ For quick one-off operations, sessions are created automatically:
172
+
173
+ ```python
174
+ from everyrow.ops import single_agent
175
+
176
+ result = await single_agent(
177
+ task="What is the capital of France?",
178
+ input={"country": "France"},
179
+ )
180
+ ```
181
+
182
+ For multiple operations, use an explicit session:
183
+
184
+ ```python
185
+ from everyrow import create_session
186
+
187
+ async with create_session(name="My Session") as session:
188
+ print(f"View session at: {session.get_url()}")
189
+ # All operations here share the same session
190
+ ```
191
+
192
+ If you want more explicit control over the client (for example, to reuse it across sessions or configure custom settings), you can create it directly:
193
+
194
+ ```python
195
+ from everyrow import create_client, create_session
196
+
197
+ async with create_client() as client:
198
+ async with create_session(client=client, name="My Session") as session:
199
+ # ...
200
+ ```
201
+
202
+ Sessions are visible on the [everyrow.io](https://everyrow.io) dashboard.
203
+
204
+ ### Async Operations
205
+
206
+ All utilities have async variants for background processing. These need an explicit session since the task persists beyond the function call:
207
+
208
+ ```python
209
+ from everyrow import create_session
210
+ from everyrow.ops import rank_async
211
+
212
+ async with create_session(name="Async Ranking") as session:
213
+ task = await rank_async(
214
+ session=session,
215
+ task="Score this organization",
216
+ input=dataframe,
217
+ field_name="score",
218
+ )
219
+
220
+ # Continue with other work...
221
+ result = await task.await_result()
222
+ ```
223
+
224
+ ## Case Studies
225
+
226
+ More at [futuresearch.ai/solutions](https://futuresearch.ai/solutions/).
227
+
228
+ **Notebooks:**
229
+ - [CRM Deduplication](case_studies/dedupe/case_01_crm_data.ipynb)
230
+ - [Thematic Stock Screen](case_studies/screen/thematic_stock_screen.ipynb)
231
+ - [Oil Price Margin Screen](case_studies/screen/oil_price_margin_screen.ipynb)
232
+
233
+ **On futuresearch.ai:**
234
+ - [Lead Scoring with Data Fragmentation](https://futuresearch.ai/lead-scoring-data-fragmentation/)
235
+ - [Software Supplier Matching](https://futuresearch.ai/software-supplier-matching/)
236
+ - [Researcher Deduplication](https://futuresearch.ai/researcher-dedupe-case-study/)
237
+
238
+ To run notebooks:
239
+
240
+ ```bash
241
+ uv sync --group case-studies
242
+ ```
243
+
244
+ ## Development
245
+
246
+ ```bash
247
+ uv sync
248
+ lefthook install
249
+ ```
250
+
251
+ ```bash
252
+ uv run pytest # tests
253
+ uv run ruff check . # lint
254
+ uv run ruff format . # format
255
+ uv run basedpyright # type check
256
+ ./generate_openapi.sh # regenerate client
257
+ ```
258
+
259
+ The `everyrow/generated/` directory is excluded from linting (auto-generated code).
260
+
261
+ ## License
262
+
263
+ This project is licensed under the MIT License - see LICENSE.txt file for details.
@@ -23,7 +23,7 @@
23
23
  "execution_count": null,
24
24
  "metadata": {},
25
25
  "outputs": [],
26
- "source": "from datetime import datetime\nfrom textwrap import dedent\n\nimport pandas as pd\nfrom dotenv import load_dotenv\n\nfrom everyrow import create_client, create_session\nfrom everyrow.ops import dedupe\n\nload_dotenv()"
26
+ "source": "from datetime import datetime\nfrom textwrap import dedent\n\nimport pandas as pd\nfrom dotenv import load_dotenv\n\nfrom everyrow.ops import dedupe\n\nload_dotenv()"
27
27
  },
28
28
  {
29
29
  "cell_type": "markdown",
@@ -222,34 +222,8 @@
222
222
  "cell_type": "code",
223
223
  "execution_count": null,
224
224
  "metadata": {},
225
- "outputs": [
226
- {
227
- "name": "stdout",
228
- "output_type": "stream",
229
- "text": [
230
- "Session URL: https://everyrow.io/sessions/912cde86-8f35-4381-95a2-7bf1e68bb4f6\n",
231
- "Deduplicating CRM data...\n",
232
- "\n"
233
- ]
234
- }
235
- ],
236
- "source": [
237
- "equivalence_relation = dedent(\"\"\"\n",
238
- " Two entries are duplicates if they include data for the same legal entity.\n",
239
- "\"\"\")\n",
240
- "\n",
241
- "async with create_client() as client:\n",
242
- " session_name = f\"CRM Deduplication {datetime.now().isoformat()}\"\n",
243
- " async with create_session(client=client, name=session_name) as session:\n",
244
- " print(f\"Session URL: {session.get_url()}\")\n",
245
- " print(\"Deduplicating CRM data...\\n\")\n",
246
- "\n",
247
- " result = await dedupe(\n",
248
- " session=session,\n",
249
- " input=data,\n",
250
- " equivalence_relation=equivalence_relation,\n",
251
- " )"
252
- ]
225
+ "outputs": [],
226
+ "source": "equivalence_relation = dedent(\"\"\"\n Two entries are duplicates if they include data for the same legal entity.\n\"\"\")\n\nprint(\"Deduplicating CRM data...\\n\")\n\nresult = await dedupe(\n input=data,\n equivalence_relation=equivalence_relation,\n)"
253
227
  },
254
228
  {
255
229
  "cell_type": "markdown",