Brian Lovin
/
Hacker News
Daily Digest email

Get the top HN stories in your inbox every day.

HL33tibCe7

The author writes well and makes compelling points. His "I want to get off Mr Golang's Wild Ride" post is good too.

But I don't find myself agreeing with his position, which is "you shouldn't use Go for production services" (he explicitly says this in one of his Go posts, I forget which one and don't have time to look right now).

The better alternative to Go is Rust. Okay, sure, I'm willing to admit that in the examples presented, Rust handles things better. But Rust isn't a panacea. Rust is complicated and hard, and often it's not worth taking on that burden just to theoretically handle cases that rarely occur and even more rarely cause any problem. Programming is a means to an end, and the cost of using Rust (hiring, increased development time) is often not worth it.

The reason Go is successful is because it's easy for companies to use to solve production problems with teams of varying expertise. Its stdlib is well-featured, its ecosystem is good. There's generally one correct way of doing things. The same doesn't appear true in Rust. For example, an _incredibly_ common thing to do in production code is to make a web request. In Go, there is no need for debate, you use the stdlib. In Rust, you have to use a crate, which requires a decision to be made. Even worse is the async story, in Rust you have to decide whether to use Tokio or whatever. That burden is just not present with Go.

Btw this article should not be flagged and it's pathetic that people have flagged it.

cytzol

> Programming is a means to an end, and the cost of using Rust (hiring, increased development time) is often not worth it.

I agree with this. I learnt Rust before Go, and using Go makes me feel like The Oatmeal piracy guy[1]:

"I'm not sure if I should use Go to write this HTTP service. I'd lose immutability tracking, I'd lose compiler-enforced thread safety, I'd lose the powerful type system, I'd lose the comprehensive error handling, I'd suffer from a million little papercuts, I'd have to use the weird date formatting system, I'd have to check nil pointers, I'd...

...oh, it's seven days later and I've already accomplished more writing networking servers and clients in Go than I ever have in years with Rust."

This isn't to say the points raised about Go aren't true. They are true, and if a better language were available, I wouldn't stand my ground and argue their benefits, I'd switch to it. The last comment I happened to post on this website is about how Go is insufficient without its army of linting tools [2]! Yes, I'm incredibly happy to have learnt both Go and Rust as their combination has expanded my skillset and the range of programs I'm willing to write tremendously. But if someone said to me "you should just use Rust instead of Go for your production services", I'd think the "just" was doing some incredibly heavy lifting.

An article that I'd like to see is one comparing the two languages for this niche (networking servers and clients), contrasting not just the language pitfalls but the third-party libraries necessary, the iteration speed, and the choices you'll have to make up-front. My guess is that the languages would be judged more closely together.

[1]: https://theoatmeal.com/comics/game_of_thrones [2]: https://news.ycombinator.com/item?id=30749921

mumblemumble

I don't really use Go, I think mostly because I'm not in the target market, but this article's complaints (and some of these comments) actually got me thinking that I should take another look at it.

A long time ago, in a Haskell community chat, I saw someone dismiss Go with a pithy comment along the lines of, "Go isn't a programming language, it's a DSL for writing network services." I think I may need to re-assess that comment as actually being a really compelling elevator pitch for the language.

Armed with that perspective, I'm seeing why I wasn't terribly convinced by the article's specific complaints about Go. "Traditional IPC is a PITA and forces you toward talking over a socket? Well, yes, exactly. That's kind of the whole point."

Sometimes I wonder if we are all suffering unnecessarily because of our incessant demanding that all languages try to be all things to all people.

lupire

> Sometimes I wonder if we are all suffering unnecessarily because of our incessant demanding that all languages try to be all things to all people.

Programmers aren't. Programmers are building stuff and talking about that. Opinion bloggers are suffering for clicks.

andai

I was struck by ThePrimeagen[0] saying that it took him 5x longer to write a game server in Rust than in Go—despite having significantly more Rust experience. They performed about the same (I think Go actually did better due to how much easier it was to get concurrency working?).

Personally I lean towards strict compilers (I suppose years of JavaScript has traumatized me), but 5x dev time is a big tradeoff! Of course this is just one data point, but it did seem worth mentioning.

[0] - https://www.youtube.com/watch?v=Z0GX2mTUtfo

ay

My experience in writing a small side project in both (on the order of 2-3 KLOC) was that the time to a working project is significantly shorter with golang. The time to the correctly working project was about the same between the two.

Golang gets out of the way in me doing what I want.

Rust actively resists me doing things I will later regret.

Also, unexpectedly, I have gotten some positive comments on my C coding style after I coded some Rust.

All of this is completely anecdotal and personal experience, of course.

Thaxll

The problem with:

"I'm not sure if I should use Go to write this HTTP service. I'd lose immutability tracking, I'd lose compiler-enforced thread safety, I'd lose the powerful type system, I'd lose the comprehensive error handling, I'd suffer from a million little papercuts, I'd have to use the weird date formatting system, I'd have to check nil pointers, I'd...

None of the modern language do it beside Rust so every language are then bad?

mumblemumble

I think the quote marks were there to indicate that this was walking through a hypothetical thought process that someone might go through. (It proceeds on to the next line after that, where you see the closing quote mark.) The gist of the whole thing was basically to say, "Don't make the perfect the enemy of the good."

cytzol

Sorry, I don't get what you mean. Could you elaborate or re-phrase?

ianbutler

Checkout Elixir, I think it's better than GO for a lot of the use cases GO handles.

blippage

Oh man. The fake ads on that first link had me rolling around. Have an upvote!

EdwardDiego

Haha, your comment on the weird date formatting rings very true.

prirun

I haven't used Go or Rust seriously, but have written some Go toy code. This part of your post struck a nerve with me. I modified it slightly, to relate to Go's error handling, for me at least:

> often it's not worth taking on that burden just to theoretically handle cases that rarely occur and even more rarely cause any problem. Programming is a means to an end, and the cost of [Edit] adding if err != nil to every line of code [/Edit] (increased development time) is often not worth it.

I basically like Go, I really want to like Go, but as a Python person who has used exceptions with good success for 13 years in HashBackup, I can't see myself adding an if test to practically every line of Python code, just to catch an exception that might occur once in a blue moon.

A lot of software is not so mission critical that lives depend on it. If that is the case, sure - add error checking to every line of code. But for a lot of software, IMO, it's too much work for too little reward. If something blows up in production in an unexpected way, sometimes that's okay. You log the problem, fix it, and it's fine.

I re-read the Go error handling page before posting, because maybe it's not as bad as I had initially thought. Nope, still looks pretty cryptic to me:

https://go.dev/blog/error-handling-and-go

j3s

> If something blows up in production in an unexpected way, sometimes that's okay. You log the problem, fix it, and it's fine.

as the person on call for such events, it's really not fine.

would you rather handle these errors upfront during development time or unexpectedly and uncontrollably, during runtime? having been on-call in one way or another for ~10 years, i know which i'd prefer.

after having used golang in production, i will never go back to using a dynamically typed language if i can avoid it. almost 0 thought or effort is required to handle errors correctly in go, and it's still possible to ignore them (just use `_`). not that i'd recommend ever doing that.

kaba0

It’s a big assumption that you can even handle the error at the callsite, or that you will actually handle it correctly there, or just write some low-effort attempt because the overall picture is more important for now, but later on you won’t notice how it is not correct and it will just silently fail.

Exceptions are in my honest opinion better on every single front. Checked exceptions would be the panacea but Java’s version is not the best due to subclassing. But overall bubbling up exceptions is the correct thing to do — in most cases a problem can’t be meaningfully handled at the call site. Let’s say you want to read from a file during a HTTP request but the read fails n methods deep. There can be any number of other error occurrences and the only sane choice here would be to return some error code to the web client requesting the site. Why do you want to handle it n times instead of only at the goal?

layer8

> If something blows up in production

The problem is if it doesn’t quickly blow up, but instead silently corrupts data or causes other problems down the line that are hard to backtrack to that specific missing check.

prirun

But because exceptions bubble up the stack frame, there can be no missing checks. I'm not suggesting things be coded as:

  try:
    do something
  except Exception, err:
    pass
If a piece of code is has a try/except, then it's because there is the expectation that it might fail and certain kinds of failures can be handled. If a failure is not one of the expected failures, then do a raise and let the exception go higher up. It's either going to hit a handler in the main program or will exit to command level. In either case there's a stack trace to see where the problem occurred. Exceptions tell you exactly where things blew up, whereas the "if err return" paradigm only does that if the test at each level adds identifying information.

I've seen some Go stack traces. Talk about hard to backtrack: the ones I've seen go on and on. I understand it's because there are multple Goroutines running and each one has a stack trace, but they look pretty daunting to me.

closeparen

>you use the stdlib

* First you construct a request, and check the error on that

* Then you "Do" the request and check the error on that

* Then you check the status code (you did check it, right?)

* Then you deserialize the response and check the error on that

* Then you close the response body (you did remember to close it, right?) and check the error on that

Actually making an HTTP request with Go stdlib is a many-stage process and it is very easy to screw up or forget one of the steps. I see it all the time. Actually I have seen outages related to people being too zealous and reporting errors related to closing the response body on otherwise successful requests.

Cthulhu_

> Actually I have seen outages related to people being too zealous and reporting errors related to closing the response body on otherwise successful requests.

I kinda get it though, because the compiler or linters will show that as a warning or error going "bruh you forgot to handle this error", and as a perfectionist one wants to get rid of all of those.

I mean IMO those should be logged anyway, if only so you get some data on how often it happens, if there's anything that can be done about it, and if it's harmless, to ignore the error - but make it explicit.

icholy

The content is mostly ok, but the title suggests that there's some obvious alternative to Go that we should be using. If he's implying it's Rust, then he's totally disconnected from reality.

bovermyer

It's buried in the article, but I think the suggestion is "use almost any language other than Go" rather than Rust specifically.

The takeaway - if you gloss over the ranting and look for the good bits - seems to be that you should choose a language that handles a lot of the boilerplate for you (e.g., no verbose error handling) and has FFI.

It's not a bad argument, and it's making me think about how and when I use Go. For that, at least, it's worth reading.

wperron

It's really not, and it's even saying so explicitly in the article.

draxil

Definitely.

Go and Rust both have strengths and weaknesses.

And I think they both have a love/hate dynamic because they make pretty strong choices in their own ways, and so people react strongly in response. Personally I'm a fan of both.

beltsazar

> For example, an _incredibly_ common thing to do in production code is to make a web request. In Go, there is no need for debate, you use the stdlib.

And yet, Go's HTTP client doesn't have a good default [1] because of zero values, which are argued harmful in the article.

[1]: https://medium.com/@nate510/don-t-use-go-s-default-http-clie...

azth

> The better alternative to Go is Rust

Nope, a better alternative is Java/C#/Kotlin/etc. Those offer sum types, async programming, while being more productive than golang, and provide superior tooling and a superior developer experience.

weatherlite

Why not Node? Or Typescript if you really have to have types? Or even plain old PHP/Ruby (for people that just use Go to build web backends) - doesn't Kubernetes kinda solve scaling?

Fire-Dragon-DoL

I agree with you, however I think it's even simpler than that: the author is comparing Go to rust, but it's not comparing it to the places where it shines, that is, where Java, ruby, js, python are used.

Now suddenly we go from a poor type system (Java) to a decent one in Go (this is my personal opinion). Or from no type system to SOME type system. On top of this, we are getting all the benefits of a compiled language.

Essentially this is looking Go as a system language, while I think of it as an application language.

Aside from that, the author is right in some ways.

rmasters

Flagging this post strikes me as shameful censorship of an unpopular opinion.

You may say it's the snark/anger/frustration that got flagged, but I suspect it would not have been flagged if the topic were different.

Presuming the author is making bad-faith arguments for internet blog points goes against the spirit of HN. I prefer to draw my own conclusions, thank you. I normally expect HN to take the higher ground with calm and reasoned counter arguments of the content but not today I guess.

dang

> You may say it's the snark/anger/frustration that got flagged, but I suspect it would not have been flagged if the topic were different.

HN has had plenty of threads about Go over the years. What's different here is that there was just a big Go flamewar yesterday (https://news.ycombinator.com/item?id=31191700), from the same site. Having another big Go flamewar the next day is a really bad idea, because then on top of shallow ragey flameposts (boo) the thread will fill up with fluffy ragey metaposts (double boo). More explanation here: https://news.ycombinator.com/item?id=31207126

"Shameful censorship" is one way to put it, but front page space is the scarcest resource that HN has (https://hn.algolia.com/?dateRange=all&page=0&prefix=true&que...) and the amalgam of upvotes, flags, software weightings, and mod actions is what determines which stories end up / stay there vs. which stories fall off. This is the cycle of life on HN—it's always been that way and always will. One psychological effect is that everybody feels like their favorite topic is under-represented (or shamefully censored!) and in a way everybody is right.

I've often joked by adding "even Rust hackers feel that way" but maybe that's not the best line to use in this case :)

p.s. I feel like it's been a long time since HN had a passionate explosion about flagging and censorship (side note: ctrl+f misinformation...yup, that too) around a programming language. In a way it feels like a healthy sign. Like a family fight at Thanksgiving - at least it's about, say, a board game or something.

lilyball

This strikes me as very odd. The post yesterday is about a 2-year-old article. This post is about a brand new article, from the same author, written more or less as a response to all of the responses to the original article over the past 2 years.

If a flamewar is a problem, then that's what moderation is for, including potentially locking. I know you've posted comments on divisive articles before cautioning everyone about not wanting the comments to devolve into a flamewar, that would have been a great first step here.

But instead of doing that, you're saying that because of the old article popping up again yesterday and rehashing the same old flamewar, you've chosen to suppress the author's own response. I would think that the old article popping up yesterday makes this new post especially timely and even more important. It's not a rehash of the old flamewar, it's the author's own words with a well-written and fairly comprehensive response to the common criticisms, and it's highly relevant to the HN audience. And especially in the context of the discussion yesterday it seems a good idea to ensure visibility of the author's own response so anyone who saw yesterday's flamewar can see this. It took 2 years from the old post for the author to write this response, I'm pretty sure you don't have to worry about having a third post tomorrow.

pvg

The guiding logic here is 'it would be boring to have a discussion of X on the front page every day'. For many X, there's infinitely many things to say but the front page is finite and has a goal of not being boring. HN's been moderated like that for ages and it seems to work reasonably well.

undefined

[deleted]

gkfasdfasdf

I learned a great deal from the article. Thankfully I discovered it from twitter. If flame wars are the issue, then the thread should be locked, rather than pulling it from the front page. Really disappointed in this move.

mumblemumble

> Having another big Go flamewar the next day...

I haven't read all the comments on this one yet - there are quite a lot of them already - but reading this makes me think that perhaps we don't see the same comment section. (Perhaps because I'm not tasked with moderation, so I don't have much reason to go look at the 2nd page.) They've mostly been very thoughtful and balanced. It strikes me as some of the highest quality discussion on the subject of Go that I've seen on this site in years. It's a shame it was flagged and then buried on the 2nd page. A pinned comment reminding us not to get our hackles up in response to the author's abrasive style seems like it would have been plenty sufficient. I fear that, in your haste to head off an anticipated flamewar, what you've actually done is suppressed a potentially healing example to the community that it really is possible to have a mature conversation about Go.

dang

I don't have the impression that interesting technical discussion about Go has been particularly scarce on HN over the years? But if you think that today's thread is different enough from yesterday's thread to be significantly higher-quality and not just generic (i.e. about something specifically interesting in the OP, rather than just another generic discussion of Go, even if it's a good generic discussion of Go), then I'd be willing to take another look - in that case the best thing would be to link to the subthreads that you think make the best case for it.

The and in the previous paragraph is important, though, because a core moderation principle is to de-emphasize generic discussion (and follow-up threads, and repetition generally) in favor of significant new information. Past explanations on all that, if anyone cares:

https://hn.algolia.com/?dateRange=all&page=0&prefix=true&que...

https://hn.algolia.com/?dateRange=all&page=0&prefix=true&que...

https://hn.algolia.com/?dateRange=all&page=0&prefix=false&so...

https://hn.algolia.com/?dateRange=all&page=0&prefix=false&so...

rmasters

I appreciate the extra context. For what it's worth, I was not aware of the previous discussion and I just thought it was an interesting post. (I really don't have any feelings about golang one way or another.)

I can appreciate your point about having limited resources to moderate posts that have a track record of generating big flamewars. But I didn't get the impression from the comments (many being ad-hominem) that the post was flagged for that reason and my use of the word "shameful" was directed at those comments.

pg_1234

As someone coding in Go (and having doubts about the language) I find articles like this professionally valuable.

They don't have to be correct, they just need to provoke meaningful discourse, which for me means crowdsourcing the insights of hundreds of fellow devs.

dang

Yes. The problem here is that there was a big one of those just yesterday. HN does poorly with repetition, and throwing in the indignation aspect and the meta aspect (can you believe what an HN commenter said yesterday? the nerve!) guarantees that the thread will get high and go crazy. None of that is intentional, but it's a well-known failure mode, so the flags in this case were helpful. We've taken the [flagged] stigma off the title above, so as not to rub salt in any wounds.

The system has checks and balances to prevent such things from dominating discussion here. (Flags are part of that system; so are software bells and whistles; so are moderators). If we didn't have those, the front page would consist of nothing but sensational flamewars and endless towers of meta!

hu3

I agree. The signal to noise ratio of these "Rust vs Go" post comments is so bad they border being mostly a pile of anecdotes.

Also not meant to diminish the blogger but if you check their posts, it almost seems they feed on Go flamewar.

I could read every one of the 443 comments and still come out with zero knowledge gained because that's the kind of comment these posts incentivize.

Startups were built with less man-hours than what was collectively wasted on this thread.

victoryhb

I am also surprised that a reasoned discussion like this gets flagged while comments calling it a "shitpost" are not.

dang

It's like this: when the input is a soup of reasoned discussion plus sensational flamebait, the flamebait will always dominate, and will always determine the output. Sad, but reliable.

goodpoint

Because people learn to cling emotionally to hyped-up topics.

Any criticism of sacred icon is taken like an aggression to the reader's sense of self.

otterley

rglullis

What's "inappropriate" about the post? I for one wish that we had more posts like these instead of typical stuff that has been getting to the front page lately.

sph

whimsicalism

That post also got flagged initially FWIW.

blindseer

I've used Go and Rust professionally and in side projects, and I had used Go first before Rust. When I first used Go, I was like "oh wow, this is so simple and easy", and I didn't realize that I was putting up with the language. Learning Rust was relatively harder, but once I did and wrote some non trivial programs in Rust, it was like a pathway in my brain opened up and was previously blocked, and then when I went back to Go, I was painfully aware of issues that I the programmer had to keep in mind (or write a LOT of boilerplate code to keep track of). Issues that Rust's type system just solves.

The way `nil` can seep into your codebase in Go and how bad the FFI is in Go will prevent me from ever choosing it for a project going forward. And I personally would not feel confident modifying Go code written by someone else, and would not feel confident accepting PRs into my Go codebase unless I understood every line inside and out.

Rust is a breath of fresh air in that regard.

All that said, I think the author here is idealistic in a certain sense. In the scale of "solving a problem by hand (or using Excel/a proprietary tool etc)" to "writing a computer program to automate it", both Go and Rust are very close to each other. And once someone learns Go and knows it well enough, the incremental cost of learning Rust or even thinking about the problems Rust solves for you becomes not worth it. I think that it's sad that this is the way it works, but that's just how it is. It's easy for settle for a local optima like Go when taking into consideration family, pets, salary, time, effort etc.

I do think on a long enough timescale, programmers will eventually move to a "better" language. But in my opinion, that time scale exceeds the lifespan of a human :)

busterarm

I will say that playing around with Rust was an enjoyable experience, but it still has some warts where I think it's not quite ready for serious work yet (even though serious work is being done with it).

These days I find myself leaning heavily on either Haskell or Elixir/Erlang's ecosystem (with a preference for the latter). Or JavaScript (there's just an order of magnitude more jobs)...

whimsicalism

I find it difficult to see a standard where Rust is not ready for "serious work" but Haskell is.

busterarm

I can install a working Haskell toolchain with my package manager instead of the farcical `curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh`.

If you're an automation-oriented kind of person like it's my job to be, setting up repeatable toolchians based around the above is a total crock of shit.

bobbylarrybobby

What did you think those warts were?

mcronce

I use Rust for just about everything and I can definitely think of plenty of warts, but none of them make it "not quite ready for serious work" for my definitions of "serious work". I guess my point is that I'm curious what serious work this user is doing that Rust is unsuitable for - that kind of information is useful for language evolution, among other things.

zigger69

> I do think on a long enough timescale, programmers will eventually move to a "better" language. But in my opinion, that time scale exceeds the lifespan of a human :)

Zig exists and is here today.

streblo

I didn't care in the last post and I don't care about this one either. I care about my productivity, I care about my team's productivity, and I care about getting stuff shipped. Those are the things I care about, and go works great for that. If you care about those things too, and you're using go, you shouldn't stop using go.

My whole career people have been telling me to stop using languages or tools I've been productive with. I've built successful companies where everything was written in python, the whole time people on HN telling me how I was using a lowly language because of things like whitespace significance or strings that were not unicode by default.

If you care about other stuff, fine. If you don't think go works for you, don't use go. Just stop telling people who are using go (and other productive languages) to stop using them because of obscure language design issues or obscure API choices that people rarely encounter day to day. That isn't what matters to most people, and it's actually bad advice.

The problem is that there are a ton of less experienced people reading stuff on HN (just as I once was) who will take this to heart but have nothing actionable to gain from it, except to think they're a bad developer using a bad language. They aren't, and they're not.

busterarm

I use Go. I'm not a Rustacean. I've also used a whole bunch of things that are not Go.

In reading this article, I'm finding myself agreeing with 100% of the author's criticisms. I've seen every specific problem mentioned be a thing that bogs companies I've worked for down and erode productivity. A lot of time the ops peoples' (aka: my) productivity specifically.

I haven't worked at a single company where teams of developers using Golang have been able to get the basic networking stuff right.

"Why are my TCP connections not closing? Why am I encountering port exhaustion?" Go's frustrating inability to inter-op matters quite a lot at the end of the day. GRPC and protobufs are f'in messy and full of footguns.

Thing is, I've been around the block. I know that these problems don't have to be problems. We have a tremendously bad tendency in this field to join cargo cults.

When looking for my next gig, if the company is big enough, I'm likely to start seeing Go as a negative, unless they've got that Tailscale kind of expertise.

pphysch

> GRPC and protobufs are f'in messy and full of footguns.

Distributed data modeling is inherently messy and IME gRPC is one of the least messy, most scalable solutions to it. Or do you have a better alternative?

azth

protobuf has issues with optional fields, as was pointed out in the post. Couple that with a language with a weak type system like golang (no sum types), and it's very verbose and slow to develop in. Targeting better languages helps alleviate the latter.

hnarn

> "Why are my TCP connections not closing? Why am I encountering port exhaustion?"

So… why?

Thaxll

"Why are my TCP connections not closing? Why am I encountering port exhaustion?"

This has nothing to do with Go. You're implying Go has a bug in its TCP implementation which I assume is false.

Networking works just fine in Go and it's actually easy to use.

https://pkg.go.dev/net

Edit: I'm getting downvoted but please share with TCP issues in Go.

busterarm

The author of the blog post literally covered it in the article he wrote two years prior that's linked in the first sentence.

It's not "TCP issues in Go" it's "Go leaves you to figure these things out for yourself and write bad code that doesn't work if you don't thoroughly understand its gotchas."

Also, if you've been following Go over the years, you'll know that there's basically _always_ open issues (https://github.com/golang/go/issues/39063) in net & net/http about how Timeouts get mishandled and connections end up not being closed.

Cloudflare even had to write a whole (now old and outdated as hell) article explaining how to "do it properly" https://blog.cloudflare.com/the-complete-guide-to-golang-net... so that you don't footgun yourself.

Diggsey

> You're implying Go has a bug in its TCP implementation which I assume is false.

No, the parent is implying that Go's TCP implementation is easy to use incorrectly. Specifically in ways which cause the aforementioned issues.

tasuki

I believe that you are perfectly productive with Go, the article hasn't claimed otherwise.

I used to be quite productive with PHP. That does not mean PHP is a good language.

> The problem is that there are a ton of less experienced people reading stuff on HN (just as I once was) who will take this to heart but have nothing actionable to gain from it, except to think they're a bad developer using a bad language. They aren't, and they're not.

You are replying to an article mentioning many of Go's problems, without rebuking any of the article's points. Perhaps these poor people are using a bad language? (Also perhaps some people reading this are "bad developers", whatever that means? Perhaps I am! What does that matter?)

seba_dos1

The article's author has written and shipped tons of quality Go code that is still used in production by many people, myself included.

Sometimes, a poor language is a good tool for specific task despite of being generally a poor language. Sometimes, knowing and liking a bad language makes you use it for tasks it's not suited for. Go is in the same category as JavaScript and PHP there, which have their valid uses, but also a lot of valid reasons to stay away from. You only learn how and when to choose them once you become experienced enough in several languages to notice the differences between them over long term usage and project maintenance.

nightski

I mean, this is Hacker News. Not corporate programmer news. Building a successful company has very little to do with tech choices. But that doesn't mean we shouldn't discuss these things as tinkerers and hackers.

bombcar

> Building a successful company has very little to do with tech choices.

This is what Hacker News doesn't want to hear, and so needs to hear.

Like obsessing over the school supply list at the beginning of the year and getting everything perfect; it's not the whole of success, nor is it even really a huge part. But it can be fun.

zanellato19

So many companies succeed _despite_ their tech choices and so many fail also despite their tech choices.

In the end, even at mostly software companies, if you don't have a good sales model, a good sales team, a good marketing team, its likely you will out of business soon.

greybox

I don't think that the author is telling anyone to stop using Go. They are suggesting that there should be a better alternative, and there are lessons to be learnt.

I don't think we should be so cynical as to just lie down and accept that some things are just too hard to get right

oxnrtr

Especially when other languages got them right.

beltsazar

> I didn't care in the last post and I don't care about this one either. I care about my productivity, I care about my team's productivity, and I care about getting stuff shipped. Those are the things I care about, and go works great for that.

If your definition of "productivity" is the time spent in programming, I think you and the author are not in disagreement. The point that the author makes is that using a language with sophisticated type systems prevents some categories of bugs to happen in the first place. That means less time spent in debugging and fixing the code.

kretaceous

As a beginner learning Go for the past 3 weeks, thanks for the last paragraph.

I was looking into a new language to learn outside of JS and Python. I wanted to learn a hot language. I did some digging between Rust and Go and found out that Go is more suitable for web backends, CLI apps, etc. while Rust was more of a contender to C/C++, as it was primarily was made to be used as a memory-safe, correct, strict language to write low level software.

I don't generally involve myself in the latter so I chose Go. I definitely want to learn Rust someday but is it worth it if I don't get into that low level of things?

What are Go's and Rust's target applications according to readers here?

NIckGeek

Rust is a general purpose programming language. It can do low level systems programming but it's also highly capable of doing web backends, web frontends (wasm), game design, small utility scripts, etc.

A big thing people learning Rust do my mistake is to try and use all of the low level features straight away. Rust has tools like Rc, RefCell, Arc, and RwLock that let you have a garbage collected language (well, reference counted) and not worry about any of the low level memory management details.

See things like https://ggez.rs/ for games and https://www.arewewebyet.org/ for web stuff.

Although honestly I think if you're looking for a "hot" backend web language I'd say Elixir is the more well designed one than Go.

kretaceous

With your and the sibling commenters comment, I've made up my mind:

I'll definitely learn Rust one day and make stuff with it when I have proper time and I'm not learning anything else.

Thanks for the insights!

Karrot_Kream

Rust is indeed a general purpose programming language, but unlike the sibling poster I'm not going to sell it for low-level systems programming _and_ other things just because it can and has some (hit-or-miss depending on the domain) crates for them.

Rust is a complex language and its APIs tend to reflect the underlying domain complexity nearly 1:1. It also does not have a GC. Rust interops with native code well. When you're writing code that needs to be very correct especially in complicated problem domains, Rust is a great language to reach for because it bubbles up that underlying complexity so well. If you really need the lack of GC pausing then Rust is also IMO much better than most other non-GC languages in common use (c.f. C, C++). If you need C interop, then Rust is great. If you're a fan of writing elegant abstractions, Rust is also a great tool as its macro processor and language constructs make it easy to write abstractions (compared to other imperative languages at least). But its use for other areas is, IMO, a bit fraught.

Go is a lot more opinionated as a language. Its stdlib hides the complexity for certain interfaces. It has a simple-to-use concurrency model that the whole language opts into. It compiles quickly. It produces a no-nonsense static binary and has a great cross-compilation story. Go code is repetitive but simple to read. Go's tooling is stellar and because of how easy it is to write third-party tooling, people often build useful tools for themselves. I find it really easy to hack on or debug other Go projects if needed. Overall, Go is opinionated, and if the applications you're writing and the style you're writing them in fall into Go's opinions then you'll love it. If you don't like Go's style, you'll hate it. Go is my go-to (pun not intended lol) language for hobby coding because when coding as a hobby I'm often working on a constrained problem and don't need Rust's complexity.

To offer a concrete example, the OP in his previous blog post wrote a diatribe about Go's filepath handling on Windows, but when I recently used Rust to write something that templated a few filenames, the whole thing took incredibly long. The complexities of Rust filepaths accurately reflect all the edge cases available for different platforms but was ridiculous overkill for my simple app that I was hacking on that was only ever going to run on a single Linux x64 platform.

IMO to just "get things done" use Go. If you find yourself fighting Go's idioms, then Go isn't for you. If you really enjoy writing elegant abstractions, Go isn't for you. If you need to go deep into an API that Go simplifies and will spend most of your logic doing just that, then Go isn't for you. If you can't tolerate the GC pauses then Go isn't for you. Otherwise just use Go to get stuff done.

kretaceous

Thank you for the detailed explanation! That actually clarifies a lot of things.

Indeed, there's no straight-forward answer to the question "Should I learn Rust as a web backend developer?". It depends on all of the above things you mentioned here.

Go: Trades off correctness with opinions and abstractions. Has a GC. Has a simple, dare I say old or not-modern, type system. Easy to pick up. Hard to have full control over the program.

Rust: Reflects and embraces the actual system with its complexity. Correctness is first and foremost as it deals with all the edge cases. Not easy to pick up. But worth it for critical projects.

In a realisation, why do people even compare these two? :)

tomlin

I think your POV works in your very specific world view. As a head of an agency, hiring a developer that knows mainline languages serves a lot of good in hiring, keeping teams happy, and low turnover. We've all seen the agencies that hop on a new, hip language - only to go up in flames 6 months later because they couldn't find talent for their narrow viewpoint.

This isn't an argument against Go, moreso that your perspective is objectively elitist.

boulos

As people have remarked, Amos's style can be grating and hyperbolic. That doesn't make a lot of his complaints about Go as a language incorrect.

I do think he's misunderstanding that the design intent is "networked C" and that Go + Protobuf is much better than he thinks. A lot of his complaints with the language and runtime boil down to:

- It's got a primitive type system (yep, nobody disagrees)

- It leaves a lot of problems to you (yep, just like C)

- you can't integrate it into existing binaries (yep, distributed systems connected by RPC)

He comes to terms with the last one and admits it, but it is not only the thing Go is good at but it was the design intent. If you start from "we want a language and runtime for writing distributed systems that would otherwise be written in C or Java" then Go is pretty good!

I'm a happy Go, Rust, C, and C++ person. They're each for different things. That Rust worked out (is working out?) despite being an incredibly powerful and complex language (compared to C) is awesome. In the mid-2000s, it's not clear that you'd bet on a language like Rust. It is clear you could do better than Java or C++ for distributed systems programming, and Go hit that pretty reasonably (I do wish the language had a better type system, and I'm glad to see Ian finally land generics, but I'd absolutely reach for Rust when writing code in a small group that can handle the "language complexity" in exchange for the benefits).

kaba0

What I don’t generally get is why Go when there is Java already? Like other than the somewhat smaller memory footprint that is not inherent to the language, but the runtime — in what way is Go better that could not have been a Java library? Hell, with Google’s resources one other GC/mode could be added to OpenJDK that prioritizes memory footprint (at the expensive of throughput - there is no free lunch).

Sure, Java has some warts but it is a very easy and small language, the reflection-based frameworks are not at all mandatory, Java can be quite expressive without those as well and it is extremely performant. Once value types get included it will be really hard to get ahead of Java.

boulos

There are a few things, mostly due to the runtimes but also because the JVM bytecode assumption has real implications for system behavior.

Let's start with bytecode. It "requires" (except for AOT work) a warm-up / JIT phase that tends towards slower start times. This isn't hard and fast, but in practice it's true. (And when you search for "jvm startup", you end up at lots of pages about how to tune things to try to make this better). For some people, just as bad or even worse (remember, distributed system) is the impact that JIT-compilation and warm-up has on tail latencies. The static nature of most compiled languages mean this isn't a thing you worry about. You've got enough tail latency problems in your life, you don't need "oh hey, I just saw this loop for the Nth time, I took 10ms to hot compile it!".

That leads into the runtime and some of the language choices around it. Java GCs are generally fighting a harder problem than Go's GC, and with a very different tuning point. Java making everything an object and support classloading and so on, has real knock-on effects for the amount of work required to get high-quality, low-pause GC to work. This is much better today than it was in 2008 when the Go team started, but it's still the case that Go has an out-of-the-box better GC experience. Yes there exist special, tuned GCs (e.g., Azul's C4, Shenandoah) but Java GCs have to really be super clever compared to the fairly simple strategies that work in Go; I applaud the ingenuity in Java GC work, but if what you care about is "reasonably good at collecting memory, never pauses for long", the Go language decisions made the GC problem easier.

I think it's fair to ask "Shouldn't Google have just improved Java?", but I think you miss out on lots of the concurrency ergonomics. Again, this has to be compared to a decade ago. Especially post 2010 (Oracle acquisition) it was super unclear that you'd want to attempt to "bet on Java".

To be clear, I do think Go is at the wrong point on the language/type-system sophistication curve for my tastes. That said, I find myself shaking my head at most Java code, while looking at the Go code and thinking "sigh, lots of repetition. I hope one day that gets better, but at least it's obvious".

azth

> Yes there exist special, tuned GCs (e.g., Azul's C4, Shenandoah) but Java GCs have to really be super clever compared to the fairly simple strategies that work in Go;

It doesn't matter at the end, when those GCs work. There's also ZGC by the way, which has been consistently improving release over release, with sub ms pauses in the latest release for TB sized heaps, something that golang's gc cannot match.

> I applaud the ingenuity in Java GC work, but if what you care about is "reasonably good at collecting memory, never pauses for long", the Go language decisions made the GC problem easier.

Now if you want to have high throughput and willing to sacrifice some latency, Java's GC selection allows you to do that. Where as in golang you're stuck with the single gc implementation and have to resort to finicky code changes.

mumblemumble

I have barely touched Go, but, from what I've seen, I think I might be able to add a couple more to that:

Java is more intimidating to get in to. It starts with "Oh dear, which JDK do I use?", proceeds to, "Oh dear, now I have to pick a build tool and every single one has a near-vertical learning curve by modern standards." Then you're on to, "I want to do X. Why are there 28 competing libraries for X, and why are the most popular ones invariably the most hated?" And so on.

There's a strong case to be made that procedural is a better paradigm than object-oriented for a lot of the niche that Go targets.

You mentioned concurrency ergonomics, but I just wanted to emphasize that I doubt that Java's concurrency story can ever be a match for Go's. There's too much legacy baggage that can never be unloaded.

kaba0

> Let's start with bytecode. It "requires" (except for AOT work) a warm-up / JIT phase that tends towards slower start times

This is true, but relatively easily solved by AOT compilation which has been tried 2 decades ago as well as now and many times in-between. With a closed-world assumption done by Graal it is not a hard thing to do.

Re: GC

What language decisions do you mean? Other than having value types and some form of pointers, I really don’t see that much of a win. Sure, in some basic networking case allocating on the stack manually almost everything may be possible, but my experience shows that general purpose programs simply live or die by heap allocations and you can’t generally avoid them. And here the complex, but state of the art GCs of Java demonstratedly win big times, and this is the reason why the performance advantages of Go are not so pronounced or even existing for more complex use-cases.

But I will give you that the Oracle acquisition is indeed a good point - though it fortunately turned out to be a good thing for the Java ecosystem in hindsight.

Do you mean complex reflection-heavy java code or even simple explicit one? Because while I agree the latter is not the most common one in some areas, I find it to be surprisingly readable and simple, while still being expressive enough when needed.

azth

> If you start from "we want a language and runtime for writing distributed systems that would otherwise be written in C or Java" then Go is pretty good!

C and Java are far from the same. I'd argue that Java addresses or solves many of the criticisms he listed for golang (sum types, pattern matching, immutability with records, superior error handling with exceptions, nullability tracking with annotations, resource handling with try-with-resources, etc.).

kitd

The author obviously doesn't like Go. Ok, he can have his own opinions.

I've been coding professionally since 1987, using everything from mainframe assembler, Fortran, C, VB, Java, C++, to most recently Go. IMHO, the language itself plays a smaller role in its usefulness than most think. As important is the tooling, stdlib, ecosystem, community and "StackOverflow"-ability.

Go has a few warts, like every language, but not that many, and they are more than made up for by how easy it is to assemble and run a project using it. It's that that makes it the most productive language I've used so far.

14113

From the article: "[...] as developers get more and more senior, they tend to ignore more and more problems, because they've gotten so used to it. That's the way it's always been done, and they've learned to live with them, so they've stopped questioning it any more."

AnimalMuppet

As developers get more and more senior, they have a different perspective on what constitutes a "serious" problem. Also, as developers get more experience with a language, they get better at doing things in ways that are idiomatic for that language - they work with the language instead of against it.

Take Haskell. If I were a Haskell novice, and tried to do everything procedurally with do notation, and then complained that Haskell had all these problems, would that make Haskell a bad language? No. Would it mean that all Haskell programmers were telling themselves lies in order to keep using it? No. It would mean that I was using it badly.

If I were a brand new programmer, and took up Java, I might well complain about "public static void main(String[] args)". But an experienced programmer would brush that off, telling me that that's just syntax - there are real problems with Java, but that isn't one.

So this particular statement, that senior and more experienced devs ignore more and more problems, isn't proof of anything. It's particularly not proof that developers have to keep lying to themselves in order to keep using Go. (They may, but this isn't proof.)

tracerbulletx

As developers get more and more senior they tend to ignore more and more problems because they realize the majority of them actually don't matter very much to doing useful work.

mumblemumble

Or, perhaps more frequently, they can quickly see that any possible fix for it would be penny wise and pound foolish.

hnlmorg

He made some good points in the article but this particular paragraph stuck out as being hypocritical. The entire motivation of him writing this was because he felt people dismissed his previous article out of hand. And then he makes a remark that preemptively dismisses any rebuttal out of hand (and as others have pointed out, can equally apply to any language so hardly a point worth complaining against Go specifically).

randomdata

> as developers get more and more senior, they tend to ignore more and more problems, because they've gotten so used to it.

I've been coding professionally since the 90s. The last project I worked on was in Go. It was pleasant and surprisingly productive. A few warts, like the parent said, but all told it was a great experience. I'm now working on a Typescript project. It is painful. Typescript itself is quite nice, but the deep problems with the rest of the ecosystem have not gone unnoticed.

yegle

Hmm won't this apply to any language and therefore not a valid argument? A: language FOO is a great language! B: You are telling lies because you are fluent in this language and ignore the problems in the language.

formerly_proven

IME there are sort of two kinds of people here. People who are "fans" and defend "their" toy and people who don't. For example, I've been using Python for a very long time. I'm a "Senior Python Developer" so to speak. I quite like it for various purposes, but I can also talk your ear off about problems with Python.

I'd say if you run into someone who says they're experienced with X or love X etc., but they can't give criticism of it, they're most likely either not that experienced with X, or fanboys.

sophacles

Yes. This is true of any environment. That's why I ask new hires to write down every WTF moment, every question and every idea for improvement they have as they get up to speed on our systems. Just because I'm used to avoiding a problem doesn't mean the problem must exist.

xtracto

It seems to me there are two ways to evaluate the "beauty" of a language: there's the people who love the language theoretically (well constructed, coherent, nice typing, etc) and then there's people who love the usefulness/utility of the language.

For example, I hate python as a language (spaces syntax? Self,self,self, lack of static type, etc) but I've been using it lately and it's nice using it due to libraries, community,etc.

jayd16

Just speaking abstractly, whether problems are ignored has no bearing on the existence, size or count of the problems.

adhoc_slime

This has perhaps been my biggest pain-point with Golang..

Woe unto those who do not follow the idiosyncrasies of how golang handles versioning, package management, tooling etc.

if this is really your most important part of a language I would whole-heartedly recommend looking at rust which has been a breathe of fresh air in terms of package management and tooling.

busterarm

As an operations person who cares about deploying repeatable systems at scale, Rust's package management (and the toolchain's "packaging" itself) is an absolute nightmare. But at least I with MUSL can I have a 100% statically linked binary, which really should have been easier but that's another argument.

Seriously though, Rust team needs to have its Come To Jesus moment about not piping shit off the internet to sh.

conradludgate

I'm interested if you could elaborate on that?

My company deploys many Rust (web) applications to production and I've not experienced these issues with cargo

myrrlyn

rustup is available in your package manager's repository

Thaxll

Go tooling is awesome compared to other language ( Rust included ). Everything is built it and you don't need something external, everything works out of the box dependencies included, it has been the case for 4 years with go mod.

The fact that you can cross compile a win10 .exe on a raspberry pi with a single command as easy as "GOARCH=amd64 GOOS=win go build ." it's very powerful and I don't know a single language that does it out of the box like go does.

Go tooling is one of the strongest point of Go you have all of that built-in:

- compilation

- testing

- benchamark

- dep managment

formerly_proven

> it's very powerful and I don't know a single language that does it out of the box like go does.

zig build -Dtarget=x86_64-windows

jeroenhd

I love Rust as a language but its packaging mechanism is as flawed as all the others. I don't really see what breath of fresh air it brings.

I suppose you can define feature flags in your Cargo.toml but that's about it.

yen223

Golang has the most hilarious approach to date formatting

lenkite

Lol, I thought it was some sort of Joke when I first learnt it. And kept hunting for the 'proper' way. When I realised this was serious, I banged my head against the wall.

Karrot_Kream

+100. I found a lot of the points in the post pretty silly/arbitrary, but if he had talked about date formatting I would be all aboard.

undefined

[deleted]

thegeekpirate

You might enjoy https://golangti.me which I wrote to help with my inability to remember it!

paskozdilar

For me, the goroutines + channels + select is what makes Go leagues above any other popular language.

As far as I know, no other popular language allows you to read from multiple queues at the same time, which is an extremely useful pattern in concurrent programming. The only way to "select" from multiple sources in other languages is to use some kind of poll/select syscall on file descriptors - and even that is very limited, since kernel (at least Linux) does not allow userspace programs to create private file descriptors for intra-process communication - they must always be bound to some file/pipe/socket.

fasterthanlime

> As far as I know, no other popular language allows you to read from multiple queues at the same time

Off the top of my head, that's certainly possible in Rust, C++ and Java - probably many others I just don't know about.

That particular bit of concurrency goodness comes from the 70s, so you can be sure other languages picked it up.

npe

As I understand it, he's talking about select/alt (i.e. guarded commands from CSP) being a native feature of the language rather than callback-based approaches. It's possible to implement CSP channels in most languages, but they're not first-class like go.

bheadmaster

If you could spare some time, would you please demonstrate an example? Any language of those mentioned would be OK.

thestoicattack

Ada too, I think.

lalaithion

If that's all you want, Haskell has had goroutines (forkIO, yes it's called "fork" but it doesn't spawn an OS level process, that's forkOS), channels, and select since 1996. https://www.microsoft.com/en-us/research/wp-content/uploads/...

otterley

People also want a programming language they can easily read and that has enough market share to work well in team environments.

aidaman

nobody should ever write haskell

jcelerier

here's some documentation on how to do it in C++ with boost in 2008, before go even existed: in this example two threads pull events from a single queue.

https://www.boost.org/doc/libs/1_35_0/doc/html/boost_asio/tu...

(of course it was possible before)

paskozdilar

I'm not really experienced with Boost so I'm having a hard time understanding what that snippet does. Is there any example that is completely self-contained (or at least limited to STL)?

moralestapia

>read from multiple queues at the same time

That's a trivial thing in javascript.

paskozdilar

If you could spare some time, would you please demonstrate an example?

metadat

How? Javascript is single threaded run loop.

jayd16

Lots of languages have similar async, channel and pattern matching syntax these days. Kotlin, C#, off the top of my head. Probably a lot more.

alyandon

Yeah, it's pretty obvious to me the author doesn't like Go and some of the arguments raised really aren't concerns in (my very limited part of) the real world.

I've written a fair amount of Go and I am not bothered at all by the general ergonomics of the language. Some of the issues the author points out (like accidentally copying structs with embedded synchronization primitives) are caught by linters which you should be using regardless of what language you are coding in.

Edit: I dabble with Rust from time to time as well.

innagadadavida

A couple of things to add to this: the language spec is like a page long and very readable. Also the entire compiler toolchain and everything is written in Go and doesn’t depend llvm etc. This doesn’t help the developer but is a pretty unique aspect of Go.

atombender

The language spec (https://go.dev/ref/spec) is about 96 pages when printed on A4 paper. Certainly not a page long.

josephcsible

If a language spec is only a page long, it's leaving a bunch of important things unspecified.

metadat

Can you clarify further? Otherwise this seems like a shallow dismissal, which is against our HN community guidelines, and makes for uninteresting discussion.

randomdata

> Also the entire compiler toolchain and everything is written in Go and doesn’t depend llvm etc.

Depends on which implementation you're talking about. One of the stated goals of the Go project is that there must not be just one implementation. gc does not, but tinygo depends on llvm. gccgo depends on gcc.

crawshaw

Tailscalar here.

Go made prototyping our product easy. We have relatively rarely needed Go expertise on the team to make the product better, when we did it was for the exotic iOS environment (not normal iOS, the Network Extension).

It’s far from perfect (and I really should write an experience report about all the times Go has let us down!), but it gives us less trouble than Node and Swift do, for our relatively minor uses of those languages. I don’t think any other language would have been a better choice, even putting our expertise aside.

On the whole I would say you don’t need Go experts on your team to build products in the language.

VMtest

Author's criticisms are valid, but

"There's two types of languages, languages people complain about and languages no one uses"

Is author being serious about all people who write Go for production would be waking up at 3am to fix issues? If this is happening, software engineers are being abused, enough said

And not recommending C/C++ because it is easy to shoot yourself in the foot, apparently the devs enter hospitals so many times when memory-related vulnerabilities happen in Windows/Linux/Android/MacOs/iOS and Chrome/Safari/Firefox

people should stop idolizing programming languages

cglan

I just don't see the issue with Go. After dealing with inscrutable errors in some python code that interfaces with OpenSSL. Or dealing with impossible to trace errors in Spring Boot. Or Javascript? An absolute nightmare from start to finish. There's something extremely nice to get an error, place a breakpoint and trace exactly (even if it's a third party library) that error is happening.

I will take all the footguns in the world for that ability. Plus in general the tooling is just amazing. I know there is other Unix tooling out there but I'm sorry, they kinda suck and are terrible to use. They're for the type of person who can use vim with their eyes closed and unfortunately that's not me.

The other footguns he mentioned? Valid. A linter will catch a chunk of them though. I just generally don't think they matter half the time. I think of it like the iPhone. It's a pleasure to use like 80% of the time maybe 85% and 10% it feels hacky and terrible to get something working and 5% you just can't or shouldn't do it.

So for the 80% use case (backend crud apps or backend web apis) I'd take Go every time. Plus it compiles almost instantly versus multi minute turnaround times in a lot of other languages.

noisy_boy

> Or dealing with impossible to trace errors in Spring Boot.

Spring Boot is not Java. You can debug Java just as easily. On the upside, you can probably get the same stuff done in probably one third less code + use the vast ecosystem. On the downside, compilation may be a bit slower and you don't get a nice little executable out of the box.

I wrote a tool in Golang and while it did everything as advertised, the boilerplate just bogged me down. Any new changes is just so much more LOC compared to Java (or Python or Rust...). To be clear, I would prefer Java or Rust compared to Python any day. Either way, I just don't want to write so much verbose code anymore.

cglan

I don’t think I’ve ever seen Java used in isolation without spring boot

nevi-me

Not a CS, but a damn good technical accountant and well self-taught developer.

I led a team that wrote an accounting & reporting software for a specific technical problem. We had an architect who only knew Spring, and hasn't been out there pretty much in a decade.

I clashed severely with him, to the point where he made an arrogant argument about something he was clearly wrong with. He said "I bet my salary that you're wrong" in front of people. I bet mine too, and the following day I demonstrated that he was wrong. I gave him my bank account (it was pay day). It was a hard bet to lose, so I said he didn't need to pay it, and I asked him to be removed from the team (because he showed that he wouldn't learn).

We went on to build the system without Spring, without TomCat and with more freedom to write SAL where an ORM couldn't solve the problem better.

Interestingly, we used grpc between the front-end and the backend JVM microservices.

As other people say, check out projects in GitHub. Look at what new Java, Kotlin, Scala projects look like.

There's a lot of interesting stuff in JVM-land that don't touch Spring.

Interestingly on the software that we wrote, compute was the biggest bottleneck. I rewrote some parts in Rust, but ended up canning the work because nobody else would be able or willing to touch the code.

Sindisil

Y'all need to get out more often! ;)

Yes, Spring Boot is very popular, but there is a whole world of Java outside Spring, even if you confine yourself to just web apps (which is far from the only domain in which Java is used).

erik_seaberg

It’s worth remembering that Spring Boot didn’t exist for the first nineteen years we used Java.

japhib

This comment is hilarious ^

vbezhenar

How is Spring Boot not Java? Spring Boot is a simple Java library.

guipsp

Spring boot is not, in any way shape or form, a "simple" java "library". Not only is it a complex framework, it also uses features very few java programmers are exposed to, such as runtime code generation.

kaba0

I seriously doubt that Go would compile faster than Java. Like, neither does any reasonable amount of optimization, and I have never heard Java considered slow in compile time. Sure, one can do some very cryptic module-graph with their chosen build tool, but otherwise it should be as fast as it gets.

steaminghams

I generally like go and also see its problems as the author does.

However, with respect to the points about Go as a prototyping/starter language, there is not better language to start writing a project with in my opinion. Lots of languages have big communities of packages of various levels of maintenance but almost no other language has a standard library that is as usable as Go with the same guarantees between versions. I think its the biggest downfall of all these new languages like Rust/Zig/Hare etc, they all go for these minuscule standard libraries. I have no wish to start a project with any of them as all of them would involve I hunt down the 'best' http library and the 'best' async library and weigh their upsides and downsides, so I just reach for go and crack out the code I need to get it done, nothing else lets me do that half as easily, maintenance may be harder but at least I'm probably going to spend less time maintaining the list of packages that are still usable.

valcron1000

If you want a big standard library why not use something like Java or C#? I mean, you even have UI toolkits available from the get go

steaminghams

I dont know them as well as I do Go but the libraries (java especially) don't feel as coherent as the go libraries do, though that may be subjective and to do with my lack of experience with them. In addition both of these languages are large enough and have projects structured in such a way as to make it difficult to just use a text editor, which i consider a barrier to me just 'cracking out' a project.

C# also had pretty middling linux support the last time i worked with dotnet. and java tooling is not as out of the box as go is where I have to know is gradle good or still used or should i just use maven. Its all part of me not wanting to have to choose the best dependencies for my project and being handed for the most part good enough dependencies by the language standard library.

Another thing to appreciate in go is it produces good enough binaries and produces them very very quickly -- i've worked on several massive go projects and the build/test turnaround time is quite good.

conor-

With Go you can develop a web service with few to no external deps or frameworks, compile it into a single, static binary and then deploy it in a minimal distroless container.

With Java and C# there's a lot of other fuss involved with figuring out deployment. The code, build, test cycle is also much slower in C#/.NET ime. That's starting to improve a bit with the newer dotnet, but still feels behind other everything but the kitchen sink frameworks like Rails, which I would more compare C# to since C# without .NET/dotnet is uncommon.

metaltyphoon

Thats a lot of nonsense. The developer loop is way faster now in C# with the introduction of hot reload.

> fuss involved

The commands are almost the same from the go tooling, dotnet build , dotnet run, dotnet format, dotnet test…

Anything outside of hellow world for a web sevice in go, you will use a third party library while in .NET its given to you.

kaba0

Java can literally hot-swap classes, how does it have a slower code-build-test cycle? It also has possibly the best debug mode and observability.

kgeist

We have tens of microservices written in Go.

Go is good for onboarding new devs because it's simple. Our existing PHP devs were taught Go and it was painless. Jumping from PHP straight into Rust would be pretty painful, I think. Finding Rust devs isn't easy in our town.

But I agree with most of the points. You got to be very careful when writing in Go, because there are many gotchas. So many gotchas that I had to write a large document describing all the conventions and rules to remember to write bug-free (hopefully) Go. This "Go with conventions" reminds of the days when you'd try to simulate OOP in C - it works but error-prone.

Many of the problems are caught early with good unit and integration testing, however, just like with scripting languages. In my experience, most of the bugs in production in our Go microservices come from logical mistakes, not from misusing Go.

frou_dh

That means Go was easy for those devs to pick up, not that Go is simple.

Rich Hickey gave an all time classic presentation about this seemingly nitpicky but important distinction https://www.youtube.com/watch?v=SxdOUGdseq4

themantri

Interestingly, I have always heard Go is simple, but not easy.

undefined

[deleted]

oxnrtr

I readily believe that PHP devs struggle with anything more complex with Go, but that makes me question how people end up with the lack of will to learn and improve in this profession.

aidaman

can you shoot me the doc?

mcluck

I'm honestly surprised at the response to this article. I'm not involved in the Rust or Go spaces enough to have any strong opinions. This article was, yes, a little aggressive in tone but presented very honest and accurate information about a language that the author clearly has experience in. It seems like a lot of the people complaining in the comments didn't actually read the article. The author even explains how those who have bought in to Go may not want to hear what they're saying and it's right. No one wants to hear that their baby is ugly but sometimes it's the truth.

To those who do use Go: someone can call your baby ugly and you can still love it.

BaseballPhysics

I couldn't agree more. Some of the comments on this post are way out of line, straying into personal attacks on the author or their intentions. It's clearly touched a nerve and the reaction seems wildly out of proportion to the content.

busterarm

It's always sad to see when someone's favorite tool gets criticized that they fail to realize that there is no perfect tool and that we're just talking about tools.

It always plays out that way though.

jhugo

One thing to consider is that there is now a lot of Go out there, especially in the ops world thanks to k8s, Terraform, etc. A lot of people have put a lot of effort into learning it, and may have even built their career around it. So it's not surprising (even if it's a little sad) that people react very strongly to criticism of it. You sometimes see similar reactions to criticism of JS.

Just this week I've been dealing with a random crash when we run `terraform plan` which turned out to be a data race in Terraform itself. I honestly can't understand why something like Terraform, dealing with critical infrastructure, secrets, etc, would be built in a language like Go, apart from that all the other ops-adjacent stuff was being built in Go. The discussion in TFA about not selecting your tools solely based on what other companies are using is cogent.

Thaxll

When the author make such claim:

"It may well be that Go is not adequate for production services unless"

Who is exactly the author to tell us to not use a language that was proven to be just fine and successful. What actually OP shipped in production to be able to make such claim? Does it means also that Java / C# / Python, Ruby ect have the same fate since they're not up to part with Rust?

Kubernetes is everywhere and is built 100% in Go, it solves real complex issues, so was Go the wrong choice for it?

You can find many tools built in Go that are used by pretty much every compagnies now days, was Go the wrong language for those tools as well? Kuberentes, Docker, Grafana, Prometheus, esbuild etc ... the list is actually long.

Yes Go is not a perfect language, but saying that you should not use it production where the last 10years has shown that it deliver value is wrong.

rglullis

"Not being adequate != don't use it ever". Plenty of situations where pragmatism leads us to building things with "inadequate" tools.

Besides that, you do realize that your comment is a perfect embodiment of "Others use it, so it must be good for us too", which is the very first "lie" that he is describing?

Thaxll

I gave example of very successful tool used, Kubernetes works fine, did you ever heard about Kuberentes gone bad or full of bug or unusable? It's very stable and it's used by millions of people.

oxnrtr

a) calm down

b) please read the article before complaining

ploxiln

Let's not pretend that some flagging of this article represents all or most developers who use Go, and also not pretend that this post represents all or most developers who use Rust.

What kinda gets me from this genre of post, is that it sounds like writing good software in any language besides Rust is impossible, or even impractical. Like 10 years ago it was impractical for anyone to enjoy writing good software. (Or maybe Haskell or Ocaml would be acceptable?)

I've written a fair bit of Go, lots of Python and C, lots of bash and posix sh ... and I've written good and reliable-for-purpose software in all these languages, and I've enjoyed it much of the time. (In college I also wrote a chess playing engine in java, a malloc implementation and a trivial unix-like OS kernel with fork and threads in C of course, also a mips and z80 cpu implementation in verilog for fpga ... does that make me a "blub" programmer?)

Is it really an unacceptable flaw to have a program that only works with printable paths, and only makes sense to run on one's own files? Or which runs fine on both unix and windows, but doesn't do anything with file permissions? Or which only operates on file permissions on unix, but only runs on our servers and VMs?

I like high quality software, I really do. But I think that people writing these blog posts want something more, something impossibly pure. They want a messiah, and if everyone just believed, the world would be perfect. I like high quality software which has been possible and practical for 20+ years.

thatswrong0

I didn't get that desire for purity that you gleaned from it.

The fact is that (as the author pointed out) Golang is missing basic language features that other languages have adopted since the creation of C that eliminate whole classes of errors, and it's pretty easy to accidentally do the wrong thing as a result.

Nil pointer exceptions, for example, don't have to exist anymore.. and yet they do in Go because they couldn't be bothered to add sum types. Its type system is barely a step above a dynamic language. You have to write the same imperative looping code over and over because Rob Pike would rather just use a for loop than something mildly expressive like map or filter (https://github.com/robpike/filter). Every function that does meaningful work is littered with if err != nil { return err }. Etc.

It is easy to write code in Go, but IMO it's not easy to write and maintain a production grade system with any amount of complexity in Go because you _have_ to be careful, you can't encode invariants explicitly and let the compiler find problems for you, and you have to repeat yourself so often.

Mawr

> I didn't get that desire for purity that you gleaned from it.

'Folks who develop an allergic reaction to "big balls of mutable state without sum types" tend to gravitate towards languages that gives them control over mutability, lifetimes, and lets them build abstractions.'

This mutability argument is present throughout the article. Seems like nothing sans Rust or niche functional languages is enough.

> Nil pointer exceptions, for example, don't have to exist anymore..

The language most notorious for those is Java due to almost everything being passed via a nullable reference. When everything can be nullable, how can you know where to check for it? Go addresses this to an extent by explicitly separating pointers from values. Values are the default and cannot be nil, so the opportunity for null dereferences is greatly diminished. It's not a perfect solution, but it's not nothing either.

> and yet they do in Go because they couldn't be bothered to add sum types.

Damn those lazy Go devs!

> Its type system is barely a step above a dynamic language.

Turns out even a basic type system is a huge improvement over none. Just being able to restrict values to concrete types goes a long way.

> You have to write the same imperative looping code over and over because Rob Pike would rather just use a for loop than something mildly expressive like map or filter (https://github.com/robpike/filter).

There are arguments to be made either way, but I definitely agree generics (along with iterators) should have been there since day 1.

> Every function that does meaningful work is littered with if err != nil { return err }.

One big positive of this that I don't see in other languages is every `return` in a function must be on the start of a line. That is, every single exit path of a function is easily findable by visually scanning the start of each line for `return`.

> you can't encode invariants explicitly

I'm curious, are there any limitations here besides enums/sum types?

oxnrtr

> What kinda gets me from this genre of post, is that it sounds like writing good software in any language besides Rust is impossible, or even impractical. Like 10 years ago it was impractical for anyone to enjoy writing good software. (Or maybe Haskell or Ocaml would be acceptable?)

I think what we are seeing here is that the expectations are growing and people demand more from their tools.

This is a good thing, even if some languages cannot keep up with the higher standards and fall behind.

gjsman-1000

This is the second day in a row where a post about Go in a negative light was flagged. The first one was an extremely detailed criticism, maintained the front page, and was flagged like crazy. What gives?

sph

This is the second day in a row where a post about Go _from the same blog_ has been posted. I think that's enough, especially since it's mostly a knee jerk reaction from that very HN post from yesterday.

https://news.ycombinator.com/item?id=31191700

BaseballPhysics

> This is the second day in a row where a post about Go _from the same blog_ has been posted.

Unless you consider this post either spam or off topic (and I personally don't believe it falls into either category), then flagging the post is not in keeping with my understanding of the site guidelines.

Just don't upvote it.

ackfoobar

This post is (sort-of) a response to yesterday's discussion. I think it's fair to post it today.

gjsman-1000

Who cares if it is a legitimate criticism and makes unique points in both cases (also, they were both written two years apart!)? Some call it "inflammatory" but it has scientific and critical value nonetheless.

whimsicalism

What makes a reaction knee jerk? Is it just not liking it?

brundolf

To play devil's advocate: this author is known for often having a combative style. There's usually lots of good substance alongside that style, but the tone is what it is, and you could argue that it's needlessly incendiary. (Though in their defense, the post yesterday was self-described at the very top as "a proper rant")

HN is a powder keg of emotions about programming languages, and fasterthanlime's posts tend to be... shall we say, "sparky"

gjsman-1000

But that is literally one of the oldest logical fallacies in the book - Ad Homenem - defined as "(of an argument or reaction) directed against a person rather than the position they are maintaining."

bayesian_horse

Many people say Go is a better language to scale a codebase than Python, mainly because of typing, but I really doubt it. I can't tell for sure, because I haven't done a lot of Go coding. But to me the stated problems and the general lower-level nature suggest a productivity loss compared to Python, on average.

sophacles

I've written lots of python. Biggest codebase had ~100Ksloc of it.

I currently have a ~80Ksloc codebase in Go.

I like python. I dislike go.

I still hold the position that scaling a codebase is easier in go than in python.

* Goroutines + channels are generally easier for someone besides the author to reason about than their python equivalents, leading to a more consistency and better boundary definition.

* Python has a lot of magic in it - and that stuff is really cool, powerful and fun - but.. it also makes it incredibly easy to write stuff that works well together until it breaks in some wierd corner of a seemingly unrelated object somewhere.

* As python codebases grow, duck-typing becomes much less pleasant - you start seeing a bunch of `if isinstance(...)` in the code and eventually someone will come along and start implementing parts of a type system on top of the python code that exists (see also the previous point).

Those are the primary reasons for me, but there's also just a certain lack of friction in the go codebase (compared to python anyway) that I can't really describe well.

bayesian_horse

For me it is hard to attribute such differences to a programming language rather than the people creating and maintaining the code.

At the moment I am maintaining a C# codebase which doesn't feel maintainable at all, and I don't think C# is the only problem there.

Mawr

> This article was, yes, a little aggressive in tone

A little?

"[...] but I remember fondly the time an audience member asked the Go team "why did you choose to ignore any research about type systems since the 1970s"?"

"Unless you're out for confirmation bias, that whole article is a very compelling argument against using Go for that specific problem."

"[...] and tooling that would make C developers jealous, if they bothered looking outside their bubble."

"[...] and most importantly, you adopted a language that happened by accident."

"Evidently, the Go team didn't want to design a language. [...] "And so they didn't. They didn't design a language. It sorta just "happened"."

"And breaking down an argument to its smallest pieces, rebutting them one by one, is a self-defense tactic used by those who cannot afford to adjust their position in the slightest. "

"We've reached the fifth stage of grief: acceptance."

"Because it has been decided that abstractions are for academics and fools [...]"

> [...] but presented very honest and accurate information about a language that the author clearly has experience in.

It's biased flamebait, just like the original article.

> It seems like a lot of the people complaining in the comments didn't actually read the article. The author even explains how those who have bought in to Go may not want to hear what they're saying and it's right. No one wants to hear that their baby is ugly but sometimes it's the truth.

>

> To those who do use Go: someone can call your baby ugly and you can still love it.

Sure, I'd love to read such a well-considered article. Please link any you know of below.

Here's an exemplary article that managed to criticize Go without evoking a flamewar ([1]): https://gitlab.com/esr/reposurgeon/-/blob/master/GoNotes.ado...

I pose that if you present valid arguments in a reasonable, intellectually-curious way, people will respond positively. But if you set out on a holy war instead, well...

[1]: https://news.ycombinator.com/item?id=29494136

oxnrtr

It only hurts because it's true.

eatonphil

I use Go heavily cross-platform developing DataStation [0] and dsq [1]. I am not an expert. And I don't have proof for it but on some rudimentary benchmarks the Linux-specific file idioms in the Go standard library definitely don't seem to translate well to even macOS let alone Windows. For example some good streaming techniques for reading large files on Linux that work really well there seemed to be pretty bad on macOS.

I think Amos has presented more proof than I can on the topic of just how Linux-influenced Go is. And I think it is fine for the majority of Go users because the majority users of Go are building server apps or Linux CLIs.

Amos has spent some time building cross-platform desktop systems with Go for itch.io and I think I'm seeing some of the same things they are in that scenario.

I think this is a reasonable article. I didn't notice anything too flame-y myself but if for you Amos gets flame-y at any point I think that's worth ignoring because there does seem to be something up with Go in cross-platform applications. Amos does have good experience here. (Go look at itchi.io's github like wharf [2] or butler [3] where they are/were the main contributor.)

I like Go a lot and for most things I'd keep using it still. Just sharing some observations.

[0] https://github.com/multiprocessio/datastation

[1] https://github.com/multiprocessio/dsq

[2] https://github.com/itchio/wharf

[3] https://github.com/itchio/butler

Daily Digest email

Get the top HN stories in your inbox every day.

Lies we tell ourselves to keep using Golang - Hacker News