Enable safe recursion in VaultUpdate type

pull/33/head
Bram 2024-07-15 15:50:32 +02:00
parent a95fbbb856
commit d7a7fa385c
3 changed files with 116 additions and 59 deletions

View File

@ -56,6 +56,8 @@ import Internal.Tools.Json as Json
import Internal.Tools.Timestamp exposing (Timestamp) import Internal.Tools.Timestamp exposing (Timestamp)
import Internal.Values.Context as Context exposing (AccessToken, Context, Versions) import Internal.Values.Context as Context exposing (AccessToken, Context, Versions)
import Internal.Values.Settings as Settings import Internal.Values.Settings as Settings
import Recursion
import Recursion.Fold
{-| There are lots of different data types in the Elm SDK, and many of them {-| There are lots of different data types in the Elm SDK, and many of them
@ -292,47 +294,85 @@ toMaybe data =
{-| Updates the Envelope with a given EnvelopeUpdate value. {-| Updates the Envelope with a given EnvelopeUpdate value.
-} -}
update : (au -> a -> a) -> EnvelopeUpdate au -> Envelope a -> Envelope a update : (au -> a -> a) -> EnvelopeUpdate au -> Envelope a -> Envelope a
update updateContent eu ({ context } as data) = update updateContent eu startData =
case eu of Recursion.runRecursion
ContentUpdate v -> (\updt ->
{ data | content = updateContent v data.content } case updt of
ContentUpdate v ->
Recursion.base
(\data ->
{ data | content = updateContent v data.content }
)
HttpRequest _ -> HttpRequest _ ->
data Recursion.base identity
More items -> More items ->
List.foldl (update updateContent) data items Recursion.Fold.foldList (<<) identity items
Optional (Just u) -> Optional (Just u) ->
update updateContent u data Recursion.recurse u
Optional Nothing -> Optional Nothing ->
data Recursion.base identity
RemoveAccessToken token -> RemoveAccessToken token ->
{ data | context = { context | accessTokens = Hashdict.removeKey token context.accessTokens } } Recursion.base
(\({context} as data) ->
{ data
| context =
{ context
| accessTokens =
Hashdict.removeKey token context.accessTokens
}
}
)
RemovePasswordIfNecessary -> RemovePasswordIfNecessary ->
if data.settings.removePasswordOnLogin then Recursion.base
{ data | context = { context | password = Nothing } } (\({context} as data) ->
if data.settings.removePasswordOnLogin then
{ data | context = { context | password = Nothing } }
else else
data data
)
SetAccessToken a -> SetAccessToken a ->
{ data | context = { context | accessTokens = Hashdict.insert a context.accessTokens } } Recursion.base
(\({context} as data) ->
{ data | context = { context | accessTokens = Hashdict.insert a context.accessTokens } }
)
SetBaseUrl b -> SetBaseUrl b ->
{ data | context = { context | baseUrl = Just b } } Recursion.base
(\({ context } as data) ->
{ data | context = { context | baseUrl = Just b } }
)
SetDeviceId d -> SetDeviceId d ->
{ data | context = { context | deviceId = Just d } } Recursion.base
(\({ context } as data) ->
{ data | context = { context | deviceId = Just d } }
)
SetNow n -> SetNow n ->
{ data | context = { context | now = Just n } } Recursion.base
(\({ context } as data) ->
{ data | context = { context | now = Just n } }
)
SetRefreshToken r -> SetRefreshToken r ->
{ data | context = { context | refreshToken = Just r } } Recursion.base
(\({ context } as data) ->
{ data | context = { context | refreshToken = Just r } }
)
SetVersions vs -> SetVersions vs ->
{ data | context = { context | versions = Just vs } } Recursion.base
(\({ context } as data) ->
{ data | context = { context | versions = Just vs } }
)
)
eu
startData

View File

@ -58,6 +58,8 @@ import Internal.Values.StateManager as StateManager exposing (StateManager)
import Internal.Values.Timeline as Timeline exposing (Timeline) import Internal.Values.Timeline as Timeline exposing (Timeline)
import Internal.Values.User exposing (User) import Internal.Values.User exposing (User)
import Json.Encode as E import Json.Encode as E
import Recursion
import Recursion.Fold
{-| The Batch is a group of new events from somewhere in the timeline. {-| The Batch is a group of new events from somewhere in the timeline.
@ -246,21 +248,26 @@ setAccountData key value room =
{-| Update the Room based on given instructions. {-| Update the Room based on given instructions.
-} -}
update : RoomUpdate -> Room -> Room update : RoomUpdate -> Room -> Room
update ru room = update roomUpdate startRoom =
case ru of Recursion.runRecursion
AddEvent _ -> (\ru ->
-- TODO: Add event case ru of
room AddEvent _ ->
-- TODO: Add event
Recursion.base identity
AddSync batch -> AddSync batch ->
addSync batch room Recursion.base (addSync batch)
Invite _ -> Invite _ ->
-- TODO: Invite user -- TODO: Invite user
room Recursion.base identity
More items -> More items ->
List.foldl update room items Recursion.Fold.foldList (<<) identity items
SetAccountData key value -> SetAccountData key value ->
setAccountData key value room Recursion.base (setAccountData key value)
)
roomUpdate
startRoom

View File

@ -38,6 +38,8 @@ import Internal.Tools.Hashdict as Hashdict exposing (Hashdict)
import Internal.Tools.Json as Json import Internal.Tools.Json as Json
import Internal.Values.Room as Room exposing (Room) import Internal.Values.Room as Room exposing (Room)
import Internal.Values.User as User exposing (User) import Internal.Values.User as User exposing (User)
import Recursion
import Recursion.Fold
{-| This is the Vault type. {-| This is the Vault type.
@ -139,21 +141,29 @@ updateRoom roomId f vault =
{-| Update the Vault using a VaultUpdate type. {-| Update the Vault using a VaultUpdate type.
-} -}
update : VaultUpdate -> Vault -> Vault update : VaultUpdate -> Vault -> Vault
update vu vault = update vaultUpdate startVault =
case vu of Recursion.runRecursion
CreateRoomIfNotExists roomId -> (\vu ->
updateRoom roomId case vu of
(Maybe.withDefault (Room.init roomId) >> Maybe.Just) CreateRoomIfNotExists roomId ->
vault (Maybe.withDefault (Room.init roomId) >> Maybe.Just)
|> updateRoom roomId
|> Recursion.base
MapRoom roomId ru -> MapRoom roomId ru ->
mapRoom roomId (Room.update ru) vault Recursion.base (mapRoom roomId (Room.update ru))
More items -> More items ->
List.foldl update vault items Recursion.Fold.foldList (<<) identity items
SetAccountData key value -> SetAccountData key value ->
setAccountData key value vault Recursion.base (setAccountData key value)
SetUser user -> SetUser user ->
{ vault | user = Just user } Recursion.base
(\vault ->
{ vault | user = Just user }
)
)
vaultUpdate
startVault