spec/fetcher_spec.rb in lastpass-1.0.1 vs spec/fetcher_spec.rb in lastpass-1.1.0
- old
+ new
@@ -5,16 +5,32 @@
describe LastPass::Fetcher do
let(:username) { "username" }
let(:password) { "password" }
let(:key_iteration_count) { 5000 }
+
+ let(:hash) { "7880a04588cfab954aa1a2da98fd9c0d2c6eba4c53e36a94510e6dbf30759256" }
let(:session_id) { "53ru,Hb713QnEVM5zWZ16jMvxS0" }
let(:session) { LastPass::Session.new session_id, key_iteration_count }
+
let(:blob_response) { "TFBBVgAAAAMxMjJQUkVNAAAACjE0MTQ5" }
let(:blob_bytes) { blob_response.decode64 }
let(:blob) { LastPass::Blob.new blob_bytes, key_iteration_count }
+ let(:login_post_data) { {method: "mobile",
+ web: 1,
+ xml: 1,
+ username: username,
+ hash: hash,
+ iterations: key_iteration_count} }
+
+ let(:google_authenticator_code) { "123456" }
+ let(:yubikey_password) { "emdbwzemyisymdnevznyqhqnklaqheaxszzvtnxjrmkb" }
+
+ let(:login_post_data_with_google_authenticator_code) { login_post_data.merge({otp: google_authenticator_code})}
+ let(:login_post_data_with_yubikey_password) { login_post_data.merge({otp: yubikey_password}) }
+
describe ".request_iteration_count" do
it "makes a POST request" do
expect(web_client = double("web_client")).to receive(:post)
.with("https://lastpass.com/iterations.php", query: {email: username})
.and_return(http_ok(key_iteration_count.to_s))
@@ -38,74 +54,111 @@
it "raises an exception on invalid key iteration count" do
expect {
LastPass::Fetcher.request_iteration_count username,
double("web_client", post: http_ok("not a number"))
- }.to raise_error LastPass::InvalidResponse, "Key iteration count is invalid"
+ }.to raise_error LastPass::InvalidResponseError, "Key iteration count is invalid"
end
it "raises an exception on zero key iteration count" do
expect {
LastPass::Fetcher.request_iteration_count username,
double("web_client", post: http_ok("0"))
- }.to raise_error LastPass::InvalidResponse, "Key iteration count is not positive"
+ }.to raise_error LastPass::InvalidResponseError, "Key iteration count is not positive"
end
it "raises an exception on negative key iteration count" do
expect {
LastPass::Fetcher.request_iteration_count username,
double("web_client", post: http_ok("-1"))
- }.to raise_error LastPass::InvalidResponse, "Key iteration count is not positive"
+ }.to raise_error LastPass::InvalidResponseError, "Key iteration count is not positive"
end
end
describe ".request_login" do
- it "makes a POST request" do
- expect(web_client = double("web_client")).to receive(:post)
- .with("https://lastpass.com/login.php", format: :xml, body: anything)
+ def verify_post_request multifactor_password, post_data
+ web_client = double("web_client")
+ expect(web_client).to receive(:post)
+ .with("https://lastpass.com/login.php", format: :xml, body: post_data)
.and_return(http_ok("ok" => {"sessionid" => session_id}))
- LastPass::Fetcher.request_login username, password, key_iteration_count, web_client
+ LastPass::Fetcher.request_login username,
+ password,
+ key_iteration_count,
+ multifactor_password,
+ web_client
end
+ it "makes a POST request" do
+ verify_post_request nil, login_post_data
+ end
+
+ it "makes a POST request with Google Authenticator code" do
+ verify_post_request google_authenticator_code, login_post_data_with_google_authenticator_code
+ end
+
+ it "makes a POST request with Yubikey password" do
+ verify_post_request yubikey_password, login_post_data_with_yubikey_password
+ end
+
it "returns a session" do
expect(request_login_with_xml "<ok sessionid='#{session_id}' />").to eq session
end
it "raises an exception on HTTP error" do
expect { request_login_with_error }.to raise_error LastPass::NetworkError
end
it "raises an exception when response is not a hash" do
- expect { request_login_with_ok "not a hash" }.to raise_error LastPass::InvalidResponse
+ expect { request_login_with_ok "not a hash" }.to raise_error LastPass::InvalidResponseError
end
it "raises an exception on unknown response schema" do
- expect { request_login_with_xml "<unknown />" }.to raise_error LastPass::UnknownResponseSchema
+ expect { request_login_with_xml "<unknown />" }.to raise_error LastPass::UnknownResponseSchemaError
end
it "raises an exception on unknown response schema" do
- expect { request_login_with_xml "<response />" }.to raise_error LastPass::UnknownResponseSchema
+ expect { request_login_with_xml "<response />" }.to raise_error LastPass::UnknownResponseSchemaError
end
it "raises an exception on unknown response schema" do
expect { request_login_with_xml "<response><error /></response>" }
- .to raise_error LastPass::UnknownResponseSchema
+ .to raise_error LastPass::UnknownResponseSchemaError
end
it "raises an exception on unknown username" do
message = "Unknown email address."
expect { request_login_with_lastpass_error "unknownemail", message }
- .to raise_error LastPass::LastPassUnknownUsername, message
+ .to raise_error LastPass::LastPassUnknownUsernameError, message
end
it "raises an exception on invalid password" do
message = "Invalid password!"
expect { request_login_with_lastpass_error "unknownpassword", message }
- .to raise_error LastPass::LastPassInvalidPassword, message
+ .to raise_error LastPass::LastPassInvalidPasswordError, message
end
+ it "raises an exception on missing Google Authenticator code" do
+ message = "Google Authenticator authentication required! " +
+ "Upgrade your browser extension so you can enter it."
+ expect { request_login_with_lastpass_error "googleauthrequired", message }
+ .to raise_error LastPass::LastPassIncorrectGoogleAuthenticatorCodeError, message
+ end
+
+ it "raises an exception on incorrect Google Authenticator code" do
+ message = "Google Authenticator authentication failed!"
+ expect { request_login_with_lastpass_error "googleauthfailed", message }
+ .to raise_error LastPass::LastPassIncorrectGoogleAuthenticatorCodeError, message
+ end
+
+ it "raises an exception on missing/incorrect Yubikey password" do
+ message = "Your account settings have restricted you from logging in " +
+ "from mobile devices that do not support YubiKey authentication."
+ expect { request_login_with_lastpass_error "yubikeyrestricted", message }
+ .to raise_error LastPass::LastPassIncorrectYubikeyPasswordError, message
+ end
+
it "raises an exception on unknown LastPass error with a message" do
message = "Unknow error message"
expect { request_login_with_lastpass_error "Unknown cause", message }
.to raise_error LastPass::LastPassUnknownError, message
end
@@ -118,11 +171,11 @@
end
describe ".fetch" do
it "makes a GET request" do
expect(web_client = double("web_client")).to receive(:get)
- .with("https://lastpass.com/getaccts.php?mobile=1&b64=1&hash=0.0",
+ .with("https://lastpass.com/getaccts.php?mobile=1&b64=1&hash=0.0&hasplugin=3.0.23&requestsrc=android",
format: :plain,
cookies: {"PHPSESSID" => session_id})
.and_return(http_ok(blob_response))
LastPass::Fetcher.fetch session, web_client
@@ -221,8 +274,9 @@
def request_login_with_response response
LastPass::Fetcher.request_login username,
password,
key_iteration_count,
+ nil,
double("web_client", post: response)
end
end