Heim  >  Artikel  >  Backend-Entwicklung  >  Unterstützt zusammengesetzte Schlüssel in ASP.NET-Web-API-OData

Unterstützt zusammengesetzte Schlüssel in ASP.NET-Web-API-OData

PHP中文网
PHP中文网Original
2017-06-17 16:33:571859Durchsuche

本文转自:

Der standardmäßige EntitySetController unterstützt keine zusammengesetzten Schlüssel. Wenn Sie also zusammengesetzte Schlüsselmodelle haben, ist etwas zusätzliche Arbeit erforderlich. Hier ist ein Beispiel dafür.

Das Modell ist einfach:

<code>public class Person
{
    [Key]
    public string FirstName { get; set; }
    [Key]
    public string LastName { get; set; }

    public int Age { get; set; }
}
</code>

Die Odata-URL für dieses Modell sieht folgendermaßen aus:

<code>GET http://localhost:33051/People(FirstName='Kate',LastName='Jones') HTTP/1.1
</code>

Und wir möchten stark typisierte Parameter in Web-API-Aktionen für diese URL haben.

<code>    public Person Get([FromODataUri] string firstName, [FromODataUri] string lastName)
</code>

Beachten Sie, dass das FromODataUri-Modellbinderattribut zum Parsen von der Odata-URI-Darstellung zum CLR-Typ verwendet wird. In odata ist der String-Wert „'xxx'“ und wir möchten, dass er „xxx“ ist.

Damit die Route funktioniert, können Sie eine benutzerdefinierte Routing-Konvention hinzufügen, um den Schlüsselpfad zu analysieren. Hier ist eine Beispielimplementierung:

<code>public class CompositeKeyRoutingConvention : EntityRoutingConvention
{
    public override string SelectAction(System.Web.Http.OData.Routing.ODataPath odataPath, System.Web.Http.Controllers.HttpControllerContext controllerContext, ILookup<string, System.Web.Http.Controllers.HttpActionDescriptor> actionMap)
    {
        var action = base.SelectAction(odataPath, controllerContext, actionMap);
        if (action != null)
        {
            var routeValues = controllerContext.RouteData.Values;
            if (routeValues.ContainsKey(ODataRouteConstants.Key))
            {
                var keyRaw = routeValues[ODataRouteConstants.Key] as string;
                IEnumerable<string> compoundKeyPairs = keyRaw.Split(',');
                if (compoundKeyPairs == null || compoundKeyPairs.Count() == 0)
                {
                    return action;
                }

                foreach (var compoundKeyPair in compoundKeyPairs)
                {
                    string[] pair = compoundKeyPair.Split('=');
                    if (pair == null || pair.Length != 2)
                    {
                        continue;
                    }
                    var keyName = pair[0].Trim();
                    var keyValue = pair[1].Trim();

                    routeValues.Add(keyName, keyValue);
                }
            }
        }

        return action;
    }
}
</code>

Die Konvention wird von EntityRoutingConvention geerbt, der Standardkonvention für die Verarbeitung von Entitätsschlüsseln. Durch den Aufruf von base.SelectAction wird der vollständige Schlüsselpfad zu routeValues ​​hinzugefügt. Die neue Konvention prüft, ob sie „“ enthält, teilt sie in mehrere Schlüssel auf und setzt jeden von ihnen in „routeValues“. Wenn also die Web-API Aktionen auswählt, werden diese Werte verwendet, um zu bestimmen, welche Aktion ausgewählt werden soll. Wenn kein „“ gefunden wird, verhält es sich genauso wie die Basiskonvention.

Um die Konvention zu registrieren, müssen Sie sie beim Zuordnen der OData-Route festlegen:

<code>public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.EnableQuerySupport();

        var mb = new ODataConventionModelBuilder(config);
        mb.EntitySet<Person>("People");

        var conventions = ODataRoutingConventions.CreateDefault();
        conventions.Insert(0, new CompositeKeyRoutingConvention());

        config.Routes.MapODataRoute(
            routeName: "OData", 
            routePrefix: null, 
            model: mb.GetEdmModel(), 
            pathHandler: new DefaultODataPathHandler(), 
            routingConventions: conventions);
    }
}
</code>

Registrieren Sie die Route an der Position 0, damit sie vor anderen Standard-Routing-Konventionen ausgeführt wird. Daher wird die standardmäßige EntityRoutingConvetion nicht davor ausgeführt. Danach sollten Sie mit der Routing-Arbeit beginnen können.

Wie erstellt man dann eine URL für zusammengesetzte Schlüssel? 
Sie müssen dies nicht tun, wenn OData-Links den Bearbeitungslink und den Selbstlink enthalten, wenn Sie ODataConventionModelBuilder verwenden. Es erkennt automatisch zusammengesetzte Schlüssel und erstellt die URI für Sie.

Sie müssen jedoch den Link für den Standort-Header erstellen. Hier ist ein Beispielcode von PeopleController.cs zur Bearbeitung von Post-Anfragen:

<code>public HttpResponseMessage PostPerson(Person person)
{
    if (ModelState.IsValid)
    {
        _repo.UpdateOrAdd(person);

        HttpResponseMessage response = Request.CreateResponse(HttpStatusCode.Created, person);
        string key = string.Format(
            "{0}={1},{2}={3}",
            "FirstName", ODataUriUtils.ConvertToUriLiteral(person.FirstName, Microsoft.Data.OData.ODataVersion.V3),
            "LastName", ODataUriUtils.ConvertToUriLiteral(person.LastName, Microsoft.Data.OData.ODataVersion.V3));
        response.Headers.Location = new Uri(Url.ODataLink(
            new EntitySetPathSegment("People"),
            new KeyValuePathSegment(key)));
        return response;
    }
    else
    {
        return Request.CreateResponse(HttpStatusCode.BadRequest);
    }
}
</code>

Ich hoffe, es hilft.

 

Das obige ist der detaillierte Inhalt vonUnterstützt zusammengesetzte Schlüssel in ASP.NET-Web-API-OData. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn