diff of 32e8cda49a3bf4a5862032472a6c7b01e3048521

32e8cda49a3bf4a5862032472a6c7b01e3048521
diff --git a/elm-frontti/elm.json b/elm-frontti/elm.json
deleted file mode 100644
index c8df00f..0000000
--- a/elm-frontti/elm.json
+++ /dev/null
@@ -1,47 +0,0 @@
-{
-    "type": "application",
-    "source-directories": [
-        "src"
-    ],
-    "elm-version": "0.19.1",
-    "dependencies": {
-        "direct": {
-            "NoRedInk/elm-json-decode-pipeline": "1.0.0",
-            "PanagiotisGeorgiadis/elm-datetime": "1.3.0",
-            "TSFoster/elm-uuid": "4.2.0",
-            "danhandrea/elm-date-format": "2.0.1",
-            "elm/browser": "1.0.2",
-            "elm/core": "1.0.5",
-            "elm/file": "1.0.5",
-            "elm/html": "1.0.0",
-            "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",
-            "waratuman/time-extra": "1.1.0"
-        },
-        "indirect": {
-            "TSFoster/elm-bytes-extra": "1.3.0",
-            "TSFoster/elm-md5": "2.0.1",
-            "TSFoster/elm-sha1": "2.1.1",
-            "danfishgold/base64-bytes": "1.1.0",
-            "elm/bytes": "1.0.8",
-            "elm/parser": "1.1.0",
-            "elm/virtual-dom": "1.0.2",
-            "justinmimbs/timezone-data": "2.1.4",
-            "rtfeldman/elm-hex": "1.0.0",
-            "rtfeldman/elm-iso8601-date-strings": "1.1.3"
-        }
-    },
-    "test-dependencies": {
-        "direct": {},
-        "indirect": {}
-    }
-}
diff --git a/elm-frontti/src/Ajax_cmds.elm b/elm-frontti/src/Ajax_cmds.elm
deleted file mode 100644
index 52492f6..0000000
--- a/elm-frontti/src/Ajax_cmds.elm
+++ /dev/null
@@ -1,220 +0,0 @@
-module Ajax_cmds exposing (..)
-
-import Article
-import User
-import Page
-import Feeds
-import Message exposing (..)
-import Http exposing (..)
-import Image
-import Initial
-import Settings
-import Logs
-import Json.Decode as Json
-
-getSession =
-    Http.get
-        { url = "/api/login/session"
-        , expect = Http.expectJson GotSession User.userDecoder}
-
-getEditablePosts : Cmd Msg
-getEditablePosts =
-    Http.get
-        { url = "/api/posts/all-titles"
-        , expect = Http.expectJson EditableTitlesReceived (Json.list Article.sidebarTitleDecoder) }
-
-getPage page_id =
-    Http.get
-        { url = "/api/posts/page/" ++ (String.fromInt page_id)
-        , expect = Http.expectJson PageReceived Page.pageDecoder}
-
-getPost : Int -> Cmd Msg
-getPost post_id =
-    Http.get
-        { url = "/api/posts/post/" ++ (String.fromInt post_id)
-        , expect = Http.expectJson PostReceived Article.articleDecoder}
-
-getSettings =
-    Http.get
-        { url = "/api/settings/client-settings"
-        , expect = Http.expectJson SettingsReceived Settings.settingsDecoder}
-
-getSettingsAdmin =
-    Http.get
-        { url = "/api/settings/client-settings"
-        , expect = Http.expectJson AdminSettingsReceived Settings.settingsDecoder}        
-
-getTitles =
-    Http.get
-        { url = "/api/posts/titles"
-        , expect = Http.expectJson TitlesReceived (Json.list Article.sidebarTitleDecoder)}
-
-postLogin username password =
-    Http.post
-       { url = "/api/login/login"
-       , expect = Http.expectJson LoginSuccess User.userDecoder
-       , body = Http.jsonBody <| User.encodeLoggingIn <| User.UserLoggingIn username password}
-
-getPostEditorData post_id =
-    Http.get
-        { url = "/api/posts/post/" ++ (String.fromInt post_id) ++ "/allow-hidden/true"
-        , expect = Http.expectJson EditorPostReceived Article.articleDecoder}
-
-putArticle : Article.Article -> Cmd Msg        
-putArticle article =
-    Http.request
-        { method = "PUT"
-        , headers = []
-        , url = "/api/posts/post"
-        , body = Http.jsonBody <| Article.encode article
-        , expect = Http.expectString HttpGoHome
-        , timeout = Nothing
-        , tracker = Nothing
-        }
-                   
--- returns { :id :name }
-getListOfImages : Bool -> Cmd Msg
-getListOfImages managerCalled = Http.get
-                  { url = "/api/pictures/list/all"
-                  , expect = Http.expectJson (GotListOfImages managerCalled) (Json.list Image.imageDecoder)}
-
-
-postPicture handler_msg url pictureFile = Http.post 
-                          { url = url
-                          , body = Http.multipartBody [ Http.filePart "file" pictureFile ]
-                          , expect = Http.expectJson handler_msg Image.imageResponseDecoder }
-
-
-deletePictures ids = Http.request
-                     { url = "/api/pictures"
-                     , method = "DELETE"
-                     , headers = []
-                     , expect = Http.expectString HttpManagerGetListOfImages
-                     , body = Http.jsonBody <| (Image.list_of_uuids_encode ids)
-                     , timeout = Nothing
-                     , tracker = Nothing}
-
-getReferencingPosts id = Http.get
-                         { url = "/api/pictures/referencing/" ++ id
-                         , expect = Http.expectJson GotReferencingPosts (Json.list Image.referencingPostDecoder)}
-
-loadTaggedPosts tags = Http.get
-                       { url = "/api/posts/tagged/" ++ tags
-                       , expect = Http.expectJson GotTaggedPosts (Json.list Article.articleDecoder)}
-
-loadPostVersion post_id_int version_id_int =
-    let post_id = String.fromInt post_id_int
-        version_id = String.fromInt version_id_int in
-    Http.get
-        { url = "/api/posts/post/" ++ post_id ++ "/version/" ++ version_id
-        , expect = Http.expectJson GotOldPost Article.articleDecoder}
-
-generateNewPost =
-    Http.request
-        { method = "POST"
-        , headers = []
-        , url = "/api/posts/new_post"
-        , body = emptyBody
-        , expect = Http.expectJson NewPostGenerated Json.int
-        , timeout = Nothing
-        , tracker = Nothing
-        }
-        
-saveSettings settings =
-    Http.request
-        { method = "PUT"
-        , headers = []
-        , url = "/api/settings/client-settings"
-        , body = Http.jsonBody (Settings.encodeSettings settings)
-        , expect = Http.expectWhatever SettingsSaved
-        , timeout = Nothing
-        , tracker = Nothing}
-
-searchPreviouslyPosts search_term =
-    Http.post
-        { url = "/api/posts/search-previously"
-        , body = Http.stringBody "application/json" search_term
-        , expect = Http.expectJson PreviouslySearchResult (Json.list Article.previouslyDocDecoder)}
-
-
-loadPreviousArticle post_id =
-    Http.get
-        { url = "/api/posts/post/" ++ (String.fromInt post_id)
-        , expect = Http.expectJson PreviousPostReceived Article.articleDecoder}
-
-getFeeds archived =
-    Http.get
-        { url = if archived then
-                    "/api/user/feeds?archived=archived"
-              else
-                  "/api/user/feeds"
-        , expect = Http.expectJson FeedsReceived (Json.list Feeds.feedDecoder)}
-
-addFeed newFeed =
-    Http.post
-        { url = "/api/user/feeds"
-        , body = Http.jsonBody (Feeds.newFeedEncoder newFeed)
-        , expect = Http.expectWhatever FeedAdded }
-
-markFeedItemRead feed_id item_id =
-    Http.post
-        { url = "/api/user/feeds/" ++ feed_id ++ "/" ++ item_id ++ "/mark-read"
-        , body = Http.emptyBody
-        , expect = Http.expectWhatever FeedItemReadResponse}
-
-deleteFeed feed_id =
-    Http.request
-        { url = "/api/user/feeds/" ++ feed_id
-        , method = "DELETE"
-        , headers = []
-        , expect = Http.expectWhatever FeedDeleted
-        , body = Http.emptyBody
-        , timeout = Nothing
-        , tracker = Nothing}
-
-getFeedMeta =
-    Http.get
-        { url = "/api/user/feeds/meta"
-        , expect = Http.expectJson FeedMetaReceived Feeds.metadataDecoder}
-
-postExcerpt excerpt feed_id =
-    Http.post
-        { url = " /api/posts/excerpt/" ++ feed_id
-        , body = Http.stringBody "text/plain" excerpt
-        , expect = Http.expectJson NewPostGenerated Json.int}
-
-getAdminLogs =
-    Http.get
-        { url = "/api/logs"
-        , expect = Http.expectJson GotAdminLogs (Json.list Logs.decoder)}
-
-saveGroups groups =
-    Http.post
-        { url = "/api/logs/groups"
-        , body = Http.jsonBody <| Logs.groupsEncoder groups
-        , expect = Http.expectWhatever LogGroupsSaved}
-
-getLogGroups =
-    Http.get
-        { url = "/api/logs/groups"
-        , expect = Http.expectJson GotLogGroups Logs.groupsDecoder}
-
-getTopbarAlarms permissions =
-    if List.member "update-settings" permissions then
-        Http.get
-            { url = "/api/logs/alarm"
-            , expect = Http.expectJson GotTopbarLogAlarm Logs.topbarAlarmDecoder}
-    else
-        Cmd.none
-
-submitUser user oldpasswd newpasswd = 
-    Http.post
-        { url = "/api/user/submit"
-        , body = Http.jsonBody (User.encodeEditorUser user oldpasswd newpasswd)
-        , expect = Http.expectWhatever UserSubmitResult}
-
-postInitialData data =
-    Http.post
-        { url = "/api/initial"
-        , body = Http.jsonBody <| Initial.initialEncoder data
-        , expect = Http.expectWhatever PostInitialSuccess}
diff --git a/elm-frontti/src/Article.elm b/elm-frontti/src/Article.elm
deleted file mode 100644
index 2e67007..0000000
--- a/elm-frontti/src/Article.elm
+++ /dev/null
@@ -1,146 +0,0 @@
-module Article exposing (..)
-
-import Creator exposing (encode)
-
-import DateTime exposing (DateTime)
-import Json.Encode as Json exposing (..)
-import Json.Encode.Extra exposing (..)
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Decode.Pipeline exposing (required)
-import Json.Decode.Extra as Extra
-import Time
-
--- {
---   "tags": [],
---   "creator": {
---     "username": "feuer",
---     "nickname": "Feuer",
---     "img_location": "https://feuerx.net/etc/feuer.jpeg"
---   },
---   "content": "<p>Tämä on testi posti :D</p>\n\n<p>Uusi paragraaaaaaaafffi</p>",
---   "comments": [],
---   "amount-of-comments": 0,
---   "title": "Testi Posti",
---   "id": 1,
---   "versions": [],
---   "version": null,
---   "created_at": "2020-10-16T07:52:59Z",
---   "previosly": [{"id": 666,
---                  "title": "Titteli"}]
--- }
-
-import Creator exposing (Creator, creatorDecoder)
-
-decodeApply : Decode.Decoder a -> Decode.Decoder (a -> b) -> Decode.Decoder b
-decodeApply value partial =
-    Decode.andThen (\p -> Decode.map p value) partial
-
-type ArticleSource
-    = Murja
-    | Rss
-      String -- <-link 
-      
-type alias PreviousArticle =
-    { id: Int
-    , title: String}
-
-type alias Article =
-    { creator : Creator
-    , tags : List String
-    , content : String
-    -- TODO make a comment type
-    , comments : Maybe (List String)
-    -- , amount_of_comments : Int
-    , title : String
-    , id : Int
-    , versions: Maybe (List Int)
-    , version : Maybe Int
-    , created_at: Maybe Time.Posix
-    , hidden : Bool
-    , unlisted : Bool
-    , previously: List PreviousArticle
-    , source: ArticleSource}
-
--- encoder
-
-encodePreviously prev =
-    object
-      [ ( "id", int prev.id)
-      , ( "title", string prev.title)]
-
-encode : Article -> Json.Value
-encode article =
-    object
-        [ ( "creator", Creator.encode article.creator )
-        , ( "tags", list string article.tags)
-        , ( "content", string article.content)
-        , ( "comments", (list string (case article.comments of
-                                         Just comments -> comments
-                                         Nothing -> [])))
-        , ( "title", string article.title)
-        , ( "id", int article.id)
-        , ( "version", (maybe int) article.version)
-        , ( "created_at", (maybe iso8601) article.created_at)
-        , ( "hidden", bool article.hidden)
-        , ( "unlisted", bool article.unlisted)
-        , ( "previously", list encodePreviously article.previously)
-        ]
-
-
--- decoder
-
-    
-tagsDecoder = Decode.field "tags" (Decode.list Decode.string)
-contentDecoder = Decode.field "content" Decode.string
-commentsDecoder = Decode.maybe (Decode.field "comments" (Decode.list Decode.string))
--- amount_of_commentsDecoder = Decode.field "amount-of-comments" Decode.int                  
-titleDecoder = Decode.field "title" Decode.string
-idDecoder = Decode.field "id" Decode.int
-versionsDecoder = Decode.maybe (Decode.field "versions" (Decode.list Decode.int))
-versionDecoder = Decode.maybe (Decode.field "version" Decode.int)
-created_atDecoder = Decode.field "created_at" (Decode.maybe Extra.iso8601)
-creator_Decoder = Decode.field "creator" creatorDecoder
-hiddenDecoder = Decode.field "hidden" Decode.bool
-unlistedDecoder = Decode.field "unlisted" Decode.bool
-
-previouslyDocDecoder =
-    Decode.succeed PreviousArticle
-        |> decodeApply idDecoder
-        |> decodeApply titleDecoder
-
-previouslyDecoder = Decode.field "previously" (Decode.list previouslyDocDecoder)
-
--- |> == clojure's ->>
-articleDecoder : Decoder Article                    
-articleDecoder =
-    Decode.succeed Article
-        |> decodeApply creator_Decoder
-        |> decodeApply tagsDecoder
-        |> decodeApply contentDecoder
-        |> decodeApply commentsDecoder
-        |> decodeApply titleDecoder
-        |> decodeApply idDecoder
-        |> decodeApply versionsDecoder
-        |> decodeApply versionDecoder
-        |> decodeApply created_atDecoder
-        |> decodeApply hiddenDecoder
-        |> decodeApply unlistedDecoder
-        |> decodeApply previouslyDecoder
-        |> decodeApply (Decode.succeed Murja)
-
-type alias Title =
-    { title : String
-    , id : Int
-    , year : Int
-    , month: Int
-    , tags: List String
-    }
-    
-
-sidebarTitleDecoder =
-    Decode.succeed Title
-        |> decodeApply (Decode.field "Title" Decode.string)
-        |> decodeApply (Decode.field "Id" Decode.int)
-        |> decodeApply (Decode.field "Year" Decode.int)
-        |> decodeApply (Decode.field "Month" Decode.int)
-        |> decodeApply (Decode.field "Tags" (Decode.list Decode.string))
diff --git a/elm-frontti/src/Article_view.elm b/elm-frontti/src/Article_view.elm
deleted file mode 100644
index 02f9865..0000000
--- a/elm-frontti/src/Article_view.elm
+++ /dev/null
@@ -1,59 +0,0 @@
-module Article_view exposing (..)
-
-import DateFormat as Df
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (onInput, onClick)
-import User
-import Message exposing (..)
-import Settings
-import Time
-import Article
-
-
-formatDateTime formatString zone posixTime =
-    Df.format formatString zone posixTime
-
-articleView settings loginstate zone the_actual_post =
-    let versions = Maybe.withDefault [] the_actual_post.versions
-        url = case the_actual_post.source of
-                  Article.Rss link -> link 
-                  Article.Murja -> ("/blog/post/" ++ String.fromInt the_actual_post.id)
-    in
-        div [class "post"] [ a [ href url ] [ text the_actual_post.title ]
-                           , div [class "meta"] (List.append [ User.user_avatar the_actual_post.creator
-                                                             , p [] [text ("By " ++ the_actual_post.creator.nickname)]
-                                                             , case the_actual_post.created_at of
-                                                                   Just writing_time ->
-                                                                       p [] [text ("Written at " ++ (formatDateTime settings.time_format zone writing_time))]
-                                                                   Nothing ->
-                                                                       p [] [text ("No idea when it's written")]]
-                                                     (let post_id = the_actual_post.id in
-                                                      (List.map (\version -> a [ href ("/blog/post/" ++ String.fromInt post_id ++ "/version/" ++ String.fromInt version) ] [ text ((String.fromInt version) ++ ", ")]) versions)))
-                             
-                           , (let post_id = the_actual_post.id in
-                              case loginstate of
-                                  LoggedIn _ -> case the_actual_post.source of
-                                                    Article.Murja -> a [ href ("/blog/post/edit/" ++ String.fromInt post_id)
-                                                                       , attribute "data-testid" "edit-post-btn"
-                                                                       , onClick (OpenPostEditor post_id)] [text "Edit this post"]
-                                                    Article.Rss _ -> div [] []
-                                  _ -> div [] [])
-                                                    
-                           , article [ class "content"
-                                     , dangerouslySetInnerHTML the_actual_post.content] []
-                           , div [ class "previously" ]
-                               (  the_actual_post.previously
-                               |> List.map (\prev -> span [] [ a [ href ("/blog/post/" ++ (String.fromInt prev.id))
-                                                                 , title prev.title]
-                                                                   [ text settings.previously_label ]
-                                                             , text ", "]))
-                           , let tags = ( the_actual_post.tags
-                                        |> List.filter ((/=) ""))
-                             in
-                                 if not (List.isEmpty tags) then 
-                                     div [ class "tags" ] ( tags 
-                                                          |> List.map ( \tag -> span [] [ a [ href ("/blog/tags/" ++ tag)
-                                                                                            , class "tag" ] [text tag]
-                                                                                        , text ", "]))
-                                 else div [] []]
diff --git a/elm-frontti/src/Button.elm b/elm-frontti/src/Button.elm
deleted file mode 100644
index 9c64091..0000000
--- a/elm-frontti/src/Button.elm
+++ /dev/null
@@ -1,9 +0,0 @@
-module Button exposing (murja_button)
-
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (..)
-
-murja_button params contents =
-    button (List.append params [ class "murja-button" ])
-        contents
diff --git a/elm-frontti/src/Creator.elm b/elm-frontti/src/Creator.elm
deleted file mode 100644
index fee57f6..0000000
--- a/elm-frontti/src/Creator.elm
+++ /dev/null
@@ -1,26 +0,0 @@
-module Creator exposing (..)
-
-import Json.Encode as Json exposing (..)
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Decode.Pipeline exposing (required)
-
-type alias Creator =
-    { username : String
-    , nickname : String
-    , img_location : String}
-
-usernameDecoder = Decode.field "username" Decode.string
-nicknameDecoder = Decode.field "nickname" Decode.string
-img_locationDecoder = Decode.field "img_location" Decode.string
-
-creatorDecoder = Decode.map3 Creator usernameDecoder nicknameDecoder img_locationDecoder                      
-
--- encoder
-
-encode : Creator -> Json.Value
-encode creator =
-    object
-        [ ( "username", string creator.username)
-        , ( "nickname", string creator.nickname)
-        , ( "img_location", string creator.img_location)
-        ]
diff --git a/elm-frontti/src/Date_utils.elm b/elm-frontti/src/Date_utils.elm
deleted file mode 100644
index 1ae2823..0000000
--- a/elm-frontti/src/Date_utils.elm
+++ /dev/null
@@ -1,8 +0,0 @@
-module Date_utils exposing (int_to_month_string)
-import Array
-
--- import Dict exposing (Dict)
-
-months = Array.fromList ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"]
-
-int_to_month_string i = Array.get (i - 1) months         
diff --git a/elm-frontti/src/FeedManager.elm b/elm-frontti/src/FeedManager.elm
deleted file mode 100644
index 17a2041..0000000
--- a/elm-frontti/src/FeedManager.elm
+++ /dev/null
@@ -1,37 +0,0 @@
-module FeedManager exposing (..)
-
-import Message exposing (..)
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (onInput, onClick)
-import Button exposing (murja_button)
-import Article_view exposing (formatDateTime)
-import Time 
-
-feedmanager time_format zone feeds =
-    table [ class "feed-manager-container" ]
-        (  feeds
-        |> List.map (\f ->
-                         let last_updated = (  f.items
-                                            |> List.map (Time.posixToMillis << .pubdate)
-                                            |> List.maximum) in
-                         ( last_updated
-                         , f))
-        |> List.sortBy ((\last_updated ->
-                             case last_updated of
-                                 Just d -> d
-                                 Nothing -> 9999) << Tuple.first)
-        |> List.reverse
-        |> List.map (\tuple ->
-                         let (last_updated, f) = tuple in
-                         tr [ ]
-                         [ td [] [ text <| f.name ++ " ("
-                                 , a [ href f.url] [ text f.url ]
-                                 , text ")"]
-                         , td [] [ text <| "Last updated at " ++ (  last_updated
-                                                                 |> Maybe.map Time.millisToPosix
-                                                                 |> (Maybe.map <| formatDateTime time_format zone)
-                                                                 |> Maybe.withDefault "never")]
-                         , td []
-                              [ murja_button [ onClick <| DeleteFeed f.id ]
-                                    [ text "Delete feed" ]]]))
diff --git a/elm-frontti/src/FeedView.elm b/elm-frontti/src/FeedView.elm
deleted file mode 100644
index aa3b2a3..0000000
--- a/elm-frontti/src/FeedView.elm
+++ /dev/null
@@ -1,100 +0,0 @@
-module FeedView exposing (..)
-
-import DateFormat as Df
-import Feeds exposing (..)
-import Dict 
-import Time
-import Message exposing (..)
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (onInput, onClick, on) 
-import Button exposing (murja_button)
-import UUID
-import Article_view exposing (formatDateTime)
-import FeedManager exposing (feedmanager)
-import Tab exposing (TabEntry, tabs)
-import Random
-
-feed_item loginstate settings zone item =
-    let time_format = settings.time_format
-        article = itemToArticle item in
-    li [ class "feed-item" ]
-       ( case item.feed_id of
-             Just feed_id ->
-                 [ div [] [ murja_button [ onClick <| SelectExcerpt item.id ] [ text "Write a post about this"]]
-                 , node "dialog" [ id <| "excerpt-dialog-" ++ (UUID.toString item.id) ]
-                     (let textarea_id = "excerpt-dialog-" ++ (UUID.toString item.id) ++ "-textarea" in 
-                     [ div [ class "dialog" ]
-                           [ header [ class "previouslyHeader" ] [ button [ onClick ClosePreviousPostsModel ] [ text "X"]]
-                           , h3 [] [ text "Select an excerpt"]
-                           , textarea [ rows 30
-                                      , cols 60
-                                      , id textarea_id ] [ text item.description ]
-                           , murja_button [ onClick <| CreateExcerptPost textarea_id item.id ] [ text "Create a post" ]]])
-                 , Article_view.articleView settings loginstate zone article ]
-             Nothing ->
-                 [ text "Unknown feed" ])
-
-correctlySortedFeedItemList loginstate settings zone items = 
-    (  items
-    |> List.sortBy (Time.posixToMillis << .pubdate)
-    |> List.reverse
-    |> List.map (feed_item loginstate settings zone))
-
--- fs = feeds, elm sucks balls at shadowing
-perFeedView loginstate settings zone fs new_feed_state = 
-    ul [ class "feed-list" ]
-        (List.map (\feed ->
-                       li [ class "feed" ]
-                       [ header [] [ text <| feed.name ++ " (" ++ (String.fromInt (List.length feed.items)) ++ ")" ]
-                       , a [ href feed.url ] [ text feed.url ]
-                       , ul [ class "feed-items" ]
-                           (correctlySortedFeedItemList loginstate settings zone <| List.map (\i -> { i | feed_id = Just feed.id}) feed.items)]) fs)
-            
-singleFeedView loginstate settings zone fs =
-    let final_feed = List.concatMap (\feed -> List.map (\item -> { item | feed_id = Just feed.id}) feed.items) fs in
-    div []
-        [ header [] [ text <| (String.fromInt (List.length final_feed)) ++ " unread articles"  ]
-        , ul [ class "feed-items" ]
-            (correctlySortedFeedItemList loginstate settings zone final_feed)]
-              
-
-readerState_str state =
-    case state of
-        PerFeed -> "PerFeed"
-        SingleFeed -> "SingleFeed"
-        FeedManager -> "FeedManager"
-                             
-feeds feedReaderState loginstate show_archived settings zone fs new_feed metadata =
-    let new_feed_state = Maybe.withDefault (NewFeed "" "") new_feed
-    in
-        div [ id "feeds" ] 
-            [ label [] [ input [ type_ "checkbox"
-                               , checked show_archived
-                               , onClick <| ShowArchivedFeedItems (not show_archived)] []
-                       , text "Show read items"]
-            , tabs "rss-feed-tab" (readerState_str feedReaderState) Nothing
-                  (Dict.fromList [ ("PerFeed", TabEntry "Group by feed" "" (perFeedView loginstate settings zone fs new_feed_state) Nothing ["*"])
-                                 , ("SingleFeed", TabEntry "Show all in a feed" "" (singleFeedView loginstate settings zone fs) Nothing ["*"])
-                                 , ("FeedManager", TabEntry "Manage feeds" "" (feedmanager settings.time_format zone fs) Nothing ["*"])])
-                  
-            , h3 [] [ text "Add new feed?"]
-            , label [ for "name" ] [ text "Feed name" ]
-            , input [ id "name"
-                    , onInput SetFeedName
-                    , value new_feed_state.name
-                    , type_ "text"] []
-
-            , label [ for "url" ] [ text "Url to feed" ]
-            , input [ id "url"
-                    , onInput SetFeedUrl
-                    , value new_feed_state.url
-                    , type_ "text"] []
-            , murja_button [ onClick (AddFeed new_feed_state)] [ text "Add a feed"]
-            , case metadata of
-                  Just meta -> 
-                      details [] [ summary [] [ text "Latest feed updates at: "]
-                                 , ul []
-                                     (  meta.last_update_timestamps
-                                     |> List.map (\timestamp -> li [] [ text timestamp]))]
-                  Nothing -> text "Metadata didn't load"]
diff --git a/elm-frontti/src/Feeds.elm b/elm-frontti/src/Feeds.elm
deleted file mode 100644
index e22506d..0000000
--- a/elm-frontti/src/Feeds.elm
+++ /dev/null
@@ -1,102 +0,0 @@
-module Feeds exposing (..)
-
-import Json.Encode as Json exposing (..)
-import Json.Encode.Extra exposing (..)
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Decode.Pipeline exposing (required)
-import Json.Decode.Extra as Extra
-import Time
-
-import UUID exposing (UUID)
-
-import Article exposing (decodeApply)
-import Creator exposing (Creator)
-
-    
-type alias Item =
-    { id: UUID
-    , fetched: Time.Posix 
-    , title: String
-    , description: String 
-    , link: String
-    , author: String
-    , pubdate: Time.Posix
-    , is_read: Bool
-    -- parent id that's required for ui to function correctly 
-    , feed_id: Maybe UUID} 
-
-type alias Feed =
-    { id: UUID
-    , name: String 
-    , url: String
-    , creator: Creator
-    , items: List Item}
-
-type alias NewFeed =
-    { name: String 
-    , url: String}
-
-type alias FeedMetadata =
-    { last_update_timestamps: List String}
-
--- Article conversion
-itemToArticle item =
-    let creator = Creator "" item.author "" in 
-    Article.Article creator [] item.description Nothing item.title -1 Nothing (Just 1) (Just item.pubdate) False False [] (Article.Rss item.link)
-
--- metadata decoder
-
-metadataDecoder = Decode.succeed FeedMetadata
-                |> decodeApply (Decode.field "last-update-timestamps" (Decode.list Decode.string))
-        
--- feedDecoder
-
-creatorDecoder = Decode.field "creator" Creator.creatorDecoder
-urlDecoder = Decode.field "url" Decode.string
-nameDecoder = (Decode.field "name" Decode.string)
-idDecoder = (Decode.field "id" UUID.jsonDecoder)
-
--- itemDecoder
-fetchedDecoder = Decode.field "fetched" Extra.iso8601
-titleDecoder = Decode.field "title" Decode.string
-descriptionDecoder = Decode.field "description" Decode.string
-linkDecoder = Decode.field "link" Decode.string
-authorDecoder = Decode.field "author" Decode.string
-pubdateDecoder = Decode.field "pubdate" Extra.iso8601
-is_readDecoder = Decode.field "is_read" Decode.bool
-
-itemDecoder =
-    Decode.succeed Item
-        |> decodeApply idDecoder
-        |> decodeApply fetchedDecoder
-        |> decodeApply titleDecoder
-        |> decodeApply descriptionDecoder
-        |> decodeApply linkDecoder
-        |> decodeApply authorDecoder
-        |> decodeApply pubdateDecoder
-        |> decodeApply is_readDecoder
-        |> decodeApply (Decode.succeed Nothing)
-
-itemsDecoder =
-    Decode.field "items" (Decode.list itemDecoder)
-           
-feedDecoder: Decoder Feed
-feedDecoder =
-    Decode.succeed Feed
-        |> decodeApply idDecoder
-        |> decodeApply nameDecoder
-        |> decodeApply urlDecoder
-        |> decodeApply creatorDecoder
-        |> decodeApply itemsDecoder
-
-newFeedDecoder: Decoder NewFeed
-newFeedDecoder =
-    Decode.succeed NewFeed
-        |> decodeApply nameDecoder
-        |> decodeApply urlDecoder
-
-newFeedEncoder o =
-    Json.object
-        [ ("name", Json.string o.name)
-        , ("url", Json.string o.url) ]
-        
diff --git a/elm-frontti/src/Image.elm b/elm-frontti/src/Image.elm
deleted file mode 100644
index d11abca..0000000
--- a/elm-frontti/src/Image.elm
+++ /dev/null
@@ -1,49 +0,0 @@
-module Image exposing (..)
-
-import Json.Encode as Json exposing (..)
-import Json.Encode.Extra exposing (..)
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Decode.Pipeline exposing (required)
-import Json.Decode.Extra as Extra
-
-import UUID exposing (UUID)
-
-import Article exposing (decodeApply)
-
-type alias Image =
-    { id: UUID
-    , name: String }
-
-type alias PostImageResponse =
-    { id: UUID }
-
-type alias ReferencingPost =
-    { post_id : Int
-    , post_title : String
-    , media_id : String
-    , media_name : String}
-
-encode img =
-    object
-        [ ("id", UUID.toValue img.id)
-        , ("name", string img.name) ]
-
-idDecoder = Decode.field "id" UUID.jsonDecoder
-nameDecoder = Decode.field "name" Decode.string
-
-imageDecoder =
-    Decode.succeed Image
-        |> decodeApply idDecoder
-        |> decodeApply nameDecoder
-imageResponseDecoder = Decode.succeed PostImageResponse
-                       |> decodeApply idDecoder
-
-list_of_uuids_encode ids = Json.object
-                           [ ( "ids", Json.list UUID.toValue ids)]
-
-referencingPostDecoder =
-    Decode.succeed ReferencingPost
-        |> decodeApply (Decode.field "post_id" Decode.int)
-        |> decodeApply (Decode.field "post_title" Decode.string)
-        |> decodeApply (Decode.field "media_id" Decode.string)
-        |> decodeApply (Decode.field "media_name" Decode.string)
diff --git a/elm-frontti/src/ImageSelector.elm b/elm-frontti/src/ImageSelector.elm
deleted file mode 100644
index 1a41159..0000000
--- a/elm-frontti/src/ImageSelector.elm
+++ /dev/null
@@ -1,18 +0,0 @@
-module ImageSelector exposing (..)
-
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (onClick)
-
-import UUID
-
-import Image exposing (Image)
-import Message exposing (..)
-
-image the_actual_img = img [ src ("/api/pictures/" ++ (UUID.toString the_actual_img.id))
-                           , onClick (SelectedImage the_actual_img.id)] []
-
-imageSelector : List Image -> Html Msg
-imageSelector img_list =
-    div [ id "selector-div" ]
-        (List.map image img_list)
diff --git a/elm-frontti/src/Initial.elm b/elm-frontti/src/Initial.elm
deleted file mode 100644
index 2494c13..0000000
--- a/elm-frontti/src/Initial.elm
+++ /dev/null
@@ -1,36 +0,0 @@
-module Initial exposing (..)
-
-import Article exposing (decodeApply)
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Encode as Json
-
-type alias Initial =
-    { initial : Bool }            -- http api can't return bare booleans (as "false"s are interpreted as 404 in the middlewares
-
-type alias InitialFormData =
-    { username : String
-    , nickname : String
-    , password : String 
-    , domain : String
-    , blog_title : String
-    , rss_title : String
-    , rss_link : String
-    , rss_description : Maybe String
-    , rss_lang : String
-    , rss_email : String}
-    
-initialDecoder = succeed Initial
-               |> decodeApply (Decode.field "initial" Decode.bool)
-
-initialEncoder i =
-    Json.object
-        [ ("username", Json.string i.username)
-        , ("nickname", Json.string i.nickname)
-        , ("password", Json.string i.password)
-        , ("domain", Json.string i.domain)
-        , ("blog_title", Json.string i.blog_title)
-        , ("rss_title", Json.string i.rss_title)
-        , ("rss_link", Json.string i.rss_link)
-        , ("rss_description", Json.string (Maybe.withDefault i.blog_title i.rss_description))
-        , ("rss_lang", Json.string i.rss_lang)
-        , ("rss_email", Json.string i.rss_email)]
diff --git a/elm-frontti/src/InitialForm.elm b/elm-frontti/src/InitialForm.elm
deleted file mode 100644
index d7c524f..0000000
--- a/elm-frontti/src/InitialForm.elm
+++ /dev/null
@@ -1,67 +0,0 @@
-module InitialForm exposing (..)
-
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (onInput, onClick)
-
-import Message exposing (..)
-
-initialForm data =
-    div []
-        [ text "Welcome to your new Murja-blog. There doesn't seem to be any users in the db yet. Please provide the initial user- and rss-settings now. These can all be changed later in the ui."
-        , div [ class "initial-form" ]
-              [ h1 [] [ text "User settings"]
-              , span [] []
-              , h2 [] [ text "The initial admin user: " ]
-              , span [] []                  
-              , label [] [ text "Username (used when logging in): "
-                         , input [ type_ "text"
-                                 , value data.username
-                                 , onInput SetInitialUsername ] []]
-              , label [] [ text "Nickname (shown in the ui): "
-                         , input [ type_ "text"
-                                 , value data.nickname
-                                 , onInput SetInitialNickname ] []]
-              , label [] [ text "Password: "
-                         , input [ type_ "password"
-                                 , value data.password
-                                 , onInput SetInitialPassword ] []]
-              , span [] []
-              , h1 [] [ text "Site settings"]
-              , span [] []                  
-              , label [] [ text "Domain (the dns name this site is reached by. This is used in session cookies. This should be left empty on dev.): "
-                         , input [ type_ "text"
-                                 , value data.domain
-                                 , onInput SetInitialDomain ] []]
-              , label [] [ text "Blog's title: "
-                         , input [ type_ "text"
-                                 , value data.blog_title
-                                 , onInput SetInitialBlog_Title ] []]
-
-              -- the stupid grid layout requires a few empty spans to lay h1 out into its own row
-              , h1 [] [ text "RSS-feed settings"]
-              , span [] []            
-                  
-              , label [] [ text "Rss-feed's title: "
-                         , input [ type_ "text"
-                                 , value data.rss_title
-                                 , onInput SetInitialRss_Title ] []]
-              , label [] [ text "Rss-feed's link: "
-                         , input [ type_ "text"
-                                 , value data.rss_link
-                                 , onInput SetInitialRss_Link ] []]
-              , label [] [ text "Rss-feed's description: "
-                         , input [ type_ "text"
-                                 , value <| Maybe.withDefault data.blog_title data.rss_description
-                                 , onInput SetInitialRss_Description ] []]
-              , label [] [ text "Rss-feed's language code: "
-                         , input [ type_ "text"
-                                 , value data.rss_lang
-                                 , onInput SetInitialRss_Lang ] []]
-              , label [] [ text "Rss-feed's listed email contact address: "
-                         , input [ type_ "text"
-                                 , value data.rss_email
-                                 , onInput SetInitialRss_Email ] []]]
-        , button
-              [ onClick <| SaveInitialData data ]
-              [ text "Start using murja"]]
diff --git a/elm-frontti/src/Logs.elm b/elm-frontti/src/Logs.elm
deleted file mode 100644
index 42a481b..0000000
--- a/elm-frontti/src/Logs.elm
+++ /dev/null
@@ -1,64 +0,0 @@
-module Logs exposing (..)
-
-import Article exposing (decodeApply)
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Encode as Json exposing (..)
-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
-    , sound_alarm: Bool               
-    , members: List Log}
-
-type alias ParsedGroup =
-    { name: String
-    , regex: Regex
-    , alarmy: Bool
-    , sound_alarm: Bool 
-    , members: List Log}
-
-regex_to_parsedgroup str =
-    case Regex.fromString str of
-        Just re -> Just <| ParsedGroup str re False False []
-        Nothing -> Nothing
-                   
-str_to_group str =
-    Group str False False []
-
-parsedGroup_to_group pg =
-    Group pg.name pg.alarmy pg.members
-    
-rowDecoder = Decode.field "row" Decode.string
-decoder = Decode.succeed Log |> decodeApply rowDecoder             
-
-groupEncoder group =
-    object
-        [ ( "name", string group.name)
-        , ( "alarmy", bool group.alarmy)]
-
-groupsEncoder groups =
-    list groupEncoder groups
-
-nameDecoder = Decode.field "name" Decode.string
-alarmyDecoder = Decode.field "alarmy" Decode.bool
-sound_alarm_decoder = Decode.field "sound-alarm" Decode.bool
-
-groupDecoder = Decode.succeed Group
-               |> decodeApply nameDecoder
-               |> decodeApply alarmyDecoder
-               |> decodeApply sound_alarm_decoder
-               |> decodeApply (Decode.succeed [])
-
-groupsDecoder = Decode.list groupDecoder
-
-type alias TopbarAlarm =
-    { alarm: Bool }
-
-alarmDecoder = Decode.field "alarm" Decode.bool
-topbarAlarmDecoder = Decode.succeed TopbarAlarm
-                   |> decodeApply alarmDecoder
diff --git a/elm-frontti/src/Logviewer.elm b/elm-frontti/src/Logviewer.elm
deleted file mode 100644
index 66b2a12..0000000
--- a/elm-frontti/src/Logviewer.elm
+++ /dev/null
@@ -1,76 +0,0 @@
-module Logviewer exposing (..)
-
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (..)
-import Regex
-import List.Extra
-import Logs exposing (..)
-
-import Message exposing (..)
-
-dropMaybe: (List (Maybe a)) -> List a
-dropMaybe lst =
-    List.foldr (\val -> (\acc ->
-                            case val of
-                                Just a -> a :: acc
-                                Nothing -> acc)) [] lst
-
-log_to_list log
-    = li [] [ text log.row ]
-
-listify group 
-    = let is_ungrouped = group.name == "Ungrouped"
-      in 
-      details []
-      [ summary [ class "loggroup-summary" ] [
-             span [ class "loggroup-summary-container" ]
-                 [ text <| group.name ++ " (" ++ (String.fromInt (List.length group.members)) ++ ")" ++ (if group.sound_alarm then " ALERT!  " else "")
-                 , if not is_ungrouped then
-                       button [ onClick <| DeleteLogGroup group.name ] [ text "Delete log group" ]
-                   else div [] []
-                 , if not is_ungrouped then
-                       label [] [ input [ type_ "checkbox"
-                                        , checked group.alarmy
-                                        , onClick (SetLogAlarmy group (not group.alarmy))] []
-                                , text "Alarm"]
-                   else
-                       div [] []]]
-      , ul []
-          (List.map log_to_list group.members)]
-
-parseRegex: Group -> Maybe ParsedGroup
-parseRegex r =
-    case Regex.fromString r.name of
-        Just rr -> Just (ParsedGroup r.name rr r.alarmy r.sound_alarm r.members)
-        Nothing -> Nothing
-
-tab: List Log -> List Group -> String -> Html Msg
-tab logs groups edited_group =
-    let regexes = groups
-                  |> List.map parseRegex
-                  |> dropMaybe 
-        grouped = regexes
-                  |> List.map (\regex ->
-                                   let members = List.filter (\l -> Regex.contains regex.regex l.row) logs
-                                   in 
-                                       { regex | members = members})
-                  |> List.map listify
-        last_group = logs
-                   |> List.filter (\l -> regexes
-                                      |> List.filter (\r -> Regex.contains r.regex l.row)
-                                      |> (==) [])
-                   |> ParsedGroup "Ungrouped" Regex.never False False 
-                   |> listify 
-    in 
-    div []
-        [ h3 [] [ text "Add a new group" ]
-        , label [] [ text "Grouping regexp "
-                   , input [ type_ "text"
-                           , value edited_group
-                           , onInput EditGroupRegexp] []]
-        , button [ type_ "button"
-                 , onClick <| SaveLogGroup edited_group] [ text "Add group"]
-        , h3 [] [ text "Logs: "]
-        , div [] grouped
-        , last_group]
diff --git a/elm-frontti/src/Main.elm b/elm-frontti/src/Main.elm
deleted file mode 100644
index a672887..0000000
--- a/elm-frontti/src/Main.elm
+++ /dev/null
@@ -1,1172 +0,0 @@
-port module Main exposing (..)
-
-import Browser
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (onInput, onClick)
-
-import Http
-import Regex
-
-import Article
-import Article_view exposing (articleView)
-import Ajax_cmds exposing (..)
-import Creator as C
-import Page as P
-import Settings
-import Message exposing (..)
-import User
-import PostsAdmin
-import PostEditor
-import SettingsEditor
-import Medialist exposing (medialist)
-import Image
-import Logviewer
-import Logs
-import ImageSelector exposing (imageSelector)
-import InitialForm
-
-import DateTime exposing (DateTime)
-import Json.Decode as Decode
-import Json.Encode
-import Time
-import Task
-import Dict.Extra exposing (groupBy)
-import Dict exposing (toList, keys, get)
-import String exposing (fromInt)
-import String.Extra exposing (toSentenceCase)
-import Stack exposing (push, top, pop)
-
-import Browser.Navigation as Nav
-
-import RouteParser
-import Url
-import Date_utils exposing (int_to_month_string)
-
-import UUID
-import File exposing (mime)
-
-import FeedView
-import Feeds exposing (NewFeed)
-import Tab exposing (..)
-import UserEditor
-
--- MAIN
-
-main : Program () Model Msg
-main =
-  Browser.application
-    { init = init
-    , view = view
-    , update = update
-    , subscriptions = subscriptions
-    , onUrlChange = UrlChanged
-    , onUrlRequest = LinkClicked
-    }
-
--- SUBSCRIPTIONS
-
-
-subscriptions : Model -> Sub Msg
-subscriptions _ = Sub.batch 
-                  [ tags ReceivedTag
-                  , aceStateUpdate AceStateUpdate
-                  , excerptCreated ExcerptCreated]
-
-initialModel url key viewstate = Model viewstate Nothing False False [] Nothing LoggedOut key url Nothing Time.utc [] [] Nothing PerFeed Nothing False
-    
-viewStatePerUrl : Url.Url -> (ViewState, List (Cmd Msg))
-viewStatePerUrl url =
-    case RouteParser.url_to_route url of
-        RouteParser.Page page_id -> (Loading, [ getSettings
-                                              , getTitles
-                                              , getSession
-                                              , getPage page_id
-                                              ])
-        RouteParser.Post post_id -> (Loading, [ getSettings
-                                              , getTitles
-                                              , getSession
-                                              , getPost post_id])
-        RouteParser.Home -> (Loading, [ getSettings
-                                      , getTitles
-                                      , getSession
-                                      , getPage 1
-                                      ])
-        RouteParser.PostEditor post_id -> (Loading, [ getSettings
-                                                    , getTitles
-                                                    , getSession
-                                                    , getPostEditorData post_id])
-        RouteParser.PostAdmin -> (Loading, [ getSettings
-                                           , getSession
-                                           , getTitles
-                                           , getEditablePosts ])
-        RouteParser.MediaManager -> (Loading, [ getSettings
-                                              , getSession
-                                              , getTitles
-                                              , getListOfImages True] )
-        RouteParser.TaggedPosts tags_ -> (Loading, [ getSession
-                                                   , getSettings
-                                                   , getTitles
-                                                   , loadTaggedPosts tags_])
-
-        RouteParser.PostVersion post_id version_id -> (Loading, [ getSession
-                                                                , getSettings
-                                                                , getTitles
-                                                                , loadPostVersion post_id version_id])
-                                                                      
-        RouteParser.NotFound -> (ShowError ("Couldn't parse url " ++ (Url.toString url)), [Cmd.none])
-        RouteParser.SettingsEditor -> (Loading, [ getSession
-                                                , getSettingsAdmin 
-                                                , getTitles])
-        RouteParser.FeedReader -> (Loading, [ getSession
-                                            , getSettings
-                                            , getFeeds False 
-                                            , getFeedMeta ])
-        RouteParser.Logs -> ( (Logs [] [] "")
-                            , [ getSettings
-                              , getSession
-                              , getAdminLogs
-                              , getTitles
-                              , getLogGroups])
-        RouteParser.OwnUserSettings -> ( UserSettings "" "" Nothing
-                                       , [ getSettings
-                                         , getSession
-                                         , getTitles])
-        RouteParser.InitialSetup -> ( InitialSetup { username = ""
-                                                   , nickname = ""
-                                                   , password = "" 
-                                                   , domain = ""
-                                                   , blog_title = ""
-                                                   , rss_title = ""
-                                                   , rss_link = ""
-                                                   , rss_description = Nothing
-                                                   , rss_lang = ""
-                                                   , rss_email = ""}
-                                    , [ getSettings ])
-
-init _ url key =
-    let (viewstate, cmds) = (viewStatePerUrl url)
-        model = initialModel url key viewstate
-    in
-        ( model
-        , Cmd.batch (List.append cmds [ Task.perform AdjustTimeZone Time.here]))
-
-
--- UPDATE
-
-
--- PORTS --
-port prompt : String -> Cmd msg
-port showPreviousPostsModal: (() -> Cmd msg)
-port closePreviousPostsModal: (() -> Cmd msg)
-port showPreviousPostPreviewModal: (() -> Cmd msg)
-port tags : (String -> msg) -> Sub msg
-port aceStateUpdate : (String -> msg) -> Sub msg
-port showModal: String -> Cmd msg
-port createExcerpt: (String, String) -> Cmd msg
-port excerptCreated: ((String, String) -> msg) -> Sub msg 
-
-toggleHidden article =
-    { article | hidden = not article.hidden}
-toggleUnlisted article =
-    { article | unlisted = not article.unlisted}
-
-errToString: Http.Error -> String 
-errToString err =
-    case err of
-        Http.BadUrl str -> "Bad url: " ++ str
-        Http.Timeout -> "Timeout trying to contact the server. Are you online?"
-        Http.NetworkError -> "Network error. Are you online?"
-        Http.BadStatus status -> String.fromInt status
-        Http.BadBody body -> "Received unparseable response: " ++ body
-
-update : Msg -> Model -> (Model, Cmd Msg)
-update msg model =
-    case msg of
-        SettingsReceived result ->
-            case result of
-                Ok new_settings ->
-                    ({model | settings = Just new_settings}, Cmd.none)
-                        
-                Err http_error ->
-                    ( model
-                    , alert ("Error loading settings " ++ Debug.toString http_error))
-        PostReceived result ->
-            ( {model | view_state = case result of
-                                        Ok post -> PostView post 
-                                        Err error -> ShowError ( errToString error)}
-            , Cmd.none)
-        PageReceived result ->
-            ( {model | view_state = case result of
-                                        Ok page -> PageView page
-                                        Err error -> ShowError ( errToString error)}
-            , Cmd.none)
-        TitlesReceived result ->
-            case result of
-                Ok decoded_titles ->
-                    ({ model | titles = decoded_titles}
-                    ,  Cmd.none)
-                Err error ->
-                    ( model
-                    , alert ("Error loading titles " ++ Debug.toString error))
-        UrlChanged url ->
-            let (view_state, cmds) = viewStatePerUrl url in 
-            ({model | url = url, view_state = view_state}, Cmd.batch cmds)
-        LinkClicked urlRequest ->
-            case urlRequest of
-                Browser.Internal url ->
-                    (model, Nav.pushUrl model.key (Url.toString url))
-                Browser.External href ->
-                    (model, Nav.load href)
-        LoginFocus ->
-            ({model | loginState = LoggingIn "" ""}, Cmd.none)
-        ChangeUsername username ->
-            case model.loginState of
-                LoggingIn old_username password ->
-                    ({model | loginState = LoggingIn username password}, Cmd.none)
-                _ -> (model, Cmd.none)
-        ChangePassword password ->
-            case model.loginState of
-                LoggingIn username old_password ->
-                    ({model | loginState = LoggingIn username password}, Cmd.none)
-                _ -> (model, Cmd.none)
-        DoLogIn -> case model.loginState of
-                       LoggingIn username password ->
-                           (model, postLogin username password)
-                       _ -> (model, Cmd.none)
-        LoginSuccess result ->
-            case result of
-                Ok user ->
-                    ({model | loginState = LoggedIn user}, Cmd.none)
-                Err error ->
-                    ({model | loginState = LoginFailed}, Cmd.none)
-        GotSession result ->
-            case result of
-                Ok user ->
-                    case model.view_state of
-                        PostEditor -> 
-                            ({ model | loginState = LoggedIn user 
-                             , postEditorSettings = Nothing}
-                            , getTopbarAlarms user.permissions)
-                        UserSettings oldpwd newpwd _ ->
-                            ( { model
-                                  | loginState = LoggedIn user
-                                  , view_state = UserSettings oldpwd newpwd (Just user)}
-                            , getTopbarAlarms user.permissions)                                  
-                        _ ->
-                            ({model | loginState = LoggedIn user}
-                            , getTopbarAlarms user.permissions)
-                Err error ->
-                    case error of
-                        Http.BadStatus status ->
-                            if status == 401 then
-                                -- no valid session
-                                (model, Cmd.none)
-                            else
-                                ( model
-                                , alert ("Error (" ++ String.fromInt status ++ ") when loading session"))
-                        Http.BadBody err ->
-                            ( model
-                            , alert ("Error when loading session: " ++ err))
-                        _ -> ( model
-                             , alert ("Error when loading session"))
-        EditableTitlesReceived result ->
-            ( {model | view_state = case result of
-                                        Ok titles -> PostEditorList titles 
-                                        Err error -> ShowError ( errToString error)}
-            , Cmd.none)
-        OpenPostEditor post_id ->
-            (model, getPostEditorData post_id)
-        EditorPostReceived result ->
-            case result of
-                Ok post ->
-                    ({ model | view_state = PostEditor
-                     , postEditorSettings = Just (PostEditorSettings post "" False Nothing)}
-                    , Cmd.none)
-                Err error ->
-                    ( model
-                    , alert ("Error loading post editor " ++ Debug.toString error))
-        PromptTag prompt_message ->
-            (model, prompt prompt_message)
-        Alert alert_msg ->
-            (model, alert alert_msg)
-        RunAce content ->
-            (model, reallySetupAce content)
-        SelectTag tag ->
-            case model.postEditorSettings of
-                Just settings ->
-                    ({ model | postEditorSettings = Just
-                           { settings | selected_tag = tag}}
-                    , Cmd.none)
-                _ -> (model, Cmd.none)
-        ReceivedTag tag ->
-            case model.postEditorSettings of
-                Just settings ->
-                    let old_article = settings.article
-                        article = { old_article | tags = tag :: settings.article.tags} in
-                    ({ model | postEditorSettings = Just
-                           { settings | article = article}}
-                    , Cmd.none)
-                Nothing -> (model, alert "ReceivedTag called even though postEditorSettings is nil")
-        DropTag tag ->
-            case model.postEditorSettings of
-                Just settings ->
-                    let old_article = settings.article
-                        article = { old_article | tags = List.filter ((/=) settings.selected_tag) old_article.tags} in
-                    ({ model | postEditorSettings = Just
-                           { settings | article = article}}
-                    , Cmd.none)
-                Nothing -> (model, alert "DropTag called even though postEditorSettings is nil")
-        HttpIgnoreResponse result ->
-            (model, Cmd.none)
-        SavePost article ->
-            doGoHome_
-              { model | postEditorSettings = Nothing}
-              [ putArticle article ]
-                    
-
-        GoHome -> doGoHome model
-        HttpGoHome _ -> doGoHome model
-
-        AceStateUpdate content ->
-            case model.postEditorSettings of
-                Just settings ->
-                    let article = settings.article in
-                    ({ model | postEditorSettings = Just
-                           { settings | article =
-                                 { article | content = content}}}
-                    , Cmd.none)
-                Nothing -> (model, alert "AceStateUpdate called even though postEditorSettings is nil")
-                    
-        ChangeTitle new_title ->
-            case model.postEditorSettings of
-                Just settings ->
-                    let article = settings.article in
-                    ({ model | postEditorSettings = Just
-                           { settings | article =
-                                 { article | title = new_title}}}
-                    , Cmd.none)
-                Nothing -> (model, alert "ChangeTitle called even though postEditorSettings is nil")            
-        HttpManagerGetListOfImages _ -> (model, getListOfImages True)                                  
-        GetListOfImages -> ( { model | showImageModal = True }
-                           , getListOfImages False)
-        GotListOfImages managerCalled result ->
-            case result of
-
-                Ok images ->
-                    case managerCalled of
-                        True ->
-                            ({ model
-                                 | loadedImages = images
-                                 , view_state = MediaList
-                                 , medialist_state = Just (MediaListState [] Dict.empty)}
-                            , Cmd.batch (List.map (\image -> getReferencingPosts (UUID.toString image.id)) images))
-                        False -> 
-                            ({model | showImageModal = True, loadedImages = images}, Cmd.none)
-                Err error ->
-                    ( { model | view_state = ShowError (errToString error) }
-                    , Cmd.none)
-        SelectedImage img_id ->
-            ( {model | showImageModal = False, loadedImages = [] }
-            , addImgToAce (UUID.toString img_id))
-        EditorDragEnter ->
-            ( {model | draggingImages = True}
-            , Cmd.none)
-        EditorDragLeave ->
-            ( {model | draggingImages = False}
-            , Cmd.none)
-        GotFiles sendPicture file files ->
-            if String.startsWith "image" (mime file) then
-                ( { model | draggingImages = False }
-                , sendPicture file)
-            else
-                ( { model | draggingImages = False }
-                , alert ("Got " ++ (mime file) ++ ", expected an image"))
-        GotInputFiles files ->
-            if List.all (\file -> String.startsWith "image" (mime file)) files then
-                ( model
-                , Cmd.batch (List.map (\file -> postPicture UploadedImage PostEditor.editor_image_api file) files))
-            else
-                ( model
-                , alert ("Expected images, got " ++ (String.join ", " (List.map mime files))))
-        UploadedImage imgResponse ->
-            case imgResponse of
-                Ok actualResponse ->
-                    ( model
-                    , addImgToAce (UUID.toString actualResponse.id ))
-                Err err ->
-                    (model, alert ("Error uploading image " ++ Debug.toString err))
-        MarkImageForRemoval img_id ->
-            case model.medialist_state of
-                Just state ->
-                    if List.member img_id state.selected_ids_for_removal then
-                        ({ model | medialist_state = Just {state | selected_ids_for_removal =
-                                                               List.filter ((/=) img_id) state.selected_ids_for_removal}}
-                        , Cmd.none)
-                    else 
-                        ({ model | medialist_state = Just {state | selected_ids_for_removal = img_id :: state.selected_ids_for_removal}}
-                        , Cmd.none)
-                        
-                Nothing ->
-                    ( model
-                    , alert "Medialist state is uninitialized")
-        MarkAllImages ids ->
-            case model.medialist_state of
-                Just state ->
-                    ({ model | medialist_state = Just {state | selected_ids_for_removal = ids}}
-                    , Cmd.none)
-                Nothing -> ( model
-                           , alert "Medialist state is uninitialized")
-        RemoveSelectedImages ->
-            case model.medialist_state of
-                Just state -> 
-                    (model, deletePictures state.selected_ids_for_removal)
-                Nothing -> (model, Cmd.none)
-        GotReferencingPosts response ->
-            case response of
-                Ok posts ->
-                    case model.medialist_state of
-                        Just state -> ({ model | medialist_state = Just {state | referencing_posts =
-                                                                             Dict.union state.referencing_posts (groupBy .media_id posts)}}
-                                      , Cmd.none)
-                        Nothing -> ( model
-                                   , Cmd.none)
-                Err err ->
-                    ( model
-                    , alert "Error while downloading info about referencing posts, check your devtools' network log")
-        PushUrl url ->
-            ( model, Nav.pushUrl model.key url )
-        AdjustTimeZone zone ->
-            ( {model | zone = zone}
-            , Cmd.none)
-        GotTaggedPosts result ->
-            case result of
-                Ok posts ->
-                    ({ model | view_state = TaggedPostsView posts}
-                    , Cmd.none)
-                Err err ->
-                    ( model , alert ( "Error loading tagged posts " ++ (Debug.toString err)))
-        ToggleArticlePreview ->
-            ({ model | postEditorSettings = Maybe.map (\settings ->
-                                                           {settings | show_preview = not settings.show_preview}) model.postEditorSettings}
-            , Cmd.none)
-        GotOldPost result ->
-            case result of
-                Ok post ->
-                    ({ model | view_state = PostView post}
-                    , Cmd.none)
-                Err err ->
-                    (model , alert ("Error loading post version " ++ Debug.toString err))
-        GenNewPost ->
-            ( model
-            , generateNewPost)
-        NewPostGenerated new_post_id ->
-            case new_post_id of
-                Ok id -> 
-                    ( model
-                    , Cmd.batch
-                        [ ( Nav.pushUrl model.key ("/blog/post/edit/" ++ String.fromInt id))
-                        , getPostEditorData id])
-                Err error ->
-                    ( model
-                    , alert ("ERROR: " ++ (Debug.toString error)))
-        ToggleArticleHidden ->
-            ({ model | postEditorSettings = Maybe.map (\settings ->
-                                                           {settings | article = toggleHidden settings.article})
-                   model.postEditorSettings}
-            , Cmd.none)
-        ToggleArticleUnlisted ->
-            ({ model | postEditorSettings = Maybe.map (\settings ->
-                                                           {settings | article = toggleUnlisted settings.article})
-                   model.postEditorSettings}
-            , Cmd.none)
-        AdminSettingsReceived result -> 
-            case result of
-                Ok new_settings ->
-                    ({model
-                         | settings = Just new_settings
-                         , view_state = SettingsEditor}, Cmd.none)
-                        
-                Err http_error ->
-                    ( model
-                    , alert ("Error loading settings " ++ Debug.toString http_error))
-        SetTimeFormat tf ->
-            ({ model | settings = Maybe.map (\settings ->
-                                                 { settings | time_format = tf})
-                   model.settings}
-            , Cmd.none)
-        SetBlogTitle title ->
-            ({ model | settings = Maybe.map (\settings ->
-                                                 { settings | blog_title = title})
-                   model.settings}
-            , Cmd.none)
-        SetPageSize pg_size ->
-            case String.toInt pg_size of
-                Just page_size -> 
-                    ({ model | settings = Maybe.map (\settings ->
-                                                         { settings | recent_post_count = page_size})
-                           model.settings}
-                    , Cmd.none)
-                Nothing ->
-                    ( model
-                    , alert "Page size should be a number")
-        SaveSettings ->
-            case model.settings of
-                Just settings -> 
-                    ( model
-                    , saveSettings settings)
-                Nothing ->
-                    ( model
-                    , Cmd.none)
-        SettingsSaved result ->
-            case result of
-                Ok _ ->
-                    ( model
-                    , Cmd.none)
-                        
-                Err http_error ->
-                    ( model
-                    , alert ("Error saving settings " ++ Debug.toString http_error))
-        ShowPreviousPostsModal ->
-            ( model
-            , showPreviousPostsModal ())
-        ClosePreviousPostsModel ->
-            ( model
-            , closePreviousPostsModal ())
-        PreviouslySearchInput search_term ->
-            ( model
-            , searchPreviouslyPosts search_term)
-        PreviouslySearchResult result ->
-            case result of
-                Ok previously_posts ->
-                    let article_previouslies = case model.postEditorSettings of
-                                                    Just settings -> settings.article.previously
-                                                    Nothing -> []
-                    in
-                    ({ model |
-                           searchedPosts = List.filter (\p -> not (List.member p article_previouslies)) previously_posts}
-                    , Cmd.none)
-                Err error ->
-                    ( model
-                    , alert (errToString error))
-        SelectPreviouslyPost selectedPost  ->
-            case model.postEditorSettings of
-                Just editorSettings -> 
-                    let new_posts = List.filter ((/=) selectedPost) model.searchedPosts
-                        article = editorSettings.article
-                        previously = article.previously
-                    in
-                        ({ model
-                             | searchedPosts = new_posts
-                             , postEditorSettings = Just { editorSettings
-                                                             | article = { article
-                                                                             | previously = selectedPost :: previously}}}
-                        , Cmd.none)
-                Nothing ->
-                    ( model
-                    , Cmd.none)
-        DropPreviously previous_post ->
-            case model.postEditorSettings of
-                Just editorSettings -> 
-                    let article = editorSettings.article
-                        previously = article.previously
-                    in
-                        ({ model
-                             | postEditorSettings = Just
-                               { editorSettings
-                                     | article =
-                                     { article
-                                           | previously = List.filter ((/=) previous_post) previously}}}
-                        , Cmd.none)
-                Nothing ->
-                    ( model
-                    , Cmd.none)
-        SetPreviouslyLabel label ->
-            ({ model | settings = Maybe.map (\settings ->
-                                                 { settings | previously_label = label})
-                   model.settings}
-            , Cmd.none)
-        LoadPreviouslyPreview prev_article ->
-            ( model
-            , loadPreviousArticle prev_article.id )
-        PreviousPostReceived result ->
-            case result of
-                Ok article ->
-                    let postEditorSettings = model.postEditorSettings
-                    in
-                        ({ model
-                             | postEditorSettings = Maybe.map (\settings ->
-                                                                   { settings
-                                                                         | previewing_previously = Just article}) postEditorSettings}
-                        , showPreviousPostPreviewModal ())
-                Err err ->
-                    ( model
-                    , alert ("Failed to load a previosly-post with error: " ++ (errToString err)))
-        ClosePreviousPostPreviewModal ->
-            ( model
-            , closePreviousPostsModal ())
-        FeedsReceived result -> 
-            case result of
-                Ok fs ->
-                    let feeds = (  fs
-                                |> List.sortBy (\f -> (  f.items
-                                                      |> List.map (Time.posixToMillis << .pubdate)
-                                                      |> List.minimum
-                                                      |> Maybe.withDefault 999))
-                                |> List.reverse) 
-                    in
-                    case model.view_state of
-                        Feeds _ archived -> 
-                            ( { model | view_state = Feeds feeds archived}
-                            , Cmd.none)
-                        _ ->
-                            ( { model | view_state = Feeds feeds False}
-                            , Cmd.none)
-                Err error -> 
-                    ( { model | view_state = ShowError (errToString error) }
-                    , Cmd.none)
-        SetFeedName name ->
-            let new_feed = (Maybe.withDefault (NewFeed "" "") model.new_feed)
-            in
-            ({ model
-                 | new_feed = Just { new_feed
-                                       | name = name}}
-            , Cmd.none)
-        SetFeedUrl url ->
-            let new_feed = (Maybe.withDefault (NewFeed "" "") model.new_feed)
-            in
-            ({ model
-                 | new_feed = Just { new_feed
-                                       | url = url}}
-            , Cmd.none)
-        AddFeed new_feed ->
-            ({ model
-                 | new_feed = Nothing}
-            , addFeed new_feed)
-        FeedAdded r ->
-            case r of
-                Ok _ ->
-                    case model.view_state of
-                        Feeds _ archived -> 
-                            ( model
-                            , getFeeds archived)
-                        _ -> ( model
-                             , Cmd.none)
-                Err error ->
-                    ( { model | view_state = ShowError (errToString error) }
-                    , Cmd.none)
-        SelectTab tab_id selected_tab ->
-            case tab_id of 
-                "rss-feed-tab" ->
-                    case (str_to_readerState selected_tab) of
-                        Just readerstate -> 
-                            ({ model
-                                 | feedReaderState = readerstate}
-                            , Cmd.none)
-                        Nothing ->
-                            ( model
-                            , alert <| "Unknown selected tab " ++ selected_tab)
-                "posteditor-preview-tab" ->
-                    ({ model |
-                           postEditorSettings = 
-                           Maybe.map (\settings -> {settings
-                                                       | show_preview = selected_tab == "PreviewArticle"})
-                           model.postEditorSettings}
-                    , Cmd.none)
-                _ -> ( model
-                     , alert <| "Unknown tab " ++ tab_id)
-        ReadFeedItem feed_id item_id is_read ->
-            case model.view_state of
-                Feeds feeds show_archived ->
-                    let new_feeds = (  feeds
-                                    |> List.map (\f -> if f.id == feed_id then
-                                                           {f | items = (  f.items
-                                                                        |> List.map (\item ->
-                                                                                         if item.id == item_id then
-                                                                                             {item | is_read = is_read}
-                                                                                         else
-                                                                                             item ))}
-                                                       else
-                                                           f))
-                    in
-                        ({ model | view_state = Feeds new_feeds show_archived}
-                        , markFeedItemRead (UUID.toString feed_id) (UUID.toString item_id))
-                _ -> ( model
-                     , Cmd.none)
-        ShowArchivedFeedItems showArchived ->
-            case model.view_state of
-                Feeds feeds _ -> 
-                    ({ model
-                         | view_state = Feeds feeds showArchived}
-                    , getFeeds showArchived)
-                _ -> ( model
-                     , Cmd.none)
-        FeedItemReadResponse result ->
-            case result of
-                Ok _ -> ( model
-                        , Cmd.none)
-                Err error -> ( { model | view_state = ShowError (errToString error) }
-                             , Cmd.none)
-        DeleteFeed id ->
-            ( model 
-            , deleteFeed <| UUID.toString id)
-        FeedDeleted result ->
-            case result of 
-                Ok _ ->
-                    case model.view_state of
-                        Feeds _ archived ->
-                            ( model
-                            , getFeeds archived)
-                        _ ->
-                            ( model
-                            , Cmd.none)
-                Err error -> ( { model | view_state = ShowError (errToString error) }
-                             , Cmd.none)
-
-        FeedMetaReceived result ->
-            case result of
-                Ok metadata ->
-                    ({ model
-                         | feedMetadata = Just metadata}
-                    , Cmd.none)
-                Err error -> ( { model | view_state = ShowError (errToString error) }
-                             , Cmd.none)
-        SelectExcerpt article_uuid ->
-            ( model
-            , showModal <| "excerpt-dialog-" ++ (UUID.toString article_uuid))
-        CreateExcerptPost textarea_id feed_id ->
-            ( model
-            , createExcerpt (textarea_id, UUID.toString feed_id))
-        ExcerptCreated (excerpt, feed_id) ->
-            ( model
-            , postExcerpt excerpt feed_id)
-        GotAdminLogs result ->
-            case result of
-                Ok logs ->
-                    case model.view_state of
-                        Logs _ g str ->
-                            ({ model | view_state = Logs logs g str}
-                            , Cmd.none)
-                        _ ->
-                            ( model
-                            , alert "Wrong viewstate again")
-                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 _ ->
-                    case model.view_state of
-                        Logs logs groups asd ->
-                            let group = Logs.str_to_group new_potential_regex
-                                new_groups = (group::groups) in 
-                            ({ model | view_state = Logs logs new_groups asd }
-                            , saveGroups new_groups)
-                        _ -> ( model
-                             , Cmd.none)
-                Nothing ->
-                    ( model
-                    , alert <| "Invalid regex " ++ new_potential_regex)
-        DeleteLogGroup group ->
-            case model.view_state of
-                Logs logs groups current ->
-                    let new_groups = (List.filter (\g -> g.name /= group) groups)
-                        new_state = Logs logs new_groups current
-                    in
-                        ({ model | view_state = new_state}
-                        , saveGroups new_groups)
-                _ -> ( 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}
-                        , saveGroups new_groups)
-                _ -> ( model
-                     , Cmd.none)
-        LogGroupsSaved result ->
-            case result of
-                Ok _ -> 
-                    ( model
-                    , Cmd.none)
-                Err err ->
-                    ( model
-                    , alert <| "Saving groups failed " ++ (Debug.toString err))
-        GotLogGroups result ->
-            case result of
-                Ok groups ->
-                    let new_viewstate = 
-                            case model.view_state of
-                                Logs logs _ str -> Logs logs groups str
-                                _ -> model.view_state
-                    in
-                        ({ model
-                             | view_state = new_viewstate}
-                        , case model.view_state of
-                              Logs _ _ _ -> Cmd.none 
-                              _ -> alert "view state is wrong")
-                Err error -> 
-                    ( { model | view_state = ShowError (errToString error) }
-                    , Cmd.none)
-        GotTopbarLogAlarm res ->
-            case res of
-                Ok alarm ->
-                    ({ model | ringLogAlarm = alarm.alarm}
-                    , Cmd.none)
-                Err error -> 
-                    ( { model | view_state = ShowError (errToString error) }
-                    , Cmd.none)
-        SetDomain dm ->
-            ({ model | settings = Maybe.map (\settings ->
-                                                 { settings | domain = dm })
-                   model.settings}
-            , Cmd.none)
-        SetUsername usrname ->
-            case model.view_state of
-                UserSettings oldpwd newpwd usr ->
-                    ({ model
-                         | view_state = UserSettings oldpwd newpwd (Maybe.map (\old_usr ->
-                                                                                   {old_usr | username = usrname}) usr)}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetNickname new_nickname ->
-            case model.view_state of
-                UserSettings oldpwd newpwd usr ->
-                    ({ model
-                         | view_state = UserSettings oldpwd newpwd (Maybe.map (\old_usr ->
-                                                                                   {old_usr | nickname = new_nickname}) usr)}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetNewpwd newpwd ->
-            case model.view_state of
-                UserSettings oldpwd _ usr ->
-                    ({ model
-                         | view_state = UserSettings oldpwd newpwd usr}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetOldpwd oldpwd ->
-            case model.view_state of
-                UserSettings _ newpwd usr ->
-                    ({ model
-                         | view_state = UserSettings oldpwd newpwd usr}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SubmitChangedUser oldpasswd newpasswd user ->
-            -- TODO implement 
-            case model.loginState of
-                LoggedIn usr ->
-                    ( model
-                    , if usr.id == user.id then
-                          submitUser user oldpasswd newpasswd  
-                      else
-                          Cmd.none)
-                _ -> ( model
-                     , Cmd.none)
-        UserSubmitResult r ->
-            case r of
-                Ok _ ->
-                    ( model
-                    , Cmd.batch [ getSettings
-                                , getSession
-                                , getTitles])
-                Err error ->
-                    ( { model | view_state = ShowError (errToString error) }
-                    , Cmd.none)
-        UploadedOwnProfilePic r ->
-            case r of
-                -- we're not really interested in the return value more than "is it 2xx instead of 4xx or 5xx?", we're just as api-compatible with the posteditor's image upload functionality as possible
-                Ok _ ->
-                    ( model
-                    , Cmd.batch [ getSettings
-                                , getSession
-                                , getTitles])
-                Err error ->
-                    ( { model | view_state = ShowError (errToString error) }
-                    , Cmd.none)
-        SetInitialUsername usrname ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | username = usrname }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialNickname nckname ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | nickname = nckname }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialPassword passwd ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | password = passwd }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialDomain dmain ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | domain = dmain }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialBlog_Title title ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | blog_title = title }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialRss_Title title ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | rss_title = title }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialRss_Link link ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | rss_link = link }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialRss_Description descr ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | rss_description = (if descr == "" then
-                                                                          Nothing
-                                                                      else
-                                                                          Just descr)}}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialRss_Lang lang ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | rss_lang = lang }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SetInitialRss_Email email ->
-            case model.view_state of
-                InitialSetup formdata ->
-                    ( { model | view_state
-                            = InitialSetup { formdata
-                                                 | rss_email = email }}
-                    , Cmd.none)
-                _ -> ( model, Cmd.none)
-        SaveInitialData data ->
-            ( model
-            , postInitialData data )
-        PostInitialSuccess res ->
-            case res of
-                Ok _ ->
-                    doGoHome model
-                Err error ->
-                    ( { model | view_state = ShowError (errToString error) }
-                    , Cmd.none)                    
-                    
-doGoHome_ model other_cmds =
-    (model, Cmd.batch (List.append [ getSettings
-                                   , getTitles
-                                   , getSession
-                                   , getPage 1
-                                   , Nav.pushUrl model.key "/blog/"]
-                           other_cmds))
-
-doGoHome model = doGoHome_ model []
-
--- VIEW
-
-sidebarHistory : List Article.Title -> Html Msg
-sidebarHistory titles =
-    let grouped_by_year = groupBy .year titles in
-      div [id "grouper"]
-          [ul []
-               (List.concat (List.map (\year ->
-                                           case get year grouped_by_year of
-                                               Just per_year ->
-                                                   [li [] [details [] [summary [] [text ((fromInt year) ++ " (" ++ (fromInt (List.length per_year)) ++ ")")],
-                                                                        let grouped_by_month = groupBy .month per_year in
-                                                                          ul [] (List.concat (List.map (\month ->
-                                                                                                            case (int_to_month_string month) of
-                                                                                                                Just month_str ->
-                                                                                                                    let month_titles = titles |> List.filter (\title ->
-                                                                                                                                                                  title.year == year && title.month == month)
-                                                                                                                    in
-                                                                                                                        [li [] [details [] [summary [] [text ((toSentenceCase month_str) ++ " (" ++ (fromInt (List.length month_titles)) ++ ")")]
-                                                                                                                               , ul [class "title-list"] (month_titles
-                                                                                                                                                         |> List.map (\title ->
-                                                                                                                                                                          [li [class "title-list"]
-                                                                                                                                                                               [a [href ("/blog/post/" ++ (fromInt title.id))] [text title.title]]])
-                                                                                                                                                         |> List.concat)]]]
-                                                                                                                Nothing -> [li [] [details [] [summary [] [text ("Couldn't decode month " ++ (String.fromInt month))]]]]
-                                                                                                       ) (keys grouped_by_month) |> List.reverse))]]]
-
-                                               Nothing ->
-                                                        [li [] [text ("There's no year " ++ (fromInt year) ++ " in titles")]]) (keys grouped_by_year |> List.reverse)))]
-
-
-page_wrapper comp = 
-    div [class "flex-container"] 
-        [ div [class "page"]
-              comp]
-
-unknown_state = [ div [] [ text "Unknown viewstate in blog_tab"] ]            
-
-blog_tab settings model =
-    div [] 
-    (case model.view_state of
-        Loading ->
-            [div [] [text "LOADING"]]
-        PostView article ->
-            [ articleView settings model.loginState model.zone article ]
-        PageView page ->
-            let post_elements = (List.map (articleView settings model.loginState model.zone) page.posts) in
-            (List.concat [ (if post_elements /= [] then
-                                post_elements
-                            else
-                                [ div [class "post"] [ text <| case model.loginState of
-                                                                   LoggedIn usr -> "Hi " ++ usr.nickname ++ ", there are no (also: no user) posts in this instance"
-                                                                   _ -> "There are no (also: no user) posts in this instance"]])
-                         , [footer [ attribute "data-testid" "page-changer"
-                                   , class "page-changer" ]
-                                (if page.id > 1 then
-                                     [ a [href ("/blog/page/" ++ fromInt (page.id + 1))] [text "Older posts"]
-                                     , a [href ("/blog/page/" ++ fromInt (page.id - 1)), class "newer-post"] [text "Newer posts"]]
-                                 else
-                                     [a [href ("/blog/page/" ++ fromInt (page.id + 1))] [text "Older posts"]])]])
-        ShowError err ->
-            [pre [] [text err]]
-        TaggedPostsView articles ->
-            (List.map (articleView settings model.loginState model.zone) articles)
-        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
-        MediaList -> unknown_state
-        SettingsEditor -> unknown_state
-        Feeds _ _ -> unknown_state
-        UserSettings oldpasswd newpasswd usr_ -> case usr_ of
-                                 Just usr -> [ UserEditor.editor model.draggingImages oldpasswd newpasswd usr]
-                                 Nothing -> [ div [] [ text "Can't change user settings when there's no user"]]
-        InitialSetup data -> [ InitialForm.initialForm data]
-    )
-
-rss_tab model settings =
-    div []
-    (case model.view_state of
-        Feeds feeds show_archived -> [ FeedView.feeds model.feedReaderState model.loginState show_archived settings model.zone feeds model.new_feed model.feedMetadata]
-        _ -> [ div [] [ text "Unknown viewstate in rss_tab"] ])
-
-postmanager_tab model =
-    div [] 
-    (case model.view_state of
-        PostEditorList titles -> [ PostsAdmin.view titles ]
-        _ -> [ div [] [ text "Unknown viewstate in postmanager_tab"] ])
-
-mediamanager_tab model =
-    div [] 
-    (case model.view_state of
-        MediaList -> [ medialist model.loadedImages model.medialist_state ]
-        _ -> [ div [] [ text "Unknown viewstate in mediamanager_tab"] ])
-
-settings_tab settings model =
-    div []
-        (case model.view_state of
-            SettingsEditor -> [ SettingsEditor.editor settings]
-            _ -> [ div [] [ text "Unknown viewstate in settings_tab"] ])            
-            
-posteditor_tab settings model =
-    div [ class "posteditor-tab" ]
-    (case model.view_state of 
-        PostEditor ->
-            case model.postEditorSettings of
-                Just editorSettings ->
-                    let post = editorSettings.article
-                        tag_index = editorSettings.selected_tag in
-                    PostEditor.postEditor post tag_index model.showImageModal model.loadedImages model.draggingImages editorSettings settings model.zone model.loginState model.searchedPosts
-                Nothing -> [ div [] [ text "No post loaded" ]]
-        _ -> [ div [] [ text "Unknown viewstate in posteditor_tab" ]])
-                                                              
-view : Model -> Browser.Document Msg
-view model =
-    case model.settings of
-        Nothing ->
-            { title = "Error loading murja"
-            , body = 
-                  [div [] [text "Couldn't load settings"]]}
-        Just settings ->
-            { title = settings.blog_title
-            , body = 
-                  [ header [] [a [href "/"] [text settings.blog_title ]]
-                  , div [ class "sidebar-flex" ]
-                      [ let tabstate = viewstate_to_tabstate model.view_state in 
-                        tabs "topbar" (tabstate_to_str tabstate) (case model.loginState of
-                                                                      LoggedIn usr -> Just usr
-                                                                      _ -> Nothing)
-                            (Dict.fromList [ ("Blog"
-                                             , TabEntry "Home" ""
-                                                 (blog_tab settings model)
-                                                 (Just GoHome)
-                                                 ["*"])
-                                           , ("RssFeeds"
-                                             , TabEntry "RSS Feeds" ""
-                                                 (rss_tab model settings)
-                                                 (Just (PushUrl "/blog/feeds"))
-                                                 ["create-post"] ) -- <- TODO make a real permission for rss
-                                           , ("ManagePosts"
-                                             , TabEntry "Manage posts" ""
-                                                 (postmanager_tab model)
-                                                 (Just (PushUrl "/blog/postadmin"))
-                                                 ["create-post", "delete-post", "edit-post"])
-                                           , ("ManageMedia"
-                                             , TabEntry "Manage media" ""
-                                                 (mediamanager_tab model)
-                                                 (Just (PushUrl "/blog/mediamanager"))
-                                                 ["create-post", "delete-post", "edit-post"])
-                                           , ("SettingsTab"
-                                             , TabEntry "Settings" ""
-                                                 (settings_tab settings model)
-                                                 (Just (PushUrl "/blog/settings"))
-                                                 ["update-settings"])
-                                           , ("SettingLogs"
-                                             , TabEntry ("Logs" ++ (if model.ringLogAlarm then " (!!!!!!)" else ""))
-                                                 (if model.ringLogAlarm then " alert " else "")
-                                                 (text "in the frontpage these views don't show up anywhere")
-                                                 (Just (PushUrl "/blog/logs"))
-                                                 ["update-settings"])
-                                           , ("PostEditTab"
-                                             , TabEntry "Post editor" ""
-                                                 (posteditor_tab settings model)
-                                                 (Just GenNewPost)
-                                             ["create-post", "edit-post"])])
-                      , div [id "sidebar"] [ UserEditor.loginView model.loginState
-                                           , (sidebarHistory model.titles )
-                                           , (case model.view_state of
-                                                  PostEditorList titles -> PostsAdmin.tagList titles
-                                                  _ -> div [] [])]]]}
diff --git a/elm-frontti/src/Medialist.elm b/elm-frontti/src/Medialist.elm
deleted file mode 100644
index 90b7c71..0000000
--- a/elm-frontti/src/Medialist.elm
+++ /dev/null
@@ -1,66 +0,0 @@
-module Medialist exposing (..)
-
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (..)
-import Json.Decode as D
-import Dict
-    
-
-import Http
-
-import Article
-import Ajax_cmds exposing (..)
-import Creator as C
-import Page as P
-import Message exposing (..)
-import ImageSelector exposing (imageSelector)
-import Image
-
-import UUID
-
-referencing_post_view post = li []
-                             [ a [ href ("/blog/post/" ++ (String.fromInt post.post_id)) ]
-                                 [ text post.post_title ]]
-
-medialist images medialist_state =
-    case medialist_state of
-        Just state ->
-            div [ class "vertical-flex-container" ]
-                (List.append
-                     [div [class "title-flex-container"]
-                          [ button [ class "post-admin-title"
-                                   , onClick RemoveSelectedImages ] [ text "Remove selected" ]
-                          , div [ class "post-admin-title" ] []
-                          , button [ class "post-admin-title"
-                                   , onClick (MarkAllImages (List.map .id images))] [ text "Select all" ]]]
-                     (List.map (\image ->
-                                    let checkbox_id = "delete" ++ (UUID.toString image.id)
-                                    in 
-                                        div [ class "title-flex-container" ]
-                                    [ details [ ]
-                                          [ summary [ class "post-admin-title" ] [h2 [] [ text image.name ]
-                                                                                 , div [] [ text (UUID.toString image.id)]]
-                                          , ImageSelector.image image]
-                                    , details [ class "post-admin-title"]
-                                        [ summary [ attribute "data-testid" "referencing-post"]
-                                              [ text "Referencing posts" ]
-                                        , case (Dict.get (UUID.toString image.id) state.referencing_posts) of
-                                              Just referencing_posts ->
-                                                  if referencing_posts == [] then
-                                                      div [] [ text "No referencing posts" ]
-                                                  else
-                                                       ul []
-                                                           (List.map referencing_post_view referencing_posts)
-                                              Nothing -> div [] [ text "No referencing posts" ]]
-                                    , div [ class "post-admin-title" ]
-                                        [ label [for checkbox_id] [text "Choose for deletion"]
-                                        , input [ type_ "checkbox"
-                                                , id checkbox_id
-                                                , checked (List.member image.id state.selected_ids_for_removal)
-                                                , onClick (MarkImageForRemoval image.id)] []]])
-                          images))
-        Nothing ->
-            div [] [ text "lol et sit oo initialisoinu medialist_statea" ]
-                       
-                       
diff --git a/elm-frontti/src/Message.elm b/elm-frontti/src/Message.elm
deleted file mode 100644
index c46a44d..0000000
--- a/elm-frontti/src/Message.elm
+++ /dev/null
@@ -1,275 +0,0 @@
-port module Message exposing (..)
-
-import Http
-import Html
-import Html.Attributes
-import Json.Encode
-import Browser
-import Time
-import Page as P
-import Article
-import Browser.Navigation as Nav
-import Settings
-import Url
-import Title
-import Feeds
-import Image exposing (Image, ReferencingPost)
-import Logs
-import Initial
-
-import File exposing (File)
-import UUID exposing (UUID)
-import Stack exposing (..)
-import Dict exposing (Dict)
-import Regex 
-    
-type ViewState
-    = PageView P.Page
-    | PostView Article.Article
-    | Loading 
-    | ShowError String
-    | PostEditorList (List Title.Title)                     -- list all the posts in db
-    | PostEditor
-    | MediaList                     -- list all the image blobs in db
-    | TaggedPostsView (List Article.Article)
-    | SettingsEditor
-    | Feeds (List Feeds.Feed) Bool -- <- show_archived?
-                                   -- v- the second List will be parsed as List Regex later
-    | Logs (List Logs.Log) (List Logs.Group) String
-    | UserSettings
-      -- oldpwd 
-      String
-      -- newpwd 
-      String
-      -- the view's user we're editing instead of the LoginState's user who is logged in here 
-      (Maybe LoginUser)
-    | InitialSetup
-      Initial.InitialFormData
-                                                                                               
-      
-
--- a simplified version of ViewState type for the main.elm's tabcomponent 
-type TabState
-    = Blog
-    | RssFeeds
-    | ManagePosts
-    | ManageMedia
-    | SettingsTab 
-    | PostEditTab
-
-viewstate_to_tabstate vs =
-    case vs of
-        PageView _ -> Blog
-        PostView _ -> Blog
-        Loading -> Blog
-        ShowError _ -> Blog
-        PostEditorList _ -> ManagePosts
-        PostEditor -> PostEditTab
-        MediaList -> ManageMedia
-        TaggedPostsView _ -> Blog
-        SettingsEditor -> SettingsTab
-        Feeds _ _ -> RssFeeds
-        Logs _ _ _ -> Blog
-        UserSettings _ _ _ -> Blog
-        InitialSetup _ -> Blog 
-
-tabstate_to_str tb =
-    case tb of
-        Blog -> "Blog"
-        RssFeeds -> "RssFeeds"
-        ManagePosts -> "ManagePosts"
-        ManageMedia -> "ManageMedia"
-        SettingsTab  -> "SettingsTab"
-        PostEditTab -> "PostEditTab"
-                       
-str_to_tabstate str =
-    case str of
-        "Blog" -> Blog
-        "RssFeeds" -> RssFeeds
-        "ManagePosts" -> ManagePosts
-        "ManageMedia" -> ManageMedia
-        "SettingsTab"  -> SettingsTab
-        "PostEditTab" -> PostEditTab
-        _ -> Blog
-
-type alias User =
-    { username : String
-    , nickname : String
-    , img_location : String
-    }
-
-type LoginState
-    = LoggedIn LoginUser
-    | LoggingIn String String
-    | LoginFailed
-    | LoggedOut      
-
-
-type alias LoginUser =
-    { nickname : String
-    , username : String
-    , img_location : String
-    , primary_group_name : String
-    , permissions : List String
-    , id: Int                   --unique and immutable key, needed because UserEditor.editor lets user change all the other values
-    }
-
-type alias MediaListState =
-    { selected_ids_for_removal : List UUID
-    , referencing_posts : Dict String (List ReferencingPost)}
-
-type alias PostEditorSettings =
-    { article : Article.Article
-    , selected_tag : String
-    , show_preview : Bool
-    , previewing_previously : Maybe Article.Article}
-
-type FeedReaderState
-    = PerFeed
-    | SingleFeed
-    | FeedManager 
-      
-str_to_readerState str =
-    case str of
-        "PerFeed" -> Just PerFeed
-        "SingleFeed" -> Just SingleFeed
-        "FeedManager" -> Just FeedManager
-        _ -> Nothing
-             
-type alias Model =
-    { view_state : ViewState
-    , settings : Maybe Settings.Settings
-    , showImageModal : Bool
-    , draggingImages : Bool
-    , loadedImages : List Image
-    , medialist_state : Maybe MediaListState
-    , loginState : LoginState
-    , key : Nav.Key
-    , url : Url.Url
-    , postEditorSettings: Maybe PostEditorSettings
-    , zone : Time.Zone
-    , titles : List Article.Title
-    , searchedPosts : List Article.PreviousArticle
-    , new_feed: Maybe Feeds.NewFeed
-    , feedReaderState: FeedReaderState
-    , feedMetadata: Maybe Feeds.FeedMetadata
-    , ringLogAlarm: Bool}
-    
-type Msg
-  = PageReceived (Result Http.Error P.Page)
-  | PostReceived (Result Http.Error Article.Article)
-  | SettingsReceived (Result Http.Error Settings.Settings)
-  | TitlesReceived (Result Http.Error (List Article.Title))
-  | EditableTitlesReceived (Result Http.Error (List Article.Title))
-  | UrlChanged Url.Url
-  | LinkClicked Browser.UrlRequest
-  | LoginFocus
-  | ChangeUsername String
-  | ChangePassword String
-  | DoLogIn
-  | LoginSuccess (Result Http.Error LoginUser)
-  | GotSession (Result Http.Error LoginUser)
-  | OpenPostEditor Int
-  | EditorPostReceived (Result Http.Error Article.Article)
-  | PromptTag String
-  | ReceivedTag String
-  | AceStateUpdate String
-  | SelectTag String
-  | Alert String
-  | DropTag String
-  | SavePost Article.Article
-  | HttpIgnoreResponse (Result Http.Error String)
-  | HttpGoHome (Result Http.Error String)
-  | GoHome
-  | ChangeTitle String
-  | RunAce String
-  | GetListOfImages
-  | GotListOfImages Bool (Result Http.Error (List Image.Image))
-  | SelectedImage UUID
-  | EditorDragEnter
-  | EditorDragLeave
-  | GotFiles (File.File -> Cmd Msg) File (List File) 
-  | GotInputFiles (List File)
-  | UploadedImage (Result Http.Error Image.PostImageResponse)
-  | MarkImageForRemoval UUID
-  | MarkAllImages (List UUID)
-  | RemoveSelectedImages
-  | HttpManagerGetListOfImages (Result Http.Error String)
-  | GotReferencingPosts (Result Http.Error (List Image.ReferencingPost))
-  | PushUrl String
-  | AdjustTimeZone Time.Zone
-  | GotTaggedPosts  (Result Http.Error (List Article.Article))
-  | ToggleArticlePreview
-  | GotOldPost (Result Http.Error Article.Article)
-  | GenNewPost 
-  | NewPostGenerated (Result Http.Error Int)
-  | ToggleArticleUnlisted
-  | ToggleArticleHidden
-  | AdminSettingsReceived (Result Http.Error Settings.Settings)
-  | SetTimeFormat String
-  | SetBlogTitle String
-  | SetPageSize String
-  | SaveSettings
-  | SettingsSaved (Result Http.Error ())
-  | ShowPreviousPostsModal
-  | ClosePreviousPostsModel
-  | PreviouslySearchInput String
-  | PreviouslySearchResult (Result Http.Error (List Article.PreviousArticle))
-  | SelectPreviouslyPost Article.PreviousArticle
-  | DropPreviously Article.PreviousArticle
-  | SetPreviouslyLabel String
-  | LoadPreviouslyPreview Article.PreviousArticle
-  | PreviousPostReceived (Result Http.Error Article.Article)
-  | ClosePreviousPostPreviewModal
-  | FeedsReceived (Result Http.Error (List Feeds.Feed))
-  | SetFeedUrl String 
-  | SetFeedName String
-  | AddFeed Feeds.NewFeed
-  | FeedAdded (Result Http.Error ())
-  | SelectTab String String
-  | ReadFeedItem UUID UUID Bool
-  | ShowArchivedFeedItems Bool
-  | FeedItemReadResponse (Result Http.Error ())
-  | DeleteFeed UUID
-  | FeedDeleted (Result Http.Error ())
-  | FeedMetaReceived (Result Http.Error Feeds.FeedMetadata)
-  | SelectExcerpt UUID
-  | CreateExcerptPost String UUID 
-  | ExcerptCreated (String, String)
-  | GotAdminLogs (Result Http.Error (List Logs.Log))
-  | EditGroupRegexp String
-  | SaveLogGroup String
-  | DeleteLogGroup String
-  | SetLogAlarmy Logs.ParsedGroup Bool
-  | LogGroupsSaved (Result Http.Error ())
-  | GotLogGroups (Result Http.Error (List Logs.Group))
-  | GotTopbarLogAlarm (Result Http.Error Logs.TopbarAlarm)
-  | SetDomain String
-  | SetUsername String
-  | SetNickname String
-  | SetNewpwd String
-  | SetOldpwd String
-  | SubmitChangedUser String String LoginUser
-  | UserSubmitResult (Result Http.Error ())
-  | UploadedOwnProfilePic (Result Http.Error Image.PostImageResponse)
-  | SetInitialUsername String
-  | SetInitialNickname String
-  | SetInitialPassword String
-  | SetInitialDomain String
-  | SetInitialBlog_Title String
-  | SetInitialRss_Title String
-  | SetInitialRss_Link String
-  | SetInitialRss_Description String
-  | SetInitialRss_Lang String
-  | SetInitialRss_Email String
-  | SaveInitialData Initial.InitialFormData
-  | PostInitialSuccess (Result Http.Error ())
-
--- ports
-port reallySetupAce : String -> Cmd msg
-port addImgToAce : String -> Cmd msg
-port alert : String -> Cmd msg
-
--- dumb shit that would deserve its own module
-dangerouslySetInnerHTML: String -> Html.Attribute msg
-dangerouslySetInnerHTML = Json.Encode.string >> Html.Attributes.property "dangerouslySetInnerHTML"
diff --git a/elm-frontti/src/Page.elm b/elm-frontti/src/Page.elm
deleted file mode 100644
index c9d51db..0000000
--- a/elm-frontti/src/Page.elm
+++ /dev/null
@@ -1,22 +0,0 @@
-module Page exposing (..)
-
-
-import Http
-import Html exposing (Html, text, pre)
-import Article as A
-
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Decode.Pipeline exposing (required)
-import Json.Decode.Extra as Extra
-
-type alias Page =
-    { last_page: Bool
-    , id : Int
-    , posts: List A.Article}
-
-pageDecoder : Decoder Page
-pageDecoder =
-    Decode.map3 Page
-        (Decode.field "last-page?" Decode.bool)
-        (Decode.field "id" Decode.int)
-        (Decode.field "posts" (Decode.list A.articleDecoder))
diff --git a/elm-frontti/src/PostEditor.elm b/elm-frontti/src/PostEditor.elm
deleted file mode 100644
index 7615999..0000000
--- a/elm-frontti/src/PostEditor.elm
+++ /dev/null
@@ -1,161 +0,0 @@
-module PostEditor exposing (..)
-
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (..)
-import Json.Decode as D
-    
-
-import Http
-
-import Article_view
-import Ajax_cmds exposing (..)
-import Creator as C
-import Page as P
-import Message exposing (..)
-import ImageSelector exposing (imageSelector)
-import Button exposing (murja_button)
-import Tab exposing (..)
-import Dict exposing (Dict)
-
-import File exposing (File)
-import File.Select as Select
-
--- dropDecoder : D.Decoder Msg
-dropDecoder handler =
-  D.at ["dataTransfer","files"] (D.oneOrMore (GotFiles handler) File.decoder )
-
-
-hijackOn : String -> D.Decoder msg -> Attribute msg
-hijackOn event decoder =
-  preventDefaultOn event (D.map hijack decoder)
-
-
-hijack : msg -> (msg, Bool)
-hijack msg =
-  (msg, True)
-      
-
-optionize tag = option [value tag] [text tag]
-
-tagView post selectedTag = div [class "tagview editor-grouper"]
-                           [ select [ multiple True
-                                    , class "tag-select"
-                                    , id "tag-select"
-                                    , onInput SelectTag
-                                    , attribute "data-tags" (String.join "," post.tags)] (List.map optionize post.tags)
-                           , murja_button [ onClick (PromptTag "New tag? ")
-                                          , id "new-tag-btn"]
-                                 [ text "Add tag"]
-                           , murja_button [ onClick (DropTag selectedTag)
-                                          , attribute "data-testid" "remove-tag"]
-                               [text "Remove selected tag"]]
-
-editor params =
-    div [ class "editor-container" ]
-        [ node "ace-editor"
-             (  params
-                    ++ [ attribute "theme" "ace/theme/monokai"
-                       , attribute "mode" "ace/mode/html"])
-              []]
-
-filesDecoder : D.Decoder (List File)
-filesDecoder =
-  D.at ["target","files"] (D.list File.decoder)
-
-previously_row p
-    = li [] [ murja_button [ onClick (LoadPreviouslyPreview p) ] [ text p.title]
-            , button [ onClick (DropPreviously p)] [ text "X"]]
-
-previouslyButtons post loadedPosts previewingArticle article_settings =
-    let { app_settings, loginState , tz} = article_settings
-    in
-    div [ class "previously-buttons" ]
-        [ murja_button [ onClick ShowPreviousPostsModal ] [ text "Link previous posts"]
-        , ul []
-            ( post.previously
-            |> List.map previously_row)
-        , node "dialog" [ id "previewPreviouslyModal" ]
-            (case previewingArticle of
-                Just article ->
-                    [ div [ class "dialog" ]
-                          [ header [ class "previouslyHeader" ] [ button [ onClick ClosePreviousPostPreviewModal ] [ text "X"]]
-                          , case loginState of
-                                LoggedIn user ->
-                                    Article_view.articleView app_settings loginState tz article
-                                _ -> div [] [text "You're not logged in"]]]
-                Nothing -> [])
-        , node "dialog" [ id "previouslyModal" ]
-            [ div [ class "dialog" ]
-                  [ header [ class "previouslyHeader" ] [ button [ onClick ClosePreviousPostsModel ] [ text "X"]]
-                  , select [ multiple True
-                           , class "previouslyPostResult"]
-                      (List.map (\prev_post ->
-                                     option [ onClick (SelectPreviouslyPost prev_post) ] [ text prev_post.title ]) loadedPosts)
-                  , input [ type_ "text"
-                          , placeholder "Search for posts"
-                          , onInput PreviouslySearchInput] []]]]
-      
-postEditor post tag showImageModal loadedImages draggingImages editorSettings app_settings tz loginState searchedPosts
-    = [ div [ class "editor-top" ]
-            [ div [ id "editor-buttons"
-                  , class "editor-grouper"]
-                  [ input [ name "title"
-                          , id "editor-post-title"
-                          , value post.title
-                          , onInput ChangeTitle] []
-                  , murja_button [ id "editor-post-save"
-                                 , onClick (SavePost post) ] [text "Save version"]
-                  , label [ for "file-pictures-input"
-                          , class "murja-button"] [ text "Add pictures from device"]
-                  , input [ type_ "file"
-                          , multiple False
-                          , style "display" "none"
-                          , id "file-pictures-input"
-                          , on "change" (D.map GotInputFiles filesDecoder)] []
-                  , murja_button [ id "image-insert-btn"
-                                 , onClick GetListOfImages]
-                        [text "Insert image"]]
-            , tagView post tag
-            , previouslyButtons post searchedPosts editorSettings.previewing_previously
-                { app_settings = app_settings
-                , loginState = loginState
-                , tz = tz }
-            , div [ class "editor-grouper" ]
-                [ label [ for "hidden"]
-                      [ text "Hidden article"]
-                , input [ type_ "checkbox"
-                        , id "hidden"
-                        , checked post.hidden
-                        , onClick ToggleArticleHidden ] []
-                , label [ for "unlisted"]
-                    [ text "Unlisted article"]
-                , input [ type_ "checkbox"
-                        , id "unlisted"
-                        , checked post.unlisted
-                        , onClick ToggleArticleUnlisted] []]]
-      , if showImageModal then imageSelector loadedImages else div [] []
-      , case loginState of
-            LoggedIn user ->
-                tabs "posteditor-preview-tab" (if editorSettings.show_preview then
-                                                   "PreviewArticle"
-                                               else
-                                                   "EditArticle") (Just user)
-                    (Dict.fromList [ ("EditArticle"
-                                     , TabEntry "Edit article" ""
-                                         (editor [ id "editor-post-content"
-                                                 , style "background-color" (if draggingImages then "#880088" else "")
-                                                 , hijackOn "dragenter" (D.succeed EditorDragEnter)
-                                                 , hijackOn "dragend" (D.succeed EditorDragLeave)
-                                                 , hijackOn "dragover" (D.succeed EditorDragEnter)
-                                                 , hijackOn "dragleave" (D.succeed EditorDragLeave)
-                                                 , hijackOn "drop" (dropDecoder (postPicture UploadedImage editor_image_api))
-                                                 , hijackOn "ready" (D.succeed (RunAce post.content))])
-                                             Nothing ["*"])
-                                   , ("PreviewArticle"
-                                     , TabEntry "Preview article" ""
-                                         (Article_view.articleView app_settings loginState tz post)
-                                         Nothing ["*"])])
-            _ -> div [] [text "You're not logged in"]]
-
-editor_image_api = "/api/pictures"    
diff --git a/elm-frontti/src/PostsAdmin.elm b/elm-frontti/src/PostsAdmin.elm
deleted file mode 100644
index c20d6a5..0000000
--- a/elm-frontti/src/PostsAdmin.elm
+++ /dev/null
@@ -1,53 +0,0 @@
-module PostsAdmin exposing (..)
-
-import Message exposing (..)
-import Set
-
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (..)
-
-import Date_utils exposing (int_to_month_string)
-
-tagListElement allTags tag =
-    let count = (  allTags
-                |> List.filter ((==) tag)
-                |> List.length) in
-    a [ href ("/blog/tags/" ++ tag)
-      , style "display" "block" ]
-    [ text (tag ++ " (" ++ (String.fromInt count) ++ ")")]
-
-tagList titles =
-    let allTags = (  titles
-                  |> List.concatMap (\title -> title.tags))
-        tags = (  allTags
-               |> Set.fromList
-               |> Set.toList
-               |> List.filter ((/=) "")) in
-    div [] (List.append [h3 [] [text ("Tags in the system (" ++ String.fromInt (List.length tags) ++ "): ")]]
-                (  tags 
-                |> List.map (tagListElement allTags)))
-
-titleView title =  case (int_to_month_string title.month) of
-                       Just month -> 
-                           div [ class "title-flex-container" ] 
-                               [ span [class "post-admin-title" ] [text ( title.title ++ " - " ++ month  ++ ", " ++ (String.fromInt title.year))]
-                               , a [ href ("/blog/post/edit/" ++ String.fromInt title.id)
-                                   , attribute "data-testid" "manager-edit-post-btn"
-                                   , onClick (OpenPostEditor title.id)] [text "Edit"]
-                               -- this has never been implemented...
-                               -- , a [href ("/blog/post/remove/" ++ String.fromInt title.id)] [text "Remove"]
-                               , div [class "post-admin-title" ]
-                                   (List.append  [ h3 [] [text "Tags: "]]
-                                        (List.map (\tag -> a [ href ("/blog/tags/" ++ tag)
-                                                             , style "display" "block" ]
-                                                       [ text tag ]) title.tags))]
-                       Nothing -> div [] [text ("Parsing month " ++ (String.fromInt title.month) ++ " failed")]
-
-view titles = (div [class "vertical-flex-container"]
-                   (if titles /= [] then 
-                       (titles
-                       |> List.map titleView)
-                   else [ span [] [ text "No posts in murja. Create one by "
-                                  , button [ onClick GenNewPost ] [ text "clicking here" ]]]))
-                              
diff --git a/elm-frontti/src/RouteParser.elm b/elm-frontti/src/RouteParser.elm
deleted file mode 100644
index b3e0cca..0000000
--- a/elm-frontti/src/RouteParser.elm
+++ /dev/null
@@ -1,42 +0,0 @@
-module RouteParser exposing (..)
-
-import Url
-import Url.Parser exposing (..)
-import String exposing (fromInt)
--- http://localhost:3000/blog/post/edit/21
-type Route
-    = Page Int
-    | Post Int
-    | PostAdmin
-    | MediaManager
-    | PostEditor Int
-    | TaggedPosts String
-    | PostVersion Int Int
-    | SettingsEditor
-    | FeedReader
-    | Home
-    | Logs 
-    | NotFound
-    | OwnUserSettings
-    | InitialSetup 
-
-routeParser =
-    oneOf
-        [ map Page (s "blog" </> (s "page" </> int))
-        , map Home Url.Parser.top
-        , map Home (s "blog")
-        , map PostVersion (s "blog" </> (s "post" </> (int </> (s "version" </> int))))
-        , map Post (s "blog" </> (s "post" </> int))
-        , map PostEditor (s "blog" </> (s "post" </> (s "edit" </> int)))
-        , map MediaManager (s "blog" </> (s "mediamanager"))
-        , map SettingsEditor (s "blog" </> (s "settings"))
-        , map TaggedPosts (s "blog" </> (s "tags" </> string))
-        , map Logs (s "blog" </> (s "logs"))
-        , map PostAdmin (s "blog" </> (s "postadmin"))
-        , map FeedReader (s "blog" </> (s "feeds"))
-        , map OwnUserSettings (s "blog" </> (s "usersettings"))
-        , map InitialSetup (s "blog" </> (s "initial-setup"))]
-        
-
-url_to_route url =
-            Maybe.withDefault NotFound (parse routeParser url)
diff --git a/elm-frontti/src/Settings.elm b/elm-frontti/src/Settings.elm
deleted file mode 100644
index 18c3f8c..0000000
--- a/elm-frontti/src/Settings.elm
+++ /dev/null
@@ -1,29 +0,0 @@
-module Settings exposing (..)
-
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Decode.Pipeline exposing (required)
-import Json.Decode.Extra as Extra
-import Json.Encode as Json exposing (..)
-
-type alias Settings =
-    { time_format : String
-    , blog_title : String
-    , recent_post_count : Int
-    , previously_label: String
-    , domain: String 
-    }
-
-settingsDecoder = Decode.map5 Settings
-                  (Decode.field "time-format" Decode.string)
-                  (Decode.field "blog-title" Decode.string)
-                  (Decode.field "recent-post-count" Decode.int)
-                  (Decode.field "previously_label" Decode.string)
-                  (Decode.field "domain" Decode.string)
-                     
-encodeSettings settings =
-    object
-        [ ( "time-format", string settings.time_format )
-        , ( "blog-title", string settings.blog_title)
-        , ( "recent-post-count", int settings.recent_post_count)
-        , ( "previously_label", string settings.previously_label)
-        , ( "domain", string settings.domain)]
diff --git a/elm-frontti/src/SettingsEditor.elm b/elm-frontti/src/SettingsEditor.elm
deleted file mode 100644
index a0be10c..0000000
--- a/elm-frontti/src/SettingsEditor.elm
+++ /dev/null
@@ -1,44 +0,0 @@
-module SettingsEditor exposing (..)
-
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (..)
-import Json.Decode as D
-
-import Message exposing (..)
-
-editor settings =
-    div [ class "form-grid" ]
-        [ label [ for "time-format"]
-              [ text "Time format "]
-        , input [ id "time-format"
-                , onInput SetTimeFormat 
-                , value settings.time_format] []
-            
-        , label [ for "title" ]
-            [ text "Title" ]
-        , input [ id "title"
-                , onInput SetBlogTitle 
-                , value settings.blog_title] []
-
-        , label [ for "page_size" ]
-            [ text "Page size (posts)"]
-        , input [ id "page_size"
-                , onInput SetPageSize 
-                , value (String.fromInt settings.recent_post_count)
-                , type_ "number"] []
-
-        , label [ for "previously" ]
-            [ text "Previously link label" ]
-        , input [ id "previously"
-                , onInput SetPreviouslyLabel
-                , value settings.previously_label] []
-            
-        , label [ for "domain" ]
-            [ text "Site domain (relevant for cookies)" ]
-        , input [ id "domain"
-                , onInput SetDomain
-                , value settings.domain] []
-
-        , button [ onClick SaveSettings ]
-            [ text "Save settings"]]
diff --git a/elm-frontti/src/Tab.elm b/elm-frontti/src/Tab.elm
deleted file mode 100644
index e99186e..0000000
--- a/elm-frontti/src/Tab.elm
+++ /dev/null
@@ -1,47 +0,0 @@
-module Tab exposing (..)
-
-import Dict exposing (Dict)
-import Set exposing (Set)
-import Html exposing (..)
-import Html.Attributes exposing (..)
-import Html.Events exposing (..)
-import Message exposing (..)
-
-type alias TabEntry =
-    { title: String
-    , classes: String
-    , component: Html Msg               
-    , onclick: Maybe Msg
-    , permissions: List String}
-
--- tabs: String -> String -> Dict String TabEntry -> Html Msg
-tabs tab_id selected_tab usr tabentries =
-    let tab_ids = ( tabentries
-                  |> Dict.filter (\k -> \entry -> case usr of
-                                                      Just user -> ((  entry.permissions
-                                                                    |> Set.fromList
-                                                                    |> Set.intersect (Set.fromList user.permissions)
-                                                                    |> Set.isEmpty
-                                                                    |> not)
-                                                                   ||
-                                                                        (List.member "*" entry.permissions))
-                                                      Nothing -> (List.member "*" entry.permissions))
-                  |> Dict.keys)
-        selected_tab_component = Dict.get selected_tab tabentries 
-    in 
-    div [ class "tabs"
-        , id tab_id ]
-        [ ul [ class "tab-headers" ]
-              (  tab_ids
-              |> List.map (\id ->
-                               let entry_ = Dict.get id tabentries in
-                               case entry_ of
-                                   Just entry -> 
-                                       li [ class <| (if selected_tab == id then "tab-header tab-selected" else "tab-header") ++ " " ++ entry.classes 
-                                          , onClick (case entry.onclick of
-                                                         Just oc -> oc
-                                                         Nothing -> SelectTab tab_id id)] [ text <| entry.title ]
-                                   Nothing -> li [] [ text "Unknown tab" ]))
-        , case selected_tab_component of
-              Just c -> c.component
-              Nothing -> div [] [ text <| "Invalid selected tab key " ++ (Debug.toString selected_tab)]]
diff --git a/elm-frontti/src/Title.elm b/elm-frontti/src/Title.elm
deleted file mode 100644
index b5ffe05..0000000
--- a/elm-frontti/src/Title.elm
+++ /dev/null
@@ -1,8 +0,0 @@
-module Title exposing (..)
-
-type alias Title =
-    { title: String
-    , id: Int
-    , year: Int
-    , month: Int
-    , tags: List String}
diff --git a/elm-frontti/src/User.elm b/elm-frontti/src/User.elm
deleted file mode 100644
index 5b0ce17..0000000
--- a/elm-frontti/src/User.elm
+++ /dev/null
@@ -1,83 +0,0 @@
-module User exposing (..)
-
-import Html exposing (..)
-import Html.Attributes as A exposing (..)
-import Html.Events exposing (..)
-
-import Message exposing (..)
-import Article exposing (decodeApply)
-import Json.Decode as Decode exposing (Decoder, succeed)
-import Json.Decode.Pipeline exposing (required)
-import Json.Decode.Extra as Extra
-import Json.Encode as Json
-import File exposing (File)
-
-
-    -- {
-    --       "nickname": "Feuer",
-    --             "img_location": "https://feuerx.net/etc/feuer.jpeg",
-    --             "userid": 1,
-    --             "primary-group-name": "Admins",
-    --             "permissions": [
-    --                  "edit-self",
-    --                          "comment-post",
-    --                          "edit-user",
-    --                          "create-comment",
-    --                          "edit-post",
-    --                          "delete-post",
-    --                          "create-post",
-    --                          "create-page",
-    --                          "delete-comment",
-    --                          "delete-user",
-    --                          "can-import",
-    --                          "edit-comment"
-    --                        ]
-
-
-nicknameDecoder = Decode.field "nickname" Decode.string
-imgDecoder = Decode.field "img_location" Decode.string
-group_name_decoder = Decode.field "primary-group-name" Decode.string
-permissionsDecoder = Decode.field "permissions" (Decode.list Decode.string)
-usernameDecoder = Decode.field "username" Decode.string
-idDecoder = Decode.field "userid" Decode.int
-                     
--- |> == clojure's ->>
-userDecoder : Decoder LoginUser
-userDecoder =
-    Decode.succeed LoginUser
-        |> decodeApply nicknameDecoder
-        |> decodeApply usernameDecoder
-        |> decodeApply imgDecoder
-        |> decodeApply group_name_decoder
-        |> decodeApply permissionsDecoder
-        |> decodeApply idDecoder
-    
-stateToText state =
-    case state of
-        LoggedIn _ -> "LoggedIn"
-        LoggingIn _ _ -> "LoggingIn"
-        LoggedOut -> "LoggedOut"
-        LoginFailed -> "LoginFailed"
-
-user_avatar creator = img [class "user_avatar", src creator.img_location] []
-
-type alias UserLoggingIn =
-    { username : String
-    , password : String}
-
-encodeLoggingIn user =
-    Json.object
-        [ ("username", Json.string user.username)
-        , ("password", Json.string user.password)]
-
-encodeEditorUser : LoginUser -> String -> String-> Json.Value
-encodeEditorUser usr oldpasswd newpasswd =
-    Json.object
-        [ ("nickname", Json.string usr.nickname)
-        , ("username", Json.string usr.username)
-        , ("img_location", Json.string usr.img_location)
-        , ("id", Json.int usr.id) -- unique and immutable key, needed because UserEditor.editor lets user change all the other values
-        , ("old-password", Json.string oldpasswd)
-        , ("new-password", Json.string newpasswd)]                   
-    
-             
diff --git a/elm-frontti/src/UserEditor.elm b/elm-frontti/src/UserEditor.elm
deleted file mode 100644
index 4237da8..0000000
--- a/elm-frontti/src/UserEditor.elm
+++ /dev/null
@@ -1,68 +0,0 @@
-module UserEditor exposing (..)
-
-import Html exposing (..)
-import Html.Attributes as A exposing (..)
-import Html.Events exposing (..)
-
-import Message exposing (..)
-import PostEditor exposing (hijackOn, dropDecoder)
-import Ajax_cmds exposing (postPicture)
-
-import Json.Decode as D
-
-editor draggingImages oldpasswd newpasswd user =
-    div [] [
-         div [ class "vertical-flex-container"
-             , hijackOn "dragenter" (D.succeed EditorDragEnter)
-             , hijackOn "dragend" (D.succeed EditorDragLeave)
-             , hijackOn "dragover" (D.succeed EditorDragEnter)
-             , hijackOn "dragleave" (D.succeed EditorDragLeave)
-             , hijackOn "drop" (dropDecoder (postPicture UploadedOwnProfilePic "/api/pictures/profile"))
-             , style "background-color" (if draggingImages then "#880088" else "")
-             ]
-             [ h1 [ ] [text <| "User " ++ user.nickname ++ "'s settings" ]
-             , img [ src user.img_location
-                   , class "user_avatar"  ] []
-             , div [ id "img-helper"] [ text "If you want a new profile picture, drag and drop an image file here" ]
-             , label [] [ text "Username: "
-                        , input [ A.required True
-                                , value user.username
-                                , onInput SetUsername 
-                                , type_ "text" ] []]
-             , label [] [ text "Nickname: "
-                        , input [ A.required True
-                                , value user.nickname
-                                , onInput SetNickname
-                                , type_ "text"] []]
-             , label [] [ text "New password: "
-                        , input [ type_ "password"
-                                , onInput SetNewpwd
-                                , value newpasswd] []]
-             , label [] [ text "Current password: "
-                        , input [ A.required True
-                                , type_ "password"
-                                , value oldpasswd
-                                , onInput SetOldpwd] []]]
-        , button [ onClick (SubmitChangedUser oldpasswd newpasswd user) ] [ text "Submit changes!"]]
-        
-loginView loginstate =
-    let actual_view = [label [for "username"] [text "Username"],
-                       input [name "username", id "username", attribute "data-testid" "username-input-field", onInput ChangeUsername, onFocus LoginFocus ] [],
-                       label [for "password"] [text "Password"],
-                       input [name "password", attribute "data-testid" "password-input-field", id "password", type_ "password", onInput ChangePassword ] []
-                           -- , label [] [text ("Loginstate: " ++ stateToText loginstate)]
-                      ] in
-    div [] (case loginstate of
-                                  LoggedIn usr ->
-                                      [p [attribute "data-testid" "welcome-user-label"] [ text "Welcome, "
-                                                                                        , a [ href "/blog/usersettings" ]
-                                                                                            [ text usr.nickname]]]
-                                  LoggingIn username password ->
-                                      (List.concat [actual_view,
-                                                    [button [attribute "data-testid" "dologin", onClick DoLogIn] [text "Login!"]]])
-                                  LoggedOut ->
-                                      actual_view
-                                  LoginFailed ->
-                                      (List.concat [actual_view,
-                                                    [button [onClick DoLogIn] [text "Login!"],
-                                                     div [attribute "data-testid" "loginfailed"] [text "Login failed! Check username and password!"]]]))