예제 #1
0
def query_doc(coll, jpath):
    """ Performs a query in collection using the JSONPath.
    
    For example, return all documents satisfying the given JSONPath expression.
    i.e. all documents that contain a non-empty value at the given JSONPath
    >>> query_doc(coll, '$.app.address')


    # return all documents with a non-empty address:
    >>> query_doc(coll, '$..address')

    :param coll: collection being queried

    :type jpath: string
    :param jpath: JSONPath at which to update the fragment

    :rtype: list 
    :return: a list of map (a list of JSON documents)
    
    """
    # initially, using brute force approach:
    # 1. first get all docs,
    docs = coll.find()
    # 2. then filter those that have a match of jpath
    results = filter(lambda x: jsonpath.jsonpath(x, jpath), docs)
    return results
예제 #2
0
def append_doc(coll, doc, doc_fragment, jpath):
    """ Appends to the document fragment at the given JSONPath key.
    
    Creates the parent key(s) and document if necessary.

    :param coll: collection for which document is being updated
    
    :type doc: dict
    :param doc: JSON document to append to
    
    :type doc_fragment: map
    :param doc_fragment: document fragment to append
    
    :type jpath: string
    :param jpath: JSONPath at which to append the fragment

    :return: index at which append was done. 0 if a new list node was created
     as a result of append.
           
    """
    # modify the doc
    modify_doc(doc, doc_fragment, jpath, append=True)
    _do_save(coll, doc)
    # logger.debug('update_doc: %s, filter: %s' % (doc, filt))
    subdocs = jsonpath.jsonpath(doc, jpath)
    # print('append_doc: %s' % subdocs)
    if subdocs:
        # append happened at index {len - 1)
        ret = len(subdocs[0]) - 1
    else:
        ret = 0
    return ret
예제 #3
0
def modify_doc(doc, doc_fragment, jpath, append=False):
    """ Modifies doc by replacing doc fragment at given JSONPath
      by the given doc fragment.
      
    Creates the parent key(s) and document if necessary.

    :type doc: dict
    :param doc: JSON document to update
    
    :type doc_fragment: dict or string
    :param doc_fragment: document fragment with which to update
    
    :type jpath: string
    :param jpath: JSONPath at which to update the fragment
    :return: number of nodes modified
    """
    logger.debug('modify_doc: doc_fragment, jpath: %s, %s' % (doc_fragment, jpath))
    # eval doesn't work with ObjectId.
    # we therefore replace ObjectId with string
    # {'_id': ObjectId('506da6b025dc9a250b000000'),
    id = doc.get('_id')
    if id and not isinstance(id, str):
        doc['_id'] = str(id)
    # identify map subnode to modify/update
    subdocs = jsonpath.jsonpath(doc, jpath)
    if append and subdocs and len(subdocs) > 1:
        raise BadParameterError('append can be performed only on JSONPath that matches a single node')

    if append and (not subdocs or (subdocs and not isinstance(subdocs[0], list))):
        # create a new list
        _put(doc, jpath, [])
        subdocs = jsonpath.jsonpath(doc, jpath)
        assert(subdocs)
    if not subdocs:
        logger.debug('modify_doc: %s applied to %s yielded no results' % (jpath, doc))
        # create the given doc_fragment at jpath
        _put(doc, jpath, doc_fragment)
        ret = 1
    else:

        ret = jsonpath_replace(doc, doc_fragment, jpath, append)
        # restore original id
        # if id:
        #    doc['_id'] = id
    return ret
예제 #4
0
def extract_fragment_from_doc(doc, jpath):
    """ Extract a fragment from document at the given JSONPath.
    
    Usage:
    Extract address fragment from document
    >>> subdoc = extract_fragment_from_doc(doc, '$.app.address')

    # return all addresses in the document:
    >>> extract_fragment_from_doc(doc, '$..address')

    :param doc: doc from which fragment is being extracted

    :type jpath: string
    :param jpath: JSONPath at which to update the fragment

    :rtype: map
    :return: a JSON document
    
    """
    return jsonpath.jsonpath(doc, jpath)
예제 #5
0
def unset_doc(coll, doc, jpath):
    """ Removes node at given JSONPath 
    
    :return: True if node was unset, False if no action was taken since
     there was no code found under given jpath
    
    """
    id = doc.get('_id')
    if id and not isinstance(id, str):
        doc['_id'] = str(id)
    # identify map subnode to modify/update
    subdocs = jsonpath.jsonpath(doc, jpath)
    if subdocs:
        count = jsonpath_replace(doc, None, jpath)
        _do_save(coll, doc)
    else:
        # logger.debug('unset_doc: %s applied to %s yielded no results, therefore nothing removed from doc' % \
        #               (jpath, doc))
        count = 0
    return count
def path_jsonpath(data, expr):
    """Path expression engine using jsonpath"""
    if jsonpath is None: raise NotImplementedError("jsonpath is not installed")
    return jsonpath.jsonpath(data, expr, use_eval=False) or []
예제 #7
0
 def get_data(self, path):
     data = jsonpath.jsonpath(self.get_message(), expr=path)
     return data
예제 #8
0
    print(jsonpath(dict, '$..students[0,1,3]'))   # 输出 [{'student_id': '1', 'name': 'bob', 'sex': 'male', 'age': 6}, {'student_id': '2', 'name': 'amy', 'sex': 'female', 'age': 6}]
    print(jsonpath(dict, '$..students[:2]'))    # 输出 [{'student_id': '1', 'name': 'bob', 'sex': 'male', 'age': 6}, {'student_id': '2', 'name': 'amy', 'sex': 'female', 'age': 6}]

    # 获取students的最后一条数据
    print(jsonpath(dict, '$..students[-1:]'))  # 输出 [{'student_id': '3', 'name': 'pery', 'sex': 'male', 'age': 5}]










road_name=jsonpath.jsonpath(content2,'$..name')
    #print(road_name)
road_location=jsonpath.jsonpath(content2,'$..dir')
road_index=jsonpath.jsonpath(content2,'$..index')
road_speed=jsonpath.jsonpath(content2,'$..speed')
road_traveltime=jsonpath.jsonpath(content2,'$..travelTime')
road_date=jsonpath.jsonpath(content2,'$..delayTime')
#print(road_name+"w2,"+road_location)
#      print(road_name+","+road_location+","+road_index+","+road_speed+","+road_traveltime+","+road_date))






예제 #9
0
def jsonpath_replace(doc, fragment, jpath, append=False):
    """ 
    Performs a JSONPath update transaction.
    Implement the update part of JSONPath, using its facility to
    retrieve paths to JSONPath extraction results, rather than
    results themselves, and them building a Python statement from
    the paths that are executed to perform assignments of fragment
    to individual nodes in the dict tree.
    
    If there are more than than one nodes found in the dict tree, all of them
    will be assigned the fragment.
    If fragment is None, the node(s) will be removed.
    
    >>> tdoc = {'web': [{'instance': 'i-ba2911c0', 'address': '54.242.12.1'}, {'instance': 'this is not the one', 'address': '54.242.12.3'}, {'instance': 'this is the one', 'address': '54.242.12.3'}, {'instance': 'i-ba2911c0', 'address': '54.242.12.4'}], 'app': {'instance': 'i-30340c4a', 'address': '107.22.57.90'}, 'proxy': {'instance': 'i-ba2119c0', 'address': '50.16.150.144'}, 'database': {}}
    >>> jpath = 'web[2].address'
    >>> fragment = '111.111.111.111'
    >>> jsonpath_replace(tdoc, jpath, fragment)
    doc['web'][2]['address'] = fragment
    >>> tdoc
    {'web': [{'instance': 'i-ba2911c0', 'address': '54.242.12.1'}, 
      {'instance': 'this is not the one', 'address': '54.242.12.3'}, 
      {'instance': 'this is the one', 'address': '111.111.111.111'}, 
      {'instance': 'i-ba2911c0', 'address': '54.242.12.4'}], 
      'app': {'instance': 'i-30340c4a', 'address': '107.22.57.90'}, 
      'proxy': {'instance': 'i-ba2119c0', 'address': '50.16.150.144'}, 
      'database': {}}

    :type doc: dict
    :param doc: json doc
    :type fragment: str or dict
    :param fragment: fragment to replace JSONPath node with
    :type jpath: str
    :param jpath: JSONPath string
    
    :return: number of assignments performed
    
    """
    ipath = jsonpath.jsonpath(doc, jpath, result_type='IPATH')
    # print ipath
    # for example:
    # 1) web[2].address -> [[web', '2', 'address']]
    # or, given a certain doc:
    # 2) $..book[?(@.price<10)]', '$;..;book;?(@.price<10)
    #  -> [['store', 'book', '0'], ['store', 'book', '2']]
    docname = 'doc'
    rhs = 'fragment'
    statements = []
    # build all assignment statements
    if ipath:
        for ip in ipath:
            expr = docname
            for w in ip:
                if w.isdigit():
                    expr += "[%s]" % w
                else:
                    expr += "['%s']" % w
            if append:
                # e.g.
                # >>> if isinstance(doc['web'], list): doc['web'].append('a')
                # ... else: doc['web'] = ['a']
                statement = 'if isinstance(%s, list): %s.append(fragment)\nelse: %s = [fragment]' % \
                  (expr, expr, expr)
                expr = statement
            elif fragment is None:
                expr = "del %s" % expr
            else:
                expr += " = %s" % rhs
            statements.append(expr)

    # example result statements:
    # for case 1):
    #   ["doc['web'][2]['address'] = fragment"]
    # for case 2):
    #
    # print statements
    for s in statements:
        exec(s)
    return len(statements)
예제 #10
0
파일: 1.py 프로젝트: tmy123/api_pytest_0302
# from jsonpath import jsonpath
# # jsonpath里真有jsonpath模块jsonpath
# data = {'key1': {'key2': {'key3': {'key4': {'key5': {'key6':'python'}}}}}}
# #键值索引
# print(data['key1']['key2']['key3']['key4']['key5']['key6'])
#
# print(jsonpath(data,'$..key6')[0])
# print(jsonpath(data,'$.key1.key2.key3.key4.key5.key6')[0])
#
from jsonpath import jsonpath

data = {"username1": {"us": {"a": "1"}}}
print(data["username1"]["us"])
print(jsonpath(data, '$..username1'))
print(jsonpath.jsonpath(data, '$.username1'))

# import requests
# import jsonpath
# import json
#
# headers = {
#     'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/85.0.4183.83 Safari/537.36'
# }
# response = requests.get('https://www.lagou.com/lbs/getAllCitySearchLabels.json', headers=headers)
# dict_data = json.loads(response.content.decode())
# print(dict_data)
# print(jsonpath.jsonpath(dict_data, '$..name'))