-
Notifications
You must be signed in to change notification settings - Fork 0
feat: add agent skills for package registry queries and AI tool integration #39
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
Changes from 1 commit
Commits
Show all changes
6 commits
Select commit
Hold shift + click to select a range
143ec97
feat: add agent skills for regxa usage and AI tool integration
oritwoen 11d5c1d
feat(skills): add OpenAI Codex agents metadata
oritwoen 947a7a8
feat(skills): add metadata frontmatter with author and version
oritwoen 0912a5d
fix(skills): correct cache clear docs, shorthand scope, and error han…
oritwoen cfb1c5f
fix(skills): address second round of review feedback
oritwoen cfbe781
fix(skills): add language tag, fix helper snippet, correct tool-error…
oritwoen File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Some comments aren't visible on the classic Files Changed page.
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,112 @@ | ||
| --- | ||
| name: regxa-ai-tool | ||
| description: Integrates regxa's packageTool into AI applications built with the Vercel AI SDK. Provides structured package registry queries (info, versions, dependencies, maintainers, bulk lookups) as a tool for LLM agents. Use when building AI apps that need to query npm, PyPI, crates.io, or other registries. Do not use for direct CLI usage or non-AI integrations. | ||
| --- | ||
|
|
||
| # regxa AI Tool Integration | ||
|
|
||
| regxa exports a ready-made `packageTool` compatible with the Vercel AI SDK. It gives AI agents structured access to package registry data across npm, PyPI, crates.io, RubyGems, Packagist, and Arch Linux. | ||
|
|
||
| ## Step 1: Install Dependencies | ||
|
|
||
| ```bash | ||
| npm install regxa ai @ai-sdk/openai # or any AI SDK provider | ||
| ``` | ||
|
|
||
| ## Step 2: Register the Tool | ||
|
|
||
| Import `packageTool` from `regxa/ai` and pass it to the AI SDK: | ||
|
|
||
| ```typescript | ||
| import { generateText } from "ai"; | ||
| import { openai } from "@ai-sdk/openai"; | ||
| import { packageTool } from "regxa/ai"; | ||
|
|
||
| const result = await generateText({ | ||
| model: openai("gpt-4o"), | ||
oritwoen marked this conversation as resolved.
Show resolved
Hide resolved
|
||
| tools: { package: packageTool }, | ||
| prompt: "What are the dependencies of flask 3.1.1?", | ||
| }); | ||
| ``` | ||
|
|
||
| The tool handles PURL construction, API calls, normalization, and error handling internally. | ||
|
|
||
| ## Step 3: Understand the Operations | ||
|
|
||
| The tool accepts a discriminated union input with these operations: | ||
|
|
||
| ### `package` - Fetch package metadata | ||
|
|
||
| ```json | ||
| { "operation": "package", "purl": "pkg:npm/lodash" } | ||
| ``` | ||
|
|
||
| Returns: name, description, licenses, repository, latest version, keywords. | ||
|
|
||
| ### `versions` - List all versions | ||
|
|
||
| ```json | ||
| { "operation": "versions", "purl": "pkg:cargo/serde" } | ||
| ``` | ||
|
|
||
| Returns: version numbers, publish dates, integrity hashes, status (yanked/deprecated). | ||
|
|
||
| ### `dependencies` - List dependencies for a version | ||
|
|
||
| ```json | ||
| { "operation": "dependencies", "purl": "pkg:pypi/flask@3.1.1" } | ||
| ``` | ||
|
|
||
| Returns: dependency names, version constraints, scope (runtime/dev/test/build), optional flag. | ||
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| **Note:** The PURL must include a version. Without it, the tool returns an error. | ||
|
|
||
| ### `maintainers` - List package maintainers | ||
|
|
||
| ```json | ||
| { "operation": "maintainers", "purl": "pkg:gem/rails" } | ||
| ``` | ||
|
|
||
| Returns: login, name, email, role for each maintainer. | ||
|
|
||
| ### `bulk-packages` - Fetch multiple packages at once | ||
|
|
||
| ```json | ||
| { "operation": "bulk-packages", "purls": ["pkg:npm/lodash", "pkg:cargo/serde"], "concurrency": 10 } | ||
| ``` | ||
|
|
||
| Returns: map of PURL to package metadata. Fetches up to 50 PURLs concurrently (default concurrency: 15). Failed lookups are silently omitted. | ||
|
|
||
| ## Step 4: Use with Streaming | ||
|
|
||
| The tool works with `streamText` as well: | ||
|
|
||
| ```typescript | ||
| import { streamText } from "ai"; | ||
| import { packageTool } from "regxa/ai"; | ||
|
|
||
| const result = streamText({ | ||
| model: openai("gpt-4o"), | ||
| tools: { package: packageTool }, | ||
| prompt: "Compare the latest versions of express and fastify", | ||
| }); | ||
|
|
||
| for await (const chunk of result.textStream) { | ||
| process.stdout.write(chunk); | ||
| } | ||
| ``` | ||
|
|
||
| ## PURL Format Quick Reference | ||
|
|
||
| Read `references/purl-cheatsheet.md` for the PURL format details and ecosystem-specific examples. | ||
|
|
||
| ## Error Handling | ||
|
|
||
| The tool handles errors internally and returns them as structured error objects: | ||
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| - **Package not found**: Returns error with ecosystem and package name | ||
| - **Invalid PURL**: Returns parse error with details | ||
| - **Unknown ecosystem**: Returns list of supported ecosystems | ||
| - **Rate limiting**: The HTTP client retries automatically with exponential backoff | ||
|
|
||
| If the tool call fails at the AI SDK level, the agent receives the error message and can self-correct (e.g., fix PURL format, try a different ecosystem). | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,52 @@ | ||
| # PURL Cheatsheet | ||
|
|
||
| Quick reference for constructing PURLs to pass to the regxa AI tool. | ||
|
|
||
| ## Format | ||
|
|
||
| ``` | ||
| pkg:<type>/<name>@<version> | ||
| ``` | ||
|
|
||
| ## Examples by Ecosystem | ||
|
|
||
| | Package | PURL | | ||
| |---------|------| | ||
| | lodash (npm) | `pkg:npm/lodash` | | ||
| | lodash v4.17.21 | `pkg:npm/lodash@4.17.21` | | ||
| | @babel/core (npm scoped) | `pkg:npm/%40babel/core@7.0.0` | | ||
| | flask (PyPI) | `pkg:pypi/flask@3.1.1` | | ||
| | Django REST Framework | `pkg:pypi/django-rest-framework` | | ||
| | serde (Rust) | `pkg:cargo/serde@1.0.0` | | ||
| | rails (Ruby) | `pkg:gem/rails@7.1.0` | | ||
| | laravel/framework (PHP) | `pkg:composer/laravel/framework@11.0.0` | | ||
| | linux (Arch official) | `pkg:alpm/arch/linux` | | ||
| | yay (AUR) | `pkg:alpm/aur/yay` | | ||
|
|
||
| ## Scoped Packages | ||
|
|
||
| npm scopes: encode `@` as `%40`: | ||
| - `@vue/core` -> `pkg:npm/%40vue/core` | ||
| - `@types/node` -> `pkg:npm/%40types/node` | ||
|
|
||
| Composer vendors: use path separator: | ||
| - `symfony/console` -> `pkg:composer/symfony/console` | ||
|
|
||
| ## Common Mistakes | ||
|
|
||
| | Wrong | Correct | Why | | ||
| |-------|---------|-----| | ||
| | `pkg:npm/@babel/core` | `pkg:npm/%40babel/core` | `@` must be percent-encoded | | ||
| | `pkg:pip/flask` | `pkg:pypi/flask` | Type is `pypi`, not `pip` | | ||
| | `pkg:crate/serde` | `pkg:cargo/serde` | Type is `cargo`, not `crate` | | ||
| | `pkg:rubygems/rails` | `pkg:gem/rails` | Type is `gem`, not `rubygems` | | ||
| | `pkg:packagist/laravel/framework` | `pkg:composer/laravel/framework` | Type is `composer` | | ||
| | `pkg:pypi/Django_REST_Framework` | `pkg:pypi/django-rest-framework` | PyPI names are normalized | | ||
|
|
||
| ## Operations That Require a Version | ||
|
|
||
| The `dependencies` operation requires a version in the PURL: | ||
| - `pkg:npm/lodash@4.17.21` (works) | ||
| - `pkg:npm/lodash` (fails for dependencies) | ||
|
|
||
| All other operations work with or without a version. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,165 @@ | ||
| --- | ||
| name: regxa | ||
| description: Query package metadata from npm, PyPI, crates.io, RubyGems, Packagist, and Arch Linux using regxa. Supports looking up package info, versions, dependencies, and maintainers via PURL-native API or CLI. Use when the user needs package registry data across ecosystems. Do not use for building or publishing packages, managing lockfiles, or installing dependencies. | ||
| --- | ||
|
|
||
| # Query Package Registries with regxa | ||
|
|
||
| regxa is a universal package registry client. It queries npm, PyPI, crates.io, RubyGems, Packagist, and Arch Linux with a single API. Packages are addressed using PURLs (Package URLs). | ||
|
|
||
| ## PURL Format | ||
|
|
||
| All queries use PURLs to identify packages: | ||
|
|
||
| ``` | ||
| pkg:<type>/<name>@<version> | ||
| ``` | ||
coderabbitai[bot] marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| | Ecosystem | PURL type | Example | | ||
| |-----------|-----------|---------| | ||
| | npm | `npm` | `pkg:npm/lodash`, `pkg:npm/%40babel/core@7.0.0` | | ||
| | PyPI | `pypi` | `pkg:pypi/flask@3.1.1` | | ||
| | crates.io | `cargo` | `pkg:cargo/serde@1.0.0` | | ||
| | RubyGems | `gem` | `pkg:gem/rails@7.1.0` | | ||
| | Packagist | `composer` | `pkg:composer/laravel/framework@11.0.0` | | ||
| | Arch Linux | `alpm` | `pkg:alpm/arch/linux`, `pkg:alpm/aur/yay` | | ||
|
|
||
| Shorthand without `pkg:` prefix also works: `npm/lodash@4.17.21`. | ||
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| Read `references/purl-guide.md` for scoped packages, namespaces, and special characters. | ||
|
|
||
| ## Using the CLI | ||
|
|
||
| ### Package info | ||
|
|
||
| ```bash | ||
| regxa info npm/lodash | ||
| regxa info pkg:cargo/serde --json | ||
| ``` | ||
|
|
||
| ### Version listing | ||
|
|
||
| ```bash | ||
| regxa versions pypi/flask | ||
| regxa versions pkg:npm/%40vue/core --json | ||
| ``` | ||
|
|
||
| ### Dependencies (requires version) | ||
|
|
||
| ```bash | ||
| regxa deps npm/lodash@4.17.21 | ||
| regxa deps pkg:pypi/flask@3.1.1 --json | ||
| ``` | ||
|
|
||
| ### Maintainers | ||
|
|
||
| ```bash | ||
| regxa maintainers gem/rails | ||
| regxa maintainers pkg:composer/laravel/framework | ||
| ``` | ||
|
|
||
| ### Cache management | ||
|
|
||
| ```bash | ||
| regxa cache clear # Clear all cached data | ||
| regxa cache clear npm # Clear cache for one ecosystem | ||
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| ``` | ||
|
|
||
| All commands accept `--json` for machine-readable output and `--no-cache` to bypass the cache. | ||
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| ## Using the Library API | ||
|
|
||
| ### Install | ||
|
|
||
| ```bash | ||
| npm install regxa | ||
| ``` | ||
|
|
||
| ### One-shot PURL helpers | ||
|
|
||
| The simplest way to query. Pass a PURL string, get normalized data: | ||
|
|
||
| ```typescript | ||
| import { | ||
| fetchPackageFromPURL, | ||
| fetchVersionsFromPURL, | ||
| fetchDependenciesFromPURL, | ||
| fetchMaintainersFromPURL, | ||
| bulkFetchPackages, | ||
| } from "regxa"; | ||
|
|
||
| // Single package | ||
| const pkg = await fetchPackageFromPURL("pkg:npm/lodash"); | ||
| console.log(pkg.name, pkg.licenses, pkg.latestVersion); | ||
|
|
||
| // All versions | ||
| const versions = await fetchVersionsFromPURL("pkg:cargo/serde"); | ||
|
|
||
| // Dependencies for a specific version | ||
| const deps = await fetchDependenciesFromPURL("pkg:pypi/flask@3.1.1"); | ||
|
|
||
| // Maintainers | ||
| const maintainers = await fetchMaintainersFromPURL("pkg:gem/rails"); | ||
|
|
||
| // Bulk fetch (up to 50, concurrent) | ||
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| const packages = await bulkFetchPackages([ | ||
| "pkg:npm/lodash", | ||
| "pkg:cargo/serde", | ||
| "pkg:pypi/flask", | ||
| ]); | ||
| ``` | ||
|
|
||
| ### Registry API (lower level) | ||
|
|
||
| For more control, create a registry instance directly: | ||
|
|
||
| ```typescript | ||
| import { create } from "regxa"; | ||
|
|
||
| const npm = create("npm"); | ||
|
|
||
| const pkg = await npm.fetchPackage("lodash"); | ||
| const versions = await npm.fetchVersions("@babel/core"); | ||
| const deps = await npm.fetchDependencies("lodash", "4.17.21"); | ||
| const urls = npm.urls(); | ||
| console.log(urls.registry("lodash")); // npmjs.com URL | ||
| console.log(urls.documentation("lodash")); // docs URL | ||
| console.log(urls.purl("lodash", "4.17.21")); // PURL string | ||
| ``` | ||
|
|
||
| ### Cached queries | ||
|
|
||
| Wrap any registry with caching: | ||
|
|
||
| ```typescript | ||
| import { create, CachedRegistry } from "regxa"; | ||
|
|
||
| const npm = create("npm"); | ||
| const cached = new CachedRegistry(npm); | ||
|
|
||
| // First call fetches from network, subsequent calls use disk cache | ||
| const pkg = await cached.fetchPackage("lodash"); | ||
| ``` | ||
|
|
||
| ### Helper utilities | ||
|
|
||
| ```typescript | ||
| import { selectVersion, resolveDocsUrl } from "regxa"; | ||
|
|
||
| // Pick the best version from a list | ||
| const best = selectVersion(versions, { requested: "4.17.21" }); | ||
|
|
||
| // Resolve documentation URL with fallback chain | ||
| const docsUrl = resolveDocsUrl(pkg, registry.urls(), "4.17.21"); | ||
oritwoen marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| ``` | ||
|
|
||
| Read `references/api-reference.md` for the full type definitions and return shapes. | ||
|
|
||
| ## Error Handling | ||
|
|
||
| | Error | When | What to do | | ||
| |-------|------|------------| | ||
| | `NotFoundError` | Package or version does not exist | Check the PURL spelling and ecosystem | | ||
| | `InvalidPURLError` | Malformed PURL string | Fix the format (see PURL table above) | | ||
| | `UnknownEcosystemError` | Unsupported ecosystem type | Use one of: npm, cargo, pypi, gem, composer, alpm | | ||
| | `RateLimitError` | Registry rate limit hit | The client retries automatically; wait if persistent | | ||
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.