diff --git a/LICENSE b/LICENSE
new file mode 100644
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,21 @@
+The MIT License (MIT)
+
+Copyright (c) 2014 Roman Gonzalez
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
diff --git a/Setup.hs b/Setup.hs
new file mode 100644
--- /dev/null
+++ b/Setup.hs
@@ -0,0 +1,2 @@
+import Distribution.Simple
+main = defaultMain
diff --git a/src/Tiempo.hs b/src/Tiempo.hs
new file mode 100644
--- /dev/null
+++ b/src/Tiempo.hs
@@ -0,0 +1,271 @@
+{-# LANGUAGE DeriveDataTypeable #-}
+module Tiempo
+  ( TimeInterval
+  -- * TimeInterval to different units and types
+  , toMicroSeconds
+  , toMilliSeconds
+  , toSeconds
+  , toMinutes
+  , toHours
+  , toDays
+  , toNominalDiffTime
+
+  -- * Time manipulation
+  , fromTime
+  , fromNow
+  , agoTime
+  , ago
+
+  -- * Concurrency Utilities
+  , threadDelay
+
+  -- * Unit functions
+  , microSeconds
+  , milliSeconds
+  , seconds
+  , minutes
+  , hours
+  , days ) where
+
+import qualified Control.Concurrent as Concurrent (threadDelay)
+import           Control.DeepSeq    (NFData (..))
+import           Data.Time          (NominalDiffTime, UTCTime, addUTCTime,
+                                     getCurrentTime)
+import           Data.Typeable      (Typeable)
+
+--------------------------------------------------------------------------------
+
+data  TimeUnit
+  = Days | Hours | Minutes | Seconds | Millis | Micros
+  deriving (Eq, Show, Typeable)
+
+instance NFData TimeUnit
+
+data TimeInterval
+  = TimeInterval !TimeUnit !Int
+  deriving (Eq, Show)
+
+instance NFData TimeInterval where
+  rnf (TimeInterval unit n) =
+    unit `seq` n `seq` ()
+
+--------------------------------------------------------------------------------
+
+-- | converts the supplied @TimeInterval@ to microseconds
+toMicroSeconds :: TimeInterval -> Int
+toMicroSeconds (TimeInterval u v) = timeToMicros u v
+{-# INLINE toMicroSeconds #-}
+
+-- | converts the supplied @TimeInterval@ to milliseconds
+toMilliSeconds :: TimeInterval -> Double
+toMilliSeconds (TimeInterval u v) = timeToMillis u v
+{-# INLINE toMilliSeconds #-}
+
+-- | converts the supplied @TimeInterval@ to seconds
+toSeconds :: TimeInterval -> Double
+toSeconds (TimeInterval u v) = timeToSeconds u v
+{-# INLINE toSeconds #-}
+
+-- | converts the supplied @TimeInterval@ to minutes
+toMinutes :: TimeInterval -> Double
+toMinutes (TimeInterval u v) = timeToMinutes u v
+{-# INLINE toMinutes #-}
+
+-- | converts the supplied @TimeInterval@ to hours
+toHours :: TimeInterval -> Double
+toHours (TimeInterval u v) = timeToHours u v
+{-# INLINE toHours #-}
+
+
+-- | converts the supplied @TimeInterval@ to days
+toDays :: TimeInterval -> Double
+toDays (TimeInterval u v) = timeToDays u v
+{-# INLINE toDays #-}
+
+-- | converts the supplied @TimeInterval@ to NominalDiffTime
+toNominalDiffTime :: TimeInterval -> NominalDiffTime
+toNominalDiffTime (TimeInterval u v) = realToFrac $ timeToSeconds u v
+{-# INLINE toNominalDiffTime #-}
+
+--------------------------------------------------------------------------------
+
+-- | Adds @TimeInterval@ to @UTCTime@ returning a @UTCTime@ in the
+-- future
+fromTime :: TimeInterval ->  UTCTime -> UTCTime
+fromTime interval = addUTCTime (toNominalDiffTime interval)
+{-# INLINE fromTime #-}
+
+-- | Adds @TimeInterval@ to @getCurrentTime@ returning a
+-- @UTCTime@ in the future
+fromNow :: TimeInterval -> IO UTCTime
+fromNow interval = fromTime interval `fmap` getCurrentTime
+{-# INLINE fromNow #-}
+
+-- | Substracts @TimeInterval@ from @UTCTime@ returning a @UTCTime@ in
+-- the past
+agoTime :: TimeInterval -> UTCTime -> UTCTime
+agoTime interval = addUTCTime (realToFrac (-1 * toSeconds interval))
+{-# INLINE agoTime #-}
+
+-- | Substracts @TimeInterval@ from @getCurrentTime@ returning a
+-- @UTCTime@ in the past
+ago :: TimeInterval -> IO UTCTime
+ago interval = agoTime interval `fmap` getCurrentTime
+{-# INLINE ago #-}
+
+--------------------------------------------------------------------------------
+
+-- | Like @Control.Concurrent.threadDelay@ but accepts a
+-- @TimeInterval@ instead of an Int
+threadDelay :: TimeInterval -> IO ()
+threadDelay = Concurrent.threadDelay . toMicroSeconds
+{-# INLINE threadDelay #-}
+
+--------------------------------------------------------------------------------
+
+-- | given a number, produces a @TimeInterval@ of microseconds
+microSeconds :: Int -> TimeInterval
+microSeconds = TimeInterval Micros
+{-# INLINE microSeconds #-}
+
+-- | given a number, produces a @TimeInterval@ of milliseconds
+milliSeconds :: Int -> TimeInterval
+milliSeconds = TimeInterval Millis
+{-# INLINE milliSeconds #-}
+
+-- | given a number, produces a @TimeInterval@ of seconds
+seconds :: Int -> TimeInterval
+seconds = TimeInterval Seconds
+{-# INLINE seconds #-}
+
+-- | given a number, produces a @TimeInterval@ of minutes
+minutes :: Int -> TimeInterval
+minutes = TimeInterval Minutes
+{-# INLINE minutes #-}
+
+-- | given a number, produces a @TimeInterval@ of hours
+hours :: Int -> TimeInterval
+hours = TimeInterval Hours
+{-# INLINE hours #-}
+
+-- | given a number, produces a @TimeInterval@ of days
+days :: Int -> TimeInterval
+days = TimeInterval Days
+{-# INLINE days #-}
+--------------------------------------------------------------------------------
+
+-- | converts the supplied @TimeUnit@ to microseconds
+timeToMicros :: TimeUnit -> Int -> Int
+timeToMicros Micros us = us
+timeToMicros Millis ms = ms * (10 ^ (3 :: Int)) -- (1000µs == 1ms)
+timeToMicros Seconds secs = timeToMicros Millis (secs * milliSecondsPerSecond)
+timeToMicros Minutes mins = timeToMicros Seconds (mins * secondsPerMinute)
+timeToMicros Hours hrs = timeToMicros Minutes (hrs * minutesPerHour)
+timeToMicros Days dys = timeToMicros Hours (dys * hoursPerDay)
+{-# INLINE timeToMicros #-}
+
+timeToMillis :: TimeUnit -> Int -> Double
+timeToMillis Micros us = fromIntegral us / fromIntegral microSecondsPerMillis
+timeToMillis Millis ms = fromIntegral ms
+timeToMillis Seconds secs = fromIntegral secs * (10 ^ (3 :: Int))
+timeToMillis Minutes mins = timeToMillis Seconds (mins * secondsPerMinute)
+timeToMillis Hours hrs = timeToMillis Minutes (hrs * minutesPerHour)
+timeToMillis Days dys = timeToMillis Hours (dys * hoursPerDay)
+{-# INLINE timeToMillis #-}
+
+timeToSeconds :: TimeUnit -> Int -> Double
+timeToSeconds Micros us =
+  fromIntegral us / fromIntegral (microSecondsPerMillis * milliSecondsPerSecond)
+timeToSeconds Millis ms = fromIntegral ms / fromIntegral milliSecondsPerSecond
+timeToSeconds Seconds secs = fromIntegral secs
+timeToSeconds Minutes mins = fromIntegral $ mins * secondsPerMinute
+timeToSeconds Hours hrs = timeToSeconds Minutes (hrs * minutesPerHour)
+timeToSeconds Days dys = timeToSeconds Hours (dys * hoursPerDay)
+{-# INLINE timeToSeconds #-}
+
+
+timeToMinutes :: TimeUnit -> Int -> Double
+timeToMinutes Micros us =
+    fromIntegral us / fromIntegral microsPerHour
+  where
+    microsPerHour = product [ microSecondsPerMillis
+                            , milliSecondsPerSecond
+                            , secondsPerMinute ]
+timeToMinutes Millis ms = fromIntegral ms / fromIntegral microsPerMin
+  where
+    microsPerMin = product [ milliSecondsPerSecond
+                           , secondsPerMinute ]
+timeToMinutes Seconds secs = fromIntegral secs / fromIntegral secondsPerMinute
+timeToMinutes Minutes mins = fromIntegral mins
+timeToMinutes Hours hrs = timeToMinutes Minutes (hrs * minutesPerHour)
+timeToMinutes Days dys = timeToMinutes Hours (dys * hoursPerDay)
+{-# INLINE timeToMinutes #-}
+
+
+timeToHours :: TimeUnit -> Int -> Double
+timeToHours Micros us = fromIntegral us / fromIntegral microsPerHour
+  where
+    microsPerHour = product [ microSecondsPerMillis
+                            , milliSecondsPerSecond
+                            , secondsPerMinute
+                            , minutesPerHour ]
+timeToHours Millis ms = fromIntegral ms / fromIntegral millisPerHour
+  where
+    millisPerHour = product [ milliSecondsPerSecond
+                            , secondsPerMinute
+                            , minutesPerHour ]
+timeToHours Seconds secs =
+  fromIntegral secs / fromIntegral (secondsPerMinute * minutesPerHour)
+timeToHours Minutes mins =
+  fromIntegral mins / fromIntegral minutesPerHour
+timeToHours Hours hrs = fromIntegral hrs
+timeToHours Days dys = timeToHours Hours (dys * hoursPerDay)
+{-# INLINE timeToHours #-}
+
+
+timeToDays :: TimeUnit -> Int -> Double
+timeToDays Micros us = fromIntegral us / fromIntegral microsPerDay
+  where
+    microsPerDay = product [ microSecondsPerMillis
+                           , milliSecondsPerSecond
+                           , secondsPerMinute
+                           , minutesPerHour
+                           , hoursPerDay ]
+timeToDays Millis ms = fromIntegral ms / fromIntegral millisPerDay
+  where
+    millisPerDay = product [ milliSecondsPerSecond
+                           , secondsPerMinute
+                           , minutesPerHour
+                           , hoursPerDay ]
+timeToDays Seconds secs = fromIntegral secs / fromIntegral secondsPerDay
+  where
+    secondsPerDay = product [ secondsPerMinute
+                            , minutesPerHour
+                            , hoursPerDay ]
+timeToDays Minutes mins =
+  fromIntegral mins / fromIntegral (minutesPerHour * hoursPerDay)
+timeToDays Hours hrs = fromIntegral $ hrs * hoursPerDay
+timeToDays Days dys = fromIntegral dys
+{-# INLINE timeToDays #-}
+
+--------------------------------------------------------------------------------
+
+hoursPerDay :: Int
+hoursPerDay = 24
+{-# INLINE hoursPerDay #-}
+
+minutesPerHour :: Int
+minutesPerHour = 60
+{-# INLINE minutesPerHour #-}
+
+secondsPerMinute :: Int
+secondsPerMinute = 60
+{-# INLINE secondsPerMinute #-}
+
+milliSecondsPerSecond :: Int
+milliSecondsPerSecond = 1000
+{-# INLINE milliSecondsPerSecond #-}
+
+microSecondsPerMillis :: Int
+microSecondsPerMillis = 1000
+{-# INLINE microSecondsPerMillis #-}
diff --git a/tiempo.cabal b/tiempo.cabal
new file mode 100644
--- /dev/null
+++ b/tiempo.cabal
@@ -0,0 +1,28 @@
+-- Initial tiempo.cabal generated by cabal init.  For further
+-- documentation, see http://haskell.org/cabal/users-guide/
+
+name:                tiempo
+version:             0.0.0.0
+synopsis:            Specify time intervals in different units (secs, mins, hours, etc.)
+description:         A sane and simple API that sits on top of the time library; it allows the creation
+                     of time intervals and provides to manipulate time using them.
+homepage:            http://github.com/HaskVan/tiempo
+license:             MIT
+license-file:        LICENSE
+author:              Roman Gonzalez
+maintainer:          romanandreg@gmail.com
+category:            Data, Time
+build-type:          Simple
+cabal-version:       >=1.10
+
+library
+  exposed-modules:
+        Tiempo
+  -- other-modules:
+  -- other-extensions:
+  build-depends:
+        base >=4.6 && <4.7,
+        deepseq >= 1.3 && <1.4,
+        time
+  hs-source-dirs:      src
+  default-language:    Haskell2010
