第一篇:读书笔记《Java邮件开发详解》
读书笔记《Java邮件开发详解》
DNS
MX
自动回复 不填from 避免循环回复。
Pop3:可以查邮件总数、已占空间。
电子邮件的RFC822格式:
Return-Path:代表邮件的回复地址,该字段的内容由接收邮件的SMTP服务器填写,接收邮件的SMTP服务器从邮件发送程序发出的mail form命令中获得内容。
Received:通常格式是:Received from A by B for C,A为发送方,B为接收方,C为收件人的邮箱地址。常常被用来追踪邮件传输的路线和分析邮件的来源。From:
To:
Subject:
Date:
Cc:
Bcc:
邮件的头字段可以扩充成MIME类型。Content-Type: multipart/mixed;头字段指定编码方法。另外,也定义了邮件头字段的内涵。
MIME消息的头字段具体资源的数据类型和组合消息的组合关系,都是通过消息头中的Content-Type头字段来指定的,格式为“主类型/子类型”的形式出现,主类型有text、image、audio、application、multipart、message等;每个主类型下面又都有好多子类型。
MIME消息可以有三种组合关系:
Multipart/mixed 混合组合 内容可以是文本、附件等等。
Multipart/related 关联组合 如邮件正文要使用HTML代码引用内嵌的图片资源。意思是说某些资源要关联引用另外的资源。
Multipart/alternative 选择组合这三种关系是可以随意嵌套的,比如你寄一个复杂的盒子出去,这个盒子里面可以有好多好多小盒子,而每个盒子都可以看作一个MIME。
其他的头字段都是顾名思义的,略!
设置内容的另一种方法:
setContent(Object object, String type)
setContent(body, “text/html;charset=gb2312”);
另外一种客户端的发信方式:SMTP服务器功能的邮件发送程序
具有SMTP服务器功能的邮件发送程序会根据收件人地址的域名,直接连接到该域的SMTP服务器和进行邮件发送。根本用不到„„
JNDI:命名式:把对象绑定到context中;目录式:保存对象的属性信息实际应用中命名式和对象式常常结合使用。
Tomcat可以通过配置文件自己创建javax.mail.Session
META-INF/context.xml
auth=”Container” type=”javax.mail.Session” mail.smtp.host=”smtp.sina.com.cn” mail.transport.protool=”smtp” mail.smtp.auth=”true” /> 在web.xml中说明一下,有资源是被tomcat创建的,如果换了别的应用服务器也要创建。 不知道书上为什么费那么大劲找个Session出来,还是个没有校验的Session,收发邮件时都得再写用户名密码给服务器。为什么不随便new一个或者从System中调一个呢?感觉基本用不着,我自己写一个properties文件岂不是更好? JAF 对于通过JAF封装的数据,应用程序通过JAF提供的接口可以完成如下功能:。访问数据源中的数据 。获知数据源的数据类型 。获知可对数据源进行的各种操作 。用户对数据源执行某种操作时,自动创建执行该操作的软件部件的实例对象 好像是用来封装数据源的(比如:声音文件,java文件),这样的好处是?可以识别文件类型对文件直接操作?不知道,回头再看看。好像是附件用的,ms。 邮件搜索 用于创建逻辑组合关系的类AND、OR、NOT、Comparison 用于创建具体搜索条件的类DATE、CONTENT、HEADER 例:SearchTerm st = new AndTerm(new FromStringTerm(“zx@sina.com”),new ReceivedDateTerm(ComparisonTerm.EQ, new Date())); 这里主要说明ComparisonTerm类,常用于日期类的比较其中使用留个常量来标识六种不同的操作:EQ(=)、GE(>=)、GT(>)、LE(<=)、LT(<)、NE(!=)邮件的解析与显示 如果Message的类型是“text/*”直接显示之。如果Message的类型 (getContentType())是“multipart/mixed”,调getContent()方法得到Multipart,对其调getCount()看看其中有多少个BodyPart,遍历之;当MIME类型为“text/*”显示之,当MIME是图片、声音或附件等二进制时,调 getDataHandler方法得到封装数据的对象,然后调其getInputSteam„„.;当MIME类型为“mutlipart/mixed”再次遍历得到其中的BodyPart。 注意:Message.isMimeType(“multipart/*”)这个方法居然可以写通配附?!看看API的解释:If the subType of mimeType is the special character '*', then the subtype is ignored during the comparison.。 处理内嵌类型的multipart(multipart/related)直接交给IE浏览器去显示就好了: response.setContentType(”message/rfc822”); message.writeTo(response.getOutputStream()); 总结: 总的来说这本书讲的很基础,前半部分告诉我们什么是email、email是如何收发的及email的格式、着重说明了smtp协议和pop3协议,甚至告诉大家怎么使用协议的命令收发邮件,这些对于使用API做web开发的程序员来说用处不是很大,但第3章邮件的组织结构讲述的还是比较好的;后半部分主要对Javamail进行说明,但是我个人觉得不如IBM的在线教程介绍的实用,主要是例子写的别扭,呵呵。不过里面有一些细节可以起到拓宽知识面的作用。 此书对开发webmail用处不是很大,比如对于pop3协议来说,如何标记邮件,如何建立文件夹,如何移动邮件,甚至通讯录什么的都一点也没有提到,讲邮件搜索的时候没有说邮件过滤能不能通过搜索实现或者还是有更好的办法。更深入一点的比如用工厂模式解耦合、使用线程池提高性能等更是只字未提。哎~看来还得再找找,实在不行就操作数据库,那样麻烦很多但是应该什么都能实现。最近看webmail看的很不爽,网上这样的东西也很少,感觉没有一个套路...郁闷~~ 读书笔记 1、类和对象:类是用来定义一组对象共同具有的状态和行为的模版。而对象是现实世界中个体或事物的抽象表示,并且封装了它们的属性和行为。 2、为了防止命名冲突,Java采用了管理类文件的机制,即类包机制。(package)定义包名的语法格式: “package包名;” Java命名规则要求包的命名需要使用小写字母。 3、成员变量和成员方法: 1成员变量是在类体中定义的变量即全局变量,○成员变量一般用于定义对象的状态。成员变量是给对象使用的,每个对象被创建后都会有属于自己的属性,即成员变量。通过修改这些属性,从而改变对象的某个状态。 2成员方法是对象行为的描述。○ 定义成员方法的语法格式: “[修饰符] 返回值类型方法名([形参表]){ ······//方法体 }” 修饰符:可以是:publicprivateprotactedstaticfinall等; 返回值类型:如果方法需要返回值,必须这里声明方法的返回值类型,可以是基 本数据类型(int short double booleanvoid等),也可以是对象 类型如:数组、字符串等。 形参表:(可选部分)说明方法被调用时应该向它传递的数据。形参表可以有一 个也可以有多个,当有多个形参时每个形参之间要用“,”隔开。 1创建对象:创建对象使用到new语句。 4、对象:○ 声明并创建对象的语法格式如下: “类名对象名=new 类构造方法()” 构造方法:构造方法是类创建对象是必须执行的方法,用于构造一个新的对象并 初始化对象属性。 2访问对象的属性: ○ 语法格式: “对象名.属性” 3执行对象的行为:○对象的行为就是对象的成员方法,通常说调用或执行对象的某个方法。 语法格式: “对象名.成员方法名();” 4对象的销毁:Java提供了垃圾回收机制,对不再使用的对象会自动销毁,也可○ 以在程序中显式的为某个对象赋null值,使对象不再被使用。 垃圾回收机制会找到并销毁它,释放该对象所占用的资源。 语法格式: “对象名=null” 1创建类:Java中使用class关键字来创建类。 5、类:○ 声明并创建类的语法格式: “权限修饰符 class类名{ 类体; }” 权限修饰符:(可选项)可以使用public protected private 或者省略这3者。类体主要由成员变量和方法两部分组成。 2成员变量:在Java中对象的属性也称为成员变量。○ 声明并创建成员变量的语法格式: “权限修饰符数据类型成员变量名;” (用static关键字定义的成员变量被称为静态成员变量即类变量。静态成员变量不是分配给每个对象的,而是属于累的变量。它在内存中是唯一的,可以直接使用“类名.成员变量名”的格式去访问,他在内存中的位置是固定的,是该类的所有实例对象所共享的存储单元。) 3成员方法:在Java语言中使用成员方法对应与类对象的行为。○ 定义成员方法的语法格式: “权限修饰符返回值类型方法名(参数类型参数名){ ·······//方法体 }” (同类变量一样,由static关键字定义的成员方法被称为类方法,类方法可以不必创建对象而由类直接访问,静态方法不可以直接调用非静态方法)4局部变量:○在方法体中声明的变量为局部变量,局部变量的有效范围为方法体结束。 5this关键字:在Java语言中用this关键字来代表类对象的引用,this关键字被○ 隐式地用于引用对象的成员变量和方法。(在类方法中不可以使用this关键字。)this关键字和和对象都可以调用成员变量和方法,两者的区别: 事实上,this引用的就是本类的一个对象,在局部变量或方法参数覆盖了成员变量时,就要添加this关键字明确引用的是类成员还是局部变量的方法参数。6类的构造方法:构造方法与类同名。○ 7类的主方法:主方法是类的入口点,它定义了程序从何处开始;主方法提供对○ 程序流向的控制,Java编译器通过主方法来执行程序。 1)主方法是静态的,所以如果要直接在主方法体中 调用其他方法,则该方法必须也是静态的。 2)主方法没有返回值。 3)主方法的形参为数组。其中args[0]~args[n]分别 代表程序的第一个参数到第n个参数,可以使用 args.length获取参数的个数。 Java中完整的类声明格式: “权限修饰符class类名{ 权限修饰符数据类型成员变量名1; 权限修饰符数据类型成员变量名2; ······· 权限修饰符数据类型成员变量名n; 权限修饰符返回值类型成员方法名1(形参类型形参变量){ 方法体 } 权限修饰符返回值类型成员方法名2(形参类型形参变量){ 方法体 } ······ 权限修饰符返回值类型成员方法名n(形参类型形参变量){ 方法体 } }” 6.由于类的主方法是静态方法所以不可以调用类中的非静态方法所以当需要调用非静态方法时必须创建对象来调用。在输入不同类型的数据时要使用不同的Scanner类对象,否则只能实现输入一种数据类型。 7.abstract关键字是定义抽象类的关键字。使用abstract定义的发放成为抽象方法。抽象方法没有方法体。抽象方法的唯一意义就是被重载。 个 人 简 历 个人信息 姓名:xxxxxxx性别:x 电话:187-xxx7-xxxx年龄:22 邮箱: lxxxxxxx@xxx.com专业:软件技术应聘职位 Java软件开发工程师 专业技能 熟练掌握CoreJava编程,具有扎实的编程功底和良好的编码习惯 熟练掌握ssh(Struts2+hibernate+Spring)等轻量级框架 熟悉MVC开发模式 熟练使用Eclipse/MyEclipse工具进行Java软件开发 熟练Unix/Linux环境下Java的应用软件开发 熟练掌握MySQL、Oracle等数据库操作,能编写常用SQL语句 熟悉软件开发的主要流程,可以根据指定要求快速完成设计、编码等工作了解xml、HTML、JavaScript、Ajax技术 项目经验 一、通用电子商务平台(当当网购物系统) 开发环境:Linux 开发工具:MyEclipse8.6,Tomcat,MySQL 技术实现:Struts2+Hibernate+Spring+JavaScript+JSP+AJAX 项目描述:此系统为网上购物系统,用户可以用过该系统实现网上购物、注册、登录、浏览商 品、订货、生成订单功能。也包括对普通商品增删改查功能和购物车内书的数量的增删改功能。 责任描述:独自完成项目的整个开发过程 用户模块包括登录与注册,主要使用了AJAX对其输入的信息进行验证,结合Hibernate存储和验证用户登录等。 商品列表模块主要是用List集合来展示商品。 购物车模块则是使用Session技术来保存购物车,通过Struts2调用不通方法来操作购物车中的商品集合,实现对购物车的增删改查。 订单模块主要是用Hibernate对用户所买商品的记录进行存储。 经验总结:这个项目让我们把我们所学习的三大框架以及JS,Ajax等都联系起来。尤其是使用 Hibernate经常出现异常,在和组内成员讨论中逐步解决问题,并且更加完善代码。 通过这个项目不仅提高我个人能力,而且还促进了与他人合作的能力。 二、教学管理系统 开发环境:Linux 开发工具:MyEclipse8.6,Tomcat,MySQL 技术实现:Struts2+JavaScript+JDBC+AJAX 项目描述:项目实现了管理员对教师信息的增删改查和对学生选课的管理 责任描述:独立完成该项目的设计和实现,主要应用MVC模式的设计思想对项目进行划分。 采用JDBC对教师信息进行增删改查,在学生选课模块,使用到了Ajax来对选课进 行检验。 经验总结: 通过该项目让我对MVC设计模式有了更深一步的认识。在数据的存储方面尤其是 对JDBC对数据存储的乱码问题。通过与组内成员的不懈努力将其克服。极大的锻 炼了自己团队合作能力,项目计划能力以及写文档的能力独立解决问题的能力。 三、其它项目:BBS论坛,交友网等 实习经历 2011/12 — 2012/05北京xxx科技Java工程师实习生 教育背景 2010/09―2012/07开封大学软件技术 所获证书 C+ E国际软件工程师Java培训证书 自我评价 专业技能:虽然在大学里,我学习的是软件技术专业,已经具备了一些专业方面的基础知识。但是想在行业中有更好的发展就必须学习更多与企业应用相关的知识,所以我选择来达内进行培训。在学习期间,我踏实勤奋,按时完成课后练习及作业,不断的积累代码量,同时也能帮同学解决一些力所能及的问题。遇到难题能够主动动手查阅资料,解决问题。通过项目实战提高我的个人能力和团队协作能力。 综合能力:性格比较沉稳,为人诚恳,不怕吃苦,有高度的责任心和团队合作精神。对环境的适应能力强,有较强的团队意识和集体荣誉感,做事情比较认真仔细,对每一件事情都能认真对待,能很好的自我调节。乐于学习新的知识与技术。 1、编写程序 题目:古典问题:有一对公母猪,从出生后第3个月起每个月都生一对猪,小猪长到第三个月后每个月又生一对猪,假如猪都不死,问每个月的猪总数为多少? 答案: public class lianxi01 { public static void main(String[] args){ System.out.println(“第1个月的兔子对数: 1”); System.out.println(“第2个月的兔子对数:1”); int f1 = 1, f2 = 1, f, M=24; for(int i=3;i<=M;i++){ f = f2; f2 = f1 + f2; f1 = f; System.out.println(“第” + i +“个月的兔子对数: ”+f2); } } } 2、是非题 2.1 Java程序中的起始类名称必须与存放该类的文件名相同。() 答案:正确 2.2 原生类中的数据类型均可任意转换。() 答案:错误 3、问答题 3.1 try {}里有一个return语句,那么紧跟在这个try后的finally {}里的code会不会被执行,什么时候被执行,在return前还是后? 答案: 会执行,在return前执行。 3.2 sleep()和 wait()有什么区别: 答案: sleep是线程类(Thread)的方法,导致此线程暂停执行指定时间,给执行机会给其他线程,但是监控状态依然保持,到时后会自动恢复。调用sleep不会 释放对象锁。wait是Object类的方法,对此对象调用wait方法导致本线程放弃对象锁,进入等待此对象的等待锁定池,只有针对此对象发出notify方法(或notifyAll)后本线程才进入对象锁定池准备获得对象锁进入运行状态。 4、数据库题 聚集函数的应用 编写一条sql语句,希望从艺术家表artist_tab中,看到只有一个专长specialty的是哪些专长 答案:seelctspecialty from artist_tab group by specialty having count(*)=1’; commons-fileupload-1.1.1.jar 上传文件总结: 1、验证是否要处理的是上传文件 ServletFileUpload.isMultipartContent(request) 2、创建DiskFileItemFactory 对象并对其初始化设置 DiskFileItemFactory factory = new DiskFileItemFactory(); factory.setSizeThreshold(20 * 1024); factory.setRepository(factory.getRepository()); 3、创建ServletFileUpload 对象并设置其编码方式 ServletFileUpload upload = new ServletFileUpload(factory); upload.setHeaderEncoding(“gbk”); 4、开始获取上传文件的集合: formlists = upload.parseRequest(request); 5、设置上传文件允许的大小 int size = 2 * 1024 * 1024; 6、循环遍历formlists集合来根据其元素的类型(普通表单域还是文件域)进行赋值还是上传功能 Iterator iter = formlists.iterator(); while(iter.hasNext()){ FileItem formitem =(FileItem)iter.next(); 7、是文件域则执行上传: 具体做法:(1)、获取文件路径全名:String name = formitem.getName(); (2)、判断文件名后缀是否符合要求:!name.endsWith(“mp3”) (3)、判断文件大小是否符合要求formitem.getSize()> size If/else(4)、都符合要求则上传: 第一步:判断文件的名称不能为空(formitem.getName())、大小不能为0 (formitem.getSize()),如果不符合要求则continue执行下一循环 第 二步: 获取文件的单纯文件名称: name.substring(name.lastIndexOf(“”) + 1, name.length()); 第 三步: 设置保存到的服务器地址:fileDir(“file/”)+ “” + 单纯名称;File saveFile = new File(服务器地址); 第 四步: 上传: formitem.write(saveFile);、是普通表单域则将表单项的值赋值给相关对象变量,如JavaBean(每一次循环将该次对应的表单项的值付 给适当的变量对象) String formname = formitem.getFieldName();获取普通表单项的名称 String con = formitem.getString(“gbk”); 用formname.equals(““)来判断 下载文件具体方法: 1、获取服务器下载地址并将此地址字符串进行编码: String path=request.getParameter(“path”); 2、创建下载目录: File file = new File(path);获取普通表单项的值并编码 path=new String(path.getBytes(“iso-8859-1”)); 3、创建文件字节输入流 InputStream in = new FileInputStream(file); 4、创建输出流对象 OutputStream os = response.getOutputStream(); 5、设置该输出流的应大头、编码等配置 response.addHeader(“Content-Disposition”, “attachment;filename=” + new String(file.getName().getBytes(“gbk”),“iso-8859-1”)); response.addHeader(“Content-Length”, file.length()+ “");response.setCharacterEncoding(”gbk“); 6、开始下载: int data = 0; while((data = in.read())!=-1) { os.write(data);} 7、关闭输入输出流 os.close(); in.close(); 邮件接收的方法: DAO: 1、创建邮件接收类:Store 思路:创建Properties类并添加属性->创建Session对象->创建store对象并连接到服务器和编写关闭方法 2、获取全部已读邮件的名称集合的方法 返回String3、获取全部已读或未读邮件的内容的方法返回List(包含邮件信息和附件状态,但不包含具体附件内容)思路: 获取Store对象->获取POP3Folder对象->打开POP3Folder邮件夹->创建FetchProfile预提取对象并对其添加两个常用属性->定义Message[]对象数组并设为null->获取全部已读邮件的uid字符串->若字符串不为空则->转换为数组并进行排序->根据要求的已读或者未读条件来获取全部已读或未读邮件信息给Message[](folder.search)->后退三步-若字符串为空则->获取全部未读邮件信息Message[]---开始提取上述邮件数组中每一个邮件的详细信息->循环遍历Message[]数组->定义MimeMessage对象并赋值为数组元素->获取邮件ID、发件人、邮件时间->根据编码类型获取邮件主题->由自定义方法获取此邮件的附件对象(String[])->message[i].getFlags().getSystemFlags().toString();->如果判断返回的邮件有附件,则获取附件设置为1,否则设置为0(来控制页面中的附件图标的显示)->将此邮件信息对象添加到List中。 4、向数据库中添加已读邮件的标记的方法:iduid address5、获取指定邮件中附件的方法:此方法中重点是对邮件内容的编码处理,故这里重点介绍主要功能语法: 思路:(1)定义该邮件名称对应的所有附件连接字符串为超链接(附件之间用空格隔开)(String,由多个”附件序号=&附件名称=&邮件序号”组成),定义邮件名称字符串(已知条件) (2)Multipart multipart =(Multipart)part.getContent();得到该邮件所有的内容集合,然后对其遍历以获取每一个multipart中每一个BodyPart->判断此BodyPart是否为附件,若是附件则获取该附件的名称 并添加到(1)中的连接字符串中,连接字符串中附件序号为遍历变量j 最后: int counts = multipart.getCount(); BodyPart对象的个数 //返回MimeMultipart对象中保存的//关闭流 response.setContentType(”application/octet-stream“); for(int i = 0;i < counts;i++){} getMailAttach(multipart.getBodyPart(i), emailv); 并返回String[] obj = { 邮件主题内容, fileName1 }; 6、对输入的UTF7编码的内容进行转码的方法 Servlet: 下载附件servlet: 思路:设置response.setContentType(”text/html;charset=GBK“)、request.setCharacterEncoding(”GBK“)->创建HttpSession对象->创建ServletOutputStream对象->获取页面传递变量:附件序号、附件名称;获取session变量”message“->将附件名称进行编码处理:filename=new String(filename.getBytes(),”ISO-8859-1“)->response.setHeader(”Content-Disposition“,”attachment;filename=“+filename)->由”message”获取Multipart对象->由Multipart对象获取BodyPart对象->由BodyPart对象获取InputStream对象->开始下载: int c=0; while((c=is.read())!=-1){out.write(c);} 收取邮件servlet(邮件的全部具体信息): 1、邮箱登陆的验证方法: 思路:获取表单传递值的host username pwd->用DAO(1)中的方法进行用户验证如果正确->创建HttpSession对象->用session.setAttribute的方法保存登陆的用户信息(以上三个)-> store.close(); 2、获取当前分页页面中已读或未读的全部邮件的集合(包含邮件信息和附件状态,但不包含具体附件内容)思路:创建HttpSession对象,并获session变量host username pwd和request变量”flag“和”Page“-> request.setAttribute(”flag“, flag)->根据request变量”page”来判断是否已经开始分页浏览->若没有则先执行DAO(3)方法获取已读或未读的全部邮件集合,然后执行自定义分页类中的初始化方法获取上述集合中的第一页中的邮件集合,并request.getSession().setAttribute(”pagination", 分页类的实例化);->若已经开始分页,则将当前页page赋值为已经存在的session类型的分页类对象中的getPage方法中返回的page,并且执行自定义分页类中的类似初始化方法的获取当前页面集合的方法(具体看程序) 3、查看邮件详细信息:(获取指定邮件的信息) 思路:同DAO(3)中的方法相似 不同之处是:DAO(3)查询的是全部已读或未读 而本案查询的是指定的邮件ID TOOLS: 本案中主要为分页类的编写: 1、初始化获取第一页的集合2、获取已分页的当前页面的集合3、获取全部记录数 4、获取最大页数 5、获取当前页数 6、获取分页导航第二篇:Java读书笔记
第三篇:JAVA开发个人简历
第四篇:java开发面试题
第五篇:java web邮件学习