Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

TT-968 enabled h2c by default #3380

Merged
merged 11 commits into from Feb 17, 2021
Merged

Conversation

sredxny
Copy link
Contributor

@sredxny sredxny commented Nov 4, 2020

Description

now for all the http proxies (including the main router of gw) is activated h2c. However, this doesn't means we will consume the upstream via h2c as this should be activated via target_url. This should be merged after #3372

Related Issue

https://tyktech.atlassian.net/browse/TT-968

Motivation and Context

give solution to https://tyktech.atlassian.net/browse/TT-968

How This Has Been Tested

  • Run gw in http mode and dashboard
  • Created api A without custom port
  • consume api A via postman, and via curl (Eg: curl -v --http2-prior-knowledge http://tyk-gateway:8080/keyless/uuid)
  • Created api B with custom port
  • consume api B via postman and curl
  • Created and configured grpc service
  • Consume grpc service via grpcurl (Eg: grpcurl -plaintext -proto helloworld.proto -d '{"name": "sredny"}' tyk-gateway:12345 helloworld.Greeter/SayHello)

Screenshots (if appropriate)

Types of changes

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to change)
  • Refactoring or add test (improvements in base code or adds test coverage to functionality)

Checklist

  • Make sure you are requesting to pull a topic/feature/bugfix branch (right side). If pulling from your own
    fork, don't request your master!
  • Make sure you are making a pull request against the master branch (left side). Also, you should start
    your branch off our latest master.
  • My change requires a change to the documentation.
    • If you've changed APIs, describe what needs to be updated in the documentation.
    • If new config option added, ensure that it can be set via ENV variable
  • I have updated the documentation accordingly.
  • Modules and vendor dependencies have been updated; run go mod tidy && go mod vendor
  • When updating library version must provide reason/explanation for this update.
  • I have added tests to cover my changes.
  • All new and existing tests passed.
  • Check your code additions will not fail linting checks:
    • go fmt -s
    • go vet

@sredxny sredxny changed the title Tt 968 enabled h2c by default TT-968 enabled h2c by default Nov 4, 2020
@sredxny sredxny marked this pull request as ready for review November 6, 2020 02:11
Copy link
Contributor

@matiasinsaurralde matiasinsaurralde left a comment

Choose a reason for hiding this comment

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

LGTM, we need a rebase

Comment on lines 122 to 124
if strings.HasPrefix(spec.Proxy.TargetURL, "h2c://") {
spec.Proxy.TargetURL = strings.Replace(spec.Proxy.TargetURL, "h2c://", "http://", 1)
}
Copy link
Contributor

Choose a reason for hiding this comment

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

why are we replacing target scheme here?

Copy link
Member

Choose a reason for hiding this comment

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

Because we treat h2c as alias to http. Probably should be followed by conned in source code.

Copy link
Contributor

Choose a reason for hiding this comment

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

I'm confused, from reading h2c is not http traffic please see this doc comment https://pkg.go.dev/golang.org/x/net/http2/h2c#NewHandler

Copy link
Member

@buger buger Feb 16, 2021

Choose a reason for hiding this comment

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

This link actually has good description, saying that h2c is http1.1 compatible

@@ -763,6 +766,9 @@ func loadApps(specs []*APISpec) {
shouldTrace := trace.IsEnabled()
for _, spec := range specs {
func() {
if strings.Contains(spec.Proxy.TargetURL, "h2c://") {
spec.Protocol = "h2c"
Copy link
Contributor

Choose a reason for hiding this comment

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

should we check if spec.Protocol is already set? If for instance spec.Protocol=http and target is h2c is that allowed? If not then spec is not valid we should emit an error or something.

Copy link
Contributor Author

@sredxny sredxny Feb 16, 2021

Choose a reason for hiding this comment

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

@gernest if http is set, and the target contains "h2c://" then it has major precedence, hence we set h2c as protocol. Also, I recall that from the very beggining we did this in this way due that FE doesn't have a protocol option h2c. At this point we infer the protocol from the target url

w: h.(*handleWrapper),
h: h2c.NewHandler(h, &http2.Server{}),
}
// by default enabling h2c by wrapping handler in h2c. This ensures all features including tracing work
Copy link
Contributor

Choose a reason for hiding this comment

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

This is a very big assumptions. By default we provide http proxy, so h2c,tcp etc are special case. You explicitly set protocol to h2c inside loadApps why not check it here?. I see this will be a major source of headache.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@gernest hi, can you elaborate regarding why it could be a major source of headache? currently by enabling h2c by default we're looking to simplify the process the most that we can

Copy link
Contributor

Choose a reason for hiding this comment

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

@sredxny
By design http2 is supposed to be served over TLS, h2c is an edge case/optional that is not supported by major browsers.

The only use case for h2c is when using gRPC without tls, which is also an edge case. Why do we make edge cases default behaviour? Like I said before http/http2 is the only thing we should take for granted, we should let our customers to choose anything else

Please see this stackoverflow answer on why http2 should always be on TLS https://stackoverflow.com/a/46789195

currently by enabling h2c by default we're looking to simplify the process the most that we can

What process are you simplifying? A process of choosing protocol to use? Why this protocol: "h2c" is not simple?

Copy link
Member

Choose a reason for hiding this comment

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

protocol field require you to have separate gateway port, while in general there is no reasons for this.

Copy link
Contributor

Choose a reason for hiding this comment

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

So the issue here is to remove the need for separate port?

Copy link
Member

Choose a reason for hiding this comment

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

In general yes. The whole idea of h2c that it works though standard http protocol, and if special header found, it enable special mode which kinda emulate http2 by using http as transport.

gateway/proxy_muxer.go Outdated Show resolved Hide resolved
Copy link
Contributor Author

@sredxny sredxny left a comment

Choose a reason for hiding this comment

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

changes done

gateway/proxy_muxer.go Outdated Show resolved Hide resolved
Copy link
Contributor

@tbuchaillot tbuchaillot left a comment

Choose a reason for hiding this comment

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

Looks good!

Copy link
Contributor

@matiasinsaurralde matiasinsaurralde left a comment

Choose a reason for hiding this comment

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

LGTM

@gregdelhon gregdelhon merged commit 5c8870a into master Feb 17, 2021
@gregdelhon gregdelhon deleted the TT-968-enabled-h2c-by-default branch February 17, 2021 15:42
@matiasinsaurralde
Copy link
Contributor

/release to release-3-lts

@tykbot
Copy link

tykbot bot commented Feb 17, 2021

Working on it! Note that it can take a few minutes.

tykbot bot pushed a commit that referenced this pull request Feb 17, 2021
* fix grpc proxy connection

* clean and format code

* clean code

* remove h2c config from gateway config

* replace h2c protocol from url and set it as http

* removed config enable_h2c at api level and infer it from the target url which should contains h2c://

* update grpc test

* gofmt gw file

* enabled h2c by default to http servers

* remove duplicated registeering of healthcheck

Co-authored-by: tbuchaillot <tombuchaillot89@gmail.com>
(cherry picked from commit 5c8870a)
@tykbot
Copy link

tykbot bot commented Feb 17, 2021

@matiasinsaurralde Succesfully merged 5c8870a53bca583556e7c04aeb4d31eee999187a to release-3-lts branch.

@matiasinsaurralde
Copy link
Contributor

/release to release-3

@tykbot
Copy link

tykbot bot commented Feb 17, 2021

Working on it! Note that it can take a few minutes.

tykbot bot pushed a commit that referenced this pull request Feb 17, 2021
* fix grpc proxy connection

* clean and format code

* clean code

* remove h2c config from gateway config

* replace h2c protocol from url and set it as http

* removed config enable_h2c at api level and infer it from the target url which should contains h2c://

* update grpc test

* gofmt gw file

* enabled h2c by default to http servers

* remove duplicated registeering of healthcheck

Co-authored-by: tbuchaillot <tombuchaillot89@gmail.com>
(cherry picked from commit 5c8870a)
@tykbot
Copy link

tykbot bot commented Feb 17, 2021

@matiasinsaurralde Succesfully merged 5c8870a53bca583556e7c04aeb4d31eee999187a to release-3 branch.

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.

None yet

6 participants