Eu administro uma instalação do Discourse auto-hospedada (2026.5.0-latest). Hoje, tentei ativar o YJIT. Adicionei "templates/enable-ruby-yjit.yml" ao containers/app.yml e reconstruí o aplicativo.
Após a conclusão da reconstrução, algo interessante aconteceu. Dentro do contêiner Docker, executei env | grep RUBY_YJIT_ENABLE e obtive RUBY_YJIT_ENABLE=1. Até aqui, tudo bem. Mas, em seguida, executei sudo -u discourse RAILS_ENV=production bundle exec rails runner 'puts "YJIT enabled: #{RubyVM::YJIT.enabled?}"; puts RUBY_DESCRIPTION'… e obtive:
Portanto, o YJIT não foi ativado, apesar de ter adicionado o modelo enable-ruby-yjit.yml. Então, quando executei sudo -u discourse RAILS_ENV=production bundle exec rails runner 'puts "GlobalSetting.yjit_enabled=#{GlobalSetting.yjit_enabled}"', obtive GlobalSetting.yjit_enabled= — um valor nil!
De qualquer forma, depois de mexer um pouco mais nisso, finalmente consegui ativar o YJIT adicionando o seguinte ao containers/app.yml:
env:
DISCOURSE_YJIT_ENABLED: true
Tenho certeza de que há um bug em algum lugar (GlobalSetting.yjit_enablednão deveria nunca retornar nil), mas definir a variável de ambiente funcionou, e espero que alguém que esteja pesquisando no Google sobre isso encontre este tópico.
Isso não é um diagnóstico equivocado? Você está verificando o ENV de um novo processo Ruby recém-criado, em vez do que está executando o servidor web real.
Se você inspecionar /proc/<pid>/environ do processo mold do Pitchfork, verá a variável de ambiente YJIT lá.
Observar a presença de uma variável de ambiente não diz nada sobre se o Ruby está atualmente sendo executado com o YJIT ativado. Neste caso específico, a variável de ambiente está definida, mas algo mais estava sobrescrevendo a variável que o Rails usa para ativar (ou desativar) o YJIT na inicialização. Não há outra explicação para o fato de GlobalSetting.yjit_enabled= retornar nil, mesmo em uma nova instância do Rails. Também não há motivo para que o YJIT seja desativado em uma nova instância do Rails.
Após adicionar a variável de ambiente DISCOURSE_YJIT_ENABLED ao meu containers/app.yml,
Isso está errado. No nível do Ruby, a variável de ambiente é um dos alternadores oficiais; consulte a documentação oficial do Ruby sobre isso aqui:
Isso está errado, pois DISCOURSE_YJIT_ENABLED apenas alimenta GlobalSetting.yjit_enabled → config.yjit em config/application.rb. O Rails usa isso para habilitar o YJIT se ele ainda não estiver ativo. Ele não desabilita um YJIT já habilitado. Portanto, quando a variável de ambiente está definida, DISCOURSE_YJIT_ENABLED não tem nenhuma função.
Para provar ainda mais meu ponto, escrevi um plugin que retorna se o YJIT está habilitado no meu processo web:
Uau! Então você está dizendo que podemos usar de forma confiável a variável de ambiente para detectar se o YJIT está ativado! Eu não sabia disso; obrigado pelo link para a documentação do Ruby.
Estou um pouco confuso sobre algo, porém. Como é possível que env | grep RUBY_YJIT_ENABLE retorne RUBY_YJIT_ENABLE=1, mas uma nova instância do Rails no mesmo container, quando solicitada a imprimir #{RubyVM::YJIT.enabled?}, retorne false? Não deveria retornar true, já que, como você mencionou, essa variável de ambiente funciona no nível do Ruby?
Você provavelmente está muito ocupado e isso não deve importar, então não há necessidade de responder. Deveria ser capaz de resolver isso no meu próprio servidor. Por acaso, você poderia me passar o seu plugin? Quero uma maneira de ter certeza de que meu servidor Discourse está rodando em uma versão do Ruby com o YJIT ativado.
Vou marcar sua resposta como solução depois de replicar.
Peço desculpas por ter desperdiçado seu tempo e marquei sua resposta como a solução. Desculpe pelo ocorrido. Obrigado por investigar e por ter se dado ao trabalho de responder.