diff --git a/core/src/Streamly/FileSystem/Path.hs b/core/src/Streamly/FileSystem/Path.hs index 166ecf5923..b2e4079862 100644 --- a/core/src/Streamly/FileSystem/Path.hs +++ b/core/src/Streamly/FileSystem/Path.hs @@ -125,7 +125,7 @@ module Streamly.FileSystem.Path , isBranch -- * Combinators - , append + , extend ) where diff --git a/core/src/Streamly/FileSystem/Path/Node.hs b/core/src/Streamly/FileSystem/Path/Node.hs index 68f8b67fa0..5268f040f5 100644 --- a/core/src/Streamly/FileSystem/Path/Node.hs +++ b/core/src/Streamly/FileSystem/Path/Node.hs @@ -30,7 +30,7 @@ module Streamly.FileSystem.Path.Node , fileE -- * Operations - , append + , extend ) where diff --git a/core/src/Streamly/FileSystem/Path/Seg.hs b/core/src/Streamly/FileSystem/Path/Seg.hs index a4036b4f9e..b53ac1e57f 100644 --- a/core/src/Streamly/FileSystem/Path/Seg.hs +++ b/core/src/Streamly/FileSystem/Path/Seg.hs @@ -30,7 +30,7 @@ module Streamly.FileSystem.Path.Seg , brE -- * Operations - , append + , extend ) where diff --git a/core/src/Streamly/FileSystem/Path/SegNode.hs b/core/src/Streamly/FileSystem/Path/SegNode.hs index 54d8e705be..8dc9ed5b09 100644 --- a/core/src/Streamly/FileSystem/Path/SegNode.hs +++ b/core/src/Streamly/FileSystem/Path/SegNode.hs @@ -30,7 +30,7 @@ module Streamly.FileSystem.Path.SegNode , brfileE -- * Operations - , append + , extend ) where diff --git a/core/src/Streamly/Internal/FileSystem/DirIO.hs b/core/src/Streamly/Internal/FileSystem/DirIO.hs index b83ab05164..5b0fc88c56 100644 --- a/core/src/Streamly/Internal/FileSystem/DirIO.hs +++ b/core/src/Streamly/Internal/FileSystem/DirIO.hs @@ -314,7 +314,7 @@ toStreamWithBufferOf chunkSize h = AS.concat $ toChunksWithBufferOf chunkSize h eitherReaderPaths ::(MonadIO m, MonadCatch m) => (ReadOptions -> ReadOptions) -> Unfold m Path (Either Path Path) eitherReaderPaths f = - let () = Path.append + let () = Path.extend in UF.mapM2 (\dir -> return . bimap (dir ) (dir )) (eitherReader f) -- @@ -359,7 +359,7 @@ readEither f = S.unfold (eitherReader f) readEitherPaths :: (MonadIO m, MonadCatch m) => (ReadOptions -> ReadOptions) -> Path -> Stream m (Either Path Path) readEitherPaths f dir = - let () = Path.append + let () = Path.extend in fmap (bimap (dir ) (dir )) $ readEither f dir #if defined(mingw32_HOST_OS) || defined(__MINGW32__) diff --git a/core/src/Streamly/Internal/FileSystem/Posix/ReadDir.hsc b/core/src/Streamly/Internal/FileSystem/Posix/ReadDir.hsc index c28b3931a1..5b03efae1b 100644 --- a/core/src/Streamly/Internal/FileSystem/Posix/ReadDir.hsc +++ b/core/src/Streamly/Internal/FileSystem/Posix/ReadDir.hsc @@ -931,7 +931,7 @@ readEitherByteChunksAt confMod (ppath, alldirs) = {- if ndirs > 64 then do - let fpath = Path.unsafeAppend ppath curdir + let fpath = Path.unsafeExtend ppath curdir return $ Yield (Left (fpath, dirs1)) (ByteChunksAtLoop pfd dirp curdir xs [] 0 mbarr pos1) @@ -961,7 +961,7 @@ readEitherByteChunksAt confMod (ppath, alldirs) = -- help parallelize more in IO bound case. if ndirs > 0 then do - let fpath = Path.unsafeAppend ppath curdir + let fpath = Path.unsafeExtend ppath curdir return $ Yield (Left (fpath, dirs)) (ByteChunksAtInit pfd xs mbarr pos) diff --git a/core/src/Streamly/Internal/FileSystem/PosixPath.hs b/core/src/Streamly/Internal/FileSystem/PosixPath.hs index 4477f25116..e996a4eb6f 100644 --- a/core/src/Streamly/Internal/FileSystem/PosixPath.hs +++ b/core/src/Streamly/Internal/FileSystem/PosixPath.hs @@ -133,17 +133,17 @@ module Streamly.Internal.FileSystem.OS_PATH -- * Joining , addString -- , concat - , unsafeAppend -- XXX unsafeExtend + , unsafeExtend #ifndef IS_WINDOWS - , appendCString -- XXX extendByCString - , appendCString' + , extendByCString + , extendByCString' #endif - , append -- XXX rename to "extend" to emphasize asymmetric nature? - , append' -- XXX rename to extendDir, to avoid pinned confusion? + , extend + , extendDir , unsafeJoinPaths -- * Splitting - -- | Note: you can use 'unsafeAppend' as a replacement for the joinDrive + -- | Note: you can use 'unsafeExtend' as a replacement for the joinDrive -- function in the filepath package. , splitRoot , splitPath @@ -299,7 +299,7 @@ hasTrailingSeparator (OS_PATH arr) = -- {-# INLINE addTrailingSeparator #-} addTrailingSeparator :: OS_PATH -> OS_PATH -addTrailingSeparator p = unsafeAppend p sep +addTrailingSeparator p = unsafeExtend p sep where @@ -576,10 +576,9 @@ isBranch :: OS_PATH -> Bool isBranch = not . isRooted #ifndef IS_WINDOWS --- | Like 'append' but does not check if any of the path is empty or if the --- second path is rooted. +-- | Like 'extend' but does not check if the second path is rooted. -- --- >>> f a b = Path.toString $ Path.unsafeAppend (pack a) (pack b) +-- >>> f a b = Path.toString $ Path.unsafeExtend (pack a) (pack b) -- -- >>> f "x" "y" -- "x/y" @@ -590,21 +589,19 @@ isBranch = not . isRooted -- >>> f "x/" "/y" -- "x/y" -- -{-# INLINE unsafeAppend #-} -unsafeAppend :: OS_PATH -> OS_PATH -> OS_PATH -unsafeAppend (OS_PATH a) (OS_PATH b) = +{-# INLINE unsafeExtend #-} +unsafeExtend :: OS_PATH -> OS_PATH -> OS_PATH +unsafeExtend (OS_PATH a) (OS_PATH b) = OS_PATH $ Common.unsafeAppend Common.OS_NAME (Common.toString Unicode.UNICODE_DECODER) a b --- XXX rename it to extend or combine? - --- | Append a OS_PATH to another. Fails if the second path refers to a rooted --- path. If you want to avoid runtime failure use the typesafe --- Streamly.FileSystem.OS_PATH.Seg module. Use 'unsafeAppend' to avoid failure --- if you know it is ok to append the path. +-- | Extend an OS_PATH by appending another one to it. Fails if the second path +-- refers to a rooted path. If you want to avoid runtime failure use the +-- typesafe Streamly.FileSystem.OS_PATH.Seg module. Use 'unsafeExtend' to avoid +-- failure if you know it is ok to append the path. -- --- >>> f a b = Path.toString $ Path.append a b +-- >>> f a b = Path.toString $ Path.extend a b -- -- >>> f [path|/usr|] [path|bin|] -- "/usr/bin" @@ -613,23 +610,23 @@ unsafeAppend (OS_PATH a) (OS_PATH b) = -- >>> fails (f [path|/usr|] [path|/bin|]) -- True -- -append :: OS_PATH -> OS_PATH -> OS_PATH -append (OS_PATH a) (OS_PATH b) = +extend :: OS_PATH -> OS_PATH -> OS_PATH +extend (OS_PATH a) (OS_PATH b) = OS_PATH $ Common.append Common.OS_NAME (Common.toString Unicode.UNICODE_DECODER) a b --- | A stricter version of 'append' which requires the first path to be a +-- | A stricter version of 'extend' which requires the first path to be a -- directory like path i.e. with a trailing separator. -- --- >>> f a b = Path.toString $ Path.append' a b +-- >>> f a b = Path.toString $ Path.extendDir a b -- -- >>> fails $ f [path|/usr|] [path|bin|] -- True -- -append' :: +extendDir :: OS_PATH -> OS_PATH -> OS_PATH -append' +extendDir (OS_PATH a) (OS_PATH b) = OS_PATH $ Common.append' @@ -640,21 +637,21 @@ append' -- XXX add appendCWString for Windows? #ifndef IS_WINDOWS --- | Append a separator and a CString to the Array. This is like 'unsafeAppend' +-- | Append a separator and a CString to the Array. This is like 'unsafeExtend' -- but always inserts a separator between the two paths even if the first path -- has a trailing separator or second path has a leading separator. -- -appendCString :: OS_PATH -> CString -> IO OS_PATH -appendCString (OS_PATH a) str = +extendByCString :: OS_PATH -> CString -> IO OS_PATH +extendByCString (OS_PATH a) str = fmap OS_PATH $ Common.appendCString Common.OS_NAME a str -- | Like 'appendCString' but creates a pinned path. -- -appendCString' :: +extendByCString' :: OS_PATH -> CString -> IO OS_PATH -appendCString' +extendByCString' (OS_PATH a) str = fmap OS_PATH $ Common.appendCString' @@ -684,7 +681,7 @@ unsafeJoinPaths = undefined -- Some filepath package equivalent idioms: -- -- >>> splitDrive = Path.splitRoot --- >>> joinDrive = Path.unsafeAppend +-- >>> joinDrive = Path.unsafeExtend -- >>> takeDrive = fmap fst . Path.splitRoot -- >>> dropDrive x = Path.splitRoot x >>= snd -- >>> hasDrive = isJust . Path.splitRoot @@ -844,8 +841,8 @@ splitPath_ (OS_PATH a) = fmap OS_PATH $ Common.splitPath_ Common.OS_NAME a -- >>> takeBaseName = fmap Path.dropExtension . takeFileName -- >>> dropFileName x = Path.splitFile x >>= fst -- >>> takeDirectory x = Path.splitFile x >>= fst --- >>> replaceFileName p x = fmap (flip Path.append x) (takeDirectory p) --- >>> replaceDirectory p x = fmap (flip Path.append x) (takeFileName p) +-- >>> replaceFileName p x = fmap (flip Path.extend x) (takeDirectory p) +-- >>> replaceDirectory p x = fmap (flip Path.extend x) (takeFileName p) -- -- >>> toList (a,b) = (fmap Path.toString a, Path.toString b) -- >>> split = fmap toList . Path.splitFile . pack diff --git a/core/src/Streamly/Internal/FileSystem/PosixPath/Node.hs b/core/src/Streamly/Internal/FileSystem/PosixPath/Node.hs index 1aeb025056..d07ac62906 100644 --- a/core/src/Streamly/Internal/FileSystem/PosixPath/Node.hs +++ b/core/src/Streamly/Internal/FileSystem/PosixPath/Node.hs @@ -42,7 +42,7 @@ module Streamly.Internal.FileSystem.OS_PATH.Node , fileE -- * Operations - , append + , extend ) where @@ -147,15 +147,15 @@ file = mkQ fileE -- | Append a 'Dir' or 'File' path to a 'Dir' path. -- --- >>> Path.toString (Node.append [dir|/usr|] [dir|bin|] :: Dir PosixPath) +-- >>> Path.toString (Node.extend [dir|/usr|] [dir|bin|] :: Dir PosixPath) -- "/usr/bin" --- >>> Path.toString (Node.append [dir|/usr|] [file|bin|] :: File PosixPath) +-- >>> Path.toString (Node.extend [dir|/usr|] [file|bin|] :: File PosixPath) -- "/usr/bin" -- -- Fails if the second path is a specific location and not a path segment. -- -{-# INLINE append #-} -append :: (IsPath OS_PATH (a OS_PATH), IsNode (a OS_PATH)) => +{-# INLINE extend #-} +extend :: (IsPath OS_PATH (a OS_PATH), IsNode (a OS_PATH)) => Dir OS_PATH -> a OS_PATH -> a OS_PATH -append (Dir a) b = - unsafeFromPath $ OsPath.unsafeAppend (toPath a) (toPath b) +extend (Dir a) b = + unsafeFromPath $ OsPath.unsafeExtend (toPath a) (toPath b) diff --git a/core/src/Streamly/Internal/FileSystem/PosixPath/Seg.hs b/core/src/Streamly/Internal/FileSystem/PosixPath/Seg.hs index 659fd17c76..3830f2a1b1 100644 --- a/core/src/Streamly/Internal/FileSystem/PosixPath/Seg.hs +++ b/core/src/Streamly/Internal/FileSystem/PosixPath/Seg.hs @@ -47,7 +47,7 @@ module Streamly.Internal.FileSystem.OS_PATH.Seg , brE -- * Operations - , append + , extend ) where @@ -156,15 +156,16 @@ br = mkQ brE -- | Append a 'Branch' type path to a 'Rooted' path or 'Branch' path. -- --- >>> Path.toString (Seg.append [rt|/usr|] [br|bin|] :: Rooted PosixPath) +-- >>> Path.toString (Seg.extend [rt|/usr|] [br|bin|] :: Rooted PosixPath) -- "/usr/bin" --- >>> Path.toString (Seg.append [br|usr|] [br|bin|] :: Branch PosixPath) +-- >>> Path.toString (Seg.extend [br|usr|] [br|bin|] :: Branch PosixPath) -- "usr/bin" -- -{-# INLINE append #-} -append :: +{-# INLINE extend #-} +extend :: ( IsSeg (a OS_PATH) , IsPath OS_PATH (a OS_PATH) ) => a OS_PATH -> Branch OS_PATH -> a OS_PATH -append a (Branch c) = unsafeFromPath $ OsPath.unsafeAppend (toPath a) (toPath c) +extend a (Branch c) = + unsafeFromPath $ OsPath.unsafeExtend (toPath a) (toPath c) diff --git a/core/src/Streamly/Internal/FileSystem/PosixPath/SegNode.hs b/core/src/Streamly/Internal/FileSystem/PosixPath/SegNode.hs index 3054a682d5..a3124ec22e 100644 --- a/core/src/Streamly/Internal/FileSystem/PosixPath/SegNode.hs +++ b/core/src/Streamly/Internal/FileSystem/PosixPath/SegNode.hs @@ -1,5 +1,5 @@ {-# LANGUAGE TemplateHaskell #-} --- For constraints on "append" +-- For constraints on "extend" {-# OPTIONS_GHC -Wno-redundant-constraints #-} {-# OPTIONS_GHC -Wno-orphans #-} @@ -40,7 +40,7 @@ module Streamly.Internal.FileSystem.OS_PATH.SegNode , brfileE -- * Operations - , append + , extend ) where @@ -245,39 +245,39 @@ brfile = mkQ brfileE -- If the second path does not have 'File' or 'Dir' information then the return -- type too cannot have it. -- --- >> Path.toString (SegNode.append [rtdir|/usr|] [br|bin|] :: Rooted PosixPath) +-- >> Path.toString (SegNode.extend [rtdir|/usr|] [br|bin|] :: Rooted PosixPath) -- "/usr/bin" --- >> Path.toString (SegNode.append [brdir|usr|] [br|bin|] :: Branch PosixPath) +-- >> Path.toString (SegNode.extend [brdir|usr|] [br|bin|] :: Branch PosixPath) -- "usr/bin" -- --- >> Path.toString (SegNode.append [rt|/usr|] [br|bin|] :: Rooted PosixPath) +-- >> Path.toString (SegNode.extend [rt|/usr|] [br|bin|] :: Rooted PosixPath) -- "/usr/bin" --- >> Path.toString (SegNode.append [br|usr|] [br|bin|] :: Branch PosixPath) +-- >> Path.toString (SegNode.extend [br|usr|] [br|bin|] :: Branch PosixPath) -- "usr/bin" -- -- If the second path has 'File' or 'Dir' information then the return type -- also has it. -- --- >> Path.toString (SegNode.append [rt|/usr|] [brdir|bin|] :: Rooted (Dir PosixPath)) +-- >> Path.toString (SegNode.extend [rt|/usr|] [brdir|bin|] :: Rooted (Dir PosixPath)) -- "/usr/bin" --- >> Path.toString (SegNode.append [rt|/usr|] [brfile|bin|] :: Rooted (File PosixPath)) +-- >> Path.toString (SegNode.extend [rt|/usr|] [brfile|bin|] :: Rooted (File PosixPath)) -- "/usr/bin" --- >> Path.toString (SegNode.append [br|usr|] [brdir|bin|] :: Branch (Dir PosixPath)) +-- >> Path.toString (SegNode.extend [br|usr|] [brdir|bin|] :: Branch (Dir PosixPath)) -- "usr/bin" --- >> Path.toString (SegNode.append [br|usr|] [brfile|bin|] :: Branch (File PosixPath)) +-- >> Path.toString (SegNode.extend [br|usr|] [brfile|bin|] :: Branch (File PosixPath)) -- "usr/bin" -- -- Type error cases: -- --- >> SegNode.append [dir|/usr|] [br|bin|] -- first arg must be Rooted/Branch --- >> SegNode.append [file|/usr|] [br|bin|] -- first arg must be Rooted/Branch --- >> SegNode.append [rtfile|/usr|] [br|bin|] -- first arg must be a dir --- >> SegNode.append [rt|/usr|] [rt|/bin|] -- second arg must be seg --- >> SegNode.append [rt|/usr|] [dir|bin|] -- second arg must be seg --- >> SegNode.append [rt|/usr|] [file|bin|] -- second arg must be seg +-- >> SegNode.extend [dir|/usr|] [br|bin|] -- first arg must be Rooted/Branch +-- >> SegNode.extend [file|/usr|] [br|bin|] -- first arg must be Rooted/Branch +-- >> SegNode.extend [rtfile|/usr|] [br|bin|] -- first arg must be a dir +-- >> SegNode.extend [rt|/usr|] [rt|/bin|] -- second arg must be seg +-- >> SegNode.extend [rt|/usr|] [dir|bin|] -- second arg must be seg +-- >> SegNode.extend [rt|/usr|] [file|bin|] -- second arg must be seg -- -{-# INLINE append #-} -append :: +{-# INLINE extend #-} +extend :: ( IsSeg (a b) , HasDir (a b) @@ -285,26 +285,26 @@ append :: , IsPath OS_PATH c , IsPath OS_PATH (a c) ) => a b -> Branch c -> a c -append a (Branch c) = unsafeFromPath $ OS_NAME.unsafeAppend (toPath a) (toPath c) +extend a (Branch c) = unsafeFromPath $ OS_NAME.unsafeExtend (toPath a) (toPath c) -} -- | Append a branch type path to a directory. -- --- >>> Path.toString (SegNode.append [rtdir|/usr|] [brdir|bin|] :: Rooted (Dir PosixPath)) +-- >>> Path.toString (SegNode.extend [rtdir|/usr|] [brdir|bin|] :: Rooted (Dir PosixPath)) -- "/usr/bin" --- >>> Path.toString (SegNode.append [rtdir|/usr|] [brfile|bin|] :: Rooted (File PosixPath)) +-- >>> Path.toString (SegNode.extend [rtdir|/usr|] [brfile|bin|] :: Rooted (File PosixPath)) -- "/usr/bin" --- >>> Path.toString (SegNode.append [brdir|usr|] [brdir|bin|] :: Branch (Dir PosixPath)) +-- >>> Path.toString (SegNode.extend [brdir|usr|] [brdir|bin|] :: Branch (Dir PosixPath)) -- "usr/bin" --- >>> Path.toString (SegNode.append [brdir|usr|] [brfile|bin|] :: Branch (File PosixPath)) +-- >>> Path.toString (SegNode.extend [brdir|usr|] [brfile|bin|] :: Branch (File PosixPath)) -- "usr/bin" -- -{-# INLINE append #-} -append :: +{-# INLINE extend #-} +extend :: ( IsPath OS_PATH (a (Dir OS_PATH)) , IsPath OS_PATH (b OS_PATH) , IsPath OS_PATH (a (b OS_PATH)) ) => a (Dir OS_PATH) -> Branch (b OS_PATH) -> a (b OS_PATH) -append p1 (Branch p2) = - unsafeFromPath $ OsPath.unsafeAppend (toPath p1) (toPath p2) +extend p1 (Branch p2) = + unsafeFromPath $ OsPath.unsafeExtend (toPath p1) (toPath p2) diff --git a/core/src/Streamly/Internal/FileSystem/WindowsPath.hs b/core/src/Streamly/Internal/FileSystem/WindowsPath.hs index 139da10619..05e8d00ddc 100644 --- a/core/src/Streamly/Internal/FileSystem/WindowsPath.hs +++ b/core/src/Streamly/Internal/FileSystem/WindowsPath.hs @@ -219,10 +219,10 @@ readRaw = fromJust . fromChunk . read isRooted :: OS_PATH -> Bool isRooted (OS_PATH arr) = Common.isRooted Common.OS_NAME arr --- | Like 'append' but does not check if any of the path is empty or if the +-- | Like 'extend' but does not check if any of the path is empty or if the -- second path is rooted. -- --- >>> f a b = Path.toString $ Path.unsafeAppend (pack a) (pack b) +-- >>> f a b = Path.toString $ Path.unsafeExtend (pack a) (pack b) -- -- >>> f "x" "y" -- "x\\y" @@ -233,9 +233,9 @@ isRooted (OS_PATH arr) = Common.isRooted Common.OS_NAME arr -- >>> f "x/" "/y" -- "x/y" -- --- Note "c:" and "/x" are both rooted paths, therefore, 'append' cannot be used +-- Note "c:" and "/x" are both rooted paths, therefore, 'extend' cannot be used -- to join them. Similarly for joining "//x/" and "/y". For these cases use --- 'unsafeAppend'. 'unsafeAppend' can be used as a replacement for the +-- 'unsafeExtend'. 'unsafeExtend' can be used as a replacement for the -- joinDrive function from the filepath package. -- -- >>> f "c:" "/x" @@ -243,27 +243,27 @@ isRooted (OS_PATH arr) = Common.isRooted Common.OS_NAME arr -- >>> f "//x/" "/y" -- "//x/y" -- -{-# INLINE unsafeAppend #-} -unsafeAppend :: OS_PATH -> OS_PATH -> OS_PATH -unsafeAppend (OS_PATH a) (OS_PATH b) = +{-# INLINE unsafeExtend #-} +unsafeExtend :: OS_PATH -> OS_PATH -> OS_PATH +unsafeExtend (OS_PATH a) (OS_PATH b) = OS_PATH $ Common.unsafeAppend Common.OS_NAME (Common.toString Unicode.UNICODE_DECODER) a b -- | Append a OS_PATH to another. Fails if the second path refers to a rooted -- path. If you want to avoid runtime failure use the typesafe --- Streamly.FileSystem.OS_PATH.Seg module. Use 'unsafeAppend' to avoid failure +-- Streamly.FileSystem.OS_PATH.Seg module. Use 'unsafeExtend' to avoid failure -- if you know it is ok to append the path. -- -- Usually, append joins two paths using a separator between the paths. On -- Windows, joining a drive "c:" with path "x" does not add a separator between -- the two because "c:x" is different from "c:/x". -- --- Note "c:" and "/x" are both rooted paths, therefore, append cannot be used +-- Note "c:" and "/x" are both rooted paths, therefore, 'extend' cannot be used -- to join them. Similarly for joining "//x/" and "/y". For these cases use --- 'unsafeAppend'. +-- 'unsafeExtend'. -- --- >>> f a b = Path.toString $ Path.append a b +-- >>> f a b = Path.toString $ Path.extend a b -- -- >>> f [path|x|] [path|y|] -- "x\\y" @@ -284,23 +284,23 @@ unsafeAppend (OS_PATH a) (OS_PATH b) = -- True -- >>> fails $ f [path|//x/|] [path|/y|] -- True -append :: OS_PATH -> OS_PATH -> OS_PATH -append (OS_PATH a) (OS_PATH b) = +extend :: OS_PATH -> OS_PATH -> OS_PATH +extend (OS_PATH a) (OS_PATH b) = OS_PATH $ Common.append Common.OS_NAME (Common.toString Unicode.UNICODE_DECODER) a b --- | A stricter version of 'append' which requires the first path to be a +-- | A stricter version of 'extend' which requires the first path to be a -- directory like path i.e. with a trailing separator. -- --- >>> f a b = Path.toString $ Path.append' a b +-- >>> f a b = Path.toString $ Path.extendDir a b -- -- >>> fails $ f [path|x|] [path|y|] -- True -- -append' :: +extendDir :: OS_PATH -> OS_PATH -> OS_PATH -append' +extendDir (OS_PATH a) (OS_PATH b) = OS_PATH $ Common.append'