Tutorial: Mengirim pemberitahuan ke pengguna tertentu menggunakan Microsoft Azure Notification Hubs

Gambaran Umum

Tutorial ini menjelaskan cara menggunakan Microsoft Azure Notification Hubs untuk mengirim pemberitahuan push ke pengguna aplikasi tertentu pada perangkat tertentu. Ujung belakang ASP.NET WebAPI digunakan untuk mengautentikasi klien. Ketika ujung belakang mengautentikasi pengguna aplikasi klien, ujung belakang tersebut secara otomatis menambahkan tag ke pendaftaran pemberitahuan. Ujung belakang menggunakan tag ini untuk mengirim pemberitahuan ke pengguna tertentu.

Catatan

Kode lengkap untuk tutorial ini dapat ditemukan di GitHub.

Dalam tutorial ini, Anda akan melakukan langkah-langkah berikut:

  • Membuat proyek WebAPI
  • Mengautentikasi klien ke ujung belakang WebAPI
  • Mendaftar untuk pemberitahuan dengan menggunakan ujung belakang WebAPI
  • Mengirim pemberitahuan dari ujung belakang WebAPI
  • Menerbitkan ujung belakang WebAPI baru
  • Memperbarui kode untuk proyek klien
  • Menguji aplikasi

Prasyarat

Tutorial ini dibangun pada hub pemberitahuan dan proyek Visual Studio yang Anda buat di Tutorial: Mengirim pemberitahuan ke aplikasi Universal Windows Platform dengan menggunakan Microsoft Azure Notification Hubs. Oleh karena itu, selesaikan langkah tersebut sebelum memulai tutorial ini.

Catatan

Jika Anda menggunakan Mobile Apps di Azure App Service sebagai layanan ujung belakang Anda, lihat versi Mobile Apps dari tutorial ini.

Buat proyek WebAPI

Bagian berikut membahas pembuatan backend ASP.NET WebAPI baru. Proses ini memiliki tiga tujuan utama:

  • Mengautentikasi klien: Anda menambahkan penangan pesan untuk mengautentikasi permintaan klien dan mengaitkan pengguna dengan permintaan.
  • Daftar untuk pemberitahuan dengan menggunakan backend WebAPI: Anda menambahkan pengontrol untuk menangani pendaftaran baru untuk perangkat klien untuk menerima pemberitahuan. Nama pengguna yang diautentikasi secara otomatis ditambahkan ke pendaftaran sebagai tag.
  • Kirim pemberitahuan ke klien: Anda menambahkan pengontrol untuk menyediakan cara bagi pengguna untuk memicu dorongan aman ke perangkat dan klien yang terkait dengan tag.

Buat backend ASP.NET WebAPI baru dengan melakukan tindakan berikut:

Penting

Jika Anda menggunakan Visual Studio 2015 atau versi lebih lama, sebelum memulai tutorial ini, pastikan Anda telah menginstal versi terbaru NuGet Package Manager untuk Visual Studio.

Untuk memeriksa, mulai Visual Studio. Pada menu Alat, pilih Ekstensi dan Pembaruan. Cari NuGet Package Manager di Visual Studio versi Anda, dan pastikan Anda memiliki versi terbaru. Jika versi Anda bukan versi terbaru, hapus instalasinya, lalu instal ulang NuGet Package Manager.

Cuplikan layar kotak dialog Ekstensi dan Pembaruan dengan paket NuGet Package manage for Visual Studios package highlighted.

Catatan

Pastikan Anda telah memasang Visual Studio Azure SDK untuk penyebaran situs web.

  1. Mulai Visual Studio atau Visual Studio Express.

  2. Pilih Penjelajah Server, dan masuk ke akun Azure Anda. Untuk membuat sumber daya situs web di akun Anda, Anda harus masuk.

  3. Di Visual Studio, klik kanan solusi Visual Studio, arahkan ke Tambahkan, dan klik Proyek Baru.

  4. Perluas Visual C# , pilih Web, dan klik ASP.NET Aplikasi Web.

  5. Dalam kotak Nama, ketik AppBackend, lalu pilih OK.

    Jendela Proyek Baru

  6. Di jendela Proyek ASP.NET Baru, pilih kotak centang API Web, lalu pilih OK.

    Jendela Proyek ASP.NET Baru

  7. Di jendela Konfigurasikan Microsoft Azure Web App, pilih langganan lalu, di daftar paket Azure App Service, lakukan salah satu tindakan berikut ini:

    • Pilih paket layanan aplikasi yang telah Anda buat.
    • Pilih Buat paket layanan aplikasi baru, lalu buat paket.

    Anda tidak memerlukan database untuk tutorial ini. Setelah memilih paket layanan aplikasi, pilih OK untuk membuat proyek.

    Jendela Konfigurasikan Microsoft Azure Web App

    Jika Anda tidak melihat halaman ini untuk mengonfigurasi paket layanan aplikasi, lanjutkan dengan tutorial. Anda dapat mengonfigurasinya saat menerbitkan aplikasi nanti.

Autentikasi klien ke backened WebAPI

Di bagian ini, Anda membuat kelas message-handler baru bernama AuthenticationTestHandler untuk backend baru. Kelas ini berasal dari DelegatingHandler dan ditambahkan sebagai penangan pesan sehingga dapat memproses semua permintaan yang masuk ke backend.

  1. Di Penjelajah Solusi, klik kanan proyek AppBackend, pilih Tambahkan, lalu pilih Kelas.

  2. Beri nama kelas baru AuthenticationTestHandler.cs, lalu pilih Tambahkan untuk menghasilkan kelas. Kelas ini mengautentikasi pengguna dengan menggunakan Otentikasi Dasar untuk kesederhanaan. Aplikasi Anda dapat menggunakan skema autentikasi apa pun.

  3. Di AuthenticationTestHandler.cs, tambahkan pernyataan using berikut:

    using System.Net.Http;
    using System.Threading;
    using System.Security.Principal;
    using System.Net;
    using System.Text;
    using System.Threading.Tasks;
    
  4. Di AuthenticationTestHandler.cs, ganti AuthenticationTestHandler definisi kelas dengan kode berikut:

    Handler mengotorisasi permintaan ketika tiga kondisi berikut ini benar:

    • Permintaan ini menyertakan header Otorisasi.
    • Permintaan ini menggunakan autentikasi dasar.
    • String nama pengguna dan string kata sandi adalah string yang sama.

    Jika tidak, permintaan ditolak. Autentikasi ini bukan pendekatan autentikasi dan otorisasi yang benar. Ini hanya contoh sederhana untuk tutorial ini.

    Jika pesan permintaan diautentikasi dan diotorisasi oleh AuthenticationTestHandler, pengguna otentikasi dasar dilampirkan ke permintaan saat ini di HttpContext. Informasi pengguna di HttpContext akan digunakan oleh pengontrol lain (RegisterController) nantinya untuk menambahkan tag ke permintaan pendaftaran pemberitahuan.

    public class AuthenticationTestHandler : DelegatingHandler
    {
        protected override Task<HttpResponseMessage> SendAsync(
        HttpRequestMessage request, CancellationToken cancellationToken)
        {
            var authorizationHeader = request.Headers.GetValues("Authorization").First();
    
            if (authorizationHeader != null && authorizationHeader
                .StartsWith("Basic ", StringComparison.InvariantCultureIgnoreCase))
            {
                string authorizationUserAndPwdBase64 =
                    authorizationHeader.Substring("Basic ".Length);
                string authorizationUserAndPwd = Encoding.Default
                    .GetString(Convert.FromBase64String(authorizationUserAndPwdBase64));
                string user = authorizationUserAndPwd.Split(':')[0];
                string password = authorizationUserAndPwd.Split(':')[1];
    
                if (VerifyUserAndPwd(user, password))
                {
                    // Attach the new principal object to the current HttpContext object
                    HttpContext.Current.User =
                        new GenericPrincipal(new GenericIdentity(user), new string[0]);
                    System.Threading.Thread.CurrentPrincipal =
                        System.Web.HttpContext.Current.User;
                }
                else return Unauthorized();
            }
            else return Unauthorized();
    
            return base.SendAsync(request, cancellationToken);
        }
    
        private bool VerifyUserAndPwd(string user, string password)
        {
            // This is not a real authentication scheme.
            return user == password;
        }
    
        private Task<HttpResponseMessage> Unauthorized()
        {
            var response = new HttpResponseMessage(HttpStatusCode.Forbidden);
            var tsc = new TaskCompletionSource<HttpResponseMessage>();
            tsc.SetResult(response);
            return tsc.Task;
        }
    }
    

    Catatan

    Catatan keamanan: Kelas AuthenticationTestHandler tidak menyediakan autentikasi yang benar. Ini hanya digunakan untuk meniru autentikasi dasar dan tidak aman. Anda harus menerapkan mekanisme autentikasi aman dalam aplikasi dan layanan produksi Anda.

  5. Untuk mendaftarkan penangan pesan, tambahkan kode berikut di akhir Register metode di kelas App_Start/WebApiConfig.cs:

    config.MessageHandlers.Add(new AuthenticationTestHandler());
    
  6. Simpan perubahan Anda.

Daftar untuk pemberitahuan dengan menggunakan bakcend WebAPI

Di bagian ini, Anda menambahkan pengontrol baru ke backend WebAPI untuk menangani permintaan untuk mendaftarkan pengguna dan perangkat untuk pemberitahuan dengan menggunakan pustaka klien untuk hub notifikasi. Pengontrol menambahkan tag pengguna untuk pengguna yang diautentikasi dan dilampirkan ke HttpContext oleh AuthenticationTestHandler. Tag memiliki format string, "username:<actual username>".

  1. Pada Penjelajah Solusi, klik kanan proyek AppBackend dan pilih Manage NuGet Packages.

  2. Di panel kiri, pilih Online lalu, dalam kotak Pencarian, ketik Microsoft.Azure.NotificationHubs.

  3. Dalam daftar hasil, pilih Microsoft Azure Notification Hubs, lalu pilih Pasang. Selesaikan penginstalan, lalu tutup jendela NuGet Package Manager.

    Tindakan ini menambahkan referensi ke SDK Microsoft Azure Notification Hubs dengan menggunakan paket Microsoft.Azure.Notification Hubs NuGet.

  4. Buat file kelas baru yang mewakili koneksi dengan hub notifikasi yang digunakan untuk mengirim notifikasi. Di Penjelajah Solusi, klik kanan folder Model, pilih Tambahkan, lalu pilih Kelas. Beri nama kelas baru Notifications .cs, lalu pilih Tambahkan untuk membuat kelas.

    Jendela Tambahkan Item Baru

  5. Di Nitifications.cs, tambahkan usingpernyataan berikut di bagian atas file:

    using Microsoft.Azure.NotificationHubs;
    
  6. Ganti Notifications definisi kelas dengan kode berikut, dan ganti dua placeholder dengan string koneksi (dengan akses penuh) untuk hub notifikasi dan nama hub Anda (tersedia di portal Microsoft Azure):

    public class Notifications
    {
        public static Notifications Instance = new Notifications();
    
        public NotificationHubClient Hub { get; set; }
    
        private Notifications() {
            Hub = NotificationHubClient.CreateClientFromConnectionString("<your hub's DefaultFullSharedAccessSignature>",
                                                                            "<hub name>");
        }
    }
    

    Penting

    Masukkan nama dan DefaultListenSharedAccessSignature hub Anda sebelum melanjutkan.

  7. Selanjutnya, buat pengontrol baru bernama RegisterController. Di Penjelajah Solusi,klik kanan folder Pengontrol, pilih Tambahkan, lalu pilih Pengontrol.

  8. Pilih Web API 2 Controller - Kosong, lalu pilih Tambahkan.

    Jendela Tambahkan Perancah

  9. Dalam kotak Nama pengontrol, ketik RegisterController untuk memberi nama kelas baru, lalu pilih Tambahkan.

    Jendela Tambahkan Pengontrol

  10. Di RegisterController.cs, tambahkan pernyataan using berikut:

    using Microsoft.Azure.NotificationHubs;
    using Microsoft.Azure.NotificationHubs.Messaging;
    using AppBackend.Models;
    using System.Threading.Tasks;
    using System.Web;
    
  11. Tambahkan kode berikut di dalam RegisterController definisi kelas. Dalam kode ini, Anda menambahkan tag pengguna untuk pengguna yang dilampirkan ke HttpContext. Pengguna diautentikasi dan dilampirkan ke HttpContext oleh filter pesan yang Anda tambahkan, AuthenticationTestHandler. Anda juga dapat menambahkan pemeriksaan opsional untuk memverifikasi bahwa pengguna memiliki hak untuk mendaftarkan tag yang diminta.

    private NotificationHubClient hub;
    
    public RegisterController()
    {
        hub = Notifications.Instance.Hub;
    }
    
    public class DeviceRegistration
    {
        public string Platform { get; set; }
        public string Handle { get; set; }
        public string[] Tags { get; set; }
    }
    
    // POST api/register
    // This creates a registration id
    public async Task<string> Post(string handle = null)
    {
        string newRegistrationId = null;
    
        // make sure there are no existing registrations for this push handle (used for iOS and Android)
        if (handle != null)
        {
            var registrations = await hub.GetRegistrationsByChannelAsync(handle, 100);
    
            foreach (RegistrationDescription registration in registrations)
            {
                if (newRegistrationId == null)
                {
                    newRegistrationId = registration.RegistrationId;
                }
                else
                {
                    await hub.DeleteRegistrationAsync(registration);
                }
            }
        }
    
        if (newRegistrationId == null) 
            newRegistrationId = await hub.CreateRegistrationIdAsync();
    
        return newRegistrationId;
    }
    
    // PUT api/register/5
    // This creates or updates a registration (with provided channelURI) at the specified id
    public async Task<HttpResponseMessage> Put(string id, DeviceRegistration deviceUpdate)
    {
        RegistrationDescription registration = null;
        switch (deviceUpdate.Platform)
        {
            case "mpns":
                registration = new MpnsRegistrationDescription(deviceUpdate.Handle);
                break;
            case "wns":
                registration = new WindowsRegistrationDescription(deviceUpdate.Handle);
                break;
            case "apns":
                registration = new AppleRegistrationDescription(deviceUpdate.Handle);
                break;
            case "fcm":
                registration = new FcmRegistrationDescription(deviceUpdate.Handle);
                break;
            default:
                throw new HttpResponseException(HttpStatusCode.BadRequest);
        }
    
        registration.RegistrationId = id;
        var username = HttpContext.Current.User.Identity.Name;
    
        // add check if user is allowed to add these tags
        registration.Tags = new HashSet<string>(deviceUpdate.Tags);
        registration.Tags.Add("username:" + username);
    
        try
        {
            await hub.CreateOrUpdateRegistrationAsync(registration);
        }
        catch (MessagingException e)
        {
            ReturnGoneIfHubResponseIsGone(e);
        }
    
        return Request.CreateResponse(HttpStatusCode.OK);
    }
    
    // DELETE api/register/5
    public async Task<HttpResponseMessage> Delete(string id)
    {
        await hub.DeleteRegistrationAsync(id);
        return Request.CreateResponse(HttpStatusCode.OK);
    }
    
    private static void ReturnGoneIfHubResponseIsGone(MessagingException e)
    {
        var webex = e.InnerException as WebException;
        if (webex.Status == WebExceptionStatus.ProtocolError)
        {
            var response = (HttpWebResponse)webex.Response;
            if (response.StatusCode == HttpStatusCode.Gone)
                throw new HttpRequestException(HttpStatusCode.Gone.ToString());
        }
    }
    
  12. Simpan perubahan Anda.

Kirim pemberitahuan dari backend WebAPI

Di bagian ini, Anda menambahkan pengontrol baru yang mengekspos cara perangkat klien untuk mengirim pemberitahuan. Pemberitahuan didasarkan pada tag nama pengguna yang menggunakan Azure Notification Hubs .NET Library di ASP.NET backend WebAPI.

  1. Buat pengontrol baru lainnya bernama NotificationsController dengan cara yang sama seperti Anda membuat RegisterController di bagian sebelumnya.

  2. Di NotificationsController.cs, tambahkan using pernyataan berikut:

    using AppBackend.Models;
    using System.Threading.Tasks;
    using System.Web;
    
  3. Tambahkan metode berikut ke kelas NotificationsController:

    Kode ini mengirimkan jenis notifikasi yang didasarkan pada parameter Layanan Pemberitahuan Platform pns (PNS). Nilai to_tag digunakan untuk mengatur tag nama pengguna pada pesan. Tag ini harus cocok dengan tag nama pengguna dari pendaftaran hub notifikasi aktif. Pesan pemberitahuan ditarik dari isi permintaan KIRIMAN dan diformat untuk target PNS.

    Berdasarkan PNS yang digunakan oleh perangkat yang didukung untuk menerima notifikasi, notifikasi didukung oleh berbagai format. Misalnya, pada perangkat Windows, Anda mungkin menggunakan pemberitahuan toast dengan WNS yang tidak didukung langsung oleh PNS lain. Dalam hal demikian, backend Anda perlu memformat pemberitahuan ke pemberitahuan yang didukung untuk PNS perangkat yang Anda rencanakan untuk didukung. Kemudian gunakan API kirim yang sesuai pada kelas NotificationHubClient.

    public async Task<HttpResponseMessage> Post(string pns, [FromBody]string message, string to_tag)
    {
        var user = HttpContext.Current.User.Identity.Name;
        string[] userTag = new string[2];
        userTag[0] = "username:" + to_tag;
        userTag[1] = "from:" + user;
    
        Microsoft.Azure.NotificationHubs.NotificationOutcome outcome = null;
        HttpStatusCode ret = HttpStatusCode.InternalServerError;
    
        switch (pns.ToLower())
        {
            case "wns":
                // Windows 8.1 / Windows Phone 8.1
                var toast = @"<toast><visual><binding template=""ToastText01""><text id=""1"">" + 
                            "From " + user + ": " + message + "</text></binding></visual></toast>";
                outcome = await Notifications.Instance.Hub.SendWindowsNativeNotificationAsync(toast, userTag);
                break;
            case "apns":
                // iOS
                var alert = "{\"aps\":{\"alert\":\"" + "From " + user + ": " + message + "\"}}";
                outcome = await Notifications.Instance.Hub.SendAppleNativeNotificationAsync(alert, userTag);
                break;
            case "fcm":
                // Android
                var notif = "{ \"data\" : {\"message\":\"" + "From " + user + ": " + message + "\"}}";
                outcome = await Notifications.Instance.Hub.SendFcmNativeNotificationAsync(notif, userTag);
                break;
        }
    
        if (outcome != null)
        {
            if (!((outcome.State == Microsoft.Azure.NotificationHubs.NotificationOutcomeState.Abandoned) ||
                (outcome.State == Microsoft.Azure.NotificationHubs.NotificationOutcomeState.Unknown)))
            {
                ret = HttpStatusCode.OK;
            }
        }
    
        return Request.CreateResponse(ret);
    }
    
  4. Untuk menjalankan aplikasi dan memastikan keakuratan pekerjaan Anda sejauh ini, pilih kunci F5. Aplikasi ini membuka browser web, dan ditampilkan di beranda ASP.NET.

Terbitkan backend WebAPI baru

Selanjutnya, Anda menerapkan aplikasi ke situs web Azure untuk membuatnya dapat diakses dari semua perangkat.

  1. Klik kanan proyek AppBackend, lalu pilih Terbitkan.

  2. Pilih Microsoft Azure App Service sebagai target penerbitan Anda, lalu pilih **Terbitkan. Jendela Buat Azure App Service terbuka. Di sini Anda dapat membuat semua sumber daya Azure yang diperlukan untuk menjalankan ASP.NET web di Azure.

    Petak peta Microsoft Azure App Service

  3. Di jendela Buat Azure App Service, pilih akun Azure Anda. Pilih Ubah Jenis > Aplikasi Web. Pertahankan Nama Aplikasi Web default, lalu pilih Langganan, Grup Sumber Daya, dan Paket Azure App Service.

  4. Pilih Buat.

  5. Catat properti URL Situs di bagian Ringkasan. URL ini adalah titik akhir back-end Anda nanti dalam tutorial.

  6. Pilih Terbitkan.

Setelah Anda menyelesaikan wizard, wizard akan menerbitkan aplikasi web ASP.NET ke Azure lalu membuka aplikasi di browser default. Aplikasi Anda dapat dilihat di Azure App Services.

URL menggunakan nama aplikasi web yang Anda tentukan sebelumnya, dengan format http://<app_name>.azurewebsites.net.

Perbarui kode untuk klien UWP

Pada bagian ini, Anda memperbarui kode dalam proyek yang Anda selesaikan untuk Tutorial: Kirim pemberitahuan ke aplikasi Universal Windows Platform dengan menggunakan Azure Notification Hubs. Proyek harus sudah dikaitkan dengan penyimpanan Windows. Proyek ini juga harus dikonfigurasi untuk menggunakan hub pemberitahuan Anda. Pada bagian ini, Anda menambahkan kode untuk memanggil ujung belakang WebAPI baru dan menggunakannya untuk mendaftarkan dan mengirim pemberitahuan.

  1. Di Visual Studio, buka solusi yang Anda buat untuk Tutorial: Mengirim pemberitahuan ke aplikasi Universal Windows Platform dengan menggunakan Microsoft Azure Notification Hubs.

  2. Di Penjelajah Solusi, klik kanan proyek Universal Windows Platform (UWP) lalu klik Kelola Paket NuGet.

  3. Di sisi kiri, pilih Telusuri.

  4. Dalam kotak Pencarian, ketik Http Client.

  5. Dalam daftar hasil, klik System.Net.Http, dan klik Instal. Selesaikan penginstalan.

  6. Kembali ke kotak Pencarian NuGet, ketik Json.net. Instal paket Newtonsoft.json, lalu tutup jendela Manajer Paket NuGet.

  7. Di bagian Penjelajah Solusi, dalam proyek WindowsApp, klik dua kali MainPage.xaml untuk membukanya di editor Visual Studio.

  8. Dalam file MainPage.xaml, ganti bagian <Grid> dengan kode berikut: Kode ini menambahkan nama pengguna dan kotak teks kata sandi untuk autentikasi pengguna. Kode ini juga menambahkan kotak teks untuk pesan pemberitahuan dan tag nama pengguna yang harus menerima pemberitahuan:

    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="*"/>
        </Grid.RowDefinitions>
    
        <TextBlock Grid.Row="0" Text="Notify Users" HorizontalAlignment="Center" FontSize="48"/>
    
        <StackPanel Grid.Row="1" VerticalAlignment="Center">
            <Grid>
                <Grid.RowDefinitions>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                    <RowDefinition Height="Auto"/>
                </Grid.RowDefinitions>
                <Grid.ColumnDefinitions>
                    <ColumnDefinition></ColumnDefinition>
                    <ColumnDefinition></ColumnDefinition>
                    <ColumnDefinition></ColumnDefinition>
                </Grid.ColumnDefinitions>
                <TextBlock Grid.Row="0" Grid.ColumnSpan="3" Text="Username" FontSize="24" Margin="20,0,20,0"/>
                <TextBox Name="UsernameTextBox" Grid.Row="1" Grid.ColumnSpan="3" Margin="20,0,20,0"/>
                <TextBlock Grid.Row="2" Grid.ColumnSpan="3" Text="Password" FontSize="24" Margin="20,0,20,0" />
                <PasswordBox Name="PasswordTextBox" Grid.Row="3" Grid.ColumnSpan="3" Margin="20,0,20,0"/>
    
                <Button Grid.Row="4" Grid.ColumnSpan="3" HorizontalAlignment="Center" VerticalAlignment="Center"
                            Content="1. Login and register" Click="LoginAndRegisterClick" Margin="0,0,0,20"/>
    
                <ToggleButton Name="toggleWNS" Grid.Row="5" Grid.Column="0" HorizontalAlignment="Right" Content="WNS" IsChecked="True" />
                <ToggleButton Name="toggleFCM" Grid.Row="5" Grid.Column="1" HorizontalAlignment="Center" Content="FCM" />
                <ToggleButton Name="toggleAPNS" Grid.Row="5" Grid.Column="2" HorizontalAlignment="Left" Content="APNS" />
    
                <TextBlock Grid.Row="6" Grid.ColumnSpan="3" Text="Username Tag To Send To" FontSize="24" Margin="20,0,20,0"/>
                <TextBox Name="ToUserTagTextBox" Grid.Row="7" Grid.ColumnSpan="3" Margin="20,0,20,0" TextWrapping="Wrap" />
                <TextBlock Grid.Row="8" Grid.ColumnSpan="3" Text="Enter Notification Message" FontSize="24" Margin="20,0,20,0"/>
                <TextBox Name="NotificationMessageTextBox" Grid.Row="9" Grid.ColumnSpan="3" Margin="20,0,20,0" TextWrapping="Wrap" />
                <Button Grid.Row="10" Grid.ColumnSpan="3" HorizontalAlignment="Center" Content="2. Send push" Click="PushClick" Name="SendPushButton" />
            </Grid>
        </StackPanel>
    </Grid>
    
  9. Di bagian Penjelajah Solusi, buka file MainPage.xaml.cs untuk proyek (Windows 8.1) dan (Windows Phone 8.1) . Tambahkan pernyataan using berikut di bagian atas kedua file:

    using System.Net.Http;
    using Windows.Storage;
    using System.Net.Http.Headers;
    using Windows.Networking.PushNotifications;
    using Windows.UI.Popups;
    using System.Threading.Tasks;
    
  10. Dalam MainPage.xaml.cs untuk proyek WindowsApp, tambahkan anggota berikut ke kelas MainPage. Pastikan untuk mengganti <Enter Your Backend Endpoint> dengan titik akhir ujung belakang aktual Anda yang sudah diperoleh sebelumnya. Contohnya:http://mybackend.azurewebsites.net

    private static string BACKEND_ENDPOINT = "<Enter Your Backend Endpoint>";
    
  11. Tambahkan kode di bawah ini ke kelas MainPage di MainPage.xaml.cs untuk proyek (Windows 8.1) dan (Windows Phone 8.1) .

    Metode PushClick ini adalah handler klik untuk tombol Kirim Push. Metode ini memanggil ujung belakang untuk memicu pemberitahuan ke semua perangkat dengan tag nama pengguna yang sesuai dengan parameter to_tag. Pesan pemberitahuan dikirim sebagai konten JSON dalam isi permintaan.

    Metode LoginAndRegisterClick ini adalah handler klik untuk tombol Login dan daftar. Metode ini menyimpan token autentikasi dasar (mewakili token apa pun yang digunakan skema autentikasi Anda) di penyimpanan lokal, kemudian menggunakan RegisterClient untuk mendaftar pemberitahuan menggunakan ujung belakang.

    private async void PushClick(object sender, RoutedEventArgs e)
    {
        if (toggleWNS.IsChecked.Value)
        {
            await sendPush("wns", ToUserTagTextBox.Text, this.NotificationMessageTextBox.Text);
        }
        if (toggleFCM.IsChecked.Value)
        {
            await sendPush("fcm", ToUserTagTextBox.Text, this.NotificationMessageTextBox.Text);
        }
        if (toggleAPNS.IsChecked.Value)
        {
            await sendPush("apns", ToUserTagTextBox.Text, this.NotificationMessageTextBox.Text);
    
        }
    }
    
    private async Task sendPush(string pns, string userTag, string message)
    {
        var POST_URL = BACKEND_ENDPOINT + "/api/notifications?pns=" +
            pns + "&to_tag=" + userTag;
    
        using (var httpClient = new HttpClient())
        {
            var settings = ApplicationData.Current.LocalSettings.Values;
            httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic", (string)settings["AuthenticationToken"]);
    
            try
            {
                await httpClient.PostAsync(POST_URL, new StringContent("\"" + message + "\"",
                    System.Text.Encoding.UTF8, "application/json"));
            }
            catch (Exception ex)
            {
                MessageDialog alert = new MessageDialog(ex.Message, "Failed to send " + pns + " message");
                alert.ShowAsync();
            }
        }
    }
    
    private async void LoginAndRegisterClick(object sender, RoutedEventArgs e)
    {
        SetAuthenticationTokenInLocalStorage();
    
        var channel = await PushNotificationChannelManager.CreatePushNotificationChannelForApplicationAsync();
    
        // The "username:<user name>" tag gets automatically added by the message handler in the backend.
        // The tag passed here can be whatever other tags you may want to use.
        try
        {
            // The device handle used is different depending on the device and PNS.
            // Windows devices use the channel uri as the PNS handle.
            await new RegisterClient(BACKEND_ENDPOINT).RegisterAsync(channel.Uri, new string[] { "myTag" });
    
            var dialog = new MessageDialog("Registered as: " + UsernameTextBox.Text);
            dialog.Commands.Add(new UICommand("OK"));
            await dialog.ShowAsync();
            SendPushButton.IsEnabled = true;
        }
        catch (Exception ex)
        {
            MessageDialog alert = new MessageDialog(ex.Message, "Failed to register with RegisterClient");
            alert.ShowAsync();
        }
    }
    
    private void SetAuthenticationTokenInLocalStorage()
    {
        string username = UsernameTextBox.Text;
        string password = PasswordTextBox.Password;
    
        var token = Convert.ToBase64String(System.Text.Encoding.UTF8.GetBytes(username + ":" + password));
        ApplicationData.Current.LocalSettings.Values["AuthenticationToken"] = token;
    }
    
  12. Buka App.xaml.cs dan temukan panggilan ke InitNotificationsAsync() di penanganan aktivitasOnLaunched(). Ubah menjadi komentar atau hapus panggilan ke InitNotificationsAsync(). Handler tombol menginisialisasi pendaftaran pemberitahuan:

    protected override void OnLaunched(LaunchActivatedEventArgs e)
    {
        //InitNotificationsAsync();
    
  13. Klik kanan proyek WindowsApp, klik Tambahkan, lalu klik Kelas. Beri nama kelas sebagai RegisterClient.cs, lalu klik OK untuk membuat kelas.

    Kelas ini membungkus panggilan REST yang diperlukan untuk memanggil ujung belakang aplikasi, untuk mendaftar pemberitahuan push. Kelas ini juga secara lokal menyimpan registrationIds yang dibuat oleh Notification Hub sebagaimana dijelaskan dalam Mendaftar dari ujung belakang aplikasi Anda. Kelas ini menggunakan token otorisasi yang disimpan di penyimpanan lokal ketika Anda mengklik tombol Masuk dan daftar.

  14. Tambahkan pernyataan using berikut ke bagian atas file RegisterClient.cs:

    using Windows.Storage;
    using System.Net;
    using System.Net.Http;
    using System.Net.Http.Headers;
    using Newtonsoft.Json;
    using System.Threading.Tasks;
    using System.Linq;
    
  15. Tambahkan kode berikut di dalam definisi kelas RegisterClient:

    private string POST_URL;
    
    private class DeviceRegistration
    {
        public string Platform { get; set; }
        public string Handle { get; set; }
        public string[] Tags { get; set; }
    }
    
    public RegisterClient(string backendEndpoint)
    {
        POST_URL = backendEndpoint + "/api/register";
    }
    
    public async Task RegisterAsync(string handle, IEnumerable<string> tags)
    {
        var regId = await RetrieveRegistrationIdOrRequestNewOneAsync();
    
        var deviceRegistration = new DeviceRegistration
        {
            Platform = "wns",
            Handle = handle,
            Tags = tags.ToArray<string>()
        };
    
        var statusCode = await UpdateRegistrationAsync(regId, deviceRegistration);
    
        if (statusCode == HttpStatusCode.Gone)
        {
            // regId is expired, deleting from local storage & recreating
            var settings = ApplicationData.Current.LocalSettings.Values;
            settings.Remove("__NHRegistrationId");
            regId = await RetrieveRegistrationIdOrRequestNewOneAsync();
            statusCode = await UpdateRegistrationAsync(regId, deviceRegistration);
        }
    
        if (statusCode != HttpStatusCode.Accepted && statusCode != HttpStatusCode.OK)
        {
            // log or throw
            throw new System.Net.WebException(statusCode.ToString());
        }
    }
    
    private async Task<HttpStatusCode> UpdateRegistrationAsync(string regId, DeviceRegistration deviceRegistration)
    {
        using (var httpClient = new HttpClient())
        {
            var settings = ApplicationData.Current.LocalSettings.Values;
            httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic", (string) settings["AuthenticationToken"]);
    
            var putUri = POST_URL + "/" + regId;
    
            string json = JsonConvert.SerializeObject(deviceRegistration);
                            var response = await httpClient.PutAsync(putUri, new StringContent(json, Encoding.UTF8, "application/json"));
            return response.StatusCode;
        }
    }
    
    private async Task<string> RetrieveRegistrationIdOrRequestNewOneAsync()
    {
        var settings = ApplicationData.Current.LocalSettings.Values;
        if (!settings.ContainsKey("__NHRegistrationId"))
        {
            using (var httpClient = new HttpClient())
            {
                httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic", (string)settings["AuthenticationToken"]);
    
                var response = await httpClient.PostAsync(POST_URL, new StringContent(""));
                if (response.IsSuccessStatusCode)
                {
                    string regId = await response.Content.ReadAsStringAsync();
                    regId = regId.Substring(1, regId.Length - 2);
                    settings.Add("__NHRegistrationId", regId);
                }
                else
                {
                    throw new System.Net.WebException(response.StatusCode.ToString());
                }
            }
        }
        return (string)settings["__NHRegistrationId"];
    
    }
    
  16. Simpan semua perubahan Anda.

Menguji Aplikasi

  1. Luncurkan aplikasi pada kedua Windows.

  2. Masukkan Nama Pengguna dan Kata Sandi seperti yang ditunjukkan pada layar di bawah ini. Nama pengguna dan kata sandi ini harus berbeda dari nama pengguna dan kata sandi yang Anda masukkan di Windows Phone.

  3. Klik Masuk dan daftar dan verifikasi dialog yang menunjukkan bahwa Anda telah masuk. Kode ini juga mengaktifkan tombol Kirim Push.

    Ambil cuplikan layar aplikasi Notification Hubs yang memperlihatkan nama pengguna dan kata sandi yang telah diisi.

  4. Kemudian di bidang Tag Nama Pengguna Penerima, masukkan nama pengguna yang terdaftar. Masukkan pesan pemberitahuan dan klik Kirim Push.

  5. Hanya perangkat yang telah terdaftar dengan tag nama pengguna yang sesuai yang menerima pesan pemberitahuan.

    Cuplikan layar aplikasi Notification Hubs memperlihatkan pesan yang didorong.

Langkah berikutnya

Dalam tutorial ini, Anda akan belajar cara mengirim pemberitahuan push kepada pengguna tertentu yang memiliki tag terkait dengan pendaftaran mereka. Untuk mempelajari cara mengirim pemberitahuan push berbasis lokasi, lanjutkan ke tutorial berikut: