summaryrefslogtreecommitdiffstats
path: root/cloud_print
diff options
context:
space:
mode:
authormaksymb@chromium.org <maksymb@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-08-16 00:33:56 +0000
committermaksymb@chromium.org <maksymb@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-08-16 00:33:56 +0000
commitf7338e611f77821ed272c8c245db873d84d1ad27 (patch)
tree772fbced29e84a8ee0d19c921020772771649211 /cloud_print
parent2bec828dfe5a003391903726e1718b18d3d7559d (diff)
downloadchromium_src-f7338e611f77821ed272c8c245db873d84d1ad27.zip
chromium_src-f7338e611f77821ed272c8c245db873d84d1ad27.tar.gz
chromium_src-f7338e611f77821ed272c8c245db873d84d1ad27.tar.bz2
GCP2.0 Device: Instant AccessToken update on AuthFailed.
Also, registration timeout implemented. BUG= Review URL: https://chromiumcodereview.appspot.com/22184007 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@217880 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'cloud_print')
-rw-r--r--cloud_print/gcp20/prototype/cloud_print_request.cc7
-rw-r--r--cloud_print/gcp20/prototype/cloud_print_requester.cc15
-rw-r--r--cloud_print/gcp20/prototype/cloud_print_requester.h4
-rw-r--r--cloud_print/gcp20/prototype/printer.cc129
-rw-r--r--cloud_print/gcp20/prototype/printer.h26
-rw-r--r--cloud_print/gcp20/prototype/privet_http_server.cc4
-rw-r--r--cloud_print/gcp20/prototype/privet_http_server.h1
7 files changed, 133 insertions, 53 deletions
diff --git a/cloud_print/gcp20/prototype/cloud_print_request.cc b/cloud_print/gcp20/prototype/cloud_print_request.cc
index 2d36dcc..d8baec2 100644
--- a/cloud_print/gcp20/prototype/cloud_print_request.cc
+++ b/cloud_print/gcp20/prototype/cloud_print_request.cc
@@ -60,7 +60,6 @@ scoped_ptr<CloudPrintRequest> CloudPrintRequest::CreatePost(
void CloudPrintRequest::Run(
const std::string& access_token,
scoped_refptr<net::URLRequestContextGetter> context_getter) {
-
if (!access_token.empty())
fetcher_->AddExtraRequestHeader(base::StringPrintf(
"Authorization: Bearer \"%s\"", access_token.c_str()));
@@ -106,13 +105,13 @@ void CloudPrintRequest::OnURLFetchComplete(const URLFetcher* source) {
// this call.
} else {
- // TODO(maksymb): Add |server_http_code| and |server_api| info for errors.
+ // TODO(maksymb): Add Privet |server_http_code| and |server_api| support in
+ // case of server errors.
+ NOTIMPLEMENTED() << "HTTP code: " << http_code;
delegate_->OnFetchError("dummy", -1, http_code); // After this object can
// be deleted.
// Do *NOT* access members
// after this call.
-
- NOTIMPLEMENTED() << "HTTP code: " << http_code;
}
}
diff --git a/cloud_print/gcp20/prototype/cloud_print_requester.cc b/cloud_print/gcp20/prototype/cloud_print_requester.cc
index 1154d62..1910b7f 100644
--- a/cloud_print/gcp20/prototype/cloud_print_requester.cc
+++ b/cloud_print/gcp20/prototype/cloud_print_requester.cc
@@ -168,10 +168,15 @@ void CloudPrintRequester::OnFetchError(const std::string& server_api,
VLOG(3) << "Function: " << __FUNCTION__;
EraseRequest();
current_print_job_.reset();
- delegate_->OnServerError("Fetch error");
- // TODO(maksymb): |server_api| and other
- NOTIMPLEMENTED();
+ if (server_http_code == net::HTTP_FORBIDDEN) {
+ delegate_->OnAuthError();
+ } else {
+ delegate_->OnServerError("Fetch error");
+ }
+
+ // TODO(maksymb): Add Privet |server_http_code| and |server_api| support in
+ // case of server errors.
}
void CloudPrintRequester::OnFetchTimeoutReached() {
@@ -186,8 +191,8 @@ void CloudPrintRequester::OnGetTokensResponse(const std::string& refresh_token,
int expires_in_seconds) {
VLOG(3) << "Function: " << __FUNCTION__;
gaia_.reset();
- delegate_->OnGetAuthCodeResponseParsed(refresh_token,
- access_token, expires_in_seconds);
+ delegate_->OnRegistrationFinished(refresh_token,
+ access_token, expires_in_seconds);
}
void CloudPrintRequester::OnRefreshTokenResponse(
diff --git a/cloud_print/gcp20/prototype/cloud_print_requester.h b/cloud_print/gcp20/prototype/cloud_print_requester.h
index f9c2487..8e1e46c 100644
--- a/cloud_print/gcp20/prototype/cloud_print_requester.h
+++ b/cloud_print/gcp20/prototype/cloud_print_requester.h
@@ -39,9 +39,9 @@ class CloudPrintRequester : public base::SupportsWeakPtr<CloudPrintRequester>,
const std::string& complete_invite_url,
const std::string& device_id) = 0;
- // Invoked when server respond for registration-getAuthCode query and
+ // Invoked when server responded for registration-getAuthCode query and
// response is successfully parsed.
- virtual void OnGetAuthCodeResponseParsed(
+ virtual void OnRegistrationFinished(
const std::string& refresh_token,
const std::string& access_token,
int access_token_expires_in_seconds) = 0;
diff --git a/cloud_print/gcp20/prototype/printer.cc b/cloud_print/gcp20/prototype/printer.cc
index 4583aa7..02813ab 100644
--- a/cloud_print/gcp20/prototype/printer.cc
+++ b/cloud_print/gcp20/prototype/printer.cc
@@ -39,9 +39,9 @@ const char kPrinterDescription[] = "Printer emulator";
const char kUserConfirmationTitle[] = "Confirm registration: type 'y' if you "
"agree and any other to discard\n";
-const int64 kUserConfirmationTimeout = 30; // in seconds
-
-const uint32 kReconnectTimeout = 5; // in seconds
+const int kUserConfirmationTimeout = 30; // in seconds
+const int kRegistrationTimeout = 60; // in seconds
+const int kReconnectTimeout = 5; // in seconds
const double kTimeToNextAccessTokenUpdate = 0.8; // relatively to living time.
@@ -184,9 +184,8 @@ void Printer::Stop() {
void Printer::OnAuthError() {
LOG(ERROR) << "Auth error occurred";
- access_token_update_ = base::Time::Now();
- ChangeState(OFFLINE);
- // TODO(maksymb): Implement *instant* updating of access_token.
+ access_token_update_ = base::Time();
+ FallOffline(true);
}
std::string Printer::GetAccessToken() {
@@ -195,6 +194,15 @@ std::string Printer::GetAccessToken() {
PrivetHttpServer::RegistrationErrorStatus Printer::RegistrationStart(
const std::string& user) {
+ CheckRegistrationExpiration();
+
+ RegistrationInfo::ConfirmationState conf_state = reg_info_.confirmation_state;
+ if (reg_info_.state == RegistrationInfo::DEV_REG_REGISTRATION_ERROR ||
+ conf_state == RegistrationInfo::CONFIRMATION_TIMEOUT ||
+ conf_state == RegistrationInfo::CONFIRMATION_DISCARDED) {
+ reg_info_ = RegistrationInfo();
+ }
+
PrivetHttpServer::RegistrationErrorStatus status = CheckCommonRegErrors(user);
if (status != PrivetHttpServer::REG_ERROR_OK)
return status;
@@ -202,6 +210,8 @@ PrivetHttpServer::RegistrationErrorStatus Printer::RegistrationStart(
if (reg_info_.state != RegistrationInfo::DEV_REG_UNREGISTERED)
return PrivetHttpServer::REG_ERROR_INVALID_ACTION;
+ UpdateRegistrationExpiration();
+
reg_info_ = RegistrationInfo();
reg_info_.user = user;
reg_info_.state = RegistrationInfo::DEV_REG_REGISTRATION_STARTED;
@@ -242,6 +252,8 @@ PrivetHttpServer::RegistrationErrorStatus Printer::RegistrationGetClaimToken(
if (reg_info_.confirmation_state != RegistrationInfo::CONFIRMATION_CONFIRMED)
return ConfirmationToRegistrationError(reg_info_.confirmation_state);
+ UpdateRegistrationExpiration();
+
// If reply wasn't received yet, reply with |pending_user_action| error.
if (reg_info_.state == RegistrationInfo::DEV_REG_REGISTRATION_STARTED)
return PrivetHttpServer::REG_ERROR_PENDING_USER_ACTION;
@@ -268,6 +280,8 @@ PrivetHttpServer::RegistrationErrorStatus Printer::RegistrationComplete(
return PrivetHttpServer::REG_ERROR_INVALID_ACTION;
}
+ UpdateRegistrationExpiration();
+
if (reg_info_.confirmation_state != RegistrationInfo::CONFIRMATION_CONFIRMED)
return ConfirmationToRegistrationError(reg_info_.confirmation_state);
@@ -289,6 +303,8 @@ PrivetHttpServer::RegistrationErrorStatus Printer::RegistrationCancel(
if (reg_info_.state == RegistrationInfo::DEV_REG_UNREGISTERED)
return PrivetHttpServer::REG_ERROR_INVALID_ACTION;
+ InvalidateRegistrationExpiration();
+
reg_info_ = RegistrationInfo();
requester_.reset(new CloudPrintRequester(GetTaskRunner(), this));
@@ -296,13 +312,15 @@ PrivetHttpServer::RegistrationErrorStatus Printer::RegistrationCancel(
}
void Printer::GetRegistrationServerError(std::string* description) {
- DCHECK_EQ(reg_info_.state, RegistrationInfo::DEV_REG_REGISTRATION_ERROR) <<
- "Method shouldn't be called when not needed.";
+ DCHECK_EQ(reg_info_.state, RegistrationInfo::DEV_REG_REGISTRATION_ERROR)
+ << "Method shouldn't be called when not needed.";
*description = reg_info_.error_description;
}
void Printer::CreateInfo(PrivetHttpServer::DeviceInfo* info) {
+ CheckRegistrationExpiration();
+
// TODO(maksymb): Replace "text" with constants.
*info = PrivetHttpServer::DeviceInfo();
@@ -345,9 +363,11 @@ void Printer::OnRegistrationStartResponseParsed(
reg_info_.complete_invite_url = complete_invite_url;
}
-void Printer::OnGetAuthCodeResponseParsed(const std::string& refresh_token,
- const std::string& access_token,
- int access_token_expires_in_seconds) {
+void Printer::OnRegistrationFinished(const std::string& refresh_token,
+ const std::string& access_token,
+ int access_token_expires_in_seconds) {
+ InvalidateRegistrationExpiration();
+
reg_info_.state = RegistrationInfo::DEV_REG_REGISTERED;
reg_info_.refresh_token = refresh_token;
RememberAccessToken(access_token, access_token_expires_in_seconds);
@@ -380,20 +400,19 @@ void Printer::OnRegistrationError(const std::string& description) {
LOG(ERROR) << "server_error: " << description;
// TODO(maksymb): Implement waiting after error and timeout of registration.
- reg_info_.state = RegistrationInfo::DEV_REG_REGISTRATION_ERROR;
- reg_info_.error_description = description;
+ SetRegistrationError(description);
}
void Printer::OnNetworkError() {
VLOG(3) << "Function: " << __FUNCTION__;
- ChangeState(OFFLINE);
+ FallOffline(false);
}
void Printer::OnServerError(const std::string& description) {
VLOG(3) << "Function: " << __FUNCTION__;
LOG(ERROR) << "Server error: " << description;
- ChangeState(OFFLINE);
+ FallOffline(false);
}
void Printer::OnPrintJobsAvailable(const std::vector<Job>& jobs) {
@@ -439,7 +458,7 @@ void Printer::OnXmppAuthError() {
}
void Printer::OnXmppNetworkError() {
- ChangeState(OFFLINE);
+ FallOffline(false);
}
void Printer::OnXmppNewPrintJob(const std::string& device_id) {
@@ -542,9 +561,18 @@ void Printer::RememberAccessToken(const std::string& access_token,
SaveToFile();
}
+void Printer::SetRegistrationError(const std::string& description) {
+ DCHECK(!IsRegistered());
+ reg_info_.state = RegistrationInfo::DEV_REG_REGISTRATION_ERROR;
+ reg_info_.error_description = description;
+}
+
PrivetHttpServer::RegistrationErrorStatus Printer::CheckCommonRegErrors(
- const std::string& user) const {
+ const std::string& user) {
+ CheckRegistrationExpiration();
DCHECK(!IsRegistered());
+ if (connection_state_ != ONLINE)
+ return PrivetHttpServer::REG_ERROR_OFFLINE;
if (reg_info_.state != RegistrationInfo::DEV_REG_UNREGISTERED &&
user != reg_info_.user) {
@@ -554,10 +582,14 @@ PrivetHttpServer::RegistrationErrorStatus Printer::CheckCommonRegErrors(
if (reg_info_.state == RegistrationInfo::DEV_REG_REGISTRATION_ERROR)
return PrivetHttpServer::REG_ERROR_SERVER_ERROR;
+ DCHECK(connection_state_ == ONLINE);
+
return PrivetHttpServer::REG_ERROR_OK;
}
void Printer::WaitUserConfirmation(base::Time valid_until) {
+ // TODO(maksymb): Move to separate class.
+
if (base::Time::Now() > valid_until) {
reg_info_.confirmation_state = RegistrationInfo::CONFIRMATION_TIMEOUT;
LOG(INFO) << "Confirmation timeout reached.";
@@ -723,9 +755,28 @@ void Printer::PostOnIdle() {
base::Bind(&Printer::OnIdle, AsWeakPtr()));
}
+void Printer::CheckRegistrationExpiration() {
+ if (!registration_expiration_.is_null() &&
+ registration_expiration_ < base::Time::Now()) {
+ reg_info_ = RegistrationInfo();
+ InvalidateRegistrationExpiration();
+ if (connection_state_ != ONLINE)
+ TryConnect();
+ }
+}
+
+void Printer::UpdateRegistrationExpiration() {
+ registration_expiration_ =
+ base::Time::Now() + base::TimeDelta::FromSeconds(kRegistrationTimeout);
+}
+
+void Printer::InvalidateRegistrationExpiration() {
+ registration_expiration_ = base::Time();
+}
+
PrivetHttpServer::RegistrationErrorStatus
- Printer::ConfirmationToRegistrationError(
- RegistrationInfo::ConfirmationState state) {
+Printer::ConfirmationToRegistrationError(
+ RegistrationInfo::ConfirmationState state) {
switch (state) {
case RegistrationInfo::CONFIRMATION_PENDING:
return PrivetHttpServer::REG_ERROR_PENDING_USER_ACTION;
@@ -759,6 +810,23 @@ std::string Printer::ConnectionStateToString(ConnectionState state) const {
}
}
+void Printer::FallOffline(bool instant_reconnect) {
+ bool changed = ChangeState(OFFLINE);
+ DCHECK(changed) << "Falling offline from offline is now allowed";
+
+ if (!IsRegistered())
+ SetRegistrationError("Cannot access server during registration process");
+
+ if (instant_reconnect) {
+ TryConnect();
+ } else {
+ base::MessageLoop::current()->PostDelayedTask(
+ FROM_HERE,
+ base::Bind(&Printer::TryConnect, AsWeakPtr()),
+ base::TimeDelta::FromSeconds(kReconnectTimeout));
+ }
+}
+
bool Printer::ChangeState(ConnectionState new_state) {
if (connection_state_ == new_state)
return false;
@@ -771,26 +839,9 @@ bool Printer::ChangeState(ConnectionState new_state) {
dns_server_.UpdateMetadata(CreateTxt());
- switch (connection_state_) {
- case CONNECTING:
- break;
-
- case ONLINE:
- break;
-
- case OFFLINE:
- requester_.reset();
- xmpp_listener_.reset();
- base::MessageLoop::current()->PostDelayedTask(
- FROM_HERE,
- base::Bind(&Printer::TryConnect, AsWeakPtr()),
- base::TimeDelta::FromSeconds(kReconnectTimeout));
-
- case NOT_CONFIGURED:
- break;
-
- default:
- NOTREACHED();
+ if (connection_state_ == OFFLINE) {
+ requester_.reset();
+ xmpp_listener_.reset();
}
return true;
diff --git a/cloud_print/gcp20/prototype/printer.h b/cloud_print/gcp20/prototype/printer.h
index fab9189..b4ee260 100644
--- a/cloud_print/gcp20/prototype/printer.h
+++ b/cloud_print/gcp20/prototype/printer.h
@@ -115,7 +115,7 @@ class Printer : public base::SupportsWeakPtr<Printer>,
const std::string& registration_token,
const std::string& complete_invite_url,
const std::string& device_id) OVERRIDE;
- virtual void OnGetAuthCodeResponseParsed(
+ virtual void OnRegistrationFinished(
const std::string& refresh_token,
const std::string& access_token,
int access_token_expires_in_seconds) OVERRIDE;
@@ -165,11 +165,14 @@ class Printer : public base::SupportsWeakPtr<Printer>,
void RememberAccessToken(const std::string& access_token,
int expires_in_seconds);
+ // Sets registration state to error and adds description.
+ void SetRegistrationError(const std::string& description);
+
// Checks if register call is called correctly (|user| is correct,
// error is no set etc). Returns |false| if error status is put into |status|.
// Otherwise no error was occurred.
PrivetHttpServer::RegistrationErrorStatus CheckCommonRegErrors(
- const std::string& user) const;
+ const std::string& user);
// Checks if confirmation was received.
void WaitUserConfirmation(base::Time valid_until);
@@ -187,13 +190,27 @@ class Printer : public base::SupportsWeakPtr<Printer>,
// Adds |OnIdle| method to the MessageLoop.
void PostOnIdle();
+ // Registration timeout.
+ void CheckRegistrationExpiration();
+
+ // Delays expiration after user action.
+ void UpdateRegistrationExpiration();
+
+ // Deletes registration expiration at all.
+ void InvalidateRegistrationExpiration();
+
// Converts errors.
PrivetHttpServer::RegistrationErrorStatus ConfirmationToRegistrationError(
RegistrationInfo::ConfirmationState state);
std::string ConnectionStateToString(ConnectionState state) const;
- // Changes state and update info in DNS server.
+ // Changes state to OFFLINE and posts TryReconnect.
+ // For registration reconnect is instant every time.
+ void FallOffline(bool instant_reconnect);
+
+ // Changes state and update info in DNS server. Returns |true| if state
+ // was changed (otherwise state was the same).
bool ChangeState(ConnectionState new_state);
RegistrationInfo reg_info_;
@@ -224,6 +241,9 @@ class Printer : public base::SupportsWeakPtr<Printer>,
// Uses for calculating uptime.
base::Time starttime_;
+ // Uses to validate registration timeout.
+ base::Time registration_expiration_;
+
// Used for preventing two and more OnIdle posted in message loop.
bool on_idle_posted_;
diff --git a/cloud_print/gcp20/prototype/privet_http_server.cc b/cloud_print/gcp20/prototype/privet_http_server.cc
index 0a21059..45e633d 100644
--- a/cloud_print/gcp20/prototype/privet_http_server.cc
+++ b/cloud_print/gcp20/prototype/privet_http_server.cc
@@ -315,6 +315,10 @@ void PrivetHttpServer::ProcessRegistrationStatus(
case REG_ERROR_INVALID_ACTION:
*current_response = CreateError("invalid_action");
break;
+ case REG_ERROR_OFFLINE:
+ *current_response = CreateError("offline");
+ break;
+
case REG_ERROR_SERVER_ERROR: {
std::string description;
delegate_->GetRegistrationServerError(&description);
diff --git a/cloud_print/gcp20/prototype/privet_http_server.h b/cloud_print/gcp20/prototype/privet_http_server.h
index fc80d90..b551976 100644
--- a/cloud_print/gcp20/prototype/privet_http_server.h
+++ b/cloud_print/gcp20/prototype/privet_http_server.h
@@ -29,6 +29,7 @@ class PrivetHttpServer: public net::HttpServer::Delegate {
REG_ERROR_USER_CANCEL,
REG_ERROR_CONFIRMATION_TIMEOUT,
REG_ERROR_INVALID_ACTION,
+ REG_ERROR_OFFLINE,
REG_ERROR_SERVER_ERROR
};