{"record":{"id":"75b97e5380c0dfda","repo":"containerd/containerd","slug":"unsupported-client-type-t","errorCode":null,"errorMessage":"unsupported client type %T","messagePattern":"unsupported client type %T","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"core/sandbox/bridge.go","lineNumber":37,"sourceCode":"// NewClient returns a new sandbox client that handles both GRPC and TTRPC clients.\nfunc NewClient(client any) (api.TTRPCSandboxService, error) {\n\tswitch c := client.(type) {\n\tcase *ttrpc.Client:\n\t\treturn api.NewTTRPCSandboxClient(c), nil\n\tcase grpc.ClientConnInterface:\n\t\treturn &grpcBridge{api.NewSandboxClient(c)}, nil\n\tdefault:\n\t\treturn nil, fmt.Errorf(\"unsupported client type %T\", client)\n\t}\n}\n\ntype grpcBridge struct {\n\tclient api.SandboxClient\n}\n\nvar _ api.TTRPCSandboxService = (*grpcBridge)(nil)\n\nfunc (g *grpcBridge) CreateSandbox(ctx context.Context, request *api.CreateSandboxRequest) (*api.CreateSandboxResponse, error) {\n\treturn g.client.CreateSandbox(ctx, request)\n}\n\nfunc (g *grpcBridge) StartSandbox(ctx context.Context, request *api.StartSandboxRequest) (*api.StartSandboxResponse, error) {\n\treturn g.client.StartSandbox(ctx, request)\n}","sourceCodeStart":19,"sourceCodeEnd":55,"githubUrl":"https://github.com/containerd/containerd/blob/4246446a2bf7d03837b0244118d858799393bd80/core/sandbox/bridge.go#L19-L55","documentation":"Returned by sandbox.NewClient (core/sandbox/bridge.go:37) when the passed client is neither a *ttrpc.Client nor a grpc.ClientConnInterface. It is a programming/configuration error: only TTRPC and gRPC sandbox clients are supported for bridging to the sandbox service API.","triggerScenarios":"Calling sandbox.NewClient (directly or via sandbox Create/Start/getSandbox paths) with a client value that is neither *ttrpc.Client nor a gRPC ClientConnInterface.","commonSituations":"Passing a raw net.Conn, a custom connection wrapper, or a client type from a different transport library into the sandbox bridge; API changes where callers previously passed a different client type.","solutions":["Pass a *ttrpc.Client or a *grpc.ClientConn (any grpc.ClientConnInterface) obtained from the shim's connection.","Convert your connection: use ttrpc.NewClient(conn) or grpc.NewClient(addr/sock) before calling NewClient.","Check the caller (Create/Start/getSandbox) is forwarding the correct client type from the container's shim connection."],"exampleFix":"// before\ncl, err := sandbox.NewClient(ctx, rawNetConn)\n// after\ncl, err := sandbox.NewClient(ctx, ttrpc.NewClient(rawNetConn))","handlingStrategy":"type-guard","validationCode":"switch c := client.(type) {\ncase *ttrpc.Client, grpc.ClientConnInterface:\n    // ok\ndefault:\n    return fmt.Errorf(\"need ttrpc.Client or grpc ClientConnInterface, got %T\", client)\n}","typeGuard":"func isSandboxClient(c any) bool {\n    switch c.(type) {\n    case *ttrpc.Client:\n        return true\n    case grpc.ClientConnInterface:\n        return true\n    }\n    return false\n}","tryCatchPattern":"if err != nil {\n    if strings.Contains(err.Error(), \"unsupported client type\") {\n        return fmt.Errorf(\"bridge the connection via ttrpc.NewClient or grpc.NewClient first\")\n    }\n    return err\n}","preventionTips":["Always obtain the shim client via containerd's connection helpers (ttrpc/gRPC) before calling sandbox APIs.","Pass *grpc.ClientConn, not net.Conn or custom wrappers.","Add a compile-time assertion that your client satisfies grpc.ClientConnInterface."],"tags":["type-mismatch","sandbox","ttrpc","grpc"],"backgroundTag":"unsupported-client-type","analyzedSha":"4246446a2bf7d03837b0244118d858799393bd80","analyzedAt":"2026-09-02T00:14:43.053Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-09T06:17:21.866Z"}