def put_elts(self, elts, graph_ids=None, cache=False): """Put graph elements in DB. :param elts: graph elements to put in DB. :type elts: dict, GraphElement or list of dict/GraphElement. :param str graph_ids: element graph id. None if elt is a graph. :param bool cache: use query cache if True (False by default). :return: corresponding graph elts. :rtype: list of GraphElements """ result= [] # ensure elts is a list if isinstance(elts, (dict, GraphElement)): elts= [elts] for elt in elts: gelt= elt # in case of dict, get the corresponding graph elt and save it if isinstance(gelt, dict): gelt= GraphElement.new(**gelt) gelt.process(event={}) gelt.save(manager=self, cache=cache) else: # in case of graphelt, save its serialized form in db serialized_elt= gelt.to_dict() # put elt value in storage self[GraphManager.STORAGE].put_element( _id=elt.id, element=serialized_elt, cache=cache ) # add the graphical element to the result result.append(gelt) # associate all elt ids with all graph ids if graph_ids is not None: # eliminate doublons of elts elt_ids= set([gelt.id for gelt in result]) # ensure graph_ids is a basestring graph_ids= ensure_iterable(graph_ids) graphs= self[GraphManager.STORAGE].get_elements(ids=graph_ids) # add elt ids in elts of graphs for graph in graphs: graph[Graph.ELTS]= list(graph[Graph.ELTS] | elt_ids) # save all graphs self[GraphManager.STORAGE].put_elements(elements=graphs) return result
def get_elts( self, ids=None, types=None, graph_ids=None, info=None, base_type=None, query=None, serialize=True, cls=None ): """Get graph element(s) related to input ids, types and query. :param ids: list of ids or id of element to retrieve. If None, get all elements. If str, get one element. :type ids: list or str :param types: graph element types to retrieve. :type types: list or str :param graph_ids: graph ids from where find elts. :type graph_ids: list or str :param info: info query. :param dict query: element search query. :param str base_type: elt base type. :param bool serialize: serialize result to GraphElements if True (by default). :param type cls: GraphElement type to retrieve if not None. :return: element(s) corresponding to input ids and query. :rtype: list or dict """ # check if only one element is asked unique = isinstance(ids, basestring) # init query if query is None: query = {} # put base type in query if base_type is not None: query[GraphElement.BASE_TYPE] = base_type # put types in query if not None if types is not None: if not isinstance(types, basestring): types = {'$in': types} query[GraphElement.TYPE] = types # put info if not None if info is not None: if isinstance(info, dict): for name in info: data_name = 'info.{0}'.format(name) query[data_name] = info[name] else: query[Vertice.INFO] = info # find ids among graphs if graph_ids is not None: result = [] graphs = self.get_elts(ids=graph_ids, serialize=False) if graphs is not None: # all graph elt ids elt_ids = set() # ensure graphs is a list of graphs if isinstance(graphs, dict): graphs = [graphs] for graph in graphs: if Graph.ELTS in graph: elts = set(graph[Graph.ELTS]) elt_ids |= elts # if ids is not given, use elt_ids if ids is None: ids = list(elt_ids) else: # else use jonction of elt_ids and ids if isinstance(ids, basestring): ids = [ids] ids = list(elt_ids & set(ids)) # get elements with ids and query result = self[GraphManager.STORAGE].get_elements(ids=ids, query=query) if result is not None and serialize: if isinstance(result, dict): result = GraphElement.new(**result) # ensure cls is respected if cls is not None and not isinstance(result, cls): result = None else: # save reference to new in order to ease its use new = GraphElement.new result = list( new(**elt) for elt in result ) # ensure cls is respected if cls is not None: result = [elt for elt in result if isinstance(elt, cls)] if unique and isinstance(result, list): result = result[0] if result else None return result