Docker의 Rails에서 API에 요청을 보낼 때 Errno :: EADDRNOTAVAIL

Aug 15 2020

내가하고 싶은 것

Rails의 Book 모델에서 Google Books API를 눌러 도서 정보에 대한 응답을 받고 싶습니다.

발생한 오류

web_1 | Errno::EADDRNOTAVAIL (Failed to open TCP connection to :80 (Address not available-connect(2) for nil port 80)):
web_1 |
web_1 | app/models/book.rb:24:in `search'
web_1 | app/controllers/books_controller.rb:3:in `search'

암호

양식에서 보낸 키워드 (책 이름, 저자 등)를 사용하여 API를 누르십시오.

class BooksController <ApplicationController
  def search
    @results = Book.search(params[:book_search][:search_key_word])
  end
end

비 ASCII 문자가 포함되어 있으므로 url_encode방법을 사용하여 인코딩됩니다 .

class Book <ApplicationRecord
  class << self
    def search(key_word)
      api_endpoint = ERB::Util.url_encode("https://www.googleapis.com/books/v1/volumes?q=#{key_word}&maxResults=20")
      response = Net::HTTP.get(URI.parse(api_endpoint)) # I'm getting the above error.
      JSON.parse(response)
    end
  end
end

물론 동일한 엔드 포인트에 대해 curl 명령을 실행하면 적절한 응답이 제공됩니다.

도커 사용과 관련이 있습니까? 알파인 리눅스를 기반으로합니다.https://hub.docker.com/layers/ruby/library/ruby/2.6.6-alpine/images/sha256-95d5b6bf7084a6a0f04b48a7fc1c533ccb15e1550c670ff589ef56e620f40286?context=explore

환경

  • 도커 2.3.0.4
  • 도커 작성 3.8
  • rails 컨테이너 기본 이미지 ruby ​​: 2.6.6-alpine
  • 루비 2.6.6
  • 레일 6.0.3.2

당신이 어떤 생각이 있으면 가르쳐 주시면 감사하겠습니다.
도와 주셔서 감사합니다.

답변

1 Tatsuro Aug 16 2020 at 07:03

해결되었습니다.

원인은

ERB::Util.url_encode("https://www.googleapis.com/books/v1/volumes?q=#{key_word}&maxResults=20")

이 부분에서 인코딩 할 때 반환 된 문자열이 그대로 URI.parse에 전달되면 URI :: Generic이 반환되었습니다. uri 호스트와 체계가 모두 nil이며 올바르게 획득 할 수없는 것 같습니다. Net :: HTTP.get 그대로 전달되므로 제목과 같은 오류가 발생합니다.

URI.encode더 이상 사용되지 않으므로 다른 방법으로 인코딩하고 싶었습니다. 마지막으로를 사용하여 인코딩 된 문자열에 대해 URI.parse를 수행하면 WEBrick::HTTPUtils.#escapeURI :: HTTP 인스턴스가 반환되고 체계 등이 올바르게 설정되어 해결되었습니다.

대단히 감사합니다.

참고

def search(key_word)
  uri = URI.parse(WEBrick::HTTPUtils.escape("https://www.googleapis.com/books/v1/volumes?q=#{key_word}&maxResults=20"))
  response = Net::HTTP.get_response(uri)
  JSON.parse(response.body)
end