1 /*****************************************************************
2 * Licensed to the Apache Software Foundation (ASF) under one *
3 * or more contributor license agreements. See the NOTICE file *
4 * distributed with this work for additional information *
5 * regarding copyright ownership. The ASF licenses this file *
6 * to you under the Apache License, Version 2.0 (the *
7 * "License"); you may not use this file except in compliance *
8 * with the License. You may obtain a copy of the License at *
9 * *
10 * http://www.apache.org/licenses/LICENSE-2.0 *
11 * *
12 * Unless required by applicable law or agreed to in writing, *
13 * software distributed under the License is distributed on an *
14 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY *
15 * KIND, either express or implied. See the License for the *
16 * specific language governing permissions and limitations *
17 * under the License. *
18 ****************************************************************/
19 package org.apache.james.pop3server;
20
21 import org.apache.avalon.cornerstone.services.sockets.SocketManager;
22 import org.apache.avalon.cornerstone.services.threads.ThreadManager;
23 import org.apache.avalon.framework.container.ContainerUtil;
24 import org.apache.commons.net.pop3.POP3Client;
25 import org.apache.commons.net.pop3.POP3MessageInfo;
26 import org.apache.james.core.MailImpl;
27 import org.apache.james.core.MimeMessageCopyOnWriteProxy;
28 import org.apache.james.core.MimeMessageInputStreamSource;
29 import org.apache.james.services.JamesConnectionManager;
30 import org.apache.james.services.MailServer;
31 import org.apache.james.services.UsersRepository;
32 import org.apache.james.test.mock.avalon.MockLogger;
33 import org.apache.james.test.mock.avalon.MockServiceManager;
34 import org.apache.james.test.mock.avalon.MockSocketManager;
35 import org.apache.james.test.mock.avalon.MockThreadManager;
36 import org.apache.james.test.mock.james.MockMailRepository;
37 import org.apache.james.test.mock.james.MockMailServer;
38 import org.apache.james.test.util.Util;
39 import org.apache.james.userrepository.MockUsersRepository;
40 import org.apache.james.util.connection.SimpleConnectionManager;
41 import org.apache.mailet.MailAddress;
42
43 import javax.mail.MessagingException;
44 import javax.mail.internet.MimeMessage;
45 import javax.mail.util.SharedByteArrayInputStream;
46
47 import java.io.Reader;
48 import java.util.ArrayList;
49
50 import junit.framework.TestCase;
51
52 /***
53 * Tests the org.apache.james.smtpserver.SMTPServer unit
54 */
55 public class POP3ServerTest extends TestCase {
56 private int m_pop3ListenerPort = Util.getNonPrivilegedPort();
57
58 private MockMailServer m_mailServer;
59
60 private POP3TestConfiguration m_testConfiguration;
61
62 private POP3Server m_pop3Server;
63
64 private MockUsersRepository m_usersRepository = new MockUsersRepository();
65 private POP3Client m_pop3Protocol = null;
66
67 public POP3ServerTest() {
68 super("POP3ServerTest");
69 }
70
71 protected void setUp() throws Exception {
72 m_pop3Server = new POP3Server();
73 ContainerUtil.enableLogging(m_pop3Server, new MockLogger());
74 ContainerUtil.service(m_pop3Server, setUpServiceManager());
75 m_testConfiguration = new POP3TestConfiguration(m_pop3ListenerPort);
76 }
77
78 private void finishSetUp(POP3TestConfiguration testConfiguration)
79 throws Exception {
80 testConfiguration.init();
81 ContainerUtil.configure(m_pop3Server, testConfiguration);
82 ContainerUtil.initialize(m_pop3Server);
83 }
84
85 private MockServiceManager setUpServiceManager() {
86 MockServiceManager serviceManager = new MockServiceManager();
87 SimpleConnectionManager connectionManager = new SimpleConnectionManager();
88 ContainerUtil.enableLogging(connectionManager, new MockLogger());
89 serviceManager.put(JamesConnectionManager.ROLE, connectionManager);
90 m_mailServer = new MockMailServer();
91 serviceManager
92 .put(MailServer.ROLE, m_mailServer);
93 serviceManager.put(UsersRepository.ROLE,
94 m_usersRepository);
95 serviceManager.put(SocketManager.ROLE, new MockSocketManager(
96 m_pop3ListenerPort));
97 serviceManager.put(ThreadManager.ROLE, new MockThreadManager());
98 return serviceManager;
99 }
100
101 protected void tearDown() throws Exception {
102 super.tearDown();
103 if (m_pop3Protocol != null) {
104 m_pop3Protocol.sendCommand("quit");
105 m_pop3Protocol.disconnect();
106 }
107 m_pop3Server.dispose();
108 }
109
110 public void testAuthenticationFail() throws Exception {
111 finishSetUp(m_testConfiguration);
112
113 m_pop3Protocol = new POP3Client();
114 m_pop3Protocol.connect("127.0.0.1", m_pop3ListenerPort);
115
116 m_usersRepository.addUser("known", "test2");
117
118 m_pop3Protocol.login("known", "test");
119 assertEquals(0, m_pop3Protocol.getState());
120 assertTrue(m_pop3Protocol.getReplyString().startsWith("-ERR"));
121 }
122
123 public void testUnknownUser() throws Exception {
124 finishSetUp(m_testConfiguration);
125
126 m_pop3Protocol = new POP3Client();
127 m_pop3Protocol.connect("127.0.0.1", m_pop3ListenerPort);
128
129 m_pop3Protocol.login("unknown", "test");
130 assertEquals(0, m_pop3Protocol.getState());
131 assertTrue(m_pop3Protocol.getReplyString().startsWith("-ERR"));
132 }
133
134 public void testKnownUserEmptyInbox() throws Exception {
135 finishSetUp(m_testConfiguration);
136
137 m_pop3Protocol = new POP3Client();
138 m_pop3Protocol.connect("127.0.0.1",m_pop3ListenerPort);
139
140 m_usersRepository.addUser("foo", "bar");
141 m_mailServer.setUserInbox("foo", new MockMailRepository());
142
143 m_pop3Protocol.login("foo", "bar");
144 System.err.println(m_pop3Protocol.getState());
145 assertEquals(1, m_pop3Protocol.getState());
146
147 POP3MessageInfo[] entries = m_pop3Protocol.listMessages();
148 assertEquals(1, m_pop3Protocol.getState());
149
150 assertNotNull(entries);
151 assertEquals(entries.length, 0);
152 }
153
154 public void testNotAsciiCharsInPassword() throws Exception {
155 finishSetUp(m_testConfiguration);
156
157 m_pop3Protocol = new POP3Client();
158 m_pop3Protocol.connect("127.0.0.1",m_pop3ListenerPort);
159
160 String pass = "bar" + (new String(new char[] { 200, 210 })) + "foo";
161 m_usersRepository.addUser("foo", pass);
162 m_mailServer.setUserInbox("foo", new MockMailRepository());
163
164 m_pop3Protocol.login("foo", pass);
165 assertEquals(1, m_pop3Protocol.getState());
166 }
167
168 public void testKnownUserInboxWithMessages() throws Exception {
169 finishSetUp(m_testConfiguration);
170
171 m_pop3Protocol = new POP3Client();
172 m_pop3Protocol.connect("127.0.0.1",m_pop3ListenerPort);
173
174 m_usersRepository.addUser("foo2", "bar2");
175 MockMailRepository mailRep = new MockMailRepository();
176
177 setupTestMails(mailRep);
178
179 m_mailServer.setUserInbox("foo2", mailRep);
180
181 m_pop3Protocol.login("foo2", "bar2");
182 assertEquals(1, m_pop3Protocol.getState());
183
184 POP3MessageInfo[] entries = m_pop3Protocol.listMessages();
185
186 assertNotNull(entries);
187 assertEquals(2, entries.length);
188 assertEquals(1, m_pop3Protocol.getState());
189
190 Reader r = m_pop3Protocol.retrieveMessageTop(entries[0].number, 0);
191 assertNotNull(r);
192 r.close();
193
194 Reader r2 = m_pop3Protocol.retrieveMessage(entries[0].number);
195 assertNotNull(r2);
196 r2.close();
197
198 boolean deleted = m_pop3Protocol.deleteMessage(entries[0].number);
199
200 assertTrue(deleted);
201 assertEquals(1, m_pop3Protocol.getState());
202
203 m_pop3Protocol.sendCommand("quit");
204 m_pop3Protocol.disconnect();
205
206 m_pop3Protocol.connect("127.0.0.1",m_pop3ListenerPort);
207
208 m_pop3Protocol.login("foo2", "bar2");
209 assertEquals(1, m_pop3Protocol.getState());
210
211 entries = null;
212
213 POP3MessageInfo stats = m_pop3Protocol.status();
214 assertEquals(92, stats.size);
215 assertEquals(1, stats.number);
216
217 entries = m_pop3Protocol.listMessages();
218
219 assertNotNull(entries);
220 assertEquals(1, entries.length);
221 assertEquals(1, m_pop3Protocol.getState());
222
223 Reader r3 = m_pop3Protocol.retrieveMessageTop(entries[0].number, 0);
224 assertNotNull(r3);
225 r3.close();
226 }
227
228 private void setupTestMails(MockMailRepository mailRep) throws MessagingException {
229 ArrayList recipients = new ArrayList();
230 recipients.add(new MailAddress("recipient@test.com"));
231 MimeMessage mw = new MimeMessageCopyOnWriteProxy(
232 new MimeMessageInputStreamSource(
233 "test",
234 new SharedByteArrayInputStream(
235 ("Return-path: return@test.com\r\n"+
236 "Content-Transfer-Encoding: plain\r\n"+
237 "Subject: test\r\n\r\n"+
238 "Body Text\r\n").getBytes())));
239 MailImpl m = new MailImpl("name", new MailAddress("from@test.com"),
240 recipients, mw);
241 mailRep.store(m);
242 MimeMessage mw2 = new MimeMessageCopyOnWriteProxy(
243 new MimeMessageInputStreamSource(
244 "test2",
245 new SharedByteArrayInputStream(
246 ("").getBytes())));
247 MailImpl mailimpl2 = new MailImpl("name2", new MailAddress("from@test.com"),
248 recipients, mw2);
249 mailRep.store(mailimpl2);
250 m.dispose();
251 mailimpl2.dispose();
252 }
253
254 public void testTwoSimultaneousMails() throws Exception {
255 finishSetUp(m_testConfiguration);
256
257
258 m_usersRepository.addUser("foo1", "bar1");
259 MockMailRepository mailRep1 = new MockMailRepository();
260 setupTestMails(mailRep1);
261 m_mailServer.setUserInbox("foo1", mailRep1);
262
263 m_usersRepository.addUser("foo2", "bar2");
264 MockMailRepository mailRep2 = new MockMailRepository();
265
266 m_mailServer.setUserInbox("foo2", mailRep2);
267
268 POP3Client pop3Protocol2 = null;
269 try {
270
271 m_pop3Protocol = new POP3Client();
272 m_pop3Protocol.connect("127.0.0.1", m_pop3ListenerPort);
273 pop3Protocol2 = new POP3Client();
274 pop3Protocol2.connect("127.0.0.1", m_pop3ListenerPort);
275
276 assertEquals("first connection taken", 0, m_pop3Protocol.getState());
277 assertEquals("second connection taken", 0, pop3Protocol2.getState());
278
279
280 m_pop3Protocol.login("foo1", "bar1");
281
282 pop3Protocol2.login("foo2", "bar2");
283
284 POP3MessageInfo[] entries = m_pop3Protocol.listMessages();
285 assertEquals("foo1 has mails", 2, entries.length);
286
287 entries = pop3Protocol2.listMessages();
288 assertEquals("foo2 has no mails", 0, entries.length);
289
290 } finally {
291
292 if (pop3Protocol2 != null) {
293 pop3Protocol2.sendCommand("quit");
294 pop3Protocol2.disconnect();
295 }
296 }
297 }
298
299 }