adobe / aem-spa-project-archetype

Maven Archetype for creating new AEM SPA projects
Apache License 2.0
61 stars 32 forks source link

Add PWA features #98

Closed samuelmeuli closed 4 years ago

samuelmeuli commented 5 years ago
Q                       A
Fixed Issues? Closes #61, closes #83
Patch: Bug Fix? No
Minor: New Feature? No
Major: Breaking Change? Yes
Tests Added + Pass? Yes
Documentation Provided Yes
Any Dependency Changes? Yes
License Apache License, Version 2.0

This PR configures the archetype to generate projects with features of a Progressive Web App.

The features can be tested using Lighthouse. All checks should pass with this setup.

Note: Currently, all files are served by AEM with a Service-Worker-Allowed header. This will be improved in a future PR using a Servlet Filter (so only service worker files are served with that header).

godanny86 commented 4 years ago

@samuelmeuli , @pfauchere after a little digging I feel strongly that we should not bootstrap projects with the react-app-rewired. Looking at the Readme for the react-app-rewired it appears there is limited support and it falls outside of "official" recommendations by React/facebook. This, of course, is fine for many customers but they need to understand the risks ahead of time. Since all SPA editor projects should start from the archetype this seems like a dangerous path to send customers down by default.

I'd prefer to stick as close to: https://create-react-app.dev/docs/making-a-progressive-web-app as possible. Forgive me @samuelmeuli, remind me again what functionality the rewired-app provides that we needed? Maybe we can solve some of this at the Dispatcher/Apache level for things like loading the Service Worker at the root of the site? If there are some features of PWA that require the app to either be ejected and/or use react-app-rewired then maybe we can document these steps instead of forcing customers to not use CRA?

samuelmeuli commented 4 years ago

@godanny86 I agree that using react-scripts-rewired is not ideal, but in my opinion it's one of the cleaner approaches.

The main problems that need to be solved are the following:

Possible solutions we've identified:

  1. Generating a custom service worker with Workbox after building the app using CRA and removing the undesired generated files. Environment variables could be replaced with a script which runs after the build. This approach isn't very clean or easy to understand, but avoids modifications to the CRA Webpack config. I initially implemented this and can send you the code if you like.

  2. [Current approach] Using react-scripts-rewired and customize-cra to edit CRA's Webpack configuration. This avoids any additional build steps and is easy to understand, but – as you mentioned – might cause maintainability issues.

  3. Forking CRA and editing the Webpack config. Will lead to higher maintenance effort, but might be the cleanest solution for users.

  4. Ejecting CRA and editing the Webpack config. That way, we would miss out on future features/fixes of CRA.

  5. Dropping CRA and using a custom Webpack config. Also easy to understand for users, but this requires them to extend the Webpack config if they need additional features (which might otherwise be part of CRA).

The situation for Angular is pretty much the same. The service worker and manifest files generated using angular-cli are not sufficient for our use case, and @angular-builders/custom-webpack also allows us to modify the default Webpack configuration. Therefore, most of the custom Webpack config from React can be applied to the Angular app as well.

My preferred approach would be 3, and possibly 2 and 5. @godanny86, please let me know what you think or if you have any other ideas :)

cc @pfauchere

godanny86 commented 4 years ago

hi @samuelmeuli, thank you for the detailed response! The complexity of this problem is not lost on me and you have explored many different solutions. My point is that the archetype should be a starting point to accelerate a customer project but not at the cost of choosing an implementation path. To your point, there seems to be several approaches for implementing a PWA and without a definitive consensus, I think we should let projects choose the most appropriate path based on their app requirements.

My approach would be to continue to provide as basic of a project as possible and add as many PWA features that we can. If some advanced configurations like complete off-line functionality, advanced caching, and code-splitting cannot be achieved then so be it. We can still provide samples and recommendations on how to achieve these advanced configurations and let projects decide how to implement them. At least we are moving projects closer to PWA and in the future, if it turns out most customers want/need those advanced configurations we can make a determination then...