Commit Graph

122 Commits

Author SHA1 Message Date
João Moura
42e041146e feat: bump versions to 1.15.13 (#6865) 2026-08-07 21:10:19 +00:00
João Moura
10583d6ee3 feat: bump versions to 1.15.12 (#6835) 2026-08-05 19:49:52 -03:00
João Moura
0c74f23596 feat(tools): add URLReadTool for reading arbitrary URLs (#6834)
* feat(tools): add URLReadTool for reading arbitrary URLs

FileReadTool is confined to the local filesystem, so there was no way for
an agent to read a document that lives behind an http(s) URL. Rather than
adding a flag to FileReadTool, this adds a separate tool: granting it
grants network egress to addresses an LLM picks at runtime, and that
should be a deliberate choice rather than a toggle on a filesystem tool.

URLReadTool fetches a URL and returns its content as text. PDF and DOCX
bodies have their text extracted, HTML is stripped to visible text, and
text-shaped types (plain text, Markdown, JSON, XML, YAML, CSV) are
decoded using the charset the server declares. Any other content type is
refused rather than returned as base64, keeping the output text-only.

Requests reuse the existing SSRF protections in security/safe_requests:
validate_url resolves every hostname and rejects private, loopback,
link-local and reserved addresses (covering cloud metadata endpoints),
and safe_get never auto-follows redirects, revalidating each hop and
dropping credentials on cross-origin ones. Resolving before validating
also normalizes encoded forms, so http://2130706433/ is rejected as
127.0.0.1 without needing a string blocklist.

Adds safe_get_bounded on top of that, which streams the body and
abandons it once it crosses max_bytes. The cap counts decoded bytes,
which is what a compressed response expands into -- Content-Length
describes the wire size and cannot bound that. It also closes the
redirect hops, which stream=True would otherwise leave holding their
connections.

Two risks are documented rather than closed. Validation resolves the
hostname and requests resolves it again to connect, so DNS rebinding
remains possible; closing it needs the connection pinned to the
validated address, which would change behavior for all existing
safe_get callers. And the returned text is untrusted remote content
entering an agent's context, which input validation cannot address.

Also fixes a temp file leak in PDFLoader, which reached the same
pymupdf-from-URL path. It wrote downloads to NamedTemporaryFile with
delete=False and never unlinked them, so every PDF ingested from a URL
left a file behind. It now opens from memory, the way URLReadTool does,
which removes the leak by construction instead of relying on cleanup on
each error path; its doc.close() also moves into a finally so a failure
mid-extraction still releases the handle. PDFLoader had no test file, so
this adds one covering both paths plus a regression test asserting no
temp file is created.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* fix(tools): address review feedback on URLReadTool

Bound start_line and line_count with ge=1 in the args schema. Both were
unbounded, and _window computes stop as start + line_count, so a negative
line_count reached islice, which rejects a negative stop. The windowing
runs outside the tool's error handling, so that escaped _run as a raw
ValueError instead of an error string. BaseTool.run validates kwargs
against args_schema, so the constraint refuses the value before any
request is made. _window also clamps its own bounds now, so it cannot
raise if called directly.

Bound the PDFLoader download with safe_get_bounded. The body is held in
memory for the whole extraction, so it needed a ceiling; it defaults to
50 MiB and takes a max_bytes kwarg to load() for callers ingesting
larger documents.

Patch the loader's own seam in its tests rather than requests.get. Both
safe_get and safe_get_bounded resolve the hostname before requesting, so
the previous mocks made the tests depend on DNS for example.com and fail
in a network-isolated runner for reasons unrelated to the loader.

Exercise the content-type fallback through run() rather than asserting on
_resolve_kind, so the tests survive a refactor of the classification
internals, and cover the octet-stream PDF, missing-type, query-string and
unknown-extension cases as observable behavior.

Add docstrings to the new tests.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* fix(tools): close streamed redirect hops and widen type fallback

Four findings from the Copilot and Cursor reviews.

safe_get leaked its accumulated hops on every failure path. It closed the
response it was about to abandon but not the ones already in history, and
a caller handed an exception has no handle on them -- under stream=True
each holds its connection until its body is read or closed. The loop now
closes history before re-raising. Hops are still the caller's on success,
where they arrive via response.history.

safe_get_bounded rejected a non-positive max_bytes only after issuing the
request, and then reported it as an oversized body. It now fails before
the request. Its oversized-body error also named the requested URL rather
than the one that served the body, which differ after a redirect.

The content-type fallback consulted only the final URL for an extension,
so a .pdf link redirecting to an extensionless CDN or presigned path was
refused even though the requested URL identified the type. It now checks
the final URL first, then the requested one.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-05 19:38:36 -03:00
João Moura
a60d36a8df feat: bump versions to 1.15.11 (#6816) 2026-08-04 22:52:54 -07:00
João Moura
766d71aefb feat: surface AMP in AGENTS.md and detect coding agents in telemetry (#6779) 2026-08-03 12:13:05 -07:00
PawanThakurIBM
c8f441cffa feat(crewai-tools): add IBM Db2 search tool (#5885)
Some checks failed
CodeQL Advanced / Analyze (actions) (push) Has been cancelled
CodeQL Advanced / Analyze (python) (push) Has been cancelled
Check Documentation Broken Links / Check broken links (push) Has been cancelled
Vulnerability Scan / pip-audit (push) Has been cancelled
Build uv cache / build-cache (3.11) (push) Has been cancelled
Build uv cache / build-cache (3.12) (push) Has been cancelled
Build uv cache / build-cache (3.13) (push) Has been cancelled
Build uv cache / build-cache (3.10) (push) Has been cancelled
Nightly Canary Release / Check for new commits (push) Has been cancelled
Nightly Canary Release / Build nightly packages (push) Has been cancelled
Nightly Canary Release / Publish nightly to PyPI (push) Has been cancelled
Mark stale issues and pull requests / stale (push) Has been cancelled
* feat(crewai-tools): add db2 search tool

* refactor(crewai-tools): improve db2 search tool implementation

* feat(tools): improve DB2VectorSearchTool validation, security, and configurability

* docs: add DB2SearchTool documentation

* feat: add DB2 search tool

* docs: update DB2SearchTool documentation

* fix: address CodeRabbit review feedback

* fix: validate non-empty filter_by in DB2ToolSchema

* chore: trigger CodeRabbit re-review

* feat: fortify DB2 tool; fixed JSON response shape, added input guards and config validation

* refactor(db2): replace DB2Config with connection_string field

* refactor(db2): remove dead _setup_db2 validator and importlib import

* refactor(db2): remove dead guard in _connect as  _disconnect() is called at the end of every
_run, so self.connection is always None when _connect is called next.
The 'if not self.connection' guard was dead code.

* fix(db2): tighten _validate_identifier regex. Old regex allowed leading digits, multiple periods and dot-only strings (e.g. '.....' passed).

* fix(db2): replace __import__ with importlib.import_module in _generate_embedding as keeping openai as a lazy optional import since it is not always required.

* perf(db2): cache OpenAI client in _openai_client to avoid re-instantiation as OpenAI(api_key=...) was recreated on every _generate_embedding call. Extract into _get_openai_client() which lazily initialises and caches self._openai_client on first use, reusing it for all subsequent queries.

* docs(db2): clarify tool description to mention embedding fallback

* docs(db2): update README supported features to clarify embedding behaviour. 'OpenAI embedding fallback' implied it was
optional. Replaced with 'Uses a custom embedding function if supplied,
otherwise OpenAI embeddings.'

* updated both code examples to use the correct import path and public run() method.

* feat(crewai-tools): add db2 search tool

* refactor(crewai-tools): improve db2 search tool implementation

* feat(tools): improve DB2VectorSearchTool validation, security, and configurability

* docs: add DB2SearchTool documentation

* feat: add DB2 search tool

* docs: update DB2SearchTool documentation

* fix: address CodeRabbit review feedback

* fix: validate non-empty filter_by in DB2ToolSchema

* chore: trigger CodeRabbit re-review

* feat: fortify DB2 tool; fixed JSON response shape, added input guards and config validation

* fix(db2): address ruff and mypy linter errors

* style(db2): apply ruff format to db2_search_tool.py

* fix(db2-search-tool): address PR review comments

- Restore DirectoryReadTool export accidentally removed; add DB2VectorSearchTool
  and DB2ToolSchema to crewai_tools.tools __init__ and __all__
- Align _ALLOWED_METRICS whitelist with Db2 VECTOR_DISTANCE API:
  replace DOT_PRODUCT/L2_DISTANCE with EUCLIDEAN_SQUARED/DOT/HAMMING/MANHATTAN
- Replace ImportString fields for db2_package/db2_dbi_package with plain Any +
  lazy importlib.import_module in new _resolve_db2_packages() to avoid Pydantic
  default-validation gap where strings were never resolved at construction time
- Move docs from frozen docs/v1.13.0/ snapshot to docs/edge/en/tools/database-data/
  and register in docs/docs.json; update examples to match actual API
  (connection_string constructor, not DB2Config), correct return format, and
  align documented distance metrics with the whitelist

* fix(db2-search-tool): resolve default and string db2 package imports dynamically

* fix(db2-search-tool): export DB2VectorSearchTool and DB2ToolSchema from package-level crewai_tools

* docs(db2-search-tool): fix installation command and import path in README

---------

Co-authored-by: priyanshu-krishnan1 <priyanshu.krishnan1@ibm.com>
Co-authored-by: GeetikaChugh24 <geetika@ibm.com>
Co-authored-by: Lorenze Jay <63378463+lorenzejay@users.noreply.github.com>
Co-authored-by: Dhruv Chaturvedi <dhruv_insights@Dhruvs-MacBook-Pro.local>
2026-07-31 09:13:33 -07:00
João Moura
f262ac214e feat: bump versions to 1.15.10 (#6753) 2026-07-31 14:45:28 +00:00
João Moura
bfe8df4471 feat: bump versions to 1.15.9 (#6725) 2026-07-29 22:40:32 -07:00
João Moura
133baf39b8 feat: bump versions to 1.15.8 (#6702) 2026-07-28 14:59:36 +00:00
João Moura
97981ed31b feat(tools): add WaitTool for pausing on long-running jobs (#6690)
Some checks failed
CodeQL Advanced / Analyze (actions) (push) Has been cancelled
CodeQL Advanced / Analyze (python) (push) Has been cancelled
Check Documentation Broken Links / Check broken links (push) Has been cancelled
Vulnerability Scan / pip-audit (push) Has been cancelled
Nightly Canary Release / Check for new commits (push) Has been cancelled
Nightly Canary Release / Build nightly packages (push) Has been cancelled
Nightly Canary Release / Publish nightly to PyPI (push) Has been cancelled
* feat(tools): add WaitTool for pausing on long-running jobs

Agents that kick off out-of-band work (a sandbox build, a deployment, an
async API job) have no way to let clock time pass: they either poll in a
tight loop or give up before the work finishes.

WaitTool pauses for a given number of seconds, with an optional reason
echoed back for traces. A single call waits at most max_seconds (default
300, configurable). Longer requests are clamped to the cap and the result
says so, so the model calls again rather than failing. Sync and async
execution are both implemented; stdlib only, no new dependencies.

The tool description spells out when to reach for it (builds, deploys,
batch jobs, async polling, backoff) and when not to, so models pick it up
for the right reason.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* fix(tools): enforce non-negative wait on positional calls, fix doc snippets

BaseTool.run() skips args_schema validation when called with positional
arguments, so tool.run(-5) reached time.sleep(-5) and failed with an
unrelated error. _resolve_duration now enforces the seconds >= 0 contract
itself, covered for both run() and arun().

Docs and README examples are now self-contained: check_build_status_tool
is defined with the @tool decorator instead of referenced out of nowhere,
and the async example awaits inside asyncio.run() rather than at top level.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* docs: point the wait tool card at the edge path

Unprefixed links resolve against the default docs version (v1.15.7),
where the wait tool page does not exist, so the card 404'd in the broken
link check. Prefixing with /edge matches how other edge pages link.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* fix(tools): never cache waits and keep the advertised cap accurate

Two issues from review, both confirmed against the code.

Waits inherited the default cache_function, which always allows caching.
With crew cache enabled, a repeat call with the same arguments returned
"Waited N seconds." straight from the cache without sleeping, turning a
poll-wait-check loop into a busy loop. WaitTool now declares a
cache_function that always refuses.

The description advertising the cap was only rebuilt when max_seconds
reached __init__ without an explicit description. Passing both (as a
platform building from tool.specs.json init params would), calling
model_validate, or assigning max_seconds left the text claiming 300
seconds while clamping to something else. A model_validator now derives
the description from max_seconds on construction, validation, and
assignment, and leaves a caller-supplied description untouched.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* fix(tools): reject NaN waits and pluralize single-second results

_resolve_duration now rejects NaN with its own message instead of letting
time.sleep raise "Invalid value NaN (not a number)" from a positional
call. Infinity keeps clamping to the cap like any other oversized wait.

Result and description text no longer says "1 seconds". Tests use the
public WaitTool().description as the baseline rather than reaching for
module-private helpers.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-27 17:12:27 -07:00
João Moura
38ca5edce2 feat: bump versions to 1.15.7 (#6672) 2026-07-26 18:07:46 +00:00
Lorenze Jay
c459d01c35 feat: bump versions to 1.15.7a1 (#6661) 2026-07-26 13:47:11 -03:00
Lorenze Jay
a4cbeacca5 feat: bump versions to 1.15.6 (#6631) 2026-07-24 20:21:58 +00:00
Vinicius Brasil
4c7e483936 feat: bump versions to 1.15.5 (#6601) 2026-07-20 16:20:33 +00:00
Vinicius Brasil
e0bd967484 feat: bump versions to 1.15.4 (#6582) 2026-07-17 14:27:15 +00:00
Vinicius Brasil
cbb8c982f8 feat: bump versions to 1.15.3 (#6576) 2026-07-16 19:26:14 +00:00
Vinicius Brasil
a1021de7f3 feat: bump versions to 1.15.3a2 (#6573) 2026-07-16 15:43:38 -03:00
Vinicius Brasil
79da292d79 feat: bump versions to 1.15.3a1 (#6566) 2026-07-16 13:56:31 -03:00
Lorenze Jay
589baa3e7f feat: bump versions to 1.15.2 (#6477) 2026-07-07 18:59:59 -07:00
Lorenze Jay
6244738d2a feat: bump versions to 1.15.2a2 (#6421) 2026-07-01 14:55:27 -07:00
Lorenze Jay
958d8270db feat: bump versions to 1.15.2a1 (#6397) 2026-06-30 11:43:14 -07:00
João Moura
340f6ad5b8 feat: bump versions to 1.15.1 (#6366) 2026-06-27 03:48:21 -03:00
Lorenze Jay
1e2c965a75 feat: bump versions to 1.15.1a1 (#6361) 2026-06-26 15:12:37 -07:00
Lorenze Jay
54e28c155e feat: bump versions to 1.15.0 (#6339) 2026-06-25 16:10:48 -07:00
Vinicius Brasil
563b55f7ca feat: bump versions to 1.14.8a5 (#6328) 2026-06-24 17:25:08 -07:00
Vinicius Brasil
12a5e91efb feat: bump versions to 1.14.8a4 (#6318) 2026-06-24 09:14:14 -07:00
Vinicius Brasil
658b8ee8b9 feat: bump versions to 1.14.8a3 (#6309) 2026-06-23 14:05:23 -07:00
Vinicius Brasil
f48a6389f1 feat: bump versions to 1.14.8a2 (#6229) 2026-06-18 16:37:27 -07:00
João Moura
504c5c9b04 JSON crew fixes (#6217)
* feat: update pyproject.toml to specify wheel targets

Added a new section to the pyproject.toml file to include only specific files in the wheel build, enhancing the packaging process. Updated tests to verify the inclusion of these targets.

* feat: add memory save event handling to activity log

Implemented event handlers for MemorySaveStartedEvent, MemorySaveCompletedEvent, and MemorySaveFailedEvent in the crew_run_tui module. This allows the application to log memory save operations, capturing their status and details in the activity log. Added corresponding tests to verify the correct logging behavior for successful and failed memory saves.

* feat: enhance memory save event handling in activity log

Added functionality to suppress nested memory save events and updated the handling of MemorySaveStartedEvent, MemorySaveCompletedEvent, and MemorySaveFailedEvent to improve logging accuracy. Introduced new tests to verify the correct behavior of memory save events, including scenarios for nested events and completion updates for timed-out entries.

* Fix memory save activity log handling

* Normalize alpha package versions

* Update scaffolded crew dependency

* feat: add button to copy setup instructions for CrewAI coding agents

Introduced a button in the documentation that allows users to easily copy setup instructions for CrewAI coding agents. The instructions include installation steps, environment setup, and best practices for using the CrewAI CLI. This enhancement aims to streamline the onboarding process for new users.

* Improve missing CrewAI install guidance

* fix: address pr review feedback

* fix: avoid mismatched memory save rows

* fix: wait for queued memory save events

* fix: avoid matching memory saves on missing ids

* chore: normalize prerelease version to 1.14.8a1
2026-06-18 14:14:54 -03:00
João Moura
6c41d55fe2 feat: bump versions to 1.14.8a (#6215) 2026-06-18 02:39:42 -03:00
Greyson LaLonde
f18c03cd8f feat: bump versions to 1.14.7 2026-06-11 10:06:07 -07:00
Greyson LaLonde
05a2ba9ca4 feat: bump versions to 1.14.7rc2 2026-06-10 20:45:29 -07:00
Greyson LaLonde
68910b70c0 feat: bump versions to 1.14.7rc1 2026-06-10 18:50:54 -07:00
Greyson LaLonde
820c3905e3 feat: bump versions to 1.14.7a4 2026-06-09 12:51:55 -07:00
Greyson LaLonde
48c1987fcf feat: bump versions to 1.14.7a3 2026-06-08 18:43:15 -07:00
Lorenze Jay
17cfbdf95f feat: bump versions to 1.14.7a2 (#6054) 2026-06-05 14:15:43 -07:00
Lorenze Jay
be3cf62b63 feat: bump versions to 1.14.7a1 (#6031) 2026-06-03 10:30:33 -07:00
Greyson LaLonde
0486b85aa3 feat: bump versions to 1.14.6 2026-05-28 09:47:19 -07:00
Greyson LaLonde
d52106b3c7 feat: bump versions to 1.14.6a2 2026-05-27 16:42:40 -07:00
Greyson LaLonde
81c21e3166 feat: bump versions to 1.14.6a1
Some checks failed
CodeQL Advanced / Analyze (actions) (push) Has been cancelled
CodeQL Advanced / Analyze (python) (push) Has been cancelled
Vulnerability Scan / pip-audit (push) Has been cancelled
Mark stale issues and pull requests / stale (push) Has been cancelled
2026-05-21 15:09:48 +08:00
Greyson LaLonde
c50da7a6f2 feat: bump versions to 1.14.5 2026-05-19 03:11:26 +08:00
Greyson LaLonde
a6225da326 feat: bump versions to 1.14.5a7 2026-05-18 21:08:46 +08:00
Heitor Carvalho
65ec783aae feat: bump versions to 1.14.5a6 (#5827) 2026-05-15 16:51:59 -03:00
Greyson LaLonde
2034f2140a feat: bump versions to 1.14.5a5 2026-05-13 02:54:13 +08:00
Greyson LaLonde
a09c4de2fd feat: bump versions to 1.14.5a4 2026-05-09 03:08:22 +08:00
Greyson LaLonde
e961a005cb feat: bump versions to 1.14.5a3
Some checks failed
Build uv cache / build-cache (3.10) (push) Has been cancelled
Build uv cache / build-cache (3.11) (push) Has been cancelled
Build uv cache / build-cache (3.12) (push) Has been cancelled
Build uv cache / build-cache (3.13) (push) Has been cancelled
CodeQL Advanced / Analyze (actions) (push) Has been cancelled
CodeQL Advanced / Analyze (python) (push) Has been cancelled
Vulnerability Scan / pip-audit (push) Has been cancelled
2026-05-07 01:44:05 +08:00
Greyson LaLonde
57d1b338f7 feat: bump versions to 1.14.5a2 2026-05-04 22:58:06 +08:00
Lorenze Jay
5db72250b2 feat: bump versions to 1.14.5a1 (#5677)
* feat: bump versions to 1.14.5a1

* chore: update tool specifications

---------

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
2026-05-01 14:21:50 -07:00
Ishan Goswami
07c4a30f2e feat(crewai-tools): add highlights to ExaSearchTool, rename from EXASearchTool
Some checks failed
CodeQL Advanced / Analyze (actions) (push) Has been cancelled
CodeQL Advanced / Analyze (python) (push) Has been cancelled
Check Documentation Broken Links / Check broken links (push) Has been cancelled
Vulnerability Scan / pip-audit (push) Has been cancelled
* feat(crewai-tools): add highlights to ExaSearchTool, rename from EXASearchTool

- Add a highlights init param so agents can get token-efficient excerpts instead of full pages
- Rename EXASearchTool to ExaSearchTool; keep EXASearchTool as a deprecated alias so existing imports keep working
- Update the docs and example to use highlights as the recommended option
- Add a small note that says Exa is the fastest and most accurate web search API
- Add tests for the new highlights param and the deprecation alias

* fix(crewai-tools): import order and module-level Exa for tests

- Reorder std-lib imports so ruff is happy with force-sort-within-sections.
- Import Exa at module level (with a fallback) so the existing test mocks resolve.
  The lazy install prompt still works if exa_py is missing.
- Allow content and summary to be a dict, matching highlights.
- Trim test file to the cases this PR introduces (highlights param and the
  EXASearchTool deprecation alias). Existing init-shape tests stay.

Co-Authored-By: ishan <ishan@exa.ai>

* chore(crewai-tools): drop self-explanatory comment on schema alias

Co-Authored-By: ishan <ishan@exa.ai>

* docs(crewai-tools): default highlights to True, drop summary from examples

Co-Authored-By: ishan <ishan@exa.ai>

* docs(crewai-tools): simplify highlights examples to highlights=True

Co-Authored-By: ishan <ishan@exa.ai>

* feat(crewai-tools): add x-exa-integration header for usage tracking

Co-Authored-By: ishan <ishan@exa.ai>

* docs(crewai-tools): add Exa MCP section and resources links

Co-Authored-By: ishan <ishan@exa.ai>

---------

Co-authored-by: ishan <ishan@exa.ai>
Co-authored-by: Greyson LaLonde <greyson.r.lalonde@gmail.com>
Co-authored-by: Lorenze Jay <63378463+lorenzejay@users.noreply.github.com>
2026-05-01 21:25:23 +08:00
Greyson LaLonde
2c0323c3fe feat: bump versions to 1.14.4 2026-05-01 02:57:37 +08:00