Hacker News new | past | comments | ask | show | jobs | submit login
Ask HN: What are some of the most elegant codebases in your favorite language?
223 points by debanjan16 on June 17, 2023 | hide | past | favorite | 178 comments
Your favorite language can be anything - Lisp, Python, C, Haskell, etc.

Which codebases are the most elegant ones written in your favorite language that new comers to the language can learn something from?




I'd nominate Java itself.

In the decades Java sources have been available, any of the kazillion junior programmers could debug-step into java.* and see exactly what's happening -- progressive disclosure at its finest for building expertise.

Most other languages have a hard boundary, so the roots of language are a matter of conceptual documentation and experience. Java also offers that fly-over knowledge, but when problems arise, programmers love knowing exactly and seeing directly.

Personally, in a pinch I prefer the actual to the elegant.


While I think there's a lot to love about Java, the standard library itself is not an especially great role model. Most of it was written a long time ago and has a fairly antiquated style - lots of mutable state, nullability, and checked exceptions. Not that the library isn't an incredible asset - it's luxuriously rich compared to working in Node.js - but if it were written from scratch today, I suspect it would look fairly different. Eg, the collection classes would use Optional and have separate read/write interfaces.

For an example of "modern Java" I would point at something like this (which I wrote, sorry about the hubris):

https://github.com/stickfigure/hattery


As much of a fan as I am of Java, I have to agree. There are some real bombshells in the library that can either make your coding life or debugging a prod service miserable (sometimes both). Other additions are great, but have hurt readability a bit (i.e. Java lambdas).

Checked exceptions get a bad rep, but I've frequently found taking advantage of their hierarchical nature can be beneficial to at least making them less bad to catch. When I work with languages that have no exception support at all, I sometimes even miss them.


As much as "not" a big fan of java, I need to give credit where it is due.. as my (almost) first language almost 25 years ago I learnt heaps by going through the source code. Sure there were bad and (what are now) outdated conventions etc. But as a junior eng learning how layouts worked, how data structures were implemented, how network code was written and tons more, the Java src folder was a huge treasure mine. Did I mention swing?


I only looked over your code for a minute but found some stuff I would comment on in a code review.

Comment for a method says "null safe" - why not use an annotation?

A package called "util" is a code smell for me.

UrlUtils only provides two methods for URL encoding so why not name it appropriately?


I’ve always heard about the “util” package code smell but usually in complex contexts that are hard to discuss.

How would you refactor this to avoid a util package or a UrlUtils class?


From your repo: Respectfully, I disagree that checked exceptions are a misfeature. Java’s implementation definitely leaves a lot to be desired (inheritance doesn’t make sense for them), but otherwise checked exceptions are a better form of Result types.


Unchecked exceptions are the better version of Result type.

The problem with checked exceptions is that methods throwing them force its callers to react to the even if they are irrelevant to them. In 99% of cases I don't have any JSON specific error handling, yet Jackson forces me to do a try-catch-rethrow ceremony in thpse 99% to declare I don't want to do anything specific.


That’s the not too comfortable part. But with a tiny bit of syntax sugar (say, a ! or ? that expands to a mini-try-catch block) it would be more than fine.


Yes, I would be fine with a shorthand syntax like that. But it's not available which makes checked exceptions more trouble than worth.


After a decade of programming 50+ hours a week in many languages (typescript, javascript, python, scala, java, lua, bash, c++, etc), I have come to the conclusion that Java is simply the best. The tooling, libraries, stability, verbose rigidity. It forces a style of programming that simply scales to more engineers better


As an end user though, I honestly can’t think of any Java software I actually enjoy using. Minecraft? That’s literally the only thing that comes to mind.


This was true for me as well until I used DBeaver (a universal database browser tool) I only realized it was java after I tried connecting to a really old server that needed me to change my ssl settings in the JRE. The user interface feels fairly snappy. DBeaver is a really fantastic tool and I don't see myself changing any time soon. It even supports making its own SSH tunnels to your database server using your local ssh agent.

I can attest that AWT and Swing were hot garbage 20 years ago, though. The cross-platform aspect worked great, but the algorithms weren't worth making cross-platform to begin with. It was basically a giant GUI ecosystem written by people with no understanding of how to implement graphics efficiently. My favorite was how they bragged about their "lightweight" visual components that don't require OS-level window objects. Except, OS window objects are part of an algorithm that tracks exposure regions and repaints it efficiently without needing to redraw the whole screen. Swing took the approach of repainting the entire application window in a back-buffer on every visual change and then copying that up to the entire application window area, even for things as small as tooltip pop-ups or menus.

I haven't checked which GUI framework DBeaver is using. I suppose it's possible that it is Swing and my workstation is just so fast these days that the inefficiency doesn't matter.


I think you just don’t realize when a given software is Java. I personally really like intellij, one might say it is “bloated” (though I hate that word), but that’s only because of indexing everything, not due to java itself.

On the server front many cloud infrastructures themselves, apple servers, pretty much every top 500 company has some form of business critical infrastructure chugging along on top of the JVM happily.


Oh no, I realize what software I use is Java. Swing feels bad to use. On my workstation at least, JetBrains IDEs are slow, I haven’t used it in a long time, but Eclipse was slow, NetBeans was slow, there’s an enterprisey Java web start application I need to use at work and that’s slow. Like I said, Minecraft is the only piece of software written in Java that I enjoyed using.


I think java is geared towards server applications because the JRE is so finicky about memory and other machine level details you can only control on your own services

Most major web services have java microservices that take on the performance critical and logic intensive parts of the business


Have you tried Jetbrains stuff?


I have. Maybe I don’t have enough RAM for it, but I find their IDEs to be slow and laggy.

Xcode and Visual Studio Code feel so much snappier on the same machine.


Take some time to learn the navigation and refactoring abilities of the JetBrains family. It is IMHO unmatched by most. Using almost any other IDE feels like a downgrade, especially on large codebases with complex dependencies. Beyond Java, they have excellent support for Python, C#, Go, Javascript, and more. The engine builds a deep understanding of your code, which can make ctrl-space to suggest a method on an object feel delightful (and a Godsend on big Java names).

I also strongly prefer the keyboard shortcut set JetBrains uses. Having to reach all the way up to my function keys for combo operations makes me sad; even when I use other IDEs I love using an Intellij keybinding when available to quickly jump in and be efficient.

But to your point, I also tend to use it on higher end workstations (i.e. minimum of 16GB RAM, local repo pulls on fast SSDs, tons of logical cores, etc.).


Used JetBrains for more than 10 years, but got tired of it lagging all the time and using so much memory (even on M1 Pro with 32GB RAM, even on small projects). So I switched to VSCode for everything except Java. And I’m not a person who is easily annoyed I would say.


They seem to have fixed a lot of the weird lags recently. Right click context menu used to be slow, and the python debugger had performance issues for sure up to a year or so ago. Both way better now


I used VSCode for JS for a while, until a major refactor, the experience was awful and I switched to Intellij. I love it and never going back.


I find it very weird that Xcode is faster than... anything, really


It may be faster than.. visual studio.


It IS faster than JetBrains, at least on my machine.


They limit the usable memory way too low by default — if you have RAM increase it to at least 2GB, but 4 may be even better and it will be snappy as hell.


Android apps are full of Java.


I was an Android user for years, iOS and most native iOS apps feel more performant and less laggy to me.


Java doesn’t enforce any particular style. I’ve seen extremely procedural code that is full of statics where it’s obvious the authors were attempting to write C in Java. I’ve seen all manner of attempts at OOP where classes were meticulously restricted to nouns and the opposite where every class was a Service/Verb. Of late I’ve seen Java server side code that’s drank the reactive kool aid and done it’s level best to recreate NodeJS in Java.

Now, your assertion about scaling to more engineers may be true but I’d argue tooling is the main reason for this because Java certainly doesn’t enforce any particular style of programming.


Have you tried C#? It looks a lot nicer to work with than Java.


I'm using C# and Java professionally. I've been using for a long time while I'm newish on C#. Also I'm on a older version of .net vs. a modern Java. Honestly to me the language doesn't feel that great. It always feels sluggish, to work with, like I'm fighting against the language. And then there is the ecosystem, Spring Boot is just such a breeze to get a web app running with all the integrations you could ever want being just there. Add in Lombok and Apache commons and it's a real pleasure to develop in Java for me.


The ecosystem is nowhere near as mature though. I don’t work with either anymore but back in 2017 I made the switch from C# to Java and it felt like a breath of fresh air when it came to the maturity and capability of JVM tooling compared to what’s available for .NET.


Try JetBrains Rider, and be sure you are using a recent flavor of dotnet. When I migrated past 4.x to 6 of the .Net ecosystem, it dramatically improved my ability to work and deploy in C# with their rather delightful build system.

For example, in the Monogame game library, you can build a self contained binary for Windows, Linux or MacOSX nearly effortlessly with just a single command line.


But these executables are quite huge, are they not?


Could it be any worse than an Electron application?


The dotnet ecosystem is incredibly mature. Its as old as java in most tooling cases, IDE, Language, Build System etc. The runtime is the newish part.


The ecosystem is certainly more mature than many smaller languages, but it is still in a different league than Java’s. Most of it is not too great copies of the corresponding Java library, often being made by Microsoft only, with plenty of paid options while in the java world all of it is open-source and free, while offering a much wider selection.

Also, you will find a java library for that random new tech you want to use, while it is likely missing for .NET.


I'm curious, what kind of tooling are we talking about?


Interesting. Did you try Jetbrains Rider as an IDE?


https://github.com/EnterpriseQualityCoding/FizzBuzzEnterpris...

On a more serious note, most Java code on Github is now written by Copilot.


In javaland, the actual ideal is somewhere in the feature set supported by Groovy. CompileStatic groovy is probably the best, you get a lot of good features for no performance hit.


Java was the language I used in university. While it may be well structured, I hated it as a junior level dev. There’s just so many unnecessary classes and abstractions to accomplish basic stuff.

It makes sense in large applications with experienced developers, but it sucks to learn.


It was very sparse with any syntactic sugar or ways to shorten common operations. Now it's much better, especially if you eschew the 00s style of programming - with obligatory getters and AbstractSingletonProxyFactoryBeans.


My experience with languages is that people want more exotic languages as they gain experience, than they grow away from them and go back to pragmatic ones. I think Java strikes a great balance here, and while I also had a phase where I thought how much better Scala is for example, I can appreciate java much more nowadays and will default to it for most projects.


Yes. I have been burned by this in C#, it’s very frustrating.


you can step directly into System.* source as well...


Go and it’s standard library. ‘Elegant’ is pretty subjective, but it’s a treasure trove of learning how things work under the hood. I’ve learned loads about networking, compression, encryption and more by browsing through it, because the code is super easy to read and understand.


What makes it easy to read and understand though? I am seriously having a hard time figuring this out. People tout Go for this all the time, but I don't know of a single codebase in it that I think fits that description. When I look through them they look convoluted and just sort of messed up. Things like awkward error handling, dealing with null, capitalization for public/private, magic functions, and imports, and much, much more all add up and make me abhor the language. I don't think it's good or easy to use at all, but people rave about it.


Speaking for myself, the language itself is simple. There aren't a lot of features, which means you do have to write more and it's more verbose, but learning the entirety of the language's features is very easy to do.

Even with the relative magic of things like init functions that execute on import, there's so much less magic that you have to consider.

IMO it's the easiest to jump into for this reason. Yes, the code itself might be excessive, but reading Go is as simple as can be.


I'll echo this. When I'm looking at a Go codebase that somebody else wrote, it's a minimal effort to understand what it does. Rarely, if ever, do I scratch my head at a particularly clever type derivation or obscure language feature; macros are pretty much non-existent; even user-defined types are easily reduced by the IDE and language server. Patterns are standardized and yes, it's verbose, but predictably so. If something calls for containerization, it's dead simple. Go is a language for getting things done straightforwardly.

I know it's not everybody's cup of tea, and that's fine. There's room for different languages in the world. But I'm knocking out useful utilities that make a difference for my team and business in days or hours, and supremely uninterested in code golf, so I don't personally agree with the criticisms.


> People tout Go for this all the time

What gets me about go is 2 things.

Its touted as being so easy that a junior dev can pick it up easily; it's targeted towards average developers. Fine, this is a virtue; when Java said the same thing, it's a horrifying blight.

The other is that people seem to mistake motion for action. "The code flies from my fingers" is one way I've heard it said. And, sure, you have the same error catching boilerplate (which again, in go is a virtue but other languages seems to be considered a sin) 1000x, as if the clicky-clicky of the keyboard is some measure of productivity.

It's got a big "blub paradox" thing going, to my eyes. I don't find it elegant at all, or maybe I mean not very expressive.

Taken ad absurdum, I have a language that only adds 1 to a variable. I can understand that language in milliseconds. But I can't do much with it. Maybe go hits a good balance, I dunno, but I found it quite tedious.


It’s the complete lack of magic. What you see in front of you is pretty much exactly what happens. You don’t have to keep a cathedral of language semantic subtleties in your head when reading someone else’s code.


Pointer vs value receivers and named returns have so many gotchas that it is not even funny. Lack of magic my ass.


The way you avoid these are twofold:

1) Use the pointer receiver unless you have a really good reason to do otherwise.

2) Never, ever use named returns. Code can (and should) always be written to not use them.


Can you elaborate point 2, please?I am wondering how is that related to the issue of pointer and value semantics.


Can you name any? I have never seen a “gotcha” because it’s just explicit… it’s not like you are surprised by a pointer.


Then why don’t we go back to assembly? There is even less magic there, every line is trivial to understand, isn’t it?


I love Go. I think it depends on what trajectory you followed to reach to Go or any other language. For me it was

BASIC -> VB -> Java -> Python for some time -> Go

How you feel about Go is how I feel about JavaScript


I went Pascal, C, Perl, Python, Go

And I like Typescript to some point.

I do not think they languages are mutually exclusive (on the like scale). But I am just an amateur hobbyist dev.


That’s because JavaScript is an awful language and I just don’t understand why people keep insisting on using it for everything. It even infected infra as code.


That’s because it is easy to use. Maybe you use too much python or Java but go was designed to specifically allow people to memorize the entire syntax, truly.

Want to make a function or variable or field public? Just capitalize it. That’s it.

Error handling? Check if the error isn’t nil and handle it, otherwise move on. No need for silly things like try except.

And there are no magic functions because everything is explicit.

Go is just simple and pleasant to use.


Try except isn't silly it shortens the code a lot. An exception can simply break out of a function, checking for error requires an explicit check at every line of the function and an added return statement to get out of the function.


(Opinions are my own)

At my employer we use a subset of C++ and we use Go. We have a process by which when you write code others have to review it and you need to have a review by someone who is an "expert" [0] in the language [1]. You become an "expert" by being ordained by a shadowy committee who reviews code you submit to the code repository. They look for knowledge of the core language, how this language is used within the company, the external and internal libraries, performance, testing, etc. There are many factors and if you demonstrate all of them you get marked as being this type of "expert."

Before I joined this company I had written code which was launched into production in the following languages: Java, PHP, C, C++, assembly (arm + x86), Python, JavaScript (browser + node), and a few more. I would consider myself about average in all of these. I did not write any golang.

After I joined my current job I obtained this "expert" bit for both C++ and Go. It took ~1.5 years to get the C++. It took ~3-5 months for Go.

You can actually see the first golang code I wrote (this was at home when I was experimenting with the language before convincing some team members we should rewrite some of our infra in go): https://github.com/gravypod/gitfs

It has all sorts of mistakes but I didn't read any guides. I just used https://cs.opensource.google to search for examples of things that I thought I would need to do (ex: "how do I do a switch statement").

For C++ I had worked on ~2 projects that used it. My first few PRs were very rough and I had a lot of performance issues that crept into my code. If I didn't already have a lot of C experience I would have also had a bunch of pointer/lifetime stuff the reviewers would have found (I know this from reviewing new team members first lines of C or C++).

I know that to some C++ represents a literal worst case but most people coming from C++ to Go will think it's amazing because it removes all of the common footguns.

> Things like awkward error handling

Yes, it is very clunky and annoying but it's very simple. It's just a normal if statement and doesn't use any special language rules. I think this would still be better if there was dedicated syntax for it (something like throw/try/catch which works the same way but gives it a different syntax) but honestly I don't think it's as bad as it's made out to be. It's basically a "less bad" errno and that worked go-... dece-... ehm fine for many years.

> dealing with null

I've never really had to think about this too much. There are some times it is important but I rarely return nullable things without errors and it hasn't bitten me yet. My code is not provably correct but for the things I'm working on I don't need that guarantee. If I did I'd probably switch to Rust or something with better type safety.

> capitalization for public/private

Yea, this sucks but it doesn't really get in my way much. I don't like it but it isn't actively hurting my usage.

> magic functions

Like `String()`? I don't know if that's the worst think in the world. Python, C++, and Java have things like this.

> and imports

It's not been too bad for me. What I think is unfortunate is that the package of something is unconnected to where it is in most go usages which is annoying but it makes things more terse. This does actually hamper my productivity.

> I don't think it's good or easy to use at all, but people rave about it.

It's pretty easy to use because all of the libraries I've seen share common interfaces for behavior. This makes things feel a lot more cohesive. fuse-go and billy was very easy to use in gitfs because of this.

[0] - This is not an expert as in "knows everything" but more like "has been seen to consistently write efficient, simple to understand, idiomatic code." It basically means that when someone else from this subset of SWEs reviews your code they often do not have many comments. Again, I want to stress, this is not expert as in "knows everything" just as in "good enough".

[1] - https://abseil.io/resources/swe-book/html/ch03.html#what_is_...


Well, c++ is literally the most complex language, famously not even Stroustrup would say he knows the whole, so comparing go to that hardly makes it look good.


Is there any programming language that is universally seen as objectively good?


No, because the different trade-offs they make all have costs and benefits. For example, C’s precise memory management can give better performance compared to PHP, but also requires more expensive programmers to work with it. If all you’re doing is a simple CRUD system, C’s power would be counter-productive, so PHP is a “better” language in that context.

So a “good” language depends on what you’re trying to do with it.


I remember with smug satisfaction a time that I was able to settle a pedantic argument from a so called "security expert" by pasting the code from the library function he was questioning.

Very satisfying to be able to say "nope, it's fine, here's the source".


I find the Golang standard library code annoying to read and understand because of their use of single letter variables or very short abbreviations. I know some people like this but I don’t.


The single letter variable is only supposed to be used within a relatively short function or code block. They should be relatively obvious; I personally find this to work well, but I can understand where sometimes it wouldn't be clear what the author was referring to.


RT-11 on the PDP-11 (all in PDP-11 assembler). Back in the early 80's you could rebuild it in several different ways, depending on whether you wanted it "single job" (as it was back then) or not.

As an example, here's the PDP-11 assembler to convert a binary number to decimal ASCII (no idea who wrote it, but they certainly made every word count):-

  CNV10:  MOV     R0,-(SP)     ;Subroutine to convert Binary # in R0
  1$:     CLR     R0           ;to Decimal ASCII by repetitive
          INC     R0           ;subtraction. The remainder for each
  2$:     SUB     #10.,@SP     ;radix is made into ASCII and pushed
          BGE     1$           ;on the stack, then the routine calls
          ADD     #72,@SP      ;itself. The code at 2$ pops the ASCII
          DEC     R0           ;digits off the stack and into the out-
          BEQ     2$           ;put buffer, eventually returning to
          CALL    CNV10        ;the calling program. This is a VERY
          MOVB    (SP)+,(R1)+  ;useful routine, is short and is
          RETURN               ;memory efficient.
Courtesy bitsavers.org (http://www.bitsavers.org/pdf/dec/pdp11/rt11/v5.6_Aug91/AA-PD...)


So many, I like reading how other people write code.

R - sf package is a clean example of functional OOP

Python - pytudes (Peter Norvig’s notebooks)

Haskell - Elm compiler. I could mostly understand what’s going on even though I barely know any Haskell.

Ruby - Sequel is really nice.

Rust - Ripgrep

Pretty much any F# codebase is super readable too.


> R - sf package is a clean example of functional OOP

Funny because I detest it because of how difficult it makes it to dig into and customise spatial data and visualisations at a low level like I am used to with the spatial packages it sort of supercedes


+1 on F#, highly under-rated language IMHO.


Do you have any F# favorites? People often mention jet.com repos, but I’m interested to hear about others.


Jet.com has a lot of good ones yeah. One I was looking through the other day is a GitHub repo under /ScottArbeit/Grace and it’s an interesting take on version control. It was a pretty cool repo to look through. To make it easier though, remember that F# source code files are all “in order” so you read them from top down, which Github doesn’t currently have functionality for.


For folks coming here later, you can figure out the order that you should view them in by reading into the `.fsproj` file, which will lay out compile units in order.


Shewchuk’s Triangle code for Delaunay mesh generation is some of the most elegant C-code I’ve ever seen [1]. It even won the SIAM Wilkinson Prize for numerical software at the time it was written. It’s written in a literate style, and builds up from the most fundamental arithmetic operations and data structures, all the way to one of the most efficient mesh generators of its kind. He has a few other codebases written in a similar style [2, 3]. It’s very different from what you see in the wild, but it’s been great for understanding what’s happening under the hood for complex algorithms like mesh generation.

1. https://www.cs.cmu.edu/~quake/triangle.html

2. https://github.com/ctlee/Stellar

3. https://www.cs.cmu.edu/~quake/robust.html


Working with Perl, two things spoiled me for other languages: JSON and DBI/DBD.

In Perl, everything serializes to JSON without fuss. It can be "lossy"; objects without an explicit JSON serialization method and coderefs can't be deserialized, but serializations at least have placeholders for them.

Compare to Python's json module, which doesn't try very hard to serialize things and throws exceptions every time it runs across something new. It's very frustrating to use.

Perl's DBI provides a universal API for all databases, with implementation-specific details in an underlying DBD module (which both provides glue between the DBI abstraction and programmer access to features specific to different database systems).

Compare to Python, where you need to import a different module and use a different API for every different kind of database. As I increasingly use Python for a living, I frequently wish they'd follow Perl's example with this.


Ruby, being a Perl-inspired language, has `.to_json` built in. You can do

```rb

   # hashes
   { foo: 'bar' }.to_json
   
   # numbers
   28.to_json

   # anything really
   ['hello', 42, { lorem: "ipsum" }].to_json
```


That’s simply not true. This method is monkeypatched by json gem


JSON was added to Ruby stdlib in ruby-2.0.0 (2013), and has been a default gem since ruby-2.3.0 (2015).

This is pretty close to "built in", I think.


You're both right, I think.


Funny enough, but I've come across some really nice Perl code in the wild at work. I was used to the vendor providing some 40 class Java monstrosity to do something that should take like a page of code, so I was pleasantly pleased to find a contractor who provides an extremely well commented page of code to do something simple, yet critical to operations. The way Perl calls the OS to do something and glue everything together was pretty elegant.


> Compare to Python, where you need to import a different module and use a different API for every different kind of database.

You... don't. Python has a unified DB api (DBAPI 2.0) which drivers usually support. They often also provide a lower-level API specific to the DB.


You might really like Ruby! It's part descended from Perl and maintains a lot of the nice things about perl such as json, and the amazing string functions.


I tried very hard to like Ruby. "On paper" it looks great, but I had a lot of trouble getting used to the syntax.

I ended up going deep on the D programming language for my "new language". As a statically typed language it's not as expressive as the Python/Ruby/Perl contingent, but it's a lot more expressive than most static languages, and its C-like syntax "clicked" with me in a way Ruby never did.

It also can approach C-like run-time performance and memory footprint at times, which I appreciate. As much as I like developing in Python and Perl, I frequently wish they had better run-time performance and a smaller memory footprint. D gives me that, at the cost of a little expressiveness.


The only thing about the JSON package though, when things go wrong, it is very unhelpful about where it goes wrong.

I usually end up always wrapping the json_decode in an eval to catch the error and handle it in an easier to understand fashion.

But I agree though, its nice how json and perl data objects pretty much map to each other. It's great.


Omg the python stdlib json / simplejson both refuse to support custom serializers for keys only, as an explicit design decision. It is justified as "JSON keys must be strings", but JSON values can only be string/float/book/null so it seems a bit arbitrary. Leads to annoying gymnastics if you want to enforce "strong typing" of keys with Enum/pydantic/etc.


> In Perl, everything serializes to JSON without fuss. It can be "lossy"; objects without an explicit JSON serialization method and coderefs can't be deserialized, but serializations at least have placeholders for them.

> Compare to Python's json module, which doesn't try very hard to serialize things and throws exceptions every time it runs across something new. It's very frustrating to use.

Sounds kinda backwards to me. I thought the fact that throwing exceptions (or "making a fuss," if you will) is better than silently producing incorrect (or "kinda lossy," if you will) results wasn't controversial anymore in 2023.


> universal API for all databases

Go has this too, very handy:

https://godocs.io/database/sql



Hmm, upon closer investigation the only one of these that holds up is:

https://news.ycombinator.com/item?id=13624926 (2017; 98 points; 67 comments)

I feel sure I'm missing a lot. This subject seems to come up every few months or so.


C++ this file covers all the math for working with NURBS curves and surfaces:

https://github.com/solvespace/solvespace/blob/master/src/srf...

There is a lot more in other files - triangulation, booleans, creation - but the core math functions are there in very readable form.


For Lisp I would recommend Edi Weitz's CL-PPCRE: https://edicl.github.io/cl-ppcre/

Pretty much anything else from Edi Weitz is also great.

Mezzano is quite elegant in my opinion, especially for an operating system. For example, this is the USB mass storage driver: https://github.com/froggey/Mezzano/blob/master/drivers/usb/m...


CL-PPCRE is great


Back when I was starting out, it was nice that Backbone had such clean, well-commented code: https://github.com/jashkenas/backbone/blob/master/backbone.j...


Indeed! jQuery as well, before the breakup into modules.


I really liked reading the source for underscore as well.


I really like Pandoc codebase [0]. It is a document converter written in Haskell.

Reading it’s source code a decade ago was a turning point for me. Prior to that, I always felt an insurmountable gap between my toy codebases and real projects. All those open source software written in C++ etc. looked so unapproachable that I felt like I could not write production ready software.

Pandoc however, was written in a language I didn’t know and did something very complicated very thoroughly, yet remained accessible. It was very nicely laid out and I could easily follow how it constructs it’s internal representation of documents and converts between them. I think this made me catch the functional programming bug for the next decade that let me build way bigger things than I had any right to, without getting crushed underneath all the complexity.

Putting together something in Java or even contributing to OOP Python codebases was still like an exercise in frustration, no matter how much better I thought I’m getting at programming I would feel stupid trying to wrap my head around those abstractions and hierarchies. Somehow FP just clicked for me and made me see how I could start from a simple library call and little by little build the complete program.

Today I am comfortable with all kinds of paradigms and levels of abstraction, but I definitely owe a lot to Pandoc for showing me I was smart enough to understand and modify real world software I did not build myself.

[0] https://github.com/jgm/pandoc


Just took a glance and it looks interesting (first time reading Haskell) - thanks!.


At the beginning of the year I was rewriting a SPA and looking for ideas on how to structure a web app. One project I looked at was Github Desktop and I think it has very clean code for an app.

https://github.com/desktop/desktop


Now if only GitHub desktops actual UI/UX wasn't a poorly thought out mess of anti-patterns and anti-design.


I use it daily and it works great. It doesn't do all that much, but what it does do saves me a bunch of time. I reach for the git CLI when something goes wrong, but that's not often.


What's wrong with it?


It completely ignores the simple UI paradigm of tabs or a sidebar. You should be able to move between repos without blowing away whatever you're in the middle of. I'm forced to be in one at all times, and I can't manage multiple repos at once via a simple sidebar. It's like it takes all of the inherent arcane complexity of Git and creates a UI that is so barebones it almost mocks you for deigning to ask for a GUI.


Interesting to know, thanks!


Thanks for recommending this, I just browsed some files online and it's looking indeed amazing.

P.S. It's now easy to check a repo file by replace .com with .dev: https://github.dev/desktop/desktop


You can also just click the . (period) key when viewing any repo.


I've really enjoyed reading (and playing with) kons-9's codebase in Common Lisp. It lets you do exploratory 3D modeling via the program's GUI or the repl. The source is very neatly structured and readable. I don't see many CL projects that do 3D rendering, so it's nice to see!

Quick demo:

https://www.youtube.com/watch?v=i0CwhEDAXB0

Repo:

https://github.com/kaveh808/kons-9


For C, I've really enjoyed reading the Ruby source code. There are good and bad spots, but overall especially if you know Ruby the language, the source is both entertaining and enlightening.


Is there a good guide that covers that codebase? I'm very familiar with Ruby but I've never dived into the C code and I'm not sure where to start.


Probably helpful to understand the API first before understanding the implementation. There is a well known guide here: http://silverhammermba.github.io/emberb/


I’m surprised that nobody has posted about Elixir yet. I nominate the excellently written Phoenix library. Not only is the code well organized and easy to find, the documentation is expansive and right next to the code.

https://github.com/phoenixframework/phoenix


Redis is a popular answer for C, and I agree.


I was going to say this too. C is more my "consistently appreciated" language than ever my favorite of the moment, but the Redis codebase is a fantastic example of it that's very easy to digest.


I don't know if elegant is the word, but I often refer to the Hashicorp repos for Go, and specifically admire Mitchell's own. Very clean, well written code most of the time.


C++

An old one, but the FTGL library (renders truetype fonts in old-school OpenGL in half a dozen different ways: texture-per-letter, texture-per-word, 2D polygons, 3D polygons, etc) is the best example of C++ inheritance I've ever run across. The code formatting isn't my favorite, and comments are sparse, but the hierarchy of objects subclassed for all the different rendering modes is just about perfect. https://sourceforge.net/p/ftgl/code/HEAD/tree/trunk/

Perl

The Mojolicious / Mojo toolkit. Great minimalist API and great documentation and clean code all around. https://metacpan.org/release/SRI/Mojolicious-9.33/view/lib/M...


arthur whitney's famous first J interpreter.

https://www.jsoftware.com/ioj/iojATW.htm

The first version of KDB the timeseries database was written by arthur in C to bootstrap the K interpreter that was used to write KDB. It was 26 files, named a.c to z.c, none larger than a single page of C written with notepad.exe.


C++ isn't my favorite programming language anymore.

I guess the Doom 3 source code is an elegant codebase. Surprisingly, they used C++ features quite sparsely.

I think that’s nice because in programming it’s about getting the job done and not about using all sorts of features for other reasons.


fs2 (reactive streaming, https://github.com/typelevel/fs2) written in Scala. It shows how nicely things can compose in a typesafe way if the language supports it.

And then, the opposite is Monix (https://monix.io/) also written in Scala. It's also about reactive streaming and the API is great, but the internal code is ugly because it sacrifices readability/composability for performance.


Php and Laravel


I`ve seen so many posts and comments about Laravel and how it has made PHP a modern choice for webdev.

As someone who has written many small apps in PHP, I might dive into it and finally see what that Laravel thing is all about.


I'm currently using Laravel at work. It's very opinionated, and some folks say it uses anti-patterns with regards to its use of facades. That being said my last job was C#/.Net and I am so much more productive with Laravel. It really allows you to develop quickly and I haven't yet bitten by any of the "anti-patterns". If you give it a shot I'd recommend just using Laravel Sail as, if you already have docker installed, you can have a full dev environment setup in less than 10 minutes.


> It's very opinionated

It is and it isn't. It does opinionated ways of doing things. But IMO what makes it so great is just how easy it is to opt out of the opinions you don't like. Facades are an excellent example of this: don't want to use them? Well, you don't have to (and IMO a really big app that may be a good choice - in a small app it likely won't matter and you might as well use them).


To me, "anti-pattern" has the same bogus meaning as "clean code"


Although at a high level many of things things are subjective, this take is almost entirely wrong in every dimension.

Anti-patterns are things like using a wrong data structure, using the wrong levels of abstractions, tightly coupling components so they are not composable, leaky interfaces, god objects doing too much

The strict definitions of many of these can be subjective at the edges, but they all objectively exist and cause fragility, instability, inflexibility and maintenance problems in the systems built from them.

Clean code is code that’s easy to read, has the right level of abstractions, uses the right data structures and has the minimal possible anti-patterns in them (ideally zero!) above.

Calling these things bogus is unfair, I grant they can be subjective in some places but they are prevalent in poorly designed systems especially by junior engineers.

Wikipedia page on anti-patterns: https://en.m.wikipedia.org/wiki/Category:Anti-patterns

There are project management anti patterns too https://en.m.wikipedia.org/wiki/Anti-pattern

Anti patterns are real. Clean code is real. If you cannot see that, I would suggest reading a lot more codebases from open source projects (pick medium and large codebases, not trivial programs) and after 10 or so you will see obvious structural and quality differences, as well as hundreds of anti patterns and examples of clean code.


I'll agree with everything here except the clean code. Clean code is about optimizing human perception and there can't be a standard for that because humans think in a wide variety of ways and it's further impacted by the level of understanding the human already has on the subject matter the code is dealing with. One person's "clean code" can be another person's nightmare.

I'll back this up with the example of Magento 1. It's a PHP e-commerce platform that has (at first glance) some of the cleanest code you'll ever see in PHP. It looked like the entire development team had come from a Java background. Every component was neatly divided into a PHP object with documented private and public methods. There was a clean MVC separation, with lots of shared behavior abstracted into "Helpers", and a Theme system handling the rendering of the front-end. I have no doubt that the authors of Magento prided themselves on how clean their code was. For them, having spent full-time careers structuring all the many features of their platform into these files, it probably did feel like a clean organization. And when I initially reviewed the code to evaluate using Magento, I also thought it was clean and was part of my choice to use it.

The problem was that when you take something as complex as a full-featured e-commerce system and modularize it so thoroughly, you end up with a literal 7000 classes, and it becomes impossible to figure out the sequence of execution of a single page request through that massive tangle. Is it "clean code" if I have to add debugging print statements to 57 source files to figure out the path of execution that renders a single page?

If I had to choose a circle of hell where I would edit Cyrus IMAP (the worst C code ever) for the rest of eternity, or edit Magento for the rest of eternity, I think I would actually choose Cyrus.


> Anti-patterns are things like using a wrong data structure

What is a "wrong data structure"? Is it wrong to do linear scans when hash access would be sufficient?

> ... using the wrong levels of abstractions

When is the abstraction level wrong? I can name you at least 10 projects that avoid so called anti-patterns by introducing unecessary abstractions. Is something really an anti-pattern if it's "solution" massively reduces your development velocity but now everything is nicely composable?

In my opinion, anti-patterns are either obvious (constantly using different names for the same thing) or totally subjective to the context (when to repeat yourself).

But maybe I'm not able to put myself into the shoes of novices and a lot of things seem obvious to me. Granted.


> What is a "wrong data structure"?

I've seen people use multiple named arrays, search for something in the first array, then use its index to find matching data in the other arrays, instead of a dictionary of string:tuple.

Another example is languages with arrays and vectors, usually one or the other is preferred. In Go you can use arrays but you're supposed to use slices whenever possible, while the opposite would be appropriate in, say, C.


This is a solid argument, thanks for taking the time to write this out!


That's an interesting take! I'm still early in my career and I ask with genuine curiosity, but why do you think "clean code" has a bogus meaning?


Not the OP, but clean code misses the point. Its is very subjective and depends on one person's previous experience and patterns they've been exposed to.

"Reasonably readable" is what I strive for nowadays, and a key aspect is that I no longer think there is an objective measure for it. It depends on the team/company you're in, and its important to keep in mind that the goal is to effectively communicate the program to them.


I suggest you read malux85's comment: https://news.ycombinator.com/item?id=36371733


Also Carbon. It makes working with dates and times (something which is by it's very nature a PITA) actually enjoyable and easily readable.

I also really appreciate FakerPHP for how easy it is to generate realistic fake values.


Really enjoyed reading through kbin as a Symfony fan. https://codeberg.org/Kbin/kbin-core


mentioned in this thread:

C

* Lua https://www.lua.org/source/

* Redis https://github.com/redis/redis (mentioned twice)

* Ruby https://github.com/ruby/ruby

* SQLite https://sqlite.org/src/dir?ci=trunk

C++

* Botan https://github.com/randombit/botan

* ClickHouse https://github.com/ClickHouse/ClickHouse

Go

* Go's standard library https://cs.opensource.google/go/go

* HashiCorp repos, particular those by Mitchell https://github.com/hashicorp

F#

* jet.com repos https://github.com/jet?language=f%23

Haskell

* Elm compiler https://github.com/elm/compiler

Lisp

* CL-PPCRE https://github.com/edicl/cl-ppcre/

* Mezzano USB driver https://github.com/froggey/Mezzano/blob/master/drivers/usb/m...

PHP

* Carbon https://github.com/briannesbitt/Carbon

* Laravel https://github.com/laravel/laravel

Python

* pytudes (notebooks) https://github.com/norvig/pytudes

R

* sf (ex of functional OOP) https://github.com/r-spatial/sf

Ruby

* Sequel https://github.com/jeremyevans/sequel/

* Sidekiq https://github.com/sidekiq/sidekiq

Rust

* ripgrep https://github.com/BurntSushi/ripgrep

Scala

* fs2 (ex of good type safety) https://github.com/typelevel/fs2

* monix (ex of ugly code with great performance) https://github.com/monix/monix

TypeScript

* GitHub Desktop (ex of SPA) https://github.com/desktop/desktop

---

thanks to: cejast, bb86754, wewxjfq, antonyt, bit, diego_moita, agjmills, freedomben, Contortion, valenterry, DethNinja, mberning, seneca


C -> Lua, Sqlite


Guava -> In Java

Golang Stdlib -> Golang

redis -> C

anything by armin ronacher -> Python


Armin Ronacher is definitely one of the engineers you should follow on GitHub, especially if you're writing Python or Rust. That guy is a genius at what he does.

Oddly, even though he wrote one of the two most popular frameworks for Python, Wikipedia still claims his entry doesn't meet notability requirements.


Anyone have any good clojure examples?


I try not to toot my own horn, but I wrote this little quadtree library that tickles that elegance part of my brain. I try very hard to write elegant code. I have other Clojure repos, but they suck. :P

https://github.com/janetacarr/quadtree-cljc


Anything by James Reeves aka weavejester (https://github.com/weavejester).


Metabase's toucan (https://github.com/metabase/toucan) has some elegantly annotated source code: https://rawgit.com/metabase/toucan/master/docs/uberdoc.html


[C#] Bitwarden server repository is probably one of the cleanest (non-novel) solution architectures I have seen so far. I always point people to it as learning material for structuring the code. It is not the most minimalistic but I feel like it strikes very good balance and does not follow blindly all the """fancy""" OOP patterns people should never use anyway.

https://github.com/bitwarden/server

Otherwise, I can see why people are burned, average Java/C# codebases look abysmal and written without understanding of (not) using heaps of mediator/factory/adapter/provider classes.


The various flavors of Forth all qualify. They are great examples of how to bootstrap towards a powerful abstraction, starting from a relatively simple context. The 80% of the 80/20 rule here comes from "writing a Forth" being an engaging learning experience.

For anyone who would like to do that, I recommend looking up one of the old standards(FIG-FORTH, FORTH-79, FORTH-83) and implementing the words in them with whatever tools and languages you like. You will hit a point where your early assumptions about the implementation are wrong. Keep going, get it to the point where you are capable of using the metaprogramming words.


https://github.com/lua/lua

Everything is nicely documented and pretty easy to read.

It's a great companion if you want to learn more about how languages are implemented.


There were 3 different libraries that impressed me:

1. The SunOS headers. Couldn't see the code but the number of header files was small enough in the 4.x Sun libraries that you could read them all. Mostly the documentation was terse but information dense.

2. The TeX sources. Knuths literate programming seems like such a missed opportunity.

3. ParcPlace VisualWorks. Due to the nature of Smalltalk you could read all the source code, learn object patterns directly from the people who invented it. A great learning experience when transitioning from C and so much better than the cfront based C++ hack.


What I find to be elegant in a codebase is where the chosen abstractions or seams that separate subdomains/concerns is well chosen that each is handled mostly in one place without a lot of ceremony or machinery. I would call these 'well factored' for factors which are domain-specific.

Each language has different ways that may lend itself as part of this shaping, but I like being able to think of this as something to look for when reading and strive for when writing, irrespective of the language at-hand.


Ruby - Devise. A beautifully functional gem that also makes customization of its magic really easy. Also ActiveRecord, as it's just a delight to read.


I found Zig implementation of json parsing is interesting. The code is free from hidden control flow !.

https://github.com/hanabi1224/Programming-Language-Benchmark...


Peter Norvig's Advent of Code solutions in Python. e.g., for 2022 - https://colab.research.google.com/github/norvig/pytudes/blob...


I nominate SDL2 and DPDK. Spent a lot of time combing through these code bases, found them to be excellent.


Back when I first was learning about GraphQL in 2016, I remember thinking the reference implementation in JavaScript was extremely clear, easy to read, and well organized. It had a "wow, I wish all the code I read was this good" feel to it for me.


The TurboVision library that came with Turbo Pascal was awesome. Borland really had their shit together back in the day. Then they got greedy and overpriced their product, and killed the community.


I think FreeBSD code in C is very well organized:

https://github.com/freebsd/freebsd-src


C++: ClickHouse. It is very readable and easy to navigate. Call stacks that you pick up in logs are very descriptive, and you can easily tell what went wrong.


gorilla.bas



Ruby - Sidekiq


Not sure if it's still the case but about 6 years ago Facebook's folly C++ library was something I'd point to for my junior engineers to get a sense of "good" C++ https://github.com/facebook/folly


Not my favourite language, but LevelDB (written in C++) is really great.


C++ - Botan

C - Redis


Open Hardware Monitor (OHM), in C#


Swing in Java obviously


Envoy proxy for C++


That's quite an indictment of C++. I concur but still.


My own ( c# ). It's not opensource yet, monetizing it first.

Full DDD, it was a refactor during COVID-19 for my ecommerce.

It powers https://belgianbrewed.com

Copy paste from: https://news.ycombinator.com/item?id=35257225

> But I believe the project is much cleaner and frankly better to understand than all other projects i've encountered for this size. I'm using DDD, so DDD knowledge is a requirement to navigate this in a breeze :) :

- https://snipboard.io/D03VWg.jpg - General overview of the architecture. Small fyi: Connectors => Autogenerated nugets to call the api's

- https://snipboard.io/9M24hB.jpg - Sample of Modules + Presentation layer

- https://snipboard.io/ybp6EH.jpg - Example of Specifications related to catalog ( = products )

- https://snipboard.io/lE9vcK.jpg - How specifications are translated to the infrastructure ( here I'm using EF, so I'm using Expressions a lot), but plain old SQL is also supported. A query is basically a list of AND/OR Specifications where a hierarchy is possible. This would translate to "(QUERY 1 ) AND ((QUERY 2) AND (QUERY 3))" in the Infrastructure layer.

- https://snipboard.io/7rVBpk.jpg - . In general, i have 2 List methods ( one for Paged queries and one not for Paged queries)

Additional fyi: Is V2, so has some legacy code. Uses my own STS. Has 2 gateways ( the ShopGateway that is used to develop new sites and the BackendGateway for the Backend). Enduser frontend is in MVC for SEO purpose, Customer backend is in Angular ( SPA). The basket is a NoSql implementation on top of SQL server.

The enduser frontend supports a hierarchy of themes ( so it's insanely flexible to create variations of pages for other clients).

There are more projects involved outside of this solution, eg. nuget repo's usable accross solutions (JWT, Specifications, ...) and "plugins" for a standalone project that is installed for end-users for syncing local data. So it's +101 projects :)

Edit: my specification implementation has been open-sourced here: https://github.com/NicoJuicy/Specification-Pattern-CSharp

Someone was curious to see it.


Look at that subtle off-white coloring. The tasteful thickness of it. Oh, my God. It even has a watermark.

Now lets see Paul Allen's screenshots of the directory structure of his codebase.


American psycho, lol.

Ok, i get it.

Just a shame that while i gave a pretty clear technical description on the "why i think so".

Nobody of the downvoters actually cared to give a actual technical counter argument or even did a test with a technical question... Instead just a reply with a partial movie script...

Ugh.


"I just finished reading the greatest script I've ever read in my life."

- "Oh, really? Who wrote it?"

"I did."


"What's the name of it?"

..."Lessons in humility"


What else my own, Java, coding for over 50 years. If YOU can't figure out what your own code is doing after ten years of not looking at it then nobody else can either. Hint, Comment your thoughts as much as possible, to make things clear when there not to you.

Format just like a book. Use full text variables, methods, class names. Don't start a project until you define your formatting. Stick to it! Do this and your documentation will be easy.

"https://github.com/csanyipal/ajqvue/blob/master/src/com/dand..."


A great example of how NOT to write Java. You say absolutely nothing with a whole lot of extra words.

For example: //============================================================== // Ajqvue Constructor //==============================================================

   public Ajqvue()
The constructor definition is already clear, I don’t need a big header telling me what a constructor is.

Instead, use comments generously where needed - for example, if you have a piece of business logic, a comment explaining the intent behind it can help the maintainer (likely you) a year down the road. What I mean by this, is that what your code DOES should be self evident - but documenting the business decision behind the implementation has done wonders for me.


Anyone suggesting their -own- code as an example of the "most elegant codebase" is dubious. Practice some humility.


I’d be a little forgiving if it was almost an art piece. Like, they spent a year making the most elegant JSON serializer possible.


The getWebsite method comment says it returns the version. That's an example of how not to comment - totally pointless and misleading if it diverges from the code. The code is nice and clear without the comments.


This is pretty good! I'd be happy to work with you :-)

There are undoubtedly some pointless comments, but there are some good ones too, and the code is understandable. I think the sibling comments are being overly harsh and are zeroing in on single examples and missing the forest for the trees.

I suspect recommending your own code as an example of the most elegant codebase is triggering to others, so there's probably a negative initial reaction and probably a lot of people clicking your link so they can point out why you're wrong


Good structure overall and appreciate the summary at the top. For the inline comments more "why" and less "what" would give higher signal-to-noise as a large percentage of that content is adding nothing that basic Java syntax and variable names don't already tell you.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: