Skip to content

Conversation

jonkafton
Copy link
Contributor

@jonkafton jonkafton commented Sep 19, 2025

What are the relevant tickets?

Closes https://github.com/mitodl/hq/issues/8616

Description (What does it do?)

Adds a share button and popover from the designs in Figma.

Adds Open Graph metadata for social media previews:

  • Title: "Joe Learner's Module Certificate | MIT Learn"
  • Description: "Joe Learner has successfully completed the Universal Artificial Intelligence Module Certificate: The Course Name"

Screenshots (if appropriate):

image image

How can this be tested?

Hopefully you have mitxonline running locally with a certificate set up (otherwise please message me for a run through).

  • Load the certificate page at http://open.odl.local:8062/certificate/{"course"|"program"}/{uuid}
  • Hit the "Share" button.
  • Check that the popover matches the designs in Figma.
  • Check that the mobile layout looks reasonable (we don't have a mobile design cc. @steven-hatch).
  • Check that the popover closes when clicked outside.
  • Check that the textbox selects url content when clicked and is copyable.
  • Check that the "Copy Link" button updates to "Copied!"
    • navigator.clipboard is only available in secure contexts, not HTTP, so locally this fails silently.
  • Check that the social media buttons link to the respective share URLs.
  • Check the Open Graph metadata is correctly set in the header (og:title and og:description).
image

@jonkafton jonkafton marked this pull request as draft September 19, 2025 16:21
@jonkafton jonkafton added the Needs Review An open Pull Request that is ready for review label Sep 20, 2025
@jonkafton jonkafton marked this pull request as ready for review September 20, 2025 08:56
<Page>
<SharePopover
open={shareOpen}
title={`${title} Certificate - MIT Open Learning`}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

close enough, but I like this a bit better:

Suggested change
title={`${title} Certificate - MIT Open Learning`}
title={`${title} Certificate issued by MIT Open Learning`}


return standardizeMetadata({
title: `${userName}'s ${displayType}`,
description: `${userName} has successfully completed the Universal Artificial Intelligence ${displayType}: ${title}`,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you give me an example of how this renders?

We have to be careful about hard-coding "Universal Artificial Intelligence" because this won't stay forever. In a case like this, which isn't very visible, I would just drop "Universal Artificial Intelligence" altogether for better future-compatibility.

Suggested change
description: `${userName} has successfully completed the Universal Artificial Intelligence ${displayType}: ${title}`,
description: `${userName} has successfully completed the ${displayType}: ${title}`,

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That currently looks like: "Joe Learner has successfully completed the Universal Artificial Intelligence Module Certificate: The Course Name".

With your suggested change: "Joe Learner has successfully completed the Module Certificate: The Course Name".

displayType is either "Module Certificate", "Series Certificate" or "MicroMasters® Certificate".

We do have "Universal Artificial Intelligence" hardcoded on the certificate text itself ("has successfully completed all requirements of the Universal Artificial Intelligence module").

Copy link
Contributor

@ChristopherChudzicki ChristopherChudzicki left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is working well! I actually got the clipboard copying to work locally on localhost:8062 ... Sometimes localhost doesn't work because of CORS, etc, but the browser doesn't actually need to make any requests with the prefetching.

A simple requested change... we should add some aria-labels to the social links.

Additionally, it would be good to add some tests for sharepopover, either a dedicated test file or in the certificate page test.

It would be nice if jsx-a11y linter caught the a11y issue above more reliably, but in lieu of that, I find these issues are usually pretty readily discovered when writing tests with getByRole, etc.

onClick={(event) => {
const input = event.currentTarget.querySelector("input")
if (!input) return
input.select()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nice touch :)

edge="circular"
variant="bordered"
startIcon={<RedLinkIcon />}
aria-label={copyText}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't need an explicit label, will use contents.

Copy link
Contributor

@ChristopherChudzicki ChristopherChudzicki left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Still need aria-labels on the links, plus some comments

Comment on lines 148 to 150
const facebookLink = document.querySelector(`a[href="${facebookHref}"]`)
const twitterLink = document.querySelector(`a[href="${twitterHref}"]`)
const linkedinLink = document.querySelector(`a[href="${linkedinHref}"]`)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think I failed to put this comment on a specific line or forgot to press submit, but :

we should add some aria-labels to the social links.

The social links right now just have icons w/o any accessible label.

Suggestion: Always try using getByRole(role, { name }) for selections like this. If it doesn't work / works awkwardly, it means we are missing some aria labels.

So:

  1. Add aria labels to the social links
  2. then getByRole("link", { name: "Share on Facebook"}) etc

Comment on lines 152 to 154
expect(facebookLink).toBeInTheDocument()
expect(twitterLink).toBeInTheDocument()
expect(linkedinLink).toBeInTheDocument()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Once you use getByRole, this will be redundant (it checks for in do + visible + not disabled, etc).

Comment on lines 164 to 167
const socialLinks = document.querySelectorAll("a")
socialLinks.forEach((link) => {
expect(link).toHaveAttribute("target", "_blank")
})
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  • Request: use getAllByRoleLink("link")
  • Suggest adding an assertion about the expected number of links
    • _Note: As currently written, this would pass if there were 0 links (though I'm sure some other test would fail). With getAllByRole, it will fail if there are 0 links, requires at least 1+. Still worth adding an expected number of links, imo.

Comment on lines 173 to 174
const copyButton = screen.getByText("Copy Link")
fireEvent.click(copyButton)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
const copyButton = screen.getByText("Copy Link")
fireEvent.click(copyButton)
const copyButton = screen.getByRole("button", { name: "Copy Link" } )
user.click(copyButton) // from @testing-library/user-events

https://testing-library.com/docs/user-event/intro/#differences-from-fireevent

@jonkafton jonkafton merged commit 14e46c3 into main Sep 29, 2025
13 checks passed
@jonkafton jonkafton deleted the jk/certificate-share branch September 29, 2025 16:00
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Needs Review An open Pull Request that is ready for review
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants