Objekt-Presenter

Der Objekt-Presenter \Alvine\Application\Web\Presenter\Data\Object ist von \Alvine\Application\Web\Presenter\Data abgeleitet und stellt Methoden für die bearbeitung von DELETE, GET, HEAD, PUT und PATCH Anfragen bereit. Für die POST Methode ist ein eigener Add-Presenter verantwortlich.

Die Steuerung, welcher View zur Anwendung kommt, erfolgt über den vom Client mitgesendeten Accept-Header. Hier ist entweder application/json oder text/html möglich. Für die HTML-Ausgabe ist der Standardview des Presenters - wenn keiner über die Konfiguration angegeben wird - die von der Methode Object::getDefaultViewClass() zurückgegebene Klasse.

Der View kann auch über die Konfiguration in der Route definiert werden.

Hinweis

Sie müssen sicherstellen das Ihr View das Interface \Alvine\Application\Web\View\InstanceFromContainer implementiert.

GET

Über die GET Anfrage können ein oder mehrere Objekte abgefragt werden. Die Einschränkung erfolgt über die definierten Parameter. Hier können die gewünschten Feldnamen über name=value eingeschränkt werden. Je nach View wird die Ausgabe als HTML-Datei oder Json zurückgegeben.

Über folgende Parameter lassen sich weitere Einstellungen vornehmen:

Parmater Beschreibung
count Ergebnisse pro Anfrage
name Name des zu ändernden Feldes
offset Offset der zurückgegeben werden soll
orderby Feldnamen nach denen Sortiert werden soll
page Seiten die zurückgegeben werden soll

Im folgenden Beispiel werden maximal 10 Objekte, beginnend auf Seite 2 und nach dem Feld name sortiert zurückgegeben.

curl --request GET \
  --url 'http://example.com/api/myobject?count=10&page=2&orderby=name' \
  --header 'accept: application/json'

Konfiguration der Route

<route id="ROUTE-ID-GET">
    <method>GET</method>
    <presenter>MyPresenter</presenter>
    <pattern><![CDATA[^\/api\/object$]]></pattern>
    <template><![CDATA[/api/object]]></template>
    <configuration>
        <model>  <!-- Klassenname des Models -->
            <class>MyModel</class>    
        </model>

        <!-- erlaubte Mimetypes für die Antwort: Möglichkeiten: json, html -->
        <mimetypes>
            <allowed>text/html</allowed>    
            <allowed>application/json</allowed>  
        </mimetypes>

        <view>  <!-- Klassenname des Views für HTML und JSON -->
            <class type="texyt/html">\Alvine\Application\Web\View\Data\Object</class>   
            <class type="application/json">\Alvine\Application\Web\View\Json\Dataset</class>    
        </view>
    </configuration>
</route>

PUT

Über die PUT Anfrage können ein oder mehrere Objekte geändert werden. Als Ergebnis wird entweder der Status 204 No Content oder wenn JSON unterstützt wird ein Array mit dem Ergebnis zurück gegeben. Über den Parameter whatif kann die Anfrage simuliert werden.

Parmater Beschreibung
whatif Anfrage nur flüchtig, ohne echte Aktion durchführen

Wird in der Route eine Redirect-URL definiert, so wird diese bei der Änderung eines Datensatzes per Location Header an den Client übergeben. Bei der Rückgabe von JSON oder mehreren Änderungen ist die Location in der Antwort enthalten.

In dem folgenden Beispiel werden die zwei Datensätze mit der ID 2 und 5 geändert.

curl --request PUT \
  --url 'http://example.com/api/object' \
  --header 'accept: application/json' \
  --header 'content-type: application/json' \
  --data '{
    "dataset": [
        {
            "id": 2,
            "name": "Neuer Name",
        },
        {
            "id": 5,
            "flag":2,
        }
    ]
}'

Im Erfolgsfall ist das Ergebnis folgendes JSON

{
  "dataset": [
    {
      "dataset": {
        "id": 2,
        "name": "Neuer Name",
        "flag": 5,
      },
      "sys": {
        "updated": "2017-10-21T16:15:35",
        "message": "200 OK",
        "code": 200,
        "location": ""
      }
    },
    {
      "dataset": {
        "id": 5,
        "name": "Alter Name",
        "flag": 2,
      },
      "sys": {
        "updated": "2017-10-21T16:15:35",
        "message": "200 OK",
        "code": 200,
        "location": ""
      }
    }
  ]
}

In diesem Beispiel wurde ein Datensatz geändert und beim zweiten Datensatz ist ein Fehler aufgetreten (die angegebene ID gibt es nicht; 404).

{
    "dataset": [
        {
            "dataset": {
              "id": 5,
              "name": "Alter Name",
              "flag": 2,
            },
            "sys": {
                "updated": "2017-10-21T16:30:31",
                "message": "200 OK",
                "code": 200,
                "location": ""
            }
        },
        {
            "sys": {
                "error": {
                    "code": 404,
                    "message": "404 Not Found"
                }
            }
        }
    ],
    "sys": {
        "error": {
            "code": 400,
            "message": "400 Bad Request"
        }
    }
}

Werden keine oder falsche Daten übertragen, so wird folgende Fehlermeldung zurückgegeben:

{
    "sys": {
        "error": {
            "code": 400,
            "message": "400 Bad Request"
        }
    }
}

Konfiguration der Route

In diesem Beispiel wird das zu ändernde Objekte über die ID bestimmt und geändert.

<route id="ROUTE-ID-UPDATE">
    <method>PUT</method>
    <presenter>MyPresenter</presenter>
    <pattern><![CDATA[^\/api\/object\/(?<id>[0-9]+)$]]></pattern>
    <template><![CDATA[/api/object/${id}]]></template>
    <configuration>
        <model>  <!-- Klassenname des Models -->
            <class>MyModel</class>    
        </model>
    </configuration>
</route> 

Mehrere Objekte können über folgende Konfiguration verarbeitet werden. Wichtig ist hier, dass der Parameter dataset definiert ist.

<route id="ROUTE-ID-UPDATE">
    <method>PUT</method>
    <presenter>MyPresenter</presenter>
    <pattern><![CDATA[^\/api\/object$]]></pattern>
    <template><![CDATA[/api/object]]></template>
    <parameters>
        <parameter name="dataset" type="ArrayType" />
    </parameters>
    <configuration>
        <model>  <!-- Klassenname des Models -->
            <class>MyModel</class>    
        </model>
    </configuration>
</route> 

Ein Redirect kann über den Linksbereich in der Route definiert werden.

<route id="ROUTE-ID-UPDATE">
    ...
    <links> 
        <!-- die ID der anzuwendende Route und die Relation "redirect" -->
        <link route="ROUTE-ID-UPDATE" relation="redirect" />
    </links>
</route> 

DELETE

Über die DELETE Anfrage können ein oder mehrere Objekte gelöscht werden. Als Ergebnis wird entweder der Status 204 No Content oder wenn JSON unterstützt wird ein Array mit dem Ergebnis zurück gegeben. Die Einschränkung, welches Objekt gelöscht werden soll erfolgt über die in den Parametern übergebene ID.

Parmater Beschreibung
whatif Anfrage nur flüchtig, ohne echte Aktion durchführen

Die folgende Anfrage löscht den Datensatz mit der ID 1.

curl --request DELETE \
  --url 'http://example.com/api/myobject/1' \
  --header 'accept: application/json'

Wird an die URL der Parameter whatif angehängt, so wird der Datensatz nur geprüft, aber nicht gelöscht.

curl --request DELETE \
  --url 'http://example.com/api/myobject/1?whatif=true' \
  --header 'accept: application/json'

Mehrere Objekte können über ein JSON mit den entsprechenden IDs gelöscht werden. Hierzu muss in der Route (siehe unten) der Parameter dataset definiert werden.

curl --request DELETE \
  --url 'http://example.com/api/myobject' \
  --header 'accept: application/json' \
  --header 'content-type: application/json' \
  --data '{
        "dataset": [
            {
                "id": 1
            },
            {
                "id": 2
            }
        ]
    }'

Das Ergebnis ist dann im Erfolgsfall folgendes:

{
    "dataset": [
        {
            "sys": {
                "message": "200 OK",
                "code": 200
            }
        },
        {
            "sys": {
                "message": "200 OK",
                "code": 200
            }
        }
    ]
}

Werden die Objekte nicht gefunden, so wird ein 404 Fehler zurückgegeben.

Konfiguration der Route

In diesem Beispiel wird die ID des zu löschenden Objektes in die URL integriert und von dort ausgelesen. Somit ist die ID der URL Bestandteil der URL.

<route id="ROUTE-ID-DELETE">
    <method>DELETE</method>
    <presenter>MyPresenter</presenter>
    <pattern><![CDATA[^\/api\/object\/(?<id>[0-9]+)$]]></pattern>
    <template><![CDATA[/api/object/${id}]]></template>
    <configuration>
        <model>  <!-- Klassenname des Models -->
            <class>MyModel</class>    
        </model>
    </configuration>
</route> 

Sollen mehrere Objekte mit einem Request gelöscht werden, so kann dies über ein JSON erfolgen. Die entsprechende Route muß folgendermaßen aussehen.

<route id="ROUTE-ID-DELETE">
    <method>DELETE</method>
    <presenter>MyPresenter</presenter>
    <pattern><![CDATA[^\/api\/object$]]></pattern>
    <template><![CDATA[/api/object]]></template>
    <parameters>
        <parameter name="dataset" type="ArrayType" />
    </parameters>
    <configuration>
        <model>  <!-- Klassenname des Models -->
            <class>MyModel</class>    
        </model>
    </configuration>
</route> 

Head-Anfragen werden durch die GET-Methode bearbeitet. Das Verhalten ist dort beschrieben.

PATCH

Mittels PATCH-Anfragen lassen sich einzelne Eigenschaften eines Objektes überschreiben. Die Daten können entweder als application/json oder x-www-form-urlencoded übertragen werden.

Parmater Beschreibung
name Name des zu ändernden Feldes
uuid Primärschlüssel des Datensatzes der geändert werden soll
pk Alternativer Name für den Primärschlüssel
value Neuer Wert des zu ändernden Feldes
whatif Anfrage nur flüchtig, ohne echte Aktion durchführen
curl --request PATCH \
  --url 'http://{{domain}}/api/commerce/item/catalog/category' \
  --header 'accept: application/json' \
  --header 'content-type: application/x-www-form-urlencoded'
  -d "pk=5&name=flag&value=1425"

Im Erfolgsfall wird folgendes zurückgegeben

{
    "dataset": {
        "id": 5,
        "name": "Alter Name",
        "flag": 1425,
    },
    "sys": {
        "updated": "2017-10-22T12:43:37",
        "message": "200 OK",
        "code": 200
    }
}

Im Fehlerfall - fehlerhafte Validierung - wird folgendes zurückgegeben.

{
    "sys": {
        "validation": {
            "report": {
                "name": {
                    "message": "wrong value",
                    "state": "error",
                    "valid": false
                }
            }
        },
        "error": {
            "code": 400,
            "message": "400 Bad Request"
        }
    }
}

Konfiguration der Route

<route id="ROUTE-ID-PATCH">
    <method>PATCH</method>
    <pattern><![CDATA[^\/api\/object$]]></pattern>
    <template><![CDATA[/api/object]]></template>
    <configuration>
        <model>  <!-- Klassenname des Models -->
            <class>MyModel</class>    
        </model>
    </configuration>
</route> 

Kommentare