Recolher opiniões da página
Envolve o DuxtPageFeedback e guarda a resposta onde a tua analítica já vive.
Cada página de documentação termina com «Esta página foi útil?», e a camada não faz nada com a resposta: mantém-na no estado do próprio componente durante a visita, emite um evento e não guarda nada. Envolver o componente é a forma de a resposta chegar até ti.
Passos
- Envolve o componente da camada com o nome dele. O Nuxt resolve o teu
ficheiro primeiro, por isso
app/components/DuxtPageFeedback.vueno teu projeto substitui o da camada — e o alias@duxtcontinua a alcançar o original pelo caminho, de modo que o invólucro mantém a marcação, as traduções e a reposição na navegação da camada:<script setup lang="ts"> import DuxtPageFeedbackBase from '@duxt/components/DuxtPageFeedback.vue'; const route = useRoute(); // O evento transporta a resposta e mais nada — a página a que pertence és tu // que a lês, e `fullPath` é a que mantém os prefixos de locale, repositório e // versão sob os quais a resposta foi realmente dada. async function onFeedback(helpful: boolean) { await $fetch('/api/feedback', { method: 'POST', body: { path: route.fullPath, helpful } }); } </script> <template> <DuxtPageFeedbackBase @feedback="onFeedback" /> </template> - Dá à resposta um sítio onde aterrar. Uma rota tua, para que o browser do
leitor nunca fale com um terceiro que não escolheste:
export default defineEventHandler(async (event) => { const { path, helpful } = await readBody(event); // O teu armazenamento, a tua analítica, a tua fila. await recordFeedback({ path, helpful }); return { ok: true }; });
Uma chamada de analítica do lado do cliente funciona da mesma maneira — substitui o$fetchdo invólucro pelo que o SDK do teu fornecedor expuser. - Compila de novo e responde à pergunta uma vez, depois verifica se a resposta chegou com o caminho que esperavas — sob um prefixo de versão, e não apenas no URL nu.
Apresentar o teu próprio controlo
O evento mantém os botões da camada. Para os substituir, usa antes o slot por omissão: expõe o mesmo estado a partir do qual o componente é apresentado, para que a reposição na navegação e o estado de «obrigado» continuem a ser tarefa da camada.
<script setup lang="ts">
import DuxtPageFeedbackBase from '@duxt/components/DuxtPageFeedback.vue';
</script>
<template>
<DuxtPageFeedbackBase v-slot="{ answered, answer }">
<form v-if="answered === undefined" @submit.prevent="answer(true)">
<label>
Diz-nos o que falta
<textarea name="comment" />
</label>
<button type="submit">Enviar</button>
</form>
<p v-else>Obrigado.</p>
</DuxtPageFeedbackBase>
</template>
answer(helpful) define o estado e emite o evento, por isso um slot e um
ouvinte compõem-se: pendura o teu formulário no slot e mantém o manipulador
@feedback do passo 1 para entregar o que ele recolheu.
Nada no componente identifica um visitante, e assim fica de propósito. Se contas respostas por página, conta-as como respostas — um browser que recarrega e responde outra vez é uma segunda resposta, não um segundo leitor, e transformar uma coisa na outra é uma questão de consentimento que a tua política de privacidade tem de responder primeiro.
Porque a camada não guarda nada
Um tema de documentação que telefonasse para casa por omissão teria de escolher um destino para os leitores de outra pessoa, e não há nenhum defensável: a camada não sabe onde vive a tua analítica nem o que promete a tua política de privacidade. Entregar a pergunta com um evento e sem backend mantém a decisão onde pertence — a mesma razão por que a linha legal do rodapé e as ligações ao repositório são entregues vazias (ADR 0005).
Lista de verificação
- O invólucro apresenta o componente da camada em vez de o reimplementar
- A resposta é enviada com o caminho em que foi dada, prefixos incluídos
- O destino é teu — uma rota, uma fila ou um SDK que escolheste
- Nada na carga útil identifica o leitor