I have followed these two guides: https://msdn.microsoft.com/en-us/library/windows/apps/hh202945(v=vs.105).aspx https://msdn.microsoft.com/library/windows/apps/xaml/hh868252
The resulting code is the following. Despite it all seems right, it returns a 404 error. How can this be? Any help will delay my suicide.
public static void PushToWindows2()
{
try
{
var accessToken = GetAccessToken("Nhz******************XkwX", "ms-app://s-1-15-2-***************-2150981501");
byte[] contentInBytes = Encoding.UTF8.GetBytes("<toast launch=\"\"><visual lang=\"en-US\"><binding template=\"ToastImageAndText01\"><image id=\"1\" src=\"World\" /><text id=\"1\">Hello</text></binding></visual></toast>");
HttpWebRequest request = HttpWebRequest.Create("https://db5.notify.windows.com/?token=awyaaaborhlhub%2bfxeytzjnz****************pftroh5l18sgorvgrkq%3d") as HttpWebRequest;
request.Method = "POST";
request.ContentLength = contentInBytes.Length;
request.ContentType= "text/xml";
request.Headers.Add("X-WindowsPhone-Target", "token");
request.Headers.Add("X-NotificationClass", "1"); ;
request.Headers.Add("X-WNS-Type", "wns/toast");
request.Headers.Add("Authorization", String.Format("Bearer {0}", accessToken.AccessToken.ToString()));
using (Stream requestStream = request.GetRequestStream())
requestStream.Write(contentInBytes, 0, contentInBytes.Length);
HttpWebResponse response = (HttpWebResponse)request.GetResponse();
string notificationStatus = response.Headers["X-NotificationStatus"];
string notificationChannelStatus = response.Headers["X-SubscriptionStatus"];
string deviceConnectionStatus = response.Headers["X-DeviceConnectionStatus"];
}
catch (Exception ex)
{
Console.Write("EXCEPTION: " + ex.Message);
}
}
[DataContract]
public class OAuthToken
{
[DataMember(Name = "access_token")]
public string AccessToken { get; set; }
[DataMember(Name = "token_type")]
public string TokenType { get; set; }
}
public static OAuthToken GetOAuthTokenFromJson(string jsonString)
{
using (var ms = new MemoryStream(Encoding.Unicode.GetBytes(jsonString)))
{
var ser = new DataContractJsonSerializer(typeof(OAuthToken));
var oAuthToken = (OAuthToken)ser.ReadObject(ms);
return oAuthToken;
}
}
public static OAuthToken GetAccessToken(string secret, string sid)
{
var urlEncodedSecret = HttpUtility.UrlEncode(secret);
var urlEncodedSid = HttpUtility.UrlEncode(sid);
var body = String.Format("grant_type=client_credentials&client_id={0}&client_secret={1}&scope=notify.windows.com",
urlEncodedSid,
urlEncodedSecret);
string response;
using (var client = new WebClient())
{
client.Headers.Add("Content-Type", "application/x-www-form-urlencoded");
response = client.UploadString("https://login.live.com/accesstoken.srf", body);
}
return GetOAuthTokenFromJson(response);
}
I have also tried to go the PushSharp route, in which case, I get the "Device subscription has expired" error. Here goes:
var config = new WnsConfiguration("424****.*******nts", "ms-app://s-1-15-2-***************1501", "Nhz************XkwX");
// Create a new broker
var wnsBroker = new WnsServiceBroker (config);
wnsBroker.QueueNotification(new WnsToastNotification {
ChannelUri = deviceId,
Payload = XElement.Parse (@"
<toast>
<visual>
<binding template=""ToastText01"">
<text id=""1"">WNS_Send_Single</text>
</binding>
</visual>
</toast>")
});
}
Update:
It is not encoding related either. I've used both the unencoded token with = and + signs and the encoding one. Still 404
HTTP 404 error for WNS means that the channel URI itself has been munged with so WNS can't understand it. It looks like from your code the channel URI is getting tolower()ed somewhere - usually the tokens start with something like "AwYAAAD". Try removing whatever's lowercasing the channel URI.
Also, it looks like you're mixing WNS and MSDN documentation when you want WNS (although this is not causing your 404 errors). This is WNS, but this is MPNS documentation. Specifically, these headers are for MPNS and will be ignored or failed by WNS:
You want to use these WNS headers instead.