-
Notifications
You must be signed in to change notification settings - Fork 15
Implement MKTG-032 in DocsSidenav and DocsPage #154
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
Conversation
|
This pull request is being automatically deployed with Vercel (learn more). π Inspect: https://vercel.com/hashicorp/react-components/GbPq6XqvzMzNP2dbwrEXYAkYhK8V |
| @@ -0,0 +1,15 @@ | |||
| const fetch = require('isomorphic-unfetch') | |||
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.
This stuff (remote file fetching from GH) seems kind of specific to the packer registry implementation. π I'm wondering if it makes sense to include the remote file fetching in this package. What do you think?
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.
Great point - have moved this out into the Packer repo π
| @@ -0,0 +1,237 @@ | |||
| @custom-media --mobile-viewports (max-width: 939px); | |||
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.
TIL!
8b0d741 to
813dfae
Compare
|
@jescalan @brkalow welp, not exactly "this afternoon", apologies for the delay - I do feel like the extra time paid off in making things a bit more ship-shape. Have also proven out the Here are the current pre-releases: Let me know if there's any part of the PR I can add more detail on.
|
| const handleMenuTransitionEnd = useCallback(() => { | ||
| setIsMenuFullyHidden(!isMobileOpen) | ||
| }, [isMobileOpen, setIsMenuFullyHidden]) | ||
| useEventListener('transitionend', handleMenuTransitionEnd, menuRef.current) |
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.
Had some fun trying to get the menu hide / show working as expected from both a visual and screen-reader standpoint. I think this approach works, and hopefully it doesn't feel too wild - I may have gone a bit overboard with the comments here.
| // we want to close the mobile rather than keep it open | ||
| useEffect(() => { | ||
| setIsMobileOpen(false) | ||
| }, [pathname]) |
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.
This fixes an issue where the mobile menu didn't close on client-side navigation - shoutout to @brkalow for suggesting this solution π
| content={filteredContent || []} | ||
| currentPath={currentPath} | ||
| Link={Link} | ||
| /> |
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.
I've changed from a function here to a component, it just felt a little clearer when trying to map how the rendering plays out to how the nav-data is structured in terms of branch and leave nodes. The way things work is still really similar with the recursive rendering etc.
brkalow
left a comment
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.
Really appreciate the improvements and enhancements you made as part of this. The implementation looks solid. Great tests!
Way to leave it better than you found it β€οΈ
| order, | ||
| pagePath, | ||
| navData, | ||
| currentPath, |
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.
Love the clarity!
| mainBranch = 'main', | ||
| order, | ||
| pagePath, | ||
| navData, |
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.
π―
| navData, | ||
| currentPath, | ||
| pageTitle, | ||
| baseRoute, |
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.
I think baseRoute makes sense. I'll keep this in mind as I'm using the supbath terminology throughout the versioned docs work.
| } | ||
| }) | ||
|
|
||
| describe('<DocsPage />', () => { |
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.
Amazing work!
| // If it's not a landing page, then we search | ||
| // through our navData to find the node with a path | ||
| // that matches the pathArray we're looking for. | ||
| function flattenRoutes(nodes) { | ||
| return nodes.reduce((acc, n) => { | ||
| if (!n.routes) return acc.concat(n) | ||
| return acc.concat(flattenRoutes(n.routes)) | ||
| }, []) | ||
| } | ||
| const allNodes = flattenRoutes(navData) |
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.
Potentially a future optimization, but we might consider moving this function to the top level and memoizing it so we only flatten the nav nodes once. I don't think we need to do it right away though!
| @@ -0,0 +1,206 @@ | |||
| #! /usr/bin/env node | |||
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.
This is great! We'll definitely need this for versioned docs transformation. I wonder where this should live with that in mind π€
See here for how I'm tentatively thinking of structuring transforms: https://github.com/hashicorp/mktg-versioned-docs/tree/main/src/transforms
| pageTitle="Glossary" | ||
| product={{ name: product.name, slug: product.slug }} | ||
| subpath="docs" | ||
| baseRoute="docs" |
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.
Not used anywhere, yet. π
Co-authored-by: Bryce Kalow <bkalow@hashicorp.com>
jescalan
left a comment
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.
This is a crazy amount of work - very impressive. Thanks for taking this on!
packages/docs-page/index.test.js
Outdated
| expect(document.title).toBe(`Test Page | Terraform by HashiCorp`) | ||
| // Confirm `baseRoute` and `navData` by checking for a rendered link | ||
| const activeLeaf = screen.getByText('AWS').parentNode | ||
| expect(activeLeaf.nodeName).toBe('A') |
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.
This is a dangerous reliance on html structure here - is there any way we can put a test id directly on the targeted element and select into that
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.
@jescalan ack yeah good point... i was on the fence here since getByText felt right, but parentNode felt wrong.
I've updated to use screen.getByText('AWS').closest('a'), and then changed the assertion to ensure the href on the a tag is correct. Have made similar updates throughout docs-page and docs-sidenav tests π
packages/docs-page/index.test.js
Outdated
| const contentParagraph = screen.getByText('This is a cool docs page!') | ||
| expect(contentParagraph.tagName).toBe('P') | ||
| // Confirm `product` is passed via class | ||
| const contentContainer = contentParagraph.parentNode.parentNode |
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.
Same here with the DOM traversal, I think this is something we want to try to avoid in tests if we can
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.
Updated - now grabbing the .closest('article'). Test might break if content no longer renders an article, but at least less brittle than the current specificity π
| const jumpToSectionElem = screen.getByText('Jump to Section') | ||
| expect(jumpToSectionElem.tagName).toBe('SPAN') | ||
| }) | ||
| }) |
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.
ππΌ
| // docs catchall route parameters: route/[[...page]].jsx. | ||
| // This default parameter ID captures that pattern. | ||
| // It can be overridden via options. | ||
| const DEFAULT_PARAM_ID = 'page' |
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.
ππΌ
| @@ -0,0 +1,206 @@ | |||
| #! /usr/bin/env node | |||
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.
I wonder that as well - maybe in the codemods repo?
| --- | ||
|
|
||
| This is a cool component for documentation | ||
| DocsSidenav renders a tree of links, with the option to include nested sections. Horizontal dividers can also be included between items. |
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.
π you didn't like my original description?
d219a3f to
8d8092c
Compare
ποΈ Asana Task
π Preview Link
This PR refactors DocsSidenav to implement the related RFC, MKTG-032.
This change also bleeds into
DocsPage, which has a significant refactor to align with the updatedDocsSidenavAPI, andGlossaryPage, which is a less drastic but still breaking refactor to align with `DocsPage.I've proven out these changes in hashicorp/packer#10656 and more recently hashicorp/packer#10716, so apart from unit tests, we have those PRs as examples of the refactored components working "in the wild". We could open further PRs on other docs sites to confirm the
GlossaryPagecompatibility, or rather the upgrade path.Release Information
Please select one (required)
Release Notes (required)
This release refactors `docs-sidenav`, `docs-page`, and `glossary-page` to implement [the MKTG-032 RFC](https://docs.google.com/document/d/1FPyWid2NmNI9E_6lH2UIMuEPqjqDCGe3F8wraPRQHQ8/edit#).PR Checklist π
Items in this checklist may not may not apply to your PR, but please consider each item carefully.