Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
271 changes: 176 additions & 95 deletions Cargo.lock

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions elm/elm.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
"bburdette/schelme": "3.0.0",
"bburdette/toop": "1.2.0",
"bburdette/typed-collections": "1.0.2",
"bburdette/websocket": "1.0.3",
"bburdette/windowkeys": "1.0.1",
"ceddlyburge/dnd-list": "1.0.0",
"dillonkearns/elm-markdown": "7.0.0",
Expand Down
1 change: 1 addition & 0 deletions elm/src/DataUtil.elm
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ type alias FileUrlInfo =
{ location : String
, filelocation : String
, tauri : Bool
, websockets : Bool
}


Expand Down
116 changes: 102 additions & 14 deletions elm/src/Main.elm
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,7 @@ import ShowMessage
import SlideShow
import SpecialNotes as SN
import SpecialNotesGui as SNG
import TDict
import TSet
import TagAThing
import TagFiles
Expand All @@ -65,6 +66,7 @@ import Url exposing (Url)
import UserSettings
import Util exposing (andMap)
import View
import WebSocket
import WindowKeys
import ZkCommon exposing (StylePalette)

Expand Down Expand Up @@ -93,6 +95,7 @@ type Msg
| TauriAdminReplyData JD.Value
| TauriPublicReplyData JD.Value
| TauriTauriReplyData JD.Value
| ReceiveSocketMsg JD.Value
| LoadUrl String
| InternalUrl Url
| TASelection JD.Value
Expand Down Expand Up @@ -174,6 +177,7 @@ decodeFlags =
|> andMap (JD.field "login" (JD.maybe DataUtil.decodeLoginData))
|> andMap (JD.field "adminsettings" OD.adminSettingsDecoder)
|> andMap (JD.field "tauri" JD.bool)
|> andMap (JD.field "websockets" JD.bool)
|> andMap (JD.field "mobile" JD.bool)


Expand All @@ -189,6 +193,7 @@ type alias Flags =
, login : Maybe DataUtil.LoginData
, adminsettings : OD.AdminSettings
, tauri : Bool
, websockets : Bool
, mobile : Bool
}

Expand All @@ -208,7 +213,7 @@ type LocalValAction
= LocalValAction
{ for : String
, name : String
, action : Maybe String -> ( Model, Cmd Msg )
, action : Model -> Maybe String -> ( Model, Cmd Msg )
}


Expand All @@ -233,7 +238,7 @@ type alias Model =
, ziClosures : Dict Int (Result Http.Error ( Time.Posix, Data.PrivateReply ) -> Msg)
, mobile : Bool
, spmodel : SP.Model
, localValAction : Maybe LocalValAction
, localValAction : Dict String LocalValAction
, zknSearchResult : Data.ZkListNoteSearchResult
}

Expand Down Expand Up @@ -869,6 +874,9 @@ showMessage msg =
TauriTauriReplyData _ ->
"TauriTauriReplyData"

ReceiveSocketMsg _ ->
"ReceiveSocketMsg"

SelectDialogMsg _ ->
"SelectDialogMsg"

Expand Down Expand Up @@ -1381,6 +1389,17 @@ sendZIMsg fui msg =
if fui.tauri then
sendZIMsgTauri <| PrivateClosureRequest Nothing msg

else if fui.websockets then
sendSocketCommand
(WebSocket.encodeCmd <|
WebSocket.Send
{ name = "private"
, content =
JE.encode 0
(Data.privateClosureRequestEncoder (PrivateClosureRequest Nothing msg))
}
)

else
HE.postJsonTask
{ url = fui.location ++ "/private"
Expand Down Expand Up @@ -2201,10 +2220,10 @@ actualupdate msg model =
( nmd, cmd )

( ReceiveLocalVal lv, _ ) ->
case model.localValAction of
case Dict.get lv.name model.localValAction of
Just (LocalValAction lva) ->
if lv.for == lva.for && lv.name == lva.name then
lva.action lv.value
lva.action { model | localValAction = Dict.remove lv.name model.localValAction } lv.value

else
( model, Cmd.none )
Expand Down Expand Up @@ -2236,6 +2255,48 @@ actualupdate msg model =
, Cmd.none
)

( ReceiveSocketMsg jd, _ ) ->
case JD.decodeValue WebSocket.decodeMsg jd of
Ok (WebSocket.Error wsm) ->
( displayMessageDialog model <| "websocket error: " ++ wsm.error
, Cmd.none
)

Ok (WebSocket.Data wsm) ->
if wsm.name == "private" then
case JD.decodeString (makeTDDecoder Data.privateClosureReplyDecoder) wsm.data of
Ok td ->
case td.data.closureId of
Just id ->
case Dict.get id model.ziClosures of
Just closure ->
let
cmsg =
closure (Ok ( td.utc, td.data.reply ))
in
actualupdate cmsg model

Nothing ->
actualupdate (ZkReplyData (Ok ( td.utc, td.data.reply ))) model

Nothing ->
actualupdate (ZkReplyData (Ok ( td.utc, td.data.reply ))) model

Err e ->
( displayMessageDialog model <| JD.errorToString e ++ "\n" ++ JE.encode 2 jd
, Cmd.none
)

else
( displayMessageDialog model <| "unknown websocket connection - \"" ++ wsm.name ++ "\""
, Cmd.none
)

Err e ->
( displayMessageDialog model <| JD.errorToString e ++ "\n" ++ JE.encode 2 jd
, Cmd.none
)

( TauriUserReplyData jd, _ ) ->
case JD.decodeValue OD.userResponseDecoder jd of
Ok d ->
Expand Down Expand Up @@ -2722,7 +2783,7 @@ actualupdate msg model =
Data.PbyZkNoteAndLinks znl ->
let
action =
\mbstate ->
\amodel mbstate ->
let
znas =
{ znal = znl, mbstate = mbstate }
Expand All @@ -2743,34 +2804,34 @@ actualupdate msg model =
ngets =
makePubNoteCacheGets model znl.zknote.content
in
( { model | state = vstate }
( { amodel | state = vstate }
, Cmd.batch ngets
)

lid =
SNG.localDataId znl.zknote.id
in
( { model | localValAction = Just <| LocalValAction { for = "lva", name = lid, action = action } }
( { model | localValAction = Dict.insert lid (LocalValAction { for = "lva", name = lid, action = action }) model.localValAction }
, LS.getLocalVal { for = "lva", name = lid }
)

Data.PbyZkNoteAndLinksWhat znlw ->
let
action =
\mbstate ->
\amodel mbstate ->
let
znas : DataUtil.ZkNoteAndStateWhat
znas =
{ znl = { znal = znlw.znl, mbstate = mbstate }
, what = znlw.what
}
in
onZkNoteStatePbWhat model pt znas
onZkNoteStatePbWhat amodel pt znas

lid =
SNG.localDataId znlw.znl.zknote.id
in
( { model | localValAction = Just <| LocalValAction { for = "lva", name = lid, action = action } }
( { model | localValAction = Dict.insert lid (LocalValAction { for = "lva", name = lid, action = action }) model.localValAction }
, LS.getLocalVal { for = "lva", name = lid }
)

Expand Down Expand Up @@ -3255,20 +3316,20 @@ actualupdate msg model =
Data.PvyZkNoteAndLinksWhat znew ->
let
action =
\mbstate ->
\amodel mbstate ->
let
znas : DataUtil.ZkNoteAndStateWhat
znas =
{ znl = { znal = znew.znl, mbstate = mbstate }
, what = znew.what
}
in
onZkNoteStateEditWhat model pt znas
onZkNoteStateEditWhat amodel pt znas

lid =
SNG.localDataId znew.znl.zknote.id
in
( { model | localValAction = Just <| LocalValAction { for = "lva", name = lid, action = action } }
( { model | localValAction = Dict.insert lid (LocalValAction { for = "lva", name = lid, action = action }) model.localValAction }
, LS.getLocalVal { for = "lva", name = lid }
)

Expand Down Expand Up @@ -5223,6 +5284,7 @@ init flags url key zone fontsize =
{ location = flags.location
, filelocation = flags.filelocation
, tauri = flags.tauri
, websockets = flags.websockets
}
, navkey = key
, seed = seed
Expand All @@ -5241,7 +5303,7 @@ init flags url key zone fontsize =
, ziClosures = Dict.empty
, mobile = flags.mobile
, spmodel = SP.initModel
, localValAction = Nothing
, localValAction = Dict.empty
, zknSearchResult =
{ notes = []
, offset = 0
Expand Down Expand Up @@ -5270,6 +5332,24 @@ init flags url key zone fontsize =
, { key = "l", ctrl = True, alt = True, shift = False, preventDefault = True }
]

opensock =
if flags.websockets then
sendSocketCommand
(WebSocket.encodeCmd <|
WebSocket.Connect
{ name = "private"
, address =
flags.location
-- http -> ws, https -> wss
|> String.replace "http" "ws"
|> (\s -> s ++ "/privatews")
, protocol = ""
}
)

else
Cmd.none

( m, c ) =
initToRoute imodel imodel.initialRoute
in
Expand All @@ -5278,6 +5358,7 @@ init flags url key zone fontsize =
[ c
, geterrornote
, setkeys
, opensock
]
)

Expand Down Expand Up @@ -5349,6 +5430,7 @@ main =
, receiveUITauriResponse TauriUserReplyData
, receivePITauriResponse TauriPublicReplyData
, receiveTITauriResponse TauriTauriReplyData
, receiveSocketMsg ReceiveSocketMsg
]
++ rdysubs
, onUrlRequest = urlRequest
Expand Down Expand Up @@ -5412,3 +5494,9 @@ port sendKeyCommand : JE.Value -> Cmd msg
skcommand : WindowKeys.WindowKeyCmd -> Cmd Msg
skcommand =
WindowKeys.send sendKeyCommand


port receiveSocketMsg : (JD.Value -> msg) -> Sub msg


port sendSocketCommand : JE.Value -> Cmd msg
2 changes: 1 addition & 1 deletion orgauth
1 change: 1 addition & 0 deletions server-lib/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -50,3 +50,4 @@ girlboss = {version = "1.0.0-alpha.4", features = ["actix-rt"]}
nom = "8.0.0"
# lapin = { version = "3.7.2", default-features = false, features = [ "rustls--ring", "default-runtime" ] }
lapin = { version = "2.5.5", default-features = true }
actix-ws = "0.4.0"
3 changes: 3 additions & 0 deletions server-lib/src/error.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use actix_session;
use actix_web::error as awe;
use actix_web::ResponseError;
use cookie;
use girlboss;
use regex;
Expand Down Expand Up @@ -49,6 +50,8 @@ pub fn annotate_string(s: String, source: Error) -> Error {
annotate(Error::String(s), source)
}

impl ResponseError for Error {}

impl fmt::Display for AnnotatedE {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{} \n source: {}", self.error, self.source)
Expand Down
9 changes: 5 additions & 4 deletions server-lib/src/interfaces.rs
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ pub fn login_data_for_token(

pub async fn connect_and_make_lapin_info(
state: &State,
token: Option<String>,
token: &Option<String>,
) -> Option<LapinInfo> {
// TODO: maybe attempt reconnect only every X seconds, so as not to
// slow processing during rmq outage.
Expand Down Expand Up @@ -236,7 +236,7 @@ pub async fn zk_interface_loggedin_streaming(
pub async fn zk_interface_loggedin(
state: &State,
conn: &Connection,
token: Option<String>,
token: &Option<String>,
uid: UserId,
msg: &PrivateRequest,
) -> Result<PrivateReply, zkerr::Error> {
Expand Down Expand Up @@ -351,8 +351,9 @@ pub async fn zk_interface_loggedin(
let jid = new_jobid(state, uid);
let lgb = state.girlboss.clone();
let server = state.server.clone();
let li = connect_and_make_lapin_info(state, token.clone()).await;
let li = connect_and_make_lapin_info(state, token).await;
let lapin_channelx = li.map(|li| li.channel).clone();
let token = token.clone();

std::thread::spawn(move || {
let rt = actix_rt::System::new();
Expand Down Expand Up @@ -410,7 +411,7 @@ pub async fn zk_interface_loggedin(
jid,
server,
lapin_channelx,
token,
token.clone(),
));
rt.run()
.map_err(|e| {
Expand Down
Loading