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

Implementing a Component System #27484

Closed
ItsJonQ opened this issue Dec 3, 2020 · 8 comments
Closed

Implementing a Component System #27484

ItsJonQ opened this issue Dec 3, 2020 · 8 comments
Assignees
Labels
[Feature] Design Tools Tools that impact the appearance of blocks both to expand the number of tools and improve the experi [Feature] UI Components Impacts or related to the UI component system [Type] Overview Comprehensive, high level view of an area of focus often with multiple tracking issues

Comments

@ItsJonQ
Copy link

ItsJonQ commented Dec 3, 2020

This is a follow up to the Sidear Controls & Component System post/proposal.


🔗 Quick Links

Projects

Information

Code


📚 Back Story

Over the past couple of months, I've been focused on designing, architecting, and refining a Component System that could serve as the "next-generation" for our humble @wordpress/components library.

This project was a personal initiative that was inspired by my experience + passion in working in Design Systems/UI on my experiences with Gutenberg - specifically in the Design Tools/Global Styles space.

I had originally wrote about it in this post, "Advancing the Editor Interface"
#24341

When I started this project, I didn't know if it was going to be viable - although of course, that was my hope.
Over time, thanks to the interest, support, and collaboration of other folks, it turned out that we may have created something special and that this may actually have a shot!

🗺 Project Walkthrough + Integration ideas

This next-gen. Components project is a lot.
There's a lot of things happening and there's a lot of code.

For those who are interested, I've recorded a video (1 hour long) where I go into detail the important systems and mechanics that make up the entire project, as well as the ideas and plans I have for integrating it successfully into Gutenberg.

https://g2components.wordpress.com/2020/12/02/walkthrough-integration-ideas/

For those who'd like to know more (or see the history of ideas), I created a dedicated blog for this project.
https://g2components.wordpress.com/

(I try to update it at least once a week)

✌️ Gutenberg Integration (aka. "Phase 2")

"Phase 1" was preparing the project to be introduced into Gutenberg. That meant a lot of refactors and adding of essential features and enhancements. We (being @saramarcondes and myself) wrapped this up last week! (:tada:)

Here comes the fun part. Time to (finally) add the code into Gutenberg!

To coordinate this, I'll be creating a dedicated Project board along with issues to track the primary tasks for integration.

"Phase 2" could be thought of as 2 chunks:

  1. Bringing over the packages (aka. core systems) needed to power the Component layer
  2. Bringing over the Components

I've created a spreadsheet that indicates these tasks mapping to a schedule/timeline:
https://docs.google.com/spreadsheets/d/1gfzznyJtTr3hHoGkGRdeBRjhuZVMRalF9NuLrxkl4Nk/edit#gid=0

We can use this issue as the main top level issue to discuss and coordinate the various phases.


A big thanks to those who've been following along this journey!
As always, feedback is always welcome.

A lot of the core systems and mechanics were made (much) better thanks to feedback from you folks.

Examples including:

  • The creation of custom themes for the theming systems
  • Z-Index registration for the Style systems
  • Improvements to component/environment awareness in the Context systems
  • Component composition + state coordination
  • Super fast performance rendering
  • Improved color management in the Style system
  • And much much more!
@ItsJonQ ItsJonQ added [Feature] UI Components Impacts or related to the UI component system [Type] Overview Comprehensive, high level view of an area of focus often with multiple tracking issues [Feature] Design Tools Tools that impact the appearance of blocks both to expand the number of tools and improve the experi labels Dec 3, 2020
@ItsJonQ ItsJonQ self-assigned this Dec 3, 2020
@gziolo
Copy link
Member

gziolo commented Dec 4, 2020

First of all, I’d like to congratulate all the fantastic work done so far. Implementing a complete and cohesive Component System will benefit all developers and users interacting with WordPress. I’m totally on board with the idea, and I hope that those efforts will succeed.

I spent quite some time reading essential blog posts you shared, watching video recordings, playing with the Storybook demo, and trying to understand how all the moving parts fit together. There is a ton to process, which on one side is impressive, but at times it also overwhelming thus, it took me way too long to respond.

I appreciate that you took backward compatibility so seriously. Indeed, it’s super important in the context of the production software with such a strong emphasis to make everything working with the legacy APIs. I liked how you illustrated the proposed strategy with an analogy in https://g2components.wordpress.com/2020/11/02/the-path-to-integration/:

The best way I can illustrate this strategy is with an analogy.
Imagine if Gutenberg’s UI was a city. Within this city, there are various areas (like Gutenberg’s sidebar or top bar). Within these areas, there are many homes (like a Gutenberg Button UI).

The technical demo for integration you shared is excellent:
https://www.youtube.com/watch?v=jTNuJU1w-yA

In practice, it might be more challenging than it looks in your demo because of how 3rd party projects integrate with the block editor using the variety of SlotFill components and WordPress hooks applied to components. We will see pretty soon. I’m referring here to the prior experience we had with refactoring the button component and toolbars. In particular, the work that @diegohaz has done for toolbars can be a great learning experience in this context. The biggest challenge was how to fall back to the old behavior of the toolbar in case 3rd party extensions don’t use the latest API. It’s quite similar in many ways to what we can deal with here as well. However, the case with merging Button and IconButton is also quite relevant as it produced a few regressions in terms of how those components visually fit into various places (or it might be a consequence of G2 toolbar changes, @youknowriad might remember better). Related issues for reference:

@ItsJonQ
Copy link
Author

ItsJonQ commented Dec 4, 2020

@gziolo Thank you for your response! I'm glad you touched on SlotFill (and that you and @diegohaz have some expertise in it). The strategies I have for integration (ultimately) rely on React Context. I'm not sure if that presents any issues. Hopefully SlotFill doesn't do anything funky with Context? 🙏

@ItsJonQ
Copy link
Author

ItsJonQ commented Dec 4, 2020

I can't seem to get <SlotFill /> to work 😂 .
All I'm doing is I'm pasting the example code in a new create-react-app / CodeSandbox environment (nothing else):
https://developer.wordpress.org/block-editor/components/slot-fill/

Getting the hook error:

×
Error: Invalid hook call. Hooks can only be called inside of the body of a function component. This could happen for one of the following reasons:
1. You might have mismatching versions of React and the renderer (such as React DOM)
2. You might be breaking the Rules of Hooks
3. You might have more than one copy of React in the same app
See https://fb.me/react-invalid-hook-call for tips about how to debug and fix this problem.

🤷


Nevermind. I think it's React 17 vs 16

@gziolo
Copy link
Member

gziolo commented Dec 4, 2020

I wanted to refer to another aspect of this issue. The most valuable resource in this context is the Walkthrough + Integration Ideas post: https://g2components.wordpress.com/2020/12/02/walkthrough-integration-ideas/.

or, more importantly, the Project Walkthrough + Integration Ideas video:
https://www.youtube.com/watch?v=TlzRwSDeJJ4

Thank you for doing this! It helped me to get up to speed with the higher-level architecture. Honestly speaking, all this makes perfect sense as what you described in terms of technical aspects. I’m sure I’m also not best suited to comment on how Component System should be built, so I will leave the job of evaluating it to folks who are more knowledgable in that area.

However, I have a slightly different view in regards to the timeline shared:
https://docs.google.com/spreadsheets/d/1gfzznyJtTr3hHoGkGRdeBRjhuZVMRalF9NuLrxkl4Nk/edit#gid=0

Again, I appreciate all the work put into outlining it. It makes my job easier to comment on “Phase 2” of the proposed plan:

“Phase 2" could be thought of as 2 chunks:

  1. Bringing over the packages (aka. core systems) needed to power the Component layer
  2. Bringing over the Components

I know that you started on the first task, which is moving utils (https://www.npmjs.com/package/@wp-g2/utils) to Gutenberg as proposed in:
#27486

I studied some bits of the code already. My initial instinct is that we should try to avoid it for now (or even for this particular package indefinitely, more on that later in the PR) and focus immediately on point (2) – Bringing over the Components.

When investigating efforts, I stumbled upon this comment from @youknowriad (ItsJonQ/g2#75 (comment)):

I see, I think it seems there's value in these packages being separate (maybe not all, we'll have to see). The important thing is that they stay as "bundled modules" (like @wordpress/icons and @wordpress/interface right now) to avoid having them leak as public APIs in WordPress.

A new package is always a real challenge. As soon as we introduce it, there is maintenance cost because of the public API factor, documentation aspects, etc. Bundled modules are one way to mitigate that. However, we still publish those packages to npm under WordPress organization. Fortunately, those packages are already hosted on npm under the wp-g2 organization. My question is then whether we need to decide what packages are required and avoid (for now) all the burden of moving the code, reviewing it, testing, etc. Instead, can we consume them from npm until we are done with part 2 of Phase 2 – Bringing over the Components? :)

There are several benefits of changing the original plan this way. We can immediately play with existing components to see how using a new version of components (Button, etc.) enabled per context works in the WordPress environment. We avoid spending a significant amount of time discussing/reviewing new APIs (assuming people agree with individual APIs, which is very optimistic to say) taken out of the context. Besides, most of the @wordpress/components package consumers are merely an implementation detail. It’s also a way to have visible results first that folks expect the most from such a system, and they can play with a new API for the component.

Again, after @youknowriad:

for the components one (I guess the highest level one), I think we should avoid the temporary package and just use a folder in @wordpress/components to start with.

I echo that. It’s a way to ignore all the public API issues, leaking new docs to the integrated systems like developers portal (https://developer.wordpress.org/block-editor/). Also, we could put all the code behind the feature flag to iterate even faster. Could we consume https://www.npmjs.com/package/@wp-g2/components as well (less of importance, mostly curious)?

We use process.env.GUTENBERG_PHASE for code bundled only in the Gutenberg plugin but gets removed through the dead code elimination in the WordPress Core. It can be enabled in the package.json file:

"GUTENBERG_PHASE": 2

The webpack plugin configures it:
'process.env.GUTENBERG_PHASE': JSON.stringify(

This is how it is used in the codebase:
process.env.GUTENBERG_PHASE === 2

We could create something similar for this project, knowing that we consume 3rd party packages in the initial phase. The difference would be that you would have to enable this flag for developing purposes explicitly. It wouldn’t be exposed in the Gutenberg plugin for a start. We wouldn’t have to worry initially about the bundle sizes, performance, public API, backward compatibility, etc.

Concluding, I'm trying to show quite a different path to achieve the same goal that might help to focus on how components are used rather than how they are internally built.

@ItsJonQ
Copy link
Author

ItsJonQ commented Dec 7, 2020

@gziolo Thank you for your very detailed thoughts!

A new package is always a real challenge. As soon as we introduce it, there is maintenance cost because of the public API factor, documentation aspects, etc. Bundled modules are one way to mitigate that.

I agree! I'm excited that we may be able to try the bundled packages first.

Instead, can we consume them from npm until we are done with part 2 of Phase 2 – Bringing over the Components? :)

I'm 💯 on board with this. It'll help us test things out faster. The only unknowns aren't necessarily with how the packages work together, but rather, how they will integrate with the existing systems. From my initial tests, it all seemed to work well. But I guess we'll know for certain in due time!

Concluding, I'm trying to show quite a different path to achieve the same goal that might help to focus on how components are used rather than how they are internally built.

I love this 🙏

@ItsJonQ
Copy link
Author

ItsJonQ commented Dec 7, 2020

Update: omgomg ❤️

The next FontSizePicker rendered and working within Gutenberg 😍

Screen Capture on 2020-12-07 at 13-27-21

This is done with the adapter/context strategy.

@ItsJonQ
Copy link
Author

ItsJonQ commented Dec 12, 2020

Haiii! 👋

Hope you all are doing well! I just wanted to give a status update for the ongoing work.

I'm going to be offline for the holidays starting next week, so I won't be available to help with this effort until the beginning of next year.


📥 Integration

In the meantime, we're currently exploring using the @wp-g2 packages directly within Gutenberg rather than individually porting them over. This strategy, suggested by @gziolo , can help us test out important integration details much faster, while maintaining the same level of stability (👍 ).

The ongoing (currently draft) PR can be found here:
#27594

⏫ Publishing @wp-g2 packages

With the above integration strategy, the packages live outside the Gutenberg codebase. Instead, they are brought in via npm.

As we iterate and refine implementation details, updates may needed on the @wp-g2 side.

I've written some documentation on how others (not myself) may be able to publish @wp-g2 packages to npm for Gutenberg consumption:

https://github.com/ItsJonQ/g2/blob/master/docs/release.md

In order to publish, you must be a contributor on the project. While I'm away, @gziolo and @saramarcondes may be able to help with this (if needed).


Hope this helps! Have a wonderful, restful, and magical December everyone <3

@mirka
Copy link
Member

mirka commented May 23, 2022

Closing in favor of our currently active tracking issues. Thanks for all your work on this!

@mirka mirka closed this as completed May 23, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
[Feature] Design Tools Tools that impact the appearance of blocks both to expand the number of tools and improve the experi [Feature] UI Components Impacts or related to the UI component system [Type] Overview Comprehensive, high level view of an area of focus often with multiple tracking issues
Projects
No open projects
Development

No branches or pull requests

3 participants