======== REST API ======== The ESP python client abstracts a lot of complexity associated with interacting with the ESP backend, but there are REST-based endpoints available for interacting with the backend directly as well. Below are descriptions of those endpoints, with examples for how to use them. Setup ===== .. note:: All examples will be provided using python as the modality for issuing requests, but these techniques are portable across other programming languages. Using the ``requests`` library in python, you can set up a ``Session`` for issuing the requests using the following (please note that the request headers below are required for the session): .. code-block:: python >>> # imports >>> import requests >>> try: >>> # python 2 >>> import cookielib as cookiejar >>> except ImportError: >>> # python 3 >>> import http.cookiejar as cookiejar >>> >>> # set up session and cookie management >>> session = requests.Session() >>> session.headers.update({ >>> "Connection": "keep-alive", >>> "Accept": "application/json", >>> "Content-Type": "application/json" >>> }) >>> jar = cookiejar.MozillaCookieJar() >>> >>> # set the url for connecting to ESP - this will vary based on your installation >>> url = 'http://localhost:8002' In order to reduce boilerplate for issuing requests in the API documentation below, the following python functions will be used and referenced throughout the examples: .. code-block:: python >>> def get(endpoint, **kwargs): >>> response = session.get( >>> url=url + endpoint, >>> cookies=jar, verify=False, >>> **kwargs >>> ) >>> return response.json() >>> >>> def post(endpoint, **kwargs): >>> response = session.post( >>> url=url + endpoint, >>> cookies=jar, verify=False, >>> **kwargs >>> ) >>> return response.json() >>> >>> def put(endpoint, **kwargs): >>> response = session.put( >>> url=url + endpoint, >>> cookies=jar, verify=False, >>> **kwargs >>> ) >>> return response.json() Login ===== In order to access the REST API, a user first needs to be authenticated. You can authenticate a session using the ``/login`` entry-point as you would in the UI. Once the session is set up (see above), you can login to the application like so: .. code-block:: python >>> post('/login', auth=requests.auth.HTTPBasicAuth( >>> 'admin@localhost', # email or username for user >>> 'my-secret-password' # password for user >>> ) Using the ``cookies=`` option will save authentication credentials for accessing other parts of the application. SampleType ========== GET --- **URLs**: * ``/api/sample_types`` - Retrieve all objects in database. * ``/api/sample_types/`` - Retrieve single object by UUID **Optional Parameters**: * ```` - UUID for the object. See ``/api/sample_types`` for an example of retrieving uuids for objects. **Success Response Code**: ``200 OK`` **Examples**: * Query all samples: .. code-block:: python >>> get('/api/sample_types') [ { "name": "Generic sample", "desc": "Types for samples with no other classification", "tags": ['test', 'sampletype'], "updated_at": "2018-08-12T22:47:41.328597Z", "created_at": "2018-08-12T22:47:41.328597Z", "uuid": "77777777-7777-4014-b700-053200000000", "def_uuid": "77777777-7777-4014-b700-053300000000", "sample_type_id": "77777777-7777-4014-b700-053300000000" "owner": "system admin (admin@localhost)", "meta": { "lab7_id_sequence": [ "ESP SEQUENCE" ] }, ... }, { 'name': 'Illumina Sample', 'uuid': 'c6eebe92-7a58-423b-af00-def28cce43b2' ... }, ... ] * Query by UUID: .. code-block:: python >>> get('/api/sample_types/77777777-7777-4014-b700-053200000000') { 'name': 'Generic sample', 'uuid': '77777777-7777-4014-b700-053200000000', ... see above example for additional details ... } Sample ====== GET --- **URLs**: * ``/api/samples`` - Retrieve all objects in database. * ``/api/samples/`` - Retrieve single object by UUID * ``/api/samples?name=`` - Retrieve single object by name **Optional Parameters**: * ```` - UUID for the object. Use ``/api/samples`` or ``/api/samples?name=`` for an example of retrieving uuids for objects. * ```` - Name for the object. **Success Response Code**: ``200 OK`` **Examples**: * Query all samples: .. code-block:: python >>> get('/api/samples') [ { 'name': 'ESP000001', 'uuid': 'bb4c535b-5245-4df5-ab7d-a6cb16de7754', 'desc': 'Description for sample.', 'in_workflow_instance': false, 'owner': 'system admin (admin@localhost)', 'created_at': '2018-07-26T16:54:16.869731Z', 'updated_at': '2018-07-27T16:54:16.869731Z', 'tags': ['tag1', 'tag2'], 'sample_type_uuid': '77777777-7777-4014-b700-053300000000', ... }, { 'name': 'ESP000002', 'uuid': 'c6eebe92-7a58-423b-af00-def28cce43b2' ... }, ... ] * Query by UUID or name: .. code-block:: python >>> get('/api/samples/bb4c535b-5245-4df5-ab7d-a6cb16de7754') >>> # ... or ... >>> get('/api/samples?name=ESP000001') [ { 'name': 'ESP000001', 'uuid': 'bb4c535b-5245-4df5-ab7d-a6cb16de7754', ... see above example for additional details ... } ] POST ---- **URLs**: * ``/api/samples`` - Create samples in the ESP database. **Payload**: Required: * ``name`` - Name of object to create. * ``sample_type`` - Definition UUID for the sample type to use. * ``sample_type_uuid`` - Definition UUID for the sample type to use. Optional: * ``tags`` - Tags for the object. * ``desc`` - Description for the object. **Success Response Code**: ``200 OK`` **Example** Create a sample in the ESP database: .. code-block:: python >>> post('/api/samples', json={ >>> 'name': 'ESP00002', >>> 'desc': 'Description for sample.', >>> 'sample_type': '77777777-7777-4014-b700-053300000000', >>> 'sample_type_uuid': '77777777-7777-4014-b700-053300000000', >>> 'tags': ['sample', 'test'] >>> }) { 'name': 'ESP000002', 'uuid': 'bb4c535b-5245-4df5-ab7d-a6cb16de7754', 'desc': 'Description for sample.', 'in_workflow_instance': false, 'owner': 'system admin (admin@localhost)', 'created_at': '2018-07-26T16:54:16.869731Z', 'updated_at': '2018-07-27T16:54:16.869731Z', 'tags': ['sample', 'test'], 'sample_type_uuid': '77777777-7777-4014-b700-053300000000', ... } Workflow ======== GET --- **URLs**: * ``/api/workflows`` - Retrieve all objects in database. * ``/api/workflows/`` - Retrieve single object by UUID * ``/api/workflows?name=`` - Retrieve single object by name **Optional Parameters**: * ```` - UUID for the object. Use ``/api/workflows`` or ``/api/workflows?name=`` for an example of retrieving uuids for objects. * ```` - Name for the object. **Success Response Code**: ``200 OK`` **Examples**: * Query all workflows: .. code-block:: python >>> get('/api/workflows') [ { "name": "My Workflow", "uuid": "26498943-9b08-4d41-92cf-d0bad19f16da", "desc": "Description for Workflow", "created_at": "2018-08-26T17:18:18.337142Z", "updated_at": "2018-08-26T17:18:18.337142Z", "owner": "system admin (admin@localhost)" "tags": ["test", "workflow"], "protocols": [ { "uuid": "4e2bf223-7364-425a-8425-f9cf68ca7897" "def_uuid": "b5fdae48-5637-49f4-aad3-7b135deff068", "sort_id": 1, ... }, ... ], ... }, { "name": "Other Workflow", "uuid": "bb4c535b-5245-4df5-ab7d-a6cb16de7754", ... }, ... ] * Query by UUID or name: .. code-block:: python >>> get('/api/workflows/26498943-9b08-4d41-92cf-d0bad19f16da') >>> # ... or ... >>> get('/api/workflows?name=My%20Workflow') [ { "name": "My Workflow", "uuid": "26498943-9b08-4d41-92cf-d0bad19f16da", ... see above example for additional details ... } ] POST ---- **URLs**: * ``/api/workflows`` - Create workflows in the ESP database. **Payload**: Required: * ``name`` - Name of object to create. * ``protocols`` - UUIDs for protocols used in this workflow. Optional: * ``tags`` - Tags for the object. * ``desc`` - Description for the object. * ``sample_types`` - UUIDs for sample types that this workflow accepts. Leave empty to accept all sample types. * ``columns`` - Values or expressions that override protocol column defaults. If provided, must be same length as protocols list. * ``sample_group_indices`` - Indices (0-indexed) for sample groups used by each protocol. If provided, must be same length as protocols list. **Success Response Code**: ``200 OK`` **Example** Create a workflow in the ESP database: .. code-block:: python >>> post('/api/workflows', json={ >>> 'name': 'Test Workflow', >>> 'desc': 'Description for workflow.', >>> 'protocols': [ >>> # use /api/protocols to get protocol uuids >>> '79fa3a28-159a-47b7-90c7-96195bd7e68f', >>> '41485bac-c2c2-4304-ae53-96cef9139001', >>> 'f9d62dcf-2c83-4a93-8abb-141c836df28f' >>> ], >>> 'sample_types': [ >>> # use /api/sample_types to get sample type uuids >>> 'ebdce4ba-c137-4801-b6fe-5f793cf61bd0', >>> 'fedd033d-be32-49fd-b448-b8c2b00d563e' >>> ], >>> 'columns': [ >>> {}, >>> { >>> "barcode": "{{ column_value('barcode', 'Barcode') }}" >>> }, >>> { >>> "barcode": "{{ column_value('barcode', 'Barcode') }}" >>> } >>> ], >>> 'sample_group_indices': [ >>> 0, >>> 0, >>> 0 >>> ], >>> 'tags': ['workflow', 'test'] >>> }) { "name": "Test Workflow", "uuid": "978a26f3-7960-4f47-a03f-aa30587b5509", ... see examples above for more detail ... } Workflow Chain ============== GET --- **URLs**: * ``/api/workflow_chains`` - Retrieve all objects in database. * ``/api/workflow_chains/`` - Retrieve single object by UUID **Optional Parameters**: * ```` - UUID for the object. Use ``/api/workflow_chains`` for an example of retrieving uuids for objects. **Success Response Code**: ``200 OK`` **Examples**: * Query all workflow chains: .. code-block:: python >>> get('/api/workflow_chains') [ { "cls": "WorkflowChain", "created_at": "2019-04-15T20:57:19.363346Z", "deleted": false, "desc": "Straight chain with three workflows", "head": "1a464eeb-98ec-4665-ac26-f62821a55db8", "labels": { "member": "c1ec629d-ef39-402d-a472-610bc593d10b", "transition": "b350d17b-012b-4425-9596-0f1d666db3e6" }, "locked": false, "members": [ { "name": "WF1 first", "uuid": "1a464eeb-98ec-4665-ac26-f62821a55db8", "workflow": "2c995ed8-354f-4830-869b-f1543c4e6f58", ... }, { "name": "WF1 second", "uuid": "c1ec629d-ef39-402d-a472-610bc593d10b", "workflow": "ea034ec3-4179-4e76-baf2-045db93219e6", ... } ], "meta": {}, "n_members": 3, "name": "WF1 straight", "owner": "system admin (admin@localhost)", "tags": [], "transitions": [ { "uuid": "b350d17b-012b-4425-9596-0f1d666db3e6", "workflow_chain_member_from": "1a464eeb-98ec-4665-ac26-f62821a55db8", "workflow_chain_member_to": "c1ec629d-ef39-402d-a472-610bc593d10b", ... } ], "updated_at": "2019-04-15T20:57:19.363346Z", "url": "/api/workflow_chains/b5a9b942-20fb-42d6-9363-98cfee495952", "uuid": "b5a9b942-20fb-42d6-9363-98cfee495952" }, ... ] * Query by UUID: .. code-block:: python >>> get('/api/workflow_chains/b5a9b942-20fb-42d6-9363-98cfee495952') { "cls": "WorkflowChain", "created_at": "2019-04-15T20:57:19.363346Z", "deleted": false, "desc": "Straight chain with three workflows", "head": "1a464eeb-98ec-4665-ac26-f62821a55db8", "labels": { "member": "c1ec629d-ef39-402d-a472-610bc593d10b", "transition": "b350d17b-012b-4425-9596-0f1d666db3e6" }, "locked": false, "members": [ { "name": "WF1 first", "uuid": "1a464eeb-98ec-4665-ac26-f62821a55db8", "workflow": "2c995ed8-354f-4830-869b-f1543c4e6f58", ... }, { "name": "WF1 second", "uuid": "c1ec629d-ef39-402d-a472-610bc593d10b", "workflow": "ea034ec3-4179-4e76-baf2-045db93219e6", ... } ], "meta": {}, "n_members": 3, "name": "WF1 straight", "owner": "system admin (admin@localhost)", "tags": [], "transitions": [ { "uuid": "b350d17b-012b-4425-9596-0f1d666db3e6", "workflow_chain_member_from": "1a464eeb-98ec-4665-ac26-f62821a55db8", "workflow_chain_member_to": "c1ec629d-ef39-402d-a472-610bc593d10b", ... } ], "updated_at": "2019-04-15T20:57:19.363346Z", "url": "/api/workflow_chains/b5a9b942-20fb-42d6-9363-98cfee495952", "uuid": "b5a9b942-20fb-42d6-9363-98cfee495952" } POST ---- **URLs**: * ``/api/workflow_chains`` - Create workflow chains in the ESP database. **Payload**: Required: * No Required Payload Parameters Optional: * ``name`` - Name of the object to create. * ``desc`` - Description for the object. * ``tags`` - Tags for the object. * ``members`` - Workflows that will be used as nodes in the chain. * ``transitions`` - Edges connection the chain nodes. **Success Response Code**: ``200 OK`` **Example** Create a workflow chain in the ESP database: .. code-block:: python >>> post('/api/workflow_chains', json={ >>> 'members': [ >>> { >>> 'is_head': true, >>> 'workflow': 'cef3ec54-68d0-429a-a920-a244beac3f15', >>> 'name': 'Node 1' >>> }, >>> { >>> 'is_head': false, >>> 'workflow': 'cef3ec54-68d0-429a-a920-a244beac3f15', >>> 'name': 'Node 2' >>> } >>> ], >>> 'transitions': [ >>> { >>> 'workflow_chain_member_from': 'Node 1', >>> 'workflow_chain_member_to': 'Node 2' >>> } >>> ] >>> }) { "cls": "WorkflowChain", "created_at": "2019-04-15T21:29:06.207766Z", "deleted": false, "desc": null, "head": "2d152c34-2cf4-42f6-9c14-a9a8b5fb9d64", "labels": { "member": "723a5a5d-9c44-4a52-8251-30b459e945d3", "transition": "c2adb2f1-45a9-48f7-95b6-315c9ebd4097" }, "locked": false, "members": [ { "cls": "WorkflowChainMember", "created_at": "2019-04-15T21:29:06.207766Z", "deleted": false, "desc": null, "meta": {}, "name": "Node 1", "owner": "system admin (admin@localhost)", "tags": [], "updated_at": "2019-04-15T21:29:06.207766Z", "url": null, "uuid": "2d152c34-2cf4-42f6-9c14-a9a8b5fb9d64", "workflow": "cef3ec54-68d0-429a-a920-a244beac3f15" }, { "cls": "WorkflowChainMember", "created_at": "2019-04-15T21:29:06.207766Z", "deleted": false, "desc": null, "meta": {}, "name": "Node 2", "owner": "system admin (admin@localhost)", "tags": [], "updated_at": "2019-04-15T21:29:06.207766Z", "url": null, "uuid": "723a5a5d-9c44-4a52-8251-30b459e945d3", "workflow": "cef3ec54-68d0-429a-a920-a244beac3f15" } ], "meta": {}, "n_members": 3, "name": null, "owner": "system admin (admin@localhost)", "tags": [], "transitions": [ { "cls": "WorkflowChainTransition", "created_at": "2019-04-15T21:29:06.207766Z", "deleted": false, "desc": null, "meta": { "resubmit_samples": false }, "name": null, "owner": "system admin (admin@localhost)", "tags": [], "updated_at": "2019-04-15T21:29:06.207766Z", "url": null, "uuid": "c2adb2f1-45a9-48f7-95b6-315c9ebd4097", "workflow_chain_member_from": "2d152c34-2cf4-42f6-9c14-a9a8b5fb9d64", "workflow_chain_member_to": "723a5a5d-9c44-4a52-8251-30b459e945d3" } ], "updated_at": "2019-04-15T21:29:06.207766Z", "url": "/api/workflow_chains/3a60b29b-16d0-44c4-a459-20abfd082435", "uuid": "3a60b29b-16d0-44c4-a459-20abfd082435" } Project ======= GET --- **URLs**: * ``/api/projects`` - Retrieve all objects in database. * ``/api/projects/`` - Retrieve single object by UUID * ``/api/projects?name=`` - Retrieve single object by name **Optional Parameters**: * ```` - UUID for the object. Use ``/api/projects`` or ``/api/projects?name=`` for an example of retrieving uuids for objects. * ```` - Name for the object. **Success Response Code**: ``200 OK`` **Examples**: * Query all projects: .. code-block:: python >>> get('/api/projects') [ { "name": "My Project", "uuid": "d739924f-8a96-4c9a-ab22-045002b93bbd", "desc": "Description for Project", "created_at": "2018-07-26T17:16:50.022329Z", "updated_at": "2018-07-26T17:16:50.022329Z", "tags": ["project", "test"], "owner": "system admin (admin@localhost)", "workflow_instances": [ { "name": "Test Experiment", "uuid": "9788004b-8bb4-47aa-9b4c-6dd6e59be1ea", "workflow": "456f7390-0f70-4897-a85e-c2892b170f14", ... } ], ... }, { "name": "My Other Project", "uuid": "bb4c535b-5245-4df5-ab7d-a6cb16de7754", ... }, ... ] * Query by UUID or name: .. code-block:: python >>> get('/api/projects/d739924f-8a96-4c9a-ab22-045002b93bbd') >>> # ... or ... >>> get('/api/projects?name=My%20Project') [ { "name": "My Project", "uuid": "d739924f-8a96-4c9a-ab22-045002b93bbd", "desc": "Description for Project", "created_at": "2018-07-26T17:16:50.022329Z", "updated_at": "2018-07-26T17:16:50.022329Z", "tags": ["project", "test"], "owner": "system admin (admin@localhost)", "workflow_instances": [ { "name": "Test Experiment", "uuid": "9788004b-8bb4-47aa-9b4c-6dd6e59be1ea", "workflow": "456f7390-0f70-4897-a85e-c2892b170f14", ... } ], ... } ] POST ---- **URLs**: * ``/api/projects`` - Create projects in the ESP database. **Payload**: Required: * ``name`` - Name of object to create. Optional: * ``tags`` - Tags for the object. * ``desc`` - Description for the object. **Success Response Code**: ``200 OK`` **Example** Create a project in the ESP database: .. code-block:: python >>> post('/api/projects', json={ >>> 'name': 'My Project', >>> 'desc': 'Description for project.', >>> 'tags': ['project', 'test'] >>> }) { "name": "My Project", "uuid": "d739924f-8a96-4c9a-ab22-045002b93bbd", "desc": "Description for Project", "created_at": "2018-07-26T17:16:50.022329Z", "updated_at": "2018-07-26T17:16:50.022329Z", "tags": ["project", "test"], "owner": "system admin (admin@localhost)", "workflow_instances": [], ... } For examples of how to create a new experiment for a project, see the `Experiment`_ documentation below. Experiment ========== GET --- **URLs**: * ``/api/workflow_instances`` - Retrieve all objects in database. * ``/api/workflow_instances/`` - Retrieve single object by UUID * ``/api/workflow_instances?name=`` - Retrieve single object by name **Optional Parameters**: * ```` - UUID for the object. Use ``/api/workflow_instances`` or ``/api/workflow_instances?name=`` for an example of retrieving uuids for objects. * ```` - Name for the object. **Success Response Code**: ``200 OK`` **Examples**: * Query all experiments: .. code-block:: python >>> get('/api/workflow_instances') [ { "name": "Test Experiment", "desc": "", "uuid": "9788004b-8bb4-47aa-9b4c-6dd6e59be1ea", "project_name": "My Project", "project_uuid": "d739924f-8a96-4c9a-ab22-045002b93bbd", "workflow_uuid": "456f7390-0f70-4897-a85e-c2892b170f14", "created_at": "2018-07-26T17:18:43.649609Z", "submit_time": "2018-07-26T17:18:58.272089Z", "updated_at": "2018-07-26T17:19:38.601445Z", "start_time": "2018-07-26T17:19:13.016362Z", "owner": "system admin (admin@localhost)" "sample_sheets": [ "85266517-4870-4a93-a5da-ef015c532ec1", ... ], "tags": ['test', 'experiment'], "step_instances": [ { "name": "Test Protocol", "uuid": "1607000e-29ed-4b69-b13b-6ec249c0ff16", "protocol_uuid": "b5fdae48-5637-49f4-aad3-7b135deff068", "protocol_type": "standard", "created_at": "2018-07-26T17:18:58.272089Z", "start_time": "2018-07-26T17:18:58.272089Z", "submit_time": "2018-07-26T17:18:58.272089Z", "updated_at": "2018-07-26T17:19:38.601445Z", "owner": "system admin (admin@localhost)", ... } ], }, { "name": "My Other Experiment", "uuid": "bb4c535b-5245-4df5-ab7d-a6cb16de7754", ... }, ... ] * Query by UUID or name: .. code-block:: python >>> get('/api/workflow_instances/9788004b-8bb4-47aa-9b4c-6dd6e59be1ea') >>> # ... or ... >>> get('/api/workflow_instances?name=Test%20Experiment') [ { "name": "Test Experiment", "desc": "", "uuid": "9788004b-8bb4-47aa-9b4c-6dd6e59be1ea", "project_name": "My Project", ... see above example for additional details ... } ] POST ---- **URLs**: * ``/api/workflow_instances`` - Create experiments in the ESP database. **Payload**: Required: * ``name`` - Name of object to create. * ``project`` - UUID for project that will contain experiment. * ``workflow`` - UUID for workflow that will be used for experiment. * ``samples`` - UUIDs for samples within experiment. Optional: * ``tags`` - Tags for the object. * ``desc`` - Description for the object. **Success Response Code**: ``200 OK`` **Example** Create an experiment in the ESP database: .. code-block:: python >>> post('/api/workflow_instances', json={ >>> 'name': 'Test Experiment', >>> 'desc': 'Description for experiment.', >>> # use /api/projects to get project uuids >>> 'project': 'd739924f-8a96-4c9a-ab22-045002b93bbd', >>> # use /api/workflows to get workflow uuids >>> 'workflow': '456f7390-0f70-4897-a85e-c2892b170f14', >>> 'samples': [ >>> # use /api/samples to get sample uuids >>> 'bb4c535b-5245-4df5-ab7d-a6cb16de7754', >>> '54a56701-36e2-435e-a21f-5af28e7f00c3', >>> 'a8c8be7b-6c07-4755-8d72-e37a6408e3dc' >>> ], >>> 'tags': ['experiment', 'test'] >>> }) { "name": "Test Experiment", "uuid": "9788004b-8bb4-47aa-9b4c-6dd6e59be1ea", ... see examples above for more detail ... } For examples of how to create a new experiment for a project, see the `Experiment`_ documentation below. PUT --- **URLs**: * ``/api/workflow_instances/`` - Update experiments in the ESP database. **Parameters**: * ```` - UUID for the object. Use ``/api/workflow_instances`` or ``/api/workflow_instances?name=`` for an example of retrieving uuids for objects. **Payload**: Required: * ``name`` - Name of object. * ``submit`` - Whether or not the experiment was submitted to the LIMS section for processing (True/False). * ``samples`` - Sample UUID to submit to the LIMS section for processing. Optional: * ``tags`` - Tags for the object. * ``desc`` - Description for the object. **Success Response Code**: ``200 OK`` **Example** Add tags to an experiment and submit it to the LIMS section for processing: .. code-block:: python >>> put('/api/workflow_instances/9788004b-8bb4-47aa-9b4c-6dd6e59be1ea', json={ >>> 'name': 'Test Experiment', >>> 'submit': True, >>> 'samples': [ >>> # use /api/samples to get sample uuids >>> 'bb4c535b-5245-4df5-ab7d-a6cb16de7754', >>> '54a56701-36e2-435e-a21f-5af28e7f00c3', >>> 'a8c8be7b-6c07-4755-8d72-e37a6408e3dc' >>> ], >>> 'tags': ['experiment', 'test', 'submitted'] >>> }) [ { "name": "Test Experiment", "uuid": "9788004b-8bb4-47aa-9b4c-6dd6e59be1ea", ... see examples above for more detail ... } ] For examples of how to create a new SampleSheet from a submitted experiment, see the `SampleSheet`_ section below. SampleSheet =========== GET --- **URLs**: * ``/api/sample_sheets`` - Retrieve all objects in database. * ``/api/sample_sheets/`` - Retrieve single object by UUID * ``/api/sample_sheets?name=`` - Retrieve single object by name **Optional Parameters**: * ```` - UUID for the object. Use ``/api/sample_sheets`` or ``/api/sample_sheets?name=`` for an example of retrieving uuids for objects. * ```` - Name for the object. **Success Response Code**: ``200 OK`` **Examples**: * Query all sample sheets: .. code-block:: python >>> get('/api/sample_sheets') [ { "name": "Test Sheet", "uuid": "85266517-4870-4a93-a5da-ef015c532ec1", "workflow_uuid": "456f7390-0f70-4897-a85e-c2892b170f14" "desc": "Description for Sample Sheet", "sample_count": 3, "owner": "system admin (admin@localhost)", "start_time": "2018-08-26T17:19:12.989853Z", "updated_at": "2018-08-26T17:19:12.989853Z", "created_at": "2018-08-26T17:19:12.989853Z", "end_time": "", "tags": [], ... }, { "name": "My Other Sheet", "uuid": "bb4c535b-5245-4df5-ab7d-a6cb16de7754", ... }, ... ] * Query by UUID or name: .. code-block:: python >>> get('/api/sample_sheets/9788004b-8bb4-47aa-9b4c-6dd6e59be1ea') >>> # ... or ... >>> get('/api/sample_sheets?name=Test%20Sheet') [ { "name": "Test Sheet", "uuid": "85266517-4870-4a93-a5da-ef015c532ec1", ... see above example for additional details ... } ] POST ---- **URLs**: * ``/api/sample_sheets`` - Create sample sheets in the ESP database. **Payload**: Required: * ``name`` - Name of object to create. * ``workflow_uuid`` - Definition UUID for workflow used in processing. * ``workflow_instance_uuid`` - UUID for experiment used in processing. * ``samples`` - List with list of UUIDs for samples to process. Optional: * ``tags`` - Tags for the object. * ``desc`` - Description for the object. **Success Response Code**: ``200 OK`` **Example** Create a sample sheet in the ESP database: .. code-block:: python >>> post('/api/sample_sheets', json={ >>> 'name': 'Test Sheet', >>> # use /api/workflow_instances to get workflow uuids (workflow_uuid) >>> 'workflow_uuid': '456f7390-0f70-4897-a85e-c2892b170f14', >>> # use /api/workflow_instances to get experiment uuids (workflow_instance_uuid) >>> 'workflow_instance_uuid': '9788004b-8bb4-47aa-9b4c-6dd6e59be1ea', >>> # use /api/samples to get sample uuids. >>> 'samples': [[ # note the double list format >>> 'bb4c535b-5245-4df5-ab7d-a6cb16de7754', >>> '54a56701-36e2-435e-a21f-5af28e7f00c3', >>> 'a8c8be7b-6c07-4755-8d72-e37a6408e3dc' >>> ]], >>> }) { "name": "Test Sheet", "uuid": "9788004b-8bb4-47aa-9b4c-6dd6e59be1ea", ... see examples above for more detail ... } PUT --- **URLs**: * ``/api/sample_sheets//set_sample_values`` - Update column values for samples within a SampleSheet. **Payload**: Required: * ``step_instance_values`` - List with dictionary of Worksheet UUID with data to update. See examples in the `Worksheet`_ section below. * ``workflow_instance_uuids`` - UUID for experiment used in processing. **Success Response Code**: ``200 OK`` **Examples**: For an example of how to update columns for Worksheets in a SampleSheet, see the PUT section for `Worksheet`_ below. Documentation for editing a sample sheet was included in that section to add additional context about a Worksheet. Worksheet ========= GET --- **URLs**: * ``/api/protocol_instances`` - Retrieve all objects in database. * ``/api/protocol_instances/`` - Retrieve single object by UUID **Optional Parameters**: * ```` - UUID for the object. Use ``/api/protocol_instances`` for an example of retrieving uuids for objects. **Success Response Code**: ``200 OK`` **Examples**: * Query all worksheets: .. code-block:: python >>> get('/api/protocol_instances') [ { "name": "Test Protocol", "uuid": "1607000e-29ed-4b69-b13b-6ec249c0ff16", "tags": ['test', 'worksheet'], "protocol_type": "standard", "protocol_uuid": "b5fdae48-5637-49f4-aad3-7b135deff068", "submit_time": "2018-08-26T17:18:58.272089Z", "updated_at": "2018-08-26T17:19:38.601445Z", "created_at": "2018-08-26T17:18:58.272089Z", "start_time": "2018-08-26T17:18:58.272089Z", "owner": "system admin (admin@localhost)", "values": [ [ # entry for sample 1 { "name": "Column 1", "uuid": "18632e98-998e-47d6-8fba-ae67085e22bd", "var_type": "string", "value": "value1", "created_at": "2018-08-26T17:18:58.272089Z", "updated_at": "2018-08-27T17:18:58.272089Z", ... }, { "name": "Column 2", "uuid": "a6e34db7-525a-4d69-97f8-064562e2d088", "var_type": "numeric", "value": 1, ... }, ... ], [ # entry for sample 2 { "name": "Column 1", "uuid": "34a2d555-a946-4b2f-ace9-aa9d4047f293", "var_type": "string", "value": "value1", ... }, ... ], ... other sample column entries ... ], ... } ] * Query a worksheet by uuid: .. code-block:: python >>> get('/api/protocol_instances/1607000e-29ed-4b69-b13b-6ec249c0ff16') [ { "name": "Test Protocol", "uuid": "1607000e-29ed-4b69-b13b-6ec249c0ff16", ... see additional details from example above ... } ] PUT --- **URLs**: * ``/api/sample_sheets//set_sample_values`` - Update column values for samples within a SampleSheet. **Payload**: Required: * ``step_instance_values`` - List with dictionary of Worksheet UUID with data to update. See examples in the `Worksheet`_ section below. * ``workflow_instance_uuids`` - UUID for experiment used in processing. **Success Response Code**: ``200 OK`` **Examples**: Update `Column 1` and `Column 2` for two samples in a WorkSheet. .. code-block:: python >>> put('/api/sample_sheets/9788004b-8bb4-47aa-9b4c-6dd6e59be1ea/set_sample_values', json={ >>> 'step_instance_values': [{ >>> >>> # protocol instance uuid -> dictioanry with data to update >>> '1607000e-29ed-4b69-b13b-6ec249c0ff16': { >>> >>> # sample uuids -> dictionary with column values >>> 'bb4c535b-5245-4df5-ab7d-a6cb16de7754': { >>> 'Column 1': 'value 1', >>> 'Column 2': 1 >>> }, >>> '54a56701-36e2-435e-a21f-5af28e7f00c3': { >>> 'Column 1': 'value 2', >>> 'Column 2': 2 >>> } >>> } >>> }], >>> # experiment uuid >>> 'workflow_instance_uuids': ['9788004b-8bb4-47aa-9b4c-6dd6e59be1ea'] >>> }) Examples ======== To add context to the documentation above, the examples below provide a real-world example of interacting with the ESP database via REST API. In the examples below, the following operations are performed: 1. Set up a session and connect to the databse. 2. Create 2 samples to use in downstream examples. 3. Get a Workflow by name for downstream examples. 4. Create a Project container for downstream examples. 5. Create an Experiment with the Sample/Workflow objects from previous examples. 6. Submit the Experiment and create a SampleSheet for entering data. 7. Fill data into the first WorkSheet of the Experiment's SampleSheet. .. code-block:: python # imports # ----- import requests from functools import partial try: # python 2 import cookielib as cookiejar from urllib import quote_plus except ImportError: # python 3 import http.cookiejar as cookiejar from urllib.parse import quote_plus # 1. Set up a session and connect to the database # ----- # set up requests session and establish headers session = requests.Session() session.headers.update({ "Connection": "keep-alive", "Accept": "application/json", "Content-Type": "application/json" }) jar = cookiejar.MozillaCookieJar() url = 'http://localhost:8002' # create helper methods for issuing requests def request(endpoint, method='get', **kwargs): response = getattr(session, method)( url=url + endpoint, cookies=jar, verify=False, **kwargs ) return response.json() get = partial(request, method='get') post = partial(request, method='post') put = partial(request, method='put') # login post('/login', json={ 'email': 'admin@localhost', 'password': 'password' }) # 2. Create 2 samples to use in downstream examples. # ----- # get sample type uuid for creating samples sample_type = list(filter( lambda x: x['name'] == 'Generic sample', get('/api/sample_types') ))[0] # create samples and store uuids for later samples, sample_uuids = [], [] sample_names = ['Sample1', 'Sample2'] for name in sample_names: sample = post('/api/samples', json={ 'name': name, 'sample_type': sample_type['def_uuid'], 'sample_type_uuid': sample_type['def_uuid'], }) samples.append(sample) sample_uuids.append(sample['uuid']) # 3. Get a Workflow by name for downstream examples. # ----- # query /api/workflows to get uuid for Workflow name workflow_name = 'My Workflow' workflow = get('/api/workflows?name={}'.format(quote_plus(workflow_name)))[0] # 4. Create a Project container for downstream examples. # ----- # post to /api/projects to create new Project project = post('/api/projects', json={ 'name': 'My Project', 'desc': 'Project container for this example.' }) # 5. Create an Experiment with the Sample/Workflow objects from previous examples. # ----- # post to /api/workflow_instances to create new Experiment experiment = post('/api/workflow_instances', json={ 'name': 'New Experiment', 'desc': 'Experiment for this example.', 'project': project['uuid'], 'workflow': workflow['uuid'], 'samples': sample_uuids }) # 6. Submit the Experiment and create a SampleSheet for entering data. # ----- # put to /api/workflow_instances/ to submit Experiment to LIMS. put('/api/workflow_instances/{}'.format(experiment['uuid']), json={ 'name': 'New Experiment', 'submit': True, 'samples': sample_uuids }) # create SampleSheet from submitted Experiment. sample_sheet = post('/api/sample_sheets', json={ 'name': 'New Sheet', 'desc': 'Description for sample sheet.', 'workflow_uuid': experiment['workflow_uuid'], 'workflow_instance_uuid': experiment['uuid'], 'samples': [sample_uuids], }) # 7. Fill data into the first WorkSheet of the Experiment's SampleSheet. # ----- # get Worksheet uuid for updating data experiment_refresh = get('/api/workflow_instances/{}'.format(experiment['uuid'])) worksheets = experiment_refresh['step_instances'] worksheet_uuid = worksheets[0]['uuid'] # fill in data for the first few columns of the worksheet put('/api/sample_sheets/{}/set_sample_values'.format(sample_sheet['uuid']), json={ 'step_instance_values': [{ worksheet_uuid: { sample_uuids[0]: { 'Column 1': 'value 1', 'Column 2': 1 }, sample_uuids[1]: { 'Column 1': 'value 2', 'Column 2': 2 } } }], 'workflow_instance_uuids': [experiment['uuid']] }) Using the ESP python client, this process becomes much simpler: .. code-block:: python # 1. Set up a session and connect to the databse. # ------ import esp esp.options(email='admin@localhost', password='password') # 2. Create 2 samples to use in downstream examples. # ------ samples = Samples.create(['Sample 1', 'Sample 2']) # 3. Get a Workflow by name for downstream examples. # ------ workflow = Workflow('My Workflow') # 4. Create a Project container for downstream examples. # ------ project = Project.create({ 'name': 'My Project', 'desc': 'Project container for this example.' }) # 5. Create an Experiment with the Sample/Workflow objects from previous examples # ------ experiment = project.new_experiment({ 'name': 'New Experiment', 'desc': 'Experiment for this example.', 'workflow': workflow.uuid, 'samples': [x.name for x in samples] }) # 6. Submit the Experiment and create a SampleSheet for entering data. # ------ experiment.submit() # 7. Fill data into the first WorkSheet of the Experiment's SampleSheet. # ------ ws = experiment.protocols[0] ws['Column 1'] = ['value 1', 'value 2'] ws['Column 2'] = [1, 2] ws.save()