简体   繁体   中英

How do I test a script using RSpec?

I'm writing a script that will be run using rails runner on production to make some one-time changes to our database. I want to be sure that the script works as expected before we run it, so I'm writing RSpec tests to verify its behavior while I write it.

How can I invoke the script in my test examples? The script isn't a class or a module, so there aren't individual functions for me to test. Instead, the entire script will be loaded once, run from top to bottom, and then exited. I'm not sure how to invoke that from within an RSpec test.

I'm looking for something like:

describe "my script" do
  it "should create the correct record" do
    before_count = Orders.count

    rails runner my_script.rb # What goes here?

    expect(Orders.count).to eq(before_count + 1)
  end
end

I would move the logic from the script into its own class. Then you can invoke the class in your script and in your tests or even when you're in the rails console. I've been using this pattern for a while and its pretty useful.

I think you want to use system :

system('rails runner my_script.rb')

edit #1

If you are willing to butcher the script, you can move the active components of your script into separate module and require that:

# my_script.rb
require './lib/my_script.rb'
MyScript.call()
# lib/my_script.rb
module MyScript
  def self.call
    # your code
  end
end

Then, in test:

require './lib/my_script.rb'

describe "my script" do
  it "should create the correct record" do
    before_count = Orders.count

    MyScript.call() # here

    expect(Orders.count).to eq(before_count + 1)
  end
end

It looks like I can use Kernel#load to execute the script:

describe "my script" do
  it "should create the correct record" do
    before_count = Orders.count

    load(Rails.root.join("path", "to", "my-script.rb")

    expect(Orders.count).to eq(before_count + 1)
  end
end

We can help you with this, but this:

I'm writing a script that will be run using rails runner on production to make some one-time changes to our database.

Is what migrations are for. One time changes like this to the db should be done in a migration. This circumvents the need for rspec, as any changes like this should be reversible , as migrations should be.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM