Skip to content

v6.8.52#439

Merged
luispater merged 19 commits intomainfrom
plus
Mar 13, 2026
Merged

v6.8.52#439
luispater merged 19 commits intomainfrom
plus

Conversation

@luispater
Copy link

No description provided.

luispater and others added 18 commits March 11, 2026 10:47
test(translator): add tests for handling Claude system messages as string and array
feat(proxy): centralize proxy handling with `proxyutil` package and enhance test coverage

- Added `proxyutil` package to simplify proxy handling across the codebase.
- Refactored various components (`executor`, `cliproxy`, `auth`, etc.) to use `proxyutil` for consistent and reusable proxy logic.
- Introduced support for "direct" proxy mode to explicitly bypass all proxies.
- Updated tests to validate proxy behavior (e.g., `direct`, HTTP/HTTPS, and SOCKS5).
- Enhanced YAML configuration documentation for proxy options.
feat(config/codex): Add Codex header defaults (`user-agent`: override; `beta-features`: default)
when Amp or Claude Code sends functionResponse with an empty name in Gemini
conversation history, the Gemini API rejects the request with 400
"Name cannot be empty". this fix backfills empty names from the
corresponding preceding functionCall parts using positional matching.

covers all three Gemini translator paths:
- gemini/gemini (direct API key)
- antigravity/gemini (OAuth)
- gemini-cli/gemini (Gemini CLI)

also switches fixCLIToolResponse pending group matching from LIFO to
FIFO to correctly handle multiple sequential tool call groups.

fixes #1903
…sponse-names

fix: backfill empty functionResponse.name from preceding functionCall
Refactor Antigravity model handling and improve logging
feat(model_registry): enhance model registration and refresh mechanisms
@gemini-code-assist
Copy link

Summary of Changes

Hello, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

This pull request significantly refactors and enhances the application's proxy handling, model management, and API translation capabilities. It centralizes proxy configuration into a new utility package, enabling more flexible and explicit proxy bypass options. The model registry now supports dynamic, periodic updates for Antigravity models and provides a callback for reacting to these changes. Additionally, it introduces configurable default headers for Codex OAuth requests and improves Gemini function call translation for better API compatibility.

Highlights

  • Centralized Proxy Handling: Introduced a new proxyutil package to centralize and standardize proxy configuration logic across the application, supporting direct and none bypass options.
  • Dynamic Antigravity Model Fetching: Added a new command-line utility (cmd/fetch_antigravity_models) to dynamically fetch and save Antigravity model lists, moving away from static model configuration for this provider.
  • Enhanced Model Registry Refresh: Implemented periodic model catalog refreshes with a callback mechanism to re-register models for affected providers when definitions change, ensuring up-to-date model availability.
  • Codex Header Customization: Added configuration options (codex-header-defaults) to allow users to specify default User-Agent and x-codex-beta-features headers for Codex OAuth model requests.
  • Gemini Function Call Name Backfilling: Improved Gemini and Antigravity Gemini translators to automatically backfill empty function response names from corresponding function call names, addressing a common API compatibility issue.
  • Refactored Antigravity Model Management: Simplified Antigravity model handling by removing the dedicated primary models cache and backfill logic, now relying on the centralized model registry for dynamic updates.

🧠 New Feature in Public Preview: You can now enable Memory to help Gemini Code Assist learn from your team's feedback. This makes future code reviews more consistent and personalized to your project's style. Click here to enable Memory in your admin console.

Changelog
  • cmd/fetch_antigravity_models/main.go
    • Added new command to fetch and save Antigravity model lists to a JSON file.
  • config.example.yaml
    • Updated comments to document direct and none proxy bypass options.
    • Added example configuration for codex-header-defaults.
  • internal/api/handlers/management/api_tools.go
    • Removed direct net and golang.org/x/net/proxy imports.
    • Refactored buildProxyTransport to utilize the new proxyutil.BuildHTTPTransport function.
  • internal/api/handlers/management/api_tools_test.go
    • Removed tests related to resolveTokenForAuth and memoryAuthStore.
    • Added tests for apiCallTransport to verify direct proxy bypass and fallback behavior.
  • internal/api/handlers/management/test_store_test.go
    • Added new test file containing a memoryAuthStore implementation for testing purposes.
  • internal/auth/claude/utls_transport.go
    • Removed net/url import.
    • Refactored newUtlsRoundTripper to use proxyutil.BuildDialer for proxy configuration.
  • internal/auth/gemini/gemini_auth.go
    • Removed net, net/url, and golang.org/x/net/proxy imports.
    • Refactored proxy configuration in GetAuthenticatedClient to use proxyutil.BuildHTTPTransport.
  • internal/config/codex_websocket_header_defaults_test.go
    • Added new test file for CodexHeaderDefaults configuration loading and sanitization.
  • internal/config/config.go
    • Added CodexHeaderDefaults struct to define default headers for Codex OAuth requests.
    • Integrated CodexHeaderDefaults into the main Config struct.
    • Added SanitizeCodexHeaderDefaults method to trim whitespace from configured Codex headers.
    • Included SanitizeCodexHeaderDefaults in the LoadConfigOptional function call chain.
  • internal/registry/model_definitions.go
    • Removed AntigravityModelConfig struct.
    • Changed Antigravity field in staticModelsJSON from a map to a slice of ModelInfo.
    • Removed GetAntigravityModelConfig and cloneAntigravityModelConfig functions.
    • Updated GetAntigravityModels to return a slice of ModelInfo.
    • Adjusted GetStaticModelDefinitionsByChannel and LookupStaticModelInfo to reflect the new Antigravity model structure.
  • internal/registry/model_registry.go
    • Moved modelQuotaExceededWindow to a package-level constant.
    • Added a comment clarifying that re-registering a client clears transient scheduling state.
    • Removed local quotaExpiredDuration variables, using the constant instead.
  • internal/registry/model_updater.go
    • Added modelsRefreshInterval constant for periodic updates.
    • Introduced ModelRefreshCallback type and SetModelRefreshCallback function for external notification of model changes.
    • Implemented periodicRefresh, tryPeriodicRefresh, and tryStartupRefresh for continuous model catalog updates.
    • Refactored tryRefreshModels to detect changes between old and new model data and notify callbacks.
    • Added fetchModelsFromRemote to encapsulate remote model fetching logic.
    • Introduced detectChangedProviders, modelSectionChanged, notifyModelRefresh, and mergeProviderNames for granular change detection and notification.
    • Removed validateAntigravitySection as Antigravity models are now handled as ModelInfo slices.
  • internal/registry/models/models.json
    • Converted the antigravity section from a map of AntigravityModelConfig to an array of full ModelInfo objects.
  • internal/runtime/executor/antigravity_executor.go
    • Removed antigravityPrimaryModelsCache and associated caching/fallback functions.
    • Removed antigravityModelsPath constant, as model fetching is now handled by the new command.
  • internal/runtime/executor/antigravity_executor_models_cache_test.go
    • Removed test file related to the antigravityPrimaryModelsCache.
  • internal/runtime/executor/codex_executor.go
    • Modified applyCodexHeaders to accept a config.Config parameter.
    • Updated applyCodexHeaders to use new helper functions (codexHeaderDefaults, ensureHeaderWithConfigPrecedence) for setting User-Agent based on configuration precedence.
  • internal/runtime/executor/codex_websockets_executor.go
    • Modified applyCodexWebsocketHeaders to accept a config.Config parameter.
    • Refactored newProxyAwareWebsocketDialer to use proxyutil.Parse for robust proxy URL parsing.
    • Introduced codexHeaderDefaults to determine default Codex headers based on auth type and configuration.
    • Added ensureHeaderWithPriority and ensureHeaderWithConfigPrecedence for flexible header application logic.
  • internal/runtime/executor/codex_websockets_executor_test.go
    • Added tests for applyCodexWebsocketHeaders to verify config defaults, existing header precedence, and API key auth behavior.
    • Added a test for applyCodexHeaders to check config User-Agent for OAuth.
    • Added a test for newProxyAwareWebsocketDialer to confirm direct proxy bypass.
  • internal/runtime/executor/proxy_helpers.go
    • Removed net, net/url, and golang.org/x/net/proxy imports.
    • Refactored buildProxyTransport to use proxyutil.BuildHTTPTransport for consistent proxy setup.
  • internal/runtime/executor/proxy_helpers_test.go
    • Added new test file for newProxyAwareHTTPClient to verify direct proxy bypass.
  • internal/translator/antigravity/gemini/antigravity_gemini_request.go
    • Added CallNames field to FunctionCallGroup to store ordered function call names.
    • Modified parseFunctionResponseRaw to accept a fallbackName for backfilling empty function response names.
    • Updated fixCLIToolResponse to collect function call names and use them to backfill empty function response names in the correct order.
  • internal/translator/antigravity/gemini/antigravity_gemini_request_test.go
    • Added new tests for fixCLIToolResponse to cover backfilling empty function response names, preserving existing names, handling extra responses, and processing multiple groups in FIFO order.
  • internal/translator/codex/claude/codex_claude_request.go
    • Modified ConvertClaudeRequestToCodex to handle both string and array types for the system field.
    • Implemented filtering for x-anthropic-billing-header from system messages.
  • internal/translator/codex/claude/codex_claude_request_test.go
    • Added new test file for ConvertClaudeRequestToCodex to verify system message parsing and filtering scenarios.
  • internal/translator/gemini-cli/gemini/gemini-cli_gemini_request.go
    • Added CallNames field to FunctionCallGroup.
    • Introduced backfillFunctionResponseName to ensure function response names are populated.
    • Updated fixCLIToolResponse to collect function call names and use them for backfilling empty function response names in the correct order.
  • internal/translator/gemini/gemini/gemini_gemini_request.go
    • Added backfillEmptyFunctionResponseNames function to iterate through contents and backfill empty function response names from preceding function calls.
    • Integrated backfillEmptyFunctionResponseNames into ConvertGeminiRequestToGemini.
  • internal/translator/gemini/gemini/gemini_gemini_request_test.go
    • Added new test file for backfillEmptyFunctionResponseNames covering single, parallel, preserved, extra, and multiple group scenarios.
  • internal/util/proxy.go
    • Removed context, net, net/url, and golang.org/x/net/proxy imports.
    • Refactored SetProxy to use proxyutil.BuildHTTPTransport for consistent proxy configuration.
  • sdk/cliproxy/rtprovider.go
    • Removed context, net, net/url, and golang.org/x/net/proxy imports.
    • Refactored RoundTripperFor to use proxyutil.BuildHTTPTransport for proxy setup.
  • sdk/cliproxy/rtprovider_test.go
    • Added new test file for RoundTripperFor to verify direct proxy bypass.
  • sdk/cliproxy/service.go
    • Removed comments about FetchAntigravityModels from applyCoreAuthAddOrUpdate.
    • Added registerResolvedModelsForAuth helper function.
    • Implemented SetModelRefreshCallback to re-register models for affected providers upon catalog changes.
    • Removed backfillAntigravityModels function.
    • Updated registerModelsForAuth to use registry.GetAntigravityModels() directly and s.registerResolvedModelsForAuth.
    • Added refreshModelRegistrationForAuth and latestAuthForModelRegistration for robust model re-registration logic.
  • sdk/cliproxy/service_antigravity_backfill_test.go
    • Removed test file related to Antigravity model backfilling.
  • sdk/proxyutil/proxy.go
    • Added new package proxyutil with Mode, Setting, Parse, NewDirectTransport, BuildHTTPTransport, and BuildDialer functions to centralize proxy logic.
  • sdk/proxyutil/proxy_test.go
    • Added new test file for the proxyutil package, covering Parse and BuildHTTPTransport functionality.
Ignored Files
  • Ignored by pattern: .github/workflows/** (3)
    • .github/workflows/docker-image.yml
    • .github/workflows/pr-test-build.yml
    • .github/workflows/release.yaml
Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for GitHub and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

Copy link

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces a significant refactoring of proxy handling by centralizing it into a new sdk/proxyutil package, which is a great improvement for maintainability. It also adds periodic remote model catalog refreshing, making the service more dynamic. Additionally, there are several good fixes for function call handling in translators and a new fetch_antigravity_models tool. My review focuses on improving the new tool's implementation and suggesting a refactoring for some duplicated code in the new header handling logic.

Comment on lines +79 to +80
fmt.Fprintf(os.Stderr, "error: cannot get working directory: %v\n", err)
os.Exit(1)

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

For consistency with the logging setup in this file, please use the log package for handling errors and warnings instead of writing directly to os.Stderr.

  • For fatal errors like this one, log.Fatalf("error: cannot get working directory: %v", err) can be used. It will print the message and exit the program, simplifying the code. This applies to lines 98-99, 102-103, 118-119, 150-151, and 155-156 as well.
  • For warnings (line 132), use log.Warnf(...).
  • For non-fatal errors (line 165), use log.Errorf(...).
Suggested change
fmt.Fprintf(os.Stderr, "error: cannot get working directory: %v\n", err)
os.Exit(1)
log.Fatalf("error: cannot get working directory: %v", err)

payload = []byte(`{}`)
}

httpReq, errReq := http.NewRequestWithContext(ctx, http.MethodPost, modelsURL, strings.NewReader(string(payload)))

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Converting the byte slice payload to a string and then using strings.NewReader creates an unnecessary copy. You can use bytes.NewReader(payload) directly to avoid this allocation and improve efficiency. You will need to add "bytes" to your imports.

Suggested change
httpReq, errReq := http.NewRequestWithContext(ctx, http.MethodPost, modelsURL, strings.NewReader(string(payload)))
httpReq, errReq := http.NewRequestWithContext(ctx, http.MethodPost, modelsURL, bytes.NewReader(payload))

httpReq.Header.Set("Authorization", "Bearer "+accessToken)
httpReq.Header.Set("User-Agent", "antigravity/1.19.6 darwin/arm64")

httpClient := &http.Client{Timeout: 30 * time.Second}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

The context passed to http.NewRequestWithContext on line 184 already has a 30-second timeout. Setting a separate Timeout on the http.Client is redundant and can lead to unclear behavior regarding which timeout takes precedence. It's generally recommended to rely on the context for request cancellation and timeouts.

Suggested change
httpClient := &http.Client{Timeout: 30 * time.Second}
httpClient := &http.Client{}

Comment on lines +869 to +911
func ensureHeaderWithPriority(target http.Header, source http.Header, key, configValue, fallbackValue string) {
if target == nil {
return
}
if strings.TrimSpace(target.Get(key)) != "" {
return
}
if source != nil {
if val := strings.TrimSpace(source.Get(key)); val != "" {
target.Set(key, val)
return
}
}
if val := strings.TrimSpace(configValue); val != "" {
target.Set(key, val)
return
}
if val := strings.TrimSpace(fallbackValue); val != "" {
target.Set(key, val)
}
}

func ensureHeaderWithConfigPrecedence(target http.Header, source http.Header, key, configValue, fallbackValue string) {
if target == nil {
return
}
if strings.TrimSpace(target.Get(key)) != "" {
return
}
if val := strings.TrimSpace(configValue); val != "" {
target.Set(key, val)
return
}
if source != nil {
if val := strings.TrimSpace(source.Get(key)); val != "" {
target.Set(key, val)
return
}
}
if val := strings.TrimSpace(fallbackValue); val != "" {
target.Set(key, val)
}
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

The functions ensureHeaderWithPriority and ensureHeaderWithConfigPrecedence are very similar, with the only difference being the order of precedence between configValue and source. This duplication could be avoided by creating a single, more generic helper function that accepts an ordered list of value sources. This would make the code more maintainable and less prone to copy-paste errors.

@luispater luispater merged commit 8178efa into router-for-me:main Mar 13, 2026
0 of 2 checks passed
@luispater luispater deleted the plus branch March 13, 2026 03:30
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants