首先要感谢博客园管理员的及时回复,本系列的第二篇文章得以恢复到首页,这是对作者的莫大鼓励.说实在的本来我真的挺受打击的.好在管理员说只是排版上有些问题,要用代码块修饰下相关的信息.说来惭愧因为常年编码已经习惯了用纯文本和空白行等处理文章,确实谈不上对文章排版,后面我会多学习应用排版功能.

经过前面两篇文章,假设大家已经学会了使用 telnet 命令行登录邮箱,那么我们可以开始学习发送邮件了!

这一次我先不讲原理,先上结果图和需要的命令行吧.

图1.发送成功的命令行截图

使用到的命令如下

 AUTH LOGIN
dGVzdDFAbmV3YnQubmV0
MTIzNDU2 MAIL FROM: <test1@newbt.net>
RCPT TO: <clq@newbt.net>
DATA From: "test1@newbt.net" <test1@newbt.net>
To: "clq@newbt.net" <clq@newbt.net>
Subject: test
Date: Sun, Jan :: GMT Hello World.
.

命令比之前的多了好多行啊! 其实原理要比登录那一篇简单多了,而且没有那么多兼容性的问题,命令格式很清晰.
具体要发送的命令其实只有三个:

 谁发的信(MAIL FROM:)
发信给谁(RCPT TO:)
信件的内容是什么(DATA)

这里仍然有几个要注意的地方:
1.目前真实的环境里要登录成功后才能用这些命令,虽然 smtp 协议没有这样规定;
2.MAIL FROM,RCPT TO 命令后要带有一个英文的 ":" 符号和一个英文的 "空格",千万不要在中文输入法状态下输入这两个符号,很多初学者都错在这个地方.再强调一次,那个空格一定要有,绝对不能省略,否则很多邮箱会收不到.

大家会问了,怎么只有三个命令,"from:" 那些不也是要输入的吗?
对,那些要输入,但不是 smtp 的命令,而是邮件的内容,它们实际上是 DATA 命令的组成部分,看到最后那个 "." 了吗? 那个英文句号可不是什么信件内容的结束符号,而是 DATA 命令的结束符号,它也不是一个点那么简单,实际上它的完整表达式应该是 "<CR><LF>.<CR><LF>".这里就要说到一个网络编程中极其重要的概念 -- 就是<CR><LF> -- 回车换行,初学者马上会说了这个我知道不就是 "\n" 嘛.我要说的是这只说对了一半,因为只对了一半在实际开发中就很致命,因为换行符有很严重的兼容性问题,大多数程序员都是 C 语言出身,他们在所有的教程中都学会了用 "\n" 来换行,但真实的操作系统中换行有的却是 "\r",有的则是两个字符"\r\n"(顺便提一下在 delphi 中是 #13#10),而 CRLF 概念就是用来解决这个问题的: 为了避免这种兼容性问题,rfc 规定网络通讯中的换行一律统一使用 "\r\n" 即 CR LF (Carriage Return, Line Feed) 两个字符一起固定表示网络命令的换行.

具体到 "<CR><LF>.<CR><LF>" 那就是说邮件内容结束时请先换行输入一个点,然后再换一次行才能表示这封信是写完了.记住!有两个换行! 这个结束符号到 DATA 命令之间的内容都是信件的内容.

好了,说到这里大家可以去试试了,不过这次得申请两个 newbt.net 的邮箱. 要注意信件中的内容 from,to 部分要和 MAIL FROM, RCPT TO 命令中的保持一致,否则在真实的环境中会被认成是垃圾邮件的.

说到垃圾邮件,那就更没有什么认定标准了,虽然业界内推出过很多反垃圾邮件的建议和标准,但实际上都没有真实可行.明白这个概念后我们才好说怎么发信给 163 的邮箱.

从理论上来说将邮件发送给 163 邮箱只要将前面的 RCPT TO 命令和邮件内容中的 to 部分改成 163 地址就可以了,例如:

 MAIL FROM: <test1@newbt.net>
RCPT TO: <clq_work@.com>
DATA From: "test1@newbt.net" <test1@newbt.net>
To: "clq_work@163.com" <clq_work@.com>
Subject: test
Date: Sun, Jan :: GMT Hello World.
.

图2.发送给163的命令行截图

图3.163 收到的信件

这里的 clq_work@163.com 是我的邮箱,我确实能收到,但换成你的地址后恐怕就不行了. why? 你会百思不得其解.解决的办法是你要先用你的 163 邮箱先给 test1@newbt.net 发一封信,或者是联系地址中加上这个地址.当然了这里要换成你自己申请的 newbt.net 邮箱. 这就是 163 邮箱收不到很多网站注册邮件的最主要的原因,也是为什么我要推荐 newbt.net 的原因.(当然这还不是唯一的原因) 如果你没用 newbt.net 而是 gmail 结果也是一样的,你会说 gmail 本来就发不了嘛,这个说法不对,不过换 qq 邮箱吧.运气好的话 qq 邮箱是能收到前几封 ... 这在学习过程中会造成很大的困扰, 163 的这种做法有好有坏也不能全盘否定. 另外我还要提醒一下大家,在很多很多时候163邮箱甚至收不到自己邮箱的来信,因为触发了它的反垃圾机制,这种情况在开发过程中很多见,比如你在上面的邮件内容中少写了一个标志,这时候你就会想,怎么没收到呢? from 不对? 密码不对? 地址不对? dns 不对? 我的邮箱服务器没连上163? 163服务器还没分发到我的邮箱?

所以 163 邮箱真是不适合用来开发,不过我很推荐您一切都测试无误后用 163 确认一下.因为在 163 的环境下都实现了还有什么环境不行的!(当然了实际还是有的) 所以 163 环境我每篇文章基本上都是要走一轮的.(163快给广告费)

好了,这一篇总算是结束了,我会排版好文章,也请读者们多给建议.

--------------------------------------------------

注1:需要说明的是这是最简单的电子邮件格式,真实的邮件内容要复杂得多,具体要等到我们说到 mime 格式后才能详细说了.

注2:要换用 163 邮箱发送的话记得登录前先发送 EHLO 命令(具体原因看本系列第二篇文章)

一步一步从原理跟我学邮件收取及发送 3.telnet命令行发一封信的更多相关文章

  1. 一步一步从原理跟我学邮件收取及发送 12.telnet命令行收一封信pop3

    本系列上一篇文章中我们就说到了,这一次我们要说 pop3 收信了.虽然我觉得应该先说完 mime 格式,不过估计大家已经不耐烦了 -- 怎么老在说发送啊?我们要看收取!    好吧,来啦,来啦!收取邮 ...

  2. 一步一步从原理跟我学邮件收取及发送 8.EHLO 命令详解

    我们在上一篇中解决了接收一行命令的问题后,就可以来具体的分析邮件发送过程中涉及到的 SMTP 协议内容了. 首先来看通讯过程中的第一个内容:服务器在客户端连接上来后会主动发送一个问好的信息,所以这第一 ...

  3. 一步一步从原理跟我学邮件收取及发送 2.邮箱的登录和绕不开的base64

    一步一步从原理跟我学邮件收取及发送 2.邮箱的登录和绕不开的base64 好了,经过本系列上一篇文章 "1.网络命令的发送",假设大家已经掌握了 email 电子邮件的命令发送的方 ...

  4. 一步一步从原理跟我学邮件收取及发送 4.不同平台下的socket

    既然是面向程序员的文章那当然不能只说说原理,一定要有实际动手的操作.    其实作为我个人的经历来说,对于网络编程,这是最重要的一章! 作为一位混迹业内近20年的快退休的程序员,我学习过很多的开发语言 ...

  5. 一步一步从原理跟我学邮件收取及发送 5.C语言的socket示例

    说到 C 语言版本的程序,首先要解决的问题就是兼容性. 作为 20 年开发有 10 多年是在服务端的程序员,我深刻地感受到服务端平台的两极分化之严重,linux 派对 windows 那是超级的不屑一 ...

  6. 一步一步从原理跟我学邮件收取及发送 10.四句代码说清base64

    经过前几篇的文章,大家应该都能预感到一定要讲解 base64 函数的内容了.是的,马上要到程序登录的代码,base64 是必须要实现的. base64 很早以前我就接触了,在项目中也很喜欢用.但每换一 ...

  7. 一步一步从原理跟我学邮件收取及发送 11.完整的发送示例与go语言

    经过了这个系列的前几篇文章的学习,现在要写出一个完整的 smtp 邮件发送过程简直易如反掌.    例如我们可以轻松地写出以下的纯 C 语言代码(引用的其他C语言文件请看文末的 github 地址): ...

  8. 一步一步从原理跟我学邮件收取及发送 9.多行结果与socket的阻塞

    前几篇的文章发表后,有网友留言说没有涉及到阻塞的问题吗?在 socket 的编程当中,这确实是个很重要的问题.结合目前我们文章的内容进度,我们来看看为什么说阻塞概念很重要. 接着上篇的内容,当我们发送 ...

  9. 一步一步从原理跟我学邮件收取及发送 13.mime格式与常见字符编码

    在前面的本系列文章中我们已经学会了邮件的发送和收取.但在收取中我们看到的是一串串的乱码,回忆前面的发送过程,我们会奇怪:我们前面的邮件是明文啊.为什么明文的邮件明明也可以正常工作,还要弄乱码似的字符串 ...

随机推荐

  1. ABP .Net Core API和Angular前端APP独立部署跨域问题(No Access-Control-Allow-Origin)

    前言: 通过ABP官网(https://aspnetboilerplate.com)下载ASP.NET Core 2.x + Angular模板项目是按ReStful风格架构Web API和angul ...

  2. springboot学习(三)————使用HttpMessageConverter进行http序列化和反序列化

    以下内容,如有问题,烦请指出,谢谢! 对象的序列化/反序列化大家应该都比较熟悉:序列化就是将object转化为可以传输的二进制,反序列化就是将二进制转化为程序内部的对象.序列化/反序列化主要体现在程序 ...

  3. bzoj 4444: [Scoi2015]国旗计划

    Description A国正在开展一项伟大的计划--国旗计划.这项计划的内容是边防战士手举国旗环绕边境线奔袭一圈.这 项计划需要多名边防战士以接力的形式共同完成,为此,国土安全局已经挑选了N名优秀的 ...

  4. bzoj 2726: [SDOI2012]任务安排

    Description 机 器上有N个需要处理的任务,它们构成了一个序列.这些任务被标号为1到N,因此序列的排列为1,2,3...N.这N个任务被分成若干批,每批包含相邻的 若干任务.从时刻0开始,这 ...

  5. Windows as a Service(1)—— Windows 10服务分支

    前言 作为公司的IT管理员,管理全公司Windows 10操作系统的更新一直是工作中的头疼之处.微软提供了很多方法来帮助我们管理公司的Windows 10更新,比如Windows Server Upd ...

  6. Ubuntu中启用ssh服务---转载

    ssh程序分为有客户端程序openssh-client和服务端程序openssh-server.如果需要ssh登陆到别的电脑,需要安装openssh-client,该程序Ubuntu是默认安装的.而如 ...

  7. c#程序连接mysql,报"Illegal mix of collations (utf8_general_ci,IMPLICIT) and (utf8_unicode_ci,IMPLICIT) for operation '='"的解决方案

    =============================================== 20170607_第一次修改                       ccb_warlock === ...

  8. Head First设计模式之命令模式

    一.定义 定义:将一个请求封装成一个对象,从而使您可以用不同的请求对客户进行参数化.对请求排队或记录请求日志,以及支持可撤消的操作. 主要解决:在软件系统中,行为请求者与行为实现者通常是一种紧耦合的关 ...

  9. Zabbix Agent端配置文件说明

    Zabbix Agent端配置文件说明 由于工作中经常接触到zabbix,所以将agent配置整理一下,方便日常查看. # This is a config file for the Zabbix a ...

  10. MySQL优化三 表结构优化

    由于MySQL数据库是基于行(Row)存储的数据库,而数据库操作 IO 的时候是以 page(block)的方式,也就是说,如果我们每条记录所占用的空间量减小,就会使每个page中可存放的数据行数增大 ...