如何跨平台打开带主题和正文的默认邮件程序?
题
如何跨平台打开带主题和正文的默认邮件程序?
不幸的是,这是一个用 Java 编写的客户端应用程序,而不是一个网站。
我希望它能以跨平台的方式工作(这意味着 Windows 和 Mac,抱歉 Linux)。我很高兴在 Windows 中执行 VBScript,或在 OS X 中执行 AppleScript。但我不知道这些脚本应该包含什么。我很想执行用户的默认程序与用户的默认程序。只是搜索 Outlook 或其他内容。
在 OS X 中,我尝试执行以下命令:
open mailto:?subject=MySubject&body=TheBody
需要进行 URL 转义来替换空格 %20
.
更新 在 Windows 上,你必须玩各种游戏才能获得 start
才能正确运行。下面是正确的 Java 咒语:
class Win32 extends OS {
public void email(String subject, String body) throws Exception {
String cmd = "cmd.exe /c start \"\" \"" + formatMailto(subject, body) + "\"";
Runtime.getRuntime().exec(cmd);
}
}
解决方案
在 Java 1.6 中,您有一个标准的方法来打开平台的默认邮件程序:Desktop.mail(URI) 方法.URI可用于设置邮件的所有字段(发件人、收件人、正文、主题)。您可以查看 Java 1.6 中桌面集成的完整示例: 在 Java SE 6 中使用桌面 API
其他提示
start
在 Windows 中运行良好(见下文)。我会使用 Java 内置的 UrlEscape,然后运行“+”字符的第二个替换。
start mailto:"?subject=My%20Subject&body=The%20Body"
1.添加主题行
您可以通过添加前面带有 ' 的主题来预填充电子邮件中的主题行?主题=' 在电子邮件地址之后。
所以链接现在变成:
<a href="mailto:someone@yoursite.com?subject=Mail from Our Site">Email Us</a>
2.发送给多个收件人
邮件可以以抄送 (cc) 或密件抄送 (bcc) 的形式发送给其他收件人。
这是以类似的方式完成的,通过放置 '?cc=someoneelse@theirsite.com' 在初始地址之后。
所以链接看起来像这样:
<a href="mailto:someone@yoursite.com?cc=someoneelse@theirsite.com">Email Us</a>
如果您想发送密件抄送,只需将抄送替换为密件抄送即可。
如果您的页面上有不同主题的链接,这会非常有用。您可能会将每一页上的电子邮件发送给公司中的相应人员,但所有邮件的副本也会发送到一个中心地址。
您当然可以指定多个附加收件人,只需用逗号分隔收件人列表即可。
<a href="mailto:someone@yoursite.com?cc=someoneelse@theirsite.com, another@thatsite.com, me@mysite.com">Email Us</a>
源自 从“mailto”中获取更多信息 现在是 404。我从 waybackmachine 检索了内容。
3.组合代码
您可以通过在每个代码之间添加“&”来组合上面的各个代码位。
因此添加
me@mysite.com?subject=Hello&cc=you@yoursite.com&bcc=her@hersite.com
会向我、你和她发送一封主题为“你好”的电子邮件。
4.写电子邮件
您还可以在邮件正文中预先填写邮件正文,或者根据需要编写整个邮件!要在电子邮件正文中添加一些内容,也像上面一样简单 - '?正文=' 在电子邮件地址之后。然而,格式化该电子邮件可能有点棘手。要在单词之间创建空格,您必须使用十六进制代码 - 例如 '%20' 在每个单词之间,创建新行意味着添加 '%0D'。类似的符号如 $ 符号需要用十六进制代码编写。
如果您还希望添加主题行并将副本发送给多个收件人,这可能会导致代码变得非常长且难以编写。
它将向三个人发送一条消息,填写主题和消息,您所需要做的就是添加您的名字。
看看代码吧!
<a href="mailto:abbeyvet@outfront.net?CC=spooky@outfront.net
&BCC=thomasbrunt@outfront.net&Subject=Please%2C%20I%20insist
%21&Body=Hi%0DI%20would%20like%20to%20send%20you%20
%241000000%20to%20divide%20as%20you%20see%20fit%20among
%20yourselves%20and%20all%20the%20moderators.%0DPlease%
20let%20me%20know%20to%20whom%20I%20should%20send
%20the%20check.">this link</a>
笔记:我发现这个的原始源 URL 现在是 404ing,所以我 从 waybackmachine 抓取内容 并将其张贴在这里,以免丢失。此外,OP 表示它不适用于网站,这就是这些示例的目的,但其中一些技术可能仍然有用。
我不得不重新实现URLENCODE,因为Java可以使用 +用于空间,并且邮件从字面上拿走了。
我不知道Java是否有一些内置的方法来对字符串进行urlencoding,但是这个链接 http://www.permadi.com/tutorial/urlEncoding/ 显示了一些最常见的编码字符:
; %3B
? %3F
/ %2F
: %3A
# %23
& %24
= %3D
+ %2B
$ %26
, %2C
space %20 or +
% %25
< %3C
> %3E
~ %7E
% %25
我不知道Java是否有一些内置的方法来对字符串进行urlencoding,但是这个链接 http://www.permadi.com/tutorial/urlEncoding/ 显示了一些最常见的编码字符:
对于百分比编码的 mailto URI hnames 和 hvalues,我使用以下规则 http://shadow2531.com/opera/testcases/mailto/modern_mailto_uri_scheme.html#encoding. 。在下面 http://shadow2531.com/opera/testcases/mailto/modern_mailto_uri_scheme.html#implementations, ,有一个 Java 示例可能会有所帮助。
基本上,我使用:
private String encodex(final String s) {
try {
return java.net.URLEncoder.encode(s, "utf-8").replaceAll("\\+", "%20").replaceAll("\\%0A", "%0D%0A");
} catch (Throwable x) {
return s;
}
}
传入的字符串应该是带有 的字符串,并且杂散的 已经标准化为 。
另请注意,仅当您在命令行上传递的 mailto URI 参数被正确转义和引用时,仅在异常中返回原始字符串(如上)才是安全的。
在 Windows 上这意味着:
- 引用论证。
- 用 \ 转义引号内的任何 "。
- 使用 \ 转义 " 之前的任何 \ 或字符串结尾。
另外,在 Windows 上,如果您像在 Java 中一样处理 UTF-16 字符串,您可能需要使用 ShellExecuteW 来“打开”mailto URI。如果您不这样做并在异常时返回 s (其中某些 hvalue 未完全进行百分比编码),您最终可能会缩小一些宽字符并丢失信息。但是,并非所有邮件客户端都接受 unicode 参数,因此理想情况下,您希望使用 ShellExecute 传递正确的百分比编码的 utf8 ascii 参数。
与“start”类似,使用“open”的 ShellExecute 应在默认客户端中打开 mailto URI。
不确定其他操作系统的情况。
切勿使用 Runtime.exec(String)
在 Mac OS X 或任何其他操作系统上。如果这样做,您将必须弄清楚如何正确引用所有参数字符串等;这很痛苦而且很容易出错。
相反,使用 Runtime.exec(String[])
它接受一组已经分隔的参数。这更适合几乎所有用途。
Mailto 并不是一个糟糕的选择。但正如您所提到的,您需要确保它的编码正确。
使用 mailto 的主要问题是断线。使用 %0A 表示回车,使用 %20 表示空格。
另外,请记住,mailto 被视为与某种 URL 相同,因此具有相同的长度限制。看http://support.microsoft.com/kb/208427, ,请注意 URL 的最大长度为 2083 个字符。在本文中也证实了这一点: http://support.microsoft.com/kb/279460/en-us. 。此外,某些邮件客户端也可能有限制(我相信旧版本的 Outlook Express 的限制要小得多,例如 483 个字符之类的。如果您希望得到比这更长的字符串,那么您需要考虑替代方案。
顺便说一句,只要您可以从 Java 中发出命令,您就不必求助于踢出脚本来执行此操作(我不知道是否可以,因为我不使用 Java)。
你可以用这个...
main(string[] args){
String forUri = String.format("mailto:?subject=%s&body=%s", urlEncode(sub), urlEncode(mailBody));
Desktop.getDesktop().mail(new URI(forUri));
}
private static final String urlEncode(String str) {
try {
return URLEncoder.encode(str, "UTF-8").replace("+", "%20");
} catch (UnsupportedEncodingException e) {
throw new RuntimeException(e);
}
}
也用于格式化读取 Java发送邮件的简单方法:邮寄至链接
我已经实现了这个,并且它在 OS X 上运行良好。(Ryan 提到的最大 URL 长度尚未被编码。)
public void email(String subject, String body) throws Exception {
String cmd = "open mailto:";
cmd += "?subject=" + urlEncode(subject);
cmd += "&body=" + urlEncode(body);
Runtime.getRuntime().exec(cmd);
}
private static String urlEncode(String s) {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < s.length(); i++) {
char ch = s.charAt(i);
if (Character.isLetterOrDigit(ch)) {
sb.append(ch);
}
else {
sb.append(String.format("%%%02X", (int)ch));
}
}
return sb.toString();
}
我不得不重新实现 URLencode 因为 Java 会使用 +
空间和邮件从字面上理解了这些。尚未在 Windows 上进行测试。