Improve documentation
This commit is contained in:
parent
c4991425ab
commit
014f1ff125
@ -161,14 +161,10 @@ Also see:
|
||||
|
||||
### Why does ghcup not use stack code?
|
||||
|
||||
Oddly, this question has been asked a couple of times. For the curious, here are a few reasons:
|
||||
|
||||
1. GHCup started as a shell script. At the time of rewriting it in Haskell, the authors didn't even know that stack exposes *some* of its [installation API](https://hackage.haskell.org/package/stack-2.5.1.1/docs/Stack-Setup.html)
|
||||
2. Even if they did, it doesn't seem it would have satisfied their needs
|
||||
- it didn't support cabal installation, which was the main motivation behind GHCup back then
|
||||
- depending on a codebase as big as stack for a central part of one's application without having a short contribution pipeline would likely have caused stagnation or resulted in simply copy-pasting the relevant code in order to adjust it
|
||||
- it's not clear how GHCup would have been implemented with the provided API. It seems the codebases are fairly different. GHCup does a lot of symlink handling to expose a central `bin/` directory that users can easily put in PATH, without having to worry about anything more. It also provides explicit removal functionality, GHC cross-compilation, a TUI, etc etc.
|
||||
3. GHCup is built around unix principles and supposed to be simple.
|
||||
2. it doesn't support cabal installation, which was the main motivation behind GHCup back then
|
||||
3. depending on a codebase as big as stack for a central part of one's application without having a short contribution pipeline would likely have caused stagnation or resulted in simply copy-pasting the relevant code in order to adjust it
|
||||
4. it's not clear how GHCup would have been implemented with the provided API. It seems the codebases are fairly different. GHCup does a lot of symlink handling to expose a central `bin/` directory that users can easily put in PATH, without having to worry about anything more. It also provides explicit removal functionality, GHC cross-compilation, a TUI, etc etc.
|
||||
|
||||
### Why not unify...
|
||||
|
||||
@ -192,14 +188,12 @@ can then call into ghcup or anything else, also see:
|
||||
|
||||
#### ...installers (like, all of it)
|
||||
|
||||
So far, there hasn't been an **open** discussion about this. Is this even a good idea?
|
||||
So far, there hasn't been an open discussion about this. Is this even a good idea?
|
||||
Sometimes projects converge eventually if their overlap is big enough, sometimes they don't.
|
||||
|
||||
While unification sounds like a simplification of the ecosystem, it also takes away choice.
|
||||
Take `curl` and `wget` as an example.
|
||||
|
||||
How bad do we need this?
|
||||
|
||||
### Why not support windows?
|
||||
|
||||
Windows is supported since GHCup version 0.1.15.1.
|
||||
@ -214,12 +208,3 @@ over 2k LOC, which was very hard to maintain.
|
||||
The main concern when switching from a portable shell script to haskell was platform/architecture support.
|
||||
However, ghcup now re-uses GHCs CI infrastructure and as such is perfectly in sync with all platforms that
|
||||
GHC supports.
|
||||
|
||||
### Is GHCup affiliated with the Haskell Foundation?
|
||||
|
||||
There has been some collaboration: Windows and Stack support were mainly requested by the Haskell Foundation
|
||||
and those seemed interesting features to add.
|
||||
|
||||
Other than that, GHCup is dedicated only to its users and is supported by haskell.org through hosting and CI
|
||||
infrastructure.
|
||||
|
||||
|
64
docs/dev.md
64
docs/dev.md
@ -1,11 +1,20 @@
|
||||
# Development
|
||||
|
||||
All you wanted to know about development.
|
||||
All you wanted to know about GHCup development.
|
||||
|
||||
## Module graph
|
||||
|
||||
[![Module graph](./modules_small.svg){: .center style="width:900px"}](./modules_wide.svg)
|
||||
|
||||
Main functionality is in `GHCup` module. Utility functions are
|
||||
organised tree-ish in `GHCup.Utils` and `GHCup.Utils.*`.
|
||||
|
||||
Anything dealing with ghcup specific directories is in
|
||||
`GHCup.Utils.Dirs`.
|
||||
|
||||
Download information on where to fetch bindists from is in the appropriate
|
||||
yaml files: `data/metadata/ghcup-<yaml-ver>.yaml`.
|
||||
|
||||
## Design decisions
|
||||
|
||||
### Using [Excepts](https://hackage.haskell.org/package/haskus-utils-variant-3.0/docs/Haskus-Utils-Variant-Excepts.html) as a beefed up ExceptT
|
||||
@ -14,18 +23,18 @@ This is an open variant, similar to [plucky](https://hackage.haskell.org/package
|
||||
|
||||
### No use of haskell-TLS
|
||||
|
||||
I consider haskell-TLS an interesting experiment, but not a battle-tested and peer-reviewed crypto implementation. There is little to no research about what the intricacies of using haskell for low-level crypto are and how vulnerable such binaries are. Instead, we use either curl the binary (for FreeBSD and mac) or http-io-streams, which works with OpenSSL bindings.
|
||||
I consider haskell-TLS an interesting experiment, but not a battle-tested and peer-reviewed crypto implementation. There is little to no research about what the intricacies of using haskell for low-level crypto are and how vulnerable such binaries are. Instead, we use either curl the binary or wget. There's also an implementation based on OpenSSL bindings, but it isn't enabled by default, since it would complicate shipping static binaries.
|
||||
|
||||
### Optics instead of lens
|
||||
|
||||
They're a little safer (less Monoid weirdness with view) and have better error messages. Consider the following wit lens
|
||||
They're a little safer (less Monoid weirdness with view) and have better error messages. Consider the following with [lens](https://hackage.haskell.org/package/lens):
|
||||
|
||||
```
|
||||
> view (_Just . to (++ "abc")) Nothing
|
||||
""
|
||||
```
|
||||
|
||||
vs optics
|
||||
vs [optics](https://hackage.haskell.org/package/optics):
|
||||
|
||||
```
|
||||
> view (_Just % to (++ "abc")) Nothing
|
||||
@ -36,37 +45,38 @@ vs optics
|
||||
In an equation for ‘it’: it = view (_Just % to (++ "abc")) Nothing
|
||||
```
|
||||
|
||||
### Strict and StrictData on by default
|
||||
### StrictData on by default
|
||||
|
||||
Kazu Yamamoto [explained it in his PR](https://github.com/yesodweb/wai/pull/752#issuecomment-501531386) very well. I like to agree with him. The instances where we need non-strict behavior, we annotate it.
|
||||
|
||||
`Strict` is a little more odd as a default, since it depends on how you define your functions as well.
|
||||
|
||||
## Code style and formatting
|
||||
|
||||
1. Brittany
|
||||
2. mtl-style preferred
|
||||
3. no overly pointfree style
|
||||
Unfortunately, code formatters are semi-broken on this codebase, due to TH and CPP.
|
||||
|
||||
## Code structure
|
||||
Some light suggestions:
|
||||
|
||||
Main functionality is in `GHCup` module. Utility functions are
|
||||
organised tree-ish in `GHCup.Utils` and `GHCup.Utils.*`.
|
||||
|
||||
Anything dealing with ghcup specific directories is in
|
||||
`GHCup.Utils.Dirs`.
|
||||
|
||||
Download information on where to fetch bindists from is in the appropriate
|
||||
yaml files: `ghcup-<yaml-ver>.yaml`.
|
||||
1. mtl-style preferred
|
||||
2. no overly pointfree style
|
||||
3. use `where` a lot, so the main function body reads like prose
|
||||
4. documentation is part of the code
|
||||
|
||||
## Common Tasks
|
||||
|
||||
### Adding a new GHC version
|
||||
|
||||
1. open the latest `ghcup-<yaml-ver>.yaml`
|
||||
2. find the latest ghc version (in yaml tree e.g. `ghcupDownloads -> GHC -> 8.10.3`)
|
||||
1. open the latest `data/metadata/ghcup-<yaml-ver>.yaml`
|
||||
2. find the latest ghc version (in yaml tree e.g. `ghcupDownloads -> GHC -> 8.10.7`)
|
||||
3. copy-paste it
|
||||
4. adjust the version, tags, changelog, source url
|
||||
5. adjust the various bindist urls (make sure to also change the yaml anchors)
|
||||
6. run `cabal run exe:ghcup-gen -- check-tarballs -f ghcup-<yaml-ver>.yaml -u 'ghc-8\.10\.4'`
|
||||
6. run `cabal run exe:ghcup-gen -- check -f data/metadata/ghcup-<yaml-ver>.yaml`
|
||||
7. run `cabal run exe:ghcup-gen -- check-tarballs -f data/metadata/ghcup-<yaml-ver>.yaml -u 'ghc-8\.10\.8'`
|
||||
|
||||
### Adding a new CLI command
|
||||
|
||||
An example illustration on how to deal with [optparse-applicative](https://hackage.haskell.org/package/optparse-applicative) can be seen here: https://gitlab.haskell.org/haskell/ghcup-hs/-/commit/c19dd5ee8b2edbaf0336af143f1c75b6f4843e26
|
||||
|
||||
## Major refactors
|
||||
|
||||
@ -88,17 +98,23 @@ yaml files: `ghcup-<yaml-ver>.yaml`.
|
||||
|
||||
3. Add ChangeLog entry
|
||||
|
||||
4. Add/fix downloads in `ghcup-<ver>.yaml` (under `data/metadata`), then verify with `ghcup-gen check -f ghcup-<ver>.yaml` and possibly (example only) `ghcup-gen check-tarballs -f ghcup-<ver>.yaml -u 'ghc-8.10.7'`. Generally, new GHC/cabal/stack/hls versions are only added to the latest yaml file. New GHCup versions are added to all (great care must be taken here to not break the parser... e.g. ARM platforms don't parse in all older formats).
|
||||
4. Add/fix downloads in `ghcup-<ver>.yaml` (under `data/metadata`), then verify with `ghcup-gen check -f data/metadata/ghcup-<ver>.yaml` and possibly (example only) `ghcup-gen check-tarballs -f data/metadata/ghcup-<ver>.yaml -u 'ghc-8.10.7'`. Generally, new GHC/cabal/stack/hls versions are only added to the latest yaml file. New GHCup versions are added to all (great care must be taken here to not break the parser... e.g. ARM platforms don't parse in all older formats).
|
||||
|
||||
5. Commit and git push with tag. Wait for tests to succeed and release artifacts to build.
|
||||
|
||||
6. Download release artifacts and upload them `downloads.haskell.org/ghcup` along with checksum files (`sha256sum --tag * > SHA256SUMS && gpg --detach-sign -u <your-email> SHA256SUMS`)
|
||||
6. Download release artifacts and upload them `downloads.haskell.org/~ghcup` along with checksum files (`sha256sum --tag * > SHA256SUMS && gpg --detach-sign -u <your-email> SHA256SUMS`)
|
||||
|
||||
7. Add ghcup release artifacts to ALL yaml files (see point 4.)
|
||||
|
||||
8. Upload the final `ghcup-<ver>.yaml` to `webhost.haskell.org/ghcup/data/`.
|
||||
8. Upload the final `data/metadata/ghcup-<ver>.yaml` (and a detached GPG sig of it) to `webhost.haskell.org/ghcup/data/`.
|
||||
|
||||
9. Update `bootstrap-haskell` and `bootstrap-haskell.ps1` to `webhost.haskell.org/ghcup/sh/`
|
||||
|
||||
10. Update the ghcup symlinks at `downloads.haskell.org/ghcup`
|
||||
10. Update the top-level ghcup symlinks at `downloads.haskell.org/~ghcup`
|
||||
|
||||
11. Post on reddit/discourse/etc. and collect rewards
|
||||
|
||||
# Documentation
|
||||
|
||||
This documentation page is built via [mkdocs](https://www.mkdocs.org/), see `mkdocs.yml` and `docs/` subfolder.
|
||||
The module graph needs [graphmod](https://github.com/yav/graphmod) and is generated via `scripts/dev/modgraph.sh`.
|
||||
|
Loading…
Reference in New Issue
Block a user