Commit Graph

45 Commits

Author SHA1 Message Date
Prerna Kakkar
e2ec345e4a Merge branch 'main' into envvariable 2025-07-16 11:50:21 +00:00
prernakakkar-google
ed5ef4caea feat: Create wait for tool (#885)
`
tools:
  wait_for_tool:
    kind: wait-for
description: "Tool puts chat to sleep for given timeout example 3m,10s,
5m etc. For tasks such as cluster creation no need to wait. It takes
longer time such as 8m for instance creation. Use timeout value as
default if nothing is provided"
    timeout: 10s
`

Output: 
`
prernakakkar@prernakakkar:~/senseai/genai-toolbox$ curl -X POST -H
"Content-Type: application/json" -d '{"duration": "5m"}'
http://127.0.0.1:5000/api/tool/wa
it_for_tool/invoke
{"result":"[\"Wait for 5m0s completed successfully.\"]"}
`
2025-07-16 17:18:24 +05:30
Prerna Kakkar
6f569bc950 [feat]: Create tool to update mcp settings file for data plane with relevant env variables for alloydb 2025-07-16 07:54:42 +00:00
AlexTalreja
c081ace46b fix: cleanup unassigned err log (#857)
Ref: #843 

Addressed one of the bug fixes needed to merge before release.
2025-07-11 00:28:35 +00:00
AlexTalreja
aa8dbec970 fix: trigger reload on additional fsnotify operations (#854)
Allow fsnotify `CREATE` and `RENAME` events to trigger dynamic reload,
instead of requiring `WRITE`.

This is due to some cases with specific editors/OS, (ex: vim on Mac),
where file writes can potentially occur without ever triggering a
`WRITE` operation on the watched tools file, but solely through creation
and renaming of .swp files.
2025-07-10 16:39:26 -07:00
AlexTalreja
4c240ac3c9 feat: dynamic reloading for toolbox config (#800)
Allow Toolbox server to automatically update when users modify their
tool configuration file(s), instead of requiring a restart.

This feature is automatically enabled, but can be turned off with the
flag `--disable-reload`.
2025-07-08 17:28:12 -07:00
Mohd Mujtaba
40679d700e feat: add support for multiple YAML configuration files (#760)
# Add Multiple YAML Configuration File Support

## 🎯 Overview

This PR introduces support for loading and merging multiple YAML
configuration files in Toolbox, addressing the need for modular
configuration management in complex deployments.

##  New Features

### 1. Multiple Files Support (`--tools-files`)
- **Usage**: `--tools-files=file1.yaml,file2.yaml,file3.yaml`
- Load and intelligently merge multiple YAML configuration files
- Comma-separated file paths for maximum flexibility

### 2. Directory Support (`--tools-folder`)
- **Usage**: `--tools-folder=config-directory`
- Automatically discover and load all `.yaml` and `.yml` files from a
directory
- Simplifies configuration management for organized deployments

### 3. Smart Merging Logic
- **Sources/AuthServices/Tools**: Later files override earlier files
with same names
- **Toolsets**: Tools from same-named toolsets are combined without
duplicates
- Preserves all existing functionality while enabling composition

## 🔒 Safety & Validation

- **Mutual Exclusivity**: Prevents simultaneous use of `--tools-file`,
`--tools-files`, `--tools-folder`, and `--prebuilt`
- **Clear Error Messages**: Descriptive validation errors guide users to
correct usage
- **Comprehensive Error Handling**: Proper handling of missing files,
directories, and parsing errors
- **Full Backward Compatibility**: Existing configurations continue to
work unchanged

## 🏗️ Implementation Details

### Core Functions Added
- `mergeToolsFiles()` - Smart merging with configurable override rules
- `loadAndMergeToolsFiles()` - Multi-file loading and processing
- `loadAndMergeToolsFolder()` - Directory scanning and batch loading

### Command Structure Updates
- New `tools_files []string` field for multiple file paths
- New `tools_folder string` field for directory path
- Enhanced validation logic in `run()` function
- Updated flag definitions with proper descriptions

## 📋 Use Cases

### Organizational Benefits
- **Modular Configuration**: Separate database, API, and auth
configurations
- **Team Collaboration**: Multiple developers can work on different
config files
- **Environment Management**: Easy configuration swapping for different
environments
- **Scalability**: Large configurations can be broken into manageable
chunks

### Example Usage Patterns
```bash
# Multiple specific files
./toolbox --tools-files=database.yaml,apis.yaml,auth.yaml

# Directory-based loading
./toolbox --tools-folder=./production-configs

# Error case (properly handled)
./toolbox --tools-file=single.yaml --tools-folder=configs
# ERROR: --tools-file, --tools-files, and --tools-folder flags cannot be used simultaneously

---------

Co-authored-by: Wenxin Du <117315983+duwenxin99@users.noreply.github.com>
2025-06-30 14:00:49 -04:00
Wenxin Du
a1b60100c2 chore: Group tools by type (#743)
Group tools of the same type into the same folder so that they are more
discoverable and our tools are more organized as the number grows.
2025-06-30 11:37:48 -04:00
Yuan
d51dbc759b fix: do not listen from port for stdio (#719)
Fix #711
2025-06-17 11:35:04 -07:00
Yuan
65dba4cabc chore: update to get version from ServerConfig (#718) 2025-06-16 11:26:51 -07:00
Wenxin Du
054ec198b9 feat: Add Valkey Source and Tool (#532) 2025-06-11 23:17:32 -04:00
Wenxin Du
f0aef29b0c feat: Add Redis Source and Tool (#519)
1. Added Redis Source and Tool
2. Moved some integration test helpers from tools.go to common.go
3. Make auth integration test want an input variable
2025-06-11 22:47:27 -04:00
Yuan
075dfa47e1 feat(tools/spanner): add templateParameters field for spanner (#691)
Add `templateParameters` to support non-filter parameters and DDL
statements.

Added a new argument `ignoreDdl` at integration test. Admin client is
needed to execute ddl statement in spanner. Toolbox does not use admin
client.

Part of #535
2025-06-11 23:54:13 +00:00
Kurtis Van Gent
cf96f4c249 fix: improve versionString (#658)
Reduces complexity of the version string calculation and fixes the ci/cd
pipeline to pass the correct parameters.

---------

Co-authored-by: Averi Kitsch <akitsch@google.com>
Co-authored-by: Yuan <45984206+Yuan325@users.noreply.github.com>
2025-06-09 15:31:42 -07:00
Averi Kitsch
29aa0a70da feat(metrics): add user agent for prebuilt tools (#669)
Append "+prebuilt.<source>" to the user agent for tracking the prebuilt
tools usage. This is set before the server is initialized and the user
agent is set on the client.

Using the period to stay consistent with our other appended metadata
like "binary.linux"
2025-06-06 09:49:25 -07:00
Kurtis Van Gent
1c9ad5ea24 refactor: implement dynamic source registration (#614)
This commit refactors the source configuration and loading mechanism to
use a dynamic registration pattern. Each source package now registers
itself with a central registry via its init() function.

The server configuration code uses this registry to decode and
initialize sources, decoupling it from specific source implementations
and simplifying the addition of new sources.

Key changes:
- Introduced `sources.Register()` and `newConfig()` constructor in each
source package.
- Moved source package imports to `cmd/root.go` as blank imports to
trigger `init()` functions for self-registration.
- Removed direct imports of specific source packages from
`internal/server/config.go`.
- Renamed `SourceKind` constants to `Kind` within each source package.
- Updated tests to use the new `Kind` constants and reflect registration
changes.

---------

Co-authored-by: Yuan Teoh <yuanteoh@google.com>
2025-06-04 14:23:57 -07:00
Kurtis Van Gent
b4862825e8 refactor: implement dynamic tool registration (#613)
This PR refactors the tool configuration and loading mechanism to use a
dynamic registration pattern. Each tool package now registers itself
with a central registry, and the server configuration code uses this
registry to decode and initialize tools.

Key changes:
- Introduced tools.Register and tools.DecodeToolConfig for dynamic tool
handling.
- Removed direct imports of specific tool packages from
internal/server/config.go.
- Updated individual tool packages to include init() functions for
self-registration.
- Modified ToolKind constants to be local kind constants within each
tool package.
- Adjusted test files to reflect the changes in tool kind identifiers.

This change simplifies adding new tools and decouples the server
configuration from specific tool implementations.

---------

Co-authored-by: Yuan Teoh <yuanteoh@google.com>
Co-authored-by: Yuan <45984206+Yuan325@users.noreply.github.com>
2025-06-04 10:19:42 -07:00
Yuan
ba8a6f3a3b chore: migrate golangci-lint to v2 (#630)
gosimple had been deprecated in favor of staticcheck:
https://github.com/golangci/golangci-lint/issues/357

Other requirements are all migrated.

`std-error-handling` exclusions is included because without that, it
will ask to check all error returns from (`Close()`, or `os.Setenv`s, or
`fmt.Fprint`s...
2025-05-31 02:50:17 +00:00
dishaprakash
a29c80012e feat: Adding support for the --prebuilt flag (#604)
Introduces a new --prebuilt <source_type> flag. This flag is mutually
exclusive with the existing --tools-file flag.

Added a new directory cmd/prebuiltconfigs/ to store the prebuilt
tools.yaml files (e.g., alloydb.yaml, postgres.yaml, etc.).
These YAML files are embedded into the Go binary using the //go:embed
directive.

---------

Co-authored-by: Averi Kitsch <akitsch@google.com>
2025-05-28 14:56:42 -07:00
Yuan
1702ce1e00 feat: support MCP stdio transport protocol (#607)
Support MCP
[stdio](https://modelcontextprotocol.io/specification/2024-11-05/basic/transports#stdio)
transport protocol!

To run stdio with Toolbox, user have to use the `--stdio` flag.

Example of running MCP Toolbox with MCP Inspector via stdio transport
protocol: `npx @modelcontextprotocol/inspector ./toolbox --stdio`.

---------

Co-authored-by: Kurtis Van Gent <31518063+kurtisvg@users.noreply.github.com>
Co-authored-by: Averi Kitsch <akitsch@google.com>
2025-05-28 10:10:34 -07:00
Wenxin Du
eadb678a7b feat: Support env replacement for tool.yaml (#462)
Environment variable replacement is needed so that users don't have to
hardcode their secrets in configuring `tools.yaml`.
Both formats `$ENV_NAME` and `${ENV_NAME}` are standard ways to declare
an environment variable.
However, some database statement placeholders that are already using the
`$ENV_NAME` format.
Therefore, we only support env var declaration using `${ENV_NAME}` to
disambiguate it from other usages.

Fixes issue: https://github.com/googleapis/genai-toolbox/issues/431
2025-04-23 07:33:02 -04:00
Yuan
dced46ad88 chore: cleanup go context (#457) 2025-04-21 20:16:05 +00:00
Yuan
34a7263fdc fix: add tools-file flag and deprecate tools_file (#384)
Add `tools-file` flag and deprecate `tools_file` flag. This is not a
breaking change. The old `tools_file` flag is still usable.

User will see the following message when using `tools_file` flag: 
```
Flag --tools_file has been deprecated, please use --tools-file instead
2025-04-03T10:09:12.803165-07:00 INFO "Initialized 2 sources."
```

Help command will reveal the new flag: 
```
...
      --telemetry-service-name string   Sets the value of the service.name resource attribute for telemetry data. (default "toolbox")
      --tools-file string               File path specifying the tool configuration. (default "tools.yaml")
  -v, --version                         version for toolbox
...
```

Fixes #383
2025-04-03 11:09:31 -07:00
Yuan
04cb5fbc3e feat!: deprecate authsource in favor of authservice (#297)
Rename existing `authSource` to `authService` through deprecation.
`AuthService` more clearly distinguishes it from `Sources` objects.

`authSources` will be converted into `authServices` after the
unmarshalling process. A warning log is shown if `authSources` are used
(for both within tools parameters and defining auth services):
```
2025-02-20T13:57:51.156025-08:00 WARN "`authSources` is deprecated, use `authServices` for parameters instead"
2025-02-20T13:57:51.156569-08:00 WARN "`authSources` is deprecated, use `authServices` instead"
2025-02-20T13:57:52.047584-08:00 INFO "Initialized 1 sources."
...
```

The manifest generated will continue to use `authSources` to keep
compatibility with the sdks:
```
{
"serverVersion":"0.1.0",
"tools":{
  "test_tool2":{
    "description":"Use this tool to test\n",
    "parameters":[{
      "name":"user_id",
      "type":"string",
      "description":"Auto-populated from Google login",
      "authSources":["my-google-auth"]
      }]
    }
  }
}
```



Test cases with `authSources` are kept for compatibility. Will be
removed when `authSources` are no longer supported.
2025-02-21 18:36:04 -08:00
Yuan
df28036b84 chore: add and retrieves logger from context (#301)
Add functionality to add and retrieve logger from Go context.
2025-02-21 21:28:40 +00:00
Yuan
95d29f9e8a chore: pass logger via context through unmarshaller (#300)
Passing logger via context. With this, we will be able to add logs
during the unmarshaling process.
2025-02-21 13:02:23 -08:00
Yuan
a0ac5334d1 chore: return error for untested fields in tools.yaml (#239)
This only checks within `SourceConfig`, `ToolConfig`, and
`AuthSourceConfig`.

Error when an unknown field is provided:
`2025-01-27T22:43:46.988401-08:00 ERROR "unable to parse tool file at
\"tools.yaml\": unable to parse as \"cloud-sql-postgres\": [2:1] unknown
field \"extra\"\n 1 | database: test_database\n> 2 | extra: here\n ^\n 3
| instance: toolbox-cloudsql\n 4 | kind: cloud-sql-postgres\n 5 |
password: postgres\n 6 | "`

Error when a required field is not provided:
`2025-01-27T17:49:47.584846-08:00 ERROR "unable to parse tool file at
\"tools.yaml\": validation failed: Key: 'Config.Region' Error:Field
validation for 'Region' failed on the 'required' tag"`

---------

Co-authored-by: Kurtis Van Gent <31518063+kurtisvg@users.noreply.github.com>
2025-02-03 15:30:27 -08:00
Yuan
45fc046437 chore: migrate yaml library to goccy/go-yaml (#211)
Migrate yaml library from
[gopkg.in/yaml.v3](https://pkg.go.dev/gopkg.in/yaml.v3) to
[goccy/go-yaml](https://github.com/goccy/go-yaml).

We are trying to add validation feature to the unmarshaling of yaml.
However, `yaml.v3` currently does not support that and the library had
not been actively maintained for awhile. This migration will allow us to
use validation processing such as
[go-playground/validator](https://github.com/go-playground/validator)

---------

Co-authored-by: Kurtis Van Gent <31518063+kurtisvg@users.noreply.github.com>
2025-01-16 09:15:18 -08:00
Yuan
1fcc20a846 feat: add support for OpenTelemetry (#205)
Co-authored-by: Kurtis Van Gent <31518063+kurtisvg@users.noreply.github.com>
Co-authored-by: Wenxin Du <117315983+duwenxin99@users.noreply.github.com>
2025-01-13 15:38:38 -08:00
Kurtis Van Gent
66ab70f702 fix: handle shutdown gracefully (#178)
Adds logic to make the server shutdown gracefully, including better
respecting cancelled contexts and providing up to 10 seconds to finish
current connections.
2024-12-31 09:53:53 -07:00
Yuan
809e547a48 feat: update log with given context (#147)
Update logging with the given context.
2024-12-23 19:55:25 -08:00
Wenxin Du
abd1eb702c fix: Set server version (#150) 2024-12-18 17:15:55 -05:00
Wenxin Du
77b0d43175 feat: Add Auth Source configuration (#71)
1. Add authentication source configs to Toolbox server.
2. Add Google auth implementation.
2024-12-13 12:22:42 -05:00
Yuan
45a38ca9f0 chore: separate listen and server into two functions (#121)
Separate listen and server into two distinct functions to prevent race
condition during testing.
2024-12-09 22:57:53 +00:00
Yuan
3df68f1b69 chore: set out and err io.Writer during initialization (#112)
Logger might be created pre- or post- flag. The logger defined pre- and
post- flag should be using the same out and err writer.

This will ensure that the server uses the same out and err writer
defined with the `WithStreams` options.
2024-12-05 16:14:43 -08:00
Yuan
5c690c5c30 feat: add options for command (#110)
Add Option to configure a Command.

Currently we are only supporting `WithLogger` Option.
2024-12-05 09:02:47 -08:00
Yuan
9a0f618efc feat: add --log-level and --logging-format flags (#97)
Logging support 4 different types of logging (debug, info, warn, error).
The default logging level is Info.

User will be able to set flag for log level (allowed values: "debug",
"info", "warn", "error"), example:
`go run . --log-level debug`

User will be able to set flag for logging format (allowed values:
"standard", "JSON"), example:
`go run . --logging-format json`

**sample http request log - std:**
server
```
2024-11-12T15:08:11.451377-08:00 INFO "Initalized 0 sources.\n"
```
httplog
```
2024-11-26T15:15:53.947287-08:00 INFO Response: 200 OK service: "httplog" httpRequest: {url: "http://127.0.0.1:5000/" method: "GET" path: "/" remoteIP: "127.0.0.1:64216" proto: "HTTP/1.1" requestID: "macbookpro.roam.interna/..." scheme: "http" header: {user-agent: "curl/8.7.1" accept: "*/*"}} httpResponse: {status: 200 bytes: 22 elapsed: 0.012417}
```

**sample http request log - structured:**
server
```
{
  "timestamp":"2024-11-04T16:45:11.987299-08:00",
  "severity":"ERROR",
  "logging.googleapis.com/sourceLocation":{
    "function":"github.com/googleapis/genai-toolbox/internal/log.(*StructuredLogger).Errorf",
    "file":"/Users/yuanteoh/github/genai-toolbox/internal/log/log.go","line":157
  },
  "message":"unable to parse tool file at \"tools.yaml\": \"cloud-sql-postgres1\" is not a valid kind of data source"
}
```
httplog
```
{
  "timestamp":"2024-11-26T15:12:49.290974-08:00",
  "severity":"INFO",
  "logging.googleapis.com/sourceLocation":{
      "function":"github.com/go-chi/httplog/v2.(*RequestLoggerEntry).Write",
      "file":"/Users/yuanteoh/go/pkg/mod/github.com/go-chi/httplog/v2@v2.1.1/httplog.go","line":173
  },
  "message":"Response: 200 OK",
  "service":"httplog",
  "httpRequest":{
      "url":"http://127.0.0.1:5000/",
      "method":"GET",
      "path":"/",
      "remoteIP":"127.0.0.1:64140",
      "proto":"HTTP/1.1",
      "requestID":"yuanteoh-macbookpro.roam.internal/NBrtYBu3q9-000001",
      "scheme":"http",
      "header":{"user-agent":"curl/8.7.1","accept":"*/*"}
  },
  "httpResponse":{"status":200,"bytes":22,"elapsed":0.0115}
}
```
2024-12-03 16:52:19 +00:00
Kurtis Van Gent
efe9e8bc97 chore: refactor sources/tools each into their own package (#42)
Moves all of the "source" and "tool" implementations into their own
packages. This layout makes it a bit more clear where the
implementations are, and seems likely to scale more cleanly as more
sources and tools are added.
2024-11-01 16:44:13 -06:00
Wenxin Du
61e7b78ad8 feat: Add Toolset manifest endpoint (#11)
1. Calculate tool manifests when server starts.
2. Add toolset manifest endpoints.

---------

Co-authored-by: Kurtis Van Gent <31518063+kurtisvg@users.noreply.github.com>
2024-10-17 18:43:58 -04:00
Wenxin Du
59b4bc07f4 feat: add toolset configuration (#12)
Add `Toolset` implementation to the `tools` package:
- struct and configs.
- Custom `UnmarshalYAML` function.
- Initialization function that validates if tools specified for the
toolset exist.
2024-10-11 14:11:05 -04:00
Kurtis Van Gent
336bdc4d56 feat: stub basic control plane functionality (#9)
Stub's out some basic control plane functionality. This also required
setting up some Source and Tools initialization.
2024-09-20 14:12:16 -06:00
Kurtis Van Gent
b9ba364fb6 feat: add basic parsing from tools file (#8) 2024-08-05 09:33:07 -06:00
Kurtis Van Gent
df9ad9e33f feat: add address and port flags (#7)
Add flags for setting the address and port of the server.
2024-07-30 10:55:13 -05:00
Kurtis Van Gent
e09ae30a90 feat: add basic http server (#6) 2024-07-26 16:59:01 -05:00
Kurtis Van Gent
1539ee56dd feat: add basic CLI (#5) 2024-07-15 11:12:29 -06:00