需求:一隻監控遊戲的程式,有什麼特別的事情時,就可以發送skype訊息到我的手機。
可是不久前skype 竟然把舊的api 禁止了,所以無法再透過dll 發送訊息。
這時候skype 推出了 web版!
一開始想透過 WebBrowser 載入 此網頁,並透過注入JS的方式達到傳送訊息。(這是可行的。)
但是不太人性化,如果能更簡單就好了。
所以往另一個方向去做了研究。
Post !
研究過後,Skype 給我的感覺大概像這樣
一個使用者發送了一條訊息給Server,而Server 會通知另一個User 要接收這條訊息。
也就是說,你所傳的所有訊息,在Server 上都有一份紀錄。。。
知道大概的流程之後,接下來就是如何實作這段橋梁,讓我們透過程式做到想做的。
透過 HttpWebRequest 這個類別,建立一個 Request 然後發送我要的訊息,給Skype Server
那要傳什麼呢?
其實你只要透過 Chrome 的F12 觀察Skype Web版就知道 他發出了多少的要求給server,
而我們要做的只是 模擬同樣的要求即可。
觀察結果我們需要這兩個認證碼
1.SkypeToken →透過輸入帳號密碼取得的認證碼
2.RegistrationToken→如果要發送訊息,必須使用SkypeToken 換取這個RegistrationToken才能發送。
就像skype網頁一樣
1.輸入帳號密碼並取得SkypeToken
2.開始使用Skype (SkypeToken換取RegistrationToken)
3.選取使用者
4.發送訊息
附上寫好的Sample
https://drive.google.com/open?id=0B1XxIr6Ve-glc1lhN19fbjdzVGs
ps. 參考來源 https://github.com/Mrmaxmeier/web_skype4py/blob/master/main.py
麻煩請先學習 Chrome 的F12 開發人員工具
http://wayneprogramcity.blogspot.tw/2016/06/chrome.html#more
簡單的說就是去登入網頁版的Skype,並模擬他所需要的資料,這部分麻煩自行學習,如何透過Chrome 的 (F12)開發人員工具獲得你所需要的資料。
主要的Source code :
private string 取得SkypeToken(string 帳號, string 密碼)
{
HiddenObj obj = 取得HiddenObj();
string Url = @"https://login.skype.com/login?client_id=578134&redirect_uri=https%3A%2F%2Fweb.skype.com&intsrc=client-_-webapp-_-production-_-go-signin";
HttpWebRequest request = HttpWebRequest.Create(Url) as HttpWebRequest;
request.Method = "POST"; // 方法
request.KeepAlive = false;
string postData = "";
postData += @"username=" + 帳號;
postData += @"&password=" + 密碼;
postData += @"&timezone_field=" + obj.timezone_field;
postData += @"&pie=" + obj.pie;
postData += @"&etm=" + obj.etm;
postData += @"&js_time=" + DateTime.Now.Ticks;
postData += @"&client_id=" + @"578134";
postData += @"&redirect_uri=" + @"https://web.skype.com/";
postData += @"&intsrc=" + @"client-_-webapp-_-production-_-go-signin";
byte[] bs = Encoding.UTF8.GetBytes(postData);
using (Stream reqStream = request.GetRequestStream())
{
reqStream.Write(bs, 0, bs.Length);
}
using (WebResponse response = request.GetResponse())
{
StreamReader sr = new StreamReader(response.GetResponseStream());
string 要解析的字串 = sr.ReadToEnd();
sr.Close();
string skypetokenRegex = @"=""skypetoken"" value="".*?""";
string skypetoken = "";
Regex.Replace(要解析的字串, skypetokenRegex,
(Match 這個) =>
{
skypetoken = 這個.Value.Substring(21, 這個.Value.Length - 22);
return "";
}
);
if (skypetoken != "")
{
return "skypetoken=" + skypetoken;
}
else
{
throw new Exception("無法取得SkypeToken。" + 要解析的字串);
}
}
}
private class HiddenObj
{
public string timezone_field { get; set; }
public string pie { get; set; }
public string etm { get; set; }
}
private string 取得registrationToken(string skypetoken)
{
string Url = @"https://client-s.gateway.messenger.live.com/v1/users/ME/endpoints";
HttpWebRequest request = HttpWebRequest.Create(Url) as HttpWebRequest;
request.Method = "POST";
request.UserAgent = @"Mozilla/5.0 (Windows NT 6.3; WOW64; rv:35.0) Gecko/20100101 Firefox/35.0";
request.Accept = @"*/*";
request.Headers.Add("Accept-Language", "zh-tw,zh;q=0.8,en-us;q=0.5,en;q=0.3");
request.Headers.Add("Accept-Encoding", "gzip, deflate");
request.Headers.Add("ClientInfo", @"os=Windows; osVer=8.1; proc=Win32; lcid=en-us; deviceType=1; country=n/a; clientName=skype.com; clientVer=908/1.9.0.232//skype.com");
request.Headers.Add("Cache-Control", @"no-cache, no-store, must-revalidate");
request.Headers.Add("Pragma", "no-cache");
request.Headers.Add("Expires", "0");
request.Headers.Add("BehaviorOverride", @"redirectAs404");
request.Headers.Add("Authentication", skypetoken);
request.ContentType = @"application/json; charset=UTF-8";
request.Referer = @"https://web.skype.com/zh-Hant/";
request.Headers.Add("Origin", @"https://web.skype.com");
request.KeepAlive = false;
Dictionary<string, object> obj = new Dictionary<string, object>();
string param = JsonConvert.SerializeObject(obj);
byte[] bs = Encoding.UTF8.GetBytes(param);
using (Stream reqStream = request.GetRequestStream())
{
reqStream.Write(bs, 0, bs.Length);
}
using (WebResponse response = request.GetResponse())
{
return response.Headers["Set-RegistrationToken"];
}
}
private void 傳送訊息(string RegistrationToken, string 接收者, string 訊息)
{
string Url = @"https://client-s.gateway.messenger.live.com/v1/users/ME/conversations/" + 接收者 + @"/messages";
HttpWebRequest request = HttpWebRequest.Create(Url) as HttpWebRequest;
request.Method = "POST"; // 方法
request.UserAgent = @"Mozilla/5.0 (Windows NT 6.3; WOW64; rv:35.0) Gecko/20100101 Firefox/35.0";
request.Accept = @"application/json, text/javascript";
request.Headers.Add("Accept-Language", "zh-tw,zh;q=0.8,en-us;q=0.5,en;q=0.3");
request.Headers.Add("Accept-Encoding", "gzip, deflate");
request.Headers.Add("ClientInfo", @"os=Windows; osVer=8.1; proc=Win32; lcid=en-us; deviceType=1; country=n/a; clientName=skype.com; clientVer=908/1.9.0.232//skype.com");
request.Headers.Add("Cache-Control", @"no-cache, no-store, must-revalidate");
request.Headers.Add("Pragma", "no-cache");
request.Headers.Add("Expires", "0");
request.Headers.Add("BehaviorOverride", @"redirectAs404");
request.Headers.Add("RegistrationToken", RegistrationToken);
request.ContentType = @"application/json; charset=UTF-8";
request.Referer = @"https://web.skype.com/zh-Hant/";
request.Headers.Add("Origin", @"https://web.skype.com");
request.KeepAlive = true;
Dictionary<string, object> obj = new Dictionary<string, object>();
obj.Add("content", 訊息);
obj.Add("messagetype", "RichText");
obj.Add("contenttype", "text");
obj.Add("clientmessageid", DateTime.Now.Ticks);
string param = JsonConvert.SerializeObject(obj);
byte[] bs = Encoding.UTF8.GetBytes(param);
using (Stream reqStream = request.GetRequestStream())
{
reqStream.Write(bs, 0, bs.Length);
}
using (WebResponse response = request.GetResponse())
{
}
}
private List<ComboboxItem> 取得使用者(string 使用者帳號, string SkypeToken)
{
string Url = @"https://contacts.skype.com/contacts/v1/users/" + 使用者帳號.ToLower() + @"/contacts/";
string skypetoken = SkypeToken.Substring(11, SkypeToken.Length - 11);
HttpWebRequest request = HttpWebRequest.Create(Url) as HttpWebRequest;
request.Method = "GET"; // 方法
request.Headers.Add("X-Skypetoken", skypetoken);
List<ComboboxItem> itemlist = new List<ComboboxItem>();
using (WebResponse response = request.GetResponse())
{
StreamReader sr = new StreamReader(response.GetResponseStream());
string 要解析的字串 = sr.ReadToEnd();
sr.Close();
Newtonsoft.Json.Linq.JObject jo = Newtonsoft.Json.Linq.JObject.Parse(要解析的字串);
for (int i = 0; i < jo.Value<Newtonsoft.Json.Linq.JArray>("contacts").Count; i++)
{
if (jo.Value<Newtonsoft.Json.Linq.JArray>("contacts")[i].Value<string>("id") == "echo123")
{
continue;
}
ComboboxItem item = new ComboboxItem(
jo.Value<Newtonsoft.Json.Linq.JArray>("contacts")[i].Value<string>("display_name") + jo.Value<Newtonsoft.Json.Linq.JArray>("contacts")[i].Value<string>("id"),
"8:" + jo.Value<Newtonsoft.Json.Linq.JArray>("contacts")[i].Value<string>("id")
);
itemlist.Add(item);
}
}
return itemlist;
}
public class ComboboxItem
{
public string Text { get; set; }
public object Value { get; set; }
public ComboboxItem(string Itemtext, string Itemvalue)
{
this.Text = Itemtext;
this.Value = Itemvalue;
}
public override string ToString()
{
return Text;
}
}
private HiddenObj 取得HiddenObj()
{
HiddenObj obj = new HiddenObj();
string Url = @"https://login.skype.com/login";
HttpWebRequest request = HttpWebRequest.Create(Url) as HttpWebRequest;
request.Method = "GET"; // 方法
using (WebResponse response = request.GetResponse())
{
StreamReader sr = new StreamReader(response.GetResponseStream());
string 要解析的字串 = sr.ReadToEnd();
sr.Close();
string pieRegex = @"=""pie"" value="".*?""";
string etmRegex = @"=""etm"" value="".*?""";
string pie = "";
string etm = "";
Regex.Replace(要解析的字串, pieRegex,
(Match 這個) =>
{
pie = 這個.Value.Substring(14, 這個.Value.Length - 15);
return "";
}
);
Regex.Replace(要解析的字串, etmRegex,
(Match 這個) =>
{
etm = 這個.Value.Substring(14, 這個.Value.Length - 15);
return "";
}
);
obj.pie = pie;
obj.etm = etm;
}
obj.timezone_field = @"+08|00";
return obj;
}
titanium dive knife - Stainless Steel & Iron Cloth | TITanium
回覆刪除Stainless Steel & Iron Cloth apple watch titanium is made of steel, with a cast iron mens wedding bands titanium core that is suitable oakley titanium glasses for corrosion in stainless steel. It is made with two $47.99 titanium hair trimmer · In titanium watch band stock