cannot load such file -- 'nokogiri\nokogiri' ruby 2.7

Viewed 464

I'm running AWS Lambda locally.

When I run the lambda function this is the error I get:

 {
  "errorMessage": "cannot load such file -- nokogiri/nokogiri",
  "errorType": "Init<LoadError>",
  "stackTrace": [
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/task/vendor/ruby/2.7.0/gems/nokogiri-1.11.0.rc2/lib/nokogiri.rb:15:in `rescue in <top (required)>'",
    "/var/task/vendor/ruby/2.7.0/gems/nokogiri-1.11.0.rc2/lib/nokogiri.rb:11:in `<top (required)>'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/task/vendor/ruby/2.7.0/gems/google_drive-3.0.5/lib/google_drive/session.rb:8:in `<top (required)>'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/task/vendor/ruby/2.7.0/gems/google_drive-3.0.5/lib/google_drive.rb:7:in `<top (required)>'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/task/main.rb:7:in `<top (required)>'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'",
    "/var/lang/lib/ruby/site_ruby/2.7.0/rubygems/core_ext/kernel_require.rb:92:in `require'"
  ]
}

I looked into /var/task/vendor/ruby/2.7.0/gems/nokogiri-1.11.0.rc2/lib/nokogiri.rb:15and this is the code that makes everything blow up: `require 'nokogiri/nokogiri'

These are the files in `./vendor/ruby/2.7.0/gems/nokogiri-1.11.0.rc2/lib':

nokogiri
nokogiri.rb
xsd

And these are the files in ./vendor/ruby/2.7.0/gems/nokogiri-1.11.0.rc2/lib/nokogiri/:

css
decorators
html.rb
nokogiri.bundle
version.rb
xml.rb
xslt.rb
css.rb
html
jruby
syntax_error.rb
xml
xslt

There is no file nokogiri/nokogiri hence I suppose the error. I tried to copy nokogiri.rb into directory nokogiri nut other errors pop up.

How can I move forward?

Thanks!

1 Answers

I was facing the same exact problem until I read this article https://www.stevenringo.com/ruby-in-aws-lambda-with-postgresql-nokogiri/ .

To summarize, the problem is when using an AWS Lambda, there is no way to execute a command on the environment/Lambda. So while you can use bundle install locally, you CANNOT use it when on the Lambda. That being said and as the article mentions, we need to find a way to package and compile dependencies ahead of time in an environment that is compatible with the Lambda environment.

This leads us to an alternate solution of compiling our dependencies from the docker container to match the lambda environment. In order to fix the problem, you need to do the following:

  1. Install docker on your local machine

  2. Create a Dockerfile in your ruby project with the following lines:

    FROM lambci/lambda:build-ruby2.7
    
    CMD "/bin/bash"
    
  3. Build your docker image with the following command: docker build -t lambda-ruby2.7 . (Don't forget the period at the end!)

  4. Enter the shell inside the container with the following command: docker run --rm -it -v $PWD:/var/task -w /var/task lambda-ruby2.7

  5. From the shell/container, run bundle install --path vendor/bundle --clean

  6. Exit the shell

  7. Inside the project, zip it: zip -q -r deploy.zip .

This solution worked for me. Hopefully it can be an alternative until someone figures how to do this without using Docker.

Related