Reguläre Ausdrücke mit Validierungen in RoR 4

83

Es gibt folgenden Code:

class Product < ActiveRecord::Base
  validates :title, :description, :image_url, presence: true
  validates :price, numericality: {greater_than_or_equal_to: 0.01}
  validates :title, uniqueness: true
  validates :image_url, allow_blank: true, format: {
      with: %r{\.(gif|jpg|png)$}i,
      message: 'URL must point to GIT/JPG/PNG pictures'
  }
end

Es funktioniert, aber wenn ich versuche, es mit "Rake Test" zu testen, erhalte ich folgende Meldung:

rake aborted!
The provided regular expression is using multiline anchors (^ or $), which may present a security risk. Did you mean to use \A and \z, or forgot to add the :multiline => true option?

Was heißt das? Wie kann ich es reparieren?

Malcoauri
quelle
Hast du es versucht /\.(gif|jpg|png)$/i? Vielleicht %r{}fügt es $am Ende sein eigenes hinzu .
Wukerplank
@ Wukerplank glaube ich nicht. %r{\.(gif|jpg|png)$}i #=> /\.(gif|jpg|png)$/i, %r{\.(gif|jpg|png)}i #=> /\.(gif|jpg|png)/i.
Sawa
Ja, aber es hat nicht geholfen
Malcoauri
1
@ Wukerplank warum raten wir? in irb
rubin
3
Sie müssen das $ nach png) entfernen, was anzeigt, dass dies das letzte Element ist, und es durch \ z
Gary

Antworten:

157

^und $ist Anfang der Linie und End - of - Line Anker. Während \Aund \zist Permanent Anfang von String und Ende des String Ankers.
Sieh den Unterschied:

string = "abcde\nzzzz"
# => "abcde\nzzzz"

/^abcde$/ === string
# => true

/\Aabcde\z/ === string
# => false

So Rails ist Ihnen zu sagen : „Bist du sicher , möchten Sie verwenden ^und $? Willst du nicht verwenden \Aund \zstattdessen?“

Es gibt mehr Sicherheitsbedenken auf den Schienen, die diese Warnung hier generieren .

älterer Gott
quelle
3
Behebung des unnötigen Umgangssprache
Xaxxon
2
erklärt, was es verlangt, antwortet aber nicht, wie es behoben werden kann. Ich nehme an, wenn Sie ^ und $ verwenden möchten, müssen Sie Folgendes hinzufügen: multiline => true an der Spitze der Klasse?
Isimmons
@isimmons Indem :multiline => trueSie hinzufügen, korrigieren Sie nur die Warnung Rails, dass Sie wissen, was Sie tun.
Älterer Gott
6
Die Antwort ist da: Es wird \ A und \ z anstelle von ^ und $ verwendet, da in Ruby ^ und $ nur mit einer neuen Zeile übereinstimmen, die nicht am Anfang und Ende der Zeichenfolge steht, wodurch ein Javascript-Exploit den Test bestehen kann.
John Merlino
31

Diese Warnung wird ausgelöst, weil Ihre Validierungsregel für die Javascript-Injektion anfällig ist.

In Ihrem Fall \.(gif|jpg|png)$passt bis zum Ende der Zeile. Ihre Regel bestätigt diesen Wert also pic.png\nalert(1);als wahr:

"test.png\n<script>alert(1)</script>" === /\.(gif|jpg|png)$/i
# => true

"test.png\n<script>alert(1)</script>" === /\.(gif|jpg|png)\z/i
# => false

Lesen Sie die Artikel:

ole
quelle
Ich wünschte, wir könnten dies zur akzeptierten Antwort machen.
mlibby
2

Das Problem regexp liegt nicht in devise, sondern in config / initializers / devise.rb. Veränderung:

# Regex to use to validate the email address
config.email_regexp = /^([\w\.%\+\-]+)@([\w\-]+\.)+([\w]{2,})$/i

zu:

# Regex to use to validate the email address
  config.email_regexp = /\A([\w\.%\+\-]+)@([\w\-]+\.)+([\w]{2,})\Z/i
mcr
quelle
1

Die Warnung sagt Ihnen, dass Zeichenfolgen wie die folgende die Validierung bestehen, aber wahrscheinlich nicht das, was Sie wollen:

test = "image.gif\nthis is not an image"
re = /\.(gif|jpg|png)$/i
re.match(test) #=> #<MatchData ".gif" 1:"gif">

Beides ^und $entspricht dem Anfang / Ende einer Zeile, nicht dem Anfang / Ende der Zeichenfolge. \Aund \zentspricht dem Anfang bzw. dem Ende der vollständigen Zeichenfolge.

re = /\.(gif|jpg|png)\z/i
re.match(test) #=> nil

Der zweite Teil der Warnung ( „oder vergessen , die hinzuzufügen: mehrzeilige => true Option“) sagt Ihnen , dass , wenn Sie tatsächlich das Verhalten wollen ^und $Sie einfach die Warnung vorbei der Stille können :multilineOption.

yonosoytu
quelle
Wohin gehst du :multiline?
Pithikos
-1

Wenn Ruby aus Sicherheitsgründen \zanstelle des $Symbolzeichens sehen möchte , dass Sie es ihm geben müssen, sieht der Code folgendermaßen aus:

validates :image_url, allow_blank: true, format: {with: %r{\.(gif|jpg|png)\z}i, message: 'URL must point to GIF, JPG, PNG.'}
max
quelle