diff --git a/salak.cabal b/salak.cabal
--- a/salak.cabal
+++ b/salak.cabal
@@ -1,6 +1,6 @@
 cabal-version: 1.12
 name: salak
-version: 0.3.2
+version: 0.3.3
 license: MIT
 license-file: LICENSE
 copyright: 2019 Daniel YU
@@ -24,7 +24,9 @@
         Salak.Internal.Val
         Salak.Internal.Source
         Salak.Internal.Prop
+        Salak.Internal.Writable
     default-language: Haskell2010
+    default-extensions: RecordWildCards
     ghc-options: -Wall -fno-warn-orphans -fno-warn-missing-signatures
     build-depends:
         attoparsec >=0.13.2.2 && <0.14,
@@ -55,9 +57,11 @@
         Salak.Internal.Prop
         Salak.Internal.Source
         Salak.Internal.Val
+        Salak.Internal.Writable
         Salak.Trie
         Paths_salak
     default-language: Haskell2010
+    default-extensions: RecordWildCards
     ghc-options: -Wall -fno-warn-orphans -fno-warn-missing-signatures
     build-depends:
         QuickCheck >=2.13.2 && <2.14,
diff --git a/src/Salak.hs b/src/Salak.hs
--- a/src/Salak.hs
+++ b/src/Salak.hs
@@ -39,6 +39,7 @@
   , SourcePack
   , Salak
   , SalakException(..)
+  , module Salak.Internal.Writable
   -- * Load Functions
   -- ** Monad for Loader
   , LoadSalakT
@@ -74,6 +75,7 @@
 import           Salak.Internal
 import           Salak.Internal.Prop
 import           Salak.Internal.Source
+import           Salak.Internal.Writable
 import           System.Directory
 import           System.FilePath         ((</>))
 
@@ -82,12 +84,12 @@
 
 -- | Prop load configuration
 data PropConfig = PropConfig
-  { configKey     :: Text          -- ^ Specify config key, default is @application@.
-  , configName    :: String        -- ^ Specify config name, default is @application@.
-  , searchCurrent :: Bool          -- ^ Search current directory, default true.
-  , searchHome    :: Bool          -- ^ Search home directory, default false.
-  , commandLine   :: ParseCommandLine -- ^ How to parse commandline.
-  , loggerF       :: LFunc
+  { configKey     :: !Text          -- ^ Specify config key, default is @application@.
+  , configName    :: !String        -- ^ Specify config name, default is @application@.
+  , searchCurrent :: !Bool          -- ^ Search current directory, default true.
+  , searchHome    :: !Bool          -- ^ Search home directory, default false.
+  , commandLine   :: !ParseCommandLine -- ^ How to parse commandline.
+  , loggerF       :: !LFunc
   , loadExt       :: FilePath -> LoadSalak ()
   }
 
diff --git a/src/Salak/Internal.hs b/src/Salak/Internal.hs
--- a/src/Salak/Internal.hs
+++ b/src/Salak/Internal.hs
@@ -50,6 +50,7 @@
   , liftNT
   , SourcePack(..)
   , MonadIO
+  , module Salak.Internal.Writable
   ) where
 
 
@@ -70,18 +71,19 @@
 import           Salak.Internal.Prop
 import           Salak.Internal.Source
 import           Salak.Internal.Val
+import           Salak.Internal.Writable
 import qualified Salak.Trie              as T
 import           System.Directory
 import           System.Environment
 
 data UpdateSource = UpdateSource
-  {  ref    :: MVar Source
-  ,  refNo  :: Int
-  ,  refMap :: HashMap Int String
-  ,  lfunc  :: MVar LFunc
-  ,  qfunc  :: MVar QFunc
-  ,  update :: MVar (IO ( TraceSource -- Updated Tries
-                  , IO ()))    -- Confirm action
+  {  ref    :: !(MVar Source)
+  ,  refNo  :: !Int
+  ,  refMap :: !(HashMap Int String)
+  ,  lfunc  :: !(MVar LFunc)
+  ,  qfunc  :: !(MVar QFunc)
+  ,  update :: !(MVar (IO ( TraceSource -- Updated Tries
+                  , IO ())))    -- Confirm action
   }
 
 -- | Configuration Loader Monad, used for load properties from sources. Custom loaders using `loadTrie`
diff --git a/src/Salak/Internal/Source.hs b/src/Salak/Internal/Source.hs
--- a/src/Salak/Internal/Source.hs
+++ b/src/Salak/Internal/Source.hs
@@ -17,8 +17,8 @@
 
 -- | Reload result, show erros or changes.
 data ReloadResult = ReloadResult
-  { hasError :: Bool     -- ^ If reload process has errors.
-  , msgs     :: [String] -- ^ If hasError then this show error messages, else this show change logs.
+  { hasError :: !Bool     -- ^ If reload process has errors.
+  , msgs     :: ![String] -- ^ If hasError then this show error messages, else this show change logs.
   } deriving Show
 
 type QFunc = Source -> Either String (IO ())
@@ -26,11 +26,11 @@
 type LFunc = String -> IO ()
 
 data SourcePack = SourcePack
-  { source :: Source
-  , pref   :: [Key]
-  , qref   :: MVar QFunc
-  , lref   :: MVar LFunc
-  , reload :: IO ReloadResult
+  { source :: !Source
+  , pref   :: ![Key]
+  , qref   :: !(MVar QFunc)
+  , lref   :: !(MVar LFunc)
+  , reload :: !(IO ReloadResult)
   }
 
 diff :: Source -> Source -> T.Trie ModType
diff --git a/src/Salak/Internal/Writable.hs b/src/Salak/Internal/Writable.hs
new file mode 100644
--- /dev/null
+++ b/src/Salak/Internal/Writable.hs
@@ -0,0 +1,38 @@
+module Salak.Internal.Writable(
+  -- ** Writable Value
+    Writable
+  , toWritable
+  , getWritable
+  , setWritable
+  ) where
+
+import           Control.Concurrent.MVar
+import           Control.Monad
+
+-- | Writable data structure. `Writable` is designed for working with `IO` value pased by salak. 
+-- It provide a way to override `IO` value provided by salak, can be used in the application which need to change 
+-- values of some configurations by overriding it directly. For example, logger function can use a log level property
+-- to control which level of logs should be printed. By using `Writeable` value, we can change the property 
+-- directly.
+data Writable a = Writable
+  { valRef :: IO a
+  , setRef :: MVar (Maybe a)
+  }
+
+-- | Convert a `IO` value to `Writable` value.
+toWritable :: IO a -> IO (Writable a)
+toWritable valRef = do
+  setRef <- newMVar Nothing
+  return Writable{..}
+
+-- | Get value.
+getWritable :: Writable a -> IO a
+getWritable Writable{..} = do
+  v <- readMVar setRef
+  case v of
+    Just a -> return a
+    _      -> valRef
+
+-- | Set or remove override value.
+setWritable :: Maybe a -> Writable a -> IO ()
+setWritable s Writable{..} = void $ swapMVar setRef s
