Re-export of Shake using well-typed paths and ReaderT.

LTS Haskell 22.29:
Stackage Nightly 2024-07-16:
Latest on Hackage:

See all snapshots shake-plus appears in

MIT licensed by Daniel Firth
Maintained by [email protected]
This version can be pinned in stack with:shake-plus-,2541
Depends on 5 packages(full list with versions):

Shake+ - Super Powered Shake

Attempt at a batteries included Shake. We reexport replacements for the main utility functions of Shake with the following adjustments whereever possible.

  • Well-typed paths using the path library.
  • New type classes MonadAction, MonadUnliftAction and MonadRules with concrete ReaderT transformers:
    • RAction r a = RAction (ReaderT r Action a) and
    • ShakePlus r a = ShakePlus (ReaderT r Rules a)
  • Text instead of String wherever it is appropriate.


Using the path library is kind of a no brainer. I lose a lot of time to problems that could be avoided by using this library, so it’s everywhere. The names for these functions shadow the existing names, so you may want to import qualified Development.Shake while this library progresses if you have other FilePath based Shake rules that you want to mix into your build.

The standard Development.Shake.FilePath functions for directory manipulation are not re-exported in full, and you should use the functions in the path library (such as replaceExtension) and other path-based libraries. This will probably change.

FilePatterns are kept as-is, as Path is strongly normalizing it makes sense to keep these as Strings.


The ReaderT r Action a transformer (called RAction) is similar to the RIO type and should be used similarly. In fact, you can reuse the logging functions from RIO within any RAction block, which is one of the main motivators for having an Action which is also a MonadReader. If you need to reuse an existing shake Action in an RAction, use liftAction.


The main entry point to this library is the runShakePlus function, which collapses a ReaderT r Rules () to a Rules () and passes the environment to each underlying RAction. The rs in ShakePlus and the underlying RActions have to match. A typical setup might look like this.

let r = --setup env here
shake shakeOptions $ do

    -- include some regular shake rules.

    runShakePlus r $ do

      -- some shake-plus rules.


Changelog for shake-plus


  • Fix for GHC 9’s simplified subsumption change.


  • Re-export RuleResult and ShakeValue.


  • Re-export Development.Shake.Forward.


  • Remove unnecessary comonad dependency.


  • Drop dependency on path-like.
  • Drop dependency on within.
  • Drop Development.Shake.Plus.Loaders module.
  • Restore monomorphic Path variants of everything.
  • Move within style combinators to shake-plus-extended.


  • Add dependency on path-like.
  • Update interface to use FileLike and DirLike and drop Path and Within specific variants.


  • Add unlifted versions of parallel, forP and par.


  • Add lower bound to aeson.
  • Remove hashable dependency.


  • Reexport Development.Shake.Classes and Development.Shake.RuleResult.


  • Add runSimpleShakePlus for quickrunning with args and a log function.


  • Re-export Path and Within.


  • Add getDirectoryFilesWithinIO and getDirectoryFilesWithinIO'


  • Re-export Development.Shake.shakeArgs.


  • Re-export Development.Shake.Command with lifted command and command_.


  • Add copyFileWithin' and copyFileChangedWithin.


  • Make Within style functions more consistent in that they actually take Within values across the board.
  • Make batchLoad functions more consistent and usable.
  • need and want variants now take any Traversable.


  • Update to within- which changes the data type to an Env comonad.
  • Drop the loadSortFilterApply loader functions in favour of a simpler batchLoad set of functions which accepts a loading function which can be cached.
  • Add enough documentation to get started.


  • Add functions based on Within to better keep track of source and target directories.
  • Reexport more shake functions to remove need to import vanilla shake qualified.
  • Add convenience functions loadSortFilterApply and loadSortFilterApplyW for batch loading via MonadAction.
  • Add more of the API surface with Path and Within including variants of need, want readFile, writeFile.


  • Initial sketch of shake-plus with reexported functions. Mostly oracles, filepaths and directory functions using Path, and MonadAction, MonadUnliftAction and MonadRules with ReaderT transformers in a similar style to RIO