DEV Community

loading...
Cover image for Haskell as a first timer - Am I missing something ?

Haskell as a first timer - Am I missing something ?

oguimbal profile image Olivier Guimbal Updated on ・6 min read

NB: This is also commented on reddit


So... I've been toying a lot with Haskell lately.

But I feel a bit schizophrenic about my first impressions. There
is something both very right, and very wrong about it.

While addressing most of my top concerns about other languages, and giving me hope to discover a language that I could love, the Haskell ecosystem seems in the meantime broken where I expected it the least to be. It is sooo frustrating, and leaves a bitter taste of unachievement :(

Have I missed a crucial step ? Or is there really something broken in its ecosystem ? (may it be a victim of its age × lack of wide adoption ?)

Let me elaborate a bit.

💖 First looks - The (very) good parts

I wont dive into details, since this is widely documented, but in short, I loved:

  • Its world-class type system 😱 so smooth.
  • Immutablility, Pure FP, all that good stuff.
  • Its syntax. Not the most beginner friendly, but if feels smart and concise when you get it. Other languages then tend to feel verbose.
  • That it looks like maths
  • The simplifications the compiler hints at
  • The depth of this language. I only got a glimpse of its abstraction power, and it is definitely not playing in the same league as others. It is so exciting not to feel that a compiler is forcing you to write dumb things just because language designers felt like "this" or "that" abstraction was not part of the language.
  • TDD as in Type-Driven-Development 😁 If you've ever searched for a type signature on Hoogle, you'll get what I mean.
  • Great learning resources such as learn you a haskell or fp complete

You get the picture, I think that Haskell in itself is neat. But seriously, WTF is wrong with its ecosystem ?
Once you're done toying, and start to get like "okay, now lets do real world shit", everything seems to fall apart.

🥪 Frustration 1 - Stack configuration

If I understood right, stack was supposed to bring to Haskell a decent all-inclusive CLI equivalent to those that you have with Dotnet, Deno, Elm, and whatnot.
Okay. It kind of seems to be (or at least a huge improvement over not having it).

But when npm and friends set a standard of having one file which defines your package (dependencies, and such), why deviate from it introducing package.yaml and stack.yaml ? How the f*** am I supposed to guess that I must read a random part of the Stack documentation to understand that yea, you can install packages by adding them in package.yaml, but for some of them, you must also add them in stack.yaml ... wait ... what ??! Okay, it makes kinda sense once you know why, but why not stick to the "expected" way to go by default ?

When learning a new language or framework, I usually spend minutes trying to understand how the associated CLI & package manager works. I had to spend frustrating hours on stack to understand that it just dont work as others do. What's even more confusing is that it almost does ! Why not ? And why not a "stack install xxx" command which writes yaml files ?

💥 Frustration 2 - Stack error messages

Is it just me ? Or does installing a library though stack is just like playing russian roulette ?

I think everyone who's been a solo Haskell learner might at one point or another felt that sentiment of hoplessness, despair, and self doubt when Haskell tooling just keeps throwing at you thousands of giberrish error lines for no appearant reason, just because you tried to install a package or such (especially if you're already mastering several other ecosystems which behave "as you would expect")

For instance, how the hell am I supposed to make sense of this kind of error logs without getting a headache reading usless stuff ? (for the record, I just added a very widely used package to package.yaml... nothing fancy !)

  • I would expect Stack not to tell me "please scroll up an unkown number of lines to find the error yourself". Especially since there are a lot of things that look like errors between me and the actual error. I guess one can get used to it, but if the point of a nice build tool isnt to help you, what is ?
  • I would expect the luxry of a colorized console output, somehow ?
  • The actual error does not even mention the word "error" 😩 Pretty hard to find the error by yourself when you dont know what you're looking for.
  • If a native dependency is required, isnt it the toolchains' job to abstract that away, and to install it, or at least tell me how to install it (hint: for my error, I guess that a 600MB apt-get install pg is not the answer)

Most of the significant libraries I tried just failed miserably to install for one reason or another. Which leads me to my second frustration.

🤼 Frustration 3 - Maintainers ?

Is it just me ? Or most packages are just abandonned, even sometimes left in a state that is no longer compatible with newer versions of the GHC, with nobody left to answer 3 years old issues and pull requests ?

I am definitely okay (even a bit excited by) trying to adhere to a fringe ecosystem. I dont need millions of downloads to feel safe about a piece of code I'm using. But I fear dead communities, and it has been a bit puzzling to see how inactive most of the repos I encountered are...

Dont get me wrong: I am trying to contribute to opensource as well, so I get that supporting small projects can be demanding. There's nothing wrong in not spending your weekends on OS. But not asking for help, nor specifying that a project is unmaintained, nor even answering issues & pull requests for years feels just wrong.

nb: I dont think too much finger pointing will solve anything, so I wont name any specific library, but you dont have to search very long to find such libs on hackage.

📚 Frustration 4 - Documentawhat ?

I wont moann too much about it because I'm definitely not the first one to point that out.

I get that the holly Types are enough. I get that. But I could argue that even if you could theorically learn gibberish by reading a dictionary on a smartwatch, its usually more pleasant to read, watch or listen to actual people, producing actual sentences.

I dont understand. When you're willing to sacrifice your time to opensource... Why not writing 10 lines targetting mere mortals willing to use your code to tell the general idea behind your work ? Not doing so just feels a bit like "go fuck yourself & read the types, you dumb monkeys" 😯

👉 Conclusion - Please enlighten me

That's where I stand. I am very excited by Haskell, while really puzzled to find myself not willing to try to write actual production stuff with it, for absurd reasons.

These are just small glitches, in the sense that they feel just like superficial flaws, which have been overcome in almost all decent language communities... but they are crippling enough to me so I dont see how I could not have problems working with Haskell.

Still, I will continue to fiddle around with this awesome language, but I gave up my short term plans to build something real with it.

But I'm very open to someone willing to change my mind... What do you think ? Is Haskell dying, or in a status quo, being okay mid distance from a research language to a widely adoptable & production ready thing ? Or is it still a passionate community it seems to have been ? Are those flaws a temporary thing, or the symptoms of something rotten ? Have you had recent production successes with Haskell ? What's your reciepe to onboard people ? How do you see the future for Haskell ? What do you think of Purescript ?

ps: Sorry if my English is off, I'm french :)

Discussion (6)

pic
Editor guide
Collapse
bradparker profile image
Brad

Hey Olivier, as a fan of Haskell I'm excited that you gave it a spin but sorry to see that you had a rough time. I'm very keen to help out where I can. Re: documentation, are you able to point to the libraries you were trying to use that had poor documentation? This is something I think the whole Haskell community is keen to improve, and there are, I think, good examples we can take inspiration from e.g. hackage.haskell.org/package/base-4..., hackage.haskell.org/package/generi... or hackage.haskell.org/package/waargo.... If we know which libraries people are trying to use and having difficulty with that could really help us to improve things :)

Collapse
oguimbal profile image
Olivier Guimbal Author • Edited

These definitely look friendlier than average to me :)

Which leads me to think: Maybe the hackage search engine is a bit to blame here ? For instance, lets say that I want to decode some json string (which is, you'll agree, quite a common and basic need, and was for me one of the firsts).
So I'm this newcomer to Haskell, willing to learn, and to parse a JSON file. Naively, I would type "json" in hackage, which would lead me to the json package ... how to use that ? no clue (remember, I'm a begginer)... end of story: I'll do that with a JSON.parse() in javascript.
Now, lets say that I'm an observer, and that I notice that there is a package several lines below which has more downloads, aeson ... welll... that's better, because if I'm curious, i'll click on Encode and find what I'm looking for, written in words, but it's quite a convoluted explanation for such a simple need. "Where's that damn parse method, and why isnt it mentioned on the main page ?", I would think.

As for libraries that I was frustrated not to see working, I dont remember most of them (because I usually just leave), but here are the two which I fought the most with recently:

  • The one the log in my article refers to : persistent-postgresql, which I didnt know how to install given that it missed pq native lib (which I am supposed to know that is installable via apt-get install libpq-dev, I guess ?), and has no obvious documentation (but agreed, there is one lurking somewhere, which doesnt mention this native library thing... nor does the issues, though, so I guess that's a problem on my computer, somehow).
  • gitlib, which has quite a decent readme, but is not in stackage LTS. Meaning that I took quite a bit of time and frustration to understand how stack resolves packages, to finally notice that it doesnt compile.
Collapse
bradparker profile image
Brad

Thanks a bunch for taking the time to go into detail here. I really hope we can use this to improve things :)

  • It sounds like there's opportunity to better surface usage and activity in Hackage search results. When searching for packages my habit has become to: input my query, sort by downloads, then try sorting by last-upload date. Hackage does have a "Rating" metric for each package (you can vote for packages you like), I like the idea but I'm not sure how obvious it is or how well used. Npm has three metrics they try to surface: popularity, quality, and maintenance. It also looks like they aggregate these somehow into an 'optimal' metric. I've not been able to find information on how that aggregation is done, but there's a little info about the others in their help docs. Rubygems makes the total number of downloads very prominent in their search results. It's nearly at the same level as the name of the Gem. They also have "updated last week" and "updated last month" filters.
  • Getting from the package contents page to the best starting point in the package documentation could really be improved. This is my habit: if the package description contains a link to a module it suggests is a good starting point: I'll click on it, if not: I scroll down to the module list and try to find the most "top-level" looking module. In that case ideally there's a module that has a name which resembles the name of the package. In the case of Aeson the best starting point is Data.Aeson, but it perhaps doesn't do the best job of directing you to the decode function early enough. Rubygems appears to have a "documentation" link as part of their Gem meta data which, in the couple of examples I've just tested does a good job of taking you straight to that "best starting point" for the Gem's docs. Npm appears to rely on that information being provided in the package's README.

In the case of system-level dependencies something like a "dependencies" or "system requirements" section in the README may have helped at least a little. E.G. in the documentation for the Pg gem.

As for packages not being in LTS: I'm sorry but I can't really speak to that, I use a Cabal + Nix workflow that I can't really say is better or worse but works well for me. It helps that I've really bought into Nix so I'm not sure if I should recommend it for everyone. Developing, supporting and improving tooling is, I believe, on the roadmap for the Haskell foundation.

All great stuff to think about. Hopefully we're able to take some steps to smooth out some points of friction. Thanks again for describing your experience :)

Collapse
samuelschlesinger profile image
Samuel Schlesinger

Hey! Glad you're getting into Haskell. Haskell is definitely not dying, the Haskell Foundation was just created and funded to promote the language in more corporate settings. I've been working in Haskell for 6 years now, and its developed substantially in that time, and the contributors who developed it are still working hard and contributing to the community. It seems like you eventually understood the reason for why stack asks you to place your extra dependencies in the stack.yaml, but to be clear, its because you're extending the resolver (a consistent set of packages fixed in compatible versions) with an extra dependency that is not know to compile with the rest of everything. There are many great projects I've worked on with many package.yamls for different pieces of the project, but one stack.yaml. In this context, the advantage for the separation becomes clear. With respect to the installing external binary dependencies that will be linked into your program, there are packaging systems which abstract that away and are used widely in the Haskell community, Nix being far and away the most popular one. The two other concerns I'll admit I feel a bit similar to you about. Many impressive Haskell projects end up dead because they are the brainchild of only one or a few people and they don't have the type of commercial usage to acquire a life of their own. Most of the commonly used packages are maintained well enough, and are small enough that I could imagine myself and a small team taking on a significant part of the labor, that I feel comfortable depending on them. Many people fork a substantial part of the Haskell ecosystem to do their work, and I dislike this approach, but the fact that it is viable speaks to the simplicity of the language and ecosystem. As for documentation, many of us who write libraries (I maintain a few) find it really fun to write code and play with nice ideas, but maybe find it less fun to exposit our ideas in clear, beginner friendly language. You'll find that many libraries have sufficient, minimal haddocks, but not tutorial level documentation. If people want that sort of documentation, people need to work harder, myself included, to make our documentation better.

Collapse
oguimbal profile image
Olivier Guimbal Author • Edited

FYI there are quite a few more comments on reddit 😊

Thanks for the explanation (about stack.yaml)... yes, that's what I understood. This behaviour makes sense once I understood why those files are here, but I had to dig deep in stack documentation to understand that.

To me, the issue here is that as a begginer, I must learn how Stack resolves dependencies, and how it is managing multiple packages repositories in order to understand what I should do to install a simple dependency.... that is quite useless, and frankly quite a lot to learn, when just trying to write 30 lines of Haskell in a toy project.

As awsome and sensible as Stack might be, I think it should have a "degraded" behaviour, sensible defaults that do not leak those advanced use cases on simple projects, thus matching other package managers behaviours...

As for the documentation thing, I think that detailed tutorials are a bit overkill, but showing at least a few snippets of the most common or most simple use cases is quite enjoyable to understand what a lib does, and where to start when trying to understand it.

Collapse
ailrun profile image
Junyoung Clare Jang

For the point1: actually, there is more "clearly" named section in the stack document: docs.haskellstack.org/en/stable/st...
One thing you need to understand is, stack is not a package manager like npm or others, but it's a build tool for a project. This means it may involve more configuration than simple package manager, as it needs a setting for project build itself.

For point 2: yes, I also agree on your frustrations for stack error messages. It's not the best DX...

For the 3rd: I think it's a common thing, even in a community like NPM. OSS maintainers often give up their offsprings for many reasons. Stackage (curated version of hackage) provides a set of packages that are compatible with a specific version of GHC and each others.

Collapse
dschrempf profile image
Dominik Schrempf

Hi! I am a big fan of Haskell, and I can confirm, the language is developing fast, and there are improvements coming around every other week even. However, I have to deeply agree with your points. They are a bit direct, I would say, but true. In particular, I am very concerned about libraries without active maintainers, and about the state of the documentation of non-standard libraries.

I think one of the reasons for these problems is the way Hackage works. Stuff that gets into Hackage stays in Hackage, even when it is abandoned. I know, deprecation warnings can be added, but who does that? Hardly anybody. This must lead to libraries floating around in nimbo, and that is what we are experiencing.

On the other hand, it is very easy to judge, and hard to improve, and we are all volunteers.