diff of 37925204100860ccfe84617c955fae8f64edb900

37925204100860ccfe84617c955fae8f64edb900
diff --git a/elm-frontti/elm.json b/elm-frontti/elm.json
index d6285c7..c8df00f 100644
--- a/elm-frontti/elm.json
+++ b/elm-frontti/elm.json
@@ -17,9 +17,11 @@
             "elm/http": "2.0.0",
             "elm/json": "1.1.3",
             "elm/random": "1.0.0",
+            "elm/regex": "1.0.0",
             "elm/time": "1.0.0",
             "elm/url": "1.0.0",
             "elm-community/dict-extra": "2.4.0",
+            "elm-community/list-extra": "8.7.0",
             "elm-community/string-extra": "4.0.1",
             "mhoare/elm-stack": "3.1.2",
             "waratuman/json-extra": "1.0.2",
@@ -32,7 +34,6 @@
             "danfishgold/base64-bytes": "1.1.0",
             "elm/bytes": "1.0.8",
             "elm/parser": "1.1.0",
-            "elm/regex": "1.0.0",
             "elm/virtual-dom": "1.0.2",
             "justinmimbs/timezone-data": "2.1.4",
             "rtfeldman/elm-hex": "1.0.0",
diff --git a/elm-frontti/src/Logs.elm b/elm-frontti/src/Logs.elm
index 9440c92..4419cc7 100644
--- a/elm-frontti/src/Logs.elm
+++ b/elm-frontti/src/Logs.elm
@@ -2,11 +2,33 @@ module Logs exposing (..)
 
 import Article exposing (decodeApply)
 import Json.Decode as Decode exposing (Decoder, succeed)
+import Regex exposing (Regex)
 
 type alias Log =
     { row : String              -- let's keep them as just dumb lines for now and add smarter analytics later...
           }
 
+type alias Group =
+    { name: String
+    , alarmy: Bool 
+    , members: List Log}
 
+type alias ParsedGroup =
+    { name: String
+    , regex: Regex
+    , alarmy: Bool 
+    , members: List Log}
+
+regex_to_parsedgroup str =
+    case Regex.fromString str of
+        Just re -> Just <| ParsedGroup str re False []
+        Nothing -> Nothing
+                   
+str_to_group str =
+    Group str False []
+
+parsedGroup_to_group pg =
+    Group pg.name pg.alarmy pg.members
+    
 rowDecoder = Decode.field "row" Decode.string
 decoder = Decode.succeed Log |> decodeApply rowDecoder             
diff --git a/elm-frontti/src/Main.elm b/elm-frontti/src/Main.elm
index bbd5370..a307f28 100644
--- a/elm-frontti/src/Main.elm
+++ b/elm-frontti/src/Main.elm
@@ -6,6 +6,7 @@ import Html.Attributes exposing (..)
 import Html.Events exposing (onInput, onClick)
 
 import Http
+import Regex
 
 import Article
 import Article_view exposing (articleView)
@@ -20,6 +21,8 @@ import PostEditor
 import SettingsEditor
 import Medialist exposing (medialist)
 import Image
+import Logviewer
+import Logs
 import ImageSelector exposing (imageSelector)
 
 import DateTime exposing (DateTime)
@@ -715,11 +718,58 @@ update msg model =
         GotAdminLogs result ->
             case result of
                 Ok logs ->
-                    ({ model | view_state = Logs logs}
+                    ({ model | view_state = Logs logs [] ""}
                     , Cmd.none)
                 Err error ->
                     ( { model | view_state = ShowError (errToString error) }
                     , Cmd.none)
+        EditGroupRegexp new_regex ->
+            ((case model.view_state of
+                 Logs a b _ -> 
+                     { model | view_state = Logs a b new_regex}
+                 _ -> model)
+            , Cmd.none)
+        SaveLogGroup new_potential_regex ->
+            case Regex.fromString new_potential_regex of
+                Just _ ->
+                    let new_viewstate =
+                            case model.view_state of
+                                Logs logs groups _ ->
+                                    let group = Logs.str_to_group new_potential_regex
+                                        -- new_groups: List (Maybe Logs.Group)
+                                        new_groups = (group::groups)                                                
+                                    in 
+                                        Logs logs new_groups ""
+                                _ -> model.view_state
+                    in
+                        ({ model | view_state = new_viewstate}
+                        , Cmd.none)
+                Nothing ->
+                    ( model
+                    , alert <| "Invalid regex " ++ new_potential_regex)
+        DeleteLogGroup group ->
+            case model.view_state of
+                Logs logs groups current ->
+                    let new_state = Logs logs (List.filter (\g -> g.name /= group) groups) current
+                    in
+                        ({ model | view_state = new_state}
+                        , Cmd.none)
+                _ -> ( model
+                     , Cmd.none)
+        SetLogAlarmy group new_alarmy ->
+            case model.view_state of
+                Logs a groups b ->
+                    let new_groups = groups
+                                     |> List.map (\g ->
+                                                      if g.name == group.name then
+                                                          { g | alarmy = new_alarmy}
+                                                      else g)
+                    in
+                        ({ model
+                               | view_state = Logs a new_groups b}
+                        , Cmd.none)
+                _ -> ( model
+                     , Cmd.none)
                            
                     
 doGoHome_ model other_cmds =
@@ -798,9 +848,7 @@ blog_tab settings model =
             [pre [] [text err]]
         TaggedPostsView articles ->
             (List.map (articleView settings model.loginState model.zone) articles)
-        Logs logs ->
-         [ div [] [text <| "Logs " ++ Debug.toString logs]]
-
+        Logs logs groups current_group -> [ Logviewer.tab logs groups current_group ]
         -- ignored cases (that should maybe be removed from the enumeration?) that are inlined here to make compiler yell about new unimplemented enumerations
         PostEditorList _ -> unknown_state
         PostEditor -> unknown_state
@@ -832,11 +880,7 @@ settings_tab settings model =
     div []
         (case model.view_state of
             SettingsEditor -> [ SettingsEditor.editor settings]
-            _ -> [ div [] [ text "Unknown viewstate in settings_tab"] ])
-
-logs_tab settings model =
-    div []
-        [ text "Logs tab"]
+            _ -> [ div [] [ text "Unknown viewstate in settings_tab"] ])            
             
 posteditor_tab settings model =
     div [ class "posteditor-tab" ]
@@ -893,7 +937,7 @@ view model =
                                                  ["update-settings"])
                                            , ("SettingLogs"
                                              , TabEntry "Logs"
-                                                 (logs_tab settings model)
+                                                 (text "in the frontpage these views don't show up anywhere")
                                                  (Just (PushUrl "/blog/logs"))
                                                  ["update-settings"])
                                            , ("PostEditTab"
diff --git a/elm-frontti/src/Message.elm b/elm-frontti/src/Message.elm
index f3aa5e1..6362e4f 100644
--- a/elm-frontti/src/Message.elm
+++ b/elm-frontti/src/Message.elm
@@ -20,6 +20,7 @@ import File exposing (File)
 import UUID exposing (UUID)
 import Stack exposing (..)
 import Dict exposing (Dict)
+import Regex 
     
 type ViewState
     = PageView P.Page
@@ -32,7 +33,8 @@ type ViewState
     | TaggedPostsView (List Article.Article)
     | SettingsEditor
     | Feeds (List Feeds.Feed) Bool -- <- show_archived?
-    | Logs (List Logs.Log)
+                                   -- v- the second List will be parsed as List Regex later
+    | Logs (List Logs.Log) (List Logs.Group) String
 
 -- a simplified version of ViewState type for the main.elm's tabcomponent 
 type TabState
@@ -55,7 +57,7 @@ viewstate_to_tabstate vs =
         TaggedPostsView _ -> Blog
         SettingsEditor -> SettingsTab
         Feeds _ _ -> RssFeeds
-        Logs _ -> Blog
+        Logs _ _ _ -> Blog
 
 tabstate_to_str tb =
     case tb of
@@ -219,6 +221,10 @@ type Msg
   | CreateExcerptPost String UUID 
   | ExcerptCreated (String, String)
   | GotAdminLogs (Result Http.Error (List Logs.Log))
+  | EditGroupRegexp String
+  | SaveLogGroup String
+  | DeleteLogGroup String
+  | SetLogAlarmy Logs.ParsedGroup Bool
 
 -- ports
 port reallySetupAce : String -> Cmd msg
diff --git a/resources/css/murja.css b/resources/css/murja.css
index 6c79657..8f6a8dd 100644
--- a/resources/css/murja.css
+++ b/resources/css/murja.css
@@ -393,6 +393,17 @@ header {
     font-size: unset;
 }
 
+.loggroup-summary {
+    /* display: inline; */
+}
+
+.loggroup-summary-container {
+    display: flex;
+    flex-direction: row;
+    justify-content: space-between;
+    width: 30%;
+}
+
 @media only screen and (max-device-width:480px)
 {
     body {
diff --git a/src/main.lisp b/src/main.lisp
index e3060f3..8524130 100644
--- a/src/main.lisp
+++ b/src/main.lisp
@@ -7,25 +7,6 @@
 
 (in-package :murja)
 
-;; (setf hunchentoot:*catch-errors-p* nil)
-
-(cl-advice:make-advisable 'hunchentoot:set-cookie)
-(cl-advice:add-advice :around
-		      'hunchentoot:set-cookie
-		      (lambda (next-fn name &key (value "") expires max-age path domain secure http-only (reply hunchentoot:*reply*))
-			(let ((session-cookie? (string= name "hunchentoot-session")))
-			  (funcall next-fn
-				     name
-				     :value value
-				     :expires expires
-				     :max-age (if session-cookie?
-						  31536666
-						  max-age)
-				     :path path
-				     :domain domain
-				     :secure secure
-				     :http-only http-only
-				     :reply reply))))
 (defun stop-server ()
   (hunchentoot:stop *server*))
 
@@ -46,11 +27,19 @@
     server))
 
 (defun main (&key (port 3010))
-  (with-open-file (f murja.routes.settings-routes:*log-file* :direction :output :if-does-not-exist :create)
+  (with-open-file (f murja.routes.settings-routes:*log-file* :direction :output :if-does-not-exist :create :if-exists :append)
     (let ((*standard-output* f))
       (start-server :port port :stream f)
       (handler-case
 	  (loop do (sleep 1000))
 	(condition () nil)))))
 
+(in-package :common-lisp-user)
+(defun run ()
+  "Starts up the aggressive-murja system. Sets logging up in a way that should show up in the logs view"
+  (setf hunchentoot:*catch-errors-p* nil)
+  (bordeaux-threads:make-thread
+   (lambda ()
+     (murja:main))))
+
 ;; (start-server :port 3010)