{-# LANGUAGE DataKinds #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE LambdaCase #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE RankNTypes #-}
{-# LANGUAGE RecordWildCards #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE UndecidableInstances #-}
{-# LANGUAGE ViewPatterns #-}

-- | Copyright: (c) 2021-2022 berberman
-- SPDX-License-Identifier: MIT
-- Maintainer: berberman <[email protected]>
-- Stability: experimental
-- Portability: portable
--
-- This module mainly contains two things: 'PackageSet' and 'PkgDSL'.
-- NvFetcher accepts the former one -- a set of packages to produce nix sources expr;
-- the later one is used to construct a single package.
--
-- There are many combinators for defining packages. See the documentation of 'define' for example.
module NvFetcher.PackageSet
  ( -- * Package set
    PackageSetF,
    PackageSet,
    newPackage,
    purePackageSet,
    runPackageSet,

    -- * Package DSL

    -- ** Primitives
    PkgDSL (..),
    define,
    package,
    src,
    fetch,

    -- ** Two-in-one functions
    fromGitHub,
    fromGitHub',
    fromGitHubTag,
    fromGitHubTag',
    fromPypi,
    fromOpenVsx,
    fromVscodeMarketplace,

    -- ** Version sources
    sourceGitHub,
    sourceGitHubTag,
    sourceGit,
    sourceGit',
    sourcePypi,
    sourceAur,
    sourceArchLinux,
    sourceManual,
    sourceRepology,
    sourceWebpage,
    sourceHttpHeader,
    sourceOpenVsx,
    sourceVscodeMarketplace,
    sourceCmd,

    -- ** Fetchers
    fetchGitHub,
    fetchGitHub',
    fetchGitHubRelease,
    fetchGitHubRelease',
    fetchPypi,
    fetchGit,
    fetchGit',
    fetchUrl,
    fetchUrl',
    fetchOpenVsx,
    fetchVscodeMarketplace,
    fetchTarball,

    -- * Addons
    extractSource,
    hasCargoLocks,
    tweakVersion,
    passthru,
    pinned,
    gitDateFormat,
    forceFetch,

    -- ** Miscellaneous
    Prod,
    Append,
    Member,
    OptionalMember,
    NotElem,
    Members,
    OptionalMembers,
    Attach,
    AttachMany,
    coerce,
    liftIO,

    -- * Lenses
    (&),
    (.~),
    (%~),
    (^.),
    (?~),
    module NvFetcher.Types.Lens,
  )
where

import Control.Monad.Free
import Control.Monad.IO.Class
import Data.Coerce (coerce)
import Data.Default (def)
import qualified Data.HashMap.Strict as HMap
import Data.Kind (Constraint, Type)
import qualified Data.List.NonEmpty as NE
import Data.Map.Strict as Map
import Data.Maybe (fromMaybe, isJust)
import Data.Text (Text)
import GHC.TypeLits
import Lens.Micro
import NvFetcher.NixFetcher
import NvFetcher.Types
import NvFetcher.Types.Lens

--------------------------------------------------------------------------------

-- | Atomic terms of package set
data PackageSetF f
  = NewPackage !Package f
  | forall a. EmbedIO !(IO a) (a -> f)

instance Functor PackageSetF where
  fmap :: forall a b. (a -> b) -> PackageSetF a -> PackageSetF b
fmap a -> b
f (NewPackage Package
p a
g) = Package -> b -> PackageSetF b
forall f. Package -> f -> PackageSetF f
NewPackage Package
p (b -> PackageSetF b) -> b -> PackageSetF b
forall a b. (a -> b) -> a -> b
$ a -> b
f a
g
  fmap a -> b
f (EmbedIO IO a
action a -> a
g) = IO a -> (a -> b) -> PackageSetF b
forall f a. IO a -> (a -> f) -> PackageSetF f
EmbedIO IO a
action ((a -> b) -> PackageSetF b) -> (a -> b) -> PackageSetF b
forall a b. (a -> b) -> a -> b
$ a -> b
f (a -> b) -> (a -> a) -> a -> b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> a -> a
g

-- | Package set is a monad equipped with two capabilities:
--
-- 1. Carry defined packages
-- 2. Run IO actions
--
-- Package set is evaluated before shake runs.
-- Use 'newPackage' to add a new package, 'liftIO' to run an IO action.
type PackageSet = Free PackageSetF

instance MonadIO PackageSet where
  liftIO :: forall a. IO a -> PackageSet a
liftIO IO a
io = PackageSetF a -> Free PackageSetF a
forall (f :: * -> *) (m :: * -> *) a.
(Functor f, MonadFree f m) =>
f a -> m a
liftF (PackageSetF a -> Free PackageSetF a)
-> PackageSetF a -> Free PackageSetF a
forall a b. (a -> b) -> a -> b
$ IO a -> (a -> a) -> PackageSetF a
forall f a. IO a -> (a -> f) -> PackageSetF f
EmbedIO IO a
io a -> a
forall a. a -> a
id

-- | Add a package to package set
newPackage ::
  PackageName ->
  CheckVersion ->
  PackageFetcher ->
  Maybe PackageExtractSrc ->
  Maybe PackageCargoLockFiles ->
  PackagePassthru ->
  UseStaleVersion ->
  DateFormat ->
  ForceFetch ->
  PackageSet ()
newPackage :: PackageName
-> CheckVersion
-> PackageFetcher
-> Maybe PackageExtractSrc
-> Maybe PackageCargoLockFiles
-> PackagePassthru
-> UseStaleVersion
-> DateFormat
-> ForceFetch
-> PackageSet ()
newPackage PackageName
name CheckVersion
source PackageFetcher
fetcher Maybe PackageExtractSrc
extract Maybe PackageCargoLockFiles
cargo PackagePassthru
pasthru UseStaleVersion
useStale DateFormat
format ForceFetch
force =
  PackageSetF () -> PackageSet ()
forall (f :: * -> *) (m :: * -> *) a.
(Functor f, MonadFree f m) =>
f a -> m a
liftF (PackageSetF () -> PackageSet ())
-> PackageSetF () -> PackageSet ()
forall a b. (a -> b) -> a -> b
$ Package -> () -> PackageSetF ()
forall f. Package -> f -> PackageSetF f
NewPackage (PackageName
-> CheckVersion
-> PackageFetcher
-> Maybe PackageExtractSrc
-> Maybe PackageCargoLockFiles
-> PackagePassthru
-> UseStaleVersion
-> DateFormat
-> ForceFetch
-> Package
Package PackageName
name CheckVersion
source PackageFetcher
fetcher Maybe PackageExtractSrc
extract Maybe PackageCargoLockFiles
cargo PackagePassthru
pasthru UseStaleVersion
useStale DateFormat
format ForceFetch
force) ()

-- | Add a list of packages into package set
purePackageSet :: [Package] -> PackageSet ()
purePackageSet :: [Package] -> PackageSet ()
purePackageSet = (Package -> PackageSet ()) -> [Package] -> PackageSet ()
forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
(a -> m b) -> t a -> m ()
mapM_ (PackageSetF () -> PackageSet ()
forall (f :: * -> *) (m :: * -> *) a.
(Functor f, MonadFree f m) =>
f a -> m a
liftF (PackageSetF () -> PackageSet ())
-> (Package -> PackageSetF ()) -> Package -> PackageSet ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Package -> () -> PackageSetF ())
-> () -> Package -> PackageSetF ()
forall a b c. (a -> b -> c) -> b -> a -> c
flip Package -> () -> PackageSetF ()
forall f. Package -> f -> PackageSetF f
NewPackage ())

-- | Run package set into a set of packages
--
-- Throws exception as more then one packages with the same name
-- are defined
runPackageSet :: PackageSet () -> IO (Map PackageKey Package)
runPackageSet :: PackageSet () -> IO (Map PackageKey Package)
runPackageSet = \case
  Free (NewPackage Package
p PackageSet ()
g) ->
    PackageSet () -> IO (Map PackageKey Package)
runPackageSet PackageSet ()
g IO (Map PackageKey Package)
-> (Map PackageKey Package -> IO (Map PackageKey Package))
-> IO (Map PackageKey Package)
forall a b. IO a -> (a -> IO b) -> IO b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= \Map PackageKey Package
m ->
      if Maybe Package -> Bool
forall a. Maybe a -> Bool
isJust (PackageKey -> Map PackageKey Package -> Maybe Package
forall k a. Ord k => k -> Map k a -> Maybe a
Map.lookup (PackageName -> PackageKey
PackageKey (PackageName -> PackageKey) -> PackageName -> PackageKey
forall a b. (a -> b) -> a -> b
$ Package -> PackageName
_pname Package
p) Map PackageKey Package
m)
        then String -> IO (Map PackageKey Package)
forall a. String -> IO a
forall (m :: * -> *) a. MonadFail m => String -> m a
fail (String -> IO (Map PackageKey Package))
-> String -> IO (Map PackageKey Package)
forall a b. (a -> b) -> a -> b
$ String
"Duplicate package name: " String -> String -> String
forall a. Semigroup a => a -> a -> a
<> PackageName -> String
forall a. Show a => a -> String
show (Package -> PackageName
_pname Package
p)
        else Map PackageKey Package -> IO (Map PackageKey Package)
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Map PackageKey Package -> IO (Map PackageKey Package))
-> Map PackageKey Package -> IO (Map PackageKey Package)
forall a b. (a -> b) -> a -> b
$ PackageKey
-> Package -> Map PackageKey Package -> Map PackageKey Package
forall k a. Ord k => k -> a -> Map k a -> Map k a
Map.insert (PackageName -> PackageKey
PackageKey (PackageName -> PackageKey) -> PackageName -> PackageKey
forall a b. (a -> b) -> a -> b
$ Package -> PackageName
_pname Package
p) Package
p Map PackageKey Package
m
  Free (EmbedIO IO a
action a -> PackageSet ()
g) -> IO a
action IO a
-> (a -> IO (Map PackageKey Package))
-> IO (Map PackageKey Package)
forall a b. IO a -> (a -> IO b) -> IO b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= PackageSet () -> IO (Map PackageKey Package)
runPackageSet (PackageSet () -> IO (Map PackageKey Package))
-> (a -> PackageSet ()) -> a -> IO (Map PackageKey Package)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> PackageSet ()
g
  Pure ()
_ -> Map PackageKey Package -> IO (Map PackageKey Package)
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure Map PackageKey Package
forall a. Monoid a => a
mempty

--------------------------------------------------------------------------------

-- | Simple HList
data Prod (r :: [Type]) where
  Nil :: Prod '[]
  Cons :: !x -> Prod xs -> Prod (x ': xs)

-- | Project elements from 'Prod'
class Member (a :: Type) (r :: [Type]) where
  proj :: Prod r -> a

instance {-# OVERLAPPING #-} (NotElem x xs) => Member x (x ': xs) where
  proj :: Prod (x : xs) -> x
proj (Cons x
x Prod xs
_) = x
x
x

instance (Member x xs) => Member x (_y ': xs) where
  proj :: Prod (_y : xs) -> x
proj (Cons x
_ Prod xs
r) = Prod xs -> x
forall a (r :: [*]). Member a r => Prod r -> a
proj Prod xs
r

instance (TypeError (ShowType x :<>: 'Text " is undefined")) => Member x '[] where
  proj :: Prod '[] -> x
proj = Prod '[] -> x
forall a. HasCallStack => a
undefined

-- | Project optional elements from 'Prod'
class OptionalMember (a :: Type) (r :: [Type]) where
  projMaybe :: Prod r -> Maybe a

instance {-# OVERLAPPING #-} (NotElem x xs) => OptionalMember x (x ': xs) where
  projMaybe :: Prod (x : xs) -> Maybe x
projMaybe (Cons x
x Prod xs
_) = x -> Maybe x
forall a. a -> Maybe a
Just x
x
x

instance (OptionalMember x xs) => OptionalMember x (_y ': xs) where
  projMaybe :: Prod (_y : xs) -> Maybe x
projMaybe (Cons x
_ Prod xs
r) = Prod xs -> Maybe x
forall a (r :: [*]). OptionalMember a r => Prod r -> Maybe a
projMaybe Prod xs
r

instance OptionalMember x '[] where
  projMaybe :: Prod '[] -> Maybe x
projMaybe Prod '[]
Nil = Maybe x
forall a. Maybe a
Nothing

-- | Constraint for producing error messages
type family NotElem (x :: Type) (xs :: [Type]) :: Constraint where
  NotElem x (x ': xs) = TypeError (ShowType x :<>: 'Text " is defined more than one times")
  NotElem x (_ ': xs) = NotElem x xs
  NotElem x '[] = ()

-- | A list of 'Member'
type family Members xs r :: Constraint where
  Members '[] _ = ()
  Members (x ': xs) r = (Member x r, Members xs r)

-- | A list of 'OptionalMember'
type family OptionalMembers xs r :: Constraint where
  OptionalMembers '[] _ = ()
  OptionalMembers (x ': xs) r = (OptionalMember x r, OptionalMembers xs r)

-- | @xs ++ ys@, at type level
type family Append xs ys where
  Append '[] ys = ys
  Append (x ': xs) ys = x ': Append xs ys

-- | Attach members @xs@, with a function argument @arg@
type AttachMany xs arg = forall r. PackageSet (Prod r) -> arg -> PackageSet (Prod (Append xs r))

-- | Attach member @x@, with a function @arg@
type Attach x arg = AttachMany '[x] arg

--------------------------------------------------------------------------------

-- | A tagless final style DSL for constructing packages
class PkgDSL f where
  new :: f PackageName -> f (Prod '[PackageName])
  andThen :: f (Prod r) -> f a -> f (Prod (a ': r))
  end ::
    ( Members
        '[ PackageName,
           VersionSource,
           PackageFetcher
         ]
        r,
      OptionalMembers
        '[ PackageExtractSrc,
           PackageCargoLockFiles,
           NvcheckerOptions,
           PackagePassthru,
           UseStaleVersion,
           DateFormat,
           ForceFetch
         ]
        r
    ) =>
    f (Prod r) ->
    f ()

instance PkgDSL PackageSet where
  new :: PackageSet PackageName -> PackageSet (Prod '[PackageName])
new PackageSet PackageName
e = do
    PackageName
name <- PackageSet PackageName
e
    Prod '[PackageName] -> PackageSet (Prod '[PackageName])
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Prod '[PackageName] -> PackageSet (Prod '[PackageName]))
-> Prod '[PackageName] -> PackageSet (Prod '[PackageName])
forall a b. (a -> b) -> a -> b
$ PackageName -> Prod '[] -> Prod '[PackageName]
forall x (xs :: [*]). x -> Prod xs -> Prod (x : xs)
Cons PackageName
name Prod '[]
Nil
  andThen :: forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
andThen PackageSet (Prod r)
e PackageSet a
e' = do
    Prod r
p <- PackageSet (Prod r)
e
    a
x <- PackageSet a
e'
    Prod (a : r) -> PackageSet (Prod (a : r))
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Prod (a : r) -> PackageSet (Prod (a : r)))
-> Prod (a : r) -> PackageSet (Prod (a : r))
forall a b. (a -> b) -> a -> b
$ a -> Prod r -> Prod (a : r)
forall x (xs :: [*]). x -> Prod xs -> Prod (x : xs)
Cons a
x Prod r
p
  end :: forall (r :: [*]).
(Members '[PackageName, VersionSource, PackageFetcher] r,
 OptionalMembers
   '[PackageExtractSrc, PackageCargoLockFiles, NvcheckerOptions,
     PackagePassthru, UseStaleVersion, DateFormat, ForceFetch]
   r) =>
PackageSet (Prod r) -> PackageSet ()
end PackageSet (Prod r)
e = do
    Prod r
p <- PackageSet (Prod r)
e
    PackageName
-> CheckVersion
-> PackageFetcher
-> Maybe PackageExtractSrc
-> Maybe PackageCargoLockFiles
-> PackagePassthru
-> UseStaleVersion
-> DateFormat
-> ForceFetch
-> PackageSet ()
newPackage
      (Prod r -> PackageName
forall a (r :: [*]). Member a r => Prod r -> a
proj Prod r
p)
      (VersionSource -> NvcheckerOptions -> CheckVersion
CheckVersion (Prod r -> VersionSource
forall a (r :: [*]). Member a r => Prod r -> a
proj Prod r
p) (NvcheckerOptions -> Maybe NvcheckerOptions -> NvcheckerOptions
forall a. a -> Maybe a -> a
fromMaybe NvcheckerOptions
forall a. Default a => a
def (Prod r -> Maybe NvcheckerOptions
forall a (r :: [*]). OptionalMember a r => Prod r -> Maybe a
projMaybe Prod r
p)))
      (Prod r -> PackageFetcher
forall a (r :: [*]). Member a r => Prod r -> a
proj Prod r
p)
      (Prod r -> Maybe PackageExtractSrc
forall a (r :: [*]). OptionalMember a r => Prod r -> Maybe a
projMaybe Prod r
p)
      (Prod r -> Maybe PackageCargoLockFiles
forall a (r :: [*]). OptionalMember a r => Prod r -> Maybe a
projMaybe Prod r
p)
      (PackagePassthru -> Maybe PackagePassthru -> PackagePassthru
forall a. a -> Maybe a -> a
fromMaybe PackagePassthru
forall a. Monoid a => a
mempty (Prod r -> Maybe PackagePassthru
forall a (r :: [*]). OptionalMember a r => Prod r -> Maybe a
projMaybe Prod r
p))
      (UseStaleVersion -> Maybe UseStaleVersion -> UseStaleVersion
forall a. a -> Maybe a -> a
fromMaybe UseStaleVersion
NoStale (Prod r -> Maybe UseStaleVersion
forall a (r :: [*]). OptionalMember a r => Prod r -> Maybe a
projMaybe Prod r
p))
      (DateFormat -> Maybe DateFormat -> DateFormat
forall a. a -> Maybe a -> a
fromMaybe (Maybe PackageName -> DateFormat
DateFormat Maybe PackageName
forall a. Maybe a
Nothing) (Prod r -> Maybe DateFormat
forall a (r :: [*]). OptionalMember a r => Prod r -> Maybe a
projMaybe Prod r
p))
      (ForceFetch -> Maybe ForceFetch -> ForceFetch
forall a. a -> Maybe a -> a
fromMaybe ForceFetch
NoForceFetch (Prod r -> Maybe ForceFetch
forall a (r :: [*]). OptionalMember a r => Prod r -> Maybe a
projMaybe Prod r
p))

-- | 'PkgDSL' version of 'newPackage'
--
-- Example:
--
-- @
-- define $ package "nvfetcher-git" `sourceGit` "https://github.com/berberman/nvfetcher" `fetchGitHub` ("berberman", "nvfetcher")
-- @
define ::
  ( Members
      '[ PackageName,
         VersionSource,
         PackageFetcher
       ]
      r,
    OptionalMembers
      '[ PackageExtractSrc,
         PackageCargoLockFiles,
         PackagePassthru,
         NvcheckerOptions,
         UseStaleVersion,
         DateFormat,
         ForceFetch
       ]
      r
  ) =>
  PackageSet (Prod r) ->
  PackageSet ()
define :: forall (r :: [*]).
(Members '[PackageName, VersionSource, PackageFetcher] r,
 OptionalMembers
   '[PackageExtractSrc, PackageCargoLockFiles, PackagePassthru,
     NvcheckerOptions, UseStaleVersion, DateFormat, ForceFetch]
   r) =>
PackageSet (Prod r) -> PackageSet ()
define = Free PackageSetF (Prod r) -> PackageSet ()
forall (r :: [*]).
(Members '[PackageName, VersionSource, PackageFetcher] r,
 OptionalMembers
   '[PackageExtractSrc, PackageCargoLockFiles, NvcheckerOptions,
     PackagePassthru, UseStaleVersion, DateFormat, ForceFetch]
   r) =>
PackageSet (Prod r) -> PackageSet ()
forall (f :: * -> *) (r :: [*]).
(PkgDSL f, Members '[PackageName, VersionSource, PackageFetcher] r,
 OptionalMembers
   '[PackageExtractSrc, PackageCargoLockFiles, NvcheckerOptions,
     PackagePassthru, UseStaleVersion, DateFormat, ForceFetch]
   r) =>
f (Prod r) -> f ()
end

-- | Start chaining with the name of package to define
package :: PackageName -> PackageSet (Prod '[PackageName])
package :: PackageName -> PackageSet (Prod '[PackageName])
package = PackageSet PackageName -> PackageSet (Prod '[PackageName])
forall (f :: * -> *).
PkgDSL f =>
f PackageName -> f (Prod '[PackageName])
new (PackageSet PackageName -> PackageSet (Prod '[PackageName]))
-> (PackageName -> PackageSet PackageName)
-> PackageName
-> PackageSet (Prod '[PackageName])
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageName -> PackageSet PackageName
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure

-- | Attach version sources
src :: Attach VersionSource VersionSource
src :: Attach VersionSource VersionSource
src = ((Free PackageSetF VersionSource
 -> Free PackageSetF (Prod (VersionSource : r)))
-> (VersionSource -> Free PackageSetF VersionSource)
-> VersionSource
-> Free PackageSetF (Prod (VersionSource : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. VersionSource -> Free PackageSetF VersionSource
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure) ((Free PackageSetF VersionSource
  -> Free PackageSetF (Prod (VersionSource : r)))
 -> VersionSource -> Free PackageSetF (Prod (VersionSource : r)))
-> (PackageSet (Prod r)
    -> Free PackageSetF VersionSource
    -> Free PackageSetF (Prod (VersionSource : r)))
-> PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (VersionSource : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageSet (Prod r)
-> Free PackageSetF VersionSource
-> Free PackageSetF (Prod (VersionSource : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen

-- | Attach fetchers
fetch :: Attach PackageFetcher PackageFetcher
fetch :: Attach PackageFetcher PackageFetcher
fetch = ((Free PackageSetF PackageFetcher
 -> Free PackageSetF (Prod (PackageFetcher : r)))
-> (PackageFetcher -> Free PackageSetF PackageFetcher)
-> PackageFetcher
-> Free PackageSetF (Prod (PackageFetcher : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageFetcher -> Free PackageSetF PackageFetcher
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure) ((Free PackageSetF PackageFetcher
  -> Free PackageSetF (Prod (PackageFetcher : r)))
 -> PackageFetcher -> Free PackageSetF (Prod (PackageFetcher : r)))
-> (PackageSet (Prod r)
    -> Free PackageSetF PackageFetcher
    -> Free PackageSetF (Prod (PackageFetcher : r)))
-> PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (PackageFetcher : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageSet (Prod r)
-> Free PackageSetF PackageFetcher
-> Free PackageSetF (Prod (PackageFetcher : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen

--------------------------------------------------------------------------------

-- | A synonym of 'fetchGitHub' and 'sourceGitHub'
fromGitHub :: AttachMany '[PackageFetcher, VersionSource] (Text, Text)
fromGitHub :: AttachMany
  '[PackageFetcher, VersionSource] (PackageName, PackageName)
fromGitHub PackageSet (Prod r)
e (PackageName
owner, PackageName
repo) = PackageSet (Prod r)
-> (PackageName, PackageName,
    NixFetcher 'Fresh -> NixFetcher 'Fresh)
-> Free
     PackageSetF (Prod (Append '[PackageFetcher, VersionSource] r))
AttachMany
  '[PackageFetcher, VersionSource]
  (PackageName, PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
fromGitHub' PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, NixFetcher 'Fresh -> NixFetcher 'Fresh
forall a. a -> a
id)

-- | A synonym of 'fetchGitHub'' and 'sourceGitHub'
fromGitHub' :: AttachMany '[PackageFetcher, VersionSource] (Text, Text, NixFetcher Fresh -> NixFetcher Fresh)
fromGitHub' :: AttachMany
  '[PackageFetcher, VersionSource]
  (PackageName, PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
fromGitHub' PackageSet (Prod r)
e p :: (PackageName, PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
p@(PackageName
owner, PackageName
repo, NixFetcher 'Fresh -> NixFetcher 'Fresh
_) = PackageSet (Prod (VersionSource : r))
-> (PackageName, PackageName,
    NixFetcher 'Fresh -> NixFetcher 'Fresh)
-> PackageSet (Prod (Append '[PackageFetcher] (VersionSource : r)))
Attach
  PackageFetcher
  (PackageName, PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
fetchGitHub' (PackageSet (Prod r)
-> (PackageName, PackageName)
-> PackageSet (Prod (Append '[VersionSource] r))
Attach VersionSource (PackageName, PackageName)
sourceGitHub PackageSet (Prod r)
e (PackageName
owner, PackageName
repo)) (PackageName, PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
p

-- | A synonym of 'fetchGitHub' and 'sourceGitHubTag'
fromGitHubTag :: AttachMany '[PackageFetcher, VersionSource] (Text, Text, ListOptions -> ListOptions)
fromGitHubTag :: AttachMany
  '[PackageFetcher, VersionSource]
  (PackageName, PackageName, ListOptions -> ListOptions)
fromGitHubTag PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, ListOptions -> ListOptions
f) = PackageSet (Prod r)
-> (PackageName, PackageName, ListOptions -> ListOptions,
    NixFetcher 'Fresh -> NixFetcher 'Fresh)
-> Free
     PackageSetF (Prod (Append '[PackageFetcher, VersionSource] r))
AttachMany
  '[PackageFetcher, VersionSource]
  (PackageName, PackageName, ListOptions -> ListOptions,
   NixFetcher 'Fresh -> NixFetcher 'Fresh)
fromGitHubTag' PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, ListOptions -> ListOptions
f, NixFetcher 'Fresh -> NixFetcher 'Fresh
forall a. a -> a
id)

-- | A synonym of 'fetchGitHub'' and 'sourceGitHubTag'
fromGitHubTag' ::
  AttachMany
    '[PackageFetcher, VersionSource]
    (Text, Text, ListOptions -> ListOptions, NixFetcher Fresh -> NixFetcher Fresh)
fromGitHubTag' :: AttachMany
  '[PackageFetcher, VersionSource]
  (PackageName, PackageName, ListOptions -> ListOptions,
   NixFetcher 'Fresh -> NixFetcher 'Fresh)
fromGitHubTag' PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, ListOptions -> ListOptions
fv, NixFetcher 'Fresh -> NixFetcher 'Fresh
ff) = PackageSet (Prod (VersionSource : r))
-> (PackageName, PackageName,
    NixFetcher 'Fresh -> NixFetcher 'Fresh)
-> PackageSet (Prod (Append '[PackageFetcher] (VersionSource : r)))
Attach
  PackageFetcher
  (PackageName, PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
fetchGitHub' (PackageSet (Prod r)
-> (PackageName, PackageName, ListOptions -> ListOptions)
-> PackageSet (Prod (Append '[VersionSource] r))
Attach
  VersionSource
  (PackageName, PackageName, ListOptions -> ListOptions)
sourceGitHubTag PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, ListOptions -> ListOptions
fv)) (PackageName
owner, PackageName
repo, NixFetcher 'Fresh -> NixFetcher 'Fresh
ff)

-- | A synonym of 'fetchPypi' and 'sourcePypi'
fromPypi :: AttachMany '[PackageFetcher, VersionSource] Text
fromPypi :: AttachMany '[PackageFetcher, VersionSource] PackageName
fromPypi PackageSet (Prod r)
e PackageName
p = PackageSet (Prod (VersionSource : r))
-> PackageName
-> PackageSet (Prod (Append '[PackageFetcher] (VersionSource : r)))
Attach PackageFetcher PackageName
fetchPypi (PackageSet (Prod r)
-> PackageName -> PackageSet (Prod (Append '[VersionSource] r))
Attach VersionSource PackageName
sourcePypi PackageSet (Prod r)
e PackageName
p) PackageName
p

-- | A synonym of 'fetchOpenVsx', 'sourceOpenVsx', and 'passthru' extension's publisher with name
fromOpenVsx :: AttachMany '[PackagePassthru, PackageFetcher, VersionSource] (Text, Text)
fromOpenVsx :: AttachMany
  '[PackagePassthru, PackageFetcher, VersionSource]
  (PackageName, PackageName)
fromOpenVsx PackageSet (Prod r)
e x :: (PackageName, PackageName)
x@(PackageName
publisher, PackageName
extName) =
  PackageSet (Prod (PackageFetcher : VersionSource : r))
-> [(PackageName, PackageName)]
-> PackageSet
     (Prod
        (Append '[PackagePassthru] (PackageFetcher : VersionSource : r)))
Attach PackagePassthru [(PackageName, PackageName)]
passthru
    (PackageSet (Prod (VersionSource : r))
-> (PackageName, PackageName)
-> PackageSet (Prod (Append '[PackageFetcher] (VersionSource : r)))
Attach PackageFetcher (PackageName, PackageName)
fetchOpenVsx (PackageSet (Prod r)
-> (PackageName, PackageName)
-> PackageSet (Prod (Append '[VersionSource] r))
Attach VersionSource (PackageName, PackageName)
sourceOpenVsx PackageSet (Prod r)
e (PackageName, PackageName)
x) (PackageName, PackageName)
x)
    [ (PackageName
"name", PackageName
extName),
      (PackageName
"publisher", PackageName
publisher)
    ]

-- | A synonym of 'fetchVscodeMarketplace', 'sourceVscodeMarketplace', and 'passthru' extension's publisher with name
fromVscodeMarketplace :: AttachMany '[PackagePassthru, PackageFetcher, VersionSource] (Text, Text)
fromVscodeMarketplace :: AttachMany
  '[PackagePassthru, PackageFetcher, VersionSource]
  (PackageName, PackageName)
fromVscodeMarketplace PackageSet (Prod r)
e x :: (PackageName, PackageName)
x@(PackageName
publisher, PackageName
extName) =
  PackageSet (Prod (PackageFetcher : VersionSource : r))
-> [(PackageName, PackageName)]
-> PackageSet
     (Prod
        (Append '[PackagePassthru] (PackageFetcher : VersionSource : r)))
Attach PackagePassthru [(PackageName, PackageName)]
passthru
    (PackageSet (Prod (VersionSource : r))
-> (PackageName, PackageName)
-> PackageSet (Prod (Append '[PackageFetcher] (VersionSource : r)))
Attach PackageFetcher (PackageName, PackageName)
fetchVscodeMarketplace (PackageSet (Prod r)
-> (PackageName, PackageName)
-> PackageSet (Prod (Append '[VersionSource] r))
Attach VersionSource (PackageName, PackageName)
sourceVscodeMarketplace PackageSet (Prod r)
e (PackageName, PackageName)
x) (PackageName, PackageName)
x)
    [ (PackageName
"name", PackageName
extName),
      (PackageName
"publisher", PackageName
publisher)
    ]

--------------------------------------------------------------------------------

-- | This package follows the latest github release
sourceGitHub :: Attach VersionSource (Text, Text)
sourceGitHub :: Attach VersionSource (PackageName, PackageName)
sourceGitHub PackageSet (Prod r)
e (PackageName
owner, PackageName
repo) = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e (VersionSource
 -> Free PackageSetF (Prod (Append '[VersionSource] r)))
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
forall a b. (a -> b) -> a -> b
$ PackageName -> PackageName -> VersionSource
GitHubRelease PackageName
owner PackageName
repo

-- | This package follows the a tag from github
--
-- Args are owner, repo, and nvchecker list options to find the target tag
sourceGitHubTag :: Attach VersionSource (Text, Text, ListOptions -> ListOptions)
sourceGitHubTag :: Attach
  VersionSource
  (PackageName, PackageName, ListOptions -> ListOptions)
sourceGitHubTag PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, ListOptions -> ListOptions
f) = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e (VersionSource
 -> Free PackageSetF (Prod (Append '[VersionSource] r)))
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
forall a b. (a -> b) -> a -> b
$ PackageName -> PackageName -> ListOptions -> VersionSource
GitHubTag PackageName
owner PackageName
repo (ListOptions -> VersionSource) -> ListOptions -> VersionSource
forall a b. (a -> b) -> a -> b
$ ListOptions -> ListOptions
f ListOptions
forall a. Default a => a
def

-- | This package follows the latest git commit
--
-- Arg is git url
sourceGit :: Attach VersionSource Text
sourceGit :: Attach VersionSource PackageName
sourceGit PackageSet (Prod r)
e PackageName
_vurl = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e (VersionSource
 -> Free PackageSetF (Prod (Append '[VersionSource] r)))
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
forall a b. (a -> b) -> a -> b
$ PackageName -> Branch -> VersionSource
Git PackageName
_vurl Branch
forall a. Default a => a
def

-- | Similar to 'sourceGit', but allows to specify branch
--
-- Args are git url and branch
sourceGit' :: Attach VersionSource (Text, Text)
sourceGit' :: Attach VersionSource (PackageName, PackageName)
sourceGit' PackageSet (Prod r)
e (PackageName
_vurl, Maybe PackageName -> Branch
forall a b. Coercible a b => a -> b
coerce (Maybe PackageName -> Branch)
-> (PackageName -> Maybe PackageName) -> PackageName -> Branch
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageName -> Maybe PackageName
forall a. a -> Maybe a
Just -> Branch
_vbranch) = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e (VersionSource
 -> Free PackageSetF (Prod (Append '[VersionSource] r)))
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
forall a b. (a -> b) -> a -> b
$ Git {PackageName
Branch
_vurl :: PackageName
_vbranch :: Branch
_vurl :: PackageName
_vbranch :: Branch
..}

-- | This package follows the latest pypi release
--
-- Arg is pypi name
sourcePypi :: Attach VersionSource Text
sourcePypi :: Attach VersionSource PackageName
sourcePypi PackageSet (Prod r)
e PackageName
_pypi = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e Pypi {PackageName
_pypi :: PackageName
_pypi :: PackageName
..}

-- | This package follows the version of an Arch Linux package
--
-- Arg is package name in Arch Linux repo
sourceArchLinux :: Attach VersionSource Text
sourceArchLinux :: Attach VersionSource PackageName
sourceArchLinux PackageSet (Prod r)
e PackageName
_archpkg = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e ArchLinux {PackageName
_archpkg :: PackageName
_archpkg :: PackageName
..}

-- | This package follows the version of an Aur package
--
-- Arg is package name in Aur
sourceAur :: Attach VersionSource Text
sourceAur :: Attach VersionSource PackageName
sourceAur PackageSet (Prod r)
e PackageName
_aur = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e Aur {PackageName
_aur :: PackageName
_aur :: PackageName
..}

-- | This package follows a pinned version
--
-- Arg is manual version
sourceManual :: Attach VersionSource Text
sourceManual :: Attach VersionSource PackageName
sourceManual PackageSet (Prod r)
e PackageName
_manual = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e Manual {PackageName
_manual :: PackageName
_manual :: PackageName
..}

-- | This package follows the version of a repology package
--
-- Args are repology project name and repo
sourceRepology :: Attach VersionSource (Text, Text)
sourceRepology :: Attach VersionSource (PackageName, PackageName)
sourceRepology PackageSet (Prod r)
e (PackageName
project, PackageName
repo) = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e (VersionSource
 -> Free PackageSetF (Prod (Append '[VersionSource] r)))
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
forall a b. (a -> b) -> a -> b
$ PackageName -> PackageName -> VersionSource
Repology PackageName
project PackageName
repo

-- | This package follows a version extracted from web page
--
-- Args are web page url, regex, and list options
sourceWebpage :: Attach VersionSource (Text, Text, ListOptions -> ListOptions)
sourceWebpage :: Attach
  VersionSource
  (PackageName, PackageName, ListOptions -> ListOptions)
sourceWebpage PackageSet (Prod r)
e (PackageName
_vurl, PackageName
_regex, ListOptions -> ListOptions
f) = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e (VersionSource
 -> Free PackageSetF (Prod (Append '[VersionSource] r)))
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
forall a b. (a -> b) -> a -> b
$ PackageName -> PackageName -> ListOptions -> VersionSource
Webpage PackageName
_vurl PackageName
_regex (ListOptions -> VersionSource) -> ListOptions -> VersionSource
forall a b. (a -> b) -> a -> b
$ ListOptions -> ListOptions
f ListOptions
forall a. Default a => a
def

-- | This package follows a version extracted from http header
--
-- Args are the url of the http request, regex, and list options
sourceHttpHeader :: Attach VersionSource (Text, Text, ListOptions -> ListOptions)
sourceHttpHeader :: Attach
  VersionSource
  (PackageName, PackageName, ListOptions -> ListOptions)
sourceHttpHeader PackageSet (Prod r)
e (PackageName
_vurl, PackageName
_regex, ListOptions -> ListOptions
f) = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e (VersionSource
 -> Free PackageSetF (Prod (Append '[VersionSource] r)))
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
forall a b. (a -> b) -> a -> b
$ PackageName -> PackageName -> ListOptions -> VersionSource
HttpHeader PackageName
_vurl PackageName
_regex (ListOptions -> VersionSource) -> ListOptions -> VersionSource
forall a b. (a -> b) -> a -> b
$ ListOptions -> ListOptions
f ListOptions
forall a. Default a => a
def

-- | This package follows a version in Open VSX
--
-- Args are publisher and extension name
sourceOpenVsx :: Attach VersionSource (Text, Text)
sourceOpenVsx :: Attach VersionSource (PackageName, PackageName)
sourceOpenVsx PackageSet (Prod r)
e (PackageName
_ovPublisher, PackageName
_ovExtName) = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e OpenVsx {PackageName
_ovPublisher :: PackageName
_ovExtName :: PackageName
_ovPublisher :: PackageName
_ovExtName :: PackageName
..}

-- | This package follows a version in Vscode Marketplace
--
-- Args are publisher and extension name
sourceVscodeMarketplace :: Attach VersionSource (Text, Text)
sourceVscodeMarketplace :: Attach VersionSource (PackageName, PackageName)
sourceVscodeMarketplace PackageSet (Prod r)
e (PackageName
_vsmPublisher, PackageName
_vsmExtName) = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e VscodeMarketplace {PackageName
_vsmPublisher :: PackageName
_vsmExtName :: PackageName
_vsmPublisher :: PackageName
_vsmExtName :: PackageName
..}

-- | This package follows a version from a shell command
--
-- Arg is the command to run
sourceCmd :: Attach VersionSource Text
sourceCmd :: Attach VersionSource PackageName
sourceCmd PackageSet (Prod r)
e PackageName
_vcmd = PackageSet (Prod r)
-> VersionSource
-> Free PackageSetF (Prod (Append '[VersionSource] r))
Attach VersionSource VersionSource
src PackageSet (Prod r)
e Cmd {PackageName
_vcmd :: PackageName
_vcmd :: PackageName
..}

--------------------------------------------------------------------------------

-- | This package is fetched from a github repo
--
-- Args are owner and repo
fetchGitHub :: Attach PackageFetcher (Text, Text)
fetchGitHub :: Attach PackageFetcher (PackageName, PackageName)
fetchGitHub PackageSet (Prod r)
e (PackageName
owner, PackageName
repo) = PackageSet (Prod r)
-> (PackageName, PackageName,
    NixFetcher 'Fresh -> NixFetcher 'Fresh)
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach
  PackageFetcher
  (PackageName, PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
fetchGitHub' PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, NixFetcher 'Fresh -> NixFetcher 'Fresh
forall a. a -> a
id)

-- | This package is fetched from a github repo
--
-- Similar to 'fetchGitHub', but allows a modifier to the fetcher.
-- For example, you can enable fetch submodules like:
--
-- @
-- define $ package "qliveplayer" `sourceGitHub` ("THMonster", "QLivePlayer") `fetchGitHub'` ("THMonster", "QLivePlayer", fetchSubmodules .~ True)
-- @
fetchGitHub' :: Attach PackageFetcher (Text, Text, NixFetcher Fresh -> NixFetcher Fresh)
fetchGitHub' :: Attach
  PackageFetcher
  (PackageName, PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
fetchGitHub' PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, NixFetcher 'Fresh -> NixFetcher 'Fresh
f) = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageFetcher
 -> Free PackageSetF (Prod (Append '[PackageFetcher] r)))
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
forall a b. (a -> b) -> a -> b
$ NixFetcher 'Fresh -> NixFetcher 'Fresh
f (NixFetcher 'Fresh -> NixFetcher 'Fresh)
-> PackageFetcher -> PackageFetcher
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (PackageName, PackageName) -> PackageFetcher
gitHubFetcher (PackageName
owner, PackageName
repo)

-- | This package is fetched from a file in github release
--
-- Args are owner, repo, and file name
fetchGitHubRelease :: Attach PackageFetcher (Text, Text, Text)
fetchGitHubRelease :: Attach PackageFetcher (PackageName, PackageName, PackageName)
fetchGitHubRelease PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, PackageName
fp) = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageFetcher
 -> Free PackageSetF (Prod (Append '[PackageFetcher] r)))
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
forall a b. (a -> b) -> a -> b
$ (PackageName, PackageName) -> PackageName -> PackageFetcher
gitHubReleaseFetcher (PackageName
owner, PackageName
repo) PackageName
fp

-- | This package is fetched from a file in github release
--
-- Args are owner, repo, and file name computed from version
fetchGitHubRelease' :: Attach PackageFetcher (Text, Text, Version -> Text)
fetchGitHubRelease' :: Attach
  PackageFetcher (PackageName, PackageName, Version -> PackageName)
fetchGitHubRelease' PackageSet (Prod r)
e (PackageName
owner, PackageName
repo, Version -> PackageName
f) = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageFetcher
 -> Free PackageSetF (Prod (Append '[PackageFetcher] r)))
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
forall a b. (a -> b) -> a -> b
$ (PackageName, PackageName)
-> (Version -> PackageName) -> PackageFetcher
gitHubReleaseFetcher' (PackageName
owner, PackageName
repo) Version -> PackageName
f

-- | This package is fetched from pypi
--
-- Arg is pypi name
fetchPypi :: Attach PackageFetcher Text
fetchPypi :: Attach PackageFetcher PackageName
fetchPypi PackageSet (Prod r)
e = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageFetcher -> Free PackageSetF (Prod (PackageFetcher : r)))
-> (PackageName -> PackageFetcher)
-> PackageName
-> Free PackageSetF (Prod (PackageFetcher : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageName -> PackageFetcher
pypiFetcher

-- | This package is fetched from git
--
-- Arg is git url
fetchGit :: Attach PackageFetcher Text
fetchGit :: Attach PackageFetcher PackageName
fetchGit PackageSet (Prod r)
e PackageName
u = PackageSet (Prod r)
-> (PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach
  PackageFetcher
  (PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
fetchGit' PackageSet (Prod r)
e (PackageName
u, NixFetcher 'Fresh -> NixFetcher 'Fresh
forall a. a -> a
id)

-- | This package is fetched from git
--
-- Similar to 'fetchGit', but allows a modifier to the fetcher.
-- See 'fetchGitHub'' for a concret example.
fetchGit' :: Attach PackageFetcher (Text, NixFetcher Fresh -> NixFetcher Fresh)
fetchGit' :: Attach
  PackageFetcher
  (PackageName, NixFetcher 'Fresh -> NixFetcher 'Fresh)
fetchGit' PackageSet (Prod r)
e (PackageName
u, NixFetcher 'Fresh -> NixFetcher 'Fresh
f) = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageFetcher
 -> Free PackageSetF (Prod (Append '[PackageFetcher] r)))
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
forall a b. (a -> b) -> a -> b
$ NixFetcher 'Fresh -> NixFetcher 'Fresh
f (NixFetcher 'Fresh -> NixFetcher 'Fresh)
-> PackageFetcher -> PackageFetcher
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageName -> PackageFetcher
gitFetcher PackageName
u

-- | This package is fetched from url
--
-- Arg is a function which constructs the url from a version
fetchUrl :: Attach PackageFetcher (Version -> Text)
fetchUrl :: Attach PackageFetcher (Version -> PackageName)
fetchUrl PackageSet (Prod r)
e Version -> PackageName
f = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageName -> NixFetcher 'Fresh
urlFetcher (PackageName -> NixFetcher 'Fresh)
-> (Version -> PackageName) -> PackageFetcher
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Version -> PackageName
f)

-- | This package is fetched from url
--
-- Args are a function which constructs the url from a version and a file name
fetchUrl' :: Attach PackageFetcher (Text, Version -> Text)
fetchUrl' :: Attach PackageFetcher (PackageName, Version -> PackageName)
fetchUrl' PackageSet (Prod r)
e (PackageName
name, Version -> PackageName
f) = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (\Version
v -> PackageName
-> Maybe PackageName
-> FetchResult Checksum 'Fresh
-> NixFetcher 'Fresh
forall (k :: FetchStatus).
PackageName
-> Maybe PackageName -> FetchResult Checksum k -> NixFetcher k
FetchUrl (Version -> PackageName
f Version
v) (PackageName -> Maybe PackageName
forall a. a -> Maybe a
Just PackageName
name) ())

-- | This package is fetched from Open VSX
--
-- Args are publisher and extension name
fetchOpenVsx :: Attach PackageFetcher (Text, Text)
fetchOpenVsx :: Attach PackageFetcher (PackageName, PackageName)
fetchOpenVsx PackageSet (Prod r)
e = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageFetcher -> Free PackageSetF (Prod (PackageFetcher : r)))
-> ((PackageName, PackageName) -> PackageFetcher)
-> (PackageName, PackageName)
-> Free PackageSetF (Prod (PackageFetcher : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (PackageName, PackageName) -> PackageFetcher
vscodeMarketplaceFetcher

-- | This package is fetched from Vscode Marketplace
--
-- Args are publisher and extension name
fetchVscodeMarketplace :: Attach PackageFetcher (Text, Text)
fetchVscodeMarketplace :: Attach PackageFetcher (PackageName, PackageName)
fetchVscodeMarketplace PackageSet (Prod r)
e = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageFetcher -> Free PackageSetF (Prod (PackageFetcher : r)))
-> ((PackageName, PackageName) -> PackageFetcher)
-> (PackageName, PackageName)
-> Free PackageSetF (Prod (PackageFetcher : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (PackageName, PackageName) -> PackageFetcher
vscodeMarketplaceFetcher

-- | This package is a tarball, fetched from url
--
-- Arg is a function which constructs the url from a version
fetchTarball :: Attach PackageFetcher (Version -> Text)
fetchTarball :: Attach PackageFetcher (Version -> PackageName)
fetchTarball PackageSet (Prod r)
e Version -> PackageName
f = PackageSet (Prod r)
-> PackageFetcher
-> Free PackageSetF (Prod (Append '[PackageFetcher] r))
Attach PackageFetcher PackageFetcher
fetch PackageSet (Prod r)
e (PackageName -> NixFetcher 'Fresh
tarballFetcher (PackageName -> NixFetcher 'Fresh)
-> (Version -> PackageName) -> PackageFetcher
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Version -> PackageName
f)

--------------------------------------------------------------------------------

-- | Extract files from fetched package source
extractSource :: Attach PackageExtractSrc [FilePath]
extractSource :: Attach PackageExtractSrc [String]
extractSource = ((Free PackageSetF PackageExtractSrc
 -> Free PackageSetF (Prod (PackageExtractSrc : r)))
-> ([String] -> Free PackageSetF PackageExtractSrc)
-> [String]
-> Free PackageSetF (Prod (PackageExtractSrc : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageExtractSrc -> Free PackageSetF PackageExtractSrc
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (PackageExtractSrc -> Free PackageSetF PackageExtractSrc)
-> ([String] -> PackageExtractSrc)
-> [String]
-> Free PackageSetF PackageExtractSrc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. NonEmpty String -> PackageExtractSrc
PackageExtractSrc (NonEmpty String -> PackageExtractSrc)
-> ([String] -> NonEmpty String) -> [String] -> PackageExtractSrc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [String] -> NonEmpty String
forall a. HasCallStack => [a] -> NonEmpty a
NE.fromList) ((Free PackageSetF PackageExtractSrc
  -> Free PackageSetF (Prod (PackageExtractSrc : r)))
 -> [String] -> Free PackageSetF (Prod (PackageExtractSrc : r)))
-> (PackageSet (Prod r)
    -> Free PackageSetF PackageExtractSrc
    -> Free PackageSetF (Prod (PackageExtractSrc : r)))
-> PackageSet (Prod r)
-> [String]
-> Free PackageSetF (Prod (PackageExtractSrc : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageSet (Prod r)
-> Free PackageSetF PackageExtractSrc
-> Free PackageSetF (Prod (PackageExtractSrc : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen

-- | Run 'FetchRustGitDependencies' given the path to @Cargo.lock@ files
--
-- The lock files will be extracted as well.
hasCargoLocks :: Attach PackageCargoLockFiles [FilePath]
hasCargoLocks :: Attach PackageCargoLockFiles [String]
hasCargoLocks = ((Free PackageSetF PackageCargoLockFiles
 -> Free PackageSetF (Prod (PackageCargoLockFiles : r)))
-> ([String] -> Free PackageSetF PackageCargoLockFiles)
-> [String]
-> Free PackageSetF (Prod (PackageCargoLockFiles : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageCargoLockFiles -> Free PackageSetF PackageCargoLockFiles
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (PackageCargoLockFiles -> Free PackageSetF PackageCargoLockFiles)
-> ([String] -> PackageCargoLockFiles)
-> [String]
-> Free PackageSetF PackageCargoLockFiles
forall b c a. (b -> c) -> (a -> b) -> a -> c
. NonEmpty String -> PackageCargoLockFiles
PackageCargoLockFiles (NonEmpty String -> PackageCargoLockFiles)
-> ([String] -> NonEmpty String)
-> [String]
-> PackageCargoLockFiles
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [String] -> NonEmpty String
forall a. HasCallStack => [a] -> NonEmpty a
NE.fromList) ((Free PackageSetF PackageCargoLockFiles
  -> Free PackageSetF (Prod (PackageCargoLockFiles : r)))
 -> [String] -> Free PackageSetF (Prod (PackageCargoLockFiles : r)))
-> (PackageSet (Prod r)
    -> Free PackageSetF PackageCargoLockFiles
    -> Free PackageSetF (Prod (PackageCargoLockFiles : r)))
-> PackageSet (Prod r)
-> [String]
-> Free PackageSetF (Prod (PackageCargoLockFiles : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageSet (Prod r)
-> Free PackageSetF PackageCargoLockFiles
-> Free PackageSetF (Prod (PackageCargoLockFiles : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen

-- | Set 'NvcheckerOptions' for a package, which can tweak the version number we obtain
tweakVersion :: Attach NvcheckerOptions (NvcheckerOptions -> NvcheckerOptions)
tweakVersion :: Attach NvcheckerOptions (NvcheckerOptions -> NvcheckerOptions)
tweakVersion = ((Free PackageSetF NvcheckerOptions
 -> Free PackageSetF (Prod (NvcheckerOptions : r)))
-> ((NvcheckerOptions -> NvcheckerOptions)
    -> Free PackageSetF NvcheckerOptions)
-> (NvcheckerOptions -> NvcheckerOptions)
-> Free PackageSetF (Prod (NvcheckerOptions : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. NvcheckerOptions -> Free PackageSetF NvcheckerOptions
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (NvcheckerOptions -> Free PackageSetF NvcheckerOptions)
-> ((NvcheckerOptions -> NvcheckerOptions) -> NvcheckerOptions)
-> (NvcheckerOptions -> NvcheckerOptions)
-> Free PackageSetF NvcheckerOptions
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ((NvcheckerOptions -> NvcheckerOptions)
-> NvcheckerOptions -> NvcheckerOptions
forall a b. (a -> b) -> a -> b
$ NvcheckerOptions
forall a. Default a => a
def)) ((Free PackageSetF NvcheckerOptions
  -> Free PackageSetF (Prod (NvcheckerOptions : r)))
 -> (NvcheckerOptions -> NvcheckerOptions)
 -> Free PackageSetF (Prod (NvcheckerOptions : r)))
-> (PackageSet (Prod r)
    -> Free PackageSetF NvcheckerOptions
    -> Free PackageSetF (Prod (NvcheckerOptions : r)))
-> PackageSet (Prod r)
-> (NvcheckerOptions -> NvcheckerOptions)
-> Free PackageSetF (Prod (NvcheckerOptions : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageSet (Prod r)
-> Free PackageSetF NvcheckerOptions
-> Free PackageSetF (Prod (NvcheckerOptions : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen

-- | An attrs set to pass through
--
-- Arg is a list of kv pairs
passthru :: Attach PackagePassthru [(Text, Text)]
passthru :: Attach PackagePassthru [(PackageName, PackageName)]
passthru = ((Free PackageSetF PackagePassthru
 -> Free PackageSetF (Prod (PackagePassthru : r)))
-> ([(PackageName, PackageName)]
    -> Free PackageSetF PackagePassthru)
-> [(PackageName, PackageName)]
-> Free PackageSetF (Prod (PackagePassthru : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackagePassthru -> Free PackageSetF PackagePassthru
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (PackagePassthru -> Free PackageSetF PackagePassthru)
-> ([(PackageName, PackageName)] -> PackagePassthru)
-> [(PackageName, PackageName)]
-> Free PackageSetF PackagePassthru
forall b c a. (b -> c) -> (a -> b) -> a -> c
. HashMap PackageName PackageName -> PackagePassthru
PackagePassthru (HashMap PackageName PackageName -> PackagePassthru)
-> ([(PackageName, PackageName)]
    -> HashMap PackageName PackageName)
-> [(PackageName, PackageName)]
-> PackagePassthru
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [(PackageName, PackageName)] -> HashMap PackageName PackageName
forall k v. (Eq k, Hashable k) => [(k, v)] -> HashMap k v
HMap.fromList) ((Free PackageSetF PackagePassthru
  -> Free PackageSetF (Prod (PackagePassthru : r)))
 -> [(PackageName, PackageName)]
 -> Free PackageSetF (Prod (PackagePassthru : r)))
-> (PackageSet (Prod r)
    -> Free PackageSetF PackagePassthru
    -> Free PackageSetF (Prod (PackagePassthru : r)))
-> PackageSet (Prod r)
-> [(PackageName, PackageName)]
-> Free PackageSetF (Prod (PackagePassthru : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageSet (Prod r)
-> Free PackageSetF PackagePassthru
-> Free PackageSetF (Prod (PackagePassthru : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen

-- | Pin a package
--
-- new version won't be checked if we have a stale version
pinned :: PackageSet (Prod r) -> PackageSet (Prod (UseStaleVersion : r))
pinned :: forall (r :: [*]).
PackageSet (Prod r) -> PackageSet (Prod (UseStaleVersion : r))
pinned = (PackageSet (Prod r)
 -> Free PackageSetF UseStaleVersion
 -> PackageSet (Prod (UseStaleVersion : r)))
-> Free PackageSetF UseStaleVersion
-> PackageSet (Prod r)
-> PackageSet (Prod (UseStaleVersion : r))
forall a b c. (a -> b -> c) -> b -> a -> c
flip PackageSet (Prod r)
-> Free PackageSetF UseStaleVersion
-> PackageSet (Prod (UseStaleVersion : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen (Free PackageSetF UseStaleVersion
 -> PackageSet (Prod r) -> PackageSet (Prod (UseStaleVersion : r)))
-> (UseStaleVersion -> Free PackageSetF UseStaleVersion)
-> UseStaleVersion
-> PackageSet (Prod r)
-> PackageSet (Prod (UseStaleVersion : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. UseStaleVersion -> Free PackageSetF UseStaleVersion
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (UseStaleVersion
 -> PackageSet (Prod r) -> PackageSet (Prod (UseStaleVersion : r)))
-> UseStaleVersion
-> PackageSet (Prod r)
-> PackageSet (Prod (UseStaleVersion : r))
forall a b. (a -> b) -> a -> b
$ UseStaleVersion
PermanentStale

-- | Specify the date format for getting git commit date
--
-- Available only for git version source
gitDateFormat :: Attach DateFormat (Maybe Text)
gitDateFormat :: Attach DateFormat (Maybe PackageName)
gitDateFormat = ((Free PackageSetF DateFormat
 -> Free PackageSetF (Prod (DateFormat : r)))
-> (Maybe PackageName -> Free PackageSetF DateFormat)
-> Maybe PackageName
-> Free PackageSetF (Prod (DateFormat : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DateFormat -> Free PackageSetF DateFormat
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (DateFormat -> Free PackageSetF DateFormat)
-> (Maybe PackageName -> DateFormat)
-> Maybe PackageName
-> Free PackageSetF DateFormat
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Maybe PackageName -> DateFormat
DateFormat) ((Free PackageSetF DateFormat
  -> Free PackageSetF (Prod (DateFormat : r)))
 -> Maybe PackageName -> Free PackageSetF (Prod (DateFormat : r)))
-> (PackageSet (Prod r)
    -> Free PackageSetF DateFormat
    -> Free PackageSetF (Prod (DateFormat : r)))
-> PackageSet (Prod r)
-> Maybe PackageName
-> Free PackageSetF (Prod (DateFormat : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PackageSet (Prod r)
-> Free PackageSetF DateFormat
-> Free PackageSetF (Prod (DateFormat : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen

-- | Set always fetching regardless of the version changing
forceFetch :: PackageSet (Prod r) -> PackageSet (Prod (ForceFetch : r))
forceFetch :: forall (r :: [*]).
PackageSet (Prod r) -> PackageSet (Prod (ForceFetch : r))
forceFetch = (PackageSet (Prod r)
 -> Free PackageSetF ForceFetch
 -> PackageSet (Prod (ForceFetch : r)))
-> Free PackageSetF ForceFetch
-> PackageSet (Prod r)
-> PackageSet (Prod (ForceFetch : r))
forall a b c. (a -> b -> c) -> b -> a -> c
flip PackageSet (Prod r)
-> Free PackageSetF ForceFetch
-> PackageSet (Prod (ForceFetch : r))
forall (r :: [*]) a.
PackageSet (Prod r) -> PackageSet a -> PackageSet (Prod (a : r))
forall (f :: * -> *) (r :: [*]) a.
PkgDSL f =>
f (Prod r) -> f a -> f (Prod (a : r))
andThen (Free PackageSetF ForceFetch
 -> PackageSet (Prod r) -> PackageSet (Prod (ForceFetch : r)))
-> (ForceFetch -> Free PackageSetF ForceFetch)
-> ForceFetch
-> PackageSet (Prod r)
-> PackageSet (Prod (ForceFetch : r))
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ForceFetch -> Free PackageSetF ForceFetch
forall a. a -> Free PackageSetF a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ForceFetch
 -> PackageSet (Prod r) -> PackageSet (Prod (ForceFetch : r)))
-> ForceFetch
-> PackageSet (Prod r)
-> PackageSet (Prod (ForceFetch : r))
forall a b. (a -> b) -> a -> b
$ ForceFetch
ForceFetch