úÎș­ŻyŒ      !"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~€‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—˜™š›œžŸ ĄąŁ€„Чš©Ș«Ź­źŻ°±ČłŽ”¶·žčș»oC3This class allows selective behaviour for file and 3 directory paths and is mostly for internal use. DE7This class allows selective behaviour for absolute and 2 relative paths and is mostly for internal use. FŒ3This class provides a way to prevent other modules  from making further E or C  instances GHIJKLMNœŸżO,This is the main filepath abstract datatype ÀÁ7Invariant - this should always have type :: DirPath ar PQRST%Map over the components of the path. S> pathMap (map toLower) "/tmp/Reports/SpreadSheets" == "/tmp/reports/spreadsheets" ÂĂCurrently not exported ÄCurrently not exported U Convert the O into a plain Ć. This is simply an  alias for Æ. ÇVWXUse a Ć as a O whose type is determined  by its context. > asPath "/tmp" == "/tmp" "> asPath "file.txt" == "file.txt" /> isAbsolute (asPath "/tmp" :: AbsDir) == True 0> isAbsolute (asPath "/tmp" :: RelDir) == False 4> getPathString (asPath "/tmp" :: AbsDir) == "/tmp" 3> getPathString (asPath "/tmp" :: RelDir) == "tmp" YUse a Ć as a M. No checking is done. 5> getPathString (asRelFile "file.txt") == "file.txt" 6> getPathString (asRelFile "/file.txt") == "file.txt" +> getPathString (asRelFile "tmp") == "tmp" ,> getPathString (asRelFile "/tmp") == "tmp" ZUse a Ć as a K. No checking is done. 4> getPathString (asRelDir "file.txt") == "file.txt" 5> getPathString (asRelDir "/file.txt") == "file.txt" *> getPathString (asRelDir "tmp") == "tmp" +> getPathString (asRelDir "/tmp") == "tmp" [Use a Ć as an N. No checking is done. 6> getPathString (asAbsFile "file.txt") == "/file.txt" 7> getPathString (asAbsFile "/file.txt") == "/file.txt" ,> getPathString (asAbsFile "tmp") == "/tmp" -> getPathString (asAbsFile "/tmp") == "/tmp" \Use a Ć as an L. No checking is done. 5> getPathString (asAbsDir "file.txt") == "/file.txt" 6> getPathString (asAbsDir "/file.txt") == "/file.txt" +> getPathString (asAbsDir "tmp") == "/tmp" ,> getPathString (asAbsDir "/tmp") == "/tmp" ]Use a Ć as a ' RelPath fd'. No checking is done. ^Use a Ć as an ' AbsPath fd'. No checking is done. _Use a Ć as a ' FilePath ar'. No checking is done. `Use a Ć as a ' DirPath ar'. No checking is done. a;Examines the supplied string and constructs an absolute or  relative path as appropriate. => either id (const "fred") (mkPathAbsOrRel "/tmp") == "/tmp" => either id (const "fred") (mkPathAbsOrRel "tmp") == "fred" b?Searches for a file or directory with the supplied path string  and returns a Q or P( path as appropriate. If neither exists  at the supplied path, È is returned. c Convert a Ć into an J by interpreting it as 4 relative to the supplied directory if necessary. /> mkAbsPath "/tmp" "foo.txt" == "/tmp/foo.txt" 4> mkAbsPath "/tmp" "/etc/foo.txt" == "/etc/foo.txt" d Convert a Ć into an J by interpreting it as % relative to the cwd if necessary. ÉILift a function which can operate on either Abs or Rel Path to one which  operates on Strings. A At present this fn is the only reason we have Rank-2 types, it' s also not ( doing anything useful at present. We may want to expose it later though  so leave it for now... ÊËÌÍe>Join an (absolute or relative) directory path with a relative 0 (file or directory) path to form a new path. fCWe only allow files (and not directories) to have extensions added ' by this function. This is because it's the vastly common case and E an attempt to add one to a directory will - more often than not -  represent an error.  We don'9t however want to prevent the corresponding operation on D directories, and so we provide a function that is more flexible:  ‘. g6Add an extension, even if there is already one there.  E.g.  addExtension "foo.txt" "bat" -> " foo.txt.bat". 2> addExtension "file.txt" "bib" == "file.txt.bib" -> addExtension "file." ".bib" == "file..bib" +> addExtension "file" ".bib" == "file.bib" 1> takeFileName (addExtension "" "ext") == ".ext" h>Join an (absolute or relative) directory path with a relative 0 (file or directory) path to form a new path. iRemove last extension, and the "." preceding it. ,> dropExtension x == fst (splitExtension x) jDrop all extensions *> not $ hasAnExtension (dropExtensions x) klASet the extension of a file, overwriting one if already present. 3> replaceExtension "file.txt" ".bob" == "file.bob" 2> replaceExtension "file.txt" "bob" == "file.bob" /> replaceExtension "file" ".bob" == "file.bob" +> replaceExtension "file.txt" "" == "file" <> replaceExtension "file.fred.bob" "txt" == "file.fred.txt" mnopSplit on the extension. g is the inverse. (> uncurry (<.>) (splitExtension x) == x /> uncurry addExtension (splitExtension x) == x /> splitExtension "file.txt" == ("file",".txt") '> splitExtension "file" == ("file","") 9> splitExtension "file/file.txt" == ("file/file",".txt") ;> splitExtension "file.txt/boris" == ("file.txt/boris","") C> splitExtension "file.txt/boris.ext" == ("file.txt/boris",".ext") K> splitExtension "file/path.txt.bob.fred" == ("file/path.txt.bob",".fred") qSplit on all extensions 6> splitExtensions "file.tar.gz" == ("file",".tar.gz") ÎrÏsGet the basename of a file 5> takeBaseName "/tmp/somedir/myfile.txt" == "myfile" *> takeBaseName "./myfile.txt" == "myfile" (> takeBaseName "myfile.txt" == "myfile" tu%Get the extension of a file, returns "" for no extension, .ext otherwise. ,> takeExtension x == snd (splitExtension x) 1> takeExtension (addExtension x "ext") == ".ext" 5> takeExtension (replaceExtension x "ext") == ".ext" vGet all extensions ,> takeExtensions "file.tar.gz" == ".tar.gz" wIGet the filename component of a file path (ie stripping all parent dirs) 9> takeFileName "/tmp/somedir/myfile.txt" == "myfile.txt" .> takeFileName "./myfile.txt" == "myfile.txt" ,> takeFileName "myfile.txt" == "myfile.txt" Đx3Check whether two strings are equal as file paths. '> equalFilePath "/tmp/" "/tmp" == True (> equalFilePath "/tmp" "tmp" == False y Constructs a O from a list of components. D> joinPath ["/tmp","someDir","file.txt"] == "/tmp/someDir/file.txt" P> (joinPath ["/tmp","someDir","file.txt"] :: RelFile) == "tmp/someDir/file.txt" zCurrently just transforms: => normalise "/tmp/fred/./jim/./file" == "/tmp/fred/jim/file" {)Deconstructs a path into its components. _> splitPath ("/tmp/someDir/myfile.txt" :: AbsDir) == (["tmp","someDir","myfile.txt"],Nothing) \> splitPath ("/tmp/someDir/myfile.txt" :: AbsFile) == (["tmp","someDir"],Just "myfile.txt") \> splitPath (asAbsFile "/tmp/someDir/myfile.txt") == (["tmp","someDir"],Just "myfile.txt") |CThis function can be used to construct a relative path by removing  the supplied L! from the front. It is a runtime Ń if the  supplied J doesn't start with the L. Z> makeRelative "/tmp/somedir" "/tmp/somedir/anotherdir/file.txt" == "anotherdir/file.txt" }@Joins an absolute directory with a relative path to construct a  new absolute path. 9> makeAbsolute "/tmp" "file.txt" == "/tmp/file.txt" >> makeAbsolute "/tmp" "adir/file.txt" == "/tmp/adir/file.txt" ~1Converts a relative path into an absolute one by - prepending the current working directory. As for }+, but for use when the path may already be 2 absolute (in which case it is left unchanged). M> genericMakeAbsolute "/tmp" (asRelFile "file.txt") == "/tmp/file.txt" R> genericMakeAbsolute "/tmp" (asRelFile "adir/file.txt") == "/tmp/adir/file.txt" N> genericMakeAbsolute "/tmp" (asAbsFile "adir/file.txt") == "/adir/file.txt" N> genericMakeAbsolute "/tmp" (asAbsFile "/adir/file.txt") == "/adir/file.txt" €As for ~+, but for use when the path may already be 2 absolute (in which case it is left unchanged). ÒӁTest whether a O ar fd is absolute. )> isAbsolute (asAbsFile "fred") == True *> isAbsolute (asRelFile "fred") == False )> isAbsolute (asAbsFile "/fred") == True *> isAbsolute (asRelFile "/fred") == False ‚Test whether the Ć& would correspond to an absolute path  if interpreted as a O. ƒ7Invariant - this should return True iff arg is of type O Rel _  isRelative = not . isAbsolute „Test whether the Ć% would correspond to a relative path  if interpreted as a O. + isRelativeString = not . isAbsoluteString …+Does the given filename have an extension? 3> null (takeExtension x) == not (hasAnExtension x) †2Does the given filename have the given extension? )> hasExtension ".hs" "MyCode.hs" == True .> hasExtension ".hs" "MyCode.hs.bak" == False -> hasExtension ".hs" "MyCode.bak.hs" == True ‡This is largely for System.FilePath compatability ˆThis is largely for System.FilePath compatability ‰File extension character > extSeparator == '.' ŠThis is largely for System.FilePath compatability ‹FThe character that separates directories. In the case where more than  one character is possible, ‹ is the 'ideal' one.  > isPathSeparator pathSeparator Œ%The list of all possible separators. &> pathSeparator `elem` pathSeparators VThe character that is used to separate the entries in the $PATH environment variable. Ž)Is the character an extension character? *> isExtSeparator a == (a == extSeparator) Rather than using (== ‹), use this. Test if something  is a path separator. 1> isPathSeparator a == (a `elem` pathSeparators) #Is the character a file separator? 8> isSearchPathSeparator a == (a == searchPathSeparator) ‘#This is a more flexible variant of g / f which can " work with files or directories '> genericAddExtension "/" "x" == "/.x" ’“”•–—ÔŐÖŚŰÙ*Allow use of OverloadedStrings if desired UCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~€‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—UOSRQPNMLKJIHGEFCDUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~€T‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—UCDDEFFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~€‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—˜™š›œ An alias for Ÿ. žTRetrieve the contents of a directory path (which may be relative) as absolute paths ŸReturns paths relative to0 the supplied (abs or relative) directory path. ( eg (for current working directory of / somewhere/cwd/): C show (relDirectoryContents "d/e/f/") == (["subDir1A","subDir1B"], K ["file1A","file1B"])  A convenient alternative to Ÿ if you only want files. ĄA convenient alternative to Ÿ if you only want directories. ąŁ€„Чš©Ș«Ź­źŻ°±ČÚB˜™š›œžŸ ĄąŁ€„Чš©Ș«Ź­źŻ°±Č˜™š›œžŸ ĄąŁ€„Чš©Ș«Ź­źŻB°±Č˜™š›œžŸ ĄąŁ€„Чš©Ș«Ź­źŻ°±Č łŽ”¶·žčș»ÛK  !"#$%&'()*+,-./0123456789:;<=>?@AłŽ”¶·žčș»KłŽ”¶·žčș»42A=>?@&%$#8567!3 '<9:;10/".-, +)*( łŽ”¶·žčș»Ü      !"#$%&'()*+,-./01232425262728292:2;2<=>?@?A?B?C?DEFEGEHEIJKJLJMJNJOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~€‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—˜™š›œžŸ ĄąŁ€„Чš©Ș«Ź­źŻ°±ČłŽ”¶·žčș»ŒœŸżÀÁÂĂÄĆÆÇÈÉÊËÌÍÍÎÏĐŃÒÓÔŐÖŚŰÙÚÛÜĘȚßàáâăäćæçèéêëìççípathtype-0.0.2System.Path.IOSystem.Path.Directory System.Pathbase System.IOprintghc-prim GHC.TypesIOfixIOhPrint hPutStrLnhReadyreadIOreadLninteract getContentsgetLinegetCharputStrLnputStrputCharGHC.IO.Handle.FDisEOFstderrstdin GHC.IO.HandlehShowhSetBinaryModehIsTerminalDevicehGetEchohSetEcho hIsSeekable hGetBuffering hIsWritable hIsReadable hIsClosedhIsOpenhTellhSeekhSetPosnhGetPosn hSetBuffering hLookAheadhIsEOF hSetFileSize hFileSizehClose HandlePosnGHC.IO.Handle.TexthGetBufNonBlockinghGetBufhPutBufNonBlockinghPutBufhPutStrhPutChar hGetContentshGetLinehGetChar hWaitForInputstdouthFlushGHC.IO.Handle.TypesHandle NoBuffering LineBufferingBlockBuffering BufferMode GHC.IO.Device AbsoluteSeek RelativeSeek SeekFromEndSeekMode GHC.IO.IOModeReadMode WriteMode AppendMode ReadWriteModeIOModedirectory-1.0.1.1System.Directory Permissions FileDirClassfileDir AbsRelClassabsRelDirPathFilePathRelPathAbsPathRelDirAbsDirRelFileAbsFilePathDirFileRelAbspathMap getPathStringrootDir currentDirasPath asRelFileasRelDir asAbsFileasAbsDir asRelPath asAbsPath asFilePath asDirPathmkPathAbsOrRelmkPathFileOrDir mkAbsPathmkAbsPathFromCwd<.> addExtensioncombine dropExtensiondropExtensions dropFileNamereplaceExtensionreplaceBaseNamereplaceDirectoryreplaceFileNamesplitExtensionsplitExtensions splitFileName takeBaseName takeDirectory takeExtensiontakeExtensions takeFileName equalFilePathjoinPath normalise splitPath makeRelative makeAbsolutemakeAbsoluteFromCwdgenericMakeAbsolutegenericMakeAbsoluteFromCwd isAbsoluteisAbsoluteString isRelativeisRelativeStringhasAnExtension hasExtensionaddTrailingPathSeparatordropTrailingPathSeparator extSeparatorhasTrailingPathSeparator pathSeparatorpathSeparatorssearchPathSeparatorisExtSeparatorisPathSeparatorisSearchPathSeparatorgenericAddExtensiongenericDropExtensiongenericDropExtensionsgenericSplitExtensiongenericSplitExtensionsgenericTakeExtensiongenericTakeExtensionscreateDirectorycreateDirectoryIfMissingremoveDirectoryremoveDirectoryRecursiverenameDirectorygetDirectoryContentsabsDirectoryContentsrelDirectoryContents filesInDir dirsInDirgetCurrentDirectorysetCurrentDirectorygetHomeDirectorygetAppUserDataDirectorygetUserDocumentsDirectorygetTemporaryDirectory removeFile renameFilecopyFilecanonicalizePathmakeRelativeToCurrentDirectoryfindExecutable doesFileExistdoesDirectoryExistgetPermissionssetPermissionsgetModificationTimewithFileopenFilereadFile writeFile appendFilewithBinaryFileopenBinaryFile openTempFileopenBinaryTempFilePrivate PathComponentunPathComponentFileDirPathRootpcMap pathAbsRel pathFileDirGHC.BaseStringGHC.Showshowprop_asPath_getPathString Data.MaybeNothing onPathStringmkPathFromComponentsmkPathComponentspathComponents(prop_mkPathFromComponents_pathComponentsprop_splitCombineprop_split_combineprop_takeFileName_endGHC.Errerror prop_makeAbsoluteFromDir_endSame"prop_makeAbsoluteFromDir_startSamevectorOfqcFileComponentqcDirComponent qcFilePath qcDirPath$fIsStringPath