Erro ao compilar a versão mais recente

Olá. Estou recebendo o seguinte erro ao executar ./installer rebuild web_only nas versões mais recentes do Discourse.

fs.js:114
    throw err;
    ^

Error: ENOENT: no such file or directory, open 'root='/assets',url='/assets/vendor-4681e47c140b5a5bea2bfb1fec89365858288a8ea0c21979c0167ad9b570ee3d.js.map''
    at Object.openSync (fs.js:438:3)
    at Object.writeFileSync (fs.js:1189:35)
    at done (/usr/lib/node_modules/uglify-js/bin/uglifyjs:516:20)
    at cb (/usr/lib/node_modules/uglify-js/bin/uglifyjs:324:39)
    at /usr/lib/node_modules/uglify-js/bin/uglifyjs:391:9
    at FSReqWrap.readFileAfterClose [as oncomplete] (internal/fs/read_file_context.js:53:3)
rake aborted!
Errno::ENOENT: No such file or directory @ rb_file_s_size - /var/www/discourse/public/assets/vendor-4681e47c140b5a5bea2bfb1fec89365858288a8ea0c21979c0167ad9b570ee3d.js
/var/www/discourse/lib/tasks/assets.rake:268:in `size'
/var/www/discourse/lib/tasks/assets.rake:268:in `block (4 levels) in <top (required)>'
/var/www/discourse/lib/tasks/assets.rake:159:in `block in concurrent?'
/var/www/discourse/lib/tasks/assets.rake:259:in `block (3 levels) in <top (required)>'
/var/www/discourse/lib/tasks/assets.rake:250:in `each'
/var/www/discourse/lib/tasks/assets.rake:250:in `block (2 levels) in <top (required)>'
/var/www/discourse/lib/tasks/assets.rake:159:in `concurrent?'
/var/www/discourse/lib/tasks/assets.rake:247:in `block in <top (required)>'
/var/www/discourse/vendor/bundle/ruby/2.6.0/gems/rake-13.0.1/exe/rake:27:in `<top (required)>'
/usr/local/bin/bundle:23:in `load'
/usr/local/bin/bundle:23:in `<main>'
Tasks: TOP => assets:precompile
(See full trace by running task with --trace)
I, [2019-12-11T22:53:15.806396 #18]  INFO -- : Downloading MaxMindDB...
Compressing Javascript and Generating Source Maps



FAILED
--------------------
Pups::ExecError: cd /var/www/discourse && su discourse -c 'bundle exec rake assets:precompile' failed with return #<Process::Status: pid 17151 exit 1>
Location of failure: /pups/lib/pups/exec_command.rb:112:in `spawn'
exec failed with the params {"cd"=>"$home", "hook"=>"assets_precompile", "cmd"=>["su discourse -c 'bundle exec rake assets:precompile'"]}
f565d457b97d7ff12a258b03a456563a5a0e928c707c70e194ef88ba170aaf3a
** FAILED TO BOOTSTRAP ** please scroll up and look for earlier error messages, there may be more than one

Desativei todos os plugins, mas o problema persiste. Alguém pode ajudar a entender o que está acontecendo?

Já vimos isso em outro lugar antes.

Pode tentar

./launcher cleanup
git pull
./launcher rebuild app

Se isso não funcionar, tente remover todos os containers na máquina e todas as imagens.

Obrigado pela resposta rápida, @sam. Vou tentar isso.

Uma pergunta rápida. O “git pull” que estou assumindo puxa a versão mais recente do discourse-docker, certo?

Em geral, é necessário atualizar o discourse-docker e o discourse ao mesmo tempo?

Atualmente, não tenho o discourse-docker controlado pelo git. Em vez disso, baixo uma revisão específica do discourse-docker (como um arquivo Zip) ao configurar o servidor e fixo a versão do discourse em um commit específico durante a implantação do discourse.

O motivo pelo qual faço isso é tentar tornar a construção repetível, ou seja, executar o mesmo comando com a mesma configuração + fonte em dois momentos diferentes deve produzir o mesmo artefato. Em geral, isso é uma boa ideia e me salvou de muitos pesadelos operacionais com outros softwares ao longo dos anos :wink: Isso porque dá a você a capacidade de reverter para uma configuração conhecida como boa.

No entanto, acho que estou nadando contra a maré aqui com o discourse, pois parece querer puxar as versões mais recentes de várias partes do software durante a construção. Estou começando a me perguntar se minhas tentativas de tornar a construção repetível estão, na verdade, me prejudicando?

Palavras muito verdadeiras. Você entrou em um estado totalmente insustentável com essa gambiarra :flushed_face:

Recomendo que você puxe a versão mais recente do git o mais rápido possível.

Imagens Docker antigas da base do Discourse são incompatíveis com o Discourse atual, além de faltarem muitas correções de segurança.

Obrigado, @sam. Fiz isso e agora consigo compilar a nova versão. Felizmente, tudo isso estava na versão beta, então não houve danos :slight_smile: No entanto, não tenho certeza se é “malabarismo técnico” querer uma compilação repetível :thinking:

O que estou tentando alcançar aqui é a capacidade de reverter para uma versão conhecida como boa. Suponha que eu execute ./launcher rebuild app no tempo t1 e o Discourse funcione. Em seguida, executo ./launcher rebuild app no tempo t2 e algo dá errado. Como faço para retornar o software à versão anterior? Acredito que poderia aceitar o fato de a compilação não ser repetível, desde que pudesse reverter para um estado conhecido como bom. Como o launcher já criou uma imagem Docker funcional no tempo t1, é possível instruí-lo a usar uma imagem específica, em vez da imagem defeituosa criada no tempo t2?

Alguma ideia?

Desculpe se me desviei um pouco do tópico; posso republicar se preferir.

Se você deseja builds reproduzíveis, é necessário fixar sua versão do Discourse em um SHA específico por meio da configuração do seu contêiner, bem como de cada plugin.

Isso significa que você deixará de receber correções para o Discourse, correções de segurança para a imagem do Docker e assim por diante, mas a build será bastante reproduzível.

Você também pode precisar alterar os modelos para fossilizar certos componentes e nunca receber atualizações de segurança para dependências do apt.

Ok, já fixei a versão do Discourse em um commit específico e também posso fazer isso para os plugins. Mas, se eu não fixar também o discourse-docker, isso não resultará em uma situação onde o discourse-base é atualizado a cada build, mas o Discourse não? Isso não causará uma incompatibilidade semelhante, só que ao contrário (porque o discourse-base ficará à frente do Discourse)?

Estou confuso: como esse erro apareceu se o Discourse está fixado em uma versão antiga?

Se o NGINX tem uma vulnerabilidade crítica, você deseja que ela seja corrigida?

O erro apareceu quando atualizei a versão fixada do Discourse de 2.4.0.beta2 para 2.4.0beta8.

Claro que gostaria que vulnerabilidades críticas em sistemas de software dependentes fossem corrigidas ao executar uma nova build! Parece fantástico!

No entanto, também gostaria de poder fazer rollback caso a nova versão apresente problemas :slight_smile:

Deixe-me apresentar um exemplo concreto:

Suponha que minha configuração esteja no estado atual:

discourse: 2.4.0beta2 (fixado em web_only.yml)

Executo ./launcher rebuild web_only e tudo funciona.

Agora meu sistema está neste estado:

discourse: 2.4.0beta2
discourse-docker: LATEST-AT-TIME-T1

Então, altero minha configuração para este estado:

discourse: 2.4.0beta8 (fixado em web_only.yml)

Executo ./launcher rebuild web_only e algo quebra.

Meu sistema agora está neste estado:

discourse: 2.4.0beta8
discourse-docker: LATEST-AT-TIME-T2

Agora, quero voltar para a versão anterior para que tudo volte a funcionar. Então, altero a versão fixada do Discourse para 2.4.0beta2 e faço uma nova build. No entanto, ao executar ./launcher rebuild web_only, o sistema agora está neste estado:

discourse: 2.4.0beta2
discourse-docker: LATEST-AT-TIME-T2

Embora a versão fixada do Discourse seja a mesma, a versão do discourse-base (e o restante do discourse-docker, templates, o próprio ./launcher etc.) será diferente agora. Portanto, não estarei retornando a um estado conhecido como estável, e temo que a build nem sequer funcione.

Desculpe se estou sendo lento aqui; tudo o que quero é ter a capacidade de voltar ao estado seguro caso haja problemas durante uma atualização. Talvez executar novamente ./launcher rebuild web_only não seja o caminho certo para fazer rollback aqui? Para outros sistemas que implanto, eu simplesmente implantaria uma imagem Docker anterior. Existe alguma maneira de instruir o launcher a fazer isso?

Sim, você precisa repensar seu processo aqui. Nossas migrações de banco de dados não são reversíveis.

Se quiser testar uma atualização sem comprometer, você precisa operar em um sandbox de staging.

Sim, entendo que é difícil reverter uma migração de banco de dados. O Discourse claramente não foi construído pensando no meu tipo de estratégia de gerenciamento de lançamentos e implantações. Devo parar de nadar contra a maré aqui.

Tenho um ambiente de staging. Então, vou simplesmente abandonar qualquer ideia de build e implantação repetíveis, testar no staging e depois torcer para tudo dar certo ao migrar para a produção.

Obrigado pela ajuda, @sam