복붙노트

[RUBY-ON-RAILS] 레일 : 유효성 검사 링크 (URL을)에 좋은 방법 무엇입니까?

RUBY-ON-RAILS

레일 : 유효성 검사 링크 (URL을)에 좋은 방법 무엇입니까?

궁금 해서요 어떻게 레일 최고의 유효성 검사 URL을 것입니다. 나는 정규 표현식을 사용하여 생각,하지만 확인이 가장 좋은 방법 인 경우입니다했다.

내가 정규식을 사용한다면 그리고, 누군가가 나에게 하나를 제안 할 수 있을까? 나는 정규식 여전히 새로운입니다.

해결법

  1. ==============================

    1.URL을 검증하는 것은 어려운 일이다. 그것은 또한 매우 광범위한 요청합니다.

    URL을 검증하는 것은 어려운 일이다. 그것은 또한 매우 광범위한 요청합니다.

    당신은 무엇을 정확하게 수행 할 수 있습니까? 당신이 URL의 형식, 존재, 또는 무엇을 확인 하시겠습니까? 수행하려는 작업에 따라 몇 가지 가능성이있다.

    정규 표현식은 URL의 형식을 확인할 수 있습니다. 그러나 심지어 복잡한 정규 표현식은 유효한 URL 다루고있는 보장 할 수 없다.

    간단한 정규 표현식을 경우 예를 들어, 다음 호스트를 거부 아마 것

    http://invalid##host.com
    

    그러나 수

    http://invalid-host.foo
    

    기존 TLD를 고려하면 그 유효한 호스트되지만 유효한 도메인입니다. 당신은 호스트 이름이 아닌 도메인을 확인하려면 다음과 같은 하나의 유효한 호스트 이름이기 때문에 사실,이 솔루션은 작동합니다

    http://host.foo
    

    또한 다음과 같은 하나

    http://localhost
    

    자, 내가 당신에게 몇 가지 솔루션을 제공 할 수 있습니다.

    도메인을 확인하려면, 당신은 정규 표현식에 대해 잊지해야합니다. 순간에 사용할 수있는 가장 좋은 방법은 공공 접미사 목록, 모질라에 의해 유지되는 목록입니다. 나는 공공 접미사 목록에 대한 구문 분석 및 유효성 검사 도메인에 대한 루비 라이브러리를 생성하고,이 PublicSuffix라고.

    당신이 URI / URL의 형식을 확인하고 싶은 경우에, 당신은 정규 표현식을 사용할 수도 있습니다. 대신에 하나의 검색의, 루비 내장 URI.parse 방법을 사용합니다.

    require 'uri'
    
    def valid_url?(uri)
      uri = URI.parse(uri) && !uri.host.nil?
    rescue URI::InvalidURIError
      false
    end
    

    당신은 더 제한하도록 결정할 수 있습니다. 당신이 원하는 경우 예를 들어, URL은 다음 유효성 검사가 더 정확 만들 수는 HTTP / HTTPS URL이 될 수 있습니다.

    require 'uri'
    
    def valid_url?(url)
      uri = URI.parse(url)
      uri.is_a?(URI::HTTP) && !uri.host.nil?
    rescue URI::InvalidURIError
      false
    end
    

    물론, 경로 또는 체계에 대한 검사를 포함하여이 방법에 적용 할 수있는 개선의 톤이있다.

    마지막으로, 당신은 또한 발리에이 코드를 패키지 할 수 있습니다 :

    class HttpUrlValidator < ActiveModel::EachValidator
    
      def self.compliant?(value)
        uri = URI.parse(value)
        uri.is_a?(URI::HTTP) && !uri.host.nil?
      rescue URI::InvalidURIError
        false
      end
    
      def validate_each(record, attribute, value)
        unless value.present? && self.class.compliant?(value)
          record.errors.add(attribute, "is not a valid HTTP URL")
        end
      end
    
    end
    
    # in the model
    validates :example_attribute, http_url: true
    
  2. ==============================

    2.내 모델 내부에 하나의 라이너를 사용 :

    내 모델 내부에 하나의 라이너를 사용 :

    유효성 : 홈페이지, 형식 : URI :: 정규 표현식 (w % [HTTP HTTPS])

    내가 사용하는 충분한 및 간단한 생각합니다. 내부적 매우 동일한 정규 표현식을 사용 더욱이 그것은 시몬의 방법으로 이론적으로 동등해야한다.

  3. ==============================

    3.시몬의 생각에 따라, 당신은 쉽게 당신의 자신의 유효성 검사기를 만들 수 있습니다.

    시몬의 생각에 따라, 당신은 쉽게 당신의 자신의 유효성 검사기를 만들 수 있습니다.

    class UrlValidator < ActiveModel::EachValidator
      def validate_each(record, attribute, value)
        return if value.blank?
        begin
          uri = URI.parse(value)
          resp = uri.kind_of?(URI::HTTP)
        rescue URI::InvalidURIError
          resp = false
        end
        unless resp == true
          record.errors[attribute] << (options[:message] || "is not an url")
        end
      end
    end
    

    다음 사용

    validates :url, :presence => true, :url => true
    

    모델이다.

  4. ==============================

    4.(단지 주소 지정을위한 좋은 래퍼 :: URI.parse 솔루션) validate_url 보석도 있습니다.

    (단지 주소 지정을위한 좋은 래퍼 :: URI.parse 솔루션) validate_url 보석도 있습니다.

    그냥 추가

    gem 'validate_url'
    

    당신의 Gemfile에, 그리고 당신이 할 수있는 모델

    validates :click_through_url, url: true
    
  5. ==============================

    5.이 질문은 이미 대답하지만, 도대체, 내가 사용하고 해결책을 제안한다.

    이 질문은 이미 대답하지만, 도대체, 내가 사용하고 해결책을 제안한다.

    정규 표현식은 내가 만난 모든 URL과 함께 잘 작동합니다. setter 메소드는 어떤 프로토콜이 언급되지 않은 경우 (: //하자가 HTTP 가정) 알아서하는 것입니다.

    그리고 마지막으로, 우리는 페이지를 가져 오지 시도합니다. 어쩌면 내가 리디렉션 및뿐만 아니라 HTTP 200 OK를 받아 들여야한다.

    # app/models/my_model.rb
    validates :website, :allow_blank => true, :uri => { :format => /(^$)|(^(http|https):\/\/[a-z0-9]+([\-\.]{1}[a-z0-9]+)*\.[a-z]{2,5}(([0-9]{1,5})?\/.*)?$)/ix }
    
    def website= url_str
      unless url_str.blank?
        unless url_str.split(':')[0] == 'http' || url_str.split(':')[0] == 'https'
            url_str = "http://" + url_str
        end
      end  
      write_attribute :website, url_str
    end
    

    과...

    # app/validators/uri_vaidator.rb
    require 'net/http'
    
    # Thanks Ilya! http://www.igvita.com/2006/09/07/validating-url-in-ruby-on-rails/
    # Original credits: http://blog.inquirylabs.com/2006/04/13/simple-uri-validation/
    # HTTP Codes: http://www.ruby-doc.org/stdlib/libdoc/net/http/rdoc/classes/Net/HTTPResponse.html
    
    class UriValidator < ActiveModel::EachValidator
      def validate_each(object, attribute, value)
        raise(ArgumentError, "A regular expression must be supplied as the :format option of the options hash") unless options[:format].nil? or options[:format].is_a?(Regexp)
        configuration = { :message => I18n.t('errors.events.invalid_url'), :format => URI::regexp(%w(http https)) }
        configuration.update(options)
    
        if value =~ configuration[:format]
          begin # check header response
            case Net::HTTP.get_response(URI.parse(value))
              when Net::HTTPSuccess then true
              else object.errors.add(attribute, configuration[:message]) and false
            end
          rescue # Recover on DNS failures..
            object.errors.add(attribute, configuration[:message]) and false
          end
        else
          object.errors.add(attribute, configuration[:message]) and false
        end
      end
    end
    
  6. ==============================

    6.또한 제도, 검사 도메인 영역 및 IP 호스트 이름없이 URL을 수 있습니다 valid_url 보석을 시도 할 수 있습니다.

    또한 제도, 검사 도메인 영역 및 IP 호스트 이름없이 URL을 수 있습니다 valid_url 보석을 시도 할 수 있습니다.

    당신의 Gemfile에 추가 :

    보석 'valid_url'

    그리고 모델 :

    class WebSite < ActiveRecord::Base
      validates :url, :url => true
    end
    
  7. ==============================

    7.그냥 내 2 센트 :

    그냥 내 2 센트 :

    before_validation :format_website
    validate :website_validator
    
    private
    
    def format_website
      self.website = "http://#{self.website}" unless self.website[/^https?/]
    end
    
    def website_validator
      errors[:website] << I18n.t("activerecord.errors.messages.invalid") unless website_valid?
    end
    
    def website_valid?
      !!website.match(/^(https?:\/\/)?([\da-z\.-]+)\.([a-z\.]{2,6})([\/\w \.-=\?]*)*\/?$/)
    end
    

    편집 : 변경 정규식 매개 변수 URL을하였습니다.

  8. ==============================

    8.나를 위해 일한 솔루션했다 :

    나를 위해 일한 솔루션했다 :

    validates_format_of :url, :with => /\A(https?:\/\/)?([\da-z\.-]+)\.([a-z\.]{2,6})([\/\w\.-]*)*\/?\Z/i
    

    나는 당신이 부착하지만 난과 같이 URL을 지원하고있어 그 예 중 일부를 사용하려고했다 :

    당신이 사용하는 경우 때문에 ^는 A의 사용 및 Z에 주목하고 레일 검증에서이 경고 보안을 볼 수 있습니다 $.

     Valid ones:
     'www.crowdint.com'
     'crowdint.com'
     'http://crowdint.com'
     'http://www.crowdint.com'
    
     Invalid ones:
      'http://www.crowdint. com'
      'http://fake'
      'http:fake'
    
  9. ==============================

    9.나는 (내가 레일 응용 프로그램의 URL을 확인하는 데 필요한) 최근에 같은 문제로 실행하지만 유니 코드 URL의 추가 요구 사항에 대처했다 (예 : http : //кц.рф) ...

    나는 (내가 레일 응용 프로그램의 URL을 확인하는 데 필요한) 최근에 같은 문제로 실행하지만 유니 코드 URL의 추가 요구 사항에 대처했다 (예 : http : //кц.рф) ...

    나는 몇 가지 해결책을 연구하고 다음 건너 온 :

  10. ==============================

    10.여기에 데이비드 제임스에 의해 게시 발리의 업데이트 버전입니다. 그것은 벤자민 플라이셔에 의해 게시되었습니다. 한편, 나는 여기에서 찾을 수 있습니다 업데이트 된 포크를 밀었다.

    여기에 데이비드 제임스에 의해 게시 발리의 업데이트 버전입니다. 그것은 벤자민 플라이셔에 의해 게시되었습니다. 한편, 나는 여기에서 찾을 수 있습니다 업데이트 된 포크를 밀었다.

    require 'addressable/uri'
    
    # Source: http://gist.github.com/bf4/5320847
    # Accepts options[:message] and options[:allowed_protocols]
    # spec/validators/uri_validator_spec.rb
    class UriValidator < ActiveModel::EachValidator
    
      def validate_each(record, attribute, value)
        uri = parse_uri(value)
        if !uri
          record.errors[attribute] << generic_failure_message
        elsif !allowed_protocols.include?(uri.scheme)
          record.errors[attribute] << "must begin with #{allowed_protocols_humanized}"
        end
      end
    
    private
    
      def generic_failure_message
        options[:message] || "is an invalid URL"
      end
    
      def allowed_protocols_humanized
        allowed_protocols.to_sentence(:two_words_connector => ' or ')
      end
    
      def allowed_protocols
        @allowed_protocols ||= [(options[:allowed_protocols] || ['http', 'https'])].flatten
      end
    
      def parse_uri(value)
        uri = Addressable::URI.parse(value)
        uri.scheme && uri.host && uri
      rescue URI::InvalidURIError, Addressable::URI::InvalidURIError, TypeError
      end
    
    end
    

    ...

    require 'spec_helper'
    
    # Source: http://gist.github.com/bf4/5320847
    # spec/validators/uri_validator_spec.rb
    describe UriValidator do
      subject do
        Class.new do
          include ActiveModel::Validations
          attr_accessor :url
          validates :url, uri: true
        end.new
      end
    
      it "should be valid for a valid http url" do
        subject.url = 'http://www.google.com'
        subject.valid?
        subject.errors.full_messages.should == []
      end
    
      ['http://google', 'http://.com', 'http://ftp://ftp.google.com', 'http://ssh://google.com'].each do |invalid_url|
        it "#{invalid_url.inspect} is a invalid http url" do
          subject.url = invalid_url
          subject.valid?
          subject.errors.full_messages.should == []
        end
      end
    
      ['http:/www.google.com','<>hi'].each do |invalid_url|
        it "#{invalid_url.inspect} is an invalid url" do
          subject.url = invalid_url
          subject.valid?
          subject.errors.should have_key(:url)
          subject.errors[:url].should include("is an invalid URL")
        end
      end
    
      ['www.google.com','google.com'].each do |invalid_url|
        it "#{invalid_url.inspect} is an invalid url" do
          subject.url = invalid_url
          subject.valid?
          subject.errors.should have_key(:url)
          subject.errors[:url].should include("is an invalid URL")
        end
      end
    
      ['ftp://ftp.google.com','ssh://google.com'].each do |invalid_url|
        it "#{invalid_url.inspect} is an invalid url" do
          subject.url = invalid_url
          subject.valid?
          subject.errors.should have_key(:url)
          subject.errors[:url].should include("must begin with http or https")
        end
      end
    end
    

    유효한 주소로 해석되는 이상한 HTTP URI를 여전히 있다는 것을 통지를 바랍니다.

    http://google  
    http://.com  
    http://ftp://ftp.google.com  
    http://ssh://google.com
    

    다음 예제를 다루고 주소 보석에 대한 문제입니다.

  11. ==============================

    11.나는 위의 lafeber 솔루션에 약간의 변화를 사용합니다. 그것은 (예 : www.many ... dots.com의 예를 들어 같은) 호스트 이름의 연속적인 점을 허용하지 않습니다 :

    나는 위의 lafeber 솔루션에 약간의 변화를 사용합니다. 그것은 (예 : www.many ... dots.com의 예를 들어 같은) 호스트 이름의 연속적인 점을 허용하지 않습니다 :

    %r"\A(https?://)?[a-z\d\-]+(\.[a-z\d\-]+)*\.[a-z]{2,6}(/.*)?\Z"i
    

    URI.parse 어떤 경우에는 당신이 (당신이 신속하게 twitter.com/username 같은 형태의 URL을 철자에 사용자를 허용하려면, 예를 들어 경우) 할 수 있습니다 무엇을하지 않은, 구성표 추가하는 설정을 의무화하는 것

  12. ==============================

    12.나는 'activevalidators'보석을 사용하고있다 그것의 작품을 꽤 잘 (단지 URL을 검증)

    나는 'activevalidators'보석을 사용하고있다 그것의 작품을 꽤 잘 (단지 URL을 검증)

    당신은 여기에서 찾을 수 있습니다

    그것은 모든 기록하지만 보석은 당신이 초기화 말에 다음 몇 줄을 추가 할 수 있습니다 추가 기본적으로 한 번 것 : /config/environments/initializers/active_validators_activation.rb를

    # Activate all the validators
    ActiveValidators.activate(:all)
    

    (참고 : 대체 할 수있다 : 홈페이지 나 : 모두가 그냥 값의 유효성 검사 특정 유형 원한다면 무엇이든)

    그리고 다시이 같은 모델 뭔가에

    class Url < ActiveRecord::Base
       validates :url, :presence => true, :url => true
    end
    

    이제 서버를 다시 시작하고 그것을해야

  13. ==============================

    13.당신은 같은 것을 사용하여 여러 URL을 확인할 수 있습니다 :

    당신은 같은 것을 사용하여 여러 URL을 확인할 수 있습니다 :

    validates_format_of [:field1, :field2], with: URI.regexp(['http', 'https']), allow_nil: true
    
  14. ==============================

    14.https://github.com/perfectline/validates_url 당신을 위해 거의 모든 것을 할 것입니다 좋은 간단한 보석이다

    https://github.com/perfectline/validates_url 당신을 위해 거의 모든 것을 할 것입니다 좋은 간단한 보석이다

  15. ==============================

    15.최근에 나는이 같은 문제를했고 나는 유효한 URL을 주변에 작품을 발견했다.

    최근에 나는이 같은 문제를했고 나는 유효한 URL을 주변에 작품을 발견했다.

    validates_format_of :url, :with => URI::regexp(%w(http https))
    validate :validate_url
    def validate_url
    
      unless self.url.blank?
    
        begin
    
          source = URI.parse(self.url)
    
          resp = Net::HTTP.get_response(source)
    
        rescue URI::InvalidURIError
    
          errors.add(:url,'is Invalid')
    
        rescue SocketError 
    
          errors.add(:url,'is Invalid')
    
        end
    
    
    
      end
    

    validate_url 방법의 첫 번째 부분은 유효성을 URL 형식에 충분하다. 두 번째 부분은 URL이 요청을 전송하여 존재 확인합니다.

  16. ==============================

    16.당신이 간단한 검증 및 사용자 지정 오류 메시지를 원하는 경우 :

    당신이 간단한 검증 및 사용자 지정 오류 메시지를 원하는 경우 :

      validates :some_field_expecting_url_value,
                format: {
                  with: URI.regexp(%w[http https]),
                  message: 'is not a valid URL'
                }
    
  17. ==============================

    17.나는 유효를 추가 할 수있는 URI 모듈을 monkeypatch 좋아? 방법

    나는 유효를 추가 할 수있는 URI 모듈을 monkeypatch 좋아? 방법

    내부 설정 / 초기화 / uri.rb

    module URI
      def self.valid?(url)
        uri = URI.parse(url)
        uri.is_a?(URI::HTTP) && !uri.host.nil?
      rescue URI::InvalidURIError
        false
      end
    end
    
  18. ==============================

    18.그리고 모듈로

    그리고 모듈로

    module UrlValidator
      extend ActiveSupport::Concern
      included do
        validates :url, presence: true, uniqueness: true
        validate :url_format
      end
    
      def url_format
        begin
          errors.add(:url, "Invalid url") unless URI(self.url).is_a?(URI::HTTP)
        rescue URI::InvalidURIError
          errors.add(:url, "Invalid url")
        end
      end
    end
    

    그리고 당신이에 대한 유효성 검사 URL을 원하는 모든 모델에서 URL 검사기를 포함한다. 그냥 옵션을 포함.

  19. ==============================

    19.URL 유효성 검사 웹 사이트의 수와 같은 정규 표현식을 사용하여 간단하게 처리 할 수없는 성장을 계속하고 새 도메인 이름 지정 방식이 올라오고 계속.

    URL 유효성 검사 웹 사이트의 수와 같은 정규 표현식을 사용하여 간단하게 처리 할 수없는 성장을 계속하고 새 도메인 이름 지정 방식이 올라오고 계속.

    내 경우, 나는 단순히 사용자 정의 유효성 검사기를 쓰기 성공적인 응답을 검사하는.

    class UrlValidator < ActiveModel::Validator
      def validate(record)
        begin
          url = URI.parse(record.path)
          response = Net::HTTP.get(url)
          true if response.is_a?(Net::HTTPSuccess)   
        rescue StandardError => error
          record.errors[:path] << 'Web address is invalid'
          false
        end  
      end
    end
    

    나는 record.path를 사용하여 내 모델의 경로 속성을 검증하고있다. [: 경로] I는 record.errors를 사용하여 각각의 속성 이름 오류 가압하고있다.

    당신은 단순히 모든 속성의 이름으로이를 대체 할 수 있습니다.

    그런 다음에, 나는 단순히 내 모델에서 사용자 정의 유효성 검사기를 호출합니다.

    class Url < ApplicationRecord
    
      # validations
      validates_presence_of :path
      validates_with UrlValidator
    
    end
    
  20. ==============================

    20.나에게 좋은이 하나가 작동을 위해 당신은 이것에 대한 정규식을 사용할 수 있습니다 :

    나에게 좋은이 하나가 작동을 위해 당신은 이것에 대한 정규식을 사용할 수 있습니다 :

    (^|[\s.:;?\-\]<\(])(ftp|https?:\/\/[-\w;\/?:@&=+$\|\_.!~*\|'()\[\]%#,]+[\w\/#](\(\))?)(?=$|[\s',\|\(\).:;?\-\[\]>\)])
    
  21. from https://stackoverflow.com/questions/7167895/rails-whats-a-good-way-to-validate-links-urls by cc-by-sa and MIT license