Alterando o bucket s3 para uploads

Olá!

Estamos migrando todos os nossos uploads/imagens entre dois serviços compatíveis com S3 (ambos são DigitalOcean Spaces, caso isso importe) e percebi que estamos presos em um estado bastante problemático.

Vou começar explicando como a migração foi feita:

  1. Clonamos/sincronizamos o bucket inicial para o novo bucket usando o rclone.
  2. Todas as referências na página Arquivos na administração do Discourse foram atualizadas para os novos endpoints.
  3. Foi executada uma re-bake.

Infelizmente, isso não fez o que queríamos, e agora todas as imagens estão “sumidas” do fórum. Elas ainda estão no bucket S3 (e, por sorte, também no antigo), mas nenhum post consegue encontrar sua respectiva imagem.

O tamanho do bucket é de cerca de 60 GB, então é (mesmo que não seja extremo) uma quantidade considerável de dados.

Reconstruí o container, tentei recuperar coisas do tombstone, fiz praticamente tudo que consegui pensar ou encontrar no fórum de suporte ou em tarefas rake.
Também tentei com uma substituição de banco de dados (via discourse remap).

Cada imagem aparece basicamente assim no conteúdo baked no momento:

<img src="https://xxxx.xxxxx.xx/images/transparent.png" alt="image" data-orig-src="upload://h8UudilPhVsGnNmvlJ5lQYEr8PT.jpeg" width="375" height="500">

O que me faz pensar que o b64-sha do link está quebrado ou que o sha da imagem mudou por algum motivo.

Alguém já fez isso antes? Todas as imagens estão perdidas para sempre? (sim, sim, tenho um backup e as imagens antigas, então sei que há um caminho).

Vale a pena mencionar que também tentei usar o URI do CDN fornecido para o bucket de espaços (com um rebake).

Saída de uploads ausentes:

rake posts:missing_uploads
Procurando por uploads ausentes em: default
Corrigindo uploads ausentes:
🚫
17075 uploads de posts estão ausentes.

16906 uploads estão ausentes.
1 de 16906 são uploads do esquema antigo.
14646 de 139801 posts foram afetados.

post_uploads possui 3448 entradas
optimized_images possui 25681 entradas
uploads possui 5764 entradas

Você pode ver Moving from one S3 bucket to another

Acho que tenho um rascunho de como fazer que tentarei postar amanhã.

Isso seria muito útil, mto obrigada!

Olá @Jite!

Veja se isso funciona para você. Se funcionar, vou criar um howto adequado.

Buckets antigos

Isso pressupõe que você possa instalar e configurar uma ferramenta para mover seus dados do seu bucket antigo para uma máquina local e, em seguida, fazer o mesmo do local para o novo bucket. Consulte aws cli sync (que pode ser configurado para buckets não-AWS) e gsutil rsync para obter informações. Se você tiver grandes quantidades de dados ou estiver migrando entre buckets do mesmo provedor, talvez queira investigar métodos que movam os dados diretamente entre os buckets.

Entre em um diretório adequado para um espaço de armazenamento temporário (por exemplo, mkdir temp-bucket; cd temp-bucket) antes de executar algo como o seguinte. Estes exemplos incluem as opções -n e --dry-run para mostrar o que acontecerá. Se parecer o que você deseja, execute o comando novamente sem essa opção.

Mover dados antigos do bucket antigo para o local

    gsutil  rsync -r -n  gs://=OLD= .

ou

    aws s3 sync s3://=OLD= .

Mover dados do local para o novo bucket

    gsutil rsync -r -n . gs://=NEW=

ou

    aws s3 sync . s3://=NEW=

Atualizar o banco de dados para usar o novo bucket

Você executará esses comandos no console do Rails. Para acessá-lo, faça:

cd /var/discourse
./launcher enter app
rails c

Para o novo bucket, faça o upload de uma imagem com a nova configuração e execute:

Upload.last.url

Você deverá ver algo como:

=> "//discourse-bucket.s3.dualstack.us-east-2.amazonaws.com/original/2X/7/12345fbea574afc4e02db80107e6682430aede2c.png"

Em seguida, extraia discourse-bucket.s3.dualstack.us-east-2.amazonaws.com para o novo bucket. Obtenha o hostname do bucket antigo da mesma forma a partir do exemplo acima.

Use isso para verificar se seus uploads estão onde você acha que estão:

Upload.order(Arel.sql('RANDOM()')).limit(10).pluck(:id, :url)

Agora, você atualizará o banco de dados para usar o novo bucket em vez do antigo. DbHelper.remap substituirá as ocorrências em todas as tabelas.

DbHelper.remap("//=OLDHOST=/","//=NEWHOST=/")

Migrar para a AWS pode exigir a limpeza do seu s3_endpoint.

NOTA: Se você tiver um s3_endpoint definido nas suas Configurações do Site no banco de dados e migrar para a AWS (onde nenhum endpoint é necessário), será necessário limpar essa configuração do site após construir o novo contêiner com as configurações atualizadas (ou após restaurar um banco de dados que tenha essa configuração definida).

Reassar posts que referenciam o bucket em vez da CDN do S3

Se você tiver posts que linkam diretamente para o novo bucket do S3 (talvez você não tivesse um s3_cdn_url definido antes), veja como reassar apenas os posts que precisam disso.

Obtenha os posts:

  posts=Post.where("cooked like '%=NEWHOST=%'")

Veja quantos:

  posts.count

Reassare esses posts:

  posts.each do |p| p.rebake! end

Ou, basta substituir o bucket pela CDN:

posts.each do |p|
  p.cooked.gsub!(/=NEWHOST=/,"=CDN=")
  p.save!
end

Obrigado pela resposta.

Basicamente, fiz o mesmo da última vez, mas tentei novamente. O problema é que posts.count retorna 0. Todos os posts têm o arquivo transparent.png no conteúdo processado (cooked) e contêm um hash no conteúdo não processado (uncooked).

Existe alguma maneira de fazer com que a imagem seja resolvida corretamente durante o bake?

Hmm. Certo. Essa mudança ‘cozida’ serve apenas para evitar a reimplementação. Se uma reimplementação não funciona, então há algo mais errado. Talvez os recursos não estejam onde o Discourse acha que estão?

Bem, é possível, mas a “migração” foi basicamente uma cópia 1:1 de todos os arquivos no bucket, hehe…

Então você pode substituir a URL antiga do bucket pela nova e funciona?

Os valores em Uploads parecem corretos?

Tenho um pouco de medo de que voltar ao bucket antigo possa iniciar um trabalho para mover tudo para o tombstone, já que agora eles são “antigos”, mas sim, o banco de dados parece apontar para as imagens corretas (nova localização). Basicamente, são apenas as postagens antigas que não resolvem para a imagem correta (acho que…).

Depois de executar a tarefa rake de recuperação do toombstone e, em seguida, a tarefa rake fix_missing_uploads, finalmente consegui fazê-lo começar a “corrigir” as imagens.
Parece que elas estão sendo baixadas e carregadas novamente, o que leva muito tempo e consome muitos recursos, mas, pelo menos, os usuários recuperarão suas imagens!

Obrigado pela ajuda @pfaffman :slight_smile: