Ruby
 Computer >> コンピューター >  >> プログラミング >> Ruby

Railsでワンタイムスクリプトを書く

CSVファイルからアプリに大量のデータをインポートしたいと思ったことはありませんか?または、カスタマーレビューの一部で正しくエンコードされていない文字を修正する必要があるかもしれません。または、Redisにデータを保存する方法について考えを変え、すべてを古い形式から新しい形式に移動する必要がありました。

Avvoでは、これらを「アドホックタスク」と呼んでいました。のように、おそらく一度だけ実行する必要があります。 では、Railsでアドホックタスクを処理するための最良の方法は何ですか?

データベース移行を作成する

データベース内のデータの構造を変更する必要がある場合は、移行が適切に機能します。タスクが実行されたかどうかを追跡し、変更を他の環境に引き継ぎます。これは、移行が構築されたものです。 為に。また、おそらくすでにそれらを使用しているものでもあります。

同時にデータを変更する場合は、移行が可能性があります うまくできた。ただし、注意すべき点がいくつかあります。

Permissions.create(...)のようなものを呼び出す 移行中に問題が発生する可能性があります。モデルが変更された場合、移行の実行時にモデルが使用できない可能性があるため、移行が失敗する可能性があります。または、移行を作成してから実行するまでの間にモデルが変更されている可能性があります。これを回避する方法はいくつかありますが、エラーが発生しやすく、奇妙な方法で失敗する可能性があります。

タスクにActiveRecordが含まれていない場合も、移行はあまり役に立ちません。

これらは取引を妨げるものではありません。 しかし、移行時に多くのデータをインポートまたは変更しない傾向があります。より良いオプションがあります。

レーキタスクを作成する

あなたには仕事があります。おそらく一度だけ実行したいと思うでしょう。そして、あなたはそれをあなたのマシンでテストし、本番環境で実行できるようにしたいと思っています。

レーキタスクはこれに非常に適しています。 Railsはあなたのためにレーキタスクを生成することさえできます:

$ be rails g task locations import
      create  lib/tasks/locations.rake

これにより、コードを次の場所に格納するためのファイルが作成されます。

lib /タスク/locations.rake
namespace :locations do
  desc "TODO"
  task import: :environment do

  end
end

そのtaskの内部 ブロックすると、Railsアプリですべてのモデルと残りのコードを使用できます。 Railsコンソールに座っているのと同じようにコードを記述できるため、データのインポートと変更は簡単です。

タスクを作成したら、rake locations:importを使用してタスクを実行できます。 。 Herokuを使用している場合は、heroku run rake locations:importを使用して実行できます。 。 Capistranoを使用している場合は、capistrano-rakegemを使用してタスクを実行できます。ただし、さらに良いオプションがあるかもしれません。

sidekiq-schedulerを使用してスケジュールされたジョブを作成します

アプリが十分に大きい場合は、おそらく すでにSidekiq、Resque、またはそのようなものを使用しています。

これらのバックグラウンドジョブプロセッサのほとんどは、後で実行するようにジョブをスケジュールできます。たとえば、Sidekiqには、sidekiq-schedulerの宝石があります。そして、sidekiq-schedulerを使用すると、実行できるトリックがあります。

自動的に決してない仕事があった場合はどうなりますか 自分でスケジュールしますが、手動で いつでもスケジュールできますか? これは、後でもう一度実行したい、またはUIを使用して実行したい「1回限りの」ジョブに最適です。

sidekiq-schedulerでは、遠い将来にジョブをスケジュールし、ジョブを無効に設定できます:

sidekiq.yml
:schedule:
  location_importer:
    class: LocationImporterWorker
    at: '3001/01/01'
    enabled: false

次に、sidekiq-webにアクセスすると、ジョブを手動でキューに入れるためのボタンが表示されます。

Railsでワンタイムスクリプトを書く

これにより、開発と本番の両方で、準備ができていればいつでもジョブを実行できます。また、もう一度実行する必要がある場合は、UIに表示されます。

仕事が危険な場合、これは最善の選択肢ではありません。誤ってそのボタンをクリックするのは簡単すぎます。また、ジョブがすぐに終了する場合にSidekiqが最適に機能するため、ジョブが完了するまでに時間がかかる場合も、それは素晴らしいことではありません。あなたの仕事は労働者を引き継ぎます、そしてあなたはあなたの仕事が終わるまでSidekiqを安全に再開することができません。 ただし、ジョブが高速で、複数回安全に実行できる場合は、これでうまくいきます。 クリーンナップのようなタスクの場合は、したいと決めるかもしれません。 定期的に実行します。

スケジューリングとトリガーだけに集中したい場合、または1回限りのスクリプトでパラメーターを設定するための柔軟性が必要な場合は、リーダーのDmitryがsidekiq-enqueuerを紹介してくれました。 sidekiq-enqueuerを使用すると、SidekiqWebインターフェイスを介してジョブのスケジュールとパラメータの設定を行うことができます。

SSHを本番環境に接続し、コードをRailsコンソールに貼り付けます

冗談です。

どちらを選ぶべきですか?

これらすべての方法を使用して、1回限りのタスクを実行しました。 しかし、私は通常、最初にレーキタスクに行きます。 それは機能し、誤って実行することは難しく、使い終わったら簡単に取り除くことができます。ただし、毎回レーキタスクを選択するわけではありません。

次の場合に移行を選択する可能性があります:

  • このジョブは、データベーススキーマの変更の一部としてSQLを使用してデータを修正します。
  • この作業は、列のデータを変更したり、いくつかのレコードを追加したりするなど、非常に単純なデータ作業です。
  • ジョブが実行されたかどうかを簡単に追跡し、再度実行しないようにしたい。

次の場合にSidekiqの仕事を選ぶかもしれません:

  • 後でもう一度ジョブを実行したいと思うかもしれません。
  • 私ではない誰かがそれを実行する必要があります。ボタンをクリックするだけです。
  • これは、短いデータインポートまたはデータクリーンアップジョブです。最初は期待していなくても、おそらく定期的に実行する必要があります。

君はどうでしょう?他に選択肢はありますか、それとも別の選択をしますか? コメントを残して私に知らせてください!


  1. RailsをAWSLambdaにデプロイする

    サーバーレスコンピューティングは、サーバーの管理とプロビジョニングの作業をクラウドプロバイダーに任せるのに役立ち、ほとんどのテクノロジーチームにとって急速に重要になっています。 AWS Lambdaは、多くのテクノロジーチームで使用されているサーバーレステクノロジーの一種です。 AWS Lambdaは、NodeJS、Java、Python、Rubyなどのコアプログラミング言語のほとんどをサポートしています。コアプログラミング言語はサポートされていますが、これらの言語で構築されたフレームワークの一部である機能に依存してサーバーレス関数を実行したい場合があります。この投稿では、AWSLambdaで

  2. Rails5でのAngularの使用

    あなたは前にその話を聞いたことがあります。分散型で完全に機能するバックエンドAPIと、通常のツールセットで作成されたフロントエンドで実行されているアプリケーションがすでにあります。 次に、Angularに移動します。または、AngularをRailsプロジェクトと統合する方法を探しているだけかもしれません。これは、この方法を好むためです。私たちはあなたを責めません。 このようなアプローチを使用すると、両方の世界を活用して、たとえばRailsとAngularのどちらの機能を使用してフォーマットするかを決定できます。 構築するもの 心配する必要はありません。このチュートリアルは、この目的のた