proteum 2.5.20 → 2.5.21
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "proteum",
|
|
3
3
|
"description": "LLM-first Opinionated Typescript Framework for web applications.",
|
|
4
|
-
"version": "2.5.
|
|
4
|
+
"version": "2.5.21",
|
|
5
5
|
"author": "Gaetan Le Gac (https://github.com/gaetanlegac)",
|
|
6
6
|
"repository": "git://github.com/gaetanlegac/proteum.git",
|
|
7
7
|
"license": "MIT",
|
|
@@ -30,14 +30,36 @@ export type TDefaultJsonLdInput = {
|
|
|
30
30
|
- HELPERS
|
|
31
31
|
----------------------------------*/
|
|
32
32
|
|
|
33
|
-
|
|
34
|
-
|
|
33
|
+
/**
|
|
34
|
+
* `WebPage` and the schema.org types that specialise it. A page that describes itself as an
|
|
35
|
+
* `AboutPage` or a `CollectionPage` has described its web page: the generic node beside it
|
|
36
|
+
* would be a second page for the same URL, exactly as beside a plain `WebPage`.
|
|
37
|
+
*/
|
|
38
|
+
const WEB_PAGE_TYPES: ReadonlySet<string> = new Set([
|
|
39
|
+
'WebPage',
|
|
40
|
+
'AboutPage',
|
|
41
|
+
'CheckoutPage',
|
|
42
|
+
'CollectionPage',
|
|
43
|
+
'ContactPage',
|
|
44
|
+
'FAQPage',
|
|
45
|
+
'ItemPage',
|
|
46
|
+
'MedicalWebPage',
|
|
47
|
+
'ProfilePage',
|
|
48
|
+
'QAPage',
|
|
49
|
+
'RealEstateListing',
|
|
50
|
+
'SearchResultsPage',
|
|
51
|
+
]);
|
|
52
|
+
|
|
53
|
+
const describesWebPage = (node: TJsonLdNode): boolean =>
|
|
54
|
+
(Array.isArray(node['@type']) ? node['@type'] : [node['@type']]).some(
|
|
55
|
+
(type) => typeof type === 'string' && WEB_PAGE_TYPES.has(type),
|
|
56
|
+
);
|
|
35
57
|
|
|
36
58
|
/**
|
|
37
59
|
* The publisher identity every page carries (`#organization`, `#website`) plus a generic
|
|
38
60
|
* `WebPage` for pages that describe none themselves.
|
|
39
61
|
*
|
|
40
|
-
* A page that already pushed a `WebPage
|
|
62
|
+
* A page that already pushed a `WebPage`, or one of its subtypes, keeps its own: a second node for the same URL
|
|
41
63
|
* with another name and description reads as two contradictory pages to a consumer.
|
|
42
64
|
* Empty `sameAs` and `potentialAction` arrays are left out for the same reason: they say
|
|
43
65
|
* "no profiles" and "no actions" where the app said nothing. `identity.web.jsonld` can
|
|
@@ -78,7 +100,7 @@ export const buildDefaultJsonLd = ({
|
|
|
78
100
|
},
|
|
79
101
|
];
|
|
80
102
|
|
|
81
|
-
if (!pageJsonLd.some(
|
|
103
|
+
if (!pageJsonLd.some(describesWebPage)) {
|
|
82
104
|
nodes.push({
|
|
83
105
|
'@type': 'WebPage',
|
|
84
106
|
'@id': url,
|
|
@@ -19,7 +19,7 @@ const input = {
|
|
|
19
19
|
};
|
|
20
20
|
|
|
21
21
|
test('default JSON-LD adds a generic WebPage only when the page has none', () => {
|
|
22
|
-
const withoutPage = buildDefaultJsonLd({ ...input, pageJsonLd: [{ '@type': '
|
|
22
|
+
const withoutPage = buildDefaultJsonLd({ ...input, pageJsonLd: [{ '@type': 'BreadcrumbList' }] });
|
|
23
23
|
assert.deepEqual(withoutPage.map((node) => node['@type']), ['Organization', 'WebSite', 'WebPage']);
|
|
24
24
|
assert.equal(withoutPage[2]['@id'], 'https://example.test/pricing');
|
|
25
25
|
assert.equal(withoutPage[2].name, 'Pricing');
|
|
@@ -32,6 +32,14 @@ test('default JSON-LD adds a generic WebPage only when the page has none', () =>
|
|
|
32
32
|
|
|
33
33
|
const withTypedArray = buildDefaultJsonLd({ ...input, pageJsonLd: [{ '@type': ['WebPage', 'FAQPage'] }] });
|
|
34
34
|
assert.deepEqual(withTypedArray.map((node) => node['@type']), ['Organization', 'WebSite']);
|
|
35
|
+
|
|
36
|
+
// Subtypes of WebPage count: an AboutPage or a CollectionPage has described the page.
|
|
37
|
+
for (const subtype of ['AboutPage', 'CollectionPage', 'FAQPage', 'ProfilePage']) {
|
|
38
|
+
const nodes = buildDefaultJsonLd({ ...input, pageJsonLd: [{ '@type': subtype }] });
|
|
39
|
+
assert.deepEqual(nodes.map((node) => node['@type']), ['Organization', 'WebSite'], subtype);
|
|
40
|
+
}
|
|
41
|
+
const unrelated = buildDefaultJsonLd({ ...input, pageJsonLd: [{ '@type': 'SoftwareApplication' }] });
|
|
42
|
+
assert.equal(unrelated.length, 3);
|
|
35
43
|
});
|
|
36
44
|
|
|
37
45
|
test('default JSON-LD emits no empty sameAs or potentialAction, and keeps identity additions', () => {
|