diff --git a/README.md b/README.md
--- a/README.md
+++ b/README.md
@@ -6,30 +6,53 @@
 
 # Usage
 
-`query` executes a single query.
-`runQueries` executes multiple queries at once that were created them with `addQuery`
+## Constructing Queries
 
-In extended mode you may want to escape special query characters with `escapeString`
+The data type `Query` is used to represent queries to the server. It specifies
+a search string and the indexes to run the query on, as well as a comment,
+which may be the empty string. In order to run a query on all indexes, use
+`"*"` in the index field.
 
-`buildExcerpts` creates highlighted excerpts
+The convenience function `query` executes a single query and constructs the
+`Query` by itself, so you don't have to.
 
-You will probably need to import the types also:
+To execute more than one `Query`, use `runQueries`. Details are below in the
+section [*Batch Queries*](#batch-queries). To construct simple queries, you can
+also use `simpleQuery :: Text -> Query` which constructs a `Query` over all
+indexes. Don't forget that you can use record updates on a `Query`.
 
+In extended mode you may want to escape special query characters with `escapeString`.
+
+All interaction with the server, including sending queries and receiving
+results, is based on the `Data.Text` string type. You might therefore want to
+enable the `OverloadedStrings` pragma.
+
+## Excerpts and XML Indexes
+
+`buildExcerpts` creates highlighted excerpts.
+
+You will probably need to import the types as well:
+
     import qualified Text.Search.Sphinx as Sphinx
     import qualified Text.Search.Sphinx.Types as SphinxT
 
-There is also an `Indexable` module for generating an xml file of data to be indexed
+There is also an `Indexable` module for generating an xml file of data to be indexed.
 
-## runQueries helpers
+## Batch Queries
 
-`runQueries` pipelines multiple queries together. If you are trying to combine the results, there are some helpers such as `maybeQueries` and `resultsToMatches`
+You can send more than one query per request to the server (which may enable
+server-side query optimization in certain cases. Refer to the
+[Sphinx manual](http://sphinxsearch.com/docs/2.0.4/api-func-addquery.html)
+for details.) The function `runQueries` pipelines multiple queries together. If you
+are trying to combine the results, there are some helpers such as
+`maybeQueries` and `resultsToMatches`.
 
 ~~~~~~ {.haskell}
       mr <- Sphinx.maybeQueries sphinxLogger sphinxConfig [
-                 addQuery "db1" query1
-               , addQuery "db2" query1
-               , addQuery "db1" query2
-               , addQuery "db2" query2
+                 SphinxT.Query query1 "db1" ""
+               , SphinxT.Query query1 "db2" ""
+               , SphinxT.Query query2 "db1" ""
+               , SphinxT.Query query2 "db2" ""
                ]
       case mr of
         Nothing -> return Nothing
@@ -40,9 +63,24 @@
              else return $ Just combined
 ~~~~~~
 
+**A note** for those transitioning from `0.5.*` to `0.6`: the function `addQueries`
+has been removed. You can now directly send a list of `Query` to the server by using
+`runQueries`, which will handle the serialization for you behind the scenes.
 
+## Encoding
 
+The sphinx server itself does not know about encodings except for the
+difference between single-byte encodings and multi-byte encodings. It assumes
+that all incoming queries are already properly encoded and matches the raw
+bytes it receives; the same holds for the results returned by the server. Hence
+the responsibilty for using the proper encoding (and decoding) routines lies
+with the caller.
 
+Version 0.6.0 of `haskell-sphinx-client` introduces the `encoding` field in
+both the `Configuration` data type and the `ExcerptConfiguration` data type.
+The library handles proper encoding and decoding in the background; just
+make sure you set the right encoding setting in the configuration!
+
 Details
 =======
 
@@ -59,4 +97,4 @@
 Usage of this haskell client
 ----------------------------
 Tupil originally wrote this for use on a commercial project.
-This sphinx package is now finding some use in the Yesod community. [Here is a well described example usage](http://www.yesodweb.com/book/sphinx), but do keep in mind there is no requirement to tie the *generation* of sphinx documents to your web application, just your database. Used in Yesod applications yesdoweb.com and eatnutrients.com.
+This sphinx package is now finding some use in the Yesod community. [Here is a well described example usage](https://github.com/yesodweb/yesod/wiki/Sphinx-Search), but do keep in mind there is no requirement to tie the *generation* of sphinx documents to your web application, just your database. Used in Yesod applications yesdoweb.com and eatnutrients.com.
diff --git a/Text/Search/Sphinx.hs b/Text/Search/Sphinx.hs
--- a/Text/Search/Sphinx.hs
+++ b/Text/Search/Sphinx.hs
@@ -5,13 +5,22 @@
 -- setFilterFloatRange, setGeoAnchor
 -- resetFilters, resetGroupBy
 -- updateAttributes,
--- buildKeyWords, escapeString, status, open, close
-module Text.Search.Sphinx ( module Text.Search.Sphinx
+-- buildKeyWords, status, open, close
+module Text.Search.Sphinx 
+  ( escapeText
+  , query
+  , buildExcerpts
+  , runQueries
+  , runQueries'
+  , resultsToMatches
+  , maybeQueries
+  , T.Query(..), simpleQuery
   , Configuration(..), defaultConfig
   ) where
 
 import qualified Text.Search.Sphinx.Types as T (
   Match,
+  Query(..),
   VerCommand(VcSearch, VcExcerpt),
   SearchdCommand(ScSearch, ScExcerpt),
   Filter, Filter(..),
@@ -21,9 +30,9 @@
 
 import Text.Search.Sphinx.Configuration (Configuration(..), defaultConfig)
 import qualified Text.Search.Sphinx.ExcerptConfiguration as ExConf (ExcerptConfiguration(..))
-import Text.Search.Sphinx.Get (times, getResult, readHeader, getStr)
+import Text.Search.Sphinx.Get (times, getResult, readHeader, getStr, getTxt)
 import Text.Search.Sphinx.Put (num, num64, enum, list, numC, strC, foldPuts,
-                              numC64, stringIntList, str, cmd, verCmd)
+                              numC64, stringIntList, str, txt, cmd, verCmd)
 
 import Data.Binary.Put (Put, runPut)
 import Data.Binary.Get (runGet, getWord32be)
@@ -38,6 +47,10 @@
 import Prelude hiding (filter, tail)
 import Data.List (nub)
 
+import Data.Text (Text)
+import qualified Data.Text as X
+import qualified Data.Text.ICU.Convert as ICU
+
 {- the funnest way to debug this is to run the same query with an existing working client and look at the difference
  - sudo tcpflow -i lo dst port 9306 
 import Debug.Trace; debug a = trace (show a) a
@@ -46,23 +59,22 @@
 escapedChars :: String
 escapedChars =  '"':'\\':"-!@~/()*[]="
 
--- | escape all possible meta characters.
---   most of these characters only need to be escaped in certain contexts
+-- | Escape all possible meta characters.
+--   Most of these characters only need to be escaped in certain contexts
 --   however, in normal searching they will all be ignored
-escapeString :: String -> String
-escapeString [] = []
-escapeString (x:xs) = if x `elem` escapedChars
-                        then '\\':x:escapeString xs
-                        else      x:escapeString xs
+escapeText :: Text -> Text
+escapeText = X.intercalate "\\" . breakBy (`elem` escapedChars)
+    where breakBy p t | X.null t  = [X.empty]
+                      | otherwise = (if p $ X.head t then ("":) else id) $ X.groupBy (\_ x -> not $ p x) t
 
 -- | The 'query' function runs a single query against the Sphinx daemon.
---   To pipeline multiple queries in a batch, use addQuery and runQueries
+--   To pipeline multiple queries in a batch, use and 'runQueries'.
 query :: Configuration -- ^ The configuration
-      -> String        -- ^ The indexes, "*" means every index
-      -> String        -- ^ The query string
+      -> Text        -- ^ The indexes, \"*\" means every index
+      -> Text        -- ^ The query string
       -> IO (T.Result T.QueryResult) -- ^ just one search result back
 query config indexes search = do
-    let q = addQuery config search indexes ""
+    let q = T.Query search indexes X.empty
     results <- runQueries' config [q]
     -- same as toSearchResult, but we know there is just one query
     -- could just remove and use runQueries in the future
@@ -75,9 +87,16 @@
       T.Retry   retry           -> T.Retry retry
       T.Warning warning (result:results) -> case result of
                         T.QueryOk result        -> T.Warning warning result
-                        T.QueryWarning w result -> T.Warning (BS.append warning w) result
+                        T.QueryWarning w result -> T.Warning (X.append warning w) result
                         T.QueryError code e     -> T.Error code e
 
+-- | This is a convenience function which accepts a search string and
+-- builds a query for that string over all indexes without attaching
+-- comments to the queries.
+simpleQuery :: Text  -- ^ The query string
+            -> T.Query -- ^ A query value that can be sent to 'runQueries'
+simpleQuery q = T.Query q "*" X.empty
+
 connect :: String -> Int -> IO Handle
 connect host port = do
   connection <- connectTo host (PortNumber $ fromIntegral $ port)
@@ -89,24 +108,25 @@
 
 -- | TODO: add configuration options
 buildExcerpts :: ExConf.ExcerptConfiguration -- ^ Contains host and port for connection and optional configuration for buildExcerpts
-              -> [String]               -- ^ list of document contents to be highlighted
-              -> String                 -- ^ The indexes, "*" means every index
-              -> String                 -- ^ The query string to use for excerpts
-              -> IO (T.Result [BS.ByteString]) -- ^ the documents with excerpts highlighted
+              -> [Text]               -- ^ list of document contents to be highlighted
+              -> Text                 -- ^ The indexes, \"*\" means every index
+              -> Text                  -- ^ The query string to use for excerpts
+              -> IO (T.Result [Text]) -- ^ the documents with excerpts highlighted
 buildExcerpts config docs indexes words = do
   conn <- connect (ExConf.host config) (ExConf.port config)
-  let req = runPut $ makeBuildExcerpt addExcerpt
+  conv <- ICU.open (ExConf.encoding config) Nothing
+  let req = runPut $ makeBuildExcerpt (addExcerpt conv)
   BS.hPut conn req
   hFlush conn
   (status, response) <- getResponse conn
   case status of
-    T.OK      -> return $ T.Ok (getResults response)
-    T.WARNING -> return $ T.Warning (runGet getStr response) (getResults response)
-    T.RETRY   -> return $ T.Retry (errorMessage response)
-    T.ERROR n -> return $ T.Error n (errorMessage response)
+    T.OK      -> return $ T.Ok (getResults response conv)
+    T.WARNING -> return $ T.Warning (runGet (getTxt conv) response) (getResults response conv)
+    T.RETRY   -> return $ T.Retry (errorMessage conv response)
+    T.ERROR n -> return $ T.Error n (errorMessage conv response)
   where
-    getResults response = runGet ((length docs) `times` getStr) response
-    errorMessage response = BS.tail (BS.tail (BS.tail (BS.tail response)))
+    getResults response conv = runGet ((length docs) `times` getTxt conv) response
+    errorMessage conv response = runGet (getTxt conv) (BS.drop 4 response)
 
     makeBuildExcerpt putExcerpt = do
       cmd    T.ScExcerpt
@@ -114,19 +134,19 @@
       num $ fromEnum $ BS.length (runPut putExcerpt)
       putExcerpt
 
-    addExcerpt :: Put
-    addExcerpt = do
+    addExcerpt :: ICU.Converter -> Put
+    addExcerpt conv = do
       num 0 -- mode
       num $ excerptFlags config
-      str indexes
-      str words
+      txt conv indexes
+      txt conv words
       strC config [ExConf.beforeMatch, ExConf.afterMatch, ExConf.chunkSeparator]
       numC config [ExConf.limit, ExConf.around, ExConf.limitPassages, ExConf.limitWords, ExConf.startPassageId]
       str $ ExConf.htmlStripMode config
 #ifndef ONE_ONE_BETA
       str $ ExConf.passageBoundary config
 #endif
-      list str docs
+      list (txt conv) docs
 
     modeFlag :: ExConf.ExcerptConfiguration -> (ExConf.ExcerptConfiguration -> Bool) -> Int -> Int
     modeFlag cfg setting value = if setting cfg then value else 0
@@ -144,10 +164,10 @@
       ])
 
 
--- | Use with addQuery to pipeline multiple queries.
+-- | Make multiple queries at once, using a list of 'T.Query'.
 -- For a single query, just use the query method
 -- Easier handling of query result than runQueries'
-runQueries :: Configuration -> [Put] -> IO (T.Result [T.QueryResult])
+runQueries :: Configuration -> [T.Query] -> IO (T.Result [T.QueryResult])
 runQueries cfg qs = runQueries' cfg qs >>= return . toSearchResult
   where
     --   with batched queries, each query can have an error code,
@@ -161,39 +181,39 @@
     toSearchResult :: T.Result [T.SingleResult] -> T.Result [T.QueryResult]
     toSearchResult results =
         case results of
-          T.Ok rs              -> fromOk rs [] BS.empty
+          T.Ok rs              -> fromOk rs [] X.empty
           T.Warning warning rs -> fromWarn warning rs []
           T.Retry   retry      -> T.Retry retry
           T.Error   code error -> T.Error code error
       where
-        fromOk :: [T.SingleResult] -> [T.QueryResult] -> BS.ByteString -> T.Result [T.QueryResult]
-        fromOk [] acc warn | BS.null warn = T.Ok acc
+        fromOk :: [T.SingleResult] -> [T.QueryResult] -> Text -> T.Result [T.QueryResult]
+        fromOk [] acc warn | X.null warn = T.Ok acc
                            | otherwise = T.Warning warn acc
         fromOk (r:rs) acc warn = case r of
           T.QueryOk result        -> fromOk rs (acc ++ [result]) warn
-          T.QueryWarning w result -> fromOk rs (acc ++ [result]) (BS.append warn w)
+          T.QueryWarning w result -> fromOk rs (acc ++ [result]) (X.append warn w)
           T.QueryError code e     -> T.Error code e
 
-        fromWarn :: BS.ByteString -> [T.SingleResult] -> [T.QueryResult] -> T.Result [T.QueryResult]
+        fromWarn :: Text -> [T.SingleResult] -> [T.QueryResult] -> T.Result [T.QueryResult]
         fromWarn warning [] acc = T.Warning warning acc
         fromWarn warning (r:rs) acc = case r of
           T.QueryOk result        -> fromWarn warning rs (result:acc)
-          T.QueryWarning w result -> fromWarn (BS.append warning w) rs (result:acc)
+          T.QueryWarning w result -> fromWarn (X.append warning w) rs (result:acc)
           T.QueryError code e     -> T.Error code e
 
--- | lower level- called by 'runQueries'
--- | This may be useful for debugging problems- warning messages won't get compressed
-runQueries' :: Configuration -> [Put] -> IO (T.Result [T.SingleResult])
+-- | Lower level- called by 'runQueries'.
+-- This may be useful for debugging problems- warning messages won't get compressed
+runQueries' :: Configuration -> [T.Query] -> IO (T.Result [T.SingleResult])
 runQueries' config qs = do
     conn <- connect (host config) (port config)
-    BS.hPut conn request
+    conv <- ICU.open (encoding config) Nothing
+    let queryReq = foldPuts $ map (serializeQuery config conv) qs
+    BS.hPut conn (request queryReq)
     hFlush conn
-    getSearchResult conn
+    getSearchResult conn conv
   where 
     numQueries = length qs
-    queryReq = foldPuts qs
-
-    request = runPut $ do
+    request qr = runPut $ do
                 cmd T.ScSearch
                 verCmd T.VcSearch
                 num $ 
@@ -202,24 +222,24 @@
 #else
                       8
 #endif
-                        + (fromEnum $ BS.length (runPut queryReq))
+                        + (fromEnum $ BS.length (runPut qr))
 #ifndef ONE_ONE_BETA
                 num 0
 #endif
                 num numQueries
-                queryReq
+                qr
 
-    getSearchResult :: Handle -> IO (T.Result [T.SingleResult])
-    getSearchResult conn = do
+    getSearchResult :: Handle -> ICU.Converter -> IO (T.Result [T.SingleResult])
+    getSearchResult conn conv = do
       (status, response) <- getResponse conn
       case status of
-        T.OK      -> return $ T.Ok (getResults response)
-        T.WARNING -> return $ T.Warning (runGet getStr response) (getResults response)
-        T.RETRY   -> return $ T.Retry (errorMessage response)
-        T.ERROR n -> return $ T.Error n (errorMessage response)
+        T.OK      -> return $ T.Ok (getResults response conv)
+        T.WARNING -> return $ T.Warning (runGet (getTxt conv) response) (getResults response conv)
+        T.RETRY   -> return $ T.Retry (errorMessage conv response)
+        T.ERROR n -> return $ T.Error n (errorMessage conv response)
       where
-        getResults response = runGet (numQueries `times` getResult) response
-        errorMessage response = BS.tail (BS.tail (BS.tail (BS.tail response)))
+        getResults response conv = runGet (numQueries `times` getResult conv) response
+        errorMessage conv response = runGet (getTxt conv) (BS.drop 4 response)
 
 
 -- | Combine results from 'runQueries' into matches.
@@ -237,7 +257,7 @@
 
 -- | executes 'runQueries'. Log warning and errors, automatically retry.
 -- Return a Nothing on error, otherwise a Just.
-maybeQueries :: (BS.ByteString -> IO ()) -> Configuration -> [Put] -> IO (Maybe [T.QueryResult])
+maybeQueries :: (Text -> IO ()) -> Configuration -> [T.Query] -> IO (Maybe [T.QueryResult])
 maybeQueries logCallback conf queries = do
   result <- runQueries conf queries
   case result of
@@ -245,9 +265,8 @@
     T.Retry msg      -> logCallback msg  >> maybeQueries logCallback conf queries
     T.Warning w r    -> logCallback w    >> return (Just r)
     T.Error code msg ->
-      logCallback (BS.concat ["Error code ",BS8.pack $ show code,". ",msg]) >> return Nothing
+      logCallback (X.concat ["Error code ",X.pack $ show code,". ",msg]) >> return Nothing
 
--- | TODO: hide this function
 getResponse :: Handle -> IO (T.Status, BS.ByteString)
 getResponse conn = do
   header <- BS.hGet conn 8
@@ -259,17 +278,17 @@
   return (status, response)
 
 -- | use with runQueries to pipeline a batch of queries
-addQuery :: Configuration -> String -> String -> String -> Put
-addQuery cfg query indexes comment = do
+serializeQuery :: Configuration -> ICU.Converter -> T.Query -> Put
+serializeQuery cfg conv (T.Query qry indexes comment) = do
     numC cfg [ offset
              , limit
              , fromEnum . mode
              , fromEnum . ranker
              , fromEnum . sort]
     str (sortBy cfg)
-    str query
+    txt conv qry
     list num (weights cfg)
-    str indexes
+    txt conv indexes
     num 1                     -- id64 range marker
     numC64 cfg [minId, maxId] -- id64 range
 
@@ -287,7 +306,7 @@
     stringIntList (indexWeights cfg)
     num (maxQueryTime cfg)
     stringIntList (fieldWeights cfg)
-    str comment
+    txt conv comment
     num 0 -- attribute overrides (none)
     str (selectClause cfg) -- select-list
     where
diff --git a/Text/Search/Sphinx/Configuration.hs b/Text/Search/Sphinx/Configuration.hs
--- a/Text/Search/Sphinx/Configuration.hs
+++ b/Text/Search/Sphinx/Configuration.hs
@@ -3,11 +3,28 @@
 import qualified Text.Search.Sphinx.Types as T
 
 -- | The configuration for a query
+--
+-- A note about encodings: The encoding specified here is used to encode
+-- every @Text@ value that is sent to the server, and it used to decode all
+-- of the server's answers, including error messages.
+--
+-- If the specified encoding doesn't support characters sent to the server,
+-- they will silently be substituted with the byte value of @\'\\SUB\' ::
+-- 'Char'@ before transmission.
+--
+-- If the server sends a byte value back that the encoding doesn't understand,
+-- the affected bytes will be converted into special values as
+-- specified by that encoding. For example, when decoding invalid UTF-8,
+-- all invalid bytes are going to be substituted with @\'\\65533\' ::
+-- 'Char'@.
+--
 data Configuration = Configuration {
     -- | The hostname of the Sphinx daemon
     host :: String
     -- | The portnumber of the Sphinx daemon
   , port :: Int
+    -- | Encoding used to encode queries to the server, and decode server responses
+  , encoding :: String
     -- | Per-field weights
   , weights :: [Int]
     -- | How many records to seek from result-set start (default is 0)
@@ -50,7 +67,7 @@
   , maxQueryTime :: Int
     -- | Per-field-name weights
   , fieldWeights :: [(String, Int)]
-    -- | attributes to select, defaults to '*'
+    -- | attributes to select, defaults to \"*\"
   , selectClause :: String -- setSelect in regular API
 }
  deriving (Show)
@@ -59,6 +76,7 @@
 defaultConfig = Configuration {
                   port          = 3312
                 , host          = "127.0.0.1"
+                , encoding      = "UTF-8"
                 , weights       = []
                 , offset        = 0
                 , limit         = 20
diff --git a/Text/Search/Sphinx/ExcerptConfiguration.hs b/Text/Search/Sphinx/ExcerptConfiguration.hs
--- a/Text/Search/Sphinx/ExcerptConfiguration.hs
+++ b/Text/Search/Sphinx/ExcerptConfiguration.hs
@@ -7,6 +7,8 @@
     host :: String
     -- | The portnumber of the Sphinx daemon
   , port :: Int
+    -- | Encoding used to encode queries to the server, and decode server responses
+  , encoding :: String
   , beforeMatch :: String
   , afterMatch :: String
   , chunkSeparator :: String
@@ -33,6 +35,7 @@
 defaultConfig = ExcerptConfiguration {
     port          = 3312
   , host          = "127.0.0.1"
+  , encoding      = "utf8"
   , beforeMatch = "<b>"
   , afterMatch = "</b>"
   , chunkSeparator = "..."
diff --git a/Text/Search/Sphinx/Get.hs b/Text/Search/Sphinx/Get.hs
--- a/Text/Search/Sphinx/Get.hs
+++ b/Text/Search/Sphinx/Get.hs
@@ -10,6 +10,8 @@
 import qualified Text.Search.Sphinx.Types as T
 import Data.Maybe (isJust, fromJust)
 
+import qualified Data.Text.ICU.Convert as ICU
+
 -- Utility functions
 getNum :: Get Int
 getNum = getWord32be >>= return . fromEnum
@@ -24,17 +26,23 @@
                 num `times` f
 times = replicateM
 
+getTxt conv = liftM (ICU.toUnicode conv) getStrStr
+
 getStr = do len <- getNum
             getLazyByteString (fromIntegral len)
 
-getResult :: Get (T.SingleResult)
-getResult = do
+-- Get a strict 'ByteString'.
+getStrStr = do len <- getNum
+               getByteString (fromIntegral len)
+
+getResult :: ICU.Converter -> Get (T.SingleResult)
+getResult conv = do
   statusNum <- getNum
   case T.toQueryStatus statusNum of
-    T.QueryERROR n -> do e <- getStr
+    T.QueryERROR n -> do e <- getTxt conv
                          return $ T.QueryError statusNum e
     T.QueryOK      -> getResultOk >>= return . T.QueryOk
-    T.QueryWARNING -> do w <- getStr
+    T.QueryWARNING -> do w <- getTxt conv
                          getResultOk >>= return . (T.QueryWarning w)
   where
     getResultOk = do
@@ -42,17 +50,18 @@
       attrs      <- readList readAttrPair
       matchCount <- getNum
       id64       <- getNum
-      matches    <- matchCount `times` readMatch (id64 > 0) (map snd attrs)
+      matches    <- matchCount `times` readMatch (id64 > 0) (map snd attrs) conv
       [total, totalFound, time, numWords] <- 4 `times` getNum
-      wrds       <- numWords `times` readWord
+      wrds       <- numWords `times` readWord conv
       return $ T.QueryResult matches total totalFound wrds (map fst attrs)
 
 
-readWord = do s <- getStr
-              [doc, hits] <- 2 `times` getNum
-              return (s, doc, hits)
+readWord conv = do
+    s <- getStrStr
+    [doc, hits] <- 2 `times` getNum
+    return (ICU.toUnicode conv s, doc, hits)
 
-readMatch isId64 attrs = do
+readMatch isId64 attrs conv = do
     doc <- if isId64 then getNum64 else (getNum >>= return . fromIntegral)
     weight <- getNum
     matchAttrs <- mapM readAttr attrs
@@ -60,7 +69,7 @@
   where
     readAttr (T.AttrTMulti attr)  = (readList (readAttr attr)) >>= return . T.AttrMulti
     readAttr T.AttrTBigInt    = getNum64 >>= return . T.AttrBigInt
-    readAttr T.AttrTString    = getStr  >>= return . T.AttrString
+    readAttr T.AttrTString    = getStrStr  >>= return . T.AttrString . ICU.toUnicode conv
     readAttr T.AttrTUInt      = getNum >>= return . T.AttrUInt
     readAttr T.AttrTFloat     = getFloat >>= return . T.AttrFloat
     readAttr _                = getNum  >>= return . T.AttrUInt
diff --git a/Text/Search/Sphinx/Indexable.hs b/Text/Search/Sphinx/Indexable.hs
--- a/Text/Search/Sphinx/Indexable.hs
+++ b/Text/Search/Sphinx/Indexable.hs
@@ -4,7 +4,7 @@
   )
   where
 
-import Data.ByteString.Lazy.UTF8 (toString)
+import Data.Text (unpack)
 import qualified Text.Search.Sphinx.Types as T
 
 --import Text.Search.Sphinx.Types
@@ -37,7 +37,7 @@
 docEl (name, content) = normalEl name `text` indexableEl content
 
 indexableEl (T.AttrUInt i)   = simpleText $ show i
-indexableEl (T.AttrString s) = simpleText $ toString s
+indexableEl (T.AttrString s) = simpleText $ unpack s
 indexableEl (T.AttrFloat f)  = simpleText $ show f
 indexableEl _  = error "not implemented"
 
diff --git a/Text/Search/Sphinx/Put.hs b/Text/Search/Sphinx/Put.hs
--- a/Text/Search/Sphinx/Put.hs
+++ b/Text/Search/Sphinx/Put.hs
@@ -8,6 +8,10 @@
 import qualified Data.ByteString.Lazy as BS
 import qualified Text.Search.Sphinx.Types as T
 
+import Data.Text (Text)
+import qualified Data.Text.ICU.Convert as ICU
+import qualified Data.ByteString as Strict (length)
+
 num     = putWord32be . fromIntegral
 num64 i = putWord64be $ fromIntegral i
 
@@ -39,3 +43,8 @@
 foldPuts [] = return ()
 foldPuts [p] = p
 foldPuts (p:ps) = p >> foldPuts ps
+
+txt :: ICU.Converter -> Text -> Put
+txt conv t = do let bs = ICU.fromUnicode conv t
+                num (fromEnum $ Strict.length bs)
+                putByteString bs
diff --git a/Text/Search/Sphinx/Types.hs b/Text/Search/Sphinx/Types.hs
--- a/Text/Search/Sphinx/Types.hs
+++ b/Text/Search/Sphinx/Types.hs
@@ -6,7 +6,15 @@
 import Data.ByteString.Lazy (ByteString)
 import Data.Int (Int64)
 import Data.Maybe (Maybe, isJust)
+import Data.Text (Text,empty)
 
+-- | Data structure representing one query. It can be sent with 'runQueries'
+-- or 'runQueries'' to the server in batch mode.
+data Query = Query { queryString :: Text -- ^ The actual query string
+                   , queryIndexes :: Text -- ^ The indexes, \"*\" means every index
+                   , queryComment :: Text  -- ^ A comment string.
+                   } deriving (Show)
+
 -- | Search commands
 data SearchdCommand = ScSearch
                     | ScExcerpt
@@ -160,7 +168,7 @@
       -- | Total amount of matching documents in index.
     , totalFound :: Int
       -- | processed words with the number of docs and the number of hits.
-    , words :: [(ByteString, Int, Int)]
+    , words :: [(Text, Int, Int)]
       -- | List of attribute names returned in the result.
       -- | The Match will contain just the attribute values in the same order.
     , attributeNames :: [ByteString]
@@ -169,15 +177,15 @@
 
 -- | a single query result, runQueries returns a list of these
 data SingleResult = QueryOk QueryResult
-                  | QueryWarning ByteString QueryResult
-                  | QueryError Int ByteString
+                  | QueryWarning Text QueryResult
+                  | QueryError Int Text
                   deriving (Show)
 
 -- | a result returned from searchd
 data Result a = Ok a
-              | Warning ByteString a
-              | Error Int ByteString
-              | Retry ByteString
+              | Warning Text a
+              | Error Int Text
+              | Retry Text
               deriving (Show)
 
 data Match = Match {
@@ -196,6 +204,6 @@
 data Attr = AttrMulti [Attr]
           | AttrUInt  Int
           | AttrBigInt Int64
-          | AttrString ByteString
+          | AttrString Text
           | AttrFloat Float
           deriving (Show)
diff --git a/sphinx.cabal b/sphinx.cabal
--- a/sphinx.cabal
+++ b/sphinx.cabal
@@ -1,12 +1,12 @@
 Name:            sphinx
-Version:         0.5.3.1
+Version:         0.6.0
 Synopsis:        Haskell bindings to the Sphinx full-text searching daemon.
 Description:     Haskell bindings to the Sphinx full-text searching daemon. Compatible with Sphinx version 2.0
 Category:        Text, Search, Database
 License:         BSD3
 License-file:    LICENSE
 Author:          Chris Eidhof <ce+sphinx@tupil.com>, Greg Weber
-Maintainer:      Greg Weber <greg@gregweber.info>
+Maintainer:      Greg Weber <greg@gregweber.info>, Aleksandar Dimitrov <aleks.dimitrov@gmail.com>
 homepage:        https://github.com/gregwebs/haskell-sphinx-client
 
 cabal-version:   >= 1.2
@@ -31,7 +31,8 @@
   Build-Depends:   base >= 4 && < 5,
                    binary, data-binary-ieee754,
                    bytestring, network,
-                   xml, utf8-string >= 0.3
+                   xml, 
+                   text < 0.12, text-icu < 0.7
 
   if flag(version-1-1-beta)
     cpp-options:   -DONE_ONE_BETA
