diff --git a/.ghcid b/.ghcid deleted file mode 100644 index 8a442e6..0000000 --- a/.ghcid +++ /dev/null @@ -1 +0,0 @@ ---warnings -T ":main" diff --git a/README.md b/README.md index 0b13a48..811bb0a 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ Get a Haskell development environment up and running quickly, as long as Nix is This repository is a Haskell project template that is optimized for a fully reproducible and friendly development environment. It is based on: -- [Nix](http://www.srid.ca/haskell-nix) + [Flakes](https://serokell.io/blog/practical-nix-flakes) (via [`github:srid/haskell-flake`](https://github.com/srid/haskell-flake)) + GHC 9 +- [Nix](https://srid.ca/haskell-nix) + [Flakes](https://serokell.io/blog/practical-nix-flakes) (via [`github:srid/haskell-flake`](https://github.com/srid/haskell-flake)) + GHC 9 - VSCode + [HLS](https://github.com/haskell/haskell-language-server) - [fourmolu](https://github.com/fourmolu/fourmolu) autoformatting - [Relude](https://github.com/kowainik/relude#relude) as Prelude. @@ -49,6 +49,7 @@ git add . && git commit -m rename - Run `nix flake update` to update all flake inputs. - Run `treefmt` in nix shell to autoformat the project. This uses [treefmt](https://github.com/numtide/treefmt), which uses `./treefmt.toml` (where fourmolu and nixpkgs-fmt are specified). - Run `bin/hoogle` to start Hoogle with packages in your cabal file. +- Run `bin/test` to run the test suite. - Run the application without installing: `nix run github:srid/haskell-template` (or `nix run .` from checkout) ## Alternatives diff --git a/bin/run b/bin/run index f28011c..e568fb5 100755 --- a/bin/run +++ b/bin/run @@ -1,8 +1,4 @@ #!/usr/bin/env bash set -xe -# This will run ghcid, which uses `./.ghcid` to invoke your program main entry -# point, with the specified args. -# -# If you change ./.ghcid, ghcid will automatically reload. -exec nix develop -c ghcid +exec nix develop -c ghcid -c "cabal repl exe:haskell-template" --warnings -T :main diff --git a/bin/test b/bin/test new file mode 100755 index 0000000..1af41c2 --- /dev/null +++ b/bin/test @@ -0,0 +1,4 @@ +#!/usr/bin/env bash +set -xe + +exec nix develop -c ghcid -c "cabal repl test:tests" diff --git a/haskell-template.cabal b/haskell-template.cabal index f632dd5..cf46712 100644 --- a/haskell-template.cabal +++ b/haskell-template.cabal @@ -21,35 +21,17 @@ extra-source-files: LICENSE README.md -executable haskell-template - build-depends: - , aeson - , async - , base >=4.13.0.0 && <=4.18.0.0 - , bytestring - , containers - , data-default - , directory - , filepath - , mtl - , optics-core - , profunctors - , relude - , shower - , text - , time - , with-utf8 +common shared + ghc-options: + -Wall -Wincomplete-record-updates -Wincomplete-uni-patterns + -Wmissing-deriving-strategies -Wunused-foralls -Wunused-foralls + -fprint-explicit-foralls -fprint-explicit-kinds mixins: base hiding (Prelude), relude (Relude as Prelude, Relude.Container.One), relude - ghc-options: - -Wall -Wincomplete-record-updates -Wincomplete-uni-patterns - -Wmissing-deriving-strategies -Wunused-foralls -Wunused-foralls - -fprint-explicit-foralls -fprint-explicit-kinds - default-extensions: NoStarIsType BangPatterns @@ -91,6 +73,41 @@ executable haskell-template TypeOperators ViewPatterns - main-is: Main.hs - hs-source-dirs: src - default-language: Haskell2010 + build-depends: + , aeson + , async + , base >=4.13.0.0 && <=4.18.0.0 + , bytestring + , containers + , data-default + , directory + , filepath + , mtl + , optics-core + , profunctors + , relude + , shower + , text + , time + , with-utf8 + +executable haskell-template + import: shared + main-is: Main.hs + hs-source-dirs: src + default-language: Haskell2010 + other-modules: Lib + +library + import: shared + exposed-modules: Lib + hs-source-dirs: src + +test-suite tests + import: shared + main-is: Main.hs + type: exitcode-stdio-1.0 + hs-source-dirs: tests + build-depends: + , haskell-template + , hspec diff --git a/src/Lib.hs b/src/Lib.hs new file mode 100644 index 0000000..7c55ddf --- /dev/null +++ b/src/Lib.hs @@ -0,0 +1,4 @@ +module Lib (hello) where + +hello :: Text +hello = "Hello 🌎" diff --git a/src/Main.hs b/src/Main.hs index 540ecf0..44a1d36 100644 --- a/src/Main.hs +++ b/src/Main.hs @@ -1,15 +1,15 @@ module Main where +import Lib qualified import Main.Utf8 qualified as Utf8 {- | Main entry point. - The `bin/run` script will invoke this function. See `.ghcid` file to change - that. + The `bin/run` script will invoke this function. -} main :: IO () main = do -- For withUtf8, see https://serokell.io/blog/haskell-with-utf8 Utf8.withUtf8 $ do - putStrLn "Hello 🌎" + putTextLn Lib.hello diff --git a/tests/Main.hs b/tests/Main.hs new file mode 100644 index 0000000..17e0ee7 --- /dev/null +++ b/tests/Main.hs @@ -0,0 +1,10 @@ +module Main where + +import Lib qualified +import Test.Hspec (describe, hspec, it, shouldContain) + +main :: IO () +main = hspec $ do + describe "Lib.hello" $ do + it "contains the world emoji" $ do + toString Lib.hello `shouldContain` "🌎"