Skip to content

Report unbounded traffic to Otel#648

Merged
thomasjib merged 17 commits into
mainfrom
thomas/unbounded-otel
May 27, 2025
Merged

Report unbounded traffic to Otel#648
thomasjib merged 17 commits into
mainfrom
thomas/unbounded-otel

Conversation

@thomasjib

Copy link
Copy Markdown
Contributor

This fixes a wrapping bug, and adds some keys in the otel reporting to record the bytes processed through unbounded. This depends on this PR in unbounded being merged first.

@thomasjib thomasjib requested review from Copilot and reflog April 8, 2025 22:33

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Copilot reviewed 7 out of 9 changed files in this pull request and generated 1 comment.

Files not reviewed (2)
  • go.mod: Language not supported
  • rts/rts.ini: Language not supported

Comment thread reporting.go
}
instrument.ProxiedBytes(context.Background(), deltaStats.SentTotal, deltaStats.RecvTotal, platform, platformVersion, libraryVersion, appVersion, app, locale, dataCapCohort, probingError, client_ip, deviceID, originHost, arch)

ctxWithTeamId := context.WithValue(context.Background(), common.UnboundedTeamId, unboundedTeamId)

Copilot AI Apr 8, 2025

Copy link

Choose a reason for hiding this comment

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

Using context.Background() here discards the upstream context, including cancellation and timeout signals. Consider using the existing 'ctx' to ensure that context propagation is maintained.

Suggested change
ctxWithTeamId := context.WithValue(context.Background(), common.UnboundedTeamId, unboundedTeamId)
ctxWithTeamId := context.WithValue(ctx, common.UnboundedTeamId, unboundedTeamId)

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

The ctx variable isn't a context.Context, so this would not compile

Comment thread reporting.go
instrument.ProxiedBytes(context.Background(), deltaStats.SentTotal, deltaStats.RecvTotal, platform, platformVersion, libraryVersion, appVersion, app, locale, dataCapCohort, probingError, client_ip, deviceID, originHost, arch)

ctxWithTeamId := context.WithValue(context.Background(), common.UnboundedTeamId, unboundedTeamId)
instrument.ProxiedBytes(ctxWithTeamId, deltaStats.SentTotal, deltaStats.RecvTotal, platform, platformVersion, libraryVersion, appVersion, app, locale, dataCapCohort, probingError, client_ip, deviceID, originHost, arch)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Using the context was a quick way of passing the unbounded team id here without having to change the other things that use the instrument.ProxiedBytes(), should that be changed to be another parameter? or is this fine

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I don't get why this line is needed
ctxWithTeamId := context.WithValue(context.Background(), common.UnboundedTeamId, unboundedTeamId)

first of all it discards the original context and uses Background instead
second - it adds UnboundedTeamId, but on line 49 you already have that ID in the context? 🤔

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

I did it this way because the report function takes ctx map[string]interface{} as a parameter, not an actual context.Context. So in the previous implementation of this, the instrument.ProxiedBytes function was passed a context.Background(), and in this case i'm just adding the one value that isn't passed as a parameter through the function. But I also thought this was a strange way of doing this.

Comment thread reporting.go Outdated
Comment thread reporting.go
instrument.ProxiedBytes(context.Background(), deltaStats.SentTotal, deltaStats.RecvTotal, platform, platformVersion, libraryVersion, appVersion, app, locale, dataCapCohort, probingError, client_ip, deviceID, originHost, arch)

ctxWithTeamId := context.WithValue(context.Background(), common.UnboundedTeamId, unboundedTeamId)
instrument.ProxiedBytes(ctxWithTeamId, deltaStats.SentTotal, deltaStats.RecvTotal, platform, platformVersion, libraryVersion, appVersion, app, locale, dataCapCohort, probingError, client_ip, deviceID, originHost, arch)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I don't get why this line is needed
ctxWithTeamId := context.WithValue(context.Background(), common.UnboundedTeamId, unboundedTeamId)

first of all it discards the original context and uses Background instead
second - it adds UnboundedTeamId, but on line 49 you already have that ID in the context? 🤔

@reflog

reflog commented Apr 11, 2025

Copy link
Copy Markdown
Contributor

@thomasjib what's the status of this? did you test it out? do you see the stats + unbounded id in big query?

@thomasjib

Copy link
Copy Markdown
Contributor Author

@reflog, the tracking portion worked, and is in big-query, but the value for team_id is "". The problem I'm working on now is that I am able to get the header for team_id from the unbounded consumer -> egress server, but I'm not able to read that header in http-proxy

@thomasjib

Copy link
Copy Markdown
Contributor Author

This also brings up the go-version for http-proxy, which introduced this bug which I made pass the tests, but I didn't add any other fixes. So I am unsure if that needs anything more (thinking no if most of http-proxy is going away, just wanted to make sure someone else saw that).

@thomasjib thomasjib requested a review from Copilot May 20, 2025 22:28

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Pull Request Overview

This PR fixes a TLSMasq wrapping issue by constraining curve preferences and instruments new OTEL attributes to record unbounded traffic team IDs.

  • Adds CurvePreferences to TLSMasq tests to avoid a failing curve.
  • Retrieves and propagates UnboundedTeamId through context and OTEL attributes.
  • Updates fail signature in connectports.go and switches to baseListen in websocket proxy setup.

Reviewed Changes

Copilot reviewed 10 out of 10 changed files in this pull request and generated 3 comments.

Show a summary per file
File Description
tlsmasq/tlsmasq_test.go Constrain curve pref list in tests
reporting.go Extract and forward UnboundedTeamId in OTEL reporting
proxyfilters/connectports.go Updated fail call signature with extra argument
opsfilter/opsfilter.go Walk QUIC streams for team ID and add to measured context
instrument/instrument.go Append UnboundedTeamId to OTEL attributes
http_proxy.go Use baseListen for broflake listener builder
common/headers.go Add UnboundedTeamId header key
broflake/broflake.go Switch from NewListener to NewWebSocketListener
go.mod Bump Go version and dependencies
Comments suppressed due to low confidence (1)

opsfilter/opsfilter.go:11

  • The import path for unboundedCommon looks mismatched—ensure this is the correct package for the QUICStreamNetConn interface rather than broflake/common.
unboundedCommon "github.com/getlantern/broflake/common"

Comment thread reporting.go
}
instrument.ProxiedBytes(context.Background(), deltaStats.SentTotal, deltaStats.RecvTotal, platform, platformVersion, libraryVersion, appVersion, app, locale, dataCapCohort, probingError, client_ip, deviceID, originHost, arch)

ctxWithTeamId := context.WithValue(context.Background(), common.UnboundedTeamId, unboundedTeamId)

Copilot AI May 20, 2025

Copy link

Choose a reason for hiding this comment

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

Using context.Background() instead of the incoming Go context may drop cancellations and deadlines; consider deriving from the original context (e.g., context.WithValue(ctx, ...)).

Copilot uses AI. Check for mistakes.
Comment thread proxyfilters/connectports.go Outdated
port, err := strconv.Atoi(portString)
if err != nil {
return fail(cs, req, http.StatusBadRequest, fmt.Sprintf("Invalid port for %v: %v", req.Host, portString))
return fail(cs, req, http.StatusBadRequest, fmt.Sprintf("Invalid port for %v: %v", req.Host, portString), "")

Copilot AI May 20, 2025

Copy link

Choose a reason for hiding this comment

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

[nitpick] Passing an empty string literal as the last parameter is a magic value; consider overloading fail or providing a default internally to avoid empty arguments.

Copilot uses AI. Check for mistakes.
Comment thread tlsmasq/tlsmasq_test.go Outdated
require.NoError(t, err)

proxiedListener, err := tls.Listen("tcp", "localhost:0", &tls.Config{Certificates: []tls.Certificate{originCert}})
// all curve Ids, except for X25519MLKEM768, which breaks some of these TLSMasq tests for some reason

Copilot AI May 20, 2025

Copy link

Choose a reason for hiding this comment

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

[nitpick] The comment mentions excluding X25519MLKEM768 without context; consider referencing a ticket or adding rationale so future maintainers understand why it's omitted.

Suggested change
// all curve Ids, except for X25519MLKEM768, which breaks some of these TLSMasq tests for some reason
// All curve IDs are included except for X25519MLKEM768. This curve is excluded because it causes
// certain TLSMasq tests to fail. For more details, see issue #12345 in the project repository:
// https://github.com/getlantern/tlsmasq/issues/12345

Copilot uses AI. Check for mistakes.
@thomasjib

Copy link
Copy Markdown
Contributor Author

@reflog , this incorporates those curvePreferences changes into both the test and prod, do you think there is anywhere else to add that?

@thomasjib thomasjib requested a review from reflog May 27, 2025 16:29
@reflog

reflog commented May 27, 2025

Copy link
Copy Markdown
Contributor

@thomasjib , no this looks good!

@thomasjib

Copy link
Copy Markdown
Contributor Author

@reflog is this all set to merge?

@Crosse Crosse left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I'm good with this, if @reflog is good with it!

Comment thread tlsmasq/tlsmasq.go
var log = golog.LoggerFor("tlsmasq-listener")

// all curve Ids, except for X25519MLKEM768, which can cause errors with the TLSMasq handshake
var curvePreferences = []tls.CurveID{tls.CurveP256, tls.CurveP384, tls.CurveP521, tls.X25519}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Hard-coding the curves here means we'll have to remember to update it in the future if Go adds or updates the list of supported curves. Another option would be—

[editor's note: at this point, Seth went to the tls/crypto docs to find out how to get the list of default curves, and discovered that the Go team "helpfully" defined it as...nothing. An empty slice. Want the default list of curves? Scavenge from the defined constants, you plebian, and pray that The Go Team doesn't remove those "for simplicity's sake". Want to track the defaults? Read the f***ing code for the unexported function defaultCurvePreferences(). Good luck, sucker.

…I'm pretty sure Rob Pike just gave me the finger.]

*cough*

Uh, this looks good.

@thomasjib thomasjib merged commit 3d936a4 into main May 27, 2025
1 check passed
@thomasjib thomasjib deleted the thomas/unbounded-otel branch May 27, 2025 22:19
@thomasjib thomasjib restored the thomas/unbounded-otel branch May 30, 2025 22:14
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants