File upload via REST API?


#1

Hi,
I’m trying to upload file to Omeka S via REST API.

curl -F “file=@/home/store/im.jpg” http://localhost:8080/api/items?key_identity=hTHRcFByROlLsO5X2On9orAAwIrKqx6E&key_credential=Zcks0DyoYDGv0ZIyYxscuD5ATYoNZz6L

This results error below.

Obviously I need to tell Omeka to which item this get linked but how?
Is there anyone who have succeeded on this? I would be very grateful of any hints.

This is the last bit missing of our Omeka S workflow…

Best,
Ari

TypeError: Argument 2 passed to Omeka\Api\Manager::create() must be of the type array, null given, called in /var/www/html/application/src/Mvc/Controller/Plugin/Api.php on line 94 and defined in /var/www/html/application/src/Api/Manager.php:71
Stack trace:
#0 /var/www/html/application/src/Mvc/Controller/Plugin/Api.php(94): Omeka\Api\Manager->create('media', NULL, Array, Array)
#1 /var/www/html/application/src/Controller/ApiController.php(96): Omeka\Mvc\Controller\Plugin\Api->create('media', NULL, Array)
#2 /var/www/html/application/src/Controller/ApiController.php(181): Omeka\Controller\ApiController->create(NULL, Array)
#3 /var/www/html/vendor/zendframework/zend-mvc/src/Controller/AbstractRestfulController.php(429): Omeka\Controller\ApiController->processPostData(Object(Zend\Http\PhpEnvironment\Request))
#4 /var/www/html/application/src/Controller/ApiController.php(154): Zend\Mvc\Controller\AbstractRestfulController->onDispatch(Object(Zend\Mvc\MvcEvent))
#5 /var/www/html/vendor/zendframework/zend-eventmanager/src/EventManager.php(322): Omeka\Controller\ApiController->onDispatch(Object(Zend\Mvc\MvcEvent))
#6 /var/www/html/vendor/zendframework/zend-eventmanager/src/EventManager.php(179): Zend\EventManager\EventManager->triggerListeners(Object(Zend\Mvc\MvcEvent), Object(Closure))
#7 /var/www/html/vendor/zendframework/zend-mvc/src/Controller/AbstractController.php(105): Zend\EventManager\EventManager->triggerEventUntil(Object(Closure), Object(Zend\Mvc\MvcEvent))
#8 /var/www/html/vendor/zendframework/zend-mvc/src/Controller/AbstractRestfulController.php(313): Zend\Mvc\Controller\AbstractController->dispatch(Object(Zend\Http\PhpEnvironment\Request), Object(Zend\Http\PhpEnvironment\Response))
#9 /var/www/html/vendor/zendframework/zend-mvc/src/DispatchListener.php(119): Zend\Mvc\Controller\AbstractRestfulController->dispatch(Object(Zend\Http\PhpEnvironment\Request), Object(Zend\Http\PhpEnvironment\Response))
#10 /var/www/html/vendor/zendframework/zend-eventmanager/src/EventManager.php(322): Zend\Mvc\DispatchListener->onDispatch(Object(Zend\Mvc\MvcEvent))
#11 /var/www/html/vendor/zendframework/zend-eventmanager/src/EventManager.php(179): Zend\EventManager\EventManager->triggerListeners(Object(Zend\Mvc\MvcEvent), Object(Closure))
#12 /var/www/html/vendor/zendframework/zend-mvc/src/Application.php(332): Zend\EventManager\EventManager->triggerEventUntil(Object(Closure), Object(Zend\Mvc\MvcEvent))
#13 /var/www/html/index.php(17): Zend\Mvc\Application->run()

Example API usage (using curl)
Using the API in php
#2

At first glance, it seems possible that this is a bug on our side. We recently made significant changes that made arrays required for some calls. We’ll check into it.


#3

To upload a file you’ll need to POST it to the media endpoint, like so:

curl -F 'file[0]=@/path/to/file' -F 'data={"o:ingester": "upload", "file_index": 0, "o:item": {"o:id": [id]}}' 'http://localhost/omeka-s/api/media?...'

Note that you need to set the item ID in the data.


#4

Thanks for responses!

I had a wrong api path in my question. I was using /api/media endpoint.

I tried with this:
curl -F ‘file[0]=@/home/store/img.jpg’ -F ‘data={“o:ingester”: “upload”, “file_index”: 0, “o:item”: {“o:id”: 11}’ ‘http://localhost:8080/api/media?key_identity=hTHRcFByROlLsO5X2On9orAAwIrKqx6E&key_credential=Zcks0DyoYDGv0ZIyYxscuD5ATYoNZz6L

Still no luck, the error is the same.
Actually, the endpoint does not seem to matter. I also tried /api/foo and /api/item and still got the same error.


#5

Ah,
I was missing a curly bracket. Now it is working. Thanks for the help!

Here is a working example:

curl -F ‘file[0]=@/home/store/img.jpg’ -F ‘data={“o:ingester”: “upload”, “file_index”: “0”, “o:item”: {“o:id”: “11”}}’ ‘http://localhost:8080/api/media?key_identity=hTHRcFByROlLsO5X2On9orAAwIrKqx6E&key_credential=Zcks0DyoYDGv0ZIyYxscuD5ATYoNZz6L

This adds image to an item 11.


#6

Just in case anyone’s wondering how to upload files using Python Requests, something like this should work…

params = {
    'key_identity': key_identity,
    'key_credential': key_credential
}

data = {
    "o:ingester": "upload", 
    "file_index": "0", 
    "o:item": {"o:id": "13"}
}

files = [
     ('data', (None, json.dumps(data), 'application/json')),
     ('file[0]', ('7288020-p15.jpg', open('7288020-p15.jpg', 'rb'), 'image/jpg'))
]

response = requests.post('http://example.com/api/media', params=params, files=files)

Took me a while to figure out how to combine the JSON and image files.