-
-
Notifications
You must be signed in to change notification settings - Fork 8.5k
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(theme-classic): store selected tab in query string. #8225
Conversation
✅ [V2]
To edit notification comments on pull requests, go to your Netlify site settings. |
⚡️ Lighthouse report for the deploy preview of this PR
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks
Not good enough to merge as is.
Sync between groups is now broken: https://deploy-preview-8225--docusaurus-2.netlify.app/docs/markdown-features/tabs/#syncing-tab-choices
I'd rather not serialize as JSON.
I'd also prefer if we opt-in for querystring serialization instead of making it a default
What I'd do:
- provide
queryString: string | boolean
prop - false by default => no querystring
- true => use groupId as querystring param
- string => use value as querystring param
// When defaultValueProp is null, don't show a default tab | ||
const defaultValue = | ||
defaultValueProp === null | ||
? defaultValueProp | ||
: defaultValueProp ?? | ||
children.find((child) => child.props.default)?.props.value ?? | ||
children[0]!.props.value; | ||
if (defaultValue !== null && !values.some((a) => a.value === defaultValue)) { | ||
|
||
// Warn user about passing incorrect defaultValue as prop. | ||
if ( | ||
defaultValueProp !== null && | ||
defaultValueProp !== undefined && | ||
!values.some((a) => a.value === defaultValueProp) | ||
) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
can you explain the intent here? Not sure to understand
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Very similar to the prev check. However, this new one only throws in case of user-error. E.g. available tab keys are ke1
, key2
, key3
, but user supplies key4
. The goal is to notify user it's their fault that the tabs are not working properly.
The prev implementation would throw even if the error was on the Docusaurus (implementation) side as it checked the derived value instead of user supplied one.
For the hydration problem, I don't know exactly how we can solve it, but if would be really preferably if we didn't have that "hydration tab change" when React loads: This can be particularly disturbing in case tabs have different heights. If an anchor is provided in addition to qs tabs, it can also mess-up with the scroll position. Now this is likely not easy to solve so I won't block the PR if it can't be fixed, it can be handled later. |
Yes, the desired outcome is clear. The implementation is the question here since docusaurus uses SSG, not SSR. Curious about the solution though. @slorber I have added the desired react router APIs, but unfortunately these break unit tests as they are not renderable on the server. I wasn't able to find similar scenario (react router APIs within unit tests) throughout the codebase. Could you please give me some pointers? Thanks! |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, looks better but not yet good enough 🤪
packages/docusaurus-theme-classic/src/theme/Tabs/__tests__/index.test.tsx
Outdated
Show resolved
Hide resolved
Unfortunately that's exactly why it's not easy. There are tricks to work around this in SSG (see dark mode or ThemedImage). Don't worry, we'll eventually figure out later in another PR. |
No worries, it's expected to be an iterative process so that we are on the same page as for the required implementation direction :)
I see we are from different camps. Clean code is very subjective and although I don't agree with your opinions, I fully respect them and since you are the maintainer here, you have the upper hand ofc :D Refactored into more abstractions as requested. Let me know if that's enough or you would like me to split the custom hook into a separate file as well.
Interesting, so basically the solution here would be to render every possible value as default value (in case of tabs with 3 options, that would be 3 separate Tabs component instances) and then based on the query param (that we can get by running a render-blocking script prior to actual rendering) determine, which Tabs shall be hidden and which shall be shown, is that right? |
Hey! We are keen to use this feature for our documentation. Could you please confirm the release date? |
Did some refactoring, fixes and docs improvements => should be ready to review. Some things to review more carefully:
Please test the preview and let me know if you see anything weird |
Looks like it works as I want it to 👍 Will normally be in upcoming v2.3 |
Any word on when 2.3 becomes publicly available? |
soon, I just come back from holiday and have a hundred things to check first |
Co-authored-by: sebastienlorber <lorber.sebastien@gmail.com> Closes #7008
Pre-flight checklist
Implementation description
__noGroup__
constant key for tabs that do not belong to any group. Downsides:Let's use this PR as starting point for further discussion around UX/implementation.
Motivation
Allows for sharing tabs selection via URL - better UX.
Test Plan
Manual
Test links
Related issues/PRs
Closes #7008