Added: james/mangesieve/mailet/pom.xml URL: http://svn.apache.org/viewvc/james/mangesieve/mailet/pom.xml?rev=1236201&view=auto ============================================================================== --- james/mangesieve/mailet/pom.xml (added) +++ james/mangesieve/mailet/pom.xml Thu Jan 26 14:45:39 2012 @@ -0,0 +1,59 @@ + <!-- + Licensed to the Apache Software Foundation (ASF) under one + or more contributor license agreements. See the NOTICE file + distributed with this work for additional information + regarding copyright ownership. The ASF licenses this file + to you under the Apache License, Version 2.0 (the + "License"); you may not use this file except in compliance + with the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, + software distributed under the License is distributed on an + "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + KIND, either express or implied. See the License for the + specific language governing permissions and limitations + under the License. + --> +<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" + xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> + <modelVersion>4.0.0</modelVersion> + <parent> + <groupId>org.apache.james</groupId> + <artifactId>managesieve</artifactId> + <version>0.0.1-SNAPSHOT</version> + </parent> + + <groupId>org.apache.james</groupId> + <artifactId>managesieve-mailet</artifactId> + + <dependencies> + <dependency> + <groupId>${project.groupId}</groupId> + <artifactId>managesieve-core</artifactId> + <version>${project.version}</version> + <type>jar</type> + <scope>compile</scope> + </dependency> + <dependency> + <groupId>${project.groupId}</groupId> + <artifactId>apache-mailet</artifactId> + <version>${mailet.version}</version> + <scope>provided</scope> + </dependency> + <dependency> + <groupId>org.apache.james</groupId> + <artifactId>apache-mailet-base</artifactId> + <version>${mailet-base.version}</version> + <scope>provided</scope> + </dependency> + <dependency> + <groupId>${project.groupId}</groupId> + <artifactId>managesieve-mock</artifactId> + <version>${project.version}</version> + <type>jar</type> + <scope>test</scope> + </dependency> + </dependencies> +</project> \ No newline at end of file
Propchange: james/mangesieve/mailet/pom.xml ------------------------------------------------------------------------------ svn:eol-style = native Propchange: james/mangesieve/mailet/pom.xml ------------------------------------------------------------------------------ svn:mime-type = text/plain Added: james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/ManageSieveMailet.java URL: http://svn.apache.org/viewvc/james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/ManageSieveMailet.java?rev=1236201&view=auto ============================================================================== --- james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/ManageSieveMailet.java (added) +++ james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/ManageSieveMailet.java Thu Jan 26 14:45:39 2012 @@ -0,0 +1,277 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + * + */ + +package org.apache.james.managesieve.mailet; + +import java.io.IOException; +import java.io.InputStream; +import java.net.MalformedURLException; +import java.net.URL; +import java.util.Scanner; + +import javax.annotation.Resource; +import javax.mail.MessagingException; + +import org.apache.james.managesieve.api.SieveParser; +import org.apache.james.managesieve.api.SieveRepository; +import org.apache.james.managesieve.core.CoreProcessor; +import org.apache.james.managesieve.mailet.transcode.MessageToCoreToMessage; +import org.apache.james.managesieve.mailet.transcode.MessageToCoreToMessage.HelpProvider; +import org.apache.james.managesieve.transcode.LineToCore; +import org.apache.james.managesieve.transcode.LineToCoreToLine; +import org.apache.james.managesieve.util.SettableSession; +import org.apache.mailet.Mail; +import org.apache.mailet.MailAddress; +import org.apache.mailet.base.GenericMailet; + +/** + * <code>ManageSieveMailet</code> interprets mail from a local sender as + * commands to manage Sieve scripts stored on the mail server. The commands are + * a subset of those defined by <a + * href=http://tools.ietf.org/html/rfc5804#section + * -2>http://tools.ietf.org/html/rfc5804#section-2 "MessageToCoreToMessage"</a>. + * + * <p> + * For each supported command and associated response, the format is the same as + * defined by RFC 5804, with the exception that when Sieve scripts are involved + * in the exchange they are attached to the mail with the MIME type of + * 'application/sieve' rather than being embedded in the command. + * + * <p> + * The command is written in the subject header of a mail received by this + * mailet. Responses from this mailet are sent to the sender as mail with the + * message body containing the response. + * + * <p> + * The following commands are supported: + * <ul> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.4>CAPABILITY</a> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.5>HAVESPACE</a> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.6>PUTSCRIPT</a> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.7>LISTSCRIPTS</a> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.8>SETACTIVE</a> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.9>GETSCRIPT</a> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.10>DELETESCRIPT</a> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.11>RENAMESCRIPT</a> + * <li><a href=http://tools.ietf.org/html/rfc5804#section-2.12>CHECKSCRIPT</a> + * </ul> + * + * <h2>An Important Note About Security</h2> + * <p> + * The mail server on which this mailet is deployed MUST robustly authenticate + * the sender, who MUST be local. + * <p> + * Sieve provides powerful email processing capabilities that if hijacked can + * expose the mail of individuals and organisations to intruders. + */ +public class ManageSieveMailet extends GenericMailet implements HelpProvider { + + private class MailSession extends SettableSession { + + public MailSession() { + super(); + } + + /** + * @param mail + * the mail to set + */ + public void setMail(Mail mail) { + setUser(getUser(mail.getSender())); + setAuthentication(null != mail.getAttribute(SMTP_AUTH_USER_ATTRIBUTE_NAME)); + } + + protected String getUser(MailAddress addr) { + return new StringBuilder(addr.getLocalPart()) + .append('@') + .append(null == addr.getDomain() ? "localhost" : addr.getDomain()) + .toString(); + } + + } + + public final static String SMTP_AUTH_USER_ATTRIBUTE_NAME = "org.apache.james.SMTPAuthUser"; + + private MailSession _session = null; + + // Injected + private SieveRepository _sieveRepository = null; + + // Injected + private SieveParser _sieveParser = null; + + private MessageToCoreToMessage _transcoder = null; + + private URL _helpURL = null; + + private String _help = null; + + private boolean _cache = true; + + /** + * Creates a new instance of ManageSieveMailet. + * + */ + public ManageSieveMailet() { + super(); + } + + /** + * Creates a new instance of ManageSieveMailet. + * + * @param sieveRepository + * @param sieveParser + * @param usersRepository + */ + public ManageSieveMailet(SieveRepository sieveRepository, SieveParser sieveParser) + { + this(); + setSieveRepository(sieveRepository); + setSieveParser(sieveParser); + } + + /** + * @see org.apache.mailet.base.GenericMailet#init() + */ + @Override + public void init() throws MessagingException { + super.init(); + // Validate resources + if (null == _sieveParser) + { + throw new MessagingException("Missing resource \"sieveparser\""); + } + if (null == _sieveRepository) + { + throw new MessagingException("Missing resource \"sieverepository\""); + } + + setHelpURL(getInitParameter("helpURL")); + _cache = getInitParameter("cache", true); + _session = new MailSession(); + _transcoder = new MessageToCoreToMessage(new LineToCoreToLine(new LineToCore(new CoreProcessor(_session, + _sieveRepository, _sieveParser))), this); + } + + protected void setHelpURL(String helpURL) throws MessagingException + { + try + { + _helpURL = new URL(helpURL); + } + catch (MalformedURLException ex) + { + throw new MessagingException("Invalid helpURL", ex); + } + } + + /** + * @see org.apache.mailet.base.GenericMailet#service(org.apache.mailet.Mail) + */ + @Override + public void service(Mail mail) throws MessagingException { + + // Sanity checks + if (null == mail.getSender()) { + getMailetContext().log("ERROR: Sender is null"); + return; + } + + if (!getMailetContext().isLocalServer(mail.getSender().getDomain().toLowerCase())) { + getMailetContext().log("ERROR: Sender not local"); + return; + } + + // Update the Session for the current mail and execute + _session.setMail(mail); + getMailetContext().sendMail(_transcoder.execute(mail.getMessage())); + mail.setState(Mail.GHOST); + + // And tidy up + clearCaches(); + } + + protected void clearCaches() + { + if (!_cache) + { + _help = null; + } + } + + public String getHelp() throws MessagingException { + if (null == _help) + { + _help = computeHelp(); + } + return _help; + } + + protected String computeHelp() throws MessagingException + { + InputStream stream = null; + String help = null; + try { + stream = _helpURL.openStream(); + help = new Scanner(stream, "UTF-8").useDelimiter("\\A").next(); + } catch (IOException ex) { + throw new MessagingException("Unable to access help URL: " + _helpURL.toExternalForm(), ex); + } + finally + { + if (null != stream) + { + try { + stream.close(); + } catch (IOException ex) { + // no op + } + } + } + return help; + } + + /** + * @param sieveRepository + * the sieveRepository to set + */ + @Resource(name = "sieverepository") + public void setSieveRepository(SieveRepository repository) { + _sieveRepository = repository; + } + + /** + * @param sieveParser + * the sieveParser to set + */ + @Resource(name = "sieveparser") + public void setSieveParser(SieveParser sieveParser) { + _sieveParser = sieveParser; + } + + /** + * @see org.apache.mailet.base.GenericMailet#getMailetInfo() + */ + @Override + public String getMailetInfo() { + return getClass().getName(); + } + +} Propchange: james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/ManageSieveMailet.java ------------------------------------------------------------------------------ svn:eol-style = native Propchange: james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/ManageSieveMailet.java ------------------------------------------------------------------------------ svn:mime-type = text/plain Added: james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/transcode/MessageToCoreToMessage.java URL: http://svn.apache.org/viewvc/james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/transcode/MessageToCoreToMessage.java?rev=1236201&view=auto ============================================================================== --- james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/transcode/MessageToCoreToMessage.java (added) +++ james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/transcode/MessageToCoreToMessage.java Thu Jan 26 14:45:39 2012 @@ -0,0 +1,407 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + * + */ + +package org.apache.james.managesieve.mailet.transcode; + +import java.io.IOException; +import java.io.InputStream; +import java.net.InetAddress; +import java.net.UnknownHostException; +import java.util.HashMap; +import java.util.Map; +import java.util.Scanner; + +import javax.activation.DataHandler; +import javax.mail.Address; +import javax.mail.MessagingException; +import javax.mail.internet.InternetAddress; +import javax.mail.internet.MimeBodyPart; +import javax.mail.internet.MimeMessage; +import javax.mail.internet.MimeMultipart; +import javax.mail.util.ByteArrayDataSource; + +import org.apache.james.managesieve.transcode.LineToCoreToLine; +import org.apache.james.managesieve.util.ParserUtils; +import org.apache.mailet.base.RFC2822Headers; + +/** + * <code>MessageToCoreToMessage</code> + */ +public class MessageToCoreToMessage { + + public interface HelpProvider { + abstract public String getHelp() throws MessagingException; + } + + protected static String getScript(MimeMessage message) throws IOException, MessagingException { + String result = null; + if (message.getContentType().startsWith("multipart/")) { + MimeMultipart parts = (MimeMultipart) message.getContent(); + boolean found = false; + // Find the first part with any of: + // - an attachment type of "application/sieve" + // - a file suffix of ".siv" + // - a file suffix of ".sieve" + for (int i = 0; !found && i < parts.getCount(); i++) { + MimeBodyPart part = (MimeBodyPart) parts.getBodyPart(i); + found = part.isMimeType("application/sieve"); + if (!found) { + String fileName = null == part.getFileName() ? null : part.getFileName() + .toLowerCase(); + found = null != fileName + && (fileName.endsWith(".siv") || fileName.endsWith(".sieve")); + } + if (found) { + InputStream is = (InputStream) part.getContent(); + Scanner scanner = null; + try { + scanner = new Scanner(is, "UTF-8").useDelimiter("\\A"); + if (scanner.hasNext()) { + result = scanner.next(); + } + } finally { + if (null != scanner) { + scanner.close(); + } + } + } + } + } + if (null == result) + { + throw new MessagingException("Script part not found in this message"); + } + return result; + } + + protected static MimeBodyPart toPart(String name, String content) throws MessagingException, + IOException { + MimeBodyPart scriptPart = new MimeBodyPart(); + scriptPart.setDataHandler( + new DataHandler( + new ByteArrayDataSource( + content, + "application/sieve; charset=UTF-8") + )); + scriptPart.setDisposition(MimeBodyPart.ATTACHMENT); + scriptPart.setFileName(name); + return scriptPart; + } + + protected static MimeBodyPart toPart(String message) throws MessagingException { + MimeBodyPart part = new MimeBodyPart(); + part.setText(message); + part.setDisposition(MimeBodyPart.INLINE); + return part; + } + + private interface Executable { + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException; + } + + private Map<String, Executable> _commands = null; + + private LineToCoreToLine _adapter = null; + + private HelpProvider _helpProvider = null; + + private MessageToCoreToMessage() + { + super(); + _commands = computeCommands(); + } + + public MessageToCoreToMessage(LineToCoreToLine adapter, HelpProvider helpProvider) + { + this(); + _adapter = adapter; + _helpProvider = helpProvider; + } + + public MimeMessage execute(MimeMessage message) throws MessagingException { + // Extract the command and operands from the subject + String subject = null == message.getSubject() ? "" : message.getSubject(); + String[] args = subject.split(" ", 2); + // If there are no arguments, reply with help + String command = 0 == args.length ? "HELP" : args[0].toUpperCase(); + Executable executable = null; + // If the command isn't supported, reply with help + if (null == (executable = _commands.get(command))) { + executable = _commands.get("HELP"); + } + // Execute the resultant command... + MimeMultipart content = executable.execute(args.length > 1 ? args[1] : "", message); + // ...and wrap it in a MimeMessage + MimeMessage reply = (MimeMessage) message.reply(false); + reply.setContent(content); + if (null == message.getAllRecipients() || 0 >= message.getAllRecipients().length) { + throw new MessagingException("Message has no recipients"); + } else { + Address from = message.getAllRecipients()[0]; + reply.setFrom(from); + } + reply.saveChanges(); + return reply; + } + + protected Map<String, Executable> computeCommands() { + Map<String, Executable> commands = new HashMap<String, Executable>(); + commands.put("HELP", new Executable() { + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return help(operands, message); + } + }); + commands.put("CAPABILITY", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return capability(operands, message); + } + }); + commands.put("CHECKSCRIPT", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return checkScript(operands, message); + } + }); + commands.put("DELETESCRIPT", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return deleteScript(operands, message); + } + }); + commands.put("GETSCRIPT", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return getScript(operands, message); + } + }); + commands.put("HAVESPACE", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return haveSpace(operands, message); + } + }); + commands.put("LISTSCRIPTS", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return listScripts(operands, message); + } + }); + commands.put("PUTSCRIPT", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return putScript(operands, message); + } + }); + commands.put("RENAMESCRIPT", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return renameScript(operands, message); + } + }); + commands.put("SETACTIVE", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return setActive(operands, message); + } + }); + commands.put("GETACTIVE", new Executable() { + + public MimeMultipart execute(String operands, MimeMessage message) + throws MessagingException { + return getActive(operands, message); + } + }); + + return commands; + } + + protected MimeMultipart help(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(_helpProvider.getHelp())); + return multipart; + } + + protected MimeMultipart capability(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(_adapter.capability(operands))); + return multipart; + } + + protected MimeMultipart checkScript(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + String result = null; + Scanner scanner = new Scanner(operands).useDelimiter("\\A"); + if (scanner.hasNext()) { + result = "NO \"Too many arguments: " + scanner.next() + "\""; + } else { + try { + String content = getScript(message); + result = _adapter.checkScript(content); + } catch (MessagingException ex) { + result = "NO \"" + ex.getMessage() + "\""; + } catch (IOException ex) { + result = "NO \"Failed to read script part\""; + } + } + multipart.addBodyPart(toPart(result)); + return multipart; + } + + protected MimeMultipart deleteScript(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(_adapter.deleteScript(operands))); + return multipart; + } + + protected MimeMultipart getScript(String operands, MimeMessage message) + throws MessagingException { + String result = _adapter.getScript(operands); + // Everything but the last line is the script + // The last line is the response + String response = null; + String script = null; + int endOfScript = result.lastIndexOf("\r\n"); + if (endOfScript > 0) { + script = result.substring(0, endOfScript); + response = result.substring(endOfScript + "\r\n".length()); + } else { + response = result; + } + + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(response)); + if (null != script) { + try { + multipart.addBodyPart(toPart(ParserUtils.unquote(ParserUtils + .getScriptName(operands)), script)); + } catch (IOException ex) { + throw new MessagingException("Failed to add script part", ex); + } + } + return multipart; + } + + protected MimeMultipart haveSpace(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(_adapter.haveSpace(operands))); + return multipart; + } + + protected MimeMultipart listScripts(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(_adapter.listScripts(operands))); + return multipart; + } + + protected MimeMultipart putScript(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + String result = null; + String scriptName = ParserUtils.getScriptName(operands); + if (null == scriptName || scriptName.isEmpty()) { + result = "NO \"Missing argument: script name\""; + } else { + Scanner scanner = new Scanner(operands.substring(scriptName.length()).trim()) + .useDelimiter("\\A"); + if (scanner.hasNext()) { + result = "NO \"Too many arguments: " + scanner.next() + "\""; + } else { + StringBuilder builder = new StringBuilder(scriptName); + String content = null; + try { + content = getScript(message); + } catch (MessagingException ex) { + result = "NO \"" + ex.getMessage() + "\""; + } catch (IOException ex) { + result = "NO \"Failed to read script part\""; + } + if (null != content) { + builder + .append(' ') + .append(content); + } + result = _adapter.putScript(builder.toString().trim()); + } + } + multipart.addBodyPart(toPart(result)); + return multipart; + } + + protected MimeMultipart renameScript(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(_adapter.renameScript(operands))); + return multipart; + } + + protected MimeMultipart setActive(String operands, MimeMessage message) + throws MessagingException { + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(_adapter.setActive(operands))); + return multipart; + } + + protected MimeMultipart getActive(String operands, MimeMessage message) + throws MessagingException { + String result = _adapter.getActive(operands); + _adapter.getActive(operands); + // Everything but the last line is the script + // The last line is the response + String response = null; + String script = null; + int endOfScript = result.lastIndexOf("\r\n"); + if (endOfScript > 0) { + script = result.substring(0, endOfScript); + response = result.substring(endOfScript + "\r\n".length()); + } else { + response = result; + } + + MimeMultipart multipart = new MimeMultipart(); + multipart.addBodyPart(toPart(response)); + if (null != script) { + try { + multipart.addBodyPart(toPart("active", script)); + } catch (IOException ex) { + throw new MessagingException("Failed to add script part", ex); + } + } + return multipart; + } + +} Propchange: james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/transcode/MessageToCoreToMessage.java ------------------------------------------------------------------------------ svn:eol-style = native Propchange: james/mangesieve/mailet/src/main/java/org/apache/james/managesieve/mailet/transcode/MessageToCoreToMessage.java ------------------------------------------------------------------------------ svn:mime-type = text/plain Added: james/mangesieve/mailet/src/main/resources/managesieve.help.txt URL: http://svn.apache.org/viewvc/james/mangesieve/mailet/src/main/resources/managesieve.help.txt?rev=1236201&view=auto ============================================================================== --- james/mangesieve/mailet/src/main/resources/managesieve.help.txt (added) +++ james/mangesieve/mailet/src/main/resources/managesieve.help.txt Thu Jan 26 14:45:39 2012 @@ -0,0 +1,112 @@ +managesieve implements the commands defined by RFC 5804 ((http://tools.ietf.org/html/rfc5804) to manage sieve scripts via mail messages. A mail is sent to the managesieve user with the command and parameters in the subject header. Sieve scripts are exchanged as mail attachments. + +Consult your mail administrator for the name of the managesieve user configured for your installation. + +Users MUST be SMTP authenticated to execute all except the CAPABILITY and HELP commands (see note (1) below). + +Commands are executed and answered within the namespace of the sending user as denoted by the sender header of the mail. Thus, a command such as LISTSCRIPTS lists the scripts within namespace of the user identified by the sender header. + +The supported commands are summarised in "Command Summary" below. Generally the responses are self describing. For full details see RFC 5804 - Commands (http://tools.ietf.org/html/rfc5804#section-2). + +In these descriptions the following keywords apply: + +- sieve-name + The name of a sieve script enclosed in parentheses, eg: "my script". An empty name is not allowed. +- active-sieve-name + As sieve-name, except an empty name, eg: "", is allowed. +- old-sieve-name + As sieve-name +- new-sieve-name + As sieve-name +- sieve-script + A mail attachment recognised as a sieve script. This is the first attachment in a mail satisfying any of these characteristics: + - A MIME type of "application/sieve" + - A filename with the suffix ".sieve" + - A filename with the suffix ".siv" + Returned sieve-scripts always have the MIME type of "application/sieve" + +Command Summary +--------------- + +CAPABILITY + Subject: + CAPABILITY + Attachments: + none +Answers the capabilities of the underlying sieve inplementation. + +CHECKSCRIPT + Subject: + CHECKSCRIPT + Attachments: + sieve-script +Verifies the attached sieve-script without storing it on the server. + +DELETESCRIPT + Subject: + DELETESCRIPT sieve-name + Attachments: + none +Deletes the named sieve script. + +GETACTIVE + Subject: + GETACTIVE + Attachments: + none +Answers the active sieve script as an attachment. + +GETSCRIPT + Subject: + GETSCRIPT sieve-name + Attachments: + none +Answers the named sieve script as an attachment. + +HAVESPACE + Subject: + HAVESPACE sieve-name number + Attachments: + none +Answers OK if there is available space to store a script with the given name of the given size, else NO. + +HELP + Subject: + HELP + Attachments: + none +Answers this text. + +LISTSCRIPTS + Subject: + LISTSCRIPTS + Attachments: + none +Answers a list of the sieve scripts stored on the server, indicating which, if any, is the active script. + +PUTSCRIPT + Subject: + PUTSCRIPT sieve-name + Attachments: + sieve-script +Verifies the attached sieve-script and if there are no errors stores it on the server using the given name. + +RENAMESCRIPT + Subject: + RENAMESCRIPT old-sieve-name new-sieve-name + Attachments: + none +Renames the script stored on the server named old-sieve-name to new-sieve-name. + +SETACTIVE + Subject: + SETACTIVE active-sieve-name + Attachments: + none +Sets the active script on the server to the given name. Use an empty string, "", to deactivate all scripts. + +Notes +----- +1) Some mail servers optionally allow configurations that enable local clients to post without SMTP authentication, such configurations will fail as managesieve requires SMTP authentication in all circumstances. To repeat, users MUST be SMTP authenticated to execute all except the CAPABILITY and HELP commands. + + Propchange: james/mangesieve/mailet/src/main/resources/managesieve.help.txt ------------------------------------------------------------------------------ svn:eol-style = native Propchange: james/mangesieve/mailet/src/main/resources/managesieve.help.txt ------------------------------------------------------------------------------ svn:mime-type = text/plain --------------------------------------------------------------------- To unsubscribe, e-mail: server-dev-unsubscr...@james.apache.org For additional commands, e-mail: server-dev-h...@james.apache.org