@lynxflow/seo-engine 1.8.4 → 1.8.5
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/dist/index.js +59 -1
- package/package.json +1 -1
- package/src/index.ts +2 -0
- package/src/public-manifest-engine.ts +109 -0
package/dist/index.js
CHANGED
|
@@ -7980,6 +7980,62 @@ L'activation est instantanée en 1 clic sans compétences techniques.`}
|
|
|
7980
7980
|
`.trim();
|
|
7981
7981
|
}
|
|
7982
7982
|
}
|
|
7983
|
+
// packages/lynx-seo-engine/src/public-manifest-engine.ts
|
|
7984
|
+
class PublicRoutesManifestEngine2 {
|
|
7985
|
+
static registeredRoutes = new Map;
|
|
7986
|
+
static registerManifest(config) {
|
|
7987
|
+
let count = 0;
|
|
7988
|
+
if (config.routes && Array.isArray(config.routes)) {
|
|
7989
|
+
for (const r of config.routes) {
|
|
7990
|
+
this.registeredRoutes.set(r.path, r);
|
|
7991
|
+
count++;
|
|
7992
|
+
}
|
|
7993
|
+
}
|
|
7994
|
+
if (config.navMenuItems && Array.isArray(config.navMenuItems)) {
|
|
7995
|
+
for (const nav of config.navMenuItems) {
|
|
7996
|
+
if (!this.registeredRoutes.has(nav.url)) {
|
|
7997
|
+
this.registeredRoutes.set(nav.url, {
|
|
7998
|
+
path: nav.url,
|
|
7999
|
+
title: nav.label,
|
|
8000
|
+
category: nav.category || "Main Navigation",
|
|
8001
|
+
description: `Page officielle ${nav.label} disponible sur le site.`,
|
|
8002
|
+
paragraphs: [`Découvrez la solution ${nav.label} pour optimiser vos processus et vos résultats.`],
|
|
8003
|
+
keyFeatures: [`Accès direct à ${nav.label}`, "Intégration transparente"]
|
|
8004
|
+
});
|
|
8005
|
+
count++;
|
|
8006
|
+
}
|
|
8007
|
+
}
|
|
8008
|
+
}
|
|
8009
|
+
if (config.contentCollections && Array.isArray(config.contentCollections)) {
|
|
8010
|
+
for (const doc of config.contentCollections) {
|
|
8011
|
+
const paragraphs = doc.content.split(`
|
|
8012
|
+
|
|
8013
|
+
`).map((p) => p.replace(/[#*`]/g, "").trim()).filter((p) => p.length > 30).slice(0, 15);
|
|
8014
|
+
this.registeredRoutes.set(doc.slug, {
|
|
8015
|
+
path: doc.slug.startsWith("/") ? doc.slug : `/${doc.slug}`,
|
|
8016
|
+
title: doc.title,
|
|
8017
|
+
category: "Documentation & Features",
|
|
8018
|
+
paragraphs,
|
|
8019
|
+
description: paragraphs[0] || doc.title
|
|
8020
|
+
});
|
|
8021
|
+
count++;
|
|
8022
|
+
}
|
|
8023
|
+
}
|
|
8024
|
+
return count;
|
|
8025
|
+
}
|
|
8026
|
+
static registerWordPressMenu(menuItems) {
|
|
8027
|
+
return this.registerManifest({
|
|
8028
|
+
framework: "wordpress",
|
|
8029
|
+
navMenuItems: menuItems.map((m) => ({ label: m.title, url: m.url }))
|
|
8030
|
+
});
|
|
8031
|
+
}
|
|
8032
|
+
static getSeedRoutes() {
|
|
8033
|
+
return Array.from(this.registeredRoutes.values());
|
|
8034
|
+
}
|
|
8035
|
+
static getRoute(pathOrSlug) {
|
|
8036
|
+
return this.registeredRoutes.get(pathOrSlug);
|
|
8037
|
+
}
|
|
8038
|
+
}
|
|
7983
8039
|
|
|
7984
8040
|
// packages/lynx-seo-engine/src/index.ts
|
|
7985
8041
|
function createLynxSeoEngine(config) {
|
|
@@ -8023,7 +8079,8 @@ var LynxSeo = {
|
|
|
8023
8079
|
yoastReadability: YoastParityEngine,
|
|
8024
8080
|
rbac: TeamRbacEngine,
|
|
8025
8081
|
realReviews: RealReviewsSyncEngine,
|
|
8026
|
-
knowledgeHarvester: FeaturesKnowledgeHarvester
|
|
8082
|
+
knowledgeHarvester: FeaturesKnowledgeHarvester,
|
|
8083
|
+
manifest: PublicRoutesManifestEngine
|
|
8027
8084
|
};
|
|
8028
8085
|
var src_default = LynxSeo;
|
|
8029
8086
|
export {
|
|
@@ -8058,6 +8115,7 @@ export {
|
|
|
8058
8115
|
RssSyndicationFeedGenerator,
|
|
8059
8116
|
RealReviewsSyncEngine,
|
|
8060
8117
|
RankMathParityEngine,
|
|
8118
|
+
PublicRoutesManifestEngine2 as PublicRoutesManifestEngine,
|
|
8061
8119
|
PseoMatrixEngine,
|
|
8062
8120
|
PowerWordsPsychologyEngine,
|
|
8063
8121
|
PSEO_AGENT_SYSTEM_PROMPT,
|
package/package.json
CHANGED
package/src/index.ts
CHANGED
|
@@ -148,7 +148,9 @@ export const LynxSeo = {
|
|
|
148
148
|
rbac: TeamRbacEngine,
|
|
149
149
|
realReviews: RealReviewsSyncEngine,
|
|
150
150
|
knowledgeHarvester: FeaturesKnowledgeHarvester,
|
|
151
|
+
manifest: PublicRoutesManifestEngine,
|
|
151
152
|
};
|
|
152
153
|
|
|
153
154
|
export { FeaturesKnowledgeHarvester, type ExtractedFeatureKnowledge } from "./features-knowledge-harvester";
|
|
155
|
+
export { PublicRoutesManifestEngine, type PublicRouteItem, type FrameworkManifestConfig } from "./public-manifest-engine";
|
|
154
156
|
export default LynxSeo;
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 🗺️ Universal Public Routes & Navigation Manifest Engine
|
|
3
|
+
*
|
|
4
|
+
* Allows developers and LLM agents to connect their real public pages (10-50 seed pages)
|
|
5
|
+
* from ANY framework (Next.js, TanStack Router, Astro, Nuxt, WordPress, Laravel, Remix).
|
|
6
|
+
*
|
|
7
|
+
* Instead of scanning millions of generated URLs, it inspects ONLY the root product pages,
|
|
8
|
+
* navigation menus, or route trees to build the knowledge base for all programmatic pages.
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
export interface PublicRouteItem {
|
|
12
|
+
path: string;
|
|
13
|
+
title: string;
|
|
14
|
+
description?: string;
|
|
15
|
+
category?: string;
|
|
16
|
+
paragraphs?: string[];
|
|
17
|
+
keyFeatures?: string[];
|
|
18
|
+
faqs?: { question: string; answer: string }[];
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
export interface FrameworkManifestConfig {
|
|
22
|
+
framework?: "nextjs" | "tanstack" | "astro" | "wordpress" | "nuxt" | "custom";
|
|
23
|
+
routes?: PublicRouteItem[];
|
|
24
|
+
navMenuItems?: Array<{ label: string; url: string; category?: string }>;
|
|
25
|
+
contentCollections?: Array<{ slug: string; title: string; content: string }>;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
export class PublicRoutesManifestEngine {
|
|
29
|
+
private static registeredRoutes: Map<string, PublicRouteItem> = new Map();
|
|
30
|
+
|
|
31
|
+
/**
|
|
32
|
+
* 1. Register Public Routes & Navigation Menu (Universal Entrypoint)
|
|
33
|
+
*/
|
|
34
|
+
static registerManifest(config: FrameworkManifestConfig): number {
|
|
35
|
+
let count = 0;
|
|
36
|
+
|
|
37
|
+
// A. Explicit Route Items
|
|
38
|
+
if (config.routes && Array.isArray(config.routes)) {
|
|
39
|
+
for (const r of config.routes) {
|
|
40
|
+
this.registeredRoutes.set(r.path, r);
|
|
41
|
+
count++;
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
// B. From Navigation Menu Items (WordPress Menus, Navbar JSON, etc.)
|
|
46
|
+
if (config.navMenuItems && Array.isArray(config.navMenuItems)) {
|
|
47
|
+
for (const nav of config.navMenuItems) {
|
|
48
|
+
if (!this.registeredRoutes.has(nav.url)) {
|
|
49
|
+
this.registeredRoutes.set(nav.url, {
|
|
50
|
+
path: nav.url,
|
|
51
|
+
title: nav.label,
|
|
52
|
+
category: nav.category || "Main Navigation",
|
|
53
|
+
description: `Page officielle ${nav.label} disponible sur le site.`,
|
|
54
|
+
paragraphs: [`Découvrez la solution ${nav.label} pour optimiser vos processus et vos résultats.`],
|
|
55
|
+
keyFeatures: [`Accès direct à ${nav.label}`, "Intégration transparente"],
|
|
56
|
+
});
|
|
57
|
+
count++;
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
// C. From Markdown / MDX Content Collections (Astro, Next.js Contentlayer)
|
|
63
|
+
if (config.contentCollections && Array.isArray(config.contentCollections)) {
|
|
64
|
+
for (const doc of config.contentCollections) {
|
|
65
|
+
const paragraphs = doc.content
|
|
66
|
+
.split("\n\n")
|
|
67
|
+
.map((p) => p.replace(/[#*`]/g, "").trim())
|
|
68
|
+
.filter((p) => p.length > 30)
|
|
69
|
+
.slice(0, 15);
|
|
70
|
+
|
|
71
|
+
this.registeredRoutes.set(doc.slug, {
|
|
72
|
+
path: doc.slug.startsWith("/") ? doc.slug : `/${doc.slug}`,
|
|
73
|
+
title: doc.title,
|
|
74
|
+
category: "Documentation & Features",
|
|
75
|
+
paragraphs,
|
|
76
|
+
description: paragraphs[0] || doc.title,
|
|
77
|
+
});
|
|
78
|
+
count++;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
return count;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
/**
|
|
86
|
+
* 2. Auto-Adapter for WordPress Menu & Pages
|
|
87
|
+
* In WordPress: pass result of wp_get_nav_menu_items() or get_pages()
|
|
88
|
+
*/
|
|
89
|
+
static registerWordPressMenu(menuItems: Array<{ title: string; url: string }>): number {
|
|
90
|
+
return this.registerManifest({
|
|
91
|
+
framework: "wordpress",
|
|
92
|
+
navMenuItems: menuItems.map((m) => ({ label: m.title, url: m.url })),
|
|
93
|
+
});
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
/**
|
|
97
|
+
* 3. Get all discovered seed public pages
|
|
98
|
+
*/
|
|
99
|
+
static getSeedRoutes(): PublicRouteItem[] {
|
|
100
|
+
return Array.from(this.registeredRoutes.values());
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
/**
|
|
104
|
+
* 4. Retrieve single route details
|
|
105
|
+
*/
|
|
106
|
+
static getRoute(pathOrSlug: string): PublicRouteItem | undefined {
|
|
107
|
+
return this.registeredRoutes.get(pathOrSlug);
|
|
108
|
+
}
|
|
109
|
+
}
|