Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Using JSURL for data serialization in links #329

Merged
merged 1 commit into from
Apr 5, 2020

Conversation

dkozar
Copy link
Contributor

@dkozar dkozar commented Mar 31, 2020

Related issues and PRs

Description

Proposing alternative URL serialization (more read here: #326).

JSURL format: http://localhost:3000/?~(population~(ICUBeds~80~cases~%27CHE-Basel-Stadt~country~%27Switzerland~hospitalBeds~698~importsPerDay~0.1~populationServed~195000~suspectedCasesToday~10)~epidemiological~(infectiousPeriod~3~latencyTime~5~lengthHospitalStay~4~lengthICUStay~16~overflowSeverity~2~peakMonth~0~r0~2~seasonalForcing~0.2)~simulation~(simulationTimeRange~(tMax~1598918400000~tMin~1580428800000)~numberStochasticRuns~0)~containment~(~(y~1~t~1580428800000)~(y~1~t~1582483200000)~(y~0.6068708388814913~t~1584537600000)~(y~1~t~1586592000000)~(y~1~t~1588646400000)~(y~0.8250332889480693~t~1590700800000)~(y~1~t~1592755200000)~(y~0.5966444740346205~t~1594809600000)~(y~1~t~1596864000000)~(y~0.9170705725699069~t~1598918400000))~current~%27Custom)

Comparison of the old (URL encoded) and new (JSURL) format:

image

Note: There was an issue with Dates, because current application is passing dates to serializer. I'm suggesting to convert all the dates to Epoch before passing it to serializer.

Impacted Areas in the application

The app will continue to read the legacy URLs, however the newly created ones will be in the JSURL format.

Testing

This is a POC. I'm planning to write a thorough unit tests. There is a problem with current unit tests - it seems that a lot of tests are failing (in master branch).

image

@vercel
Copy link

vercel bot commented Mar 31, 2020

This pull request is being automatically deployed with ZEIT Now (learn more).
To see the status of your deployment, click below or on the icon next to each commit.

🔍 Inspect: https://zeit.co/covid19-scenarios/covid19-scenarios/q549sg6w3
✅ Preview: https://covid19-scenarios-git-fork-dkozar-feat-jsurl.covid19-scenarios.now.sh

@dkozar
Copy link
Contributor Author

dkozar commented Apr 1, 2020

I fixed the browser freezing problem and wrote unit tests around the de/serialization:

image

@dkozar
Copy link
Contributor Author

dkozar commented Apr 1, 2020

This is now ready for a merge. Are we going for the better URL encoding? 😄

@dkozar dkozar mentioned this pull request Apr 1, 2020
Comment on lines 3 to 39
const serialize = (params: AllParams): string => {
return encodeURIComponent(JSON.stringify(params))
}

const deserialize = (queryString: string): AllParams => {
try {
const obj = JSON.parse(decodeURIComponent(queryString))

const simulationTimeRangeOriginal = obj.simulation.simulationTimeRange
const simulationTimeRangeConverted = {
tMin: new Date(simulationTimeRangeOriginal.tMin),
tMax: new Date(simulationTimeRangeOriginal.tMax),
}

// NOTE: Error in original parser. It should be: obj.containment
const containmentOriginal = obj.containment
const containmentConverted = {
...containmentOriginal,
// NOTE: Error in original parser. It should be: containmentOriginal.reduction.map
reduction: containmentOriginal.map((c: { t: number; y: number }) => ({
y: c.y,
t: new Date(c.t),
})),
}

return {
...obj,
containment: containmentConverted,
simulation: {
...obj.simulation,
simulationTimeRange: simulationTimeRangeConverted,
},
}
} catch (error) {
throw new Error('encodeURIComponent: Error while parsing URL')
}
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do you think it would be possible to merge these serialize/deserialize functions and the serialize/deserialize functions in jsUrl.ts into a single deserialize function which accepts a parse function and a single serialize function which accepts a stringify function? I see that you have extra logic in the jsUrl serialize function to convert Date objects to numbers but I think that is the only difference? This probably isn't that big of deal as once I merged in my io-ts changes it will make serialization/deserialization much simpler.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, we can massage it further afterwards. Currently there are 2 pairs of serializers because of the backward compatibility. Once we use only JSURL, this will be even simpler.

Dates are problematic, that’s why I would suggest to use timestamps starting from the DTO level.

@nnoll
Copy link
Collaborator

nnoll commented Apr 3, 2020

I fear we have a bit of duplicated work going on with respect to this feature. Specifically, how does this square with PR #338? If these are both solving the same problem, we should begin coordinating resources.

@dkozar
Copy link
Contributor Author

dkozar commented Apr 3, 2020

@nnoll they are not solving the same issue. Mine is solving the serialization into a string that is appended to the URL. Theirs is solving the problem one level above, and that is making the types used in the object to serialize more robust.

There are conflicts, but that doesn’t mean they solve the same thing.

Second one will obviously need to rebase.

@ivan-aksamentov
Copy link
Member

ivan-aksamentov commented Apr 3, 2020

@dkozar Hi Danko! This is an interesting feature. Not sure if we really need this, but it is visually appealing, definitely. For example when sharing via email.

Our users are non-technical mostly. Maybe they'd prefer a shorter links (compression)? I don't know.

For sure, links should be shareable on social media (is there a length limitation there?)

I will do something else with URLs right now #283, because this is top priority before a release in a few days. But we will definitely come back to the link format.

@dkozar
Copy link
Contributor Author

dkozar commented Apr 3, 2020

@dkozar Hi Danko! This is an interesting feature. Not sure if we really need this, but it is visually appealing, definitely. For example when sharing via email.

Our users are non-technical mostly. Maybe they'd prefer a shorter links (compression)? I don't know.

Hey,

JSURL gives you the balance between compression and insight what's in the data (it's human-readable).

For sure, links should be shareable on social media (is there a length limitation there?)

Probably there is some limit.

I will do something else with URLs right now #283, because this is top priority before a release in a few days. But we will definitely come back to the link format.

Sure. Hopefully this will sort of some parts of our URL serialization, which seems very messy right now and hard to follow.

I created a PR to address this, please tell me what you think: https://github.com/neherlab/covid19_scenarios/pull/387/files

Maybe we could use parts of this PR.

Note: This PR just improves the data flow and separates concerns (to the best of my knowledge/professional experience). It also introduces some unit tests.

@dkozar
Copy link
Contributor Author

dkozar commented Apr 3, 2020

@ivan-aksamentov I just pulled the latest from upstream/master and it seems the de/serialization is commented out, why is that? Currently the application doesn't persist anything in the URL.

@ivan-aksamentov
Copy link
Member

@dkozar sorry, master is a bit broken now, someone have merged something wrongly.

@ivan-aksamentov
Copy link
Member

@dkozar Can you please send your email on Spectrum, we will invite you to our Slack?
https://spectrum.chat/users/ivan-aksamentov
It's faster to talk there

@dkozar
Copy link
Contributor Author

dkozar commented Apr 5, 2020

OK here we go.

Please note that there are some issues related to strings sometimes being received from the backend (?) instead of dates.

image

This has a tendency to break the app and should be fixed at the source ASAP:

image

In order for it to work, I've wrapped some calls to Date.getTime() with try..catch. Once we mitigate the root cause, those helper functions could be removed.

As far as I manually tested, persistance works as expected. There are issues with some pieces of a form (like Mitigation section), but thee doesn't seem to be related to serialization. Also, there is the 1 second debouncing issue that currently exists because of the form problem.

Although the PR seems extensive, the crux is here:

Snag_50980424

So from now on, JSURL serialiser is being used.

Note that this PR doesn't cover introduction of URL version.

Currently the URL is like:

/?datablob

In later PR I'll address this so we'll have:

/?d=datablob&v=1

Unit tests are working corrrectly:

image

PS. Note that, in the future, if you want to change the data that will be persisted in the URL, you have to change only the DtoConverter.ts file. This is the single file dealing with rearranging the object and replacing dates with Epoch.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants