From b4fdbb9f208ba1715c107717c9656adb7fbd6f12 Mon Sep 17 00:00:00 2001 From: ManUtopiK <emmanuel.salomon@gmail.com> Date: Fri, 17 Sep 2021 19:27:47 +0200 Subject: [PATCH] Improve lexique search terms and added synonyms --- components/global/Lexique.vue | 65 ++++++++++++++++++++-------------- components/page/PageBottom.vue | 2 +- content/lexique/blockchain.md | 6 ++++ content/lexique/junistes.md | 2 +- content/lexique/noeud.md | 7 ++-- content/lexique/trm.md | 19 +++++----- nuxt.config.js | 46 +++++++++++++++++++++++- pages/lexique/_slug.vue | 29 +++++++-------- static/admin/config.yml | 1 + 9 files changed, 121 insertions(+), 56 deletions(-) create mode 100644 content/lexique/blockchain.md diff --git a/components/global/Lexique.vue b/components/global/Lexique.vue index c34f43c3..bb88a3d7 100644 --- a/components/global/Lexique.vue +++ b/components/global/Lexique.vue @@ -1,27 +1,30 @@ <template> <span class="tooltip-box relative" - :class="page && 'cursor-pointer'" - v-on="page ? { click: onClick } : {}" + :class="document && 'cursor-pointer'" + v-on="document ? { click: onClick } : {}" > - <abbr :aria-label="page ? page.title : title" :title="page ? '' : null"> + <abbr + :aria-label="document ? document.title : title" + :title="document ? '' : null" + > <slot /> </abbr> <client-only> <div - v-if="page" - class="tooltip absolute bg-gray-200 invisible opacity-0 left-1/2 px-4 py-2 rounded-xl shadow-lg text-gray-600 text-sm z-50" + v-if="document" + class="tooltip absolute bg-blue-100 border-blue-200 border invisible opacity-0 left-1/2 px-4 py-3 rounded-xl shadow-2xl text-gray-600 text-sm z-50" > <span class="triangle absolute"></span> - <span v-if="title" class="block mb-2 uppercase"> - {{ title }} + <span class="block font-bold text-lg uppercase"> + {{ document.title }} : </span> - <span>{{ page.description }}</span> + <span>{{ document.description }}</span> - <span class="block font-extralight mt-2 text-xs"> + <span class="block font-light mt-3 text-xs text-purple-800"> {{ $t('lexique.tooltipReadmore') }} </span> </div> @@ -40,23 +43,24 @@ export default { }, data() { return { - page: null, + document: null, } }, async fetch() { if (this.computedTitle) { - try { - this.page = await this.$content( - 'lexique', - this.computedTitle.toLowerCase() - ) - .only(['title', 'description']) - .fetch() - } catch (e) { - // eslint-disable-next-line no-console - console.warn( - `lexique term '${this.computedTitle}' not found in /content/lexique/ from file ${this.$parent.fileUrl}` - ) + const term = this.computedTitle.toLowerCase() + const results = await this.$content('lexique') + .where({ + $or: [ + { title: { $regex: [`^${term}$`, 'i'] } }, // case insensitive + { synonyms: { $contains: term } }, // search in synonyms + ], + }) + .limit(1) + .fetch() + + if (results.length) { + this.document = results[0] } } }, @@ -68,7 +72,7 @@ export default { }, methods: { onClick() { - this.$router.push(`/lexique/${this.computedTitle.toLowerCase()}`) + this.$router.push(this.document.path) }, }, } @@ -92,11 +96,20 @@ abbr { opacity: 1; } .triangle { - border-width: 0 6px 6px; + border-width: 0 10px 10px; border-color: transparent; - border-bottom-color: rgba(229, 231, 235, var(--tw-bg-opacity)); - top: -6px; + border-bottom-color: #bfdbfe; + top: -10px; left: 50%; transform: translateX(-50%); } +.triangle:before { + content: ''; + position: absolute; + border-width: 0 10px 10px; + border-color: transparent; + border-bottom-color: #dbeafe; + top: 2px; + left: -10px; +} </style> diff --git a/components/page/PageBottom.vue b/components/page/PageBottom.vue index 25f51118..39102ae9 100644 --- a/components/page/PageBottom.vue +++ b/components/page/PageBottom.vue @@ -6,7 +6,7 @@ </span> <a - :href="`admin/#/collections${document.dir}/entries/${document.slug}`" + :href="`/admin/#/collections${document.dir}/entries/${document.slug}`" target="_blank" rel="noopener noreferrer" class="hover:underline" diff --git a/content/lexique/blockchain.md b/content/lexique/blockchain.md new file mode 100644 index 00000000..7088615d --- /dev/null +++ b/content/lexique/blockchain.md @@ -0,0 +1,6 @@ +--- +title: Blockchain +description: Mode de stockage et de transmission de données sous forme de blocs + liés les uns aux autres et protégés contre toute modification. +--- +TODO: Expliquer le fonctionnement... \ No newline at end of file diff --git a/content/lexique/junistes.md b/content/lexique/junistes.md index db67751f..92ec3822 100644 --- a/content/lexique/junistes.md +++ b/content/lexique/junistes.md @@ -1,7 +1,7 @@ --- title: Junistes description: Les utilisateurs de la june -synonym: +synonyms: - juniste - jüniste - jünistes diff --git a/content/lexique/noeud.md b/content/lexique/noeud.md index dd3895bc..928f80db 100644 --- a/content/lexique/noeud.md +++ b/content/lexique/noeud.md @@ -1,9 +1,10 @@ --- -title: "Nœud" +title: Nœud description: Un nœud est un ordinateur qui fait fonctionner la monnaie. -synonym: - - nœud +synonyms: - noeud + - nœuds + - noeuds --- Les nœuds sont les ordinateurs équipés du logiciel Duniter qui gère la <lexique>blockchain</lexique> de la Ğ1. Ces ordinateurs sont mis à disposition par des utilisateurs de la Ğ1. diff --git a/content/lexique/trm.md b/content/lexique/trm.md index 0ed907dc..475c9afe 100644 --- a/content/lexique/trm.md +++ b/content/lexique/trm.md @@ -1,16 +1,19 @@ --- -title: TRM -description: Théorie Relative de la Monnaie +title: Théorie Relative de La monnaie +description: Théorie monétaire utilisé comme fondement de la monnaie libre +synonyms: + - trm --- ## Une Théorie et un livre -La Théorie est décrite par Stéphane Laborde dans son livre *"la théorie relative de la monnaie"*. +La théorie est décrite par Stéphane Laborde dans son livre *"la théorie relative de la monnaie"*. ### La théorie -Basée sur 4 axiomes : les <lexique>4 libertés économiques</lexique>. -Avec un calcul mathématique, pour respecté ces 4 libertés la théorie décrit la création monétaire sous forme d'"un dividende universel tel que : **DU=c(M/N)**\ -Le Dividende Universel 'DU' est une portion 'c' de la masse monétaie par individu 'M/N' +Basée sur 4 axiomes : les <lexique>4 libertés économiques</lexique>.\ +Avec un calcul mathématique, pour respecter ces 4 libertés la théorie décrit la création monétaire sous forme d'un dividende universel tel que : **DU=c(M/N)**.\ +Le Dividende Universel 'DU' est une portion 'c' de la masse monétaire par individu 'M/N'. -### Le livre -Le livre est disponible en vente en ligne, mais également librement sur le site <http://trm.creationmonetaire.info/> Ou en pdf sur <https://www.econologie.com/fichiers/partager3/1319653067F3tO5k.pdf> \ No newline at end of file +### Le livre + +Le livre est disponible en vente en ligne, mais également librement sur le site <http://trm.creationmonetaire.info/> Ou en PDF sur <https://www.econologie.com/fichiers/partager3/1319653067F3tO5k.pdf> \ No newline at end of file diff --git a/nuxt.config.js b/nuxt.config.js index da11f698..fc2c354b 100644 --- a/nuxt.config.js +++ b/nuxt.config.js @@ -210,9 +210,53 @@ export default { return file.data = JSON.stringify(JSON.parse(file.data).ressources) }, - 'content:file:beforeInsert': (document) => { + async 'content:file:beforeInsert'(document) { if (document.extension === '.md') { + /* + * Add reading time + */ document.readingTime = require('reading-time')(document.text) + + /* + * Add lexique terms and check if terms exist + */ + // Search lexique terms + const lexiqueTerms = [ + ...document.text.matchAll( + /<lexique[>]([^<]*)<\/|<lexique\s+title="(.*)"/g + ), + ].map((match) => { + return (match[2] || match[1]).toLowerCase() // Priority for term in title="" + }) + + if (lexiqueTerms.length) { + // Add terms to document + document.lexiqueTerms = [...new Set(lexiqueTerms)] // remove duplicate + + const { $content } = require('@nuxt/content') + // Check if term exists + if ($content) { + for (let i = 0; i < document.lexiqueTerms.length; i++) { + const term = document.lexiqueTerms[i] + const lexique = await $content('lexique') + .where({ + $or: [ + { title: { $regex: [`^${term}$`, 'i'] } }, // case insensitive + { synonyms: { $contains: term } }, // search in synonyms + ], + }) + .limit(1) + .fetch() + + if (!lexique.length) { + // eslint-disable-next-line no-console + console.warn( + `Term "${term}" in file ${document.path}.${document.extension} doesn't exist` + ) + } + } + } + } } }, }, diff --git a/pages/lexique/_slug.vue b/pages/lexique/_slug.vue index 21bbf721..9e883d5c 100644 --- a/pages/lexique/_slug.vue +++ b/pages/lexique/_slug.vue @@ -12,7 +12,9 @@ <PageToc v-if="document.toc" :document="document" class="mb-8" /> <aside v-if="pagesWithTerm.length" class="mb-8"> - <h1 class="text-2xl">Pages contenant "{{ document.title }}"</h1> + <h1 class="text-xl uppercase text-gray-400 font-bold mb-2"> + Pages contenant "{{ document.title }}" + </h1> <nuxt-link v-for="(item, index) of pagesWithTerm" @@ -31,29 +33,24 @@ </template> <script> -import { reduceResults, headDocument as head } from '~/libs/helpers' +import { headDocument as head } from '~/libs/helpers' export default { name: 'LexiqueSlug', async asyncData({ $content, params, error }) { try { const document = await $content('lexique', params.slug).fetch() - - const pagesWithSlot = await $content({ deep: true }) - .search(`<lexique>${params.slug}</lexique>`) - .fetch() - const pagesWithProp = await $content({ deep: true }) - .search(`<lexique title="${params.slug}">`) + const synonyms = document.synonyms || [] + + const pagesWithTerm = await $content({ deep: true }) + .where({ $and: [{ extension: '.md' }, { dir: { $ne: '/ui' } }] }) + .where({ + lexiqueTerms: { + $containsAny: [document.title.toLowerCase(), ...synonyms], + }, + }) .fetch() - // Merge and deduplicate - const slugs = new Set(pagesWithSlot.map((item) => item.slug)) - const results = [ - ...pagesWithSlot, - ...pagesWithProp.filter((item) => !slugs.has(item.slug)), - ] - const pagesWithTerm = reduceResults(results) - return { document, pagesWithTerm } } catch (err) { return error({ statusCode: 404, message: err.message }) diff --git a/static/admin/config.yml b/static/admin/config.yml index 6a78fe35..654bc122 100644 --- a/static/admin/config.yml +++ b/static/admin/config.yml @@ -75,6 +75,7 @@ collections: fields: - { label: Titre, name: title, widget: string } - { label: Résumé, name: description, widget: string, hint: Le résumé est affiché dans le lexique et dans les bulles d'info. } + - { label: Synonymes, name: synonyms, widget: list, hint: Synonymes du titre. Séparé par des virgules. Insensible à la casse. } - { label: Définition, name: body, widget: markdown } - name: ressources -- GitLab