toodles 0.1.0.3 → 0.1.0.4
raw patch · 4 files changed
+47/−12 lines, 4 files
Files
- README.md +20/−4
- app/Main.hs +7/−4
- toodles.cabal +2/−2
- web/js/app.js +18/−2
README.md view
@@ -1,11 +1,13 @@ # Toodles [](https://travis-ci.org/aviaviavi/toodles)+[](https://hackage.haskell.org/package/toodles) Toodles scrapes your entire repository for TODO entries and organizes them so-you can manage your project directly from the code. View, filter, sort, and then-edit your TODO's with an easy to use web application. When you're done, commit-and push your changes and share changes with your team!+you can manage your project directly from the code. View, filter, sort, and edit+your TODO's with an easy to use web application. When you make changes via+toodles, the edits will be applied directly the TODO entries in your code.+When you're done, commit and push your changes to share them with your team!  @@ -73,7 +75,22 @@ - Typescript - Yaml +### Installing +You can get toodles by installing with [stack](https://docs.haskellstack.org) or+[cabal](https://www.haskell.org/cabal/download.html). Run `stack install+toodles` or `cabal install toodles` and you're done! If there is desire for it I+can look into precompiled distribution.++### Running++```bash+# $ toodles -d <root directory of your project> -p <port to run server>+# for more info run:+# $ toodles --help+$ toodles -d /path/to/your/project -p 9001+```+ ### Current Limitations Due to the parser's current simplicity, Toodles won't see TODO's in multiline initiated comment. For instance in javascript@@ -87,5 +104,4 @@ */ ```-
app/Main.hs view
@@ -5,7 +5,7 @@ {-# LANGUAGE ScopedTypeVariables #-} {-# LANGUAGE TypeOperators #-} --- TODO(avi|p=3|#techdebt) - break this into modules+-- TODO(avi|p=3|#cleanup) - break this into modules module Main where import qualified Control.Exception as E@@ -121,7 +121,6 @@ toodlesAPI :: Proxy ToodlesAPI toodlesAPI = Proxy - slice :: Int -> Int -> [a] -> [a] slice f t xs = take (t - f + 1) (drop f xs) @@ -361,7 +360,7 @@ parseAssignee :: Parser String parseAssignee = many (noneOf [')', '|', '=']) --- TODO(avi|p=3|#techdebt) - fix and type this better+-- TODO(avi|p=3|#cleanup) - fix and type this better parseDetails :: T.Text -> (Maybe T.Text, Maybe T.Text, [(T.Text, T.Text)], [T.Text]) parseDetails toParse =@@ -445,7 +444,7 @@ (do putStrLn $ printf "Running toodles for path: %s" path files <- recurseDir SystemFS path let validFiles = filter (isValidFile config) files- -- TODO(avi|p=3|#techdebt) - make sure it's a file first+ -- TODO(avi|p=3|#cleanup) - make sure it's a file first mapM (\f -> SourceFile f . (map T.pack . lines) <$>@@ -483,10 +482,14 @@ groupedTodos = foldl foldTodoHelper ([], False) parsedTodoLines in fst groupedTodos +-- fold fn to concatenate todos that a multiple, single line comments foldTodoHelper :: ([TodoEntry], Bool) -> Maybe TodoEntry -> ([TodoEntry], Bool) foldTodoHelper (todoEntries :: [TodoEntry], currentlyBuildingTodoLines :: Bool) maybeTodo+ -- We're not on a todo line, keep going | isNothing maybeTodo = (todoEntries, False)+ -- We see the start of a new todo | isEntryHead $ fromJust maybeTodo = (todoEntries ++ [fromJust maybeTodo], True)+ -- We a body line of a todo to concatenate to the current one | isBodyLine (fromJust maybeTodo) && currentlyBuildingTodoLines = (init todoEntries ++ [combineTodo (last todoEntries) (fromJust maybeTodo)], True) | otherwise = (todoEntries, False)
toodles.cabal view
@@ -2,10 +2,10 @@ -- -- see: https://github.com/sol/hpack ----- hash: 703679257a67bc8f02883cf8b85e4c1c53a777ac55e49065b72d92d2c829fb2b+-- hash: a2afad22ce77b0d765b58bb81080fe61bced7c38ceb5c79a35a19c50831faf2a name: toodles-version: 0.1.0.3+version: 0.1.0.4 synopsis: Manage the TODO entries in your code description: See the README on GitHub at <https://github.com/aviaviavi/toodles#readme> category: Project Management
web/js/app.js view
@@ -12,7 +12,8 @@ customAttributeKeys: [], setAssignee: "", addTags: "",- setPriority: null+ setPriority: null,+ lastSortField: null, } }, created: function() {@@ -47,8 +48,13 @@ }) console.log("todos", this.todos) this.loading = false+ if (!recompute) { this.sortTodos('priority')+ } else {+ const field = this.lastSortField || 'priority'+ this.sortMultiplier[field] *= -1 // reset the multipler+ this.sortTodos(field) } this.customAttributeKeys = Array.from(new Set([].concat.apply([], this.todos.map(t => {@@ -56,6 +62,7 @@ })))) this.customAttributeKeys.sort()+ this.hideDropdown() }.bind(this), error: function() { this.loading = false@@ -64,8 +71,9 @@ }) }.bind(this) },- // TODO(avi|p=2|key=a val) - make sorts persist refreshes+ sortTodos: function(sortField) {+ this.lastSortField = sortField if (!sortField || typeof sortField !== 'string') { sortField = this.customSortSelected }@@ -112,6 +120,7 @@ editSeletedTodos: function() { $(".modal").addClass("is-active")+ this.hideDropdown() }, closeModal: function() {@@ -132,6 +141,7 @@ this.todos = this.todos.filter(function(t) { return !t.selected }.bind(this))+ this.hideDropdown() }.bind(this) }) } else {@@ -143,11 +153,17 @@ this.todos.map(function(t) { t.selected = true })+ this.hideDropdown() }, toggleMenuBurger: function(ev) { $(".navbar-burger").toggleClass("is-active") $(".navbar-menu").toggleClass("is-active")+ },++ hideDropdown: function(ev) {+ $(".navbar-menu").removeClass("is-active")+ $(".navbar-burger").removeClass("is-active") }, submitTodoEdits: function(){