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

Render navbar at compile time using a template #1054

Closed
ang-zeyu opened this issue Feb 25, 2020 · 9 comments
Closed

Render navbar at compile time using a template #1054

ang-zeyu opened this issue Feb 25, 2020 · 9 comments
Labels
a-ReaderUsability s.UnderDiscussion The team will evaluate this issue to decide whether it is worth adding

Comments

@ang-zeyu
Copy link
Contributor

ang-zeyu commented Feb 25, 2020

Is your request related to a problem?

The most visible sign of FOUC is the flashing navbar, even with the temporary styles applied to them.

Describe the solution you'd like

We could remove the navbar component from vue-strap and instead adapt the template over to /markbind and render it at compile time.

  • This should eliminate the flashing navbar entirely, without sacrificing the usability of it.
    • Other components placed within the navbar would still need vue-strap to render correctly ( e.g. badges ), but the main structure and style of the navbar would be pre-rendered otherwise
  • We could also remove the temporaryStyle implementations, which should result in a cleaner codebase

Describe alternatives you've considered

1)Introduce more specific ( to the color of the nav bar ) temporary styles. While it is a good temporary fix, it cannot eliminate FOUC completely as there is still reliance on vue-strap to render the dom structure of the navbar

  • The navbar is often the first thing that readers notice when loading the page, and it would be nice to have it stay completely "constant" across page loads / reloads to be less disruptive.

2)Explore introducing vue SSR to this project to eliminate FOUC for every page after vue-strap is moved over. Problems:

  • The initial vue bundle served to the client as rendered by markbind has to be built for every page, which may significantly impact build times.
    • That said, this may be the better long term and more widely applicable solution to FOUC, and we can disable SSR when running markbind serve and only have it active during markbind build
  • Still, this is a really big change, which can really take some time to discuss and flesh out, leaving the navbar as is in the meantime. Hence, we could still use the above approach as a full solution first and explore SSR in the future if need be.

Additional context

na

@ang-zeyu ang-zeyu changed the title Render navbar at compile time using a template and enhance mobile view navigation Render navbar at compile time using a template and Enhance mobile view navigation Feb 25, 2020
@ang-zeyu ang-zeyu changed the title Render navbar at compile time using a template and Enhance mobile view navigation Render navbar at compile time using a template & Enhance mobile view navigation Feb 25, 2020
@openorclose
Copy link
Contributor

I've experimented with the vue prerendering part here:

https://github.com/openorclose/markbind/tree/prerender

It only prerenders on markbind build, and only prerenders index for now.

So you do markbind build, go inside _site and open up index.html to get the prerendered version.

The styles are there just fine:

image

But the problem is that we are unable to put vue back in after prerendering.

What prerendering allows you to do is:

(e.g. <tooltip content="123">tooltip</tooltip>)

When you build the files, a headless browser will run the Vue and convert the tooltip into <span>s and then save it to a html file.

However, to make this html file interactive, you still need the original vue code <tooltip content="123">tooltip</tooltip>in the final output. What vue does is compare the diff between the html already there and its regenerated virtual dom.

This means that we would need to double the size of our served HTML, since we would serve the prerendered data AND the original unrendered data.

@openorclose
Copy link
Contributor

A potential direction we could explore:

Try to make as many vue-strap components as we can "static" (like Pic and Thumb already are). Static in that there is no user interaction with them.

Then we can try to find a way to only prerender these components and reduce FOUC this way.


An even more drastic alternative (but would probably solve FOUC altogether) would be to remove our dependency on Vue altogether and do it old-style, manually generating the HTML and adding in event listeners after page load.

@ang-zeyu
Copy link
Contributor Author

ang-zeyu commented Feb 26, 2020

After server rendering it, the client takes over the html and does client side hydration.
No "two htmls" are required

But the problem is that we are unable to put vue back in after prerendering.

The server would send a modified vue bundle to the client that contains the "initial state" of the application.
It's still a very drastic step that needs time to flesh out otherwise though, which I don't think we should attempt at the moment

A potential direction we could explore:

We could test out how effective functional components are as an alternative after MarkBind/vue-strap#130 and #981, which also improves performance for stateless components.
Prerendering certain components would likely be more complicated than performing SSR on the entire file

@openorclose
Copy link
Contributor

After server rendering it, the client takes over the html and does client side hydration.
No "two htmls" are required

But the problem is that we are unable to put vue back in after prerendering.

The server would send a modified vue bundle to the client that contains the "initial state" of the application.
It's still a very drastic step that needs time to flesh out otherwise though, which I don't think we should attempt at the moment

Yup, this modified vue bundle would be the one containing the original vue source for normal uses. The point is, Vue can't just look at the prerendered HTML and know what to do. A lot of information is lost such as event handlers and other data not inside the HTML.

For example, the prerendered tooltip would look like

<span><span style="border-bottom: 1px dashed;">tooltip</span></span>

The rendered HTML doesn't contain the content of the tooltip at all.

@openorclose
Copy link
Contributor

We could test out how effective functional components are as an alternative after MarkBind/vue-strap#130 and #981, which also improves performance for stateless components.

Yup, agreed with this

@ang-zeyu
Copy link
Contributor Author

ang-zeyu commented Feb 26, 2020

The rendered HTML doesn't contain the content of the tooltip at all.

One of the main upsides of SSR is exactly to defer the costs of client side rendering with front end frameworks, while keeping the full feature set of such frameworks, which is essential for how most websites are single page applications nowadays.

The downside in a typical backend would be a delay in server response time as the server has to render the page, but depending on the use case, it may lead to a faster TTI for the client, especially on mobile devices with not as much computing power.
In markbind, that would be the build times during markbind build.

From the vue docs:

Hydration refers to the client-side process during which Vue takes over the static HTML sent by the server and turns it into dynamic DOM that can react to client-side data changes.

@ang-zeyu ang-zeyu added the s.UnderDiscussion The team will evaluate this issue to decide whether it is worth adding label Feb 29, 2020
@ang-zeyu ang-zeyu changed the title Render navbar at compile time using a template & Enhance mobile view navigation Render navbar at compile time using a template Mar 11, 2020
@ang-zeyu
Copy link
Contributor Author

Removed the mobile view navigation part of the issue ( duplicate of #980 )

@ang-zeyu
Copy link
Contributor Author

Opinions needed @acjh @marvinchin
Should this be done, or postponed till we implement vue SSR? ( if it's a thing, but many, many things need to be resolved for this )

I'm thinking of attempting #980 at the same time as well, effectively "stuffing" the site-nav into the navbar, but with mobile view formatting.

@ang-zeyu
Copy link
Contributor Author

closing in favour of SSR first. We can reconsider if even with SSR fouc is still noticeable.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
a-ReaderUsability s.UnderDiscussion The team will evaluate this issue to decide whether it is worth adding
Projects
None yet
Development

No branches or pull requests

2 participants