Seltsames Problem mit devise valid_password?

78

In den letzten 2 Stunden habe ich versucht, ein seltsames Problem in der Entwicklung zu beheben, bei dem ich mich nicht anmelden kann.

Hier ist das Zeug, auf das ich mich auch beziehe:

password 
=> 'vinodsobale'

password == 'vinodsobale'
=> true

resource.valid_password?(password)

=> false

resource.valid_password?('vinodsobale')

=> true

Fügen Sie auch den Screenshot hinzu:

Geben Sie hier die Bildbeschreibung ein Hinweis: Ich habe den Debugger in devise aktiviert, sodass der obige Code ein interner Code ist.

Für mich sieht es nach einem Problem aus Devise.secure_compare.

Viren
quelle
2
Ein GitHub-Problem öffnen? Am besten mit einem reproduzierbaren Test.
vemv
4
@Viren - Ich habe keine Ahnung von Ruby oder Devise, aber ich würde die Codierung des angegebenen Passworts überprüfen.
MByD
3
Können Sie password.encodinguns das Ergebnis mitteilen? Dies ist das einzige, was ich mir vorstellen kann, dort falsch zu laufen. Sie können auch damit herumspielen ::BCrypt::Engine.hash_secret(password, salt)und dies mit dem tatsächlich gespeicherten Hash vergleichen. Für diesen Vergleich text.byteskönnte sich auch dies als nützlich erweisen.
Rudolf
4
Können Sie überprüfen password.bytesund 'vinodsobale'.bytesnur um sicher zu gehen?
Rudolf
3
@ lad2025, was meinst du mit "gespeichert"? Ist es das password? Wenn dies der NULL character \0Fall ist, sollte es in Unicode codiert sein und password == 'vinodsobale'nicht zurückkehren true.
Vutran

Antworten:

3

Dieses Problem ist auf einen bekannten Fehler bei der Beschädigung von Zeichenfolgen in Ruby 2.2.0 zurückzuführen, der in 2.2.2 behoben wurde.

Wie im Fehlerbericht beschrieben, trat die Beschädigung auf, als BCrypt eine bestimmte API zur Zeichenfolgenerstellung aus seiner C-Erweiterung aufrief, die Devise v3.3.0 durch Aufrufen ::BCrypt::Engine.hash_secretvon der Devise::Models::DatabaseAuthenticatable#valid_password?Methode auslöste . Eine gerätespezifische Problemumgehung für diesen Fehler wurde in Version 3.5.0 veröffentlicht.

Die Lösung ist entweder:

  • Ruby auf < 2.2.0oder auf upgraden >= 2.2.2;
  • Aktualisieren Sie das Gerät auf >= 3.5.0.
wjordan
quelle
0

Wie wäre es mit

resource.valid_password?(password.to_s)

Ich hoffe es hilft dir.

Сергій Назаревич
quelle
3
Bitte bearbeiten Sie Ihren Beitrag und erklären Sie, warum dies funktionieren würde.
Rohit Gupta
Warum denkst du, wird das funktionieren? Ich sehe viele Probleme damit. Erstens habe ich bereits erwähnt, dh password == 'vinodsobale' Übereinstimmungen. Das war, wenn vinodsoblees vom Typ ist string(was wir alle sehen können), dann passwordist es auch stringso, .to_sdass man nichts anderes hervorbringt. Zweitens ist der Code, den Sie gerade erwähnen, Teil des internen Codes. Wie möchten Sie diesen implementieren, indem Sie den Code öffnen und ihn mit Affen patchen?
Viren
1
Es kann sein, dass der Gleichheitsoperator die Methode to_s automatisch aufruft, wenn auf der rechten Seite ein ungültiger Typ vorhanden ist. Aber ich rate nur. Hast Du es versucht?
Pablo Jomer
Es ist eine plausible Erklärung.
Sevenseacat
2
Du hast benutzt password == 'vinosobale'. Könnten Sie password === 'vidodsobale' Streichhölzer versuchen ? Könnten Sie diese Frage lesen - stackoverflow.com/questions/7156955/… ?
21ергій Назаревич
0

Devise DatabaseAuthenticatable#valid_password?verwendet eine Methode namens " Encryptor::compareEs werden 2 Objekte verwendet", das aktuell gespeicherte Kennwort und das neue Kennwort, das Sie vergleichen möchten. Ich glaube, dass diese Methode einen Nebeneffekt hat, der den zweiten Parameter in der Mitte ändert, sodass stattdessen das Objekt geändert wird von einmal wird es zweimal geändert, was zu einem falschen Ergebnis führt. Es kann also funktionieren, wenn Sie ein doppeltes Objekt des Passworts übergeben haben. kannst du versuchen zu benutzenvalid_password? password.dup

Emad Elsaid
quelle
Wenn dies der Fall ist, warum erfolgt die Änderung nicht, wenn resource.valid_password?('vinodsobale')jedes Mal, wenn ich dies ausführte , eine Zeichenfolge angegeben wird, die funktioniert hat, undreturn true
Viren
0

Möglicherweise liegt ein Problem mit der Codierung zwischen der Originalquelle und Ihrer Konsole vor. Wenn Sie ausführen password.codepoints, sollten Sie in der Lage sein, die tatsächliche Codierung zu sehen. Das Ausführen .codepointsder unformatierten 'Passwort'-Zeichenfolge sollte zurückkehren [112, 97, 115, 115, 119, 111, 114, 100].

Torrey Payne
quelle