openvibers/openvibe.mediahub Commits
Share buttons styled again on Video and Pics (#318)
Changes
@@@ -25,23 +25,6 @@ const kit = require('openvibe-shared/kit');const code = (s) => html`<code>${s}</code>`;--/**-- * The Share button, built by the shared kit (openvibe-shared 4.114.0): the same quiet button with the same share-- * icon on every OpenVibe site. The navbar fetches the sheet the first time the button is pressed.-- *-- * url: the page's own public address — the link that is shared-- * title: what the thing is called-- * text: a line sent with it (the thing's own summary)-- * image: a picture of it (a thumbnail), for the places that take one-- * embed: an embeddable player address, for the places that take one-- * timeFrom: the player whose moment can be shared (a selector), so the sheet can offer "Start at …"-- */--function shareButton({ title = '', url = '', text = '', image = '', embed = '', timeFrom = null, small = false }) {-- const line = String(text || '').trim().replace(/\s+/g, ' ').slice(0, 240);-- const button = kit.share({ title, url, text: line, image, embed, small });-- return timeFrom ? button.replace('data-ov-share-sheet', `data-ov-share-sheet data-time-from="${esc(timeFrom)}"`) : button;--}--/*** The Share button: the one share sheet every OpenVibe site opens (openvibe-shared 4.114.0). The navbar fetches* the sheet the first time the button is pressed, so the button itself only says what is being shared:@@@ -54,7 +37,9 @@ function shareButton({ title = '', url = '', text = '', image = '', embed = '',** Nothing is stored and no clip is made: a moment is the page's own address with a time on it.*/--function shareButton({ url = '', title = '', text = '', image = '', timeFrom = null, kind = null, id = null, cls = '', label = 'Share', icon = 'fa-solid fa-share-nodes' }) {++// A caller with no class of its own gets the kit's quiet button (kit.css is on every page that shows one): an empty class++// drew an unstyled grey box beside the row's buttons (11-07).++function shareButton({ url = '', title = '', text = '', image = '', timeFrom = null, kind = null, id = null, cls = 'ovk-btn ovk-btn--quiet', label = 'Share', icon = 'fa-solid fa-share-nodes' }) {const line = String(text || '').trim().replace(/\s+/g, ' ');const summary = line.length > 240 ? `${line.slice(0, 237).trimEnd()}…` : line;return html`<button type="button" class="${cls}" data-ov-share-sheet${url ? html` data-url="${url}"` : ''}${title ? html` data-title="${title}"` : ''}${summary ? html` data-text="${summary}"` : ''}${image ? html` data-image="${image}"` : ''}${timeFrom ? html` data-time-from="${timeFrom}"` : ''}${kind && id ? html` data-kind="${kind}" data-id="${id}"` : ''}><i class="${icon}" aria-hidden="true"></i> ${label}</button>`;@@@ -1375,7 +1375,7 @@ ${channelName ? html`<a class="ovv-avatar" href="${localChannel || liveChannel}"<div class="ovv-byline-text">${channelName ? (localChannel ? html`<a class="ovv-channel-name" href="${localChannel}">@${channelName}</a>` : html`<span class="ovv-channel-name">@${channelName}</span>`) : ''}${metaParts.length ? html`<span class="ovv-meta">${metaParts.map((p, i) => (i === 0 ? p : [html` · `, p]))}</span>` : ''}</div></div>--<div class="ovv-actions">${manageable ? editButton('recording') : ''}${saveForm}${ownOnly ? '' : clipAction(req, id, vod)}${downloadMenu({ kind: 'vod', id, item: vod, has: { transcript: segs.length, chat: chatRows ? chatRows.rows.length + chatRows.leftOut : 0, chapters: mems.length } })}${raw(shareButton({ url: `${base}${watchPath}`, title: vod.title || 'Stream recording', text: about, image: httpsUrl(vod.thumbnail_url) || '', timeFrom: '.ovv-player' }))}${moreItems.length ? actionMenu({ icon: 'fa-solid fa-ellipsis', label: 'More', iconOnly: true, cls: 'ovv-more-menu', body: menuLinks(moreItems) }) : ''}</div>++<div class="ovv-actions">${manageable ? editButton('recording') : ''}${saveForm}${ownOnly ? '' : clipAction(req, id, vod)}${downloadMenu({ kind: 'vod', id, item: vod, has: { transcript: segs.length, chat: chatRows ? chatRows.rows.length + chatRows.leftOut : 0, chapters: mems.length } })}${raw(shareButton({ cls: 'ovv-btn', url: `${base}${watchPath}`, title: vod.title || 'Stream recording', text: about, image: httpsUrl(vod.thumbnail_url) || '', timeFrom: '.ovv-player' }))}${moreItems.length ? actionMenu({ icon: 'fa-solid fa-ellipsis', label: 'More', iconOnly: true, cls: 'ovv-more-menu', body: menuLinks(moreItems) }) : ''}</div></div>${vod.is_recording ? html`<p class="ovv-recording" role="status"><i class="fa-solid fa-circle" aria-hidden="true"></i> This recording is still in progress. <a href="${liveChannel}">Watch the live channel</a>.</p>` : ''}</div>@@@ -1513,7 +1513,7 @@ ${clipCredit}<div class="ovv-head-row"><div class="ovv-byline"><div class="ovv-byline-text"><span class="ovv-channel-name">${clip.auto_generated ? html`<span class="ovv-tag ovv-tag--inline">AI clip</span> ` : ''}${attribution}</span>${clip.created_at ? html`<span class="ovv-meta"><time datetime="${clip.created_at}">${dateLabel(clip.created_at)}</time>${manageable ? html` · ${visibilityBadge(clip.visibility)}` : ''}</span>` : ''}</div></div>--<div class="ovv-actions">${manageable ? editButton('clip') : ''}${fullRecording ? html`<a class="ovv-btn ovv-btn--primary" href="${fullRecording}" title="Watch the recording it was cut from, from this moment"><i class="fa-solid fa-film" aria-hidden="true"></i> Full recording</a>` : ''}${saveForm}${cutting ? '' : downloadMenu({ kind: 'clip', id, item: clip, has: { transcript: segs.length } })}${raw(shareButton({ url: `${base}${watchPath}`, title: clip.title || 'Clip', text: clip.ai_overview || attribution, image: httpsUrl(clip.thumbnail_url) || '', timeFrom: '.ovv-player' }))}${moreItems.length ? actionMenu({ icon: 'fa-solid fa-ellipsis', label: 'More', iconOnly: true, cls: 'ovv-more-menu', body: menuLinks(moreItems) }) : ''}</div>++<div class="ovv-actions">${manageable ? editButton('clip') : ''}${fullRecording ? html`<a class="ovv-btn ovv-btn--primary" href="${fullRecording}" title="Watch the recording it was cut from, from this moment"><i class="fa-solid fa-film" aria-hidden="true"></i> Full recording</a>` : ''}${saveForm}${cutting ? '' : downloadMenu({ kind: 'clip', id, item: clip, has: { transcript: segs.length } })}${raw(shareButton({ cls: 'ovv-btn', url: `${base}${watchPath}`, title: clip.title || 'Clip', text: clip.ai_overview || attribution, image: httpsUrl(clip.thumbnail_url) || '', timeFrom: '.ovv-player' }))}${moreItems.length ? actionMenu({ icon: 'fa-solid fa-ellipsis', label: 'More', iconOnly: true, cls: 'ovv-more-menu', body: menuLinks(moreItems) }) : ''}</div></div></div></div>@@@ -363,7 +363,7 @@ ${what}${channel ? html`<a class="ovv-avatar" href="/@${channel}" aria-hidden="true" tabindex="-1">${channel.slice(0, 1).toUpperCase()}${/^[A-Za-z0-9_]{1,32}$/.test(channel) ? html`<img src="${ctx.config.networkUrl}/avatar/${channel}" alt="" loading="lazy">` : ''}</a>` : ''}<div class="ovv-byline-text">${channel ? html`<a class="ovv-channel-name" href="/@${channel}">@${channel}</a>` : ''}</div>--<div class="ovv-byline-actions">${saveForm}${raw(shareButton({ url: `${ctx.config.video.url}${watchPath}`, title: row.title, text: about, image: thumb || '', timeFrom: ready && vod ? '.ovv-player' : null }))}</div>++<div class="ovv-byline-actions">${saveForm}${raw(shareButton({ cls: 'ovv-btn', url: `${ctx.config.video.url}${watchPath}`, title: row.title, text: about, image: thumb || '', timeFrom: ready && vod ? '.ovv-player' : null }))}</div></div>${row.description ? html`<section class="ovv-panel ovv-description"><p>${row.description}</p></section>` : ''}${aiDone && ai.overview ? html`<section class="ovv-panel" aria-labelledby="h-ai"><h2 id="h-ai">About this video</h2><p>${ai.overview}</p><p class="ovv-fine">Written by AI from the video's sound and pictures (OpenVibe.AI, run on OpenVibe's own servers).</p>@@@ -155,6 +155,7 @@ function multipart(fields, file) {assert.strictEqual(buttons.length, 1, 'one Share button: ' + buttons.join(' | '));assert.ok(buttons[0].includes(`data-url="https://openvibe.pics/i/${slug}"`), buttons[0]);assert.ok(buttons[0].includes(`data-image="https://openvibe.pics${direct}"`), buttons[0]);++ assert.ok(buttons[0].includes('class="ovk-btn ovk-btn--quiet"'), 'a styled button, never class="": ' + buttons[0]);assert.ok((await t.get(`/i/${slug}`, { headers: PICS, as: kim })).text.includes('Delete this picture'));});@@@ -434,6 +434,7 @@ function countOccurrences(haystack, needle) {const buttons = r.text.match(/<button[^>]*data-ov-share-sheet[^>]*>/g) || [];assert.strictEqual(buttons.length, 1, 'one Share button: ' + buttons.join(' | '));assert.ok(buttons[0].includes('data-url="https://openvibe.video/@streamer"'), buttons[0]);++ assert.ok(!/class=""/.test(buttons[0]), 'a styled button, never class="": ' + buttons[0]);});await check('an unknown /api path on the video host is a JSON 404, not a page', async () => {@@@ -111,6 +111,8 @@ function request(base, path, host) {const r = await getVideo(`/watch?v=${UPLOAD_ONE}`);assert.strictEqual(r.status, 200);assert.ok(r.text.includes(`<link rel="canonical" href="https://openvibe.video/watch?v=${UPLOAD_ONE}">`), 'canonical');++ // Its Share button is one of the byline row's own buttons (it was an unstyled class="" box until 11-07).++ assert.match(r.text, /<button type="button" class="ovv-btn" data-ov-share-sheet/, 'the Share button has the row\'s style');assert.ok(r.text.includes(`data-url="https://openvibe.video/watch?v=${UPLOAD_ONE}"`), 'share sheet');});
@@ -25,23 +25,6 @@ const kit = require('openvibe-shared/kit');
@@ -25,23 +25,6 @@ const kit = require('openvibe-shared/kit');
const code = (s) => html`<code>${s}</code>`;
const code = (s) => html`<code>${s}</code>`;
-/**
- * The Share button, built by the shared kit (openvibe-shared 4.114.0): the same quiet button with the same share
- * icon on every OpenVibe site. The navbar fetches the sheet the first time the button is pressed.
- *
- * url: the page's own public address — the link that is shared
- * title: what the thing is called
- * text: a line sent with it (the thing's own summary)
- * image: a picture of it (a thumbnail), for the places that take one
- * embed: an embeddable player address, for the places that take one
- * timeFrom: the player whose moment can be shared (a selector), so the sheet can offer "Start at …"
- */
-function shareButton({ title = '', url = '', text = '', image = '', embed = '', timeFrom = null, small = false }) {
- const line = String(text || '').trim().replace(/\s+/g, ' ').slice(0, 240);
- const button = kit.share({ title, url, text: line, image, embed, small });
- return timeFrom ? button.replace('data-ov-share-sheet', `data-ov-share-sheet data-time-from="${esc(timeFrom)}"`) : button;
-}
-
/**
/**
* The Share button: the one share sheet every OpenVibe site opens (openvibe-shared 4.114.0). The navbar fetches
* The Share button: the one share sheet every OpenVibe site opens (openvibe-shared 4.114.0). The navbar fetches
* the sheet the first time the button is pressed, so the button itself only says what is being shared:
* the sheet the first time the button is pressed, so the button itself only says what is being shared:
@@ -54,7 +37,9 @@ function shareButton({ title = '', url = '', text = '', image = '', embed = '',
@@ -54,7 +37,9 @@ function shareButton({ title = '', url = '', text = '', image = '', embed = '',
*
*
* Nothing is stored and no clip is made: a moment is the page's own address with a time on it.
* Nothing is stored and no clip is made: a moment is the page's own address with a time on it.
*/
*/
-function shareButton({ url = '', title = '', text = '', image = '', timeFrom = null, kind = null, id = null, cls = '', label = 'Share', icon = 'fa-solid fa-share-nodes' }) {
+// A caller with no class of its own gets the kit's quiet button (kit.css is on every page that shows one): an empty class
+// drew an unstyled grey box beside the row's buttons (11-07).
+function shareButton({ url = '', title = '', text = '', image = '', timeFrom = null, kind = null, id = null, cls = 'ovk-btn ovk-btn--quiet', label = 'Share', icon = 'fa-solid fa-share-nodes' }) {
const line = String(text || '').trim().replace(/\s+/g, ' ');
const line = String(text || '').trim().replace(/\s+/g, ' ');
const summary = line.length > 240 ? `${line.slice(0, 237).trimEnd()}…` : line;
const summary = line.length > 240 ? `${line.slice(0, 237).trimEnd()}…` : line;
return html`<button type="button" class="${cls}" data-ov-share-sheet${url ? html` data-url="${url}"` : ''}${title ? html` data-title="${title}"` : ''}${summary ? html` data-text="${summary}"` : ''}${image ? html` data-image="${image}"` : ''}${timeFrom ? html` data-time-from="${timeFrom}"` : ''}${kind && id ? html` data-kind="${kind}" data-id="${id}"` : ''}><i class="${icon}" aria-hidden="true"></i> ${label}</button>`;
return html`<button type="button" class="${cls}" data-ov-share-sheet${url ? html` data-url="${url}"` : ''}${title ? html` data-title="${title}"` : ''}${summary ? html` data-text="${summary}"` : ''}${image ? html` data-image="${image}"` : ''}${timeFrom ? html` data-time-from="${timeFrom}"` : ''}${kind && id ? html` data-kind="${kind}" data-id="${id}"` : ''}><i class="${icon}" aria-hidden="true"></i> ${label}</button>`;
@@ -1375,7 +1375,7 @@ ${channelName ? html`<a class="ovv-avatar" href="${localChannel || liveChannel}"
@@ -1375,7 +1375,7 @@ ${channelName ? html`<a class="ovv-avatar" href="${localChannel || liveChannel}"
<div class="ovv-byline-text">${channelName ? (localChannel ? html`<a class="ovv-channel-name" href="${localChannel}">@${channelName}</a>` : html`<span class="ovv-channel-name">@${channelName}</span>`) : ''}
<div class="ovv-byline-text">${channelName ? (localChannel ? html`<a class="ovv-channel-name" href="${localChannel}">@${channelName}</a>` : html`<span class="ovv-channel-name">@${channelName}</span>`) : ''}
${metaParts.length ? html`<span class="ovv-meta">${metaParts.map((p, i) => (i === 0 ? p : [html` · `, p]))}</span>` : ''}</div>
${metaParts.length ? html`<span class="ovv-meta">${metaParts.map((p, i) => (i === 0 ? p : [html` · `, p]))}</span>` : ''}</div>
</div>
</div>
-<div class="ovv-actions">${manageable ? editButton('recording') : ''}${saveForm}${ownOnly ? '' : clipAction(req, id, vod)}${downloadMenu({ kind: 'vod', id, item: vod, has: { transcript: segs.length, chat: chatRows ? chatRows.rows.length + chatRows.leftOut : 0, chapters: mems.length } })}${raw(shareButton({ url: `${base}${watchPath}`, title: vod.title || 'Stream recording', text: about, image: httpsUrl(vod.thumbnail_url) || '', timeFrom: '.ovv-player' }))}${moreItems.length ? actionMenu({ icon: 'fa-solid fa-ellipsis', label: 'More', iconOnly: true, cls: 'ovv-more-menu', body: menuLinks(moreItems) }) : ''}</div>
+<div class="ovv-actions">${manageable ? editButton('recording') : ''}${saveForm}${ownOnly ? '' : clipAction(req, id, vod)}${downloadMenu({ kind: 'vod', id, item: vod, has: { transcript: segs.length, chat: chatRows ? chatRows.rows.length + chatRows.leftOut : 0, chapters: mems.length } })}${raw(shareButton({ cls: 'ovv-btn', url: `${base}${watchPath}`, title: vod.title || 'Stream recording', text: about, image: httpsUrl(vod.thumbnail_url) || '', timeFrom: '.ovv-player' }))}${moreItems.length ? actionMenu({ icon: 'fa-solid fa-ellipsis', label: 'More', iconOnly: true, cls: 'ovv-more-menu', body: menuLinks(moreItems) }) : ''}</div>
</div>
</div>
${vod.is_recording ? html`<p class="ovv-recording" role="status"><i class="fa-solid fa-circle" aria-hidden="true"></i> This recording is still in progress. <a href="${liveChannel}">Watch the live channel</a>.</p>` : ''}
${vod.is_recording ? html`<p class="ovv-recording" role="status"><i class="fa-solid fa-circle" aria-hidden="true"></i> This recording is still in progress. <a href="${liveChannel}">Watch the live channel</a>.</p>` : ''}
</div>
</div>
@@ -1513,7 +1513,7 @@ ${clipCredit}
@@ -1513,7 +1513,7 @@ ${clipCredit}
<div class="ovv-head-row">
<div class="ovv-head-row">
<div class="ovv-byline"><div class="ovv-byline-text"><span class="ovv-channel-name">${clip.auto_generated ? html`<span class="ovv-tag ovv-tag--inline">AI clip</span> ` : ''}${attribution}</span>
<div class="ovv-byline"><div class="ovv-byline-text"><span class="ovv-channel-name">${clip.auto_generated ? html`<span class="ovv-tag ovv-tag--inline">AI clip</span> ` : ''}${attribution}</span>
${clip.created_at ? html`<span class="ovv-meta"><time datetime="${clip.created_at}">${dateLabel(clip.created_at)}</time>${manageable ? html` · ${visibilityBadge(clip.visibility)}` : ''}</span>` : ''}</div></div>
${clip.created_at ? html`<span class="ovv-meta"><time datetime="${clip.created_at}">${dateLabel(clip.created_at)}</time>${manageable ? html` · ${visibilityBadge(clip.visibility)}` : ''}</span>` : ''}</div></div>
-<div class="ovv-actions">${manageable ? editButton('clip') : ''}${fullRecording ? html`<a class="ovv-btn ovv-btn--primary" href="${fullRecording}" title="Watch the recording it was cut from, from this moment"><i class="fa-solid fa-film" aria-hidden="true"></i> Full recording</a>` : ''}${saveForm}${cutting ? '' : downloadMenu({ kind: 'clip', id, item: clip, has: { transcript: segs.length } })}${raw(shareButton({ url: `${base}${watchPath}`, title: clip.title || 'Clip', text: clip.ai_overview || attribution, image: httpsUrl(clip.thumbnail_url) || '', timeFrom: '.ovv-player' }))}${moreItems.length ? actionMenu({ icon: 'fa-solid fa-ellipsis', label: 'More', iconOnly: true, cls: 'ovv-more-menu', body: menuLinks(moreItems) }) : ''}</div>
+<div class="ovv-actions">${manageable ? editButton('clip') : ''}${fullRecording ? html`<a class="ovv-btn ovv-btn--primary" href="${fullRecording}" title="Watch the recording it was cut from, from this moment"><i class="fa-solid fa-film" aria-hidden="true"></i> Full recording</a>` : ''}${saveForm}${cutting ? '' : downloadMenu({ kind: 'clip', id, item: clip, has: { transcript: segs.length } })}${raw(shareButton({ cls: 'ovv-btn', url: `${base}${watchPath}`, title: clip.title || 'Clip', text: clip.ai_overview || attribution, image: httpsUrl(clip.thumbnail_url) || '', timeFrom: '.ovv-player' }))}${moreItems.length ? actionMenu({ icon: 'fa-solid fa-ellipsis', label: 'More', iconOnly: true, cls: 'ovv-more-menu', body: menuLinks(moreItems) }) : ''}</div>
</div>
</div>
</div>
</div>
</div>
</div>
@@ -363,7 +363,7 @@ ${what}
@@ -363,7 +363,7 @@ ${what}
${channel ? html`<a class="ovv-avatar" href="/@${channel}" aria-hidden="true" tabindex="-1">${channel.slice(0, 1).toUpperCase()}${/^[A-Za-z0-9_]{1,32}$/.test(channel) ? html`<img src="${ctx.config.networkUrl}/avatar/${channel}" alt="" loading="lazy">` : ''}</a>` : ''}
${channel ? html`<a class="ovv-avatar" href="/@${channel}" aria-hidden="true" tabindex="-1">${channel.slice(0, 1).toUpperCase()}${/^[A-Za-z0-9_]{1,32}$/.test(channel) ? html`<img src="${ctx.config.networkUrl}/avatar/${channel}" alt="" loading="lazy">` : ''}</a>` : ''}
<div class="ovv-byline-text">${channel ? html`<a class="ovv-channel-name" href="/@${channel}">@${channel}</a>` : ''}
<div class="ovv-byline-text">${channel ? html`<a class="ovv-channel-name" href="/@${channel}">@${channel}</a>` : ''}
</div>
</div>
-<div class="ovv-byline-actions">${saveForm}${raw(shareButton({ url: `${ctx.config.video.url}${watchPath}`, title: row.title, text: about, image: thumb || '', timeFrom: ready && vod ? '.ovv-player' : null }))}</div>
+<div class="ovv-byline-actions">${saveForm}${raw(shareButton({ cls: 'ovv-btn', url: `${ctx.config.video.url}${watchPath}`, title: row.title, text: about, image: thumb || '', timeFrom: ready && vod ? '.ovv-player' : null }))}</div>
</div>
</div>
${row.description ? html`<section class="ovv-panel ovv-description"><p>${row.description}</p></section>` : ''}
${row.description ? html`<section class="ovv-panel ovv-description"><p>${row.description}</p></section>` : ''}
${aiDone && ai.overview ? html`<section class="ovv-panel" aria-labelledby="h-ai"><h2 id="h-ai">About this video</h2><p>${ai.overview}</p><p class="ovv-fine">Written by AI from the video's sound and pictures (OpenVibe.AI, run on OpenVibe's own servers).</p>
${aiDone && ai.overview ? html`<section class="ovv-panel" aria-labelledby="h-ai"><h2 id="h-ai">About this video</h2><p>${ai.overview}</p><p class="ovv-fine">Written by AI from the video's sound and pictures (OpenVibe.AI, run on OpenVibe's own servers).</p>
@@ -155,6 +155,7 @@ function multipart(fields, file) {
@@ -155,6 +155,7 @@ function multipart(fields, file) {
assert.strictEqual(buttons.length, 1, 'one Share button: ' + buttons.join(' | '));
assert.strictEqual(buttons.length, 1, 'one Share button: ' + buttons.join(' | '));
assert.ok(buttons[0].includes(`data-url="https://openvibe.pics/i/${slug}"`), buttons[0]);
assert.ok(buttons[0].includes(`data-url="https://openvibe.pics/i/${slug}"`), buttons[0]);
assert.ok(buttons[0].includes(`data-image="https://openvibe.pics${direct}"`), buttons[0]);
assert.ok(buttons[0].includes(`data-image="https://openvibe.pics${direct}"`), buttons[0]);
+ assert.ok(buttons[0].includes('class="ovk-btn ovk-btn--quiet"'), 'a styled button, never class="": ' + buttons[0]);
assert.ok((await t.get(`/i/${slug}`, { headers: PICS, as: kim })).text.includes('Delete this picture'));
assert.ok((await t.get(`/i/${slug}`, { headers: PICS, as: kim })).text.includes('Delete this picture'));
});
});
@@ -434,6 +434,7 @@ function countOccurrences(haystack, needle) {
@@ -434,6 +434,7 @@ function countOccurrences(haystack, needle) {
const buttons = r.text.match(/<button[^>]*data-ov-share-sheet[^>]*>/g) || [];
const buttons = r.text.match(/<button[^>]*data-ov-share-sheet[^>]*>/g) || [];
assert.strictEqual(buttons.length, 1, 'one Share button: ' + buttons.join(' | '));
assert.strictEqual(buttons.length, 1, 'one Share button: ' + buttons.join(' | '));
assert.ok(buttons[0].includes('data-url="https://openvibe.video/@streamer"'), buttons[0]);
assert.ok(buttons[0].includes('data-url="https://openvibe.video/@streamer"'), buttons[0]);
+ assert.ok(!/class=""/.test(buttons[0]), 'a styled button, never class="": ' + buttons[0]);
});
});
await check('an unknown /api path on the video host is a JSON 404, not a page', async () => {
await check('an unknown /api path on the video host is a JSON 404, not a page', async () => {
@@ -111,6 +111,8 @@ function request(base, path, host) {
@@ -111,6 +111,8 @@ function request(base, path, host) {
const r = await getVideo(`/watch?v=${UPLOAD_ONE}`);
const r = await getVideo(`/watch?v=${UPLOAD_ONE}`);
assert.strictEqual(r.status, 200);
assert.strictEqual(r.status, 200);
assert.ok(r.text.includes(`<link rel="canonical" href="https://openvibe.video/watch?v=${UPLOAD_ONE}">`), 'canonical');
assert.ok(r.text.includes(`<link rel="canonical" href="https://openvibe.video/watch?v=${UPLOAD_ONE}">`), 'canonical');
+ // Its Share button is one of the byline row's own buttons (it was an unstyled class="" box until 11-07).
+ assert.match(r.text, /<button type="button" class="ovv-btn" data-ov-share-sheet/, 'the Share button has the row\'s style');
assert.ok(r.text.includes(`data-url="https://openvibe.video/watch?v=${UPLOAD_ONE}"`), 'share sheet');
assert.ok(r.text.includes(`data-url="https://openvibe.video/watch?v=${UPLOAD_ONE}"`), 'share sheet');
});
});