summarize :: (Name, [TaskInfo]) -> JS.Value
summarize (nm,tasks) =
  JS.object
    [ "name"        .= nm
    , "percent"     .= percent
    , "autoSolve"   .= autoLen
    , "otherSolve"  .= otherLen
    , "todo"        .= totLen
    , "solutions"   .= map jsTask solved
    ]

  where
  (unsolved,solved) = partition (null . taskSlns) tasks
  (auto,nonAuto)    = partition taskAuto solved
  autoLen           = length auto
  otherLen          = length nonAuto
  doneLen           = autoLen + otherLen
  totLen            = doneLen + length unsolved
  percent           = if totLen == 0 then 100 else div (100 * doneLen) totLen

  jsTask t          = JS.object [ "tags" .= taskTags t
                                , "slns" .= map (show . ppE) (taskSlns t)
                                , "category" .= taskCat t
                                , "auto" .= taskAuto t
                                , "label" .= taskLabel t
                                ]
summarize :: (Name, [TaskInfo]) -> JS.Value
summarize (nm,tasks) =
  JS.object
    [ "name"        .= nm
    , "percent"     .= percent
    , "autoSolve"   .= autoLen
    , "otherSolve"  .= otherLen
    , "todo"        .= totLen
    , "solutions"   .= map jsTask solved
    ]

  where
  (unsolved,solved) = partition (null . taskSlns) tasks
  (auto,nonAuto)    = partition taskAuto solved
  autoLen           = length auto
  otherLen          = length nonAuto
  doneLen           = autoLen + otherLen
  totLen            = doneLen + length unsolved
  percent           = if totLen == 0 then 100 else div (100 * doneLen) totLen

  jsTask t          = JS.object [ "tags" .= taskTags t
                                , "slns" .= map (show . ppE) (taskSlns t)
                                , "category" .= taskCat t
                                , "auto" .= taskAuto t
                                , "label" .= taskLabel t
                                ]
summarize (nm,tasks) =
  JS.object
    [ "name"        .= nm
    , "percent"     .= percent
    , "autoSolve"   .= autoLen
    , "otherSolve"  .= otherLen
    , "todo"        .= totLen
    , "solutions"   .= map jsTask solved
    ]

  where
  (unsolved,solved) = partition (null . taskSlns) tasks
  (auto,nonAuto)    = partition taskAuto solved
  autoLen           = length auto
  otherLen          = length nonAuto
  doneLen           = autoLen + otherLen
  totLen            = doneLen + length unsolved
  percent           = if totLen == 0 then 100 else div (100 * doneLen) totLen

  jsTask t          = JS.object [ "tags" .= taskTags t
                                , "slns" .= map (show . ppE) (taskSlns t)
                                , "category" .= taskCat t
                                , "auto" .= taskAuto t
                                , "label" .= taskLabel t
                                ]