现贴出主要类,主要流程都在这个类中:
package com.blankenhorn.net.mail;
import java.io.*;
import java.net.InetAddress;
import java.net.Socket;
import java.net.SocketTimeoutException;
import java.util.Date;
import java.util.StringTokenizer;
/**
* Provides a simple way to send emails to an SMTP server.
*
* @author Kai Blankenhorn <<a href="mailto:pub01@bitfolge.de">pub01@bitfolge.de</a>>
*/
public class EasySMTPConnection {
private String server = null;
private BufferedReader in = null;
private BufferedWriter out = null;
private Socket socket = null;
/**
* Usage example.
*/
public static void main(String[] args) {
try {
EasySMTPConnection smtp = new EasySMTPConnection("127.0.0.1");
Message msg = new Message();
msg.setTo("");
String[] source = {
"From: Test User <test.user@foo.bar>",
"To: Kai Blankenhorn <pub01@bitfolge.de>,
Somebody <somebodysaddress@somebodysserver.com>",
"Subject: EasySMTPConnection Test",
"Date: insertdate",
"Content-Type: text/plain; charset=iso-8859-1",
// you may set the message ID, but you don't have to
// "Message-ID:
"+EasySMTPConnection.createMessageID("yourserver.com"),
"",
"first line,",
"second line",
"as you can see, no need for newlines (\\n)",
""
};
msg = new Message(source);
smtp.sendMessage(msg);
} catch(MailProtocolException e) {
e.printStackTrace();
}
catch(InstantiationException e) {
e.printStackTrace();
}
}
/**
* Creates a unique message ID for an email message.
*
* @param hostName the internet name of the computer the mail is being sent from
*/
public static String createMessageID(String hostName) {
String msgID = new Date().getTime() + ".";
msgID += Thread.currentThread().hashCode();
msgID += hostName;
msgID = "<"+msgID+">";
return msgID;
}
/**
* Establishes a connection to the specified SMTP server.
*
* @param server the SMTP server to connect to
*/
public EasySMTPConnection(String server) throws InstantiationException {
this.server = server;
try {
this.open();
} catch(SocketTimeoutException e) {
throw new InstantiationException("Timeout: " + e.getMessage());
}
catch(IOException e) {
throw new InstantiationException("IO error: " + e.getMessage());
}
}
/**
* Opens the connection to the server stored in <code>server</code>.
*/
protected void open() throws SocketTimeoutException, IOException {
socket = new Socket(server, 25);
socket.setSoTimeout(5000);
socket.setKeepAlive(true);
in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
out = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));
String response = read();
if(!response.startsWith("220")) {
throw new IOException(response);
}
writeln("HELO " + InetAddress.getByName(InetAddress.getLocalHost().getHostAddress())
.getHostName());
response = read();
if(!response.startsWith("2")) {
throw new IOException(response);
}
}
/**
* Close the connection.
*/
public void close() {
try {
writeln("QUIT");
socket.close();
} catch(SocketTimeoutException e) {
}
catch(IOException e) {
}
}
private String read() throws SocketTimeoutException, IOException {
String line = in.readLine();
return line;
}
private void writeln(String line) throws SocketTimeoutException, IOException {
out.write(line);
out.newLine();
out.flush();
}
/**
* Reads the server's response and checks the response code.
*
* @throws MailProtocolException if the code from the server is an error code (4xx or 5xx)
* @throws SocketTimeoutException if there was a timeout while reading from the server
* @throws IOException if there was some sort of network error
*/
protected void checkResponse() throws MailProtocolException, SocketTimeoutException, IOException {
String response = read();
if(response.startsWith("4") || response.startsWith("5")) {
throw new MailProtocolException(response);
}
}
/**
* Sends an array of Strings to the server. This method just constructs a new Message object
* based on <code>msgSource</code> and then calls {@link #sendMessage(Message)}
*
* @param msgSource An array of Strings, each element containing one line of the message source.
*
Note that
there has to be an empty line to seperate header and body of the
message.
*
You don't have
to (and you're not able to) end your message with a "." line, though.
*/
public void send(String[] msgSource) throws MailProtocolException {
Message msg = new Message(msgSource);
this.sendMessage(msg);
}
/**
* Sends a Message through the server corresponding to this instance of EasySMTPConnection.
*
* @param msg the Message to send
* @throws MailProtocolException if the server replied an error to one of the commands
*/
public void sendMessage(Message msg) throws MailProtocolException {
if (msg.getMessageID()==null || msg.getMessageID().equals("")) {
msg.setMessageID(EasySMTPConnection.createMessageID("yourserver.com"));
}
try {
socket.setSoTimeout(10000);
writeln("MAIL FROM:" + extractEmail(msg.getFrom()));
checkResponse();
StringTokenizer t = new StringTokenizer(msg.getTo(), ";,");
while(t.hasMoreTokens()) {
writeln("RCPT TO:" + extractEmail(t.nextToken()));
checkResponse();
}
t = new StringTokenizer(msg.getCC(), ";,");
while(t.hasMoreTokens()) {
writeln("RCPT TO:" + extractEmail(t.nextToken()));
checkResponse();
}
t = new StringTokenizer(msg.getBCC(), ";,");
while(t.hasMoreTokens()) {
writeln("RCPT TO:" + extractEmail(t.nextToken()));
checkResponse();
}
writeln("DATA");
checkResponse();
for(int i = 0; i < msg.getHeader().length; i++) {
writeln(encodeDot(msg.getHeader()[i]));
}
writeln("X-Sent-Through: EasySMTPConnection Java class
(http://www.bitfolge.de/en)");
writeln("");
for(int i = 0; i < msg.getBody().length; i++) {
writeln(encodeDot(msg.getBody()[i]));
}
writeln(".");
checkResponse();
} catch(IOException io) {
throw new MailProtocolException(io);
}
}
protected String extractEmail(String nameAndEmail) {
String result = nameAndEmail;
if(nameAndEmail.indexOf('<') > -1) {
result =
nameAndEmail.substring(nameAndEmail.indexOf('<') + 1,
nameAndEmail.indexOf('>'));
}
return result;
}
protected String encodeDot(String line) {
String result = line;
if(line.startsWith(".")) {
result = "." + result;
}
return result;
}
/**
* Closes the connection to the server upon finalization.
*/
public void finalize() {
this.close();
}
}
只有注册用户登录后才能阅读该文。
阅读全文
log4j配置文件的位置应该放在class文件的根目录下(或者源文件根根目录下),不要放在子目录下,否则会由于找不到log4j配置文件而出错.
一个quartz用的log4j配置文件内容如下:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/">
<appender name="default" class="org.apache.log4j.ConsoleAppender">
<param name="target" value="System.out"/>
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%p] %d{dd MMM hh:mm:ss.SSS aa} %t [%c]%n%m%n%n"/>
</layout>
</appender>
<logger name="org.quartz">
<level value="debug" />
</logger>
<root>
<level value="debug" />
<appender-ref ref="default" />
</root>
</log4j:configuration>
#DEBUG用来定义输出级别,比DEBUG高的都可以输出,后面的stdout,File为输出日志的输出地方
log4j.rootLogger=DEBUG, stdout,FILE
#定义stdout输出的格式
log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern=%c{1} - %m%n
#定义文件输出的格式
log4j.appender.FILE=org.apache.log4j.FileAppender
log4j.appender.FILE.File=d:\\log.txt
log4j.appender.FILE.Append=true
log4j.appender.FILE.layout=org.apache.log4j.PatternLayout
log4j.appender.FILE.layout.ConversionPattern=[send mail info] %d - %c -%-4r [%t] %-5p %c %x - %m%n
#其中,Log4j提供的appender有以下几种:
#org.apache.log4j.ConsoleAppender(控制台),
#org.apache.log4j.FileAppender(文件),
#org.apache.log4j.DailyRollingFileAppender(每天产生一个日志文件),
#org.apache.log4j.RollingFileAppender(文件大小到达指定尺寸的时候产生一个新的文件),
#org.apache.log4j.WriterAppender(将日志信息以流格式发送到任意指定的地方)
#其中,Log4j提供的layout有以下几种:
#org.apache.log4j.HTMLLayout(以HTML表格形式布局),
#org.apache.log4j.PatternLayout(可以灵活地指定布局模式),
#org.apache.log4j.SimpleLayout(包含日志信息的级别和信息字符串),
#org.apache.log4j.TTCCLayout(包含日志产生的时间、线程、类别等等信息)
# 下面是步骤,共10步
#1 定义了两个输出端
#log4j.rootLogger = debug, A1, A2
#2 定义A1输出到控制器
#log4j.appender.A1 = org.apache.log4j.ConsoleAppender
#3 定义A1的布局模式为PatternLayout
#log4j.appender.A1.layout = org.apache.log4j.PatternLayout
#4 定义A1的输出格式
#log4j.appender.A1.layout.ConversionPattern = %-4r [%t] %-5p %c - %m%n
#5 定义A2输出到文件
#log4j.appender.A2 = org.apache.log4j.RollingFileAppender
#6 定义A2要输出到哪一个文件
#log4j.appender.A2.File = D:\\hello.log
#7 定义A2的输出文件的最大长度
#log4j.appender.A2.MaxFileSize = 1KB
#8 定义A2的备份文件数
#log4j.appender.A2.MaxBackupIndex = 3
#9 定义A2的布局模式为PatternLayout
#log4j.appender.A2.layout = org.apache.log4j.PatternLayout
#10 定义A2的输出格式
#log4j.appender.A2.layout.ConversionPattern = %d{yyyy-MM-dd hh:mm:ss}:%p %t %c
#log4j.appender.R=org.apache.log4j.RollingFileAppender //指定以文件的方式输出日志
#log4j.appender.R.File=c:/sys.html //文件位置
#log4j.appender.R.MaxFileSize=500KB //文件最大尺寸
#log4j.appender.R.MaxBackupIndex=1 //备份数
#log4j.appender.R.layout=org.apache.log4j.HTMLLayout //文件的格式为Html格式
#log4j.appender.R.layout=org.apache.log4j.PatternLayout
#log4j.appender.R.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss,SSS} [%t] [%c] [%p] - %m%n
#输出格式
#%m 输出代码中指定的消息
#%p 输出优先级,即DEBUG,INFO,WARN,ERROR,FATAL
#%r 输出自应用启动到输出该log信息耗费的毫秒数
#%c 输出所属的类目,通常就是所在类的全名
#%t 输出产生该日志事件的线程名
#%n 输出一个回车换行符,Windows平台为“\r\n”,Unix平台为“\n”
#%d 输出日志时间点的日期或时间,默认格式为ISO8601,也可以在其后指定格式,比如:%d{yyy MMM dd HH:mm:ss,SSS},输出类似:2002年10月18日 22:10:28,921
#%l 输出日志事件的发生位置,包括类目名、发生的线程,以及在代码中的行数。举例:Testlog4.main(TestLog4.java:10)
#一个教程网址:http://www.solol.org/technologic/java/j-log4j/
http://jakarta.apache.org/commons/email/userguide.html.
注意要设置字符集
email.setCharset("gb2312");
Properties props = System.getProperties();
props.setProperty("proxySet", "true");
props.setProperty("http.proxyHost", "192.168.0.200");
props.setProperty("http.proxyPort", "3128");