diff --git a/changes.txt b/changes.txt
--- a/changes.txt
+++ b/changes.txt
@@ -1,8 +1,14 @@
+0.1.2.7
+-------
+
+- Released Mon 20 Jul 2015 19:38:12 CEST
+- allowed naked todos (w/o desc) (requested by qptain nemo).
+
 0.1.2.6
 -------
 
 - Released Mon 13 Jul 2015 12:24:24 CEST
-- added shell script syntax (.sh) (requeste by qptain nemo).
+- added shell script syntax (.sh) (requested by qptain nemo).
 
 0.1.2.5
 -------
diff --git a/doc/usr/page.rst b/doc/usr/page.rst
--- a/doc/usr/page.rst
+++ b/doc/usr/page.rst
@@ -118,6 +118,8 @@
   /* Xxx: add to version control.
           Ask Timothy */
 
+  -- FIXME
+
 
 You can optionally put tags at the end of your issue, like this:
 
diff --git a/lentil.cabal b/lentil.cabal
--- a/lentil.cabal
+++ b/lentil.cabal
@@ -1,5 +1,5 @@
 name:                lentil
-version:             0.1.2.6
+version:             0.1.2.7
 synopsis:            frugal issue tracker
 description:         minumum effort, cohesive issue tracker based on
                      ubiquitous @TODO@s and @FIXME@s conventions.
diff --git a/src/Lentil/Args.hs b/src/Lentil/Args.hs
--- a/src/Lentil/Args.hs
+++ b/src/Lentil/Args.hs
@@ -143,22 +143,16 @@
                          help "filters for description NOT matching EXPR" )
 
 tag :: Parser LFilter
-tag = option optTxt ( short 't'       <>
-                      metavar "EXPR"  <>
-                      help "filter for tag matching EXPR" )
+tag = option (filterTags <$> str)
+                       ( short 't'       <>
+                         metavar "EXPR"  <>
+                         help "filter for tag matching EXPR" )
 
 notag :: Parser LFilter
-notag = option (negFilter <$> optTxt)
+notag = option (negFilter . filterTags <$> str)
                        ( short 'T'       <>
                          metavar "EXPR"  <>
                          help "filter for tag NOT matching EXPR" )
-
-
-optTxt :: ReadM LFilter
-optTxt = str >>= \oStr ->
-           if oStr == "^"
-             then return filterTagless
-             else return (filterTags oStr)
 
 
 -----------------
diff --git a/src/Lentil/Export.hs b/src/Lentil/Export.hs
--- a/src/Lentil/Export.hs
+++ b/src/Lentil/Export.hs
@@ -22,14 +22,14 @@
 issues2CSV is = printCSV (firstLine : map i2r is)
     where firstLine = ["Filepath", "Row", "Description", "Tags"]
           i2r i     = [(prettyFP . iFile) i, show (iRow i),
-                       iDesc i, tags2String (iTags i)]
+                       iPPDesc i, tags2String (iTags i)]
 
 
 -- compiler-like (gcc/ghc) warnings, parseable by emacs
 issues2Compiler :: [Issue] -> String
 issues2Compiler is = L.intercalate "\n" (map i2c is)
     where i2c i = (prettyFP . iFile) i ++ ":" ++ show (iRow i) ++ ":\n" ++
-                  "   " ++ iDesc i ++ " " ++
+                  "   " ++ iPPDesc i ++ " " ++
                   tags2StringPretty (iTags i) ++ "\n"
 
 
diff --git a/src/Lentil/Parse/Issue.hs b/src/Lentil/Parse/Issue.hs
--- a/src/Lentil/Parse/Issue.hs
+++ b/src/Lentil/Parse/Issue.hs
@@ -103,10 +103,10 @@
 -- incipit have to be bound at the beginning of line (won't pick up stuff
 -- in the middle of a sentence)
 incipit :: ParIssue FlagWord
-incipit = char '\n' >> spaces >>
-          fwpar               >>= \fw ->
-          optional (char ':') >>
-          many1 (char ' ')    >>
+incipit = char '\n' >> spaces    >>
+          fwpar                  >>= \fw ->
+          optional (char ':')    >>
+          notFollowedBy alphaNum >> -- real todo, not todoodle
           return fw
           <?> "incipit"
     where
@@ -142,8 +142,13 @@
 
 -- any text. Since tags/fields at the end of the issue are optional, we need
 -- a way to delimit this. Delimiters are: eof, tags/fields, blank line
-freeText :: ParIssue Description
-freeText = fmap htmlify (manyTill anyChar end) <?> "free text"
+freeText :: ParIssue (Maybe Description)
+freeText = fmap htmlify (manyTill anyChar end) >>= \t ->
+           case t of
+             [] -> return Nothing
+             _  -> return $ Just t
+
+         <?> "free text"
     where vp p      = try . parsecMap (const ()) $ p
           end       = lookAhead $ choice [vp (spaces1 *> tag),
                                           vp blankline, -- \n\n or \neof
diff --git a/src/Lentil/Print.hs b/src/Lentil/Print.hs
--- a/src/Lentil/Print.hs
+++ b/src/Lentil/Print.hs
@@ -52,7 +52,7 @@
                                          hang 0 (fillSep $ ppDescTags is)] )
     where
           ppDescTags :: Issue -> [Doc]
-          ppDescTags i = map string (words (iDesc is)) ++
+          ppDescTags i = map string (words (iPPDesc is)) ++
                          map (ppTag Blue) (iTags i)
 
           spInd = indNum - ind
diff --git a/src/Lentil/Query.hs b/src/Lentil/Query.hs
--- a/src/Lentil/Query.hs
+++ b/src/Lentil/Query.hs
@@ -35,14 +35,12 @@
 filterFilepath r is = filter ((=~ r) . iFile) is
 
 filterDescription :: RegExp -> [Issue] -> [Issue]
-filterDescription r is = filter ((=~ r) . iDesc) is
+filterDescription r is = filter ((=~ r) . mDesc . iDesc) is
+    where mDesc md = maybe "" id md
 
 filterTags :: RegExp -> [Issue] -> [Issue]
 filterTags r is = filter (df . iTags) is
     where df ts = any ((=~ r) . tagString) ts
-
-filterTagless :: [Issue] -> [Issue]
-filterTagless is = filter (null . iTags) is
 
 negFilter :: ([Issue] -> [Issue]) -> [Issue] -> [Issue]
 negFilter f is = is L.\\ f is
diff --git a/src/Lentil/Types.hs b/src/Lentil/Types.hs
--- a/src/Lentil/Types.hs
+++ b/src/Lentil/Types.hs
@@ -15,7 +15,7 @@
 
 data Issue = Issue { iFile   :: FilePath,
                      iRow    :: Row,
-                     iDesc   :: Description,
+                     iDesc   :: Maybe Description,
                      iTags   :: [Tag] }
              deriving (Eq, Show)
 
@@ -40,4 +40,7 @@
 prettyFP :: String -> String
 prettyFP fp | L.isPrefixOf "./" fp = drop 2 fp
             | otherwise            = fp
+
+iPPDesc :: Issue -> String
+iPPDesc i = maybe "<no description>" id . iDesc $ i
 
diff --git a/src/Main.hs b/src/Main.hs
--- a/src/Main.hs
+++ b/src/Main.hs
@@ -28,7 +28,7 @@
                                    short 'v'      <>
                                    help "show version and copyright info" )
     where
-          versionCopy = "lentil - a frugal issue tracker, version 0.1.2.6\n\
+          versionCopy = "lentil - a frugal issue tracker, version 0.1.2.7\n\
                         \(C) 2015 Francesco Ariis - http://www.ariis.it\n\
                         \released under the GNU General Public License 3\n"
 
diff --git a/test/Lentil/ArgsSpec.hs b/test/Lentil/ArgsSpec.hs
--- a/test/Lentil/ArgsSpec.hs
+++ b/test/Lentil/ArgsSpec.hs
@@ -11,7 +11,7 @@
 
 testOpt :: LOptions
 testOpt = LOptions (["alpha"], ["beta"]) Csv
-                   [filterFilepath "al", filterTagless]
+                   [filterFilepath "al", negFilter . filterTags $ "."]
                    [] (Just "foo.txt")
 
 ins :: [String]
@@ -34,4 +34,5 @@
     it "parses options" $
       ins `shouldBe` ins
       --error "args" --out `shouldBe` Just testOpt
+      -- TODO: real parsing testing options [test]
 
diff --git a/test/Lentil/ExportSpec.hs b/test/Lentil/ExportSpec.hs
--- a/test/Lentil/ExportSpec.hs
+++ b/test/Lentil/ExportSpec.hs
@@ -8,8 +8,8 @@
 
 
 is :: [Issue]
-is = [Issue "./file" 1 "da" [Tag "a", Tag "c"],
-      Issue "file" 2 "db" [Tag "e:f"]]
+is = [Issue "./file" 1 (Just "da") [Tag "a", Tag "c"],
+      Issue "file" 2 (Just "db") [Tag "e:f"]]
 
 csv :: String
 csv = "\"Filepath\",\"Row\",\"Description\",\"Tags\"\n\
diff --git a/test/Lentil/Parse/IssueSpec.hs b/test/Lentil/Parse/IssueSpec.hs
--- a/test/Lentil/Parse/IssueSpec.hs
+++ b/test/Lentil/Parse/IssueSpec.hs
@@ -62,6 +62,8 @@
           sp incipit "\nXXX: "  `shouldBe` Just Xxx
     it "doesn't work without previous newline" $
       sp incipit "\nTODO:some"  `shouldBe` Nothing
+    it "doesn't work with longer matches (todoodle)" $
+      sp incipit "\nTODOodle:some"  `shouldBe` Nothing
     it "doesn't work if you don't add a space after :" $
       sp incipit "\nTODO:some"  `shouldBe` Nothing
     it "does allow you to omit the :" $
@@ -83,58 +85,68 @@
 
   describe "freeText" $ do
     it "parses a free form text" $
-      sp freeText "this is it\n\n" `shouldBe` Just "this is it"
+      sp freeText "this is it\n\n" `shouldBe` Just (Just "this is it")
     it "can be ended by tags/fields" $
-      sp freeText "this is it [field:val]" `shouldBe` Just "this is it"
+      sp freeText "this is it [field:val]" `shouldBe` Just (Just "this is it")
     it "trims extra whitespace" $
-      sp freeText "this is  it [bug]" `shouldBe` Just "this is it"
+      sp freeText "this is  it [bug]" `shouldBe` Just (Just "this is it")
     it "cannot be ended by new issue on same line" $
       sp freeText "this is it   TODO: desc\n" `shouldBe`
-             Just "this is it TODO: desc"
+             Just (Just "this is it TODO: desc")
     it "cannot be ended by new issue on new-but-not-beginning-of-line" $
       sp freeText "this is it \nn  TODO: desc\n" `shouldBe`
-             Just "this is it n TODO: desc"
+             Just (Just "this is it n TODO: desc")
     it "can be ended by blank line" $
-      sp freeText "this is it\n\n  TODO: desc" `shouldBe` Just "this is it"
+      sp freeText "this is it\n\n  TODO: desc" `shouldBe`
+             Just (Just "this is it")
     it "can be ended by incomplete blank line (eof)" $
-      sp freeText "this is it\n" `shouldBe` Just "this is it"
+      sp freeText "this is it\n" `shouldBe` Just (Just "this is it")
 
   describe "issue" $ do
     it "parses an issue" $
       sp issue "\n fixMe this is it [t] [f:w]"
-         `shouldBe` (Just $ Issue "<f>" 2 "this is it"
+         `shouldBe` (Just $ Issue "<f>" 2 (Just "this is it")
                                   [Tag "fixme", Tag "t", Tag "f:w"])
     it "parses tagless/fieldless issues too" $
       sp issue "\nTODO: this is it\n"
-         `shouldBe` (Just $ Issue "<f>" 2 "this is it" [])
+         `shouldBe` (Just $ Issue "<f>" 2 (Just "this is it") [])
     it "parses an issue not ended by \\n" $
       sp issue "\ntodo block1 "
-         `shouldBe` (Just $ Issue "<f>" 2 "block1" [])
+         `shouldBe` (Just $ Issue "<f>" 2 (Just "block1") [])
     it "doesn't display the eventual \n at eof" $
       sp issue "\nTOdO: this is it\n"
-         `shouldBe` (Just $ Issue "<f>" 2 "this is it" [])
-    it "doesn't accept a lone (naked) todo" $
+         `shouldBe` (Just $ Issue "<f>" 2 (Just "this is it") [])
+    it "does accept a lone (naked) todo" $
       sp issue "\ntodo\n"
-         `shouldBe` Nothing
+         `shouldBe` (Just $ Issue "<f>" 2 Nothing [])
     it "issues declared with fixme get a free [fixme] tag" $
       sp issue "\nfixme blah\n"
-         `shouldBe` (Just $ Issue "<f>" 2 "blah" [Tag "fixme"])
+         `shouldBe` (Just $ Issue "<f>" 2 (Just "blah") [Tag "fixme"])
     it "doesn't parse tags non separated by a space" $
       sp issue "\ntodo blah[f]\n"
-         `shouldBe` (Just $ Issue "<f>" 2 "blah[f]" [])
+         `shouldBe` (Just $ Issue "<f>" 2 (Just "blah[f]") [])
+    it "does parse an empty todo" $
+      sp issue "\ntodo\n"
+         `shouldBe` (Just $ Issue "<f>" 2 Nothing [])
+    it "does parse an empty fixme" $
+      sp issue "\nfixme \n"
+         `shouldBe` (Just $ Issue "<f>" 2 Nothing [Tag "fixme"])
+    it "does parse an empty todo + tags" $
+      sp issue "\ntodo [alfa]\n"
+         `shouldBe` (Just $ Issue "<f>" 2 Nothing [Tag "alfa"])
 
   describe "issues" $ do
     it "parses multiple issues" $
       sp issues "\nTODO: this is it [f:w]\n TODO: hey [t]"
-         `shouldBe` Just [Issue "<f>" 2 "this is it" [Tag "f:w"],
-                          Issue "<f>" 3 "hey" [Tag "t"]]
+         `shouldBe` Just [Issue "<f>" 2 (Just "this is it") [Tag "f:w"],
+                          Issue "<f>" 3 (Just "hey") [Tag "t"]]
     it "doesn't parse multiple issues if on the same line" $
       sp issues "\nTODO: this is it [f:w] TODO: hey [t]"
-         `shouldBe` Just [Issue "<f>" 2 "this is it" [Tag "f:w"]]
+         `shouldBe` Just [Issue "<f>" 2 (Just "this is it") [Tag "f:w"]]
     it "parses two issues, tagless, if the second starts on nl" $
       sp issues "\nTODO: this is it \n  todo hey [t]"
-         `shouldBe` Just [Issue "<f>" 2 "this is it" [],
-                          Issue "<f>" 3 "hey" [Tag "t"]]
+         `shouldBe` Just [Issue "<f>" 2 (Just "this is it") [],
+                          Issue "<f>" 3 (Just "hey") [Tag "t"]]
     it "doesn't pick issues in the middle of a sentence" $
       sp issues "\nthis is not a todo as you can see" `shouldBe` (Just [])
 
diff --git a/test/Lentil/Parse/RunSpec.hs b/test/Lentil/Parse/RunSpec.hs
--- a/test/Lentil/Parse/RunSpec.hs
+++ b/test/Lentil/Parse/RunSpec.hs
@@ -30,12 +30,12 @@
     it "doesn't parse contiguous line/block as a single issue" $
         fileParser "test/test-files/specific/contiguous.c"
             `shouldReturn` [Issue "test/test-files/specific/contiguous.c" 1
-                                  "issue1" []]
+                                  (Just "issue1") []]
 
-  let spt fp = [Issue fp 1 "single comment" [],
-                Issue fp 3 "single2" [],
-                Issue fp 8 "block1"  [],
-                Issue fp 9 "block2" [Tag "tog"]]
+  let spt fp = [Issue fp 1 (Just "single comment") [],
+                Issue fp 3 (Just "single2") [],
+                Issue fp 8 (Just "block1")  [],
+                Issue fp 9 (Just "block2") [Tag "tog"]]
   describe "commentParser - languages" $ do
     it "parses a plain text source" $
         fileParser "test/test-files/lang-comm/text.txt"
@@ -69,8 +69,8 @@
     it "reads a file (code or txt) for issues" $
       let fp = "test/test-files/lang-comm/test.txt" in
       issueFinder [fp] >>= \i ->
-      i `shouldBe` [Issue fp 1 "palla" [],
-                    Issue fp 3 "beta"  [Tag "fixme"],
-                    Issue fp 4 "gamma" [Tag "xxx"],
-                    Issue fp 6 "qqq"   [Tag "fixme", Tag "bug"]]
+      i `shouldBe` [Issue fp 1 (Just "palla") [],
+                    Issue fp 3 (Just "beta")  [Tag "fixme"],
+                    Issue fp 4 (Just "gamma") [Tag "xxx"],
+                    Issue fp 6 (Just "qqq")   [Tag "fixme", Tag "bug"]]
 
diff --git a/test/Lentil/QuerySpec.hs b/test/Lentil/QuerySpec.hs
--- a/test/Lentil/QuerySpec.hs
+++ b/test/Lentil/QuerySpec.hs
@@ -14,10 +14,11 @@
 spec :: Spec
 spec = do
 
-  let i1 = Issue "a.hs" 1 "issue 1"  [Tag "ta", Tag "fl:va"]
-      i2 = Issue "a.hs" 2 "issue 12" [Tag "tb"]
-      i3 = Issue "b.hs" 1 "issue 3"  [Tag "tb", Tag "fl:vb"]
-      ix = Issue "b.hs" 1 "issue n"  []
+  let i1 = Issue "a.hs" 1 (Just "issue 1")  [Tag "ta", Tag "fl:va"]
+      i2 = Issue "a.hs" 2 (Just "issue 12") [Tag "tb"]
+      i3 = Issue "b.hs" 1 (Just "issue 3")  [Tag "tb", Tag "fl:vb"]
+      ix = Issue "b.hs" 1 (Just "issue n")  []
+      iz = Issue "b.hs" 1 Nothing           []
       is = [i1, i2, i3]
 
   describe "filter*" $ do
@@ -32,16 +33,16 @@
     it "filters by using regexps" $
       filterTags "(ta|tb)" is `shouldBe` [i1, i2, i3]
 
-  describe "filterTagless" $ do
-    it "filters by empty values" $
-      filterTagless (ix:is) `shouldBe` [ix]
-
   describe "negFilter" $ do
     it "negates a filter" $
       negFilter (filterTags "fl:") is `shouldBe` [i2]
     it "cancels itself on a double negation" $
       negFilter (negFilter (filterTags "fl:")) is
                 `shouldBe` filterTags "fl:" is
+    it "filters by empty values (description)" $
+      negFilter (filterDescription ".") (iz:is) `shouldBe` [iz]
+    it "filters by empty values (tags)" $
+      negFilter (filterTags ".") (ix:is) `shouldBe` [ix]
 
   describe "filter(And|Or)" $ do
     it "chains (boolean and) multiple filters" $
@@ -57,7 +58,7 @@
     it "sorts Issues in descending order" $
       sortIssues iFile Desc is `shouldBe` [i3, i2, i1]
     it "smart sorts strings containing naturals" $
-      sortIssues iDesc Asc is `shouldBe` [i1, i3, i2]
+      sortIssues (maybe "" id . iDesc) Asc is `shouldBe` [i1, i3, i2]
 
   describe "sortTag" $ do
     it "sorts by partial tag, empty fields first" $
@@ -66,7 +67,7 @@
   describe "chainSorts" $ do
     it "sequences sort functions" $
       chainSorts is [sortIssues iFile Desc,
-                     sortIssues iDesc Desc]
+                     sortIssues (maybe "" id . iDesc) Desc]
                  `shouldBe` [i3, i2, i1]
 
   describe "groupIssues" $ do
