Olá, este tópico fornece algum contexto sobre a migração que estou lentamente planejando e testando. Finalmente, tentei o importador Drupal na sexta-feira passada em um ambiente de teste VPS usando uma combinação de este e este. O importador ainda está em execução enquanto digito isso, então ainda não consegui testar a funcionalidade do site de teste, mas ele está prestes a terminar em breve.
O maior problema que estou enfrentando é um “valor de chave duplicado” em 8 nós aparentemente aleatórios (o equivalente a tópicos no Discourse) de um total de ~80.000 nós. Estes são os números nid específicos, caso haja algum bug de matemática muito estranho do tipo Y2K em jogo:
42081, 53125, 57807, 63932, 66756, 76561, 78250, 82707
Este mesmo erro sempre acontece nos mesmos nids ao reexecutar o importador:
Traceback (most recent call last):
19: from script/import_scripts/drupal.rb:537:in `<main>'
18: from /var/www/discourse/script/import_scripts/base.rb:47:in `perform'
17: from script/import_scripts/drupal.rb:39:in `execute'
16: from script/import_scripts/drupal.rb:169:in `import_forum_topics'
15: from /var/www/discourse/script/import_scripts/base.rb:916:in `batches'
14: from /var/www/discourse/script/import_scripts/base.rb:916:in `loop'
13: from /var/www/discourse/script/import_scripts/base.rb:917:in `block in batches'
12: from script/import_scripts/drupal.rb:195:in `block in import_forum_topics'
11: from /var/www/discourse/script/import_scripts/base.rb:224:in `all_records_exist?'
10: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activerecord-7.0.3.1/lib/active_record/transactions.rb:209:in `transaction'
9: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activerecord-7.0.3.1/lib/active_record/connection_adapters/abstract/database_statements.rb:316:in `transaction'
8: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activerecord-7.0.3.1/lib/active_record/connection_adapters/abstract/transaction.rb:317:in `within_new_transaction'
7: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activesupport-7.0.3.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:21:in `synchronize'
6: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activesupport-7.0.3.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:21:in `handle_interrupt'
5: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activesupport-7.0.3.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:25:in `block in synchronize'
4: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activesupport-7.0.3.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:25:in `handle_interrupt'
3: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activerecord-7.0.3.1/lib/active_record/connection_adapters/abstract/transaction.rb:319:in `block in within_new_transaction'
2: from /var/www/discourse/script/import_scripts/base.rb:231:in `block in all_records_exist?'
1: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/rack-mini-profiler-3.0.0/lib/patches/db/pg.rb:56:in `exec'
/var/www/discourse/vendor/bundle/ruby/2.7.0/gems/rack-mini-profiler-3.0.0/lib/patches/db/pg.rb:56:in `exec': ERROR: duplicate key value violates unique constraint "import_ids_pkey" (PG::UniqueViolation)
DETAIL: Key (val)=(nid:42081) already exists.
20: from script/import_scripts/drupal.rb:537:in `<main>'
19: from /var/www/discourse/script/import_scripts/base.rb:47:in `perform'
18: from script/import_scripts/drupal.rb:39:in `execute'
17: from script/import_scripts/drupal.rb:169:in `import_forum_topics'
16: from /var/www/discourse/script/import_scripts/base.rb:916:in `batches'
15: from /var/www/discourse/script/import_scripts/base.rb:916:in `loop'
14: from /var/www/discourse/script/import_scripts/base.rb:917:in `block in batches'
13: from script/import_scripts/drupal.rb:195:in `block in import_forum_topics'
12: from /var/www/discourse/script/import_scripts/base.rb:224:in `all_records_exist?'
11: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activerecord-7.0.3.1/lib/active_record/transactions.rb:209:in `transaction'
10: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activerecord-7.0.3.1/lib/active_record/connection_adapters/abstract/database_statements.rb:316:in `transaction'
9: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activerecord-7.0.3.1/lib/active_record/connection_adapters/abstract/transaction.rb:317:in `within_new_transaction'
8: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activesupport-7.0.3.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:21:in `synchronize'
7: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activesupport-7.0.3.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:21:in `handle_interrupt'
6: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activesupport-7.0.3.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:25:in `block in synchronize'
5: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activesupport-7.0.3.1/lib/active_support/concurrency/load_interlock_aware_monitor.rb:25:in `handle_interrupt'
4: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/activerecord-7.0.3.1/lib/active_record/connection_adapters/abstract/transaction.rb:319:in `block in within_new_transaction'
3: from /var/www/discourse/script/import_scripts/base.rb:243:in `block in all_records_exist?'
2: from /var/www/discourse/script/import_scripts/base.rb:243:in `ensure in block in all_records_exist?'
1: from /var/www/discourse/vendor/bundle/ruby/2.7.0/gems/rack-mini-profiler-3.0.0/lib/patches/db/pg.rb:56:in `exec'
/var/www/discourse/vendor/bundle/ruby/2.7.0/gems/rack-mini-profiler-3.0.0/lib/patches/db/pg.rb:56:in `exec': ERROR: current transaction is aborted, commands ignored until end of transaction block (PG::InFailedSqlTransaction)
A única maneira que consegui fazer com que ele prosseguisse foi alterando as condições SQL:
...
LEFT JOIN node_counter nc ON nc.nid = n.nid
WHERE n.type = 'forum'
AND n.status = 1
AND n.nid != 42081
AND n.nid != 53125
AND n.nid != 57807
AND n.nid != 63932
AND n.nid != 66756
AND n.nid != 76561
AND n.nid != 78250
AND n.nid != 82707
LIMIT #{BATCH_SIZE}
OFFSET #{offset};
...
Inspecionei o primeiro nó com falha, bem como os nids anteriores e posteriores a ele no banco de dados Drupal de origem, e não consigo ver nada de errado. O nid é definido como a chave primária e tem AUTO_INCREMENT, e o site Drupal original funciona bem, então não pode haver nenhum problema fundamental com a integridade do banco de dados de origem.
Além do bug acima, estas são as limitações que estou tendo com o script:
-
Permalinks: Parece que o script importador criará permalinks para os antigos URLs de nós
example.com/node/XXXXXXX. Mas também preciso manter links para comentários específicos dentro desses nós, que têm o formato:example.com/comment/YYYYYYY#comment-YYYYYYY(YYYYYYYé o mesmo em ambas as ocorrências). O esquema de URL do Drupal não inclui o ID do nó ao qual o comentário está associado, enquanto o Discourse sim (example.com/t/topic-keywords/XXXXXXX/YY), o que parece ser uma complicação importante. -
Limitações de nome de usuário: O Drupal permite espaços em nomes de usuário. Entendo que o Discourse não permite, pelo menos não permite que novos usuários os criem dessa forma. Esta postagem sugere que o script importador “converterá” automaticamente os nomes de usuário problemáticos, mas não vejo nenhum código para isso emAtualização: Na verdade, parece que o Discourse lidou com isso automaticamente da maneira correta./import_scripts/drupal.rb. -
Usuários banidos: Parece que o script importa todos os usuários, incluindo contas banidas. Eu provavelmente poderia adicionar uma condição muito facilmente à seleção SQL
WHERE status = 1para importar apenas contas de usuário ativas, mas não tenho certeza se isso causaria problemas com a serialização dos registros. Acima de tudo, eu preferiria manter esses nomes de contas previamente banidos com seus endereços de e-mail associados permanentemente bloqueados para que os mesmos usuários problemáticos não se registrem novamente no Discourse. -
Campos de perfil de usuário: Alguém sabe se há código de exemplo em um dos outros importadores para importar campos de informações pessoais dos perfis de contas de usuário? Tenho apenas um campo de perfil (“Localização”) que preciso importar.
-
Avatares (não Gravatars): Parece um pouco estranho que haja código no importador Drupal para importar Gravatars, mas não para as imagens de avatar de conta local muito mais usadas.
-
Mensagens privadas: Quase todos os fóruns Drupal 7 provavelmente usarão o módulo de terceiros privatemsg (não há funcionalidade oficial de PM no Drupal). O importador não suporta a importação de PMs. No meu caso, preciso importar cerca de 1,5 milhão deles.
Obrigado antecipadamente pela sua ajuda e por disponibilizar o script importador Drupal.




