001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one
003: * or more contributor license agreements. See the NOTICE file
004: * distributed with this work for additional information
005: * regarding copyright ownership. The ASF licenses this file
006: * to you under the Apache License, Version 2.0 (the
007: * "License"); you may not use this file except in compliance
008: * with the License. You may obtain a copy of the License at
009: *
010: * http://www.apache.org/licenses/LICENSE-2.0
011: *
012: * Unless required by applicable law or agreed to in writing,
013: * software distributed under the License is distributed on an
014: * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
015: * KIND, either express or implied. See the License for the
016: * specific language governing permissions and limitations
017: * under the License.
018: */
019:
020: package org.apache.axis2.transport.mail.server;
021:
022: import org.apache.axis2.transport.mail.Constants;
023: import org.apache.commons.logging.Log;
024: import org.apache.commons.logging.LogFactory;
025:
026: import javax.mail.MessagingException;
027: import javax.mail.internet.MimeMessage;
028: import java.io.BufferedReader;
029: import java.io.IOException;
030: import java.io.InputStream;
031: import java.io.InputStreamReader;
032: import java.io.PrintWriter;
033: import java.net.Socket;
034: import java.util.ArrayList;
035: import java.util.StringTokenizer;
036:
037: public class POP3Worker extends Thread {
038: private static final Log log = LogFactory.getLog(POP3Worker.class);
039: boolean doneProcess = false;
040: int numDeleted = 0; // This is a small hack to get the deleting working with the ArrayList. To keep it simple.
041: ArrayList messages = new ArrayList();
042: private Socket socket;
043: private Storage st;
044:
045: public POP3Worker(Socket socket, Storage st) {
046: this .socket = socket;
047: this .st = st;
048: }
049:
050: private void processInput(String input, PrintWriter printWriter) {
051: byte[] CR_LF_DOT_CR_LF = new byte[] { 0x0D, 0x0A, '.', 0x0D,
052: 0x0A };
053: String user = "";
054:
055: if (input == null) {
056: this .doneProcess = true; // This should not be happening
057: } else {
058: ArrayList tokens = new ArrayList();
059: StringTokenizer stk = new StringTokenizer(input);
060:
061: while (stk.hasMoreTokens()) {
062: tokens.add(stk.nextToken());
063: }
064:
065: if (tokens.get(0).equals(Constants.USER)) {
066: user = (String) tokens.get(1);
067: messages = st.popUserMails(user);
068: printWriter.println(Constants.OK);
069: } else if (tokens.get(0).equals(Constants.PASS)) {
070: printWriter.println(Constants.OK); // Passwords are not checked.
071: } else if (input.equals(Constants.QUIT)) {
072: printWriter.println(Constants.OK
073: + "POP3 server signing off");
074: doneProcess = true;
075: } else if (input.equals(Constants.STAT)) {
076: printWriter.println(Constants.OK + messages.size()
077: + " 1"); // We take the maildrop size as one.
078: } else if (tokens.get(0).equals(Constants.LIST)) { // scan listing
079: if (tokens.size() > 1) {
080: try {
081: int optArg = Integer.parseInt((String) tokens
082: .get(1));
083: int messageArrayIndex = optArg - 1;
084:
085: if ((messageArrayIndex < messages.size())
086: && (messageArrayIndex >= 0)) { // that is OK careful with numbering
087: printWriter.println(Constants.OK
088: + messageArrayIndex + 1 + " 120"); // Mail size of 120 is just some number.
089: } else {
090: printWriter.println(Constants.ERR
091: + "no such message, only "
092: + (messages.size() + 1)
093: + " messages in maildrop");
094: }
095: } catch (NumberFormatException e) {
096: log.info(e.getMessage());
097: printWriter
098: .println(Constants.ERR
099: + "problem passing the index. Index submited was "
100: + tokens.get(1));
101: }
102: } else {
103: printWriter.println(Constants.OK + messages.size());
104:
105: for (int i = 0; i < messages.size(); i++) {
106: int messageIndex = i + 1;
107:
108: printWriter.println(messageIndex + " 120"); // List out all the messages with a message size octet of 120
109: }
110:
111: printWriter.println(".");
112: }
113: } else if (tokens.get(0).equals(Constants.RETR)) {
114: String i = (String) tokens.get(1);
115:
116: try {
117: int index = Integer.parseInt(i);
118:
119: printWriter.println(Constants.OK);
120:
121: MimeMessage m = (MimeMessage) messages
122: .get(index - 1);
123:
124: m.writeTo(socket.getOutputStream());
125:
126: socket.getOutputStream().write(CR_LF_DOT_CR_LF); // This is a bit of a hack to get it working. Have to find a bette way to handle this.
127: socket.getOutputStream().flush();
128: } catch (NumberFormatException e) {
129: printWriter.println(Constants.ERR);
130: } catch (IOException e1) {
131: printWriter.println(Constants.ERR);
132: } catch (MessagingException e2) {
133: printWriter.println(Constants.ERR);
134: }
135: } else if (tokens.get(0).equals(Constants.DELE)) {
136: String smIndex = (String) tokens.get(1);
137:
138: try {
139: int mIndex = Integer.parseInt(smIndex) - 1
140: - numDeleted; // When one mail is deleted the index of the other mails will reduce. Asumed that the delete will occure from bottom up.
141:
142: if ((mIndex >= 0) && (mIndex < messages.size())) {
143: messages.remove(mIndex);
144: numDeleted++;
145: printWriter.println(Constants.OK);
146: } else {
147: printWriter.println(Constants.ERR);
148: }
149: } catch (NumberFormatException e) {
150: printWriter.println(Constants.ERR);
151: }
152: } else if (tokens.get(0).equals(Constants.NOOP)
153: || tokens.get(0).equals(Constants.RSET)) {
154: printWriter.println(Constants.OK);
155: } else {
156: printWriter.println(Constants.ERR);
157: }
158: }
159: }
160:
161: public void run() {
162: try {
163: InputStream inputStream = socket.getInputStream();
164: BufferedReader bufferedReader = new BufferedReader(
165: new InputStreamReader(inputStream));
166: PrintWriter printWriter = new PrintWriter(socket
167: .getOutputStream(), true);
168:
169: printWriter.println(Constants.OK + " POP3 server ready");
170:
171: String s;
172:
173: while (!doneProcess) {
174: s = bufferedReader.readLine();
175: processInput(s, printWriter);
176: }
177:
178: socket.close();
179: } catch (Exception e) {
180: log.error(e.getMessage(), e);
181: }
182: }
183: }
|