Hooks y búsqueda en vivo

Además de los helpers integrados, el asistente expone unos cuantos hooks: helpers cuyo comportamiento por defecto no hace nada, así que el widget se comporta exactamente igual que antes hasta que los sobrescribes. Se sobrescriben igual que cualquier helper (en settings.extensions.helpers, o asignando skdwn.instance.helpers.<name> en tiempo de ejecución desde la página que lo integra). El núcleo los llama en momentos concretos, así que no tienes que conectar nada en una plantilla.

Hooks de eventos

HookSe disparaRecibe
onQuerySubmitted(query)Justo después de que el usuario envíe una pregunta.query: el texto enviado.
onResponseReceived(result)Cuando llega una respuesta.result: { query, reply, references }.
onFormSubmitted(formId, values)Después de enviar un formulario.formId y el objeto values enviado.

No devuelven nada: úsalos para efectos secundarios como analítica, tu propia interfaz o avisar a la página anfitriona. Por ejemplo, para enviar cada pregunta y respuesta a tu herramienta de analítica:

// settings.extensions.helpers
{
  onQuerySubmitted: (query) => window.analytics?.track('assistant_question', { query }),
  onResponseReceived: (result) =>
    window.analytics?.track('assistant_answer', {
      query: result.query,
      sources: (result.references || []).length,
    }),
  onFormSubmitted: (formId, values) =>
    window.analytics?.track('assistant_form', { formId, ...values }),
}

Por defecto no hacen nada

Cada hook viene como una función vacía, así que si no lo tocas no cambia nada. Solo pagas por lo que sobrescribes.

Búsqueda en vivo: searchProvider

searchProvider convierte el cuadro de búsqueda en un cuadro de sugerencias instantáneas: mientras el usuario escribe, el asistente llama a tu proveedor (con debounce) y muestra lo que devuelva como un desplegable bajo el cuadro, antes de que llegue a enviar una consulta completa. Está desactivado hasta que aportas uno.

Contrato

// (query: string, ctx: { assistantId }) => Promise<Item[]> | Item[] | undefined
searchProvider: async (query) => {
  const res = await fetch(`https://example.com/search?q=${encodeURIComponent(query)}`);
  const rows = await res.json();
  return rows.map((r) => ({
    title: r.name,        // shown text (and the query run if the row has no url)
    url: r.href,          // optional — see below
    summary: r.excerpt,   // optional secondary line
    image: r.thumbnail,   // optional thumbnail
    metadata: { price: r.price }, // optional free-form, passed to the template
  }));
}

Cada elemento es { title, url?, summary?, image?, metadata? }:

  • title: el texto que se muestra y la consulta que se ejecuta al pulsar una fila

sin URL (o su botón Ask).

  • url: opcional. Si está → la fila es un enlace y al pulsarla se navega (en la misma pestaña).

Si no está → al pulsar la fila se ejecuta el título como consulta.

  • summary: segunda línea opcional.
  • image: miniatura opcional.
  • metadata: objeto libre opcional (precio, distintivos, valoración…). El elemento

completo se pasa a la plantilla suggestion, así que todo lo que pongas aquí está disponible cuando cambies el estilo de las filas.

Lo que ve el usuario

  • Mientras el proveedor se ejecuta, se muestra un esqueleto de carga en el

desplegable, para que el cuadro nunca quede vacío.

  • Cada fila tiene además un botón "Ask" que abre el asistente con el título de esa

fila como consulta: útil para convertir un resultado en una pregunta más completa.

  • El desplegable se cierra cuando el usuario hace clic fuera o abre el overlay.

Limita los resultados con settings.suggestionsLimit (por defecto 5). Es un valor solo de configuración: defínelo en la configuración del asistente; no hay control en la interfaz.

Cambia el estilo de las filas sobrescribiendo la plantilla suggestion (una fila); el contenedor exterior suggestions no cambia. El elemento completo está disponible como item, así que puedes mostrar tu metadata:

{% comment %} settings.extensions.templates.suggestion {% endcomment %}
<div class="skdwn-suggestion-row" role="option">
  <a class="skdwn-suggestion" href="{{ item.url }}" onclick="skdwn.instance.helpers.dismissSuggestions()">
    <span class="skdwn-suggestion-text">
      <span class="skdwn-suggestion-title">{{ item.title | escape }}</span>
      {% if item.metadata.price %}<span class="skdwn-suggestion-summary">{{ item.metadata.price }}</span>{% endif %}
    </span>
  </a>
  <button type="button" class="skdwn-suggestion-ask" data-query="{{ item.title | escape }}"
          onclick="skdwn.instance.helpers.askSuggestion(this)">{{ 'ask' | t: 'Ask' }}</button>
</div>

Envía la identidad del visitante a tu servicio de búsqueda

Un searchProvider se ejecuta en el navegador, así que puede llamar a cualquier endpoint al que llegue la página. Si tu búsqueda necesita el usuario que ha iniciado sesión, pasa un token mediante startOptions.params y léelo desde tu proveedor: el mismo mecanismo que usan los servicios vinculados.

Profundiza

Contacto

¿Necesitas más ayuda?

Cuéntanos qué quieres que responda el asistente de tu web. Te ayudaremos a definir el contenido, los controles y el plan de lanzamiento adecuados.