github.com/anthropics/anthropic-sdk-go@v1.70.1/betatunnel.go (about) 1 // File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details. 2 3 package anthropic 4 5 import ( 6 "context" 7 "errors" 8 "fmt" 9 "net/http" 10 "net/url" 11 "slices" 12 "time" 13 14 "github.com/anthropics/anthropic-sdk-go/internal/apijson" 15 "github.com/anthropics/anthropic-sdk-go/internal/apiquery" 16 "github.com/anthropics/anthropic-sdk-go/internal/requestconfig" 17 "github.com/anthropics/anthropic-sdk-go/option" 18 "github.com/anthropics/anthropic-sdk-go/packages/pagination" 19 "github.com/anthropics/anthropic-sdk-go/packages/param" 20 "github.com/anthropics/anthropic-sdk-go/packages/respjson" 21 "github.com/anthropics/anthropic-sdk-go/shared/constant" 22 ) 23 24 // BetaTunnelService contains methods and other services that help with interacting 25 // with the anthropic API. 26 // 27 // Note, unlike clients, this service does not read variables from the environment 28 // automatically. You should not instantiate this service directly, and instead use 29 // the [NewBetaTunnelService] method instead. 30 type BetaTunnelService struct { 31 Options []option.RequestOption 32 Certificates BetaTunnelCertificateService 33 } 34 35 // NewBetaTunnelService generates a new service that applies the given options to 36 // each request. These options are applied after the parent client's options (if 37 // there is one), and before any request-specific options. 38 func NewBetaTunnelService(opts ...option.RequestOption) (r BetaTunnelService) { 39 r = BetaTunnelService{} 40 r.Options = opts 41 r.Certificates = NewBetaTunnelCertificateService(opts...) 42 return 43 } 44 45 // The Tunnels API is in research preview. It requires the 46 // `anthropic-beta: mcp-tunnels-2026-06-22` header and may change without a 47 // deprecation period. It supersedes the Admin API endpoints at 48 // `/v1/organizations/tunnels`, which remain available during a migration window. 49 // 50 // Creates a tunnel. Creation allocates a fresh hostname and provisions the tunnel; 51 // it is not idempotent. The new tunnel rejects MCP traffic until at least one CA 52 // certificate is added. 53 func (r *BetaTunnelService) New(ctx context.Context, params BetaTunnelNewParams, opts ...option.RequestOption) (res *BetaTunnel, err error) { 54 for _, v := range params.Betas { 55 opts = append(opts, option.WithHeaderAdd("anthropic-beta", fmt.Sprintf("%v", v))) 56 } 57 if !param.IsOmitted(params.WorkspaceID) { 58 opts = append(opts, option.WithHeader("anthropic-workspace-id", fmt.Sprintf("%v", params.WorkspaceID.Value))) 59 } 60 opts = slices.Concat(r.Options, opts) 61 opts = append([]option.RequestOption{option.WithHeader("anthropic-beta", "mcp-tunnels-2026-06-22")}, opts...) 62 path := "v1/tunnels?beta=true" 63 err = requestconfig.ExecuteNewRequest(ctx, http.MethodPost, path, params, &res, opts...) 64 return res, err 65 } 66 67 // The Tunnels API is in research preview. It requires the 68 // `anthropic-beta: mcp-tunnels-2026-06-22` header and may change without a 69 // deprecation period. It supersedes the Admin API endpoints at 70 // `/v1/organizations/tunnels`, which remain available during a migration window. 71 // 72 // Fetches a tunnel by ID. 73 func (r *BetaTunnelService) Get(ctx context.Context, tunnelID string, query BetaTunnelGetParams, opts ...option.RequestOption) (res *BetaTunnel, err error) { 74 for _, v := range query.Betas { 75 opts = append(opts, option.WithHeaderAdd("anthropic-beta", fmt.Sprintf("%v", v))) 76 } 77 if !param.IsOmitted(query.WorkspaceID) { 78 opts = append(opts, option.WithHeader("anthropic-workspace-id", fmt.Sprintf("%v", query.WorkspaceID.Value))) 79 } 80 opts = slices.Concat(r.Options, opts) 81 opts = append([]option.RequestOption{option.WithHeader("anthropic-beta", "mcp-tunnels-2026-06-22")}, opts...) 82 if tunnelID == "" { 83 err = errors.New("missing required tunnel_id parameter") 84 return nil, err 85 } 86 path := fmt.Sprintf("v1/tunnels/%s?beta=true", tunnelID) 87 err = requestconfig.ExecuteNewRequest(ctx, http.MethodGet, path, nil, &res, opts...) 88 return res, err 89 } 90 91 // The Tunnels API is in research preview. It requires the 92 // `anthropic-beta: mcp-tunnels-2026-06-22` header and may change without a 93 // deprecation period. It supersedes the Admin API endpoints at 94 // `/v1/organizations/tunnels`, which remain available during a migration window. 95 // 96 // Lists tunnels. Results are ordered by creation time, newest first; archived 97 // tunnels are excluded unless include_archived is set. 98 func (r *BetaTunnelService) List(ctx context.Context, params BetaTunnelListParams, opts ...option.RequestOption) (res *pagination.PageCursor[BetaTunnel], err error) { 99 var raw *http.Response 100 for _, v := range params.Betas { 101 opts = append(opts, option.WithHeaderAdd("anthropic-beta", fmt.Sprintf("%v", v))) 102 } 103 if !param.IsOmitted(params.WorkspaceID) { 104 opts = append(opts, option.WithHeader("anthropic-workspace-id", fmt.Sprintf("%v", params.WorkspaceID.Value))) 105 } 106 opts = slices.Concat(r.Options, opts) 107 opts = append([]option.RequestOption{option.WithHeader("anthropic-beta", "mcp-tunnels-2026-06-22"), option.WithResponseInto(&raw)}, opts...) 108 path := "v1/tunnels?beta=true" 109 cfg, err := requestconfig.NewRequestConfig(ctx, http.MethodGet, path, params, &res, opts...) 110 if err != nil { 111 return nil, err 112 } 113 err = cfg.Execute() 114 if err != nil { 115 return nil, err 116 } 117 res.SetPageConfig(cfg, raw) 118 return res, nil 119 } 120 121 // The Tunnels API is in research preview. It requires the 122 // `anthropic-beta: mcp-tunnels-2026-06-22` header and may change without a 123 // deprecation period. It supersedes the Admin API endpoints at 124 // `/v1/organizations/tunnels`, which remain available during a migration window. 125 // 126 // Lists tunnels. Results are ordered by creation time, newest first; archived 127 // tunnels are excluded unless include_archived is set. 128 func (r *BetaTunnelService) ListAutoPaging(ctx context.Context, params BetaTunnelListParams, opts ...option.RequestOption) *pagination.PageCursorAutoPager[BetaTunnel] { 129 return pagination.NewPageCursorAutoPager(r.List(ctx, params, opts...)) 130 } 131 132 // The Tunnels API is in research preview. It requires the 133 // `anthropic-beta: mcp-tunnels-2026-06-22` header and may change without a 134 // deprecation period. It supersedes the Admin API endpoints at 135 // `/v1/organizations/tunnels`, which remain available during a migration window. 136 // 137 // Archives a tunnel. Archival is irreversible: every non-archived certificate on 138 // the tunnel is archived in the same operation, the hostname is retired and never 139 // re-allocated, and the tunnel token is invalidated. Retrying against an 140 // already-archived tunnel returns the existing record unchanged. 141 func (r *BetaTunnelService) Archive(ctx context.Context, tunnelID string, body BetaTunnelArchiveParams, opts ...option.RequestOption) (res *BetaTunnel, err error) { 142 for _, v := range body.Betas { 143 opts = append(opts, option.WithHeaderAdd("anthropic-beta", fmt.Sprintf("%v", v))) 144 } 145 if !param.IsOmitted(body.WorkspaceID) { 146 opts = append(opts, option.WithHeader("anthropic-workspace-id", fmt.Sprintf("%v", body.WorkspaceID.Value))) 147 } 148 opts = slices.Concat(r.Options, opts) 149 opts = append([]option.RequestOption{option.WithHeader("anthropic-beta", "mcp-tunnels-2026-06-22")}, opts...) 150 if tunnelID == "" { 151 err = errors.New("missing required tunnel_id parameter") 152 return nil, err 153 } 154 path := fmt.Sprintf("v1/tunnels/%s/archive?beta=true", tunnelID) 155 err = requestconfig.ExecuteNewRequest(ctx, http.MethodPost, path, nil, &res, opts...) 156 return res, err 157 } 158 159 // The Tunnels API is in research preview. It requires the 160 // `anthropic-beta: mcp-tunnels-2026-06-22` header and may change without a 161 // deprecation period. It supersedes the Admin API endpoints at 162 // `/v1/organizations/tunnels`, which remain available during a migration window. 163 // 164 // Reveals a tunnel's connector token. The value is fetched live on each call; 165 // Anthropic does not store it. Repeated calls return the same value until the 166 // token is rotated. Exposed as POST so the token does not appear in intermediary 167 // access logs. 168 func (r *BetaTunnelService) RevealToken(ctx context.Context, tunnelID string, body BetaTunnelRevealTokenParams, opts ...option.RequestOption) (res *BetaTunnelToken, err error) { 169 for _, v := range body.Betas { 170 opts = append(opts, option.WithHeaderAdd("anthropic-beta", fmt.Sprintf("%v", v))) 171 } 172 if !param.IsOmitted(body.WorkspaceID) { 173 opts = append(opts, option.WithHeader("anthropic-workspace-id", fmt.Sprintf("%v", body.WorkspaceID.Value))) 174 } 175 opts = slices.Concat(r.Options, opts) 176 opts = append([]option.RequestOption{option.WithHeader("anthropic-beta", "mcp-tunnels-2026-06-22")}, opts...) 177 if tunnelID == "" { 178 err = errors.New("missing required tunnel_id parameter") 179 return nil, err 180 } 181 path := fmt.Sprintf("v1/tunnels/%s/reveal_token?beta=true", tunnelID) 182 err = requestconfig.ExecuteNewRequest(ctx, http.MethodPost, path, nil, &res, opts...) 183 return res, err 184 } 185 186 // The Tunnels API is in research preview. It requires the 187 // `anthropic-beta: mcp-tunnels-2026-06-22` header and may change without a 188 // deprecation period. It supersedes the Admin API endpoints at 189 // `/v1/organizations/tunnels`, which remain available during a migration window. 190 // 191 // Rotates a tunnel's connector token. Rotation invalidates the current token for 192 // new connections and returns a fresh value; established connections are not 193 // severed. A connector restarted after rotation must use the new value. 194 func (r *BetaTunnelService) RotateToken(ctx context.Context, tunnelID string, params BetaTunnelRotateTokenParams, opts ...option.RequestOption) (res *BetaTunnelToken, err error) { 195 for _, v := range params.Betas { 196 opts = append(opts, option.WithHeaderAdd("anthropic-beta", fmt.Sprintf("%v", v))) 197 } 198 if !param.IsOmitted(params.WorkspaceID) { 199 opts = append(opts, option.WithHeader("anthropic-workspace-id", fmt.Sprintf("%v", params.WorkspaceID.Value))) 200 } 201 opts = slices.Concat(r.Options, opts) 202 opts = append([]option.RequestOption{option.WithHeader("anthropic-beta", "mcp-tunnels-2026-06-22")}, opts...) 203 if tunnelID == "" { 204 err = errors.New("missing required tunnel_id parameter") 205 return nil, err 206 } 207 path := fmt.Sprintf("v1/tunnels/%s/rotate_token?beta=true", tunnelID) 208 err = requestconfig.ExecuteNewRequest(ctx, http.MethodPost, path, params, &res, opts...) 209 return res, err 210 } 211 212 // An MCP tunnel. 213 type BetaTunnel struct { 214 // Unique identifier for the tunnel, prefixed with `tnl_`. 215 ID string `json:"id" api:"required"` 216 // A timestamp in RFC 3339 format 217 ArchivedAt time.Time `json:"archived_at" api:"required" format:"date-time"` 218 // A timestamp in RFC 3339 format 219 CreatedAt time.Time `json:"created_at" api:"required" format:"date-time"` 220 // Human-readable name for the tunnel (1-255 characters). Null if unset. 221 DisplayName string `json:"display_name" api:"required"` 222 // Anthropic-assigned hostname for the tunnel. MCP server URLs whose host is a 223 // subdomain of this value are routed through the tunnel. Globally unique and never 224 // reused, even after the tunnel is archived. 225 Domain string `json:"domain" api:"required"` 226 Type constant.Tunnel `json:"type" default:"tunnel"` 227 // JSON contains metadata for fields, check presence with [respjson.Field.Valid]. 228 JSON struct { 229 ID respjson.Field 230 ArchivedAt respjson.Field 231 CreatedAt respjson.Field 232 DisplayName respjson.Field 233 Domain respjson.Field 234 Type respjson.Field 235 ExtraFields map[string]respjson.Field 236 raw string 237 } `json:"-"` 238 } 239 240 // Returns the unmodified JSON received from the API 241 func (r BetaTunnel) RawJSON() string { return r.JSON.raw } 242 func (r *BetaTunnel) UnmarshalJSON(data []byte) error { 243 return apijson.UnmarshalRoot(data, r) 244 } 245 246 // A tunnel's connector token. 247 type BetaTunnelToken struct { 248 // Stable identifier for the current token value. Changes when the token is 249 // rotated. 250 ID string `json:"id" api:"required"` 251 // The connector token used to run the tunnel. Treat as a credential. 252 TunnelToken string `json:"tunnel_token" api:"required"` 253 Type constant.TunnelToken `json:"type" default:"tunnel_token"` 254 // JSON contains metadata for fields, check presence with [respjson.Field.Valid]. 255 JSON struct { 256 ID respjson.Field 257 TunnelToken respjson.Field 258 Type respjson.Field 259 ExtraFields map[string]respjson.Field 260 raw string 261 } `json:"-"` 262 } 263 264 // Returns the unmodified JSON received from the API 265 func (r BetaTunnelToken) RawJSON() string { return r.JSON.raw } 266 func (r *BetaTunnelToken) UnmarshalJSON(data []byte) error { 267 return apijson.UnmarshalRoot(data, r) 268 } 269 270 type BetaTunnelNewParams struct { 271 // Optional human-readable name for the tunnel (1-255 characters). 272 DisplayName param.Opt[string] `json:"display_name,omitzero"` 273 WorkspaceID param.Opt[string] `header:"anthropic-workspace-id,omitzero" json:"-"` 274 // Optional header to specify the beta version(s) you want to use. 275 Betas []AnthropicBeta `header:"anthropic-beta,omitzero" json:"-"` 276 paramObj 277 } 278 279 func (r BetaTunnelNewParams) MarshalJSON() (data []byte, err error) { 280 type shadow BetaTunnelNewParams 281 return param.MarshalObject(r, (*shadow)(&r)) 282 } 283 func (r *BetaTunnelNewParams) UnmarshalJSON(data []byte) error { 284 return apijson.UnmarshalRoot(data, r) 285 } 286 287 type BetaTunnelGetParams struct { 288 WorkspaceID param.Opt[string] `header:"anthropic-workspace-id,omitzero" json:"-"` 289 // Optional header to specify the beta version(s) you want to use. 290 Betas []AnthropicBeta `header:"anthropic-beta,omitzero" json:"-"` 291 paramObj 292 } 293 294 type BetaTunnelListParams struct { 295 // Whether to include archived tunnels in the results. Defaults to false. 296 IncludeArchived param.Opt[bool] `query:"include_archived,omitzero" json:"-"` 297 // Maximum number of tunnels to return per page. Defaults to 20, maximum 1000. 298 Limit param.Opt[int64] `query:"limit,omitzero" json:"-"` 299 // Opaque pagination cursor from a previous `list_tunnels` response. 300 Page param.Opt[string] `query:"page,omitzero" json:"-"` 301 WorkspaceID param.Opt[string] `header:"anthropic-workspace-id,omitzero" json:"-"` 302 // Optional header to specify the beta version(s) you want to use. 303 Betas []AnthropicBeta `header:"anthropic-beta,omitzero" json:"-"` 304 paramObj 305 } 306 307 // URLQuery serializes [BetaTunnelListParams]'s query parameters as `url.Values`. 308 func (r BetaTunnelListParams) URLQuery() (v url.Values, err error) { 309 return apiquery.MarshalWithSettings(r, apiquery.QuerySettings{ 310 ArrayFormat: apiquery.ArrayQueryFormatBrackets, 311 NestedFormat: apiquery.NestedQueryFormatBrackets, 312 }) 313 } 314 315 type BetaTunnelArchiveParams struct { 316 WorkspaceID param.Opt[string] `header:"anthropic-workspace-id,omitzero" json:"-"` 317 // Optional header to specify the beta version(s) you want to use. 318 Betas []AnthropicBeta `header:"anthropic-beta,omitzero" json:"-"` 319 paramObj 320 } 321 322 type BetaTunnelRevealTokenParams struct { 323 WorkspaceID param.Opt[string] `header:"anthropic-workspace-id,omitzero" json:"-"` 324 // Optional header to specify the beta version(s) you want to use. 325 Betas []AnthropicBeta `header:"anthropic-beta,omitzero" json:"-"` 326 paramObj 327 } 328 329 type BetaTunnelRotateTokenParams struct { 330 // Optional free-text reason for the rotation, recorded for audit. 331 Reason param.Opt[string] `json:"reason,omitzero"` 332 WorkspaceID param.Opt[string] `header:"anthropic-workspace-id,omitzero" json:"-"` 333 // Optional header to specify the beta version(s) you want to use. 334 Betas []AnthropicBeta `header:"anthropic-beta,omitzero" json:"-"` 335 paramObj 336 } 337 338 func (r BetaTunnelRotateTokenParams) MarshalJSON() (data []byte, err error) { 339 type shadow BetaTunnelRotateTokenParams 340 return param.MarshalObject(r, (*shadow)(&r)) 341 } 342 func (r *BetaTunnelRotateTokenParams) UnmarshalJSON(data []byte) error { 343 return apijson.UnmarshalRoot(data, r) 344 }