Commit d4a9849b authored by Michael Gratton's avatar Michael Gratton 🤞 Committed by Michael Gratton

No folders listed when STATUS returns not found for a child

Cherry picked from 71d8c8b1

Fixes #156

See merge request !189
parent df910105
Pipeline #72343 passed with stages
in 59 minutes and 54 seconds
...@@ -243,9 +243,17 @@ public class Geary.Imap.Command : BaseObject { ...@@ -243,9 +243,17 @@ public class Geary.Imap.Command : BaseObject {
); );
} }
check_has_status();
// Since this is part of the public API, perform a strict // Since this is part of the public API, perform a strict
// check on the status code. // check on the status code.
check_status(true); if (this.status.status == Status.BAD) {
throw new ImapError.SERVER_ERROR(
"%s: Command failed: %s",
to_brief_string(),
this.status.to_string()
);
}
} }
public virtual string to_string() { public virtual string to_string() {
...@@ -276,9 +284,8 @@ public class Geary.Imap.Command : BaseObject { ...@@ -276,9 +284,8 @@ public class Geary.Imap.Command : BaseObject {
this.response_timer.reset(); this.response_timer.reset();
this.complete_lock.blind_notify(); this.complete_lock.blind_notify();
cancel_send(); cancel_send();
// Since this gets called by the client connection only check
// for an expected server response, good or bad check_has_status();
check_status(false);
} }
/** /**
...@@ -340,7 +347,7 @@ public class Geary.Imap.Command : BaseObject { ...@@ -340,7 +347,7 @@ public class Geary.Imap.Command : BaseObject {
} }
} }
private void check_status(bool require_okay) throws ImapError { private void check_has_status() throws ImapError {
if (this.status == null) { if (this.status == null) {
throw new ImapError.SERVER_ERROR( throw new ImapError.SERVER_ERROR(
"%s: No command response was received", "%s: No command response was received",
...@@ -355,16 +362,6 @@ public class Geary.Imap.Command : BaseObject { ...@@ -355,16 +362,6 @@ public class Geary.Imap.Command : BaseObject {
this.status.to_string() this.status.to_string()
); );
} }
// XXX should we be distinguishing between NO and BAD
// responses here?
if (require_okay && this.status.status != Status.OK) {
throw new ImapError.SERVER_ERROR(
"%s: Command failed: %s",
to_brief_string(),
this.status.to_string()
);
}
} }
private string to_brief_string() { private string to_brief_string() {
......
...@@ -835,6 +835,10 @@ public class Geary.Imap.ClientSession : BaseObject { ...@@ -835,6 +835,10 @@ public class Geary.Imap.ClientSession : BaseObject {
/** /**
* Performs the LOGIN command using the supplied credentials. * Performs the LOGIN command using the supplied credentials.
* *
* Throws {@link ImapError.UNAUTHENTICATED} if the credentials are
* bad, unsupported, or if authentication actually failed. Returns
* the status response for the command otherwise.
*
* @see initiate_session_async * @see initiate_session_async
*/ */
public async StatusResponse login_async(Geary.Credentials credentials, public async StatusResponse login_async(Geary.Credentials credentials,
...@@ -877,32 +881,40 @@ public class Geary.Imap.ClientSession : BaseObject { ...@@ -877,32 +881,40 @@ public class Geary.Imap.ClientSession : BaseObject {
// should always proceed; only an Error could change this // should always proceed; only an Error could change this
assert(params.proceed); assert(params.proceed);
GLib.Error? login_err = null; StatusResponse response = yield command_transaction_async(
try { cmd, cancellable
yield command_transaction_async(cmd, cancellable); );
} catch (Error err) {
login_err = err;
}
if (login_err != null) { if (response.status != Status.OK) {
// Throw an error indicating auth failed here, unless // Throw an error indicating auth failed here, unless
// there is a status response and it indicates that the // there is a status response and it indicates that the
// server is merely reporting login as being unavailable, // server is merely reporting login as being unavailable,
// then don't since the creds might actually be fine. // then don't since the creds might actually be fine.
ResponseCodeType? code_type = null; ResponseCode? code = response.response_code;
if (cmd.status != null) { if (code != null) {
ResponseCode? code = cmd.status.response_code; ResponseCodeType? code_type = code.get_response_code_type();
if (code != null) { if (code_type != null) {
code_type = code.get_response_code_type(); switch (code_type.value) {
case ResponseCodeType.UNAVAILABLE:
throw new ImapError.UNAVAILABLE(
"Login restricted: %s: ", response.to_string()
);
case ResponseCodeType.AUTHENTICATIONFAILED:
// pass through to the error being thrown below
break;
default:
throw new ImapError.SERVER_ERROR(
"Login error: %s: ", response.to_string()
);
}
} }
} }
if (code_type == null || throw new ImapError.UNAUTHENTICATED(
code_type.value != ResponseCodeType.UNAVAILABLE) { "Bad credentials: %s: ", response.to_string()
throw new ImapError.UNAUTHENTICATED(login_err.message); );
} else {
throw login_err;
}
} }
return cmd.status; return cmd.status;
...@@ -1715,6 +1727,9 @@ public class Geary.Imap.ClientSession : BaseObject { ...@@ -1715,6 +1727,9 @@ public class Geary.Imap.ClientSession : BaseObject {
this.cx.send_command(cmd); this.cx.send_command(cmd);
yield cmd.wait_until_complete(cancellable); yield cmd.wait_until_complete(cancellable);
// This won't be null since the Command.wait_until_complete
// will throw an error if it is.
return cmd.status; return cmd.status;
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment