AutoEmail - 写了个监听文件修改,自动发送修改文件提示邮件的程序

AutoEmail - 写了个监听文件修改,自动发送修改文件提示邮件的程序

由于时间比较赶,现学一下午写的,很多细节没有考虑清楚,总体来说程序的鲁棒性并不算强。

链接:https://pan.baidu.com/s/1raxz-jlTmWib0gHi6YSSGw
提取码:zsrj

内含Java环境,没装Java环境需要先装好。(实在没弄明白Exe4j和inno怎么用,做出来的setup还是不能在无jre机器上跑)

1 配置发件人邮箱

发送邮件首先需要有一个邮箱账号和密码,本文以QQ邮箱为例,邮箱账号必须要开启SMTP 服务,操作步骤如下:

  • 首先登录网页版QQ邮箱(https://mail.qq.com

  • 点击“设置”

    image-20210413195300167
  • 点击“账户”

    image-20210413195343474
  • 向下滑动,找到“POP3/IMAP/SMTP/Exchange/CardDAV/CalDAV服务

    image-20210413195420280

    开启POP3/SMTP服务(示例图中已经开启)

  • 点击“生成授权码”,按照提示完成操作

    image-20210413195726813

    请记录这一步的授权码,方便后面使用。

2 监听文件

在进行这一步操作前,请确保你已经按照要求完成了步骤1。

Inked5MRUoTIeJ29Cg76_LI
  • 填写发件人

    发件人即你用来发送邮件的邮箱地址,本程序仅支持QQ/163/126邮箱

  • 填写密码

    这个密码并非qq邮箱的登录密码,而是第一步中的授权码。

  • 填写收件人

    收件人即用来接收邮件的邮箱地址,这个地址可以是任何邮箱。

  • 填写监听文件路径

    为了防止用户手动输入错误,此路径不能通过直接编辑更改。请点击“选择文件”按钮来选择你想要监听的文件。

  • 设置监听间隔(秒)

    监听间隔表示程序每隔多少秒监测一次目标文件是否被修改。在程序启动时,这个监听间隔被默认设置为60秒,你也可以手动输入一个\(\geqslant 1\)的整数来改变它。

最后,点击“开始/结束监测”,即可开始监听(再次按下本按钮可以停止监测)。

3 【推荐】导入已有的配置

为了避免每次运行本程序时,都需要重复填写一边收件人等基本信息,你可以将这些信息预先写入一个.txt文本文件中。

image-20210414093758719

这个.txt文本文件记录着发件人、密码、收件人、监听文件、监听间隔。你应该仿照图例来编写此文件

c6pNtO.png

然后将该文件存储到一个位置(本例中,我们将其命名为'conf.txt',你也可以更改为其他的名称)。然后,我们只需要点击导入已有配置按钮,选择刚刚存储的这个conf.txt,配置的信息就会被自动填充到程序中,最后点击开始/结束监测按钮即可。

4 组织结构及源码

c6u7hd.png·

GUI.java

package frame;

import java.awt.Color;
import java.awt.EventQueue;
import java.awt.Label;

import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.border.EmptyBorder;
import utils.MailUtils;
import javax.swing.JOptionPane;
import javax.swing.JTextField;
import javax.swing.JLabel;
import javax.swing.JButton;
import javax.swing.JFileChooser;

import java.awt.event.ActionListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.Date;
import java.util.regex.Pattern;
import java.awt.event.ActionEvent;

public class GUI extends JFrame {


	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	private JPanel contentPane;
	private JTextField fromField;
	private JTextField toField;
	private JTextField attachField;
	private JTextField passwordField;
	private int version = 0;
	private File checkFile;
	private Long lastModified;
	private int checkFreq;
	private boolean status;
	private Thread checkThread;
	private JTextField freqField;
	public static void main(String[] args) {
		EventQueue.invokeLater(new Runnable() {
			public void run() {
				try {
					GUI frame = new GUI();
					frame.setVisible(true);
				} catch (Exception e) {
					JOptionPane.showConfirmDialog(null,"图形用户界面创建失败","系统消息",JOptionPane.CLOSED_OPTION);
					e.printStackTrace();
				}
			}
		});
	}

	public GUI() {
		status = false;
		checkFreq = 60;
		/* 设定主窗口的基本参数 */
		
		setSize(600,400); 												
		setLocationRelativeTo(null); 									
		setVisible(true);				 								
		setTitle("AutoEmail");
		setDefaultCloseOperation(DO_NOTHING_ON_CLOSE);

		contentPane = new JPanel();
		contentPane.setForeground(new Color(153, 204, 255));
		contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
		
		setContentPane(contentPane);
		contentPane.setLayout(null);
		
		addWindowListener(new WindowAdapter() {							
			public void windowClosing(WindowEvent e) {
				int choice = JOptionPane.showConfirmDialog(null,"您确定要退出吗?","系统消息",JOptionPane.YES_NO_OPTION);
				if(choice == JOptionPane.YES_OPTION) {
					System.exit(0);
				}
			}
		});
		
		freqField = new JTextField();
		freqField.setText("60");
		freqField.setBounds(172, 263, 84, 21);
		contentPane.add(freqField);
		freqField.setColumns(10);
		
		JLabel freqLabel = new JLabel("\u76D1\u542C\u95F4\u9694\uFF08\u79D2\uFF09");
		freqLabel.setBounds(29, 266, 93, 15);
		contentPane.add(freqLabel);
		JLabel fromLabel = new JLabel("\u53D1\u4EF6\u4EBA");
		fromLabel.setBounds(29, 34, 54, 15);
		contentPane.add(fromLabel);
		
		JLabel passwordLabel = new JLabel("\u5BC6\u7801");
		passwordLabel.setBounds(29, 89, 54, 15);
		contentPane.add(passwordLabel);
		
		JLabel toLabel = new JLabel("\u6536\u4EF6\u4EBA");
		toLabel.setBounds(29, 154, 54, 15);
		contentPane.add(toLabel);
		
		JLabel attachPathLabel = new JLabel("\u76D1\u6D4B\u6587\u4EF6\u8DEF\u5F84");
		attachPathLabel.setBounds(29, 211, 93, 15);
		contentPane.add(attachPathLabel);
		
		fromField = new JTextField();
		fromField.setBounds(167, 31, 386, 21);
		contentPane.add(fromField);
		fromField.setColumns(10);
		
		passwordField = new JTextField();
		passwordField.setBounds(167, 86, 386, 21);
		contentPane.add(passwordField);
		passwordField.setColumns(10);
		
		toField = new JTextField();
		toField.setColumns(10);
		toField.setBounds(167, 151, 386, 21);
		contentPane.add(toField);
		
		attachField = new JTextField();
		attachField.setBackground(Color.YELLOW);
		attachField.setEditable(false);
		attachField.setColumns(10);
		attachField.setBounds(169, 208, 246, 21);
		contentPane.add(attachField);
		
		JButton attachChooseButton = new JButton("\u9009\u62E9\u6587\u4EF6");
		attachChooseButton.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				JFileChooser chooser = new JFileChooser();
				chooser.setFileSelectionMode(JFileChooser.FILES_ONLY);
				chooser.showDialog(new Label(), "选择监听文件");
				File file = chooser.getSelectedFile();
				if(file != null) {
					JOptionPane.showConfirmDialog(null, "选择文件成功", "系统消息", JOptionPane.CLOSED_OPTION);
					attachField.setText(file.getAbsolutePath().toString());
				}
			}
		});
		attachChooseButton.setBounds(458, 207, 93, 23);
		contentPane.add(attachChooseButton);
		
		JButton startButton = new JButton("\u5F00\u59CB/\u7ED3\u675F\u76D1\u6D4B");
		startButton.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				if(!Pattern.compile("^\\s*\\w+(?:\\.{0,1}[\\w-]+)*@[a-zA-Z0-9]+(?:[-.][a-zA-Z0-9]+)*\\.[a-zA-Z]+\\s*$").matcher(
						fromField.getText()).matches()) {
					JOptionPane.showConfirmDialog(null, "请检查邮箱格式", "邮箱格式错误", JOptionPane.CLOSED_OPTION);
				}else if(!Pattern.compile("^\\s*\\w+(?:\\.{0,1}[\\w-]+)*@[a-zA-Z0-9]+(?:[-.][a-zA-Z0-9]+)*\\.[a-zA-Z]+\\s*$").matcher(
						toField.getText()).matches()) {
					JOptionPane.showConfirmDialog(null, "请检查邮箱格式", "邮箱格式错误", JOptionPane.CLOSED_OPTION);
				}else if(passwordField.getText().isEmpty()) {
					JOptionPane.showConfirmDialog(null, "请输入stmp授权码(请参考用户手册)", "授权码为空", JOptionPane.CLOSED_OPTION);
				}else if(attachField.getText().isEmpty()) {
					JOptionPane.showConfirmDialog(null, "请选择待监听的文件", "未选择文件", JOptionPane.CLOSED_OPTION);
				}else if(freqField.getText().isEmpty()){
					JOptionPane.showConfirmDialog(null, "请选择监听间隔时间", "间隔时间不合法", JOptionPane.CLOSED_OPTION);
				}else if(status == false){
					checkFreq = Integer.valueOf(freqField.getText());
					status = true;
					MailUtils utils = new MailUtils();
					utils.init(fromField.getText(), passwordField.getText(), toField.getText());
					checkFile = new File(attachField.getText());
					lastModified = checkFile.lastModified();
					checkThread = new Thread() {
						public void run() {
							while(status) {
								Long currModified = checkFile.lastModified();
								try {
									if(currModified.longValue() != lastModified.longValue()) {
										utils.sendMessage("检测到文件更新[" + version + "]", 
												"更新时间: " + (new Date(currModified)).toString(), attachField.getText());
										lastModified = currModified;
										version += 1;
									}
									Thread.sleep(1000 * checkFreq);
								} catch (InterruptedException e) {
									e.printStackTrace();
								}
							}
						}
					};
					checkThread.start();
					JOptionPane.showConfirmDialog(null, "已开始监听", "系统消息", JOptionPane.CLOSED_OPTION);
				}else {
					JOptionPane.showConfirmDialog(null, "已停止监听", "系统消息", JOptionPane.CLOSED_OPTION);
					status = false;
				}
			}
		});
		
		
		startButton.setBounds(368, 312, 122, 31);
		contentPane.add(startButton);
		
		JButton confButton = new JButton("\u5BFC\u5165\u5DF2\u6709\u914D\u7F6E");
		confButton.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				JFileChooser chooser = new JFileChooser();
				chooser.setFileSelectionMode(JFileChooser.FILES_ONLY);
				chooser.showDialog(new Label(), "选择配置文件");
				File file = chooser.getSelectedFile();
				
				String[] conf = new String[10];
				int ptr = 0;
				
				if(file != null) {
					try {
						InputStreamReader reader = new InputStreamReader(
								new FileInputStream(file)); 
						BufferedReader br = new BufferedReader(reader);
						
						String line = "";
						line = br.readLine();
						while(line != null) {
							conf[ptr++] = line;
							line = br.readLine();
						}
						
						br.close();
						
						fromField.setText(conf[0]);
						passwordField.setText(conf[1]);
						toField.setText(conf[2]);
						attachField.setText(conf[3]);
						freqField.setText(conf[4]);
						checkFreq = Integer.valueOf(conf[4]);
						
					} catch (IOException e) {
						JOptionPane.showConfirmDialog(null,"文件读入错误", "系统错误",JOptionPane.CLOSED_OPTION);
					} 
				}
			}
		});
		confButton.setBounds(116, 312, 122, 31);
		contentPane.add(confButton);
		
		
	}
}

MailUtils.java

package utils;

import java.util.*;
import java.util.regex.Pattern;
import javax.mail.*;
import javax.mail.internet.*;
import javax.swing.JOptionPane;
import javax.activation.*;

public class MailUtils{
	private String from;
	private String host;
	private String password;
	private String to;
	
	private Session session;
	
	public void init(String _from, String _password, String _to) {
		from = _from;
		password = _password;
		to = _to;
		if(Pattern.compile("^.*@qq.com$").matcher(from).matches()) {
			host = "smtp.qq.com";
		}else if(Pattern.compile("^.*@163.com$").matcher(from).matches()) {
			host = "smtp.163.com";
		}else if(Pattern.compile("^.*@126.com$").matcher(from).matches()) {
			host = "smtp.126.com";
		}else {
			JOptionPane.showConfirmDialog(null, "仅支持QQ/163/126邮箱作为发件人", "发件人错误", JOptionPane.CLOSED_OPTION);
		}
		Properties properties = System.getProperties();
		properties.setProperty("mail.smtp.host", host);
		properties.put("mail.smtp.auth", "true");
		session = Session.getDefaultInstance(properties, new Authenticator() {
			public PasswordAuthentication getPasswordAuthentication() {
				return new PasswordAuthentication(from, password);
			}
		});
	}
	
	public void sendMessage(String subject, String text, String attachment) {
		try {
			MimeMessage message = new MimeMessage(session);
			message.setFrom(new InternetAddress(from));
			message.addRecipient(Message.RecipientType.TO, new InternetAddress(to));

			message.setSubject(subject);

			Multipart multipart = new MimeMultipart();
			
			BodyPart textPart = new MimeBodyPart();
			textPart.setText(text);

			BodyPart attachPart = new MimeBodyPart();
			DataSource source = new FileDataSource(attachment);
			attachPart.setDataHandler(new DataHandler(source));
			attachPart.setFileName(attachment);
			
			multipart.addBodyPart(textPart);
			multipart.addBodyPart(attachPart);
			
			message.setContent(multipart);
			
			Transport.send(message);
			System.out.println("发送成功!");
		} catch (MessagingException e) {
			e.printStackTrace();
		}
	}
}

posted @ 2021-04-14 09:41  popozyl  阅读(255)  评论(0编辑  收藏  举报