今天化了一个下午的时间研究了一下MSN的协议,对MSN的协议注意了有很长的时间了,但是却一直没有亲自做过什么程序。
前面有开心的MSN,后来也给陈锐发过,今天决定自己做一个程序连带学习托管C++
基于MSN的开发其实非常简单,关键是熟悉MSN的协议,大家可以在这里学习到详细的MSN协议的知识,唯一可惜的就是全部英文,有心人可以翻译过来http://www.hypothetic.org/docs/msn/index.php
MSN的协议整体是比较简单易用的,只要解决了登录的问题,其它都非常简单.根据协议来看,应该有一个gateway.messenger.hotmail.com:80的登录服务器,但是我一直连接不上,
所以就和大家一样使用messenger.hotmail.com:1863来登录了,MS为了避免这个服务器负担过重,在协议中需要根据具体的情况换登录服务器,这些都需要在程序中加以考虑,我遇到了连续
登录三次给的服务器地址以后,还要换地址的情况,看来MSN登录太慢也应该就是这个原因的了.
在一个比较关键的问题就是passport验证的问题,这里采用的是https验证的方法,上次看MSDN Show的时候CHRIS SELLS说还有另外的一个办法
不过我在这里没有采用.仍然是传统的办法
方法就是通过连接passport的nexus服务器,然后根据nexus服务器的响应进行passport登录,通过这样的练习可以熟悉passport的一部分运作机制和原理,将来在自己的服务器调用passport服务的时候就不用让用户再看到MS的影子了![]()
程序调试过程中得到了 蝈蝈和小马哥的大力帮助,让我这个dot net门外汉不至于找不到门.
我是用Managed c++进行这个开发的,在codeproject上有一个C#的project,我做完自己的程序以后发现,我们两个的代码真的很类似,说抄袭都没有人不信,但是我真的是自己写的
如果你对自己进行协议层的MSN开发没有兴趣,而对应用层的开发有兴趣,你可以联系开心或者去这里
codeproject上的demo在这里:http://www.codeproject.com/csharp/ConnectingToMSN.asp
我把我的代码贴到文章里面了,没有什么特色,大家见笑了。
打印 | 张贴于 2004-03-16 18:20:00 | Tag:暂无标签
留言反馈
联系:msnmailgj@163.com
新版本的好像和以前不太一样了。。
交流:MSN: timixu at hotmail.com
Date = Mon, 23 Jan 2006 06:14:53 GMT
Server = Microsoft-IIS/6.0
PPServer = PPV: 30 H: BAYPPLOG2A06 V: 0
Content-Type = text/html; charset=iso-8859-1
Expires = Mon, 23 Jan 2006 06:13:53 GMT
Cache-Control = no-cache
Pragma = no-cache
P3P = CP="DSP CUR OTPi IND OTRi ONL FIN"
Set-Cookie = MSPRequ=lt=1137996893&co=1&id=N
Set-Cookie = MSPBack=0; domain=.passport.com;path=/;version=1
Connection = Keep-Alive
Content-Length = 823
String username,
String challengeString,
Vector vc) throws IOException {
System.out.println("在getClientTicket里vc.size()=" + vc.size());
for (int i = 0; i < vc.size(); i++) {
System.out.println("在geClientTicket中取的vc=" + vc.get(i));
if (i == DALOGIN) {
//uri = vc.get(1).toString();
uri = "login.passport.com";
}
}
System.out.println("GetClientTicket中的uri=" + uri);
// 执行postMethod
try {
while (true) {
int step = 1;
HttpClient httpClient = new HttpClient();
String uri2 = null;
System.out.println("uri" + uri);
String uriReall = null;
if (step != 1) {
uriReall = "https://" + uri2;
} else {
uriReall = "https://" + uri;
}
GetMethod postMethod = new GetMethod(uriReall);
postMethod.getParams().setParameter(HttpMethodParams.RETRY_HANDLER,
new DefaultHttpMethodRetryHandler());
httpClient.getParams().setVersion(HttpVersion.HTTP_1_0);
postMethod.setRequestHeader(new Header("Authorization",
"Passport1.4 OrgVerb=GET,OrgURL=http%3A%2F%2Fmessenger%2Emsn%2Ecom,sign-in="
+ username.replace("@", "%40") +
",pwd=" +
password + ","
+ challengeString + "\r\n"));
postMethod.setRequestHeader(new Header("Host","login.passport.com\r\n"));
System.out.println("handshake before............");
int statusCode = httpClient.executeMethod(postMethod);
.out.println("statusCode=" + statusCode);
// HttpClient对于要求接受后继服务的请求,象POST和PUT等不能自动处理转发
if (statusCode == HttpStatus.SC_OK) {
System.out.println("AAAAAAAAAAA");
System.out.println("P3P=" +postMethod.getResponseHeader("P3P").getValue());
Header Authentication = postMethod.getResponseHeader(
"Authentication-Info");
if(Authentication == null){
System.out.println("Authentication-Info is null");
}else{
System.out.println("Authentication-Info isn't null");
}
System.out.println("BBBBBBBBBBBBB");
} else if (statusCode == HttpStatus.SC_MOVED_TEMPORARILY) {
// 从头中取出转向的地址
Header locationHeader = postMethod.getResponseHeader(
"Location");
uri2 = locationHeader.getValue();
String location = null;
if (locationHeader != null) {
location = locationHeader.getValue();
uri2 = location;
System.out.println("The page was redirected to:" +
location);
System.out.println("cache-control=:" +
postMethod.getResponseHeader(
"cache-control=").getValue());
} else {
System.err.println("Location field value is null.");
}
}
step++;
} //end while
} catch (Exception e) {
e.printStackTrace();
}
}
String username,
String challengeString,
Vector vc) throws IOException {
System.out.println("在getClientTicket里vc.size()=" + vc.size());
for (int i = 0; i < vc.size(); i++) {
System.out.println("在geClientTicket中取的vc=" + vc.get(i));
if (i == DALOGIN) {
//uri = vc.get(1).toString();
uri = "login.passport.com";
}
}
System.out.println("GetClientTicket中的uri=" + uri);
// 执行postMethod
try {
while (true) {
int step = 1;
HttpClient httpClient = new HttpClient();
String uri2 = null;
System.out.println("uri" + uri);
String uriReall = null;
if (step != 1) {
uriReall = "https://" + uri2;
} else {
uriReall = "https://" + uri;
}
GetMethod postMethod = new GetMethod(uriReall);
postMethod.getParams().setParameter(HttpMethodParams.RETRY_HANDLER,
new DefaultHttpMethodRetryHandler());
httpClient.getParams().setVersion(HttpVersion.HTTP_1_0);
postMethod.setRequestHeader(new Header("Authorization",
"Passport1.4 OrgVerb=GET,OrgURL=http%3A%2F%2Fmessenger%2Emsn%2Ecom,sign-in="
+ username.replace("@", "%40") +
",pwd=" +
password + ","
+ challengeString + "\r\n"));
postMethod.setRequestHeader(new Header("Host","login.passport.com\r\n"));
System.out.println("handshake before............");
int statusCode = httpClient.executeMethod(postMethod);
.out.println("statusCode=" + statusCode);
// HttpClient对于要求接受后继服务的请求,象POST和PUT等不能自动处理转发
if (statusCode == HttpStatus.SC_OK) {
System.out.println("AAAAAAAAAAA");
System.out.println("P3P=" +postMethod.getResponseHeader("P3P").getValue());
Header Authentication = postMethod.getResponseHeader(
"Authentication-Info");
if(Authentication == null){
System.out.println("Authentication-Info is null");
}else{
System.out.println("Authentication-Info isn't null");
}
System.out.println("BBBBBBBBBBBBB");
} else if (statusCode == HttpStatus.SC_MOVED_TEMPORARILY) {
// 从头中取出转向的地址
Header locationHeader = postMethod.getResponseHeader(
"Location");
uri2 = locationHeader.getValue();
String location = null;
if (locationHeader != null) {
location = locationHeader.getValue();
uri2 = location;
System.out.println("The page was redirected to:" +
location);
System.out.println("cache-control=:" +
postMethod.getResponseHeader(
"cache-control=").getValue());
} else {
System.err.println("Location field value is null.");
}
}
step++;
} //end while
} catch (Exception e) {
e.printStackTrace();
}
}
谢谢你!
但是认证上老出问题
<<<CHL 0 29792109415679580616
>>>QRY 11 PROD00504RLUG%WL 32
1a384df6f29cb61a6f61eb286f704141
<<<QRY 11
然后就把我断开
不知为什么
渴求交流
13202941007
请给我发一份吧,感激不尽
dragon_lsl@163.com
求高手解答!
我的MSN:OCEANHC@HOTMAIL.COM
在下先谢了
{
public:
MsnLib(void)
: m_pServer(NULL)
, m_pNs(NULL)
{
}
这块代码是什么意思呢?能不能解释一下啊?谢谢哈!
132xyz20@163.com小弟在此谢过了
我发现微软经常对MSN协议进行小改动,呵呵~
我用 C++ 和 VB 都成功登陆了,不过,UTF-8解码确实烦人~
豆腐,如果连上了,怎么通信?不明白~~
MSN Messenger或者说Windows Messenger的普通帐号使用的都是MSNP协议。这也是我们最常使用的。
而SIP是LCS及原来的Exchange IM Server所使用的协议。
简单来说,SIP只能在AD环境下使用,而MSNP则是广域网的,只需要Passport就可以了:)
我们刚好有一个需求,就是将OA电子表单链接发送到MSN.
我可以给你提供结口:)