Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/fix-footnote-long-url-wrapping.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@shopify/cli-kit': patch
---

Render banner/alert footnote URLs on a single contiguous line so long links are no longer broken by hard newlines and remain copy-pasteable when terminal hyperlinks are unsupported
10 changes: 5 additions & 5 deletions packages/cli-kit/src/private/node/ui/components/Alert.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -165,14 +165,14 @@ describe('Alert', async () => {
})

// The footnote block (rendered after the closing `╰`) must list the
// URL. Ink wraps the long URL onto its own line when it exceeds terminal
// width, so we assert the `[1]` anchor and the URL show up *outside* the
// bordered box rather than as a single contiguous `[1] URL` substring.
// URL as a single contiguous `[1] URL` line. The footnote Box is sized to
// the line length so Ink never hard-wraps the URL (which would insert
// newline characters and break copy-paste/clickability); the terminal
// soft-wraps the overflow at display time instead.
const closingBorderIndex = frame.indexOf('╰')
expect(closingBorderIndex).toBeGreaterThanOrEqual(0)
const afterBox = frame.slice(closingBorderIndex)
expect(afterBox).toContain('[1]')
expect(afterBox).toContain(longUrl)
expect(afterBox).toContain(`[1] ${longUrl}`)
// And the body must reference the footnote.
expect(frame).toContain('docs [1]')
})
Expand Down
15 changes: 12 additions & 3 deletions packages/cli-kit/src/private/node/ui/components/Banner.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,18 @@ const Footnotes = () => {

return linkIds.length > 0 ? (
<Box marginBottom={1} marginTop={-1} flexDirection="column">
{linkIds.map((id) => (
<Text key={id}>{`[${id}] ${links[id]?.url}`}</Text>
))}
{linkIds.map((id) => {
const line = `[${id}] ${links[id]?.url}`
// Render each footnote on a Box wide enough to fit the whole line so
// Ink doesn't hard-wrap long URLs (which inserts newline characters and
// breaks copy-paste/clickability). The terminal soft-wraps the overflow
// at display time without mutating the underlying text.
return (
<Box key={id} width={line.length}>
<Text>{line}</Text>
</Box>
)
})}
</Box>
) : null
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,23 +26,22 @@ describe('showMultipleCLIWarningIfNeeded', () => {

// Then
expect(mockOutput.info()).toMatchInlineSnapshot(`
"╭─ info ───────────────────────────────────────────────────────────────────────╮
│ │
│ Two Shopify CLI installations found – using global installation │
│ │
│ A global installation (v${CLI_KIT_VERSION}) and a local dependency (v3.70.0) were │
│ detected. │
│ We recommend removing the @shopify/cli and @shopify/app dependencies from │
│ your package.json, unless you want to use different versions across │
│ multiple apps. │
│ │
│ See Shopify CLI documentation. [1] │
│ │
╰──────────────────────────────────────────────────────────────────────────────╯
[1] https://shopify.dev/docs/apps/build/cli-for-apps#switch-to-a-global-executab
le-or-local-dependency
"
`)
"╭─ info ───────────────────────────────────────────────────────────────────────╮
│ │
│ Two Shopify CLI installations found – using global installation │
│ │
│ A global installation (v${CLI_KIT_VERSION}) and a local dependency (v3.70.0) were │
│ detected. │
│ We recommend removing the @shopify/cli and @shopify/app dependencies from │
│ your package.json, unless you want to use different versions across │
│ multiple apps. │
│ │
│ See Shopify CLI documentation. [1] │
│ │
╰──────────────────────────────────────────────────────────────────────────────╯
[1] https://shopify.dev/docs/apps/build/cli-for-apps#switch-to-a-global-executable-or-local-dependency
"
`)
mockOutput.clear()
})

Expand All @@ -58,23 +57,22 @@ describe('showMultipleCLIWarningIfNeeded', () => {

// Then
expect(mockOutput.info()).toMatchInlineSnapshot(`
"╭─ info ───────────────────────────────────────────────────────────────────────╮
│ │
│ Two Shopify CLI installations found – using local dependency │
│ │
│ A global installation (v3.70.0) and a local dependency (v${CLI_KIT_VERSION}) were │
│ detected. │
│ We recommend removing the @shopify/cli and @shopify/app dependencies from │
│ your package.json, unless you want to use different versions across │
│ multiple apps. │
│ │
│ See Shopify CLI documentation. [1] │
│ │
╰──────────────────────────────────────────────────────────────────────────────╯
[1] https://shopify.dev/docs/apps/build/cli-for-apps#switch-to-a-global-executab
le-or-local-dependency
"
`)
"╭─ info ───────────────────────────────────────────────────────────────────────╮
│ │
│ Two Shopify CLI installations found – using local dependency │
│ │
│ A global installation (v3.70.0) and a local dependency (v${CLI_KIT_VERSION}) were │
│ detected. │
│ We recommend removing the @shopify/cli and @shopify/app dependencies from │
│ your package.json, unless you want to use different versions across │
│ multiple apps. │
│ │
│ See Shopify CLI documentation. [1] │
│ │
╰──────────────────────────────────────────────────────────────────────────────╯
[1] https://shopify.dev/docs/apps/build/cli-for-apps#switch-to-a-global-executable-or-local-dependency
"
`)
mockOutput.clear()
})

Expand All @@ -91,23 +89,22 @@ describe('showMultipleCLIWarningIfNeeded', () => {

// Then
expect(mockOutput.info()).toMatchInlineSnapshot(`
"╭─ info ───────────────────────────────────────────────────────────────────────╮
│ │
│ Two Shopify CLI installations found – using global installation │
│ │
│ A global installation (v${CLI_KIT_VERSION}) and a local dependency (v3.70.0) were │
│ detected. │
│ We recommend removing the @shopify/cli and @shopify/app dependencies from │
│ your package.json, unless you want to use different versions across │
│ multiple apps. │
│ │
│ See Shopify CLI documentation. [1] │
│ │
╰──────────────────────────────────────────────────────────────────────────────╯
[1] https://shopify.dev/docs/apps/build/cli-for-apps#switch-to-a-global-executab
le-or-local-dependency
"
`)
"╭─ info ───────────────────────────────────────────────────────────────────────╮
│ │
│ Two Shopify CLI installations found – using global installation │
│ │
│ A global installation (v${CLI_KIT_VERSION}) and a local dependency (v3.70.0) were │
│ detected. │
│ We recommend removing the @shopify/cli and @shopify/app dependencies from │
│ your package.json, unless you want to use different versions across │
│ multiple apps. │
│ │
│ See Shopify CLI documentation. [1] │
│ │
╰──────────────────────────────────────────────────────────────────────────────╯
[1] https://shopify.dev/docs/apps/build/cli-for-apps#switch-to-a-global-executable-or-local-dependency
"
`)
})

test('does not show a warning if there is no local dependency', async () => {
Expand Down
8 changes: 2 additions & 6 deletions packages/cli-kit/src/public/node/ui.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -100,10 +100,7 @@ export type RenderAlertOptions = Omit<AlertOptions, 'type'>
* │ │
* ╰──────────────────────────────────────────────────────────╯
* [1] https://shopify.dev
* [2] https://www.google.com/search?q=jh56t9l34kpo35tw8s28hn7s
* 9s2xvzla01d8cn6j7yq&rlz=1C1GCEU_enUS832US832&oq=jh56t9l34kpo
* 35tw8s28hn7s9s2xvzla01d8cn6j7yq&aqs=chrome.0.35i39l2j0l4j46j
* 69i60.2711j0j7&sourceid=chrome&ie=UTF-8
* [2] https://www.google.com/search?q=jh56t9l34kpo35tw8s28hn7s9s2xvzla01d8cn6j7yq&rlz=1C1GCEU_enUS832US832&oq=jh56t9l34kpo35tw8s28hn7s9s2xvzla01d8cn6j7yq&aqs=chrome.0.35i39l2j0l4j46j69i60.2711j0j7&sourceid=chrome&ie=UTF-8
* [3] https://shopify.com
*
*/
Expand Down Expand Up @@ -134,8 +131,7 @@ export function renderInfo(options: RenderAlertOptions) {
* │ • See your deployment and set it live [1] │
* │ │
* ╰──────────────────────────────────────────────────────────╯
* [1] https://partners.shopify.com/1797046/apps/4523695/deploy
* ments
* [1] https://partners.shopify.com/1797046/apps/4523695/deployments
*
*/
export function renderSuccess(options: RenderAlertOptions) {
Expand Down
Loading