Datei-Presenter¶
Die Presenter für Dateien \Alvine\Application\Web\Presenter\File
, \Alvine\Application\Web\Presenter\File\Upload
und \Alvine\Application\Web\Presenter\File\Collection
stellen Methoden für die Arbeit mit Dateien bereit.
Die Standardpresenter können Dateien empfangen und lokal speichern, eine Dateiliste übertragen und Dateien löschen.
In den Beispielen wird beschrieben wie ein Benutzer Dateinen auf dem Server speichern und wieder laden kann.
Pattern¶
Das Pattern einer Route wird mit einem Regex definiert, hier muss der Schrägstrich /
nicht maskiert werden, es wird ein anderes Trennzeichen verwendent.
Platzhalter in der Route¶
Für den Pfad und die URL können unterschiedliche Platzhalter verwendet werden.
Alle Parameter stehen über ${PARAMETER:xxx}
zur Verfügung (xxx
ist der Name des Parameters).
Es können hier auch die Standardplatzhalter der Anwendung verwendet werden
Hinweis
Die verwendeten Parameter müssen im Abschnitt Parameter definiert werden. Bei Integer-Parametern ist darauf zu achten, dass diese einen Default-Wert haben. Parameter
Datei laden¶
Wenn die Dateien über den File Presenter geladen werden, wird der Mimetype der Datei mitgesendet.
Die Datei wird im Browser entsprechend angezeigt.
Hinweis
Die Server Konfiguration muss so eingestellt sein, das die Files nicht direkt vom Server ausgeliefert werden. Die Anfrage muss von Alvine verabeitet werden. location ~* api/user/files/([0-9]+)/.*.(?:avi|bin|css|js|bmp|dmg|doc|docx|dpkg|exe|flv|gif|htm|html|ico|ics|img|jpeg|jpg|m2a|m2v|mov|mp3|mp4|mpeg|mpg|msi|pdf|pkg|png|ppt|pptx|ps|rar|rss|rtf|swf|tif|tiff|txt|wmv|xhtml|xls|xml|zip)$ { try_files $uri @alvine; }
Konfiguration der Route¶
In der Konfiguration ist nur die Angabe des Server Pfad notwendig, wo die Dateien abgelegt sind.
<route id="ROUTE-ID-FILELOAD">
<method>GET</method>
<pattern><![CDATA[^/api/user/files/(?<uid>[0-9]+)/(?<file>[a-z0-9.\-_]+\.(svg|jpg|gif|png|pdf))$]]></pattern>
<template><![CDATA[/api/user/files/${uid}/${file}]]></template>
<presenter>\Alvine\Application\Web\Presenter\File</presenter>
<configuration>
<source>
<path>{CUSTOMISATIONPATH}upload/user/files/${PARAMETER:uid}</path>
</source>
</configuration>
<parameters>
<parameter name="uid" type="Integer" >0</parameter>
<parameter name="file" type="StringType" />
</parameters>
</route>
Dateien auflisten¶
Über die GET
Anfrage kann eine Dateiliste abgerufen werden. Im folgenden Beispiel wird eine Liste für die UID 10 abgerufen
curl --request GET \
--url 'http://example.com/api/user/files/10' \
--header 'accept: application/json'
Konfiguration der Route¶
In der Route muss sowohl der Pfad als auch die gewünschte URL konfiguriert werden mit der die Datei wieder geladen werden kann.
Über den Filter-Tag werden die Dateien aufgeführt, die auszugeben sind. hierzu muss ein Regex, der auf den Dateinamen angewendet wird, angegeben werden. Nur Dateien die für den Regex gültig sind, werden im Ergebnis aufgeführt.
Wird der filter weggelassen, so werden alle Dateien in das Ergebnis aufgenommen.
In diesem Beispiel ist der Filter so eingestellt, wie auch der Upload oder das Laden erlaubt wird.
Die Dateien liegen hier im Beispiel auf dem Server {CUSTOMISATIONPATH}upload/user/files/10
<route id="ROUTE-ID-FILELIST">
<method>GET</method>
<pattern><![CDATA[^/api/user/files/(?<uid>[0-9]+)$]]></pattern>
<template><![CDATA[/api/user/files/${uid}]]></template>
<presenter>\Alvine\Application\Web\Presenter\File\Collection</presenter>
<configuration>
<source>
<path>{CUSTOMISATIONPATH}upload/user/files/${PARAMETER:uid}</path>
<uri>/api/user/files/${PARAMETER:uid}/</uri>
<filter><![CDATA[/^[a-z0-9.\-_]+\.(svg|jpg|gif|png|pdf)$/]]></filter>
</source>
</configuration>
<parameters>
<parameter name="uid" type="Integer" >0</parameter>
</parameters>
</route>
ein Beispiel für ein Ergebnis
{
dataset: {
9f18cb8f8d698e3a8c5090ec36a807a3: {
name: "test.jpg",
url: "/api/user/files/10/test.jpg",
bytes: 366985,
sha1: "ae2a20bfa00f916882d4cfd07da11d298985d802",
lastAccessTime: "2019-08-25T06:21:36",
lastModifiedTime: "2019-08-20T09:55:29"
}
},
sys: {
pagination: {
total: 1
},
message: "200 OK",
code: 200
}
}
Dateien hochladen¶
Dateien können als Multipart-Mimetype hochgeladen werden. Dazu muss ein Feldname - in diesem Fall image
definiert und
im Request übergeben werden. Wird in der Route kein fester Dateiname bestimmt, so wird der übergebene Dateiname genommen.
POST http://example.com/api/file/myname/upload HTTP/1.1
Host: example.com
Content-Length: 3038
Accept: application/json
...
Cache-Control: no-cache
Content-Type: application/x-www-form-urlencoded
------WebKitFormBoundary5F4MlOdhad1hS9cu
Content-Disposition: form-data; name="image"; filename="test.gif"
Content-Type: image/gif
...
Konfiguration der Route¶
In der Route muss wie bei der Liste in destination/path
der Pfad und in destination/uri
die URL konfiguriert werden. Außerdem kann
man optional einen Dateinamen und die Option zum Überschreiben angeben. Wird ein Dateiname definiert, so wird
die Datei immer unter diesem Namen gespeichert. Ansonsten wird der Name aus der Übertragung genommen.
Im Tag name
muss der Feldname der in der Übertragung verwendet wird definiert sein.
Wird die Option overwrite
auf true
gesetzt, so wird eine vorhandene Datei überschrieben. Andernfalls
wird jeweils eine Zahl an den Dateinamen gehängt. Wird zum Beispiel der Dateiname bild.jpg
übertragen, und gibt es im Zielordner
bereits eine Datei mit diesem Namen, so wird die neue Datei unter bild-1.jpg
, danach unter bild-2.jpg
usw abgespeichert.
Ab 1000 Dateien mit dem gleichen Namen wird allerdings ein Fehler zurück gegeben. Damit sind datei-1.jpg
bis datei-999.jpg
möglich.
Die maximale Anzahl kann über eine abgeleitete Klasse geändert werden.
Über die Einschränkung restriction/bytes
kann die maximal erlaubte Dateigröße in Bytes angegeben werden. Über restriction/filter
kann
ein regulärer Ausdruck definiert werden. Der Dateiname wird gegen diesen Ausdruck geprüft. Schlägt eine Prüfung fehl, so wird eine Fehlermeldung
zurück gegeben.
<route id="ROUTE-ID-FILEUPLOAD">
<method>POST</method>
<pattern><![CDATA[^/api/user/files/(?<uid>[0-9]+)/upload$]]></pattern>
<template><![CDATA[/api/user/files/${uid}/upload]]></template>
<presenter>\Alvine\Application\Web\Presenter\File\Upload</presenter>
<configuration>
<name>file</name> <!-- Feldname im Post -->
<destination>
<path>{CUSTOMISATIONPATH}upload/user/files/${PARAMETER:uid}</path>
<uri>/api/user/files/${PARAMETER:uid}/upload</uri>
<filename>myImage.png</filename> <!-- optional dann auch den filter entsprechend einstellen wegen der Dateiendung ".png" -->
<overwrite>true</overwrite> <!-- optional -->
</destination>
<restriction>
<bytes>2000000</bytes> <!-- optional 2Mb -->
<filter><![CDATA[/^[a-z0-9.\-_]+\.(svg|jpg|gif|png|pdf)$/]]></filter> <!-- optional -->
</restriction>
</configuration>
<parameters>
<parameter name="uid" type="Integer" >0</parameter>
</parameters>
</route>
Datei löschen¶
Über den File-Presenter lassen sich Deteien über DELETE
auch löschen. Aktuell kan nur eine Datei auf einmal gelöscht werden.
Konfiguration der Route¶
In der Route muss der Pfad der Datei konfiguriert sein. Optional kann - insbesondere wenn der Dateiname nicht als URL-Parameter - sondern als Query-Parameter definiert ist - ein Filter angegeben werden. Dieser schränkt dann den erlaubten Dateinamen der zu löschenden Dateien ein.
Hinweis
Aus Sicherheitsgründen sollte der Dateiname über die URL konfiguriert werden und nicht als Parameter übergeben werden.
<route id="ROUTE-ID-FILEDELETE">
<method>DELETE</method>
<pattern><![CDATA[^/api/user/files/(?<uid>[0-9]+)/(?<file>[a-z0-9.\-_]+\.(svg|jpg|gif|png|pdf))$]]></pattern>
<template><![CDATA[/api/user/files/${uid}/${file}]]></template>
<presenter>\Alvine\Application\Web\Presenter\File</presenter>
<configuration>
<destination>
<path>{CUSTOMISATIONPATH}upload/user/files/${PARAMETER:uid}</path>
<!-- Wichtig: Wenn der Dateiname nicht über die URL, sondern über einen Parameter übergeben wird -->
<filter><![CDATA[/^[a-z0-9.\-_]+\.(svg|jpg|gif|png|pdf)$/]]></filter> <!-- optional -->
</destination>
</configuration>
<parameters>
<parameter name="file" type="StringType" />
<parameter name="uid" type="Integer" >0</parameter>
</parameters>
</route>