From 96a6e3bef6b3fce2c9f426ad2cc2199548e07a5b Mon Sep 17 00:00:00 2001 From: Flavien Darche Date: Fri, 30 Aug 2024 16:54:57 +0200 Subject: [PATCH 1/5] Service Extension Callout (Envoy external processing) --- .../workflows/service-extensions-publish.yml | 65 ++++++ contrib/envoyproxy/envoy/fakehttp.go | 189 ++++++++++++++++++ .../cmd/serviceextensions/.gitignore | 1 + .../cmd/serviceextensions/Dockerfile | 20 ++ .../cmd/serviceextensions/localhost.crt | 19 ++ .../cmd/serviceextensions/localhost.key | 27 +++ .../cmd/serviceextensions/main.go | 148 ++++++++++++++ .../internal/telemetrytest/telemetry_test.go | 2 +- ddtrace/tracer/option.go | 17 -- ddtrace/tracer/option_test.go | 2 +- go.mod | 32 +-- go.sum | 23 ++- internal/env.go | 17 ++ 13 files changed, 526 insertions(+), 36 deletions(-) create mode 100644 .github/workflows/service-extensions-publish.yml create mode 100644 contrib/envoyproxy/envoy/fakehttp.go create mode 100644 contrib/envoyproxy/go-control-plane/cmd/serviceextensions/.gitignore create mode 100644 contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile create mode 100644 contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt create mode 100644 contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key create mode 100644 contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go diff --git a/.github/workflows/service-extensions-publish.yml b/.github/workflows/service-extensions-publish.yml new file mode 100644 index 0000000000..efb97be412 --- /dev/null +++ b/.github/workflows/service-extensions-publish.yml @@ -0,0 +1,65 @@ +name: Publish Service Extensions Callout images packages + +on: + push: + tags: + - 'v*.*' + workflow_dispatch: + inputs: + tag_name: + description: 'Docker image tag to use for the package' + required: true + default: 'dev' + commit_sha: + description: 'Commit SHA to checkout' + required: true + set_as_latest: + description: 'Set the tag as latest' + required: false + default: 'false' + +permissions: + contents: read + packages: write + +env: + TAG_NAME: ${{ github.ref_name || github.event.inputs.tag_name }} + REF_NAME: ${{ github.ref || github.event.inputs.commit_sha }} + COMMIT_SHA: ${{ github.sha || github.event.inputs.commit_sha }} + PUSH_LATEST: ${{ github.event.inputs.set_as_latest || 'true' }} + +jobs: + publish-service-extensions: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 + with: + ref: ${{ env.REF_NAME }} + + - name: Set up QEMU + uses: docker/setup-qemu-action@49b3bc8e6bdd4a60e6116a5414239cba5943d3cf # V3.2.0 + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@c47758b77c9736f4b2ef4073d4d51994fabfe349 # v3.7.1 + + - name: Login to Docker + shell: bash + run: docker login -u publisher -p ${{ secrets.GITHUB_TOKEN }} ghcr.io + + - name: Replace slashes in ref name + id: replace_ref + run: echo "TAG_NAME=${TAG_NAME//\//-}" >> $GITHUB_ENV + + - name: Build and push + id: build + uses: docker/build-push-action@4f58ea79222b3b9dc2c8bbdd6debcef730109a75 # v6.9.0 + with: + context: . + file: ./contrib/envoyproxy/envoy/cmd/serviceextensions/Dockerfile + platforms: linux/amd64,linux/arm64 + push: true + tags: | + ghcr.io/datadog/dd-trace-go/service-extensions-callout:${{ env.TAG_NAME }} + ghcr.io/datadog/dd-trace-go/service-extensions-callout:${{ env.COMMIT_SHA }} + ${{ env.PUSH_LATEST == 'true' && 'ghcr.io/datadog/dd-trace-go/service-extensions-callout:latest' }} diff --git a/contrib/envoyproxy/envoy/fakehttp.go b/contrib/envoyproxy/envoy/fakehttp.go new file mode 100644 index 0000000000..2d1a4652b1 --- /dev/null +++ b/contrib/envoyproxy/envoy/fakehttp.go @@ -0,0 +1,189 @@ +// Unless explicitly stated otherwise all files in this repository are licensed +// under the Apache License Version 2.0. +// This product includes software developed at Datadog (https://www.datadoghq.com/). +// Copyright 2024 Datadog, Inc. + +package envoy + +import ( + "context" + "crypto/tls" + "fmt" + "net/http" + "net/url" + "strconv" + "strings" + "sync" + + corev3 "github.com/envoyproxy/go-control-plane/envoy/config/core/v3" + extproc "github.com/envoyproxy/go-control-plane/envoy/service/ext_proc/v3" + "google.golang.org/grpc/metadata" +) + +// checkPseudoRequestHeaders Verify the required HTTP2 headers are present +// Some mandatory headers need to be set. It can happen when it wasn't a real HTTP2 request sent by Envoy, +func checkPseudoRequestHeaders(headers map[string]string) error { + for _, header := range []string{":authority", ":scheme", ":path", ":method"} { + if _, ok := headers[header]; !ok { + return fmt.Errorf("missing required headers: %q", header) + } + } + + return nil +} + +// checkPseudoResponseHeaders Verify the required HTTP2 headers are present +// Some mandatory headers need to be set. It can happen when it wasn't a real HTTP2 request sent by Envoy, +func checkPseudoResponseHeaders(headers map[string]string) error { + if _, ok := headers[":status"]; !ok { + return fmt.Errorf("missing required ':status' headers") + } + + return nil +} + +func getRemoteAddr(md metadata.MD) string { + xfwd := md.Get("x-forwarded-for") + length := len(xfwd) + if length == 0 { + return "" + } + + // Get the first right value of x-forwarded-for headers + // The rightmost IP address is the one that will be used as the remote client IP + // https://datadoghq.atlassian.net/wiki/spaces/TS/pages/2766733526/Sensitive+IP+information#Where-does-the-value-of-the-http.client_ip-tag-come-from%3F + return xfwd[length-1] +} + +// partitionPeusdoHeaders Separate normal headers of the initial request made by the client and the pseudo headers of HTTP/2 +// - Format the headers to be used by the tracer as a map[string][]string +// - Set headers keys to be canonical +func partitionPeusdoHeaders(receivedHeaders []*corev3.HeaderValue) (map[string][]string, map[string]string) { + headers := make(map[string][]string, len(receivedHeaders)-4) + pseudoHeaders := make(map[string]string, 4) + for _, v := range receivedHeaders { + key := v.GetKey() + if key == "" { + continue + } + if key[0] == ':' { + pseudoHeaders[key] = string(v.GetRawValue()) + continue + } + + headers[http.CanonicalHeaderKey(key)] = []string{string(v.GetRawValue())} + } + return headers, pseudoHeaders +} + +func NewFakeResponseWriterFromExtProc(w http.ResponseWriter, res *extproc.ProcessingRequest_ResponseHeaders) error { + headers, pseudoHeaders := partitionPeusdoHeaders(res.ResponseHeaders.GetHeaders().GetHeaders()) + + if err := checkPseudoResponseHeaders(pseudoHeaders); err != nil { + return err + } + + status, err := strconv.Atoi(pseudoHeaders[":status"]) + if err != nil { + return fmt.Errorf("error parsing status code %q: %w", pseudoHeaders[":status"], err) + } + + for k, v := range headers { + w.Header().Set(k, strings.Join(v, ",")) + } + + w.WriteHeader(status) + return nil +} + +// NewRequestFromExtProc creates a new http.Request from an ext_proc RequestHeaders message +func NewRequestFromExtProc(ctx context.Context, req *extproc.ProcessingRequest_RequestHeaders) (*http.Request, error) { + headers, pseudoHeaders := partitionPeusdoHeaders(req.RequestHeaders.GetHeaders().GetHeaders()) + if err := checkPseudoRequestHeaders(pseudoHeaders); err != nil { + return nil, err + } + + parsedURL, err := url.Parse(fmt.Sprintf("%s://%s%s", pseudoHeaders[":scheme"], pseudoHeaders[":authority"], pseudoHeaders[":path"])) + if err != nil { + return nil, fmt.Errorf( + "error building envoy URI from scheme %q, from host %q and from path %q: %w", + pseudoHeaders[":scheme"], + pseudoHeaders[":host"], + pseudoHeaders[":path"], + err) + } + + var remoteAddr string + md, ok := metadata.FromIncomingContext(ctx) + if ok { + remoteAddr = getRemoteAddr(md) + } + + var tlsState *tls.ConnectionState + if pseudoHeaders[":scheme"] == "https" { + tlsState = &tls.ConnectionState{} + } + + headers["Host"] = append(headers["Host"], pseudoHeaders[":authority"]) + + return (&http.Request{ + Method: pseudoHeaders[":method"], + Host: pseudoHeaders[":authority"], + RequestURI: pseudoHeaders[":path"], + URL: parsedURL, + Header: headers, + RemoteAddr: remoteAddr, + TLS: tlsState, + }).WithContext(ctx), nil +} + +type FakeResponseWriter struct { + mu sync.Mutex + status int + body []byte + headers http.Header +} + +// Reset resets the FakeResponseWriter to its initial state +func (w *FakeResponseWriter) Reset() { + w.mu.Lock() + defer w.mu.Unlock() + w.status = 0 + w.body = nil + w.headers = make(http.Header) +} + +// Status is not in the [http.ResponseWriter] interface, but it is cast into it by the tracing code +func (w *FakeResponseWriter) Status() int { + w.mu.Lock() + defer w.mu.Unlock() + return w.status +} + +func (w *FakeResponseWriter) WriteHeader(status int) { + w.mu.Lock() + defer w.mu.Unlock() + w.status = status +} + +func (w *FakeResponseWriter) Header() http.Header { + w.mu.Lock() + defer w.mu.Unlock() + return w.headers +} + +func (w *FakeResponseWriter) Write(b []byte) (int, error) { + w.mu.Lock() + defer w.mu.Unlock() + w.body = append(w.body, b...) + return len(b), nil +} + +var _ http.ResponseWriter = &FakeResponseWriter{} + +// NewFakeResponseWriter creates a new FakeResponseWriter that can be used to store the response a [http.Handler] made +func NewFakeResponseWriter() *FakeResponseWriter { + return &FakeResponseWriter{ + headers: make(http.Header), + } +} diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/.gitignore b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/.gitignore new file mode 100644 index 0000000000..68295c4a55 --- /dev/null +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/.gitignore @@ -0,0 +1 @@ +serviceextensions \ No newline at end of file diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile new file mode 100644 index 0000000000..5e4080ce5e --- /dev/null +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile @@ -0,0 +1,20 @@ +# Build stage +FROM golang:1.23-alpine AS builder +ENV CGO_ENABLED=1 +WORKDIR /app +COPY . . +RUN apk add --no-cache --update git build-base +RUN go build -tags=appsec -o ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions/serviceextensions ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions + +# Runtime stage +FROM alpine:3.20.3 +RUN apk --no-cache add ca-certificates tzdata libc6-compat libgcc libstdc++ +WORKDIR /app +COPY --from=builder /app/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/serviceextensions /app/serviceextensions +COPY ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt /app/localhost.crt +COPY ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key /app/localhost.key + +EXPOSE 80 +EXPOSE 443 + +CMD ["./serviceextensions"] diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt new file mode 100644 index 0000000000..fc54fd492e --- /dev/null +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt @@ -0,0 +1,19 @@ +-----BEGIN CERTIFICATE----- +MIIDFjCCAf4CCQCzrLIhrWa55zANBgkqhkiG9w0BAQsFADBCMQswCQYDVQQGEwJV +UzETMBEGA1UECAwKQ2FsaWZvcm5pYTEPMA0GA1UECgwGR29vZ2xlMQ0wCwYDVQQL +DARnUlBDMCAXDTE5MDYyNDIyMjIzM1oYDzIxMTkwNTMxMjIyMjMzWjBWMQswCQYD +VQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEPMA0GA1UECgwGR29vZ2xlMQ0w +CwYDVQQLDARnUlBDMRIwEAYDVQQDDAlsb2NhbGhvc3QwggEiMA0GCSqGSIb3DQEB +AQUAA4IBDwAwggEKAoIBAQCtCW0TjugnIUu8BEVIYvdMP+/2GENQDjZhZ8eKR5C6 +toDGbgjsDtt/GxISAg4cg70fIvy0XolnGPZodvfHDM4lJ7yHBOdZD8TXQoE6okR7 +HZuLUJ20M0pXgWqtRewKRUjuYsSDXBnzLiZw1dcv9nGpo+Bqa8NonpiGRRpEkshF +D6T9KU9Ts/x+wMQBIra2Gj0UMh79jPhUuxcYAQA0JQGivnOtdwuPiumpnUT8j8h6 +tWg5l01EsCZWJecCF85KnGpJEVYPyPqBqGsy0nGS9plGotOWF87+jyUQt+KD63xA +aBmTro86mKDDKEK4JvzjVeMGz2UbVcLPiiZnErTFaiXJAgMBAAEwDQYJKoZIhvcN +AQELBQADggEBAKsDgOPCWp5WCy17vJbRlgfgk05sVNIHZtzrmdswjBmvSg8MUpep +XqcPNUpsljAXsf9UM5IFEMRdilUsFGWvHjBEtNAW8WUK9UV18WRuU//0w1Mp5HAN +xUEKb4BoyZr65vlCnTR+AR5c9FfPvLibhr5qHs2RA8Y3GyLOcGqBWed87jhdQLCc +P1bxB+96le5JeXq0tw215lxonI2/3ZYVK4/ok9gwXrQoWm8YieJqitk/ZQ4S17/4 +pynHtDfdxLn23EXeGx+UTxJGfpRmhEZdJ+MN7QGYoomzx5qS5XoYKxRNrDlirJpr +OqXIn8E1it+6d5gOZfuHawcNGhRLplE/pfA= +-----END CERTIFICATE----- diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key new file mode 100644 index 0000000000..72e2463282 --- /dev/null +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key @@ -0,0 +1,27 @@ +-----BEGIN RSA PRIVATE KEY----- +MIIEogIBAAKCAQEArQltE47oJyFLvARFSGL3TD/v9hhDUA42YWfHikeQuraAxm4I +7A7bfxsSEgIOHIO9HyL8tF6JZxj2aHb3xwzOJSe8hwTnWQ/E10KBOqJEex2bi1Cd +tDNKV4FqrUXsCkVI7mLEg1wZ8y4mcNXXL/ZxqaPgamvDaJ6YhkUaRJLIRQ+k/SlP +U7P8fsDEASK2tho9FDIe/Yz4VLsXGAEANCUBor5zrXcLj4rpqZ1E/I/IerVoOZdN +RLAmViXnAhfOSpxqSRFWD8j6gahrMtJxkvaZRqLTlhfO/o8lELfig+t8QGgZk66P +OpigwyhCuCb841XjBs9lG1XCz4omZxK0xWolyQIDAQABAoIBADeq/Kh6JT3RfGf0 +h8WN8TlaqHxnueAbcmtL0+oss+cdp7gu1jf7X6o4r0uT1a5ew40s2Fe+wj2kzkE1 +ZOlouTlC22gkr7j7Vbxa7PBMG/Pvxoa/XL0IczZLsGImSJXVTG1E4SvRiZeulTdf +1GbdxhtpWV1jZe5Wd4Na3+SHxF5S7m3PrHiZlYdz1ND+8XZs1NlL9+ej72qSFul9 +t/QjMWJ9pky/Wad5abnRLRyOsg+BsgnXbkUy2rD89ZxFMLda9pzXo3TPyAlBHonr +mkEsE4eRMWMpjBM79JbeyDdHn/cs/LjAZrzeDf7ugXr2CHQpKaM5O0PsNHezJII9 +L5kCfzECgYEA4M/rz1UP1/BJoSqigUlSs0tPAg8a5UlkVsh6Osuq72IPNo8qg/Fw +oV/IiIS+q+obRcFj1Od3PGdTpCJwW5dzd2fXBQGmGdj0HucnCrs13RtBh91JiF5i +y/YYI9KfgOG2ZT9gG68T0gTs6jRrS3Qd83npqjrkJqMOd7s00MK9tUcCgYEAxQq7 +T541oCYHSBRIIb0IrR25krZy9caxzCqPDwOcuuhaCqCiaq+ATvOWlSfgecm4eH0K +PCH0xlWxG0auPEwm4pA8+/WR/XJwscPZMuoht1EoKy1his4eKx/s7hHNeO6KOF0V +Y/zqIiuZnEwUoKbn7EqqNFSTT65PJKyGsICJFG8CgYAfaw9yl1myfQNdQb8aQGwN +YJ33FLNWje427qeeZe5KrDKiFloDvI9YDjHRWnPnRL1w/zj7fSm9yFb5HlMDieP6 +MQnsyjEzdY2QcA+VwVoiv3dmDHgFVeOKy6bOAtaFxYWfGr9MvygO9t9BT/gawGyb +JVORlc9i0vDnrMMR1dV7awKBgBpTWLtGc/u1mPt0Wj7HtsUKV6TWY32a0l5owTxM +S0BdksogtBJ06DukJ9Y9wawD23WdnyRxlPZ6tHLkeprrwbY7dypioOKvy4a0l+xJ +g7+uRCOgqIuXBkjUtx8HmeAyXp0xMo5tWArAsIFFWOwt4IadYygitJvMuh44PraO +NcJZAoGADEiV0dheXUCVr8DrtSom8DQMj92/G/FIYjXL8OUhh0+F+YlYP0+F8PEU +yYIWEqL/S5tVKYshimUXQa537JcRKsTVJBG/ZKD2kuqgOc72zQy3oplimXeJDCXY +h2eAQ0u8GN6tN9C4t8Kp4a3y6FGsxgu+UTxdnL3YQ+yHAVhtCzo= +-----END RSA PRIVATE KEY----- diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go new file mode 100644 index 0000000000..968cd75f42 --- /dev/null +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go @@ -0,0 +1,148 @@ +// Unless explicitly stated otherwise all files in this repository are licensed +// under the Apache License Version 2.0. +// This product includes software developed at Datadog (https://www.datadoghq.com/). +// Copyright 2016 Datadog, Inc. + +package main + +import ( + "crypto/tls" + "gopkg.in/DataDog/dd-trace-go.v1/internal" + "net" + "net/http" + "os" + "strconv" + + "gopkg.in/DataDog/dd-trace-go.v1/contrib/envoyproxy/go-control-plane" + "gopkg.in/DataDog/dd-trace-go.v1/internal/log" + "gopkg.in/DataDog/dd-trace-go.v1/internal/version" + + extproc "github.com/envoyproxy/go-control-plane/envoy/service/ext_proc/v3" + "github.com/gorilla/mux" + "google.golang.org/grpc" + "google.golang.org/grpc/credentials" + "google.golang.org/grpc/reflection" + "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer" +) + +// AppsecCalloutExtensionService defines the struct that follows the ExternalProcessorServer interface. +type AppsecCalloutExtensionService struct { + extproc.ExternalProcessorServer +} + +type serviceExtensionConfig struct { + extensionPort string + extensionHost string + healthcheckPort string +} + +func loadConfig() serviceExtensionConfig { + extensionPortInt := internal.IntEnv("DD_SERVICE_EXTENSION_PORT", 443) + if extensionPortInt < 1 || extensionPortInt > 65535 { + log.Error("service_extension: invalid port number: %d\n", extensionPortInt) + os.Exit(1) + } + + healthcheckPortInt := internal.IntEnv("DD_SERVICE_EXTENSION_HEALTHCHECK_PORT", 80) + if healthcheckPortInt < 1 || healthcheckPortInt > 65535 { + log.Error("service_extension: invalid port number: %d\n", healthcheckPortInt) + os.Exit(1) + } + + extensionHost := internal.IpEnv("DD_SERVICE_EXTENSION_HOST", "0.0.0.0") + extensionPortStr := strconv.FormatInt(int64(extensionPortInt), 10) + healthcheckPortStr := strconv.FormatInt(int64(extensionPortInt), 10) + + // check if the ports are free + l, err := net.Listen("tcp", extensionHost+":"+extensionPortStr) + if err != nil { + log.Error("service_extension: failed to listen on extension %s:%s: %v\n", extensionHost, extensionPortStr, err) + os.Exit(1) + } + err = l.Close() + if err != nil { + log.Error("service_extension: failed to close listener on %s:%s: %v\n", extensionHost, extensionPortStr, err) + os.Exit(1) + } + + l, err = net.Listen("tcp", extensionHost+":"+healthcheckPortStr) + if err != nil { + log.Error("service_extension: failed to listen on health check %s:%s: %v\n", extensionHost, healthcheckPortStr, err) + os.Exit(1) + } + err = l.Close() + if err != nil { + log.Error("service_extension: failed to close listener on %s:%s: %v\n", extensionHost, healthcheckPortStr, err) + os.Exit(1) + } + + return serviceExtensionConfig{ + extensionPort: extensionPortStr, + extensionHost: extensionHost, + healthcheckPort: healthcheckPortStr, + } +} + +func main() { + var extensionService AppsecCalloutExtensionService + + // Set the DD_VERSION to the current tracer version if not set + if os.Getenv("DD_VERSION") == "" { + if err := os.Setenv("DD_VERSION", version.Tag); err != nil { + log.Error("service_extension: failed to set DD_VERSION environment variable: %v\n", err) + } + } + + config := loadConfig() + + tracer.Start(tracer.WithAppSecEnabled(true)) + // TODO: Enable ASM standalone mode when it is developed (should be done for Q4 2024) + + go StartGPRCSsl(&extensionService, config) + log.Info("service_extension: callout gRPC server started on %s:%s\n", config.extensionHost, config.extensionPort) + + go startHealthCheck(config) + log.Info("service_extension: health check server started on %s:%s\n", config.extensionHost, config.healthcheckPort) + + select {} +} + +func startHealthCheck(config serviceExtensionConfig) { + muxServer := mux.NewRouter() + muxServer.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { + w.Header().Set("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + w.Write([]byte(`{"status": "ok", "library": {"language": "golang", "version": "` + version.Tag + `"}}`)) + }) + + server := &http.Server{ + Addr: config.extensionHost + ":" + config.healthcheckPort, + Handler: muxServer, + } + + if err := server.ListenAndServe(); err != nil { + log.Error("service_extension: error starting health check http server: %v\n", err) + } +} + +func StartGPRCSsl(service extproc.ExternalProcessorServer, config serviceExtensionConfig) { + cert, err := tls.LoadX509KeyPair("localhost.crt", "localhost.key") + if err != nil { + log.Error("service_extension: failed to load key pair: %v\n", err) + } + + lis, err := net.Listen("tcp", config.extensionHost+":"+config.extensionPort) + if err != nil { + log.Error("service_extension: gRPC server failed to listen: %v\n", err) + } + + si := go_control_plane.StreamServerInterceptor() + creds := credentials.NewServerTLSFromCert(&cert) + grpcServer := grpc.NewServer(grpc.StreamInterceptor(si), grpc.Creds(creds)) + + extproc.RegisterExternalProcessorServer(grpcServer, service) + reflection.Register(grpcServer) + if err := grpcServer.Serve(lis); err != nil { + log.Error("service_extension: error starting gRPC server: %v\n", err) + } +} diff --git a/contrib/internal/telemetrytest/telemetry_test.go b/contrib/internal/telemetrytest/telemetry_test.go index a203228fc2..7e94ca420d 100644 --- a/contrib/internal/telemetrytest/telemetry_test.go +++ b/contrib/internal/telemetrytest/telemetry_test.go @@ -83,7 +83,7 @@ func TestTelemetryEnabled(t *testing.T) { packages = append(packages, out) } for _, pkg := range packages { - if strings.Contains(pkg.ImportPath, "/test") || strings.Contains(pkg.ImportPath, "/internal") { + if strings.Contains(pkg.ImportPath, "/test") || strings.Contains(pkg.ImportPath, "/internal") || strings.Contains(pkg.ImportPath, "/cmd") { continue } if !pkg.hasTelemetryImport(t) { diff --git a/ddtrace/tracer/option.go b/ddtrace/tracer/option.go index c1ad01edf9..6ea99d89eb 100644 --- a/ddtrace/tracer/option.go +++ b/ddtrace/tracer/option.go @@ -587,23 +587,6 @@ func newConfig(opts ...StartOption) *config { // This allows persisting the initial value of globalTags for future resets and updates. globalTagsOrigin := c.globalTags.cfgOrigin c.initGlobalTags(c.globalTags.get(), globalTagsOrigin) - - // TODO: change the name once APM Platform RFC is approved - if internal.BoolEnv("DD_EXPERIMENTAL_APPSEC_STANDALONE_ENABLED", false) { - // Enable tracing as transport layer mode - // This means to stop sending trace metrics, send one trace per minute and those force-kept by other products - // using the tracer as transport layer for their data. And finally adding the _dd.apm.enabled=0 tag to all traces - // to let the backend know that it needs to keep APM UI disabled. - c.globalSampleRate = 1.0 - c.traceRateLimitPerSecond = 1.0 / 60 - c.tracingAsTransport = true - WithGlobalTag("_dd.apm.enabled", 0)(c) - // Disable runtime metrics. In `tracingAsTransport` mode, we'll still - // tell the agent we computed them, so it doesn't do it either. - c.runtimeMetrics = false - c.runtimeMetricsV2 = false - } - return c } diff --git a/ddtrace/tracer/option_test.go b/ddtrace/tracer/option_test.go index 36c3475801..16588ce95a 100644 --- a/ddtrace/tracer/option_test.go +++ b/ddtrace/tracer/option_test.go @@ -343,7 +343,7 @@ func TestIntegrationEnabled(t *testing.T) { packages = append(packages, out) } for _, pkg := range packages { - if strings.Contains(pkg.ImportPath, "/test") || strings.Contains(pkg.ImportPath, "/internal") { + if strings.Contains(pkg.ImportPath, "/test") || strings.Contains(pkg.ImportPath, "/internal") || strings.Contains(pkg.ImportPath, "/cmd") { continue } p := strings.Replace(pkg.Dir, pkg.Root, "../..", 1) diff --git a/go.mod b/go.mod index bbe71fe323..6f981cf7ac 100644 --- a/go.mod +++ b/go.mod @@ -3,7 +3,7 @@ module gopkg.in/DataDog/dd-trace-go.v1 go 1.22.0 require ( - cloud.google.com/go/pubsub v1.36.1 + cloud.google.com/go/pubsub v1.40.0 github.com/99designs/gqlgen v0.17.36 github.com/DataDog/appsec-internal-go v1.9.0 github.com/DataDog/datadog-agent/pkg/obfuscate v0.58.0 @@ -100,11 +100,11 @@ require ( go.opentelemetry.io/otel/trace v1.27.0 go.uber.org/goleak v1.3.0 golang.org/x/mod v0.20.0 - golang.org/x/oauth2 v0.18.0 - golang.org/x/sys v0.28.0 + golang.org/x/oauth2 v0.22.0 + golang.org/x/sys v0.24.0 golang.org/x/time v0.6.0 golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028 - google.golang.org/api v0.169.0 + google.golang.org/api v0.192.0 google.golang.org/grpc v1.64.1 google.golang.org/protobuf v1.34.2 gopkg.in/jinzhu/gorm.v1 v1.9.2 @@ -120,10 +120,10 @@ require ( ) require ( - cloud.google.com/go v0.112.1 // indirect - cloud.google.com/go/compute v1.25.1 // indirect - cloud.google.com/go/compute/metadata v0.2.3 // indirect - cloud.google.com/go/iam v1.1.6 // indirect + cloud.google.com/go v0.115.0 // indirect + cloud.google.com/go/compute v1.27.4 // indirect + cloud.google.com/go/compute/metadata v0.5.0 // indirect + cloud.google.com/go/iam v1.1.12 // indirect github.com/DataDog/datadog-agent/pkg/util/log v0.58.0 // indirect github.com/DataDog/datadog-agent/pkg/util/scrubber v0.58.0 // indirect github.com/DataDog/go-sqllexer v0.0.14 // indirect @@ -156,7 +156,7 @@ require ( github.com/chenzhuoyu/base64x v0.0.0-20230717121745-296ad89f973d // indirect github.com/chenzhuoyu/iasm v0.9.0 // indirect github.com/cihub/seelog v0.0.0-20170130134532-f561c5e57575 // indirect - github.com/cncf/xds/go v0.0.0-20240318125728-8a4994d93e50 // indirect + github.com/cncf/xds/go v0.0.0-20240423153145-555b57ec207b // indirect github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f // indirect github.com/dustin/go-humanize v1.0.1 // indirect @@ -171,7 +171,7 @@ require ( github.com/gabriel-vasile/mimetype v1.4.2 // indirect github.com/gin-contrib/sse v0.1.0 // indirect github.com/go-jose/go-jose/v3 v3.0.3 // indirect - github.com/go-logr/logr v1.4.1 // indirect + github.com/go-logr/logr v1.4.2 // indirect github.com/go-logr/stdr v1.2.2 // indirect github.com/go-ole/go-ole v1.2.6 // indirect github.com/go-openapi/jsonpointer v0.19.5 // indirect @@ -192,9 +192,9 @@ require ( github.com/google/gnostic v0.5.7-v3refs // indirect github.com/google/go-cmp v0.6.0 // indirect github.com/google/gofuzz v1.2.0 // indirect - github.com/google/s2a-go v0.1.7 // indirect + github.com/google/s2a-go v0.1.8 // indirect github.com/googleapis/enterprise-certificate-proxy v0.3.2 // indirect - github.com/googleapis/gax-go/v2 v2.12.2 // indirect + github.com/googleapis/gax-go/v2 v2.13.0 // indirect github.com/gorilla/websocket v1.5.0 // indirect github.com/hailocab/go-hostpool v0.0.0-20160125115350-e80d13ce29ed // indirect github.com/hashicorp/errwrap v1.1.0 // indirect @@ -279,7 +279,7 @@ require ( github.com/xdg-go/stringprep v1.0.4 // indirect github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d // indirect github.com/yusufpapurcu/wmi v1.2.4 // indirect - go.einride.tech/aip v0.66.0 // indirect + go.einride.tech/aip v0.67.1 // indirect go.opencensus.io v0.24.0 // indirect go.opentelemetry.io/collector/component v0.104.0 // indirect go.opentelemetry.io/collector/config/configtelemetry v0.104.0 // indirect @@ -300,9 +300,9 @@ require ( golang.org/x/text v0.21.0 // indirect golang.org/x/tools v0.24.0 // indirect google.golang.org/appengine v1.6.8 // indirect - google.golang.org/genproto v0.0.0-20240213162025-012b6fc9bca9 // indirect - google.golang.org/genproto/googleapis/api v0.0.0-20240318140521-94a12d6c2237 // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20240520151616-dc85e6b867a5 // indirect + google.golang.org/genproto v0.0.0-20240730163845-b1a4ccb954bf // indirect + google.golang.org/genproto/googleapis/api v0.0.0-20240725223205-93522f1f2a9f // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20240730163845-b1a4ccb954bf // indirect gopkg.in/inf.v0 v0.9.1 // indirect gopkg.in/ini.v1 v1.67.0 // indirect gopkg.in/yaml.v2 v2.4.0 // indirect diff --git a/go.sum b/go.sum index aed16d7b16..49a41890dc 100644 --- a/go.sum +++ b/go.sum @@ -40,6 +40,7 @@ cloud.google.com/go v0.107.0/go.mod h1:wpc2eNrD7hXUTy8EKS10jkxpZBjASrORK7goS+3YX cloud.google.com/go v0.110.0/go.mod h1:SJnCLqQ0FCFGSZMUNUf84MV3Aia54kn7pi8st7tMzaY= cloud.google.com/go v0.112.1 h1:uJSeirPke5UNZHIb4SxfZklVSiWWVqW4oXlETwZziwM= cloud.google.com/go v0.112.1/go.mod h1:+Vbu+Y1UU+I1rjmzeMOb/8RfkKJK2Gyxi1X6jJCZLo4= +cloud.google.com/go v0.115.0/go.mod h1:8jIM5vVgoAEoiVxQ/O4BFTfHqulPZgs/ufEzMcFMdWU= cloud.google.com/go/accessapproval v1.4.0/go.mod h1:zybIuC3KpDOvotz59lFe5qxRZx6C75OtwbisN56xYB4= cloud.google.com/go/accessapproval v1.5.0/go.mod h1:HFy3tuiGvMdcd/u+Cu5b9NkO1pEICJ46IR82PoUdplw= cloud.google.com/go/accessapproval v1.6.0/go.mod h1:R0EiYnwV5fsRFiKZkPHr6mwyk2wxUJ30nL4j2pcFY2E= @@ -172,11 +173,14 @@ cloud.google.com/go/compute v1.18.0/go.mod h1:1X7yHxec2Ga+Ss6jPyjxRxpu2uu7PLgsOV cloud.google.com/go/compute v1.19.0/go.mod h1:rikpw2y+UMidAe9tISo04EHNOIf42RLYF/q8Bs93scU= cloud.google.com/go/compute v1.25.1 h1:ZRpHJedLtTpKgr3RV1Fx23NuaAEN1Zfx9hw1u4aJdjU= cloud.google.com/go/compute v1.25.1/go.mod h1:oopOIR53ly6viBYxaDhBfJwzUAxf1zE//uf3IB011ls= +cloud.google.com/go/compute v1.27.4/go.mod h1:7JZS+h21ERAGHOy5qb7+EPyXlQwzshzrx1x6L9JhTqU= cloud.google.com/go/compute/metadata v0.1.0/go.mod h1:Z1VN+bulIf6bt4P/C37K4DyZYZEXYonfTBHHFPO/4UU= cloud.google.com/go/compute/metadata v0.2.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= cloud.google.com/go/compute/metadata v0.2.1/go.mod h1:jgHgmJd2RKBGzXqF5LR2EZMGxBkeanZ9wwa75XHJgOM= cloud.google.com/go/compute/metadata v0.2.3 h1:mg4jlk7mCAj6xXp9UJ4fjI9VUI5rubuGBW5aJ7UnBMY= cloud.google.com/go/compute/metadata v0.2.3/go.mod h1:VAV5nSsACxMJvgaAuX6Pk2AawlZn8kiOGuCv6gTkwuA= +cloud.google.com/go/compute/metadata v0.3.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= +cloud.google.com/go/compute/metadata v0.5.0/go.mod h1:aHnloV2TPI38yx4s9+wAZhHykWvVCfu7hQbF+9CWoiY= cloud.google.com/go/contactcenterinsights v1.3.0/go.mod h1:Eu2oemoePuEFc/xKFPjbTuPSj0fYJcPls9TFlPNnHHY= cloud.google.com/go/contactcenterinsights v1.4.0/go.mod h1:L2YzkGbPsv+vMQMCADxJoT9YiTTnSEd6fEvCeHTYVck= cloud.google.com/go/contactcenterinsights v1.6.0/go.mod h1:IIDlT6CLcDoyv79kDv8iWxMSTZhLxSCofVV5W6YFM/w= @@ -310,6 +314,7 @@ cloud.google.com/go/iam v0.12.0/go.mod h1:knyHGviacl11zrtZUoDuYpDgLjvr28sLQaG0YB cloud.google.com/go/iam v0.13.0/go.mod h1:ljOg+rcNfzZ5d6f1nAUJ8ZIxOaZUVoS14bKCtaLZ/D0= cloud.google.com/go/iam v1.1.6 h1:bEa06k05IO4f4uJonbB5iAgKTPpABy1ayxaIZV/GHVc= cloud.google.com/go/iam v1.1.6/go.mod h1:O0zxdPeGBoFdWW3HWmBxJsk0pfvNM/p/qa82rWOGTwI= +cloud.google.com/go/iam v1.1.12/go.mod h1:9LDX8J7dN5YRyzVHxwQzrQs9opFFqn0Mxs9nAeB+Hhg= cloud.google.com/go/iap v1.4.0/go.mod h1:RGFwRJdihTINIe4wZ2iCP0zF/qu18ZwyKxrhMhygBEc= cloud.google.com/go/iap v1.5.0/go.mod h1:UH/CGgKd4KyohZL5Pt0jSKE4m3FR51qg6FKQ/z/Ix9A= cloud.google.com/go/iap v1.6.0/go.mod h1:NSuvI9C/j7UdjGjIde7t7HBz+QTwBcapPE07+sSRcLk= @@ -424,6 +429,7 @@ cloud.google.com/go/pubsub v1.28.0/go.mod h1:vuXFpwaVoIPQMGXqRyUQigu/AX1S3IWugR9 cloud.google.com/go/pubsub v1.30.0/go.mod h1:qWi1OPS0B+b5L+Sg6Gmc9zD1Y+HaM0MdUr7LsupY1P4= cloud.google.com/go/pubsub v1.36.1 h1:dfEPuGCHGbWUhaMCTHUFjfroILEkx55iUmKBZTP5f+Y= cloud.google.com/go/pubsub v1.36.1/go.mod h1:iYjCa9EzWOoBiTdd4ps7QoMtMln5NwaZQpK1hbRfBDE= +cloud.google.com/go/pubsub v1.40.0/go.mod h1:BVJI4sI2FyXp36KFKvFwcfDRDfR8MiLT8mMhmIhdAeA= cloud.google.com/go/pubsublite v1.5.0/go.mod h1:xapqNQ1CuLfGi23Yda/9l4bBCKz/wC3KIJ5gKcxveZg= cloud.google.com/go/pubsublite v1.6.0/go.mod h1:1eFCS0U11xlOuMFV/0iBqw3zP12kddMeCbj/F3FSj9k= cloud.google.com/go/pubsublite v1.7.0/go.mod h1:8hVMwRXfDfvGm3fahVbtDbiLePT3gpoiJYJY+vxWxVM= @@ -892,6 +898,7 @@ github.com/cncf/xds/go v0.0.0-20220314180256-7f1daf1720fc/go.mod h1:eXthEFrGJvWH github.com/cncf/xds/go v0.0.0-20230105202645-06c439db220b/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20240318125728-8a4994d93e50 h1:DBmgJDC9dTfkVyGgipamEh2BpGYxScCH1TOF1LL1cXc= github.com/cncf/xds/go v0.0.0-20240318125728-8a4994d93e50/go.mod h1:5e1+Vvlzido69INQaVO6d87Qn543Xr6nooe9Kz7oBFM= +github.com/cncf/xds/go v0.0.0-20240423153145-555b57ec207b/go.mod h1:W+zGtBO5Y1IgJhy4+A9GOqVhqLpfZi+vwmdNXUehLA8= github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= github.com/cockroachdb/datadriven v0.0.0-20200714090401-bf6692d28da5/go.mod h1:h6jFvWxBdQXxjopDMZyH2UVceIRfR84bdzbkoKrsWNo= github.com/cockroachdb/errors v1.2.4/go.mod h1:rQD95gz6FARkaKkQXUksEje/d9a6wBJoCr5oaCLELYA= @@ -1201,6 +1208,7 @@ github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbV github.com/go-logr/logr v1.2.3/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= github.com/go-logr/logr v1.4.1 h1:pKouT5E8xu9zeFC39JXRDukb6JFQPXM5p5I91188VAQ= github.com/go-logr/logr v1.4.1/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= +github.com/go-logr/logr v1.4.2/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= github.com/go-logr/stdr v1.2.0/go.mod h1:YkVgnZu1ZjjL7xTxrfm/LLZBfkhTqSR1ydtm6jTKKwI= github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE= @@ -1385,6 +1393,7 @@ github.com/google/pprof v0.0.0-20230817174616-7a8ec2ada47b/go.mod h1:czg5+yv1E0Z github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= github.com/google/s2a-go v0.1.7 h1:60BLSyTrOV4/haCDW4zb1guZItoSq8foHCXrAnjBo/o= github.com/google/s2a-go v0.1.7/go.mod h1:50CgR4k1jNlWBu4UfS4AcfhVe1r6pdZPygJ3R8F0Qdw= +github.com/google/s2a-go v0.1.8/go.mod h1:6iNWHTpQ+nfNRN5E00MSdfDwVesa8hhS32PhPO8deJA= github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510/go.mod h1:pupxD2MaaD3pAXIBCelhxNneeOaAeabZDe5s4K6zSpQ= github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= @@ -1413,6 +1422,7 @@ github.com/googleapis/gax-go/v2 v2.7.0/go.mod h1:TEop28CZZQ2y+c0VxMUmu1lV+fQx57Q github.com/googleapis/gax-go/v2 v2.7.1/go.mod h1:4orTrqY6hXxxaUL4LHIPl6lGo8vAE38/qKbhSAKP6QI= github.com/googleapis/gax-go/v2 v2.12.2 h1:mhN09QQW1jEWeMF74zGR81R30z4VJzjZsfkUhuHF+DA= github.com/googleapis/gax-go/v2 v2.12.2/go.mod h1:61M8vcyyXR2kqKFxKrfA22jaA8JGF7Dc8App1U3H6jc= +github.com/googleapis/gax-go/v2 v2.13.0/go.mod h1:Z/fvTZXF8/uw7Xu5GuslPw+bplx6SS338j1Is2S+B7A= github.com/googleapis/gnostic v0.4.1/go.mod h1:LRhVm6pbyptWbWbuZ38d1eyptfvIytN3ir6b65WBswg= github.com/googleapis/gnostic v0.5.1/go.mod h1:6U4PtQXGIEt/Z3h5MAT7FNofLnw9vXk2cUuW7uA/OeU= github.com/googleapis/gnostic v0.5.5/go.mod h1:7+EbHbldMins07ALC74bsA81Ovc97DwqyJO1AENw9kA= @@ -2183,6 +2193,7 @@ github.com/zenazn/goji v1.0.1 h1:4lbD8Mx2h7IvloP7r2C0D6ltZP6Ufip8Hn0wmSK5LR8= github.com/zenazn/goji v1.0.1/go.mod h1:7S9M489iMyHBNxwZnk9/EHS098H4/F6TATF2mIxtB1Q= go.einride.tech/aip v0.66.0 h1:XfV+NQX6L7EOYK11yoHHFtndeaWh3KbD9/cN/6iWEt8= go.einride.tech/aip v0.66.0/go.mod h1:qAhMsfT7plxBX+Oy7Huol6YUvZ0ZzdUz26yZsQwfl1M= +go.einride.tech/aip v0.67.1/go.mod h1:ZGX4/zKw8dcgzdLsrvpOOGxfxI2QSk12SlP7d6c0/XI= go.etcd.io/bbolt v1.3.2/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= go.etcd.io/bbolt v1.3.3/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= go.etcd.io/bbolt v1.3.5/go.mod h1:G5EMThwa9y8QZGBClrRx5EY+Yw9kAhnjy3bSjsnlVTQ= @@ -2491,6 +2502,8 @@ golang.org/x/oauth2 v0.5.0/go.mod h1:9/XBHVqLaWO3/BRHs5jbpYCnOZVjj5V0ndyaAM7KB4I golang.org/x/oauth2 v0.6.0/go.mod h1:ycmewcwgD4Rpr3eZJLSB4Kyyljb3qDh40vJ8STE5HKw= golang.org/x/oauth2 v0.18.0 h1:09qnuIAgzdx1XplqJvW6CQqMCtGZykZWcXzPMPUusvI= golang.org/x/oauth2 v0.18.0/go.mod h1:Wf7knwG0MPoWIMMBgFlEaSUDaKskp0dCfrlJRJXbBi8= +golang.org/x/oauth2 v0.20.0/go.mod h1:XYTD2NtWslqkgxebSiOHnXEap4TF09sJSc7H1sXbhtI= +golang.org/x/oauth2 v0.22.0/go.mod h1:XYTD2NtWslqkgxebSiOHnXEap4TF09sJSc7H1sXbhtI= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -2865,6 +2878,7 @@ google.golang.org/api v0.111.0/go.mod h1:qtFHvU9mhgTJegR31csQ+rwxyUTHOKFqCKWp1J0 google.golang.org/api v0.114.0/go.mod h1:ifYI2ZsFK6/uGddGfAD5BMxlnkBqCmqHSDUVi45N5Yg= google.golang.org/api v0.169.0 h1:QwWPy71FgMWqJN/l6jVlFHUa29a7dcUy02I8o799nPY= google.golang.org/api v0.169.0/go.mod h1:gpNOiMA2tZ4mf5R9Iwf4rK/Dcz0fbdIgWYWVoxmsyLg= +google.golang.org/api v0.192.0/go.mod h1:9VcphjvAxPKLmSxVSzPlSRXy/5ARMEw5bf58WoVXafQ= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= @@ -3013,10 +3027,15 @@ google.golang.org/genproto v0.0.0-20230320184635-7606e756e683/go.mod h1:NWraEVix google.golang.org/genproto v0.0.0-20230331144136-dcfb400f0633/go.mod h1:UUQDJDOlWu4KYeJZffbWgBkS1YFobzKbLVfK69pe0Ak= google.golang.org/genproto v0.0.0-20240213162025-012b6fc9bca9 h1:9+tzLLstTlPTRyJTh+ah5wIMsBW5c4tQwGTN3thOW9Y= google.golang.org/genproto v0.0.0-20240213162025-012b6fc9bca9/go.mod h1:mqHbVIp48Muh7Ywss/AD6I5kNVKZMmAa/QEW58Gxp2s= +google.golang.org/genproto v0.0.0-20240730163845-b1a4ccb954bf/go.mod h1:mCr1K1c8kX+1iSBREvU3Juo11CB+QOEWxbRS01wWl5M= google.golang.org/genproto/googleapis/api v0.0.0-20240318140521-94a12d6c2237 h1:RFiFrvy37/mpSpdySBDrUdipW/dHwsRwh3J3+A9VgT4= google.golang.org/genproto/googleapis/api v0.0.0-20240318140521-94a12d6c2237/go.mod h1:Z5Iiy3jtmioajWHDGFk7CeugTyHtPvMHA4UTmUkyalE= +google.golang.org/genproto/googleapis/api v0.0.0-20240528184218-531527333157/go.mod h1:99sLkeliLXfdj2J75X3Ho+rrVCaJze0uwN7zDDkjPVU= +google.golang.org/genproto/googleapis/api v0.0.0-20240725223205-93522f1f2a9f/go.mod h1:AHT0dDg3SoMOgZGnZk29b5xTbPHMoEC8qthmBLJCpys= google.golang.org/genproto/googleapis/rpc v0.0.0-20240520151616-dc85e6b867a5 h1:Q2RxlXqh1cgzzUgV261vBO2jI5R/3DD1J2pM0nI4NhU= google.golang.org/genproto/googleapis/rpc v0.0.0-20240520151616-dc85e6b867a5/go.mod h1:EfXuqaE1J41VCDicxHzUDm+8rk+7ZdXzHV0IhO/I6s0= +google.golang.org/genproto/googleapis/rpc v0.0.0-20240528184218-531527333157/go.mod h1:EfXuqaE1J41VCDicxHzUDm+8rk+7ZdXzHV0IhO/I6s0= +google.golang.org/genproto/googleapis/rpc v0.0.0-20240730163845-b1a4ccb954bf/go.mod h1:Ue6ibwXGpU+dqIcODieyLOcgj7z8+IcskoNIgZxtrFY= google.golang.org/grpc v0.0.0-20160317175043-d3ddb4469d5a/go.mod h1:yo6s7OP7yaDglbqo1J04qKzAhqBH6lvTonzMVmEdcZw= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= @@ -3061,8 +3080,10 @@ google.golang.org/grpc v1.50.1/go.mod h1:ZgQEeidpAuNRZ8iRrlBKXZQP1ghovWIVhdJRyCD google.golang.org/grpc v1.51.0/go.mod h1:wgNDFcnuBGmxLKI/qn4T+m5BtEBYXJPvibbUPsAIPww= google.golang.org/grpc v1.53.0/go.mod h1:OnIrk0ipVdj4N5d9IUoFUx72/VlD7+jUsHwZgwSMQpw= google.golang.org/grpc v1.54.0/go.mod h1:PUSEXI6iWghWaB6lXM4knEgpJNu2qUcKfDtNci3EC2g= -google.golang.org/grpc v1.64.1 h1:LKtvyfbX3UGVPFcGqJ9ItpVWW6oN/2XqTxfAnwRRXiA= +google.golang.org/grpc v1.64.0 h1:KH3VH9y/MgNQg1dE7b3XfVK0GsPSIzJwdF617gUSbvY= +google.golang.org/grpc v1.64.0/go.mod h1:oxjF8E3FBnjp+/gVFYdWacaLDx9na1aqy9oovLpxQYg= google.golang.org/grpc v1.64.1/go.mod h1:hiQF4LFZelK2WKaP6W0L92zGHtiQdZxk8CrSdvyjeP0= +google.golang.org/grpc v1.65.0/go.mod h1:WgYC2ypjlB0EiQi6wdKixMqukr6lBc0Vo+oOgjrM5ZQ= google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.1.0/go.mod h1:6Kw0yEErY5E/yWrBtf03jp27GLLJujG4z/JK95pnjjw= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= diff --git a/internal/env.go b/internal/env.go index 62704b7792..e6a6bb0b19 100644 --- a/internal/env.go +++ b/internal/env.go @@ -6,6 +6,7 @@ package internal import ( + "net" "os" "strconv" "strings" @@ -59,6 +60,22 @@ func DurationEnv(key string, def time.Duration) time.Duration { return v } +// IpEnv returns the valid IP string value of an environment variable, or +// def otherwise. +func IpEnv(key string, def string) string { + vv, ok := os.LookupEnv(key) + if !ok { + return def + } + + if net.ParseIP(vv) == nil { + log.Warn("Non-IP value for env var %s, defaulting to %s", key, def) + return def + } + + return vv +} + // ForEachStringTag runs fn on every key val pair encountered in str. // str may contain multiple key val pairs separated by either space // or comma (but not a mixture of both), and each key val pair is separated by a delimiter. From 4ab33086614b14963662bf72a2201070bf2893f2 Mon Sep 17 00:00:00 2001 From: Flavien Darche Date: Wed, 11 Dec 2024 11:00:24 +0100 Subject: [PATCH 2/5] Generate self signed certificates instead of importing them Add Readme fix rebase update to register the service --- contrib/envoyproxy/envoy/fakehttp.go | 189 ------------------ .../cmd/serviceextensions/Dockerfile | 21 +- .../cmd/serviceextensions/README.md | 42 ++++ .../cmd/serviceextensions/localhost.crt | 19 -- .../cmd/serviceextensions/localhost.key | 27 --- .../cmd/serviceextensions/main.go | 18 +- go.mod | 32 +-- go.sum | 19 -- 8 files changed, 88 insertions(+), 279 deletions(-) delete mode 100644 contrib/envoyproxy/envoy/fakehttp.go create mode 100644 contrib/envoyproxy/go-control-plane/cmd/serviceextensions/README.md delete mode 100644 contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt delete mode 100644 contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key diff --git a/contrib/envoyproxy/envoy/fakehttp.go b/contrib/envoyproxy/envoy/fakehttp.go deleted file mode 100644 index 2d1a4652b1..0000000000 --- a/contrib/envoyproxy/envoy/fakehttp.go +++ /dev/null @@ -1,189 +0,0 @@ -// Unless explicitly stated otherwise all files in this repository are licensed -// under the Apache License Version 2.0. -// This product includes software developed at Datadog (https://www.datadoghq.com/). -// Copyright 2024 Datadog, Inc. - -package envoy - -import ( - "context" - "crypto/tls" - "fmt" - "net/http" - "net/url" - "strconv" - "strings" - "sync" - - corev3 "github.com/envoyproxy/go-control-plane/envoy/config/core/v3" - extproc "github.com/envoyproxy/go-control-plane/envoy/service/ext_proc/v3" - "google.golang.org/grpc/metadata" -) - -// checkPseudoRequestHeaders Verify the required HTTP2 headers are present -// Some mandatory headers need to be set. It can happen when it wasn't a real HTTP2 request sent by Envoy, -func checkPseudoRequestHeaders(headers map[string]string) error { - for _, header := range []string{":authority", ":scheme", ":path", ":method"} { - if _, ok := headers[header]; !ok { - return fmt.Errorf("missing required headers: %q", header) - } - } - - return nil -} - -// checkPseudoResponseHeaders Verify the required HTTP2 headers are present -// Some mandatory headers need to be set. It can happen when it wasn't a real HTTP2 request sent by Envoy, -func checkPseudoResponseHeaders(headers map[string]string) error { - if _, ok := headers[":status"]; !ok { - return fmt.Errorf("missing required ':status' headers") - } - - return nil -} - -func getRemoteAddr(md metadata.MD) string { - xfwd := md.Get("x-forwarded-for") - length := len(xfwd) - if length == 0 { - return "" - } - - // Get the first right value of x-forwarded-for headers - // The rightmost IP address is the one that will be used as the remote client IP - // https://datadoghq.atlassian.net/wiki/spaces/TS/pages/2766733526/Sensitive+IP+information#Where-does-the-value-of-the-http.client_ip-tag-come-from%3F - return xfwd[length-1] -} - -// partitionPeusdoHeaders Separate normal headers of the initial request made by the client and the pseudo headers of HTTP/2 -// - Format the headers to be used by the tracer as a map[string][]string -// - Set headers keys to be canonical -func partitionPeusdoHeaders(receivedHeaders []*corev3.HeaderValue) (map[string][]string, map[string]string) { - headers := make(map[string][]string, len(receivedHeaders)-4) - pseudoHeaders := make(map[string]string, 4) - for _, v := range receivedHeaders { - key := v.GetKey() - if key == "" { - continue - } - if key[0] == ':' { - pseudoHeaders[key] = string(v.GetRawValue()) - continue - } - - headers[http.CanonicalHeaderKey(key)] = []string{string(v.GetRawValue())} - } - return headers, pseudoHeaders -} - -func NewFakeResponseWriterFromExtProc(w http.ResponseWriter, res *extproc.ProcessingRequest_ResponseHeaders) error { - headers, pseudoHeaders := partitionPeusdoHeaders(res.ResponseHeaders.GetHeaders().GetHeaders()) - - if err := checkPseudoResponseHeaders(pseudoHeaders); err != nil { - return err - } - - status, err := strconv.Atoi(pseudoHeaders[":status"]) - if err != nil { - return fmt.Errorf("error parsing status code %q: %w", pseudoHeaders[":status"], err) - } - - for k, v := range headers { - w.Header().Set(k, strings.Join(v, ",")) - } - - w.WriteHeader(status) - return nil -} - -// NewRequestFromExtProc creates a new http.Request from an ext_proc RequestHeaders message -func NewRequestFromExtProc(ctx context.Context, req *extproc.ProcessingRequest_RequestHeaders) (*http.Request, error) { - headers, pseudoHeaders := partitionPeusdoHeaders(req.RequestHeaders.GetHeaders().GetHeaders()) - if err := checkPseudoRequestHeaders(pseudoHeaders); err != nil { - return nil, err - } - - parsedURL, err := url.Parse(fmt.Sprintf("%s://%s%s", pseudoHeaders[":scheme"], pseudoHeaders[":authority"], pseudoHeaders[":path"])) - if err != nil { - return nil, fmt.Errorf( - "error building envoy URI from scheme %q, from host %q and from path %q: %w", - pseudoHeaders[":scheme"], - pseudoHeaders[":host"], - pseudoHeaders[":path"], - err) - } - - var remoteAddr string - md, ok := metadata.FromIncomingContext(ctx) - if ok { - remoteAddr = getRemoteAddr(md) - } - - var tlsState *tls.ConnectionState - if pseudoHeaders[":scheme"] == "https" { - tlsState = &tls.ConnectionState{} - } - - headers["Host"] = append(headers["Host"], pseudoHeaders[":authority"]) - - return (&http.Request{ - Method: pseudoHeaders[":method"], - Host: pseudoHeaders[":authority"], - RequestURI: pseudoHeaders[":path"], - URL: parsedURL, - Header: headers, - RemoteAddr: remoteAddr, - TLS: tlsState, - }).WithContext(ctx), nil -} - -type FakeResponseWriter struct { - mu sync.Mutex - status int - body []byte - headers http.Header -} - -// Reset resets the FakeResponseWriter to its initial state -func (w *FakeResponseWriter) Reset() { - w.mu.Lock() - defer w.mu.Unlock() - w.status = 0 - w.body = nil - w.headers = make(http.Header) -} - -// Status is not in the [http.ResponseWriter] interface, but it is cast into it by the tracing code -func (w *FakeResponseWriter) Status() int { - w.mu.Lock() - defer w.mu.Unlock() - return w.status -} - -func (w *FakeResponseWriter) WriteHeader(status int) { - w.mu.Lock() - defer w.mu.Unlock() - w.status = status -} - -func (w *FakeResponseWriter) Header() http.Header { - w.mu.Lock() - defer w.mu.Unlock() - return w.headers -} - -func (w *FakeResponseWriter) Write(b []byte) (int, error) { - w.mu.Lock() - defer w.mu.Unlock() - w.body = append(w.body, b...) - return len(b), nil -} - -var _ http.ResponseWriter = &FakeResponseWriter{} - -// NewFakeResponseWriter creates a new FakeResponseWriter that can be used to store the response a [http.Handler] made -func NewFakeResponseWriter() *FakeResponseWriter { - return &FakeResponseWriter{ - headers: make(http.Header), - } -} diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile index 5e4080ce5e..871572d07c 100644 --- a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile @@ -1,9 +1,24 @@ # Build stage FROM golang:1.23-alpine AS builder ENV CGO_ENABLED=1 + WORKDIR /app COPY . . -RUN apk add --no-cache --update git build-base + +RUN apk add --no-cache --update git build-base openssl + +# Generate SSL self-signed localhost certificate +RUN openssl genrsa -out localhost.key 3072 +RUN openssl req -new \ + -key localhost.key \ + -subj "/C=US/ST=New York/O=Datadog/OU=gRPC/CN=localhost" \ + -out request.csr +RUN openssl x509 -req -days 3660 \ + -in request.csr \ + -signkey localhost.key \ + -out localhost.crt + +# Build the serviceextensions binary RUN go build -tags=appsec -o ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions/serviceextensions ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions # Runtime stage @@ -11,8 +26,8 @@ FROM alpine:3.20.3 RUN apk --no-cache add ca-certificates tzdata libc6-compat libgcc libstdc++ WORKDIR /app COPY --from=builder /app/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/serviceextensions /app/serviceextensions -COPY ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt /app/localhost.crt -COPY ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key /app/localhost.key +COPY --from=builder /app/localhost.crt /app/localhost.crt +COPY --from=builder /app/localhost.key /app/localhost.key EXPOSE 80 EXPOSE 443 diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/README.md b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/README.md new file mode 100644 index 0000000000..b2b5b8fab6 --- /dev/null +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/README.md @@ -0,0 +1,42 @@ +# ASM Service Extension + +[GCP Services Extensions](https://cloud.google.com/service-extensions/docs/overview) enable Google Cloud users to provide programmability and extensibility on Cloud Load Balancing data paths and at the edge. + +## Installation + +### From Release + +This package provides a docker image to be used with Google Cloud Service Extensions. +The images are published at each release of the tracer and can be found in [the repo registry](https://github.com/DataDog/dd-trace-go/pkgs/container/dd-trace-go%2Fservice-extensions-callout). + +### Build image + +The docker image can be build locally using docker. Start by cloning the `dd-trace-go` repo, `cd` inside it and run that command: +```sh +docker build --build-arg -f contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile -t datadog/dd-trace-go/service-extensions-callout:local . +``` + +## Configuration + +The ASM Service Extension expose some configuration. The configuration can be tweaked if the Service Extension is only used as an External Processor for Envoy that is not operated by GCP. + +>**GCP requires that the default configuration for the Service Extension should not change.** + +| Environment variable | Default value | Description | +|---|---|---| +| `DD_SERVICE_EXTENSION_HOST` | `0.0.0.0` | Host on where the gRPC and HTTP server should listen to. | +| `DD_SERVICE_EXTENSION_PORT` | `443` | Port used by the gRPC Server.
Envoy Google backend’s is only using secure connection to Service Extension. | +| `DD_SERVICE_EXTENSION_HEALTHCHECK_PORT` | `80` | Port used for the HTTP server for the health check. | + +> The Service Extension need to be connected to a deployed [Datadog agent](https://docs.datadoghq.com/agent). + +| Environment variable | Default value | Description | +|---|---|---| +| `DD_AGENT_HOST` | `N/A` | Host of a running Datadog Agent. | +| `DD_TRACE_AGENT_PORT` | `8126` | Port of a running Datadog Agent. | + +### SSL Configuration + +The Envoy of GCP is configured to communicate to the Service Extension with TLS. + +`localhost` self signed certificates are generated and bundled into the ASM Service Extension docker image and loaded at the start of the gRPC server. \ No newline at end of file diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt deleted file mode 100644 index fc54fd492e..0000000000 --- a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.crt +++ /dev/null @@ -1,19 +0,0 @@ ------BEGIN CERTIFICATE----- -MIIDFjCCAf4CCQCzrLIhrWa55zANBgkqhkiG9w0BAQsFADBCMQswCQYDVQQGEwJV -UzETMBEGA1UECAwKQ2FsaWZvcm5pYTEPMA0GA1UECgwGR29vZ2xlMQ0wCwYDVQQL -DARnUlBDMCAXDTE5MDYyNDIyMjIzM1oYDzIxMTkwNTMxMjIyMjMzWjBWMQswCQYD -VQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEPMA0GA1UECgwGR29vZ2xlMQ0w -CwYDVQQLDARnUlBDMRIwEAYDVQQDDAlsb2NhbGhvc3QwggEiMA0GCSqGSIb3DQEB -AQUAA4IBDwAwggEKAoIBAQCtCW0TjugnIUu8BEVIYvdMP+/2GENQDjZhZ8eKR5C6 -toDGbgjsDtt/GxISAg4cg70fIvy0XolnGPZodvfHDM4lJ7yHBOdZD8TXQoE6okR7 -HZuLUJ20M0pXgWqtRewKRUjuYsSDXBnzLiZw1dcv9nGpo+Bqa8NonpiGRRpEkshF -D6T9KU9Ts/x+wMQBIra2Gj0UMh79jPhUuxcYAQA0JQGivnOtdwuPiumpnUT8j8h6 -tWg5l01EsCZWJecCF85KnGpJEVYPyPqBqGsy0nGS9plGotOWF87+jyUQt+KD63xA -aBmTro86mKDDKEK4JvzjVeMGz2UbVcLPiiZnErTFaiXJAgMBAAEwDQYJKoZIhvcN -AQELBQADggEBAKsDgOPCWp5WCy17vJbRlgfgk05sVNIHZtzrmdswjBmvSg8MUpep -XqcPNUpsljAXsf9UM5IFEMRdilUsFGWvHjBEtNAW8WUK9UV18WRuU//0w1Mp5HAN -xUEKb4BoyZr65vlCnTR+AR5c9FfPvLibhr5qHs2RA8Y3GyLOcGqBWed87jhdQLCc -P1bxB+96le5JeXq0tw215lxonI2/3ZYVK4/ok9gwXrQoWm8YieJqitk/ZQ4S17/4 -pynHtDfdxLn23EXeGx+UTxJGfpRmhEZdJ+MN7QGYoomzx5qS5XoYKxRNrDlirJpr -OqXIn8E1it+6d5gOZfuHawcNGhRLplE/pfA= ------END CERTIFICATE----- diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key deleted file mode 100644 index 72e2463282..0000000000 --- a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/localhost.key +++ /dev/null @@ -1,27 +0,0 @@ ------BEGIN RSA PRIVATE KEY----- -MIIEogIBAAKCAQEArQltE47oJyFLvARFSGL3TD/v9hhDUA42YWfHikeQuraAxm4I -7A7bfxsSEgIOHIO9HyL8tF6JZxj2aHb3xwzOJSe8hwTnWQ/E10KBOqJEex2bi1Cd -tDNKV4FqrUXsCkVI7mLEg1wZ8y4mcNXXL/ZxqaPgamvDaJ6YhkUaRJLIRQ+k/SlP -U7P8fsDEASK2tho9FDIe/Yz4VLsXGAEANCUBor5zrXcLj4rpqZ1E/I/IerVoOZdN -RLAmViXnAhfOSpxqSRFWD8j6gahrMtJxkvaZRqLTlhfO/o8lELfig+t8QGgZk66P -OpigwyhCuCb841XjBs9lG1XCz4omZxK0xWolyQIDAQABAoIBADeq/Kh6JT3RfGf0 -h8WN8TlaqHxnueAbcmtL0+oss+cdp7gu1jf7X6o4r0uT1a5ew40s2Fe+wj2kzkE1 -ZOlouTlC22gkr7j7Vbxa7PBMG/Pvxoa/XL0IczZLsGImSJXVTG1E4SvRiZeulTdf -1GbdxhtpWV1jZe5Wd4Na3+SHxF5S7m3PrHiZlYdz1ND+8XZs1NlL9+ej72qSFul9 -t/QjMWJ9pky/Wad5abnRLRyOsg+BsgnXbkUy2rD89ZxFMLda9pzXo3TPyAlBHonr -mkEsE4eRMWMpjBM79JbeyDdHn/cs/LjAZrzeDf7ugXr2CHQpKaM5O0PsNHezJII9 -L5kCfzECgYEA4M/rz1UP1/BJoSqigUlSs0tPAg8a5UlkVsh6Osuq72IPNo8qg/Fw -oV/IiIS+q+obRcFj1Od3PGdTpCJwW5dzd2fXBQGmGdj0HucnCrs13RtBh91JiF5i -y/YYI9KfgOG2ZT9gG68T0gTs6jRrS3Qd83npqjrkJqMOd7s00MK9tUcCgYEAxQq7 -T541oCYHSBRIIb0IrR25krZy9caxzCqPDwOcuuhaCqCiaq+ATvOWlSfgecm4eH0K -PCH0xlWxG0auPEwm4pA8+/WR/XJwscPZMuoht1EoKy1his4eKx/s7hHNeO6KOF0V -Y/zqIiuZnEwUoKbn7EqqNFSTT65PJKyGsICJFG8CgYAfaw9yl1myfQNdQb8aQGwN -YJ33FLNWje427qeeZe5KrDKiFloDvI9YDjHRWnPnRL1w/zj7fSm9yFb5HlMDieP6 -MQnsyjEzdY2QcA+VwVoiv3dmDHgFVeOKy6bOAtaFxYWfGr9MvygO9t9BT/gawGyb -JVORlc9i0vDnrMMR1dV7awKBgBpTWLtGc/u1mPt0Wj7HtsUKV6TWY32a0l5owTxM -S0BdksogtBJ06DukJ9Y9wawD23WdnyRxlPZ6tHLkeprrwbY7dypioOKvy4a0l+xJ -g7+uRCOgqIuXBkjUtx8HmeAyXp0xMo5tWArAsIFFWOwt4IadYygitJvMuh44PraO -NcJZAoGADEiV0dheXUCVr8DrtSom8DQMj92/G/FIYjXL8OUhh0+F+YlYP0+F8PEU -yYIWEqL/S5tVKYshimUXQa537JcRKsTVJBG/ZKD2kuqgOc72zQy3oplimXeJDCXY -h2eAQ0u8GN6tN9C4t8Kp4a3y6FGsxgu+UTxdnL3YQ+yHAVhtCzo= ------END RSA PRIVATE KEY----- diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go index 968cd75f42..856bd54666 100644 --- a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go @@ -13,7 +13,7 @@ import ( "os" "strconv" - "gopkg.in/DataDog/dd-trace-go.v1/contrib/envoyproxy/go-control-plane" + gocontrolplane "gopkg.in/DataDog/dd-trace-go.v1/contrib/envoyproxy/go-control-plane" "gopkg.in/DataDog/dd-trace-go.v1/internal/log" "gopkg.in/DataDog/dd-trace-go.v1/internal/version" @@ -51,7 +51,7 @@ func loadConfig() serviceExtensionConfig { extensionHost := internal.IpEnv("DD_SERVICE_EXTENSION_HOST", "0.0.0.0") extensionPortStr := strconv.FormatInt(int64(extensionPortInt), 10) - healthcheckPortStr := strconv.FormatInt(int64(extensionPortInt), 10) + healthcheckPortStr := strconv.FormatInt(int64(healthcheckPortInt), 10) // check if the ports are free l, err := net.Listen("tcp", extensionHost+":"+extensionPortStr) @@ -129,20 +129,26 @@ func StartGPRCSsl(service extproc.ExternalProcessorServer, config serviceExtensi cert, err := tls.LoadX509KeyPair("localhost.crt", "localhost.key") if err != nil { log.Error("service_extension: failed to load key pair: %v\n", err) + os.Exit(1) + return } lis, err := net.Listen("tcp", config.extensionHost+":"+config.extensionPort) if err != nil { log.Error("service_extension: gRPC server failed to listen: %v\n", err) + os.Exit(1) + return } - si := go_control_plane.StreamServerInterceptor() - creds := credentials.NewServerTLSFromCert(&cert) - grpcServer := grpc.NewServer(grpc.StreamInterceptor(si), grpc.Creds(creds)) + grpcCredentials := credentials.NewServerTLSFromCert(&cert) + grpcServer := grpc.NewServer(grpc.Creds(grpcCredentials)) - extproc.RegisterExternalProcessorServer(grpcServer, service) + appsecEnvoyExternalProcessorServer := gocontrolplane.AppsecEnvoyExternalProcessorServer(service) + + extproc.RegisterExternalProcessorServer(grpcServer, appsecEnvoyExternalProcessorServer) reflection.Register(grpcServer) if err := grpcServer.Serve(lis); err != nil { log.Error("service_extension: error starting gRPC server: %v\n", err) + os.Exit(1) } } diff --git a/go.mod b/go.mod index 6f981cf7ac..ed327de9e8 100644 --- a/go.mod +++ b/go.mod @@ -3,7 +3,7 @@ module gopkg.in/DataDog/dd-trace-go.v1 go 1.22.0 require ( - cloud.google.com/go/pubsub v1.40.0 + cloud.google.com/go/pubsub v1.36.1 github.com/99designs/gqlgen v0.17.36 github.com/DataDog/appsec-internal-go v1.9.0 github.com/DataDog/datadog-agent/pkg/obfuscate v0.58.0 @@ -100,12 +100,12 @@ require ( go.opentelemetry.io/otel/trace v1.27.0 go.uber.org/goleak v1.3.0 golang.org/x/mod v0.20.0 - golang.org/x/oauth2 v0.22.0 + golang.org/x/oauth2 v0.18.0 golang.org/x/sys v0.24.0 golang.org/x/time v0.6.0 golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028 - google.golang.org/api v0.192.0 - google.golang.org/grpc v1.64.1 + google.golang.org/api v0.169.0 + google.golang.org/grpc v1.64.0 google.golang.org/protobuf v1.34.2 gopkg.in/jinzhu/gorm.v1 v1.9.2 gopkg.in/olivere/elastic.v3 v3.0.75 @@ -120,10 +120,10 @@ require ( ) require ( - cloud.google.com/go v0.115.0 // indirect - cloud.google.com/go/compute v1.27.4 // indirect - cloud.google.com/go/compute/metadata v0.5.0 // indirect - cloud.google.com/go/iam v1.1.12 // indirect + cloud.google.com/go v0.112.1 // indirect + cloud.google.com/go/compute v1.25.1 // indirect + cloud.google.com/go/compute/metadata v0.2.3 // indirect + cloud.google.com/go/iam v1.1.6 // indirect github.com/DataDog/datadog-agent/pkg/util/log v0.58.0 // indirect github.com/DataDog/datadog-agent/pkg/util/scrubber v0.58.0 // indirect github.com/DataDog/go-sqllexer v0.0.14 // indirect @@ -156,7 +156,7 @@ require ( github.com/chenzhuoyu/base64x v0.0.0-20230717121745-296ad89f973d // indirect github.com/chenzhuoyu/iasm v0.9.0 // indirect github.com/cihub/seelog v0.0.0-20170130134532-f561c5e57575 // indirect - github.com/cncf/xds/go v0.0.0-20240423153145-555b57ec207b // indirect + github.com/cncf/xds/go v0.0.0-20240318125728-8a4994d93e50 // indirect github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f // indirect github.com/dustin/go-humanize v1.0.1 // indirect @@ -171,7 +171,7 @@ require ( github.com/gabriel-vasile/mimetype v1.4.2 // indirect github.com/gin-contrib/sse v0.1.0 // indirect github.com/go-jose/go-jose/v3 v3.0.3 // indirect - github.com/go-logr/logr v1.4.2 // indirect + github.com/go-logr/logr v1.4.1 // indirect github.com/go-logr/stdr v1.2.2 // indirect github.com/go-ole/go-ole v1.2.6 // indirect github.com/go-openapi/jsonpointer v0.19.5 // indirect @@ -192,9 +192,9 @@ require ( github.com/google/gnostic v0.5.7-v3refs // indirect github.com/google/go-cmp v0.6.0 // indirect github.com/google/gofuzz v1.2.0 // indirect - github.com/google/s2a-go v0.1.8 // indirect + github.com/google/s2a-go v0.1.7 // indirect github.com/googleapis/enterprise-certificate-proxy v0.3.2 // indirect - github.com/googleapis/gax-go/v2 v2.13.0 // indirect + github.com/googleapis/gax-go/v2 v2.12.2 // indirect github.com/gorilla/websocket v1.5.0 // indirect github.com/hailocab/go-hostpool v0.0.0-20160125115350-e80d13ce29ed // indirect github.com/hashicorp/errwrap v1.1.0 // indirect @@ -279,7 +279,7 @@ require ( github.com/xdg-go/stringprep v1.0.4 // indirect github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d // indirect github.com/yusufpapurcu/wmi v1.2.4 // indirect - go.einride.tech/aip v0.67.1 // indirect + go.einride.tech/aip v0.66.0 // indirect go.opencensus.io v0.24.0 // indirect go.opentelemetry.io/collector/component v0.104.0 // indirect go.opentelemetry.io/collector/config/configtelemetry v0.104.0 // indirect @@ -300,9 +300,9 @@ require ( golang.org/x/text v0.21.0 // indirect golang.org/x/tools v0.24.0 // indirect google.golang.org/appengine v1.6.8 // indirect - google.golang.org/genproto v0.0.0-20240730163845-b1a4ccb954bf // indirect - google.golang.org/genproto/googleapis/api v0.0.0-20240725223205-93522f1f2a9f // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20240730163845-b1a4ccb954bf // indirect + google.golang.org/genproto v0.0.0-20240213162025-012b6fc9bca9 // indirect + google.golang.org/genproto/googleapis/api v0.0.0-20240318140521-94a12d6c2237 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20240520151616-dc85e6b867a5 // indirect gopkg.in/inf.v0 v0.9.1 // indirect gopkg.in/ini.v1 v1.67.0 // indirect gopkg.in/yaml.v2 v2.4.0 // indirect diff --git a/go.sum b/go.sum index 49a41890dc..c351013d05 100644 --- a/go.sum +++ b/go.sum @@ -40,7 +40,6 @@ cloud.google.com/go v0.107.0/go.mod h1:wpc2eNrD7hXUTy8EKS10jkxpZBjASrORK7goS+3YX cloud.google.com/go v0.110.0/go.mod h1:SJnCLqQ0FCFGSZMUNUf84MV3Aia54kn7pi8st7tMzaY= cloud.google.com/go v0.112.1 h1:uJSeirPke5UNZHIb4SxfZklVSiWWVqW4oXlETwZziwM= cloud.google.com/go v0.112.1/go.mod h1:+Vbu+Y1UU+I1rjmzeMOb/8RfkKJK2Gyxi1X6jJCZLo4= -cloud.google.com/go v0.115.0/go.mod h1:8jIM5vVgoAEoiVxQ/O4BFTfHqulPZgs/ufEzMcFMdWU= cloud.google.com/go/accessapproval v1.4.0/go.mod h1:zybIuC3KpDOvotz59lFe5qxRZx6C75OtwbisN56xYB4= cloud.google.com/go/accessapproval v1.5.0/go.mod h1:HFy3tuiGvMdcd/u+Cu5b9NkO1pEICJ46IR82PoUdplw= cloud.google.com/go/accessapproval v1.6.0/go.mod h1:R0EiYnwV5fsRFiKZkPHr6mwyk2wxUJ30nL4j2pcFY2E= @@ -173,14 +172,11 @@ cloud.google.com/go/compute v1.18.0/go.mod h1:1X7yHxec2Ga+Ss6jPyjxRxpu2uu7PLgsOV cloud.google.com/go/compute v1.19.0/go.mod h1:rikpw2y+UMidAe9tISo04EHNOIf42RLYF/q8Bs93scU= cloud.google.com/go/compute v1.25.1 h1:ZRpHJedLtTpKgr3RV1Fx23NuaAEN1Zfx9hw1u4aJdjU= cloud.google.com/go/compute v1.25.1/go.mod h1:oopOIR53ly6viBYxaDhBfJwzUAxf1zE//uf3IB011ls= -cloud.google.com/go/compute v1.27.4/go.mod h1:7JZS+h21ERAGHOy5qb7+EPyXlQwzshzrx1x6L9JhTqU= cloud.google.com/go/compute/metadata v0.1.0/go.mod h1:Z1VN+bulIf6bt4P/C37K4DyZYZEXYonfTBHHFPO/4UU= cloud.google.com/go/compute/metadata v0.2.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= cloud.google.com/go/compute/metadata v0.2.1/go.mod h1:jgHgmJd2RKBGzXqF5LR2EZMGxBkeanZ9wwa75XHJgOM= cloud.google.com/go/compute/metadata v0.2.3 h1:mg4jlk7mCAj6xXp9UJ4fjI9VUI5rubuGBW5aJ7UnBMY= cloud.google.com/go/compute/metadata v0.2.3/go.mod h1:VAV5nSsACxMJvgaAuX6Pk2AawlZn8kiOGuCv6gTkwuA= -cloud.google.com/go/compute/metadata v0.3.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= -cloud.google.com/go/compute/metadata v0.5.0/go.mod h1:aHnloV2TPI38yx4s9+wAZhHykWvVCfu7hQbF+9CWoiY= cloud.google.com/go/contactcenterinsights v1.3.0/go.mod h1:Eu2oemoePuEFc/xKFPjbTuPSj0fYJcPls9TFlPNnHHY= cloud.google.com/go/contactcenterinsights v1.4.0/go.mod h1:L2YzkGbPsv+vMQMCADxJoT9YiTTnSEd6fEvCeHTYVck= cloud.google.com/go/contactcenterinsights v1.6.0/go.mod h1:IIDlT6CLcDoyv79kDv8iWxMSTZhLxSCofVV5W6YFM/w= @@ -314,7 +310,6 @@ cloud.google.com/go/iam v0.12.0/go.mod h1:knyHGviacl11zrtZUoDuYpDgLjvr28sLQaG0YB cloud.google.com/go/iam v0.13.0/go.mod h1:ljOg+rcNfzZ5d6f1nAUJ8ZIxOaZUVoS14bKCtaLZ/D0= cloud.google.com/go/iam v1.1.6 h1:bEa06k05IO4f4uJonbB5iAgKTPpABy1ayxaIZV/GHVc= cloud.google.com/go/iam v1.1.6/go.mod h1:O0zxdPeGBoFdWW3HWmBxJsk0pfvNM/p/qa82rWOGTwI= -cloud.google.com/go/iam v1.1.12/go.mod h1:9LDX8J7dN5YRyzVHxwQzrQs9opFFqn0Mxs9nAeB+Hhg= cloud.google.com/go/iap v1.4.0/go.mod h1:RGFwRJdihTINIe4wZ2iCP0zF/qu18ZwyKxrhMhygBEc= cloud.google.com/go/iap v1.5.0/go.mod h1:UH/CGgKd4KyohZL5Pt0jSKE4m3FR51qg6FKQ/z/Ix9A= cloud.google.com/go/iap v1.6.0/go.mod h1:NSuvI9C/j7UdjGjIde7t7HBz+QTwBcapPE07+sSRcLk= @@ -429,7 +424,6 @@ cloud.google.com/go/pubsub v1.28.0/go.mod h1:vuXFpwaVoIPQMGXqRyUQigu/AX1S3IWugR9 cloud.google.com/go/pubsub v1.30.0/go.mod h1:qWi1OPS0B+b5L+Sg6Gmc9zD1Y+HaM0MdUr7LsupY1P4= cloud.google.com/go/pubsub v1.36.1 h1:dfEPuGCHGbWUhaMCTHUFjfroILEkx55iUmKBZTP5f+Y= cloud.google.com/go/pubsub v1.36.1/go.mod h1:iYjCa9EzWOoBiTdd4ps7QoMtMln5NwaZQpK1hbRfBDE= -cloud.google.com/go/pubsub v1.40.0/go.mod h1:BVJI4sI2FyXp36KFKvFwcfDRDfR8MiLT8mMhmIhdAeA= cloud.google.com/go/pubsublite v1.5.0/go.mod h1:xapqNQ1CuLfGi23Yda/9l4bBCKz/wC3KIJ5gKcxveZg= cloud.google.com/go/pubsublite v1.6.0/go.mod h1:1eFCS0U11xlOuMFV/0iBqw3zP12kddMeCbj/F3FSj9k= cloud.google.com/go/pubsublite v1.7.0/go.mod h1:8hVMwRXfDfvGm3fahVbtDbiLePT3gpoiJYJY+vxWxVM= @@ -898,7 +892,6 @@ github.com/cncf/xds/go v0.0.0-20220314180256-7f1daf1720fc/go.mod h1:eXthEFrGJvWH github.com/cncf/xds/go v0.0.0-20230105202645-06c439db220b/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20240318125728-8a4994d93e50 h1:DBmgJDC9dTfkVyGgipamEh2BpGYxScCH1TOF1LL1cXc= github.com/cncf/xds/go v0.0.0-20240318125728-8a4994d93e50/go.mod h1:5e1+Vvlzido69INQaVO6d87Qn543Xr6nooe9Kz7oBFM= -github.com/cncf/xds/go v0.0.0-20240423153145-555b57ec207b/go.mod h1:W+zGtBO5Y1IgJhy4+A9GOqVhqLpfZi+vwmdNXUehLA8= github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= github.com/cockroachdb/datadriven v0.0.0-20200714090401-bf6692d28da5/go.mod h1:h6jFvWxBdQXxjopDMZyH2UVceIRfR84bdzbkoKrsWNo= github.com/cockroachdb/errors v1.2.4/go.mod h1:rQD95gz6FARkaKkQXUksEje/d9a6wBJoCr5oaCLELYA= @@ -1208,7 +1201,6 @@ github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbV github.com/go-logr/logr v1.2.3/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= github.com/go-logr/logr v1.4.1 h1:pKouT5E8xu9zeFC39JXRDukb6JFQPXM5p5I91188VAQ= github.com/go-logr/logr v1.4.1/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= -github.com/go-logr/logr v1.4.2/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= github.com/go-logr/stdr v1.2.0/go.mod h1:YkVgnZu1ZjjL7xTxrfm/LLZBfkhTqSR1ydtm6jTKKwI= github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE= @@ -1393,7 +1385,6 @@ github.com/google/pprof v0.0.0-20230817174616-7a8ec2ada47b/go.mod h1:czg5+yv1E0Z github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= github.com/google/s2a-go v0.1.7 h1:60BLSyTrOV4/haCDW4zb1guZItoSq8foHCXrAnjBo/o= github.com/google/s2a-go v0.1.7/go.mod h1:50CgR4k1jNlWBu4UfS4AcfhVe1r6pdZPygJ3R8F0Qdw= -github.com/google/s2a-go v0.1.8/go.mod h1:6iNWHTpQ+nfNRN5E00MSdfDwVesa8hhS32PhPO8deJA= github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510/go.mod h1:pupxD2MaaD3pAXIBCelhxNneeOaAeabZDe5s4K6zSpQ= github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= @@ -1422,7 +1413,6 @@ github.com/googleapis/gax-go/v2 v2.7.0/go.mod h1:TEop28CZZQ2y+c0VxMUmu1lV+fQx57Q github.com/googleapis/gax-go/v2 v2.7.1/go.mod h1:4orTrqY6hXxxaUL4LHIPl6lGo8vAE38/qKbhSAKP6QI= github.com/googleapis/gax-go/v2 v2.12.2 h1:mhN09QQW1jEWeMF74zGR81R30z4VJzjZsfkUhuHF+DA= github.com/googleapis/gax-go/v2 v2.12.2/go.mod h1:61M8vcyyXR2kqKFxKrfA22jaA8JGF7Dc8App1U3H6jc= -github.com/googleapis/gax-go/v2 v2.13.0/go.mod h1:Z/fvTZXF8/uw7Xu5GuslPw+bplx6SS338j1Is2S+B7A= github.com/googleapis/gnostic v0.4.1/go.mod h1:LRhVm6pbyptWbWbuZ38d1eyptfvIytN3ir6b65WBswg= github.com/googleapis/gnostic v0.5.1/go.mod h1:6U4PtQXGIEt/Z3h5MAT7FNofLnw9vXk2cUuW7uA/OeU= github.com/googleapis/gnostic v0.5.5/go.mod h1:7+EbHbldMins07ALC74bsA81Ovc97DwqyJO1AENw9kA= @@ -2193,7 +2183,6 @@ github.com/zenazn/goji v1.0.1 h1:4lbD8Mx2h7IvloP7r2C0D6ltZP6Ufip8Hn0wmSK5LR8= github.com/zenazn/goji v1.0.1/go.mod h1:7S9M489iMyHBNxwZnk9/EHS098H4/F6TATF2mIxtB1Q= go.einride.tech/aip v0.66.0 h1:XfV+NQX6L7EOYK11yoHHFtndeaWh3KbD9/cN/6iWEt8= go.einride.tech/aip v0.66.0/go.mod h1:qAhMsfT7plxBX+Oy7Huol6YUvZ0ZzdUz26yZsQwfl1M= -go.einride.tech/aip v0.67.1/go.mod h1:ZGX4/zKw8dcgzdLsrvpOOGxfxI2QSk12SlP7d6c0/XI= go.etcd.io/bbolt v1.3.2/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= go.etcd.io/bbolt v1.3.3/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= go.etcd.io/bbolt v1.3.5/go.mod h1:G5EMThwa9y8QZGBClrRx5EY+Yw9kAhnjy3bSjsnlVTQ= @@ -2502,8 +2491,6 @@ golang.org/x/oauth2 v0.5.0/go.mod h1:9/XBHVqLaWO3/BRHs5jbpYCnOZVjj5V0ndyaAM7KB4I golang.org/x/oauth2 v0.6.0/go.mod h1:ycmewcwgD4Rpr3eZJLSB4Kyyljb3qDh40vJ8STE5HKw= golang.org/x/oauth2 v0.18.0 h1:09qnuIAgzdx1XplqJvW6CQqMCtGZykZWcXzPMPUusvI= golang.org/x/oauth2 v0.18.0/go.mod h1:Wf7knwG0MPoWIMMBgFlEaSUDaKskp0dCfrlJRJXbBi8= -golang.org/x/oauth2 v0.20.0/go.mod h1:XYTD2NtWslqkgxebSiOHnXEap4TF09sJSc7H1sXbhtI= -golang.org/x/oauth2 v0.22.0/go.mod h1:XYTD2NtWslqkgxebSiOHnXEap4TF09sJSc7H1sXbhtI= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -2878,7 +2865,6 @@ google.golang.org/api v0.111.0/go.mod h1:qtFHvU9mhgTJegR31csQ+rwxyUTHOKFqCKWp1J0 google.golang.org/api v0.114.0/go.mod h1:ifYI2ZsFK6/uGddGfAD5BMxlnkBqCmqHSDUVi45N5Yg= google.golang.org/api v0.169.0 h1:QwWPy71FgMWqJN/l6jVlFHUa29a7dcUy02I8o799nPY= google.golang.org/api v0.169.0/go.mod h1:gpNOiMA2tZ4mf5R9Iwf4rK/Dcz0fbdIgWYWVoxmsyLg= -google.golang.org/api v0.192.0/go.mod h1:9VcphjvAxPKLmSxVSzPlSRXy/5ARMEw5bf58WoVXafQ= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= @@ -3027,15 +3013,10 @@ google.golang.org/genproto v0.0.0-20230320184635-7606e756e683/go.mod h1:NWraEVix google.golang.org/genproto v0.0.0-20230331144136-dcfb400f0633/go.mod h1:UUQDJDOlWu4KYeJZffbWgBkS1YFobzKbLVfK69pe0Ak= google.golang.org/genproto v0.0.0-20240213162025-012b6fc9bca9 h1:9+tzLLstTlPTRyJTh+ah5wIMsBW5c4tQwGTN3thOW9Y= google.golang.org/genproto v0.0.0-20240213162025-012b6fc9bca9/go.mod h1:mqHbVIp48Muh7Ywss/AD6I5kNVKZMmAa/QEW58Gxp2s= -google.golang.org/genproto v0.0.0-20240730163845-b1a4ccb954bf/go.mod h1:mCr1K1c8kX+1iSBREvU3Juo11CB+QOEWxbRS01wWl5M= google.golang.org/genproto/googleapis/api v0.0.0-20240318140521-94a12d6c2237 h1:RFiFrvy37/mpSpdySBDrUdipW/dHwsRwh3J3+A9VgT4= google.golang.org/genproto/googleapis/api v0.0.0-20240318140521-94a12d6c2237/go.mod h1:Z5Iiy3jtmioajWHDGFk7CeugTyHtPvMHA4UTmUkyalE= -google.golang.org/genproto/googleapis/api v0.0.0-20240528184218-531527333157/go.mod h1:99sLkeliLXfdj2J75X3Ho+rrVCaJze0uwN7zDDkjPVU= -google.golang.org/genproto/googleapis/api v0.0.0-20240725223205-93522f1f2a9f/go.mod h1:AHT0dDg3SoMOgZGnZk29b5xTbPHMoEC8qthmBLJCpys= google.golang.org/genproto/googleapis/rpc v0.0.0-20240520151616-dc85e6b867a5 h1:Q2RxlXqh1cgzzUgV261vBO2jI5R/3DD1J2pM0nI4NhU= google.golang.org/genproto/googleapis/rpc v0.0.0-20240520151616-dc85e6b867a5/go.mod h1:EfXuqaE1J41VCDicxHzUDm+8rk+7ZdXzHV0IhO/I6s0= -google.golang.org/genproto/googleapis/rpc v0.0.0-20240528184218-531527333157/go.mod h1:EfXuqaE1J41VCDicxHzUDm+8rk+7ZdXzHV0IhO/I6s0= -google.golang.org/genproto/googleapis/rpc v0.0.0-20240730163845-b1a4ccb954bf/go.mod h1:Ue6ibwXGpU+dqIcODieyLOcgj7z8+IcskoNIgZxtrFY= google.golang.org/grpc v0.0.0-20160317175043-d3ddb4469d5a/go.mod h1:yo6s7OP7yaDglbqo1J04qKzAhqBH6lvTonzMVmEdcZw= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= From 7f333855a531149356d571a671aae8dc67547564 Mon Sep 17 00:00:00 2001 From: Flavien Darche Date: Mon, 16 Dec 2024 16:17:04 +0000 Subject: [PATCH 3/5] Multi build runners (arm64, amd64) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ddtrace/tracer: initialize runtimeMetricsV2 with statsd "direct" client (#3006) Co-authored-by: Felix Geisendörfer Co-authored-by: Nayef Ghattas fix(.github/workflows): add tags-ignore to avoid running CI on pushing tags for contribs and other nested modules (#3005) Co-authored-by: Hannah Kim contrib/envoyproxy: envoy external processing support (#2895) This PR adds a new gRPC Interceptor (StreamServerInterceptor) to support the interception of ext_proc v3 calls to gRPC server. When the interceptor is applied, all messages of the external processing protocol are instrumented without returning an handle to the original server code Co-authored-by: Eliott Bouhana Co-authored-by: Flavien Darche add go mod to workflows/apps (#3036) go.mod: module go.opentelemetry.io/collector/pdata@latest found (v1.21.0), but does not contain package go.opentelemetry.io/collector/pdata/internal/data/protogen/profiles/v1experimental (#3042) Signed-off-by: Eliott Bouhana chore: update latest majors (#2993) --- .../workflows/service-extensions-publish.yml | 99 +++++++++++++++---- 1 file changed, 82 insertions(+), 17 deletions(-) diff --git a/.github/workflows/service-extensions-publish.yml b/.github/workflows/service-extensions-publish.yml index efb97be412..bc1d34c8f5 100644 --- a/.github/workflows/service-extensions-publish.yml +++ b/.github/workflows/service-extensions-publish.yml @@ -27,39 +27,104 @@ env: REF_NAME: ${{ github.ref || github.event.inputs.commit_sha }} COMMIT_SHA: ${{ github.sha || github.event.inputs.commit_sha }} PUSH_LATEST: ${{ github.event.inputs.set_as_latest || 'true' }} + REGISTRY_IMAGE: ghcr.io/datadog/dd-trace-go/service-extensions-callout jobs: - publish-service-extensions: - runs-on: ubuntu-latest + build-service-extensions: + runs-on: ${{ matrix.platform == 'linux/amd64' && 'ubuntu-latest' || 'arm-4core-linux' }} + strategy: + matrix: + platform: [ linux/amd64, linux/arm64 ] + steps: + - name: Prepare + run: | + platform=${{ matrix.platform }} + echo "PLATFORM_PAIR=${platform//\//-}" >> $GITHUB_ENV + - name: Checkout uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2 with: ref: ${{ env.REF_NAME }} - - name: Set up QEMU - uses: docker/setup-qemu-action@49b3bc8e6bdd4a60e6116a5414239cba5943d3cf # V3.2.0 + - name: Install Docker (only arm64) + if: matrix.platform == 'linux/arm64' + run: | + sudo apt-get update + sudo apt-get install -y docker.io + sudo systemctl start docker + sudo systemctl enable docker + sudo usermod -aG docker $USER + newgrp docker + sudo chmod 666 /var/run/docker.sock - name: Set up Docker Buildx - uses: docker/setup-buildx-action@c47758b77c9736f4b2ef4073d4d51994fabfe349 # v3.7.1 + uses: docker/setup-buildx-action@v3.8.0 - name: Login to Docker shell: bash run: docker login -u publisher -p ${{ secrets.GITHUB_TOKEN }} ghcr.io - - name: Replace slashes in ref name - id: replace_ref - run: echo "TAG_NAME=${TAG_NAME//\//-}" >> $GITHUB_ENV + - name: Docker meta + id: meta + uses: docker/metadata-action@v5 + with: + images: ${{ env.REGISTRY_IMAGE }} - - name: Build and push + - name: Build and push by digest id: build - uses: docker/build-push-action@4f58ea79222b3b9dc2c8bbdd6debcef730109a75 # v6.9.0 + uses: docker/build-push-action@v6 with: context: . - file: ./contrib/envoyproxy/envoy/cmd/serviceextensions/Dockerfile - platforms: linux/amd64,linux/arm64 - push: true - tags: | - ghcr.io/datadog/dd-trace-go/service-extensions-callout:${{ env.TAG_NAME }} - ghcr.io/datadog/dd-trace-go/service-extensions-callout:${{ env.COMMIT_SHA }} - ${{ env.PUSH_LATEST == 'true' && 'ghcr.io/datadog/dd-trace-go/service-extensions-callout:latest' }} + file: ./contrib/envoyproxy/go-control-plane/cmd/serviceextensions/Dockerfile + platforms: ${{ matrix.platform }} + labels: ${{ steps.meta.outputs.labels }} + outputs: type=image,name=${{ env.REGISTRY_IMAGE }},push-by-digest=true,name-canonical=true,push=true + + - name: Export digest + run: | + mkdir -p /tmp/digests + digest="${{ steps.build.outputs.digest }}" + touch "/tmp/digests/${digest#sha256:}" + + - name: Upload digest + uses: actions/upload-artifact@v4 + with: + name: digests-${{ env.PLATFORM_PAIR }} + path: /tmp/digests/* + if-no-files-found: error + retention-days: 1 + + publish-service-extensions: + runs-on: ubuntu-latest + needs: + - build-service-extensions + + steps: + - name: Download digests + uses: actions/download-artifact@v4 + with: + path: /tmp/digests + pattern: digests-* + merge-multiple: true + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3.8.0 + + - name: Login to Docker + shell: bash + run: docker login -u publisher -p ${{ secrets.GITHUB_TOKEN }} ghcr.io + + - name: Create tags + id: tags + run: | + tagname=${TAG_NAME//\//-} # remove slashes from tag name + echo "tags=-t ghcr.io/datadog/dd-trace-go/service-extensions-callout:${tagname} \ + -t ghcr.io/datadog/dd-trace-go/service-extensions-callout:${{ env.COMMIT_SHA }} \ + ${{ env.PUSH_LATEST == 'true' && '-t ghcr.io/datadog/dd-trace-go/service-extensions-callout:latest' }}" >> $GITHUB_OUTPUT + + - name: Create manifest list and push + working-directory: /tmp/digests + run: | + docker buildx imagetools create ${{ steps.tags.outputs.tags }} \ + $(printf '${{ env.REGISTRY_IMAGE }}@sha256:%s ' *) From d6dda03a5b6b084fe6c146b48150ace4cd60023a Mon Sep 17 00:00:00 2001 From: Flavien Darche Date: Wed, 18 Dec 2024 15:13:45 +0100 Subject: [PATCH 4/5] Applied comments (ipenv, signals, gracefull shutdown) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Applied comments appsec: stop storing span tags, directly call span.SetTag (#3044) Signed-off-by: Eliott Bouhana ddtrace/tracer: Tracing as transport-only mode (APPSEC_STANDALONE) (#3033) Signed-off-by: Eliott Bouhana fix: improving test logic for TestStreamSendsErrorCode to avoid flakiness (#3049) vuln: upgrade golang.org/x/{crypto,net} to non-vulnerable versions (#3050) contrib/miekg/dns: resolve flaky test in TestExchange* (#3045) ddtrace/tracer: report datadog.tracer.api.errors health metric (#3024) build(deps): bump google.golang.org/grpc from 1.64.0 to 1.64.1 (#3001) Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Rodrigo Argüello ddtrace/tracer: Report datadog.tracer.queue.enqueued.traces as health metric (#3019) ddtrace/tracer: Tracing as transport-only mode (APPSEC_STANDALONE) (#3033) Signed-off-by: Eliott Bouhana fix: improving test logic for TestStreamSendsErrorCode to avoid flakiness (#3049) vuln: upgrade golang.org/x/{crypto,net} to non-vulnerable versions (#3050) contrib/miekg/dns: resolve flaky test in TestExchange* (#3045) ddtrace/tracer: report datadog.tracer.api.errors health metric (#3024) build(deps): bump google.golang.org/grpc from 1.64.0 to 1.64.1 (#3001) Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Rodrigo Argüello ddtrace/tracer: Report datadog.tracer.queue.enqueued.traces as health metric (#3019) --- .../cmd/serviceextensions/main.go | 124 ++++++++++-------- ddtrace/tracer/option.go | 17 +++ go.mod | 4 +- go.sum | 4 +- internal/env.go | 12 +- 5 files changed, 93 insertions(+), 68 deletions(-) diff --git a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go index 856bd54666..3186ae76b4 100644 --- a/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go +++ b/contrib/envoyproxy/go-control-plane/cmd/serviceextensions/main.go @@ -6,14 +6,23 @@ package main import ( + "context" "crypto/tls" - "gopkg.in/DataDog/dd-trace-go.v1/internal" + "errors" + "fmt" "net" "net/http" "os" + "os/signal" "strconv" + "syscall" + "time" + + "golang.org/x/sync/errgroup" gocontrolplane "gopkg.in/DataDog/dd-trace-go.v1/contrib/envoyproxy/go-control-plane" + "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer" + "gopkg.in/DataDog/dd-trace-go.v1/internal" "gopkg.in/DataDog/dd-trace-go.v1/internal/log" "gopkg.in/DataDog/dd-trace-go.v1/internal/version" @@ -21,8 +30,6 @@ import ( "github.com/gorilla/mux" "google.golang.org/grpc" "google.golang.org/grpc/credentials" - "google.golang.org/grpc/reflection" - "gopkg.in/DataDog/dd-trace-go.v1/ddtrace/tracer" ) // AppsecCalloutExtensionService defines the struct that follows the ExternalProcessorServer interface. @@ -38,54 +45,20 @@ type serviceExtensionConfig struct { func loadConfig() serviceExtensionConfig { extensionPortInt := internal.IntEnv("DD_SERVICE_EXTENSION_PORT", 443) - if extensionPortInt < 1 || extensionPortInt > 65535 { - log.Error("service_extension: invalid port number: %d\n", extensionPortInt) - os.Exit(1) - } - healthcheckPortInt := internal.IntEnv("DD_SERVICE_EXTENSION_HEALTHCHECK_PORT", 80) - if healthcheckPortInt < 1 || healthcheckPortInt > 65535 { - log.Error("service_extension: invalid port number: %d\n", healthcheckPortInt) - os.Exit(1) - } + extensionHostStr := internal.IpEnv("DD_SERVICE_EXTENSION_HOST", net.IP{0, 0, 0, 0}).String() - extensionHost := internal.IpEnv("DD_SERVICE_EXTENSION_HOST", "0.0.0.0") extensionPortStr := strconv.FormatInt(int64(extensionPortInt), 10) healthcheckPortStr := strconv.FormatInt(int64(healthcheckPortInt), 10) - // check if the ports are free - l, err := net.Listen("tcp", extensionHost+":"+extensionPortStr) - if err != nil { - log.Error("service_extension: failed to listen on extension %s:%s: %v\n", extensionHost, extensionPortStr, err) - os.Exit(1) - } - err = l.Close() - if err != nil { - log.Error("service_extension: failed to close listener on %s:%s: %v\n", extensionHost, extensionPortStr, err) - os.Exit(1) - } - - l, err = net.Listen("tcp", extensionHost+":"+healthcheckPortStr) - if err != nil { - log.Error("service_extension: failed to listen on health check %s:%s: %v\n", extensionHost, healthcheckPortStr, err) - os.Exit(1) - } - err = l.Close() - if err != nil { - log.Error("service_extension: failed to close listener on %s:%s: %v\n", extensionHost, healthcheckPortStr, err) - os.Exit(1) - } - return serviceExtensionConfig{ extensionPort: extensionPortStr, - extensionHost: extensionHost, + extensionHost: extensionHostStr, healthcheckPort: healthcheckPortStr, } } func main() { - var extensionService AppsecCalloutExtensionService - // Set the DD_VERSION to the current tracer version if not set if os.Getenv("DD_VERSION") == "" { if err := os.Setenv("DD_VERSION", version.Tag); err != nil { @@ -95,19 +68,42 @@ func main() { config := loadConfig() + if err := startService(config); err != nil { + log.Error("service_extension: %v\n", err) + log.Flush() + os.Exit(1) + } + + log.Info("service_extension: shutting down\n") +} + +func startService(config serviceExtensionConfig) error { + var extensionService AppsecCalloutExtensionService + tracer.Start(tracer.WithAppSecEnabled(true)) + defer tracer.Stop() // TODO: Enable ASM standalone mode when it is developed (should be done for Q4 2024) - go StartGPRCSsl(&extensionService, config) - log.Info("service_extension: callout gRPC server started on %s:%s\n", config.extensionHost, config.extensionPort) + ctx, cancel := signal.NotifyContext(context.Background(), syscall.SIGINT, syscall.SIGTERM) + defer cancel() + g, ctx := errgroup.WithContext(ctx) - go startHealthCheck(config) - log.Info("service_extension: health check server started on %s:%s\n", config.extensionHost, config.healthcheckPort) + g.Go(func() error { + return startGPRCSsl(ctx, &extensionService, config) + }) + + g.Go(func() error { + return startHealthCheck(ctx, config) + }) - select {} + if err := g.Wait(); err != nil { + return err + } + + return nil } -func startHealthCheck(config serviceExtensionConfig) { +func startHealthCheck(ctx context.Context, config serviceExtensionConfig) error { muxServer := mux.NewRouter() muxServer.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { w.Header().Set("Content-Type", "application/json") @@ -120,24 +116,32 @@ func startHealthCheck(config serviceExtensionConfig) { Handler: muxServer, } - if err := server.ListenAndServe(); err != nil { - log.Error("service_extension: error starting health check http server: %v\n", err) + go func() { + <-ctx.Done() + shutdownCtx, cancel := context.WithTimeout(context.Background(), 5*time.Second) + defer cancel() + if err := server.Shutdown(shutdownCtx); err != nil { + log.Error("service_extension: health check server shutdown: %v\n", err) + } + }() + + log.Info("service_extension: health check server started on %s:%s\n", config.extensionHost, config.healthcheckPort) + if err := server.ListenAndServe(); err != nil && !errors.Is(err, http.ErrServerClosed) { + return fmt.Errorf("health check http server: %v", err) } + + return nil } -func StartGPRCSsl(service extproc.ExternalProcessorServer, config serviceExtensionConfig) { +func startGPRCSsl(ctx context.Context, service extproc.ExternalProcessorServer, config serviceExtensionConfig) error { cert, err := tls.LoadX509KeyPair("localhost.crt", "localhost.key") if err != nil { - log.Error("service_extension: failed to load key pair: %v\n", err) - os.Exit(1) - return + return fmt.Errorf("failed to load key pair: %v", err) } lis, err := net.Listen("tcp", config.extensionHost+":"+config.extensionPort) if err != nil { - log.Error("service_extension: gRPC server failed to listen: %v\n", err) - os.Exit(1) - return + return fmt.Errorf("gRPC server: %v", err) } grpcCredentials := credentials.NewServerTLSFromCert(&cert) @@ -145,10 +149,16 @@ func StartGPRCSsl(service extproc.ExternalProcessorServer, config serviceExtensi appsecEnvoyExternalProcessorServer := gocontrolplane.AppsecEnvoyExternalProcessorServer(service) + go func() { + <-ctx.Done() + grpcServer.GracefulStop() + }() + extproc.RegisterExternalProcessorServer(grpcServer, appsecEnvoyExternalProcessorServer) - reflection.Register(grpcServer) + log.Info("service_extension: callout gRPC server started on %s:%s\n", config.extensionHost, config.extensionPort) if err := grpcServer.Serve(lis); err != nil { - log.Error("service_extension: error starting gRPC server: %v\n", err) - os.Exit(1) + return fmt.Errorf("error starting gRPC server: %v", err) } + + return nil } diff --git a/ddtrace/tracer/option.go b/ddtrace/tracer/option.go index 6ea99d89eb..c1ad01edf9 100644 --- a/ddtrace/tracer/option.go +++ b/ddtrace/tracer/option.go @@ -587,6 +587,23 @@ func newConfig(opts ...StartOption) *config { // This allows persisting the initial value of globalTags for future resets and updates. globalTagsOrigin := c.globalTags.cfgOrigin c.initGlobalTags(c.globalTags.get(), globalTagsOrigin) + + // TODO: change the name once APM Platform RFC is approved + if internal.BoolEnv("DD_EXPERIMENTAL_APPSEC_STANDALONE_ENABLED", false) { + // Enable tracing as transport layer mode + // This means to stop sending trace metrics, send one trace per minute and those force-kept by other products + // using the tracer as transport layer for their data. And finally adding the _dd.apm.enabled=0 tag to all traces + // to let the backend know that it needs to keep APM UI disabled. + c.globalSampleRate = 1.0 + c.traceRateLimitPerSecond = 1.0 / 60 + c.tracingAsTransport = true + WithGlobalTag("_dd.apm.enabled", 0)(c) + // Disable runtime metrics. In `tracingAsTransport` mode, we'll still + // tell the agent we computed them, so it doesn't do it either. + c.runtimeMetrics = false + c.runtimeMetricsV2 = false + } + return c } diff --git a/go.mod b/go.mod index ed327de9e8..bbe71fe323 100644 --- a/go.mod +++ b/go.mod @@ -101,11 +101,11 @@ require ( go.uber.org/goleak v1.3.0 golang.org/x/mod v0.20.0 golang.org/x/oauth2 v0.18.0 - golang.org/x/sys v0.24.0 + golang.org/x/sys v0.28.0 golang.org/x/time v0.6.0 golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028 google.golang.org/api v0.169.0 - google.golang.org/grpc v1.64.0 + google.golang.org/grpc v1.64.1 google.golang.org/protobuf v1.34.2 gopkg.in/jinzhu/gorm.v1 v1.9.2 gopkg.in/olivere/elastic.v3 v3.0.75 diff --git a/go.sum b/go.sum index c351013d05..aed16d7b16 100644 --- a/go.sum +++ b/go.sum @@ -3061,10 +3061,8 @@ google.golang.org/grpc v1.50.1/go.mod h1:ZgQEeidpAuNRZ8iRrlBKXZQP1ghovWIVhdJRyCD google.golang.org/grpc v1.51.0/go.mod h1:wgNDFcnuBGmxLKI/qn4T+m5BtEBYXJPvibbUPsAIPww= google.golang.org/grpc v1.53.0/go.mod h1:OnIrk0ipVdj4N5d9IUoFUx72/VlD7+jUsHwZgwSMQpw= google.golang.org/grpc v1.54.0/go.mod h1:PUSEXI6iWghWaB6lXM4knEgpJNu2qUcKfDtNci3EC2g= -google.golang.org/grpc v1.64.0 h1:KH3VH9y/MgNQg1dE7b3XfVK0GsPSIzJwdF617gUSbvY= -google.golang.org/grpc v1.64.0/go.mod h1:oxjF8E3FBnjp+/gVFYdWacaLDx9na1aqy9oovLpxQYg= +google.golang.org/grpc v1.64.1 h1:LKtvyfbX3UGVPFcGqJ9ItpVWW6oN/2XqTxfAnwRRXiA= google.golang.org/grpc v1.64.1/go.mod h1:hiQF4LFZelK2WKaP6W0L92zGHtiQdZxk8CrSdvyjeP0= -google.golang.org/grpc v1.65.0/go.mod h1:WgYC2ypjlB0EiQi6wdKixMqukr6lBc0Vo+oOgjrM5ZQ= google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.1.0/go.mod h1:6Kw0yEErY5E/yWrBtf03jp27GLLJujG4z/JK95pnjjw= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= diff --git a/internal/env.go b/internal/env.go index e6a6bb0b19..2e760526ac 100644 --- a/internal/env.go +++ b/internal/env.go @@ -60,20 +60,20 @@ func DurationEnv(key string, def time.Duration) time.Duration { return v } -// IpEnv returns the valid IP string value of an environment variable, or -// def otherwise. -func IpEnv(key string, def string) string { +// IpEnv returns the valid IP value of an environment variable, or def otherwise. +func IpEnv(key string, def net.IP) net.IP { vv, ok := os.LookupEnv(key) if !ok { return def } - if net.ParseIP(vv) == nil { - log.Warn("Non-IP value for env var %s, defaulting to %s", key, def) + ip := net.ParseIP(vv) + if ip == nil { + log.Warn("Non-IP value for env var %s, defaulting to %s", key, def.String()) return def } - return vv + return ip } // ForEachStringTag runs fn on every key val pair encountered in str. From 1613818cf1a06f0f829c59be585ac79f90ede8f0 Mon Sep 17 00:00:00 2001 From: Flavien Darche Date: Mon, 23 Dec 2024 14:38:42 +0100 Subject: [PATCH 5/5] fix go mod tidy --- go.mod | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/go.mod b/go.mod index bbe71fe323..f78b187447 100644 --- a/go.mod +++ b/go.mod @@ -101,6 +101,7 @@ require ( go.uber.org/goleak v1.3.0 golang.org/x/mod v0.20.0 golang.org/x/oauth2 v0.18.0 + golang.org/x/sync v0.10.0 golang.org/x/sys v0.28.0 golang.org/x/time v0.6.0 golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028 @@ -295,7 +296,6 @@ require ( golang.org/x/crypto v0.31.0 // indirect golang.org/x/exp v0.0.0-20230905200255-921286631fa9 // indirect golang.org/x/net v0.33.0 // indirect - golang.org/x/sync v0.10.0 // indirect golang.org/x/term v0.27.0 // indirect golang.org/x/text v0.21.0 // indirect golang.org/x/tools v0.24.0 // indirect