Esempio n. 1
0
def workflow(id=None, dn=None):
    """
    Implementation of the /workflow route
    Enforces ontological constraints on workflows types retrieved from ontology_terms.
    /workflow?do_uri=:uri - GET workflows having dataobject member giving by :uid
    """

    #Desperately need to add field error checking. Note, we have access to db.query_map
    api_version, root_url, root = get_api_version(request.url)

    if apidebug:
        print('APIDEBUG: You are: %s' % str(dn))
        print('APIDEBUG: workflow url request is %s' % request.url)

    if request.method == 'POST':
        #check for valid workflow type
        wtype = json.loads(request.data).get('type')
        ont_entry = rdb.getRecord('ontology_terms', {'path': '/Workflow/Type'},
                                  dn)[0]
        vocab = rdb.getRecord('ontology_terms',
                              {'parent_uid': ont_entry['uid']}, dn)
        valid = tuple(x['name'] for x in vocab)
        if (wtype in valid):
            ##Add logic to check for fields or exceptions from query
            type_uid = ont_entry.get('uid')
            p = json.loads(request.data)
            payload = {
                "name": p['name'],
                "description": p['description'],
                "type_uid": type_uid,
                "value": wtype
            }
            r = rdb.addWorkflow(payload, dn=dn)
            #should return ENTIRE record created. use rdb.getworkflow internally
        else:
            payload = {
                "url": request.url,
                "body": request.data,
                "hint": valid,
                "uid": -1
            }
            raise InvalidAPIUsage(message='Invalid workflow type specified',
                                  status_code=400,
                                  payload=payload)

    elif request.method == 'GET':
        if id:
            darg = dict(request.args.items(multi=True) + [('uid', id)])
            if apidebug:
                print('APIDEBUG: darg is %s' % darg)
            r = rdb.getWorkflow({'uid': id}, dn=dn)
        else:
            if 'do_uri' in request.args:
                #find data object by uri
                r = rdb.getRecord('dataobject',
                                  {'uri': request.args['do_uri']},
                                  dn=dn)
                if len(r) == 1:
                    do_uid = r[0].get('uid')
                    #find dataobject instances based on do_uid
                    doi_list = rdb.getRecord('dataobject_instance',
                                             {'do_uid': do_uid},
                                             dn=dn)
                    result = []
                    for doi in doi_list:
                        result.append(
                            rdb.getWorkflow({'uid': doi['work_uid']},
                                            dn=dn)[0])
                    r = {
                        'result': result,
                        'count': len(result),
                        'link-requested': request.url,
                        'status': 'ok'
                    }
                else:
                    r = {'uid': '0', 'msg': 'not found'}
            #general searches
            else:
                r = rdb.getWorkflow(request.args, dn=dn)
                #add workflow type here in return. Use complete path?

        if apidebug:
            print('APIDEBUG: workflow returning "%s" len %d' % (
                r,
                len(r),
            ))

    if apidebug:
        print('APIDEBUG: workflow %s' % (r, ))

    return Response(json.dumps(r, cls=MPOSetEncoder),
                    mimetype='application/json',
                    status=200)
Esempio n. 2
0
def workflow(id=None, dn=None):
    """
    Implementation of the /workflow route
    Enforces ontological constraints on workflows types retrieved from ontology_terms.
    /workflow?do_uri=:uri - GET workflows having dataobject member giving by :uid
    """

    #Desperately need to add field error checking. Note, we have access to db.query_map
    api_version,root_url,root=get_api_version(request.url)

    if apidebug:
        print ('APIDEBUG: You are: %s'% str(dn) )
        print ('APIDEBUG: workflow url request is %s' %request.url)

    if request.method == 'POST':
        #check for valid workflow type
        wtype = json.loads(request.data).get('type')
        ont_entry = rdb.getRecord('ontology_terms', {'path':'/Workflow/Type'}, dn )[0]
        vocab=rdb.getRecord('ontology_terms', {'parent_uid':ont_entry['uid']}, dn )
        valid= tuple(x['name'] for x in vocab)
        if (wtype in valid):
            ##Add logic to check for fields or exceptions from query
            type_uid = ont_entry.get('uid')
            p=json.loads(request.data)
            payload={"name":p['name'],"description":p['description'],"type_uid":type_uid,"value":wtype}
            r = rdb.addWorkflow(payload,dn=dn)
            #should return ENTIRE record created. use rdb.getworkflow internally
        else:
            payload={"url":request.url, "body":request.data, "hint":valid, "uid":-1}
            raise InvalidAPIUsage(message='Invalid workflow type specified',status_code=400,
                                    payload=payload)

    elif request.method == 'GET':
        if id:
            darg=dict(request.args.items(multi=True)+[('uid',id)])
            if apidebug:
                print('APIDEBUG: darg is %s' %darg)
            r = rdb.getWorkflow({'uid':id},dn=dn)
        else:
            if 'do_uri' in request.args:
                #find data object by uri
                r = rdb.getRecord('dataobject',{'uri':request.args['do_uri']}, dn=dn)
                if len(r)==1:
                    do_uid=r[0].get('uid')
                    #find dataobject instances based on do_uid
                    doi_list = rdb.getRecord('dataobject_instance',{'do_uid':do_uid}, dn=dn )
                    result=[]
                    for doi in doi_list:
                        result.append(rdb.getWorkflow({'uid':doi['work_uid']},dn=dn)[0])
                    r={'result':result,'count':len(result),'link-requested':request.url, 'status':'ok'}
                else:
                    r={'uid':'0','msg':'not found'}
            #general searches
            else:
                r = rdb.getWorkflow(request.args,dn=dn)
                #add workflow type here in return. Use complete path?

        if apidebug:
            print ('APIDEBUG: workflow returning "%s" len %d'% (r,len(r),))

    if apidebug:
        print ('APIDEBUG: workflow %s'% (r,) )

    return Response(json.dumps(r,cls=MPOSetEncoder),mimetype='application/json',status=200)
Esempio n. 3
0
def collectionElement(id=None, oid=None, dn=None):
    """
    /collection/:id/element       - GET a list of objects in a collection
                                   - POST to add to the collection
    /collection/:id/element/:oid - GET details of a single object in a collection.
                                    Should resolve oid to full record from relevant table.
    /collection/:id/element?detail=full[sparse] - GET collection information with full
               details [or default sparse as /collection/<id>]
    """
    api_version, root_url, root = get_api_version(request.url)
    if request.method == 'POST':

        payload = json.loads(request.data)

        #make sure the element hasn't been added to the collection already
        #elems must be a list of uids that are not already in this collection, if it exists.
        elems = payload.get('elements')
        if elems:
            if not isinstance(elems, list):
                elements = [elems]
            else:
                elements = elems
        else:
            elements = []

        #remove elements already in the collection
        for e in elements[:]:
            r = rdb.getRecord('collection_elements', {
                'uid': e,
                'parent_uid': id
            },
                              dn=dn)
            if len(r) != 0:
                elements.remove(
                    e)  #maybe add to response message this was done
        payload['elements'] = elements

        #add elements one and a time and create list of returned records
        r = []
        for e in elements:
            rr = rdb.addRecord('collection_elements',
                               json.dumps({
                                   'uid': e,
                                   'parent_uid': id
                               }),
                               dn=dn)
            r.append(rr)
            morer = rdb.getRecord('collection_elements', {'uid': rr['uid']},
                                  dn=dn)
            publishEvent('mpo_collection_elements', onlyone(morer))
    elif request.method == 'DELETE':
        if oid:
            r = rdb.deleteCollectionElement({
                'parent_uid': id,
                'uid': oid
            },
                                            dn=None)
        else:
            r = []
    elif request.method == 'GET':
        if oid:
            r = rdb.getRecord('collection_elements', {
                'parent_uid': id,
                'uid': oid
            },
                              dn=dn)
        else:
            r = rdb.getRecord('collection_elements', {'parent_uid': id}, dn=dn)

        #Find original item and add it to record.
        for record in r:
            print('collection element r', record)
            r_uid = record['uid']
            #getRecordTable returns a python dict
            record['type'] = rdb.getRecordTable(r_uid, dn=dn)

            #set default field values
            detail = {
                'related': 'not sure',
                'link-related': root_url,
                'related': 'cousins',
                'name': 'what is this?',
                'description': 'empty',
                'time': 'nowhen'
            }
            #Translation for specific types
            if record['type'] == 'workflow':
                detail = rdb.getWorkflow({'uid': r_uid}, dn=dn)[0]
                print('element workflow', detail)
                detail['related'] = rdb.getWorkflowCompositeID(
                    r_uid, dn=dn).get('alias')
                links = {}
                links['link1'] = root_url + '/workflow/' + r_uid
                links['link2'] = root_url + '/workflow?alias=' + detail[
                    'related']
                detail['link-related'] = links
            elif record['type'] == 'dataobject':
                detail = rdb.getRecord('dataobject', {'uid': r_uid}, dn=dn)[0]
                detail['related'] = detail.get('uri')
                detail['link-related'] = root_url + '/dataobject/' + r_uid
            elif record['type'] == 'dataobject_instance':
                do_uid = (rdb.getRecord('dataobject_instance',
                                        {'uid': record['uid']},
                                        dn=dn)[0]).get('do_uid')
                detail = rdb.getRecord('dataobject', {'uid': do_uid}, dn=dn)[0]
                detail['related'] = detail.get('uri')
                detail['link-related'] = root_url + '/dataobject/' + do_uid
            elif record['type'] == 'collection':
                thisdetail = rdb.getRecord('collection', {'uid': r_uid},
                                           dn=dn)[0]
                detail['related'] = None
                detail[
                    'link-related'] = root_url + '/collection/' + r_uid + '/element'
                detail['description'] = thisdetail.get('description')
                detail['name'] = thisdetail.get('name')
                detail['time'] = thisdetail.get('time')

            record['name'] = detail['name']
            record['description'] = detail['description']
            record['time'] = detail['time']
            record['related'] = detail['related']
            record['link-related'] = detail['link-related']

    istatus = 200
    #    if len(r) == 0:
    #    #istatus = 404
    #    r=[{'mesg':'No records found', 'number_of_records':0, 'status':404}]

    return Response(json.dumps(r, cls=MPOSetEncoder),
                    mimetype='application/json',
                    status=istatus)
Esempio n. 4
0
def collectionElement(id=None, oid=None, dn=None):
    """
    /collection/:id/element       - GET a list of objects in a collection
                                   - POST to add to the collection
    /collection/:id/element/:oid - GET details of a single object in a collection.
                                    Should resolve oid to full record from relevant table.
    /collection/:id/element?detail=full[sparse] - GET collection information with full
               details [or default sparse as /collection/<id>]
    """
    api_version,root_url,root=get_api_version(request.url)
    if request.method == 'POST':

        payload = json.loads(request.data)

        #make sure the element hasn't been added to the collection already
        #elems must be a list of uids that are not already in this collection, if it exists.
        elems = payload.get('elements')
        if elems:
            if not isinstance(elems,list):
                elements=[elems]
            else:
                elements=elems
        else:
            elements=[]

        #remove elements already in the collection
        for e in elements[:]:
            r = rdb.getRecord('collection_elements',{'uid':e,'parent_uid':id}, dn=dn)
            if len(r)!=0: elements.remove(e) #maybe add to response message this was done
        payload['elements'] = elements

        #add elements one and a time and create list of returned records
        r=[]
        for e in elements:
            rr=rdb.addRecord('collection_elements',json.dumps({'uid':e,'parent_uid':id}),dn=dn)
            r.append(rr)
            morer = rdb.getRecord('collection_elements',{'uid':rr['uid']},dn=dn)
            publishEvent('mpo_collection_elements',onlyone(morer))
    elif request.method == 'DELETE':
        if oid:
            r = rdb.deleteCollectionElement({'parent_uid':id,'uid':oid}, dn=None)
        else:
            r = []
    elif request.method == 'GET':
        if oid:
            r = rdb.getRecord('collection_elements',{'parent_uid':id,'uid':oid}, dn=dn)
        else:
            r = rdb.getRecord('collection_elements',{'parent_uid':id}, dn=dn)

        #Find original item and add it to record.
        for record in r:
            print ('collection element r',record)
            r_uid=record['uid']
            #getRecordTable returns a python dict
            record['type']=rdb.getRecordTable( r_uid, dn=dn )

            #set default field values
            detail={'related':'not sure','link-related':root_url,'related':'cousins',
                    'name':'what is this?','description':'empty','time':'nowhen'}
            #Translation for specific types
            if record['type']=='workflow':
                detail=rdb.getWorkflow({'uid':r_uid},dn=dn)[0]
                print('element workflow',detail)
                detail['related']=rdb.getWorkflowCompositeID(r_uid,dn=dn).get('alias')
                links={}
                links['link1']=root_url+'/workflow/'+r_uid
                links['link2']=root_url+'/workflow?alias='+detail['related']
                detail['link-related']=links
            elif record['type']=='dataobject':
                detail=rdb.getRecord('dataobject',{'uid':r_uid},dn=dn)[0]
                detail['related']=detail.get('uri')
                detail['link-related']=root_url+'/dataobject/'+r_uid
            elif record['type']=='dataobject_instance':
                do_uid=(rdb.getRecord('dataobject_instance',{'uid':record['uid']},dn=dn)[0]).get('do_uid')
                detail=rdb.getRecord('dataobject',{'uid':do_uid},dn=dn)[0]
                detail['related']=detail.get('uri')
                detail['link-related']=root_url+'/dataobject/'+do_uid
            elif record['type']=='collection':
                thisdetail=rdb.getRecord('collection',{'uid':r_uid},dn=dn)[0]
                detail['related']=None
                detail['link-related']=root_url+'/collection/'+r_uid+'/element'
                detail['description']=thisdetail.get('description')
                detail['name']=thisdetail.get('name')
                detail['time']=thisdetail.get('time')

            record['name']=detail['name']
            record['description']=detail['description']
            record['time']=detail['time']
            record['related']=detail['related']
            record['link-related']=detail['link-related']

    istatus=200
    #    if len(r) == 0:
    #    #istatus = 404
    #    r=[{'mesg':'No records found', 'number_of_records':0, 'status':404}]

    return Response(json.dumps(r,cls=MPOSetEncoder),mimetype='application/json',status=istatus)