Andy Troschke
Andy Troschke

Reputation: 479

Knative Func can't reach broker, but curl/busybox can?

I've setup a bit of a Knative test environment, and am trying eventing.

Here's a bit of output to quickly understand the cluster, there's no istio/SA shenanigans going on, as it's a fresh microk8s.

C:\dev\knative-test\functions\register-user>kubectl get broker -n default
NAME          URL                                                                            AGE   READY   REASON
user-broker   http://broker-ingress.knative-eventing.svc.cluster.local/default/user-broker   11h   True

Port forwarding/curl'ing this through busybox works and gets accepted/routed to the proper trigger and subsriber.

C:\dev\knative-test\functions\register-user>curl -v http://localhost:80/default/user-broker -X POST -H "Ce-Id: say-hello" -H "Ce-Specversion: 1.0" -H "Ce-Type: greeting" -H "Ce-Source: not-sendoff" -H "Content-Type: application/json" -d '{"msg":"Hello Knative!"}'
Note: Unnecessary use of -X or --request, POST is already inferred.
* Host localhost:80 was resolved.
* IPv6: ::1
* IPv4: 127.0.0.1
*   Trying [::1]:80...
* Connected to localhost (::1) port 80
> POST /default/user-broker HTTP/1.1
> Host: localhost
> User-Agent: curl/8.7.1
> Accept: */*
> Ce-Id: say-hello
> Ce-Specversion: 1.0
> Ce-Type: greeting
> Ce-Source: not-sendoff
> Content-Type: application/json
> Content-Length: 22
>
* upload completely sent off: 22 bytes
< HTTP/1.1 202 Accepted
< Allow: POST, OPTIONS
< Date: Sun, 11 Aug 2024 12:50:26 GMT
< Content-Length: 0
<
* Connection #0 to host localhost left intact

However, sending essentially the same message using a kn func like this:

func Handle(w http.ResponseWriter, r *http.Request) {
    ctx := cloudevents.ContextWithTarget(context.Background(), "http://broker-ingress.knative-eventing.svc.cluster.local/default/user-broker")

    p, err := cloudevents.NewHTTP(
        cloudevents.WithTarget("http://broker-ingress.knative-eventing.svc.cluster.local/default/user-broker"),
    )
    if err != nil {
        http.Error(w, err.Error(), http.StatusInternalServerError)
        return
    }

    c, err := cloudevents.NewClient(p, cloudevents.WithTimeNow(), cloudevents.WithUUIDs())
    if err != nil {
        http.Error(w, err.Error(), http.StatusInternalServerError)
        return
    }

    // Parse the request body into a User struct.
    var user User
    err = parseBody(r, &user)
    if err != nil {
        http.Error(w, err.Error(), http.StatusBadRequest)
        return
    }

    // Create a new event using cloudevents
    event := cloudevents.NewEvent()
    event.SetID(uuid.New().String())
    event.SetSource("fanfuse/functions/register-user")
    event.SetType("fanfuse.user.register")
    if err := event.SetData(cloudevents.ApplicationJSON, user); err != nil {
        http.Error(w, err.Error(), http.StatusInternalServerError)
        return
    }

    // Send the event
    if result := c.Send(ctx, event); !cloudevents.IsACK(result) {
        log.Printf("Failed to send event to broker: %v", result)
        http.Error(w, fmt.Sprintf("failed to send event: %v", result), http.StatusInternalServerError)
        return
    } else {
        log.Printf("Event sent successfully: \n%s\n", event)
    }
}

Results in the following error in the broker:

2024-08-11T12:45:10.096628364Z {"level":"warn","ts":"2024-08-11T12:45:10.096Z","logger":"mt_broker_ingress","caller":"ingress/ingress_handler.go:139","msg":"Broker getter failed","commit":"c3baeda"}
2024-08-11T12:45:10.096716467Z {"level":"warn","ts":"2024-08-11T12:45:10.096Z","logger":"mt_broker_ingress","caller":"ingress/ingress_handler.go:230","msg":"Failed to retrieve broker","commit":"c3baeda","error":"broker.eventing.knative.dev \"default\" not found"}

So, the Broker works, DNS works, the URL is correct. What's going on here? Am I missing something about the go cloudevents sdk?

Upvotes: 1

Views: 49

Answers (1)

E. Anderson
E. Anderson

Reputation: 3493

Have you tried setting up a standard HTTP server to check the request sent by your application? From looking a bit at the code, the only thing that I can see that might be strange would be if your client sent a request like:

POST http://broker-ingress.knative-eventing.svc.cluster.local/default/user-broker HTTP/1.1

I'm noticing that you're setting both cloudevents.ContextWithTarget and cloudevents.WithTarget. You might try setting only one of the two and seeing if the behavior changes.

If you find that one of these is not working correctly, please file a bug at https://github.com/knative/eventing/issues/new with the reproduction code -- this should be working (but clearly isn't for you).

Upvotes: 0

Related Questions