Delen via


Registreren vanuit uw app-back-end

Zoals vermeld in de vorige secties, moeten apparaten een of meer registraties maken in een Notification Hub om pushmeldingen te ontvangen. Een manier om deze registratie te voltooien, is dat de mobiele apparaten rechtstreeks contact opnemen met de Notification Hub om hun PNS-ingang en hun tags op te geven (of bij te werken). Deze aanpak heeft een aantal beperkingen en er zijn enkele scenario's waarin het raadzaam is contact op te maken met uw eigen app-back-end wanneer een apparaat de registratie vernieuwt. De back-end roept vervolgens de Notification Hub aan.

Wanneer moet u zich registreren vanuit uw app-back-end

Er zijn twee scenario's waarin het raadzaam is apparaatregistraties via uw app-back-end te routeren.

Tags moeten worden beveiligd

Wanneer een apparaat zich rechtstreeks registreert bij een Notification Hub, kan het elke gewenste tag opgeven. Dit is geen probleem als tags openbare belangengroepen zijn waarop elk apparaat zich kan abonneren (bijvoorbeeld nieuwsfeeds met betrekking tot sportteams). Dit kan echter een probleem zijn wanneer sommige tags alleen beschikbaar zijn voor sommige gebruikers.

Als u elke gebruiker alleen wilt registreren bij de toegestane tags, moet u de registratiebewerkingen routeren via uw eigen app-back-end, waarmee gebruikersverificatie kan worden uitgevoerd en de registratie voor de vereiste tags kan worden geautoriseerd.

Het meest voorkomende voorbeeld van dit scenario is het gebruik van tags om gebruikers-id's weer te geven. In dit geval wilt u voorkomen dat apparaten zich registreren bij tags die andere gebruikers vertegenwoordigen, omdat ze de meldingen van andere gebruikers ontvangen.

Tags worden gewijzigd door uw app-back-end

Registreren vanaf het apparaat is handig en stelt u in staat om snel pushmeldingen en uitgebreide routering naar interessegroepen in te stellen. Het registreren van het apparaat werkt echter niet goed als u tags wilt wijzigen als gevolg van gebeurtenissen die zich op andere apparaten voordoen.

Houd rekening met twee scenario's: als de tags op de telefoon van Alice zijn ingesteld als gevolg van gebeurtenissen die op de telefoon van Alice plaatsvinden, is het eenvoudig voor de app om de tags in de Notification Hub bij te werken. Als tags daarentegen moeten worden gewijzigd als gevolg van gebeurtenissen op andere apparaten (bijvoorbeeld de laptop van Alice wanneer ze zijn aangemeld bij een website), moet het apparaat wachten totdat de app weer actief is om de wijzigingen in de Notification Hub weer te geven.

Een specifiek voorbeeld van het vorige scenario is een muziek-app die een webervaring en een mobiele app bevat. In dit geval kan een specifieke gebruiker een nieuwe band volgen via de website en wilt dat het apparaat zo snel mogelijk meldingen over de nieuwe band ontvangt. Een ander voorbeeld is wanneer tags afkomstig zijn van andere onderdelen van uw back-end (bijvoorbeeld een CRM), waarmee de status van de gebruiker kan worden gewijzigd van Silver naar Gold. Deze wijziging kan ertoe leiden dat er een nieuwe tag wordt ingesteld voor de registraties van alle gebruikers.

Registreren vanuit de back-end

Bij het registreren van een apparaat moet een Notification Hub onderscheid maken tussen verschillende apparaten. Dit kan niet worden bereikt door alleen naar de PNS-ingangen te kijken, omdat ze tijdelijk en niet uniek zijn. Om dit probleem op te lossen, genereert Notification Hubs langlopende registratie-id's die elk apparaat lokaal moet opslaan om te kunnen verwijzen naar een eigen registratie telkens wanneer deze de PNS-ingang, tags of sjabloon bijwerkt.

In de volgende afbeelding ziet u de registratiestroom voor systeemeigen meldingen:

  1. Als er op het apparaat geen registratie-id lokaal is opgeslagen,

    1. Roep de back-end van de app aan om de registratie-id op te halen.

    2. App-back-end roept Notification Hubs aan om een nieuwe registratie-id te maken en retourneer vervolgens de id terug naar het apparaat.

    3. Sla de registratie-id op in de lokale opslag van het apparaat.

  2. Haal op het apparaat de registratie-id op uit de lokale opslag:

    1. Roep de back-end van de app aan, waarbij de registratie-id, PNS-handle en tags worden opgegeven.

    2. De app-back-end maakt of werkt de bijbehorende registratie op de Notification Hub bij.

    3. Als de app-back-end statuscode 410 retourneert, moet er een nieuwe registratie-id worden gemaakt. Verwijder de registratie-id uit de lokale opslag en start deze opnieuw vanaf stap 1.

Backend Registration

De stroom voor sjabloonmeldingen is vergelijkbaar. De enige verschillen zijn als volgt:

  1. Als een apparaat meerdere sjablonen gebruikt, moet het één registratie-id per sjabloon opslaan.

  2. U kunt de sjablonen identificeren met behulp van de eigenschap TemplateName van de registratie.

De volgende code is een voorbeeld van back-endeindpunten.

public class RegisterController : ApiController
    {

        private NotificationHubClient hub;

        public RegisterController()
        {
            hub = NotificationHubClient.CreateClientFromConnectionString("Endpoint=sb://buildhub-ns.servicebus.windows.net/;SharedAccessKeyName=DefaultFullSharedAccessSignature;SharedAccessKey=DuWV4SQ08poV6HZly8O/KQNWv3YRTZlExJxu3pNCjGU=", "build2014_2");
        }
        
        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()
        {
            return await hub.CreateRegistrationIdAsync();
        }

        // PUT api/register/5
        // This creates or updates a registration (with provided PNS handle) at the specified id
        public async void Put(string id, DeviceRegistration deviceUpdate)
        {
            // IMPORTANT: add logic to make sure that caller is allowed to register for the provided tags
            
            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 "gcm":
                    registration = new GcmRegistrationDescription(deviceUpdate.Handle);
                    break;
                default:
                    throw new HttpResponseException(HttpStatusCode.BadRequest);
            }

            registration.RegistrationId = id;
            registration.Tags = new HashSet<string>(deviceUpdate.Tags);

            try
            {
                await hub.CreateOrUpdateRegistrationAsync(registration);
            } catch (MessagingException e) {
                ReturnGoneIfHubResponseIsGone(e);
            }
        }

        // DELETE api/register/5
        public async void Delete(string id)
        {
            await hub.DeleteRegistrationAsync(id);
        }


        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());
            }
        }
    }

Houd er rekening mee dat u in de voorgaande code de logica moet toevoegen om ervoor te zorgen dat de client die dat eindpunt aanroept, gemachtigd is om zich te registreren voor de aangevraagde tags. Ook kan uw back-end de tags zelf toevoegen (bijvoorbeeld een userid-tag ).

In het volgende codevoorbeeld ziet u hoe u de registratiemethode implementeert voor een Windows Store-app, vanaf het apparaat, met de voorgaande eindpunten:

class RegisterClient
    {
        private string POST_URL = "{your back-end endpoints}";

        private class DeviceRegistration
        {
            public string Platform { get; set; }
            public string Handle { get; set; }
            public string[] Tags { get; set; }
        }

        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)
            {
                // log or throw
            }
        }

        private async Task<HttpStatusCode> UpdateRegistrationAsync(string regId, DeviceRegistration deviceRegistration)
        {
            using (var httpClient = new HttpClient())
            {
                var putUri = POST_URL + "/" + regId;
                var response = await httpClient.PutAsJsonAsync<DeviceRegistration>(putUri, deviceRegistration);
                return response.StatusCode;
            }
        }

        private async Task<string> RetrieveRegistrationIdOrRequestNewOneAsync()
        {
            var settings = ApplicationData.Current.LocalSettings.Values;
            if (!settings.ContainsKey("__NHRegistrationId"))
            {
                using (var httpClient = new HttpClient())
                {
                    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 Exception();
                    }
                }
            }
            return (string)settings["__NHRegistrationId"];

        }
    }

Registratie-id's opslaan in een back-enddatabase

Soms willen toepassingen de registratie-id's in de back-end van de app behouden in plaats van in de lokale opslag van het apparaat. Dit gebeurt meestal wanneer de back-end van de app al een manier heeft om apparaten te identificeren (bijvoorbeeld een installationId) en een manier om apparaatgegevens op te slaan in de back-endopslag (bijvoorbeeld bij het migreren van een aangepaste pushoplossing waarin PNS-ingangen zijn opgeslagen).

Tags wijzigen vanuit de back-end

Als u tags uit de back-end wilt wijzigen, moet u een manier hebben voor de back-end om de registraties te identificeren die moeten worden gewijzigd. Dit wordt meestal gedaan met behulp van een tag.

Stel dat er een muziek-app is waarin een gebruiker een nieuwe favoriete band van het web toevoegt en dat de back-end een tag toevoegt aan de mobiele registraties van de gebruiker als gevolg hiervan. In dit geval gebruikt de app een tag om de gebruiker te identificeren en gebruikt deze tag vervolgens om de registraties op te halen die moeten worden bijgewerkt en bijgewerkt.

In het volgende codevoorbeeld worden de registraties opgehaald en wordt er een nieuwe tag aan toegevoegd.

var registrations = await hub.GetRegistrationsByTagAsync("{userId}", 10);
            foreach (var reg in registrations)
            {
                reg.Tags.Add("{newBand}");
                await hub.UpdateRegistrationAsync(reg);
            }

Als u in dit voorbeeld sjablonen gebruikt, gaan we ervan uit dat u de tag aan al uw sjablonen toevoegt.