📄 imapprotocol.java
字号:
// dispatch remaining untagged responses
notifyResponseHandlers(r);
handleResult(response);
return namespace;
}
/**
* GETQUOTAROOT Command.
*
* Returns an array of Quota objects, representing the quotas
* for this mailbox and, indirectly, the quotaroots for this
* mailbox.
*
* @see "RFC2087"
*/
public Quota[] getQuotaRoot(String mbox) throws ProtocolException {
if (!hasCapability("QUOTA"))
throw new BadCommandException("GETQUOTAROOT not supported");
// encode the mbox as per RFC2060
mbox = BASE64MailboxEncoder.encode(mbox);
Argument args = new Argument();
args.writeString(mbox);
Response[] r = command("GETQUOTAROOT", args);
Response response = r[r.length-1];
Hashtable tab = new Hashtable();
// Grab all QUOTAROOT and QUOTA responses
if (response.isOK()) { // command succesful
for (int i = 0, len = r.length; i < len; i++) {
if (!(r[i] instanceof IMAPResponse))
continue;
IMAPResponse ir = (IMAPResponse)r[i];
if (ir.keyEquals("QUOTAROOT")) {
// quotaroot_response
// ::= "QUOTAROOT" SP astring *(SP astring)
// read name of mailbox and throw away
ir.readAtomString();
// for each quotaroot add a placeholder quota
String root = null;
while ((root = ir.readAtomString()) != null)
tab.put(root, new Quota(root));
r[i] = null;
} else if (ir.keyEquals("QUOTA")) {
Quota quota = parseQuota(ir);
Quota q = (Quota)tab.get(quota.quotaRoot);
if (q != null && q.resources != null) {
// XXX - should merge resources
}
tab.put(quota.quotaRoot, quota);
r[i] = null;
}
}
}
// dispatch remaining untagged responses
notifyResponseHandlers(r);
handleResult(response);
Quota[] qa = new Quota[tab.size()];
Enumeration e = tab.elements();
for (int i = 0; e.hasMoreElements(); i++)
qa[i] = (Quota)e.nextElement();
return qa;
}
/**
* GETQUOTA Command.
*
* Returns an array of Quota objects, representing the quotas
* for this quotaroot.
*
* @see "RFC2087"
*/
public Quota[] getQuota(String root) throws ProtocolException {
if (!hasCapability("QUOTA"))
throw new BadCommandException("QUOTA not supported");
Argument args = new Argument();
args.writeString(root);
Response[] r = command("GETQUOTA", args);
Quota quota = null;
Vector v = new Vector();
Response response = r[r.length-1];
// Grab all QUOTA responses
if (response.isOK()) { // command succesful
for (int i = 0, len = r.length; i < len; i++) {
if (!(r[i] instanceof IMAPResponse))
continue;
IMAPResponse ir = (IMAPResponse)r[i];
if (ir.keyEquals("QUOTA")) {
quota = parseQuota(ir);
v.addElement(quota);
r[i] = null;
}
}
}
// dispatch remaining untagged responses
notifyResponseHandlers(r);
handleResult(response);
Quota[] qa = new Quota[v.size()];
v.copyInto(qa);
return qa;
}
/**
* SETQUOTA Command.
*
* Set the indicated quota on the corresponding quotaroot.
*
* @see "RFC2087"
*/
public void setQuota(Quota quota) throws ProtocolException {
if (!hasCapability("QUOTA"))
throw new BadCommandException("QUOTA not supported");
Argument args = new Argument();
args.writeString(quota.quotaRoot);
Argument qargs = new Argument();
if (quota.resources != null) {
for (int i = 0; i < quota.resources.length; i++) {
qargs.writeAtom(quota.resources[i].name);
qargs.writeNumber(quota.resources[i].limit);
}
}
args.writeArgument(qargs);
Response[] r = command("SETQUOTA", args);
Response response = r[r.length-1];
// XXX - It's not clear from the RFC whether the SETQUOTA command
// will provoke untagged QUOTA responses. If it does, perhaps
// we should grab them here and return them?
/*
Quota quota = null;
Vector v = new Vector();
// Grab all QUOTA responses
if (response.isOK()) { // command succesful
for (int i = 0, len = r.length; i < len; i++) {
if (!(r[i] instanceof IMAPResponse))
continue;
IMAPResponse ir = (IMAPResponse)r[i];
if (ir.keyEquals("QUOTA")) {
quota = parseQuota(ir);
v.addElement(quota);
r[i] = null;
}
}
}
*/
// dispatch remaining untagged responses
notifyResponseHandlers(r);
handleResult(response);
/*
Quota[] qa = new Quota[v.size()];
v.copyInto(qa);
return qa;
*/
}
/**
* Parse a QUOTA response.
*/
private Quota parseQuota(Response r) throws ParsingException {
// quota_response ::= "QUOTA" SP astring SP quota_list
String quotaRoot = r.readAtomString(); // quotaroot ::= astring
Quota q = new Quota(quotaRoot);
r.skipSpaces();
// quota_list ::= "(" #quota_resource ")"
if (r.readByte() != '(')
throw new ParsingException("parse error in QUOTA");
Vector v = new Vector();
while (r.peekByte() != ')') {
// quota_resource ::= atom SP number SP number
String name = r.readAtom();
if (name != null) {
long usage = r.readLong();
long limit = r.readLong();
Quota.Resource res = new Quota.Resource(name, usage, limit);
v.addElement(res);
}
}
r.readByte();
q.resources = new Quota.Resource[v.size()];
v.copyInto(q.resources);
return q;
}
/**
* SETACL Command.
*
* @see "RFC2086"
*/
public void setACL(String mbox, char modifier, ACL acl)
throws ProtocolException {
if (!hasCapability("ACL"))
throw new BadCommandException("ACL not supported");
// encode the mbox as per RFC2060
mbox = BASE64MailboxEncoder.encode(mbox);
Argument args = new Argument();
args.writeString(mbox);
args.writeString(acl.getName());
String rights = acl.getRights().toString();
if (modifier == '+' || modifier == '-')
rights = modifier + rights;
args.writeString(rights);
Response[] r = command("SETACL", args);
Response response = r[r.length-1];
// dispatch untagged responses
notifyResponseHandlers(r);
handleResult(response);
}
/**
* DELETEACL Command.
*
* @see "RFC2086"
*/
public void deleteACL(String mbox, String user) throws ProtocolException {
if (!hasCapability("ACL"))
throw new BadCommandException("ACL not supported");
// encode the mbox as per RFC2060
mbox = BASE64MailboxEncoder.encode(mbox);
Argument args = new Argument();
args.writeString(mbox);
args.writeString(user);
Response[] r = command("DELETEACL", args);
Response response = r[r.length-1];
// dispatch untagged responses
notifyResponseHandlers(r);
handleResult(response);
}
/**
* GETACL Command.
*
* @see "RFC2086"
*/
public ACL[] getACL(String mbox) throws ProtocolException {
if (!hasCapability("ACL"))
throw new BadCommandException("ACL not supported");
// encode the mbox as per RFC2060
mbox = BASE64MailboxEncoder.encode(mbox);
Argument args = new Argument();
args.writeString(mbox);
Response[] r = command("GETACL", args);
Response response = r[r.length-1];
// Grab all ACL responses
Vector v = new Vector();
if (response.isOK()) { // command succesful
for (int i = 0, len = r.length; i < len; i++) {
if (!(r[i] instanceof IMAPResponse))
continue;
IMAPResponse ir = (IMAPResponse)r[i];
if (ir.keyEquals("ACL")) {
// acl_data ::= "ACL" SPACE mailbox
// *(SPACE identifier SPACE rights)
// read name of mailbox and throw away
ir.readAtomString();
String name = null;
while ((name = ir.readAtomString()) != null) {
String rights = ir.readAtomString();
if (rights == null)
break;
ACL acl = new ACL(name, new Rights(rights));
v.addElement(acl);
}
r[i] = null;
}
}
}
// dispatch remaining untagged responses
notifyResponseHandlers(r);
handleResult(response);
ACL[] aa = new ACL[v.size()];
v.copyInto(aa);
return aa;
}
/**
* LISTRIGHTS Command.
*
* @see "RFC2086"
*/
public Rights[] listRights(String mbox, String user)
throws ProtocolException {
if (!hasCapability("ACL"))
throw new BadCommandException("ACL not supported");
// encode the mbox as per RFC2060
mbox = BASE64MailboxEncoder.encode(mbox);
Argument args = new Argument();
args.writeString(mbox);
args.writeString(user);
Response[] r = command("LISTRIGHTS", args);
Response response = r[r.length-1];
// Grab LISTRIGHTS response
Vector v = new Vector();
if (response.isOK()) { // command succesful
for (int i = 0, len = r.length; i < len; i++) {
if (!(r[i] instanceof IMAPResponse))
continue;
IMAPResponse ir = (IMAPResponse)r[i];
if (ir.keyEquals("LISTRIGHTS")) {
// listrights_data ::= "LISTRIGHTS" SPACE mailbox
// SPACE identifier SPACE rights *(SPACE rights)
// read name of mailbox and throw away
ir.readAtomString();
// read identifier and throw away
ir.readAtomString();
String rights;
while ((rights = ir.readAtomString()) != null)
v.addElement(new Rights(rights));
r[i] = null;
}
}
}
// dispatch remaining untagged responses
notifyResponseHandlers(r);
handleResult(response);
Rights[] ra = new Rights[v.size()];
v.copyInto(ra);
return ra;
}
/**
* MYRIGHTS Command.
*
* @see "RFC2086"
*/
public Rights myRights(String mbox) throws ProtocolException {
if (!hasCapability("ACL"))
throw new BadCommandException("ACL not supported");
// encode the mbox as per RFC2060
mbox = BASE64MailboxEncoder.encode(mbox);
Argument args = new Argument();
args.writeString(mbox);
Response[] r = command("MYRIGHTS", args);
Response response = r[r.length-1];
// Grab MYRIGHTS response
Rights rights = null;
if (response.isOK()) { // command succesful
for (int i = 0, len = r.length; i < len; i++) {
if (!(r[i] instanceof IMAPResponse))
continue;
IMAPResponse ir = (IMAPResponse)r[i];
if (ir.keyEquals("MYRIGHTS")) {
// myrights_data ::= "MYRIGHTS" SPACE mailbox SPACE rights
// read name of mailbox and throw away
ir.readAtomString();
String rs = ir.readAtomString();
if (rights == null)
rights = new Rights(rs);
r[i] = null;
}
}
}
// dispatch remaining untagged responses
notifyResponseHandlers(r);
handleResult(response);
return rights;
}
/*
* The tag used on the IDLE command. Set by idleStart() and
* used in processIdleResponse() to determine if the response
* is the matching end tag.
*/
private String idleTag;
/**
* IDLE Command. <p>
*
* If the server supports the IDLE command extension, the IDLE
* command is issued and this method blocks until a response has
* been received. Once the first response has been received, the
* IDLE command is terminated and all responses are collected and
* handled and this method returns. <p>
*
* Note that while this method is blocked waiting for a response,
* no other threads may issue any commands to the server that would
* use this same connection.
*
* @see "RFC2177"
* @since JavaMail 1.4.1
*/
public synchronized void idleStart() throws ProtocolException {
if (!hasCapability("IDLE"))
throw new BadCommandException("IDLE not supported");
Response r;
// write the command
try {
idleTag = writeCommand("IDLE", null);
r = readResponse();
} catch (LiteralException lex) {
r = lex.getResponse();
} catch (Exception ex) {
// Convert this into a BYE response
r = Response.byeResponse(ex);
}
if (!r.isContinuation())
handleResult(r);
}
/**
* While an IDLE command is in progress, read a response
* sent from the server. The response is read with no locks
* held so that when the read blocks waiting for the response
* from the server it's not holding locks that would prevent
* other threads from interrupting the IDLE command.
*
* @since JavaMail 1.4.1
*/
public synchronized Response readIdleResponse() {
if (idleTag == null)
return null; // IDLE not in progress
Response r;
try {
r = readResponse();
} catch (IOException ioex) {
// convert this into a BYE response
r = Response.byeResponse(ioex);
} catch (ProtocolException pex) {
// convert this into a BYE response
r = Response.byeResponse(pex);
}
return r;
}
/**
* Process a response returned by readIdleResponse().
* This method will be called with appropriate locks
* held so that the processing of the response is safe.
*
* @since JavaMail 1.4.1
*/
public boolean processIdleResponse(Response r) throws ProtocolException {
Response[] responses = new Response[1];
responses[0] = r;
boolean done = false; // done reading responses?
notifyResponseHandlers(responses);
if (r.isBYE()) // shouldn't wait for command completion response
done = true;
// If this is a matching command completion response, we are done
if (r.isTagged() && r.getTag().equals(idleTag))
done = true;
if (done)
idleTag = null; // no longer in IDLE
handleResult(r);
return !done;
}
// the DONE command to break out of IDLE
private static final byte[] DONE = { 'D', 'O', 'N', 'E', '\r', '\n' };
/**
* Abort an IDLE command. While one thread is blocked in
* readIdleResponse(), another thread will use this method
* to abort the IDLE command, which will cause the server
* to send the closing tag for the IDLE command, which
* readIdleResponse() and processIdleResponse() will see
* and terminate the IDLE state.
*
* @since JavaMail 1.4.1
*/
public void idleAbort() throws ProtocolException {
OutputStream os = getOutputStream();
try {
os.write(DONE);
os.flush();
} catch (IOException ex) {
// nothing to do, hope to detect it again later
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -