Live data from Hacker News

Better HTTP server routing in Go 1.22

eli.thegreenplace.net

91–100 of 236 posts

Re: Better HTTP server routing in Go 1.22

#91

Forcing a panic when 2 routes are matched seems counter intuitive to me (versus, idk, every other web framework which uses the first-to-be-registered route that matches). Are there go-specific reasons for that? The edge case of "you might register HTTP routes in a bunch of places and it's harder to find that if multiple routes match" seems like something that be worked around with tooling. I've (ab)used the behavior…

You can't guarantee the order of registration will always be the same, so it's really undefined behavior. This is how the original ServeMux was designed and implemented, and they felt that was useful behavior to continue to support. From the design proposal[1]: > Using specificity for matching is easy to describe and > preserves the order-independence of the original ServeMux > patterns. But it can be hard to see at…

This seems like an issue caused by registration at a distance. I'm new to go and it is one of the things that felt most wrong.

I'm used to a router where you define a big list of routes all in one place, maybe in some DSL. That's very easy to refactor, and doesn't have any ambiguity. If a library wants a route registered it puts a snippet in the docs for users to copy.

Go in general seems to value clarity over magic at the expense of verbosity, and this is a puzzling exception.

Re: Better HTTP server routing in Go 1.22

#92
post #13

Earlier quoted context omitted.

> Are there go-specific reasons for that? In general , the reason you use a compiled / typed language like golang at all (instead of, say, perl) is to "left shift" your bugs: A bug caught when you first spin up your application is better than a bug caught after a corner case acts up in the wild, and a bug caught when you compile is better than a bug caught when you first spin up your application. I recently ran a cro…

Wouldn’t the “left-shift” be a compiler error instead of a panic?

That's where the focus usually is, but aborting at startup is the next best thing. It's an undervalued technique.

Re: Better HTTP server routing in Go 1.22

#93

How did this kind of syntax become so popular? I think express is the first to do the scheme of: app.handleGet("/route/goes/here", (req, res) => { }); Which seems like it's useful for making really quick and dirty micro-services (nano-services, even), but I still vastly prefer the more declarative and modular schemes of bootstrap or asp.net: // Middleware automatically routes "/Foo" to FooController [Controller] publ…

In order for code to be maintainable it first has to be readable.

The second example has poor readability. And that's even before we get to the issue that this approach has fallen out of favor exactly because it result in code that can be a pain in the neck to figure out.

Please don't do this. This is the kind of legacy approach that I try to teach people working for me NOT to follow.

Re: Better HTTP server routing in Go 1.22

#94

Earlier quoted context omitted.

What's wrong with automatically registering a HEAD route?

"The HTTP HEAD method requests the headers that would be returned if the HEAD request's URL was instead requested with the HTTP GET method. ". So it goes against the HTTP spec.

Go implicitly buffers the first 512 bytes to sniff a content-type header so it's no like the status quo is free of arguably incorrect magic.

Re: Better HTTP server routing in Go 1.22

#95
post #6

I would far rather the overlapping path’s just match in the order they were defined rather than panic. In their example here, had they defined the `/task/0/{action}/` path before the wildcard path, my expectation would have been for that to match first. This would allow for handlers for special cases to easily be defined. I’d far rather things just do what I say than fail in “helpful” ways. Smells really funny and no…

Except the semantics of the language matter, and it is, actually, very Go . The original ServeMux was designed to not honor registration order, because it is risky to do so. One of the key design goals of Go is to support "programming at scale", and odd side-effects due to edits made to "distant code" is the exact kind of thing you want to avoid. In trivial examples, where all of the registrations are made in a singl…

Why even allow registrations at a distance? I'm a complete go beginner but that feels more in the spirit of go to me: making you do something a little annoying that ends up being clear and simple.

Of course it's too late now but I'm surprised this API was ever considered because it seems obviously scary and wrong to let a dependency just create it's own routes.

Re: Better HTTP server routing in Go 1.22

#96
post #93

How did this kind of syntax become so popular? I think express is the first to do the scheme of: app.handleGet("/route/goes/here", (req, res) => { }); Which seems like it's useful for making really quick and dirty micro-services (nano-services, even), but I still vastly prefer the more declarative and modular schemes of bootstrap or asp.net: // Middleware automatically routes "/Foo" to FooController [Controller] publ…

In order for code to be maintainable it first has to be readable. The second example has poor readability. And that's even before we get to the issue that this approach has fallen out of favor exactly because it result in code that can be a pain in the neck to figure out. Please don't do this. This is the kind of legacy approach that I try to teach people working for me NOT to follow.

> The second example has poor readability

Only if you don't know C# or asp.net (or bootstrap). In which case: why would you be working for an organization which does?

> And that's even before we get to the issue that this approach has fallen out of favor exactly because it result in code that can be a pain in the neck to figure out.

This kind of structured approach has fallen out of favor because it's become more popular to hire javascript and react developers straight out of boot camp who have only been taught how to code one or two things.

The argument that code needs to be inherently readable to someone with 3 weeks of experience is how you get hundreds of poorly written spaghetti code microservices written in node or typescript and not a language better suited for backend development. If you want your code base to constantly look like it was written by someone following their first javascript tutorial, then by all means continue using this top-level express JS crap

> Please don't do this. This is the kind of legacy approach that I try to teach people working for me NOT to follow.

You are setting yourself up for some bad tech debt in the future

Re: Better HTTP server routing in Go 1.22

#97

Earlier quoted context omitted.

>There's nothing "black magic" about them; they're very well documented features in Java, C#, and Python. Sure there is. It's metaprogramming. Anyone in the world who can read code can understand this immediately: app.get('/', (req, res) => { res.send('hello world') }) Throw decorators in the mix, and now I need to learn exactly what this specific environment is doing with those annotations. I have absolutely no way…

Your complaint is that you have to understand your web framework before writing a program in it? Is that not the case with ALL web frameworks? > And you're now also stuck with vendor lockin to whatever framework/compiler was using them I don't understand. If you choose a web framework, you are locked in to developing things in that framework from now on. In what world do companies try to change web frameworks without…

>Your complaint is that you have to understand your web framework before writing a program in it? Is that not the case with ALL web frameworks?

My complaint is that I don't want things in my code affecting my code that aren't code. Most web frameworks avoid this, while the more enterprise stuff like Spring, Dotnet, et. al seem to lean into it. It's kind of the same argument as SQL stored procs. Should you rely on embedding your business logic directly into the runtime? Probably not.

Ultimately it's just personal preference. But if I can't compile something in my head at a glance, it shouldn't be a part of the codebase IMO.

Re: Better HTTP server routing in Go 1.22

#98
post #82

How did this kind of syntax become so popular? I think express is the first to do the scheme of: app.handleGet("/route/goes/here", (req, res) => { }); Which seems like it's useful for making really quick and dirty micro-services (nano-services, even), but I still vastly prefer the more declarative and modular schemes of bootstrap or asp.net: // Middleware automatically routes "/Foo" to FooController [Controller] publ…

You're joking, right? How is the second example better in any way? You're also doing more in your second example. You can still do service injection in JavaScript.

> You can still do service injection in JavaScript

I know that angular is really good at this, but I'm not sure what pure js frameworks would allow a service to be defined as an interface first, and then injected into the constructor of a controller (or even a handler function) based on the implementation method selected somewhere else. I just haven't seen it happen.

Re: Better HTTP server routing in Go 1.22

#99

Earlier quoted context omitted.

>There's nothing "black magic" about them; they're very well documented features in Java, C#, and Python. Sure there is. It's metaprogramming. Anyone in the world who can read code can understand this immediately: app.get('/', (req, res) => { res.send('hello world') }) Throw decorators in the mix, and now I need to learn exactly what this specific environment is doing with those annotations. I have absolutely no way…

Your complaint is that you have to understand your web framework before writing a program in it? Is that not the case with ALL web frameworks? > And you're now also stuck with vendor lockin to whatever framework/compiler was using them I don't understand. If you choose a web framework, you are locked in to developing things in that framework from now on. In what world do companies try to change web frameworks without…

No, having to spend months learning how web frameworks are going to deal with that piece of code is not a good thing. It means that the code is readable only to those who have spent a lot of time working with that framework. And it is one thing to be able to guess what is going on, if you are only superficially familiar with the framework. It is another thing entirely to know enough to be able to debug the code or to make changes without stuff breaking.

And he does have a point about vendor lock-in. I tend to classify these kinds of frameworks as "cancerous" - as they metastasize and define how you can express yourself, and paint you into a corner where it gets really hard to rid your codebase of the framework should that be necessary.

Part of my job in the past has to be technical due dil for M&A. This kind of design approach usually results in a red flag if a major part of the valuation is the codebase.

Re: Better HTTP server routing in Go 1.22

#100

Go is not my main tool but I've used Gin which goes like this: router.GET("/", func(context *gin.Context) { ... } And it seems to be no different than many other languages/frameworks. Are there more examples that use the "GET /path/" way ?

Most likely not because there's no reason to do it this way other than backwards compatibility ...
Post reply on HN