ID do tópico como uma variável?

Uma palavra comum é o oposto do que eu quero. Eu não quero que meus resultados de pesquisa contenham TODOS os tickets, eu quero uma maneira de pesquisar um ticket específico. É por isso que o ID do tópico seria ideal. Eles são gerados automaticamente e são únicos.

Não, acho que o código que estou usando também era originalmente do awesomerobot, mas não consigo mais encontrar sua origem.
Eu prefiro a colocação do que estou usando atualmente do que aquele bloco sob o texto.

Bem, eu não posso fazer isso. Talvez você possa.
Eu tenho um certo conjunto de habilidades. Codificação não está entre elas.

Então, talvez você devesse mover este tópico para Marketplace ou Feature.

1 curtida

Você me entendeu mal. Eu quis dizer ter uma palavra comum incluindo o parâmetro topic:id, para que apenas resultados desse tópico apareçam. A palavra comum remove a necessidade de alterar palavras como ‘oi’ e ‘olá’.

@tknospdr @pfaffman Criei rapidamente um componente que permite inserir o ID do tópico e ir até ele.

Crie um novo componente e adicione isto à aba JS sob o botão Editar CSS/HTML[1]:

import { apiInitializer } from "discourse/lib/api";
import Component from '@glimmer/component';
import { action } from "@ember/object";
import Form from "discourse/components/form";
import DiscourseURL from "discourse/lib/url";

export default apiInitializer((api) => {
    api.renderBeforeWrapperOutlet("full-page-search-filters",
        class GoToTopic extends Component {
            @action
            handleSubmit(data) {
                DiscourseURL.routeTo(`/t/${data.id}`);
            }

            <template>
                <div class="topic-id-go-to" style="margin-top: 1em;">
                    <Form @onSubmit={{this.handleSubmit}} as |form|>

                      <form.Field @name="id" @title="Topic id" as |field|>
                        <field.Input @type="number" @validation="required" />
                      </form.Field>

                      <form.Submit />
                    </Form>
                </div>
            </template>
        }
    );
});

Isto adiciona um campo de entrada à página de Pesquisa:


O botão Submit serve para ir ao tópico[2]; ele não afeta os resultados da pesquisa.

Espero que ajude!


  1. Minha primeira vez usando FormKit, é muito legal! ↩︎

  2. Não consegui mudar o texto do botão, pois isso exigiria locais… que precisariam de um repositório TC completo, o que pode ser exagero :person_shrugging:. ↩︎

1 curtida

Obrigado @NateDhaliwal, aprecio o esforço.
Criei o componente, colei o código na aba JS. Certifiquei-me de que estava ativo no meu tema, mas sem sucesso.
Esta é a aparência da minha página de pesquisa:

1 curtida

Configurei isso no meu site para brincar e parece funcionar, no entanto, recebo este aviso que me deixa um pouco hesitante:

Algum erro no console do navegador?

Este é o único erro:

E eu acho que é para o JS mostrar o ID do tópico, não a busca. Ele não aparece, exceto nas páginas que reservei para esse elemento.

Desativei e reativei o componente Advanced Search Banner, e agora ele está funcionando.
:man_shrugging:

1 curtida

Certo, um resumo da situação como ela se encontra atualmente:

  1. Temos uma solução funcional. Embora seja um pouco inelegant, ela atenderá às minhas necessidades até o momento em que pudermos pesquisar o ID do tópico diretamente na caixa de pesquisa padrão.
  2. O código atual sugerido por @awesomerobot parece funcionar, mas dispara o aviso que postei acima.
    2a. Quando removi o código original que eu estava usando para exibir o ID do tópico, esse aviso desapareceu…
  3. Quando você escolhe uma solução, o código para exibir o ID do tópico aparece tanto na postagem original quanto na solução. Há alguma maneira de levar isso em conta e impedir que ele apareça lá?
  4. Melhorei um pouco o CSS, agora tenho uma “pílula” em cada resposta em cada thread nas categorias especificadas em que estou usando isso. Suponho que a resposta será desmelhorar, mas se alguém souber de outra maneira, prefiro mantê-la, acho que fica bonita como está.

@awesomerobot
Seu código funciona muito bem, mas parece que quaisquer decorações CSS além do texto aparecem em todas as postagens após a primeira como um espaço vazio formatado como o CSS indica.

Desligue o bloco em linha e você terá uma barra de cor de largura total.
Mude a cor de fundo e a pílula muda de cor
etc…

Com base no que você escreveu, parece que você disse para mostrá-lo apenas na primeira postagem, mas isso afeta apenas o texto. Há algo mais que podemos fazer para remover o elemento em todas as postagens adicionais?

1 curtida

Ok, como eu disse, não sou programador, mas sou muito bom em fazer perguntas ao Grok. Aqui está um código que cuida de ambos os problemas.

  1. Chega de bolhas CSS vazias nas respostas 2 a X.
  2. Chega de duplicação do ID do tópico em soluções citadas.

Talvez mais ninguém no planeta se importe, mas esta parece ser uma boa maneira de ajudar a rastrear tópicos para aqueles de nós que usam o Discourse como um sistema de tickets.

import { apiInitializer } from "discourse/lib/api";
import Component from "@glimmer/component";

class TopicIdentifier extends Component {
  get topicId() {
    return this.args.post?.topic?.id;
  }

  get shouldShow() {
    const firstPost = this.args.post?.post_number === 1; // first post in topic
    const desiredCategories = [9, 23]; // a comma separated list of category IDs you want this to appear in 
    const isInCategory = desiredCategories.includes(
      this.args.post?.topic.category.id
    );

    return firstPost && isInCategory;
  }

  <template>
    {{#if this.shouldShow}}
      <!-- you can edit the content below, {{this.topicId}} is where the topic ID will be filled -->
      Issue Tracking # is
      {{this.topicId}} 
      <!-- you can edit the content above -->
    {{/if}}
  </template>
}

export default apiInitializer("0.8.40", (api) => {
  api.decorateCookedElement((element, helper) => {
```gjs
import { apiInitializer } from "discourse/lib/api";
import Component from "@glimmer/component";

class TopicIdentifier extends Component {
  get topicId() {
    return this.args.post?.topic?.id;
  }

  get shouldShow() {
    const firstPost = this.args.post?.post_number === 1; // first post in topic
    const desiredCategories = [9, 23]; // a comma separated list of category IDs you want this to appear in 
    const isInCategory = desiredCategories.includes(
      this.args.post?.topic.category.id
    );

    return firstPost && isInCategory;
  }

  <template>
    {{#if this.shouldShow}}
      <!-- you can edit the content below, {{this.topicId}} is where the topic ID will be filled -->
      Issue Tracking # is
      {{this.topicId}} 
      <!-- you can edit the content above -->
    {{/if}}
  </template>
}

export default apiInitializer("0.8.40", (api) => {
  api.decorateCookedElement((element, helper) => {
    // Only proceed if this is the first post and not inside a solution quote
    // Only proceed if this is the first post, not in a quote, and in the desired category
    const post = helper?.model;
    const desiredCategories = [9, 23]; // Match the categories from TopicIdentifier
    if (
    if (
      helper?.model?.post_number !== 1 ||
      !post ||
      post.post_number !== 1 ||
      !desiredCategories.includes(post.topic?.category?.id) || // Check category
      element.classList.contains("post__contents-cooked-quote") || // Check if the element itself is the quote content
      element.closest("aside.accepted-answer") || // Check for solution/quote wrapper
      element.closest(".quote") // Additional check for generic quotes
    ) {
      return;
    }

    const wrapper = document.createElement("div");
    wrapper.className = "tracking-id";

    helper?.renderGlimmer(
      wrapper,
      <template><TopicIdentifier @post={{helper.model}} /></template>
    );

    element.appendChild(wrapper);
  });
});
3 curtidas

Não consegui chegar a isso antes, mas fico feliz que você tenha descoberto! Isso parece uma solução razoável.

1 curtida

Sei que posso testar facilmente, mas você sabe de imediato se isso funcionaria se eu colocasse este JS e CSS em seu próprio componente, ou se ele tem que estar no tema em si?

Encontrei outra pequena anomalia. Eu estava vendo as bolhas de classe vazias na primeira postagem dos tópicos fora das 2 que eu queria, então tive que atualizar o código um pouco. Aqui está o produto final.

import { apiInitializer } from "discourse/lib/api";
import Component from "@glimmer/component";

class TopicIdentifier extends Component {
  get topicId() {
    return this.args.post?.topic?.id;
  }

  get shouldShow() {
    const firstPost = this.args.post?.post_number === 1; // primeira postagem no tópico
    const desiredCategories = [9, 23]; // uma lista separada por vírgulas de IDs de categoria onde você quer que isso apareça 
    const isInCategory = desiredCategories.includes(
      this.args.post?.topic.category.id
    );

    return firstPost && isInCategory;
  }

  <template>
    {{#if this.shouldShow}}
      <!-- você pode editar o conteúdo abaixo, {{this.topicId}} é onde o ID do tópico será preenchido -->
      Issue Tracking # é
      {{this.topicId}} 
      <!-- você pode editar o conteúdo acima -->
    {{/if}}
  </template>
}

export default apiInitializer("0.8.40", (api) => {
  api.decorateCookedElement((element, helper) => {
    // Apenas prossiga se esta for a primeira postagem e não dentro de uma citação de solução
    // Apenas prossiga se esta for a primeira postagem, não em uma citação, e na categoria desejada
    const post = helper?.model;
    const desiredCategories = [9, 23]; // Corresponde às categorias de TopicIdentifier
    if (
    if (
      helper?.model?.post_number !== 1 ||
      !post ||
      post.post_number !== 1 ||
      !desiredCategories.includes(post.topic?.category?.id) || // Verifica a categoria
      element.classList.contains("post__contents-cooked-quote") || // Verifica se o próprio elemento é o conteúdo da citação
      element.closest("aside.accepted-answer") || // Verifica o wrapper de solução/citação
      element.closest(".quote") // Verificação adicional para citações genéricas
    ) {
      return;
    }

    const wrapper = document.createElement("div");
    wrapper.className = "tracking-id";

    helper?.renderGlimmer(
      wrapper,
      <template><TopicIdentifier @post={{helper.model}} /></template>
    );

    element.appendChild(wrapper);
  });
});
      element.classList.contains("post__contents-cooked-quote") || // Verifica se o próprio elemento é o conteúdo da citação
      element.closest("aside.accepted-answer") || // Verifica o wrapper de solução/citação
      element.closest(".quote") // Verificação adicional para citações genéricas
    ) {
      return;
    }

    const wrapper = document.createElement("div");
    wrapper.className = "tracking-id";

    helper?.renderGlimmer(
      wrapper,
      <template><TopicIdentifier @post={{helper.model}} /></template>
    );

    element.appendChild(wrapper);
  });
});

E para responder à minha própria pergunta, movi todo o código para um novo componente de tema e tudo ainda funciona bem.