openvibers/openvibe.wiki Commits
Wiki articles: Ask your agent chip beside Share (#236)
Changes
@@@ -434,7 +434,7 @@ function articlePage(v, { html: contentHtml, discussion, actor, mediaUrl, resolvif (v.canEdit && v.decision && !v.decision.indexable && page.state === 'published') banners.push(html`<p class="wk-notice wk-info">Search engines are told not to index this page: ${v.decision.reasons.map((r) => r.code + (r.detail ? ` (${r.detail})` : '')).join(', ')}.</p>`);const actions = [html`<a href="${base}/history">History</a>`];if (v.canEdit) actions.unshift(html`<a href="${base}/edit">Edit</a>`), actions.push(html`<a href="${base}/settings">Page settings</a>`);-- if (shareUrl) actions.unshift(html`${raw(kit.share({ title, url: shareUrl, text: shareText || '', image: shareImage || null, kind: 'page', id: page.id }))}`);++ if (shareUrl) actions.unshift(html`${raw(kit.share({ title, url: shareUrl, text: shareText || '', image: shareImage || null, kind: 'page', id: page.id }))} ${raw(kit.askAgent({ text: `About the wiki page “${title}” (${shareUrl}): ` }))}`);return html`${crumbs(trail)}<article class="wk-article" data-page-id="${page.id}" data-revision="${String(rev.number)}"><header><h1>${title}</h1><nav class="wk-actions" aria-label="Page actions">${actions.map((a, i) => html`${i ? ' · ' : ''}${a}`)}</nav>${pageFacts(v, base)}</header>@@@ -23,6 +23,21 @@ const H = require('./helpers');assert.ok(r.text.includes('data-title="A shareable page"'), 'its title');assert.ok(r.text.includes('data-text="One line about the page."'), 'its summary');assert.ok(r.text.includes('class="ovk-btn ovk-btn--quiet"') && r.text.includes('<span>Share</span>'), 'the shared kit button');++ // The Ask your agent chip (openvibe-shared 4.135.0): beside Share, the article's title and public address in its text.++ const asks = r.text.match(/<button[^>]*data-ov-ask[^>]*>/g) || [];++ assert.strictEqual(asks.length, 1, 'one Ask your agent chip');++ assert.ok(asks[0].includes('data-ov-ask="About the wiki page “A shareable page” (http://wiki.test/w/share-demo/a-shareable-page): "'), asks[0]);++ assert.ok(asks[0].includes('class="ovk-ask ovk-btn'), 'the shared kit chip');++++ // Everything in that text goes through kit.askAgent's escaping, title included.++ const { page: nasty } = await h.svc.createPage(space.id, {++ title: 'Angles <script>alert(1)</script>', body: `The body of the page. ${H.LONG}`,++ }, me);++ await h.svc.publish(nasty.id, {}, me);++ const nr = await H.req(h, 'GET', `/w/share-demo/${nasty.slug}`);++ const nask = (nr.text.match(/<button[^>]*data-ov-ask[^>]*>/g) || [])[0] || '';++ assert.ok(nask.includes(`data-ov-ask="About the wiki page “Angles <script>alert(1)</script>” (http://wiki.test/w/share-demo/${nasty.slug}): "`), nask);++ assert.ok(!nask.includes('<script>'), 'the title is escaped in the chip');console.log('share sheet ok');} finally {await h.stop();
@@ -434,7 +434,7 @@ function articlePage(v, { html: contentHtml, discussion, actor, mediaUrl, resolv
@@ -434,7 +434,7 @@ function articlePage(v, { html: contentHtml, discussion, actor, mediaUrl, resolv
if (v.canEdit && v.decision && !v.decision.indexable && page.state === 'published') banners.push(html`<p class="wk-notice wk-info">Search engines are told not to index this page: ${v.decision.reasons.map((r) => r.code + (r.detail ? ` (${r.detail})` : '')).join(', ')}.</p>`);
if (v.canEdit && v.decision && !v.decision.indexable && page.state === 'published') banners.push(html`<p class="wk-notice wk-info">Search engines are told not to index this page: ${v.decision.reasons.map((r) => r.code + (r.detail ? ` (${r.detail})` : '')).join(', ')}.</p>`);
const actions = [html`<a href="${base}/history">History</a>`];
const actions = [html`<a href="${base}/history">History</a>`];
if (v.canEdit) actions.unshift(html`<a href="${base}/edit">Edit</a>`), actions.push(html`<a href="${base}/settings">Page settings</a>`);
if (v.canEdit) actions.unshift(html`<a href="${base}/edit">Edit</a>`), actions.push(html`<a href="${base}/settings">Page settings</a>`);
- if (shareUrl) actions.unshift(html`${raw(kit.share({ title, url: shareUrl, text: shareText || '', image: shareImage || null, kind: 'page', id: page.id }))}`);
+ if (shareUrl) actions.unshift(html`${raw(kit.share({ title, url: shareUrl, text: shareText || '', image: shareImage || null, kind: 'page', id: page.id }))} ${raw(kit.askAgent({ text: `About the wiki page “${title}” (${shareUrl}): ` }))}`);
return html`${crumbs(trail)}
return html`${crumbs(trail)}
<article class="wk-article" data-page-id="${page.id}" data-revision="${String(rev.number)}">
<article class="wk-article" data-page-id="${page.id}" data-revision="${String(rev.number)}">
<header><h1>${title}</h1><nav class="wk-actions" aria-label="Page actions">${actions.map((a, i) => html`${i ? ' · ' : ''}${a}`)}</nav>${pageFacts(v, base)}</header>
<header><h1>${title}</h1><nav class="wk-actions" aria-label="Page actions">${actions.map((a, i) => html`${i ? ' · ' : ''}${a}`)}</nav>${pageFacts(v, base)}</header>
@@ -23,6 +23,21 @@ const H = require('./helpers');
@@ -23,6 +23,21 @@ const H = require('./helpers');
assert.ok(r.text.includes('data-title="A shareable page"'), 'its title');
assert.ok(r.text.includes('data-title="A shareable page"'), 'its title');
assert.ok(r.text.includes('data-text="One line about the page."'), 'its summary');
assert.ok(r.text.includes('data-text="One line about the page."'), 'its summary');
assert.ok(r.text.includes('class="ovk-btn ovk-btn--quiet"') && r.text.includes('<span>Share</span>'), 'the shared kit button');
assert.ok(r.text.includes('class="ovk-btn ovk-btn--quiet"') && r.text.includes('<span>Share</span>'), 'the shared kit button');
+ // The Ask your agent chip (openvibe-shared 4.135.0): beside Share, the article's title and public address in its text.
+ const asks = r.text.match(/<button[^>]*data-ov-ask[^>]*>/g) || [];
+ assert.strictEqual(asks.length, 1, 'one Ask your agent chip');
+ assert.ok(asks[0].includes('data-ov-ask="About the wiki page “A shareable page” (http://wiki.test/w/share-demo/a-shareable-page): "'), asks[0]);
+ assert.ok(asks[0].includes('class="ovk-ask ovk-btn'), 'the shared kit chip');
+
+ // Everything in that text goes through kit.askAgent's escaping, title included.
+ const { page: nasty } = await h.svc.createPage(space.id, {
+ title: 'Angles <script>alert(1)</script>', body: `The body of the page. ${H.LONG}`,
+ }, me);
+ await h.svc.publish(nasty.id, {}, me);
+ const nr = await H.req(h, 'GET', `/w/share-demo/${nasty.slug}`);
+ const nask = (nr.text.match(/<button[^>]*data-ov-ask[^>]*>/g) || [])[0] || '';
+ assert.ok(nask.includes(`data-ov-ask="About the wiki page “Angles <script>alert(1)</script>” (http://wiki.test/w/share-demo/${nasty.slug}): "`), nask);
+ assert.ok(!nask.includes('<script>'), 'the title is escaped in the chip');
console.log('share sheet ok');
console.log('share sheet ok');
} finally {
} finally {
await h.stop();
await h.stop();