Created
February 21, 2020 17:01
-
-
Save painedpineapple/3c91830e75b708a6c78ce414e8ddef8f to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** Dependencies | |
* @glennsl/bs-json: Encoding Data | |
* bs-decode: Decoding Data | |
**/ | |
open Belt.Result; | |
[@bs.val] [@bs.scope "localStorage"] | |
external removeItem: string => unit = "removeItem"; | |
[@bs.val] [@bs.scope "localStorage"] | |
external getItem: string => Js.Nullable.t(string) = "getItem"; | |
[@bs.val] [@bs.scope "localStorage"] | |
external setItem: (string, string) => unit = "setItem"; | |
type itemWithExpiration('a) = { | |
expiresAt: float, | |
data: 'a, | |
}; | |
module Decoder = { | |
module D = Decode.AsResult.OfParseError; | |
let itemWithExpiration = (json, dataDecoder) => | |
D.Pipeline.( | |
succeed((expiresAt, data) => {expiresAt, data}) | |
->field("expiresAt", D.floatFromNumber, _) | |
->field("data", dataDecoder, _) | |
->run(json, _) | |
); | |
}; | |
module Encode = { | |
open Json; | |
let itemWithExpiration = (item, dataEncoder) => | |
Json.Encode.( | |
object_([ | |
("expiresAt", Encode.float(item.expiresAt)), | |
("data", dataEncoder(item.data)), | |
]) | |
); | |
}; | |
exception ItemWithExpirationJson(string); | |
let getItemWithExpiration = (storage_key, decoder) => | |
switch (getItem(storage_key)->Js.Nullable.toOption) { | |
| None => | |
None; | |
| Some(json) => | |
switch (json->Js.Json.parseExn->Decoder.itemWithExpiration(decoder)) { | |
| Ok(cache) => | |
if (DateFns.isBefore( | |
Js.Date.fromFloat(cache.expiresAt), | |
Js.Date.make(), | |
)) { | |
Some(cache.data); | |
} else { | |
None; | |
} | |
| Error(error) => | |
Js.log(Decode.ParseError.failureToDebugString(error)); | |
None; | |
}; | |
}; | |
let setItemWithExpiration = (storage_key, data, encoder) => | |
{expiresAt: DateFns.addDays(1., Js.Date.make())->Js.Date.getTime, data} | |
->Encode.itemWithExpiration(encoder) | |
->Js.Json.stringify | |
|> setItem(storage_key); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment