Esempio n. 1
0
    def sync(self, host, graph_name, username=None, password=None):
        """
        Sync the current internal spec using the given graph on the given host.

        :param host: The host in <hostname>:<port> or <hostname> format
        :type host: str
        :param graph_name: The name of the graph as defined in rexster.xml
        :type graph_name: str
        :param username: The username for the rexster server
        :type username: str
        :param password: The password for the rexster server
        :type password: str

        """
        from thunderdome.connection import setup, execute_query
        setup(hosts=[host],
              graph_name=graph_name,
              username=username,
              password=password,
              index_all_fields=False)

        first_undefined = self._get_first_undefined(self._results)

        if first_undefined is None:
            return

        first_undefined = first_undefined[0]

        q = ""

        # Assign any already defined types to variables and search for the
        # first undefined type to be used as the starting point for executing
        # the remaining statements.
        results = []
        for i,x in enumerate(self._results):
            if isinstance(x, Property):
                if x.name == first_undefined:
                    results = self._results[i:]
                    break
                else:
                    q += "{} = g.getType('{}')\n".format(x.name, x.name)
            elif isinstance(x, Edge):
                if x.label == first_undefined:
                    results = self._results[i:]
                    break
                else:
                    q += "{} = g.getType('{}')\n".format(x.label, x.label)
            elif isinstance(x, KeyIndex):
                if x.name == first_undefined:
                    results = self._results[i:]
                    break

        for stmt in results:
            q += "{}\n".format(stmt.gremlin)
        q += "g.stopTransaction(SUCCESS)"

        print q

        execute_query(q)
Esempio n. 2
0
    def test_db_field_io(self):
        v1 = DBFieldVertex.create(text='vertex1')
        v2 = DBFieldVertex.create(text='vertex2')
        e1 = DBFieldEdge.create(v1, v2, text='edge1')

        v1_raw = connection.execute_query('g.v(eid)', params={'eid': v1.eid})
        assert v1.text == v1_raw[0]['vertex_text']

        v2_raw = connection.execute_query('g.v(eid)', params={'eid': v2.eid})
        assert v2.text == v2_raw[0]['vertex_text']

        e1_raw = connection.execute_query('g.e(eid)', params={'eid': e1.eid})
        assert e1.text == e1_raw[0]['edge_text']
Esempio n. 3
0
    def test_db_field_io(self):
        v1 = DBFieldVertex.create(text='vertex1')
        v2 = DBFieldVertex.create(text='vertex2')
        e1 = DBFieldEdge.create(v1, v2, text='edge1')

        v1_raw = connection.execute_query('g.v(eid)', params={'eid':v1.eid})
        assert v1.text == v1_raw[0]['vertex_text']

        v2_raw = connection.execute_query('g.v(eid)', params={'eid':v2.eid})
        assert v2.text == v2_raw[0]['vertex_text']

        e1_raw = connection.execute_query('g.e(eid)', params={'eid':e1.eid})
        assert e1.text == e1_raw[0]['edge_text']
Esempio n. 4
0
    def sync(self,
             host,
             graph_name,
             username=None,
             password=None,
             dry_run=False):
        """
        Sync the current internal spec using the given graph on the given host.

        :param host: The host in <hostname>:<port> or <hostname> format
        :type host: str
        :param graph_name: The name of the graph as defined in rexster.xml
        :type graph_name: str
        :param username: The username for the rexster server
        :type username: str
        :param password: The password for the rexster server
        :type password: str
        :param dry_run: If true then the generated Gremlin will just be printed
        :type dry_run: boolean

        """
        def _get_name(x):
            """
            Return the name for the given object.

            :param x: The object
            :type x: Property, Edge, KeyIndex
            :rtype: str
            
            """
            if isinstance(x, Property) or isinstance(x, KeyIndex):
                return x.name
            elif isinstance(x, Edge):
                return x.label
            raise RuntimeError("Invalid object type {}".format(type(x)))

        if not dry_run:
            from thunderdome.connection import setup, execute_query
            setup(hosts=[host],
                  graph_name=graph_name,
                  username=username,
                  password=password,
                  index_all_fields=False)

        q = "def t = null"
        for x in self._results:
            name = _get_name(x)
            q += "t = g.getType('{}')\n".format(name)
            q += "if (t == null) {\n"
            q += "  {}\n".format(x.gremlin)
            q += "} else {\n"
            q += "  {} = g.getType('{}')\n".format(name, name)
            q += "}\n"
        q += "null"

        print q

        from thunderdome.connection import execute_query
        if not dry_run:
            return execute_query(q)
Esempio n. 5
0
    def __call__(self, instance, *args, **kwargs):
        args = list(args)
        if not self.classmethod:
            args = [instance.eid] + args
            
        params = self.defaults.copy()
        if len(args + kwargs.values()) > len(self.arg_list):
            raise TypeError('{}() takes {} args, {} given'.format(self.attr_name, len(self.arg_list), len(args)))

        #check for and calculate callable defaults
        for k,v in params.items():
            if callable(v):
                params[k] = v()

        arglist = self.arg_list[:]
        for arg in args:
            params[arglist.pop(0)] = arg
            
        for k,v in kwargs.items():
            if k not in arglist:
                an = self.attr_name
                if k in params:
                    raise TypeError(
                        "{}() got multiple values for keyword argument '{}'".format(an, k))
                else:
                    raise TypeError(
                        "{}() got an unexpected keyword argument '{}'".format(an, k))
            arglist.pop(arglist.index(k))
            params[k] = v
            

        params = self.transform_params_to_database(params)

        tmp = execute_query(self.function_body, params, transaction=self.transaction)
        return tmp
Esempio n. 6
0
 def _reload_values(self):
     """
     Re-read the values for this edge from the graph database.
     """
     results = execute_query('g.e(eid)', {'eid': self.eid})[0]
     del results['_id']
     del results['_type']
     return results
Esempio n. 7
0
 def _reload_values(self):
     """
     Re-read the values for this edge from the graph database.
     """
     results = execute_query('g.e(eid)', {'eid':self.eid})[0]
     del results['_id']
     del results['_type']
     return results
Esempio n. 8
0
    def _execute(self, func, deserialize=True):
        tmp = "{}.{}()".format(self._get_partial(), func)
        self._vars.update({"eid": self._vertex.eid, "limit": self._limit})
        results = execute_query(tmp, self._vars)

        if deserialize:
            return [Element.deserialize(r) for r in results]
        else:
            return results
Esempio n. 9
0
    def _execute(self, func, deserialize=True):
        tmp = "{}.{}()".format(self._get_partial(), func)
        self._vars.update({"eid":self._vertex.eid, "limit":self._limit})
        results = execute_query(tmp, self._vars)

        if deserialize:
            return  [Element.deserialize(r) for r in results]
        else:
            return results
Esempio n. 10
0
 def _reload_values(self):
     """
     Method for reloading the current vertex by reading its current values
     from the database.
     """
     results = execute_query('g.v(eid)', {'eid':self.eid})[0]
     del results['_id']
     del results['_type']
     return results
Esempio n. 11
0
 def _reload_values(self):
     """
     Method for reloading the current vertex by reading its current values
     from the database.
     """
     results = execute_query('g.v(eid)', {'eid': self.eid})[0]
     del results['_id']
     del results['_type']
     return results
Esempio n. 12
0
    def sync(self, host, graph_name, username=None, password=None, dry_run=False):
        """
        Sync the current internal spec using the given graph on the given host.

        :param host: The host in <hostname>:<port> or <hostname> format
        :type host: str
        :param graph_name: The name of the graph as defined in rexster.xml
        :type graph_name: str
        :param username: The username for the rexster server
        :type username: str
        :param password: The password for the rexster server
        :type password: str
        :param dry_run: If true then the generated Gremlin will just be printed
        :type dry_run: boolean

        """

        def _get_name(x):
            """
            Return the name for the given object.

            :param x: The object
            :type x: Property, Edge, KeyIndex
            :rtype: str
            
            """
            if isinstance(x, Property) or isinstance(x, KeyIndex):
                return x.name
            elif isinstance(x, Edge):
                return x.label
            raise RuntimeError("Invalid object type {}".format(type(x)))

        if not dry_run:
            from thunderdome.connection import setup, execute_query

            setup(hosts=[host], graph_name=graph_name, username=username, password=password, index_all_fields=False)

        q = "def t = null"
        for x in self._results:
            name = _get_name(x)
            q += "t = g.getType('{}')\n".format(name)
            q += "if (t == null) {\n"
            q += "  {}\n".format(x.gremlin)
            q += "} else {\n"
            q += "  {} = g.getType('{}')\n".format(name, name)
            q += "}\n"
        q += "null"

        print q

        from thunderdome.connection import execute_query

        if not dry_run:
            return execute_query(q)
Esempio n. 13
0
    def _simple_traversal(self, operation):
        """
        Perform a simple traversal starting from the current edge returning a
        list of results.

        :param operation: The operation to be performed
        :type operation: str
        :rtype: list
        
        """
        results = execute_query('g.e(eid).%s()' % operation, {'eid': self.eid})
        return [Element.deserialize(r) for r in results]
Esempio n. 14
0
    def _simple_traversal(self, operation):
        """
        Perform a simple traversal starting from the current edge returning a
        list of results.

        :param operation: The operation to be performed
        :type operation: str
        :rtype: list
        
        """
        results = execute_query('g.e(eid).%s()'%operation, {'eid':self.eid})
        return [Element.deserialize(r) for r in results]
Esempio n. 15
0
 def delete(self):
     """
     Delete the current vertex from the graph.
     """
     if self.__abstract__:
         raise ThunderdomeException('cant delete abstract elements')
     if self.eid is None:
         return self
     query = """
     g.removeVertex(g.v(eid))
     g.stopTransaction(SUCCESS)
     """
     results = execute_query(query, {'eid': self.eid})
Esempio n. 16
0
 def delete(self):
     """
     Delete the current vertex from the graph.
     """
     if self.__abstract__:
         raise ThunderdomeException('cant delete abstract elements')
     if self.eid is None:
         return self
     query = """
     g.removeVertex(g.v(eid))
     g.stopTransaction(SUCCESS)
     """
     results = execute_query(query, {'eid': self.eid})
Esempio n. 17
0
    def get_by_eid(cls, eid):
        """
        Return the edge with the given Titan-specific eid. Raises a
        DoesNotExist exception if no edge is found.

        :param eid: The Titan-specific edge id (eid)
        :type eid: int
        
        """
        results = execute_query('g.e(eid)', {'eid': eid})
        if not results:
            raise cls.DoesNotExist
        return Element.deserialize(results[0])
Esempio n. 18
0
    def get_by_eid(cls, eid):
        """
        Return the edge with the given Titan-specific eid. Raises a
        DoesNotExist exception if no edge is found.

        :param eid: The Titan-specific edge id (eid)
        :type eid: int
        
        """
        results = execute_query('g.e(eid)', {'eid':eid})
        if not results:
            raise cls.DoesNotExist
        return Element.deserialize(results[0])
Esempio n. 19
0
    def get_by_eid(cls, eid):
        """
        Look update a vertex by its Titan-specific id (eid). Raises a
        DoesNotExist exception if a vertex with the given eid was not found.

        :param eid: The numeric Titan-specific id
        :type eid: int
        :rtype: thunderdome.models.Vertex
        
        """
        results = execute_query('g.v(eid)', {'eid':eid})
        if not results:
            raise cls.DoesNotExist
        return Element.deserialize(results[0])
Esempio n. 20
0
    def get_by_eid(cls, eid):
        """
        Look update a vertex by its Titan-specific id (eid). Raises a
        DoesNotExist exception if a vertex with the given eid was not found.

        :param eid: The numeric Titan-specific id
        :type eid: int
        :rtype: thunderdome.models.Vertex
        
        """
        results = execute_query('g.v(eid)', {'eid': eid})
        if not results:
            raise cls.DoesNotExist
        return Element.deserialize(results[0])
Esempio n. 21
0
 def delete(self):
     """
     Delete the current edge from the graph.
     """
     if self.__abstract__:
         raise ThunderdomeException('cant delete abstract elements')
     if self.eid is None:
         return self
     query = """
     e = g.e(eid)
     if (e != null) {
       g.removeEdge(e)
       g.stopTransaction(SUCCESS)
     }
     """        
     results = execute_query(query, {'eid':self.eid})
Esempio n. 22
0
 def delete(self):
     """
     Delete the current edge from the graph.
     """
     if self.__abstract__:
         raise ThunderdomeException('cant delete abstract elements')
     if self.eid is None:
         return self
     query = """
     e = g.e(eid)
     if (e != null) {
       g.removeEdge(e)
       g.stopTransaction(SUCCESS)
     }
     """
     results = execute_query(query, {'eid': self.eid})
Esempio n. 23
0
    def all(cls, vids, as_dict=False):
        """
        Load all vertices with the given vids from the graph. By default this
        will return a list of vertices but if as_dict is True then it will
        return a dictionary containing vids as keys and vertices found as
        values.

        :param vids: A list of thunderdome UUIDS (vids)
        :type vids: list
        :param as_dict: Toggle whether to return a dictionary or list
        :type as_dict: boolean
        :rtype: dict or list
        
        """
        if not isinstance(vids, (list, tuple)):
            raise ThunderdomeQueryError("vids must be of type list or tuple")

        strvids = [str(v) for v in vids]
        qs = ['vids.collect{g.V("vid", it).toList()[0]}']

        results = execute_query('\n'.join(qs), {'vids': strvids})
        results = filter(None, results)

        if len(results) != len(vids):
            raise ThunderdomeQueryError(
                "the number of results don't match the number of vids requested"
            )

        objects = []
        for r in results:
            try:
                objects += [Element.deserialize(r)]
            except KeyError:
                raise ThunderdomeQueryError(
                    'Vertex type "{}" is unknown'.format(
                        r.get('element_type', '')))

        if as_dict:
            return {v.vid: v for v in objects}

        return objects
Esempio n. 24
0
    def all(cls, vids, as_dict=False):
        """
        Load all vertices with the given vids from the graph. By default this
        will return a list of vertices but if as_dict is True then it will
        return a dictionary containing vids as keys and vertices found as
        values.

        :param vids: A list of thunderdome UUIDS (vids)
        :type vids: list
        :param as_dict: Toggle whether to return a dictionary or list
        :type as_dict: boolean
        :rtype: dict or list
        
        """
        if not isinstance(vids, (list, tuple)):
            raise ThunderdomeQueryError("vids must be of type list or tuple")
        
        strvids = [str(v) for v in vids]
        qs = ['vids.collect{g.V("vid", it).toList()[0]}']
        
        results = execute_query('\n'.join(qs), {'vids':strvids})
        results = filter(None, results)
        
        if len(results) != len(vids):
            raise ThunderdomeQueryError("the number of results don't match the number of vids requested")
        
        objects = []
        for r in results:
            try:
                objects += [Element.deserialize(r)]
            except KeyError:
                raise ThunderdomeQueryError('Vertex type "{}" is unknown'.format(
                    r.get('element_type', '')
                ))
            
        if as_dict:
            return {v.vid:v for v in objects}
        
        return objects
Esempio n. 25
0
    def _get_first_undefined(self, types):
        """
        Returns the name of the first undefined type in the graph.

        :param types: All types defined in the current spec
        :type types: list

        :rtype: str

        """
        def _get_name(x):
            """
            Return the name for the given object.

            :param x: The object
            :type x: Property, Edge, KeyIndex
            :rtype: str
            
            """
            if isinstance(x, Property) or isinstance(x, KeyIndex):
                return x.name
            elif isinstance(x, Edge):
                return x.label
            raise RuntimeError("Invalid object type {}".format(type(x)))
        
        q  = "results = [:]\n"
        q += "for (x in names) {\n"
        q += "  t = g.getType(x)\n"
        q += "  if (t == null) {\n"
        q += "    return x\n"
        q += "  }\n"
        q += "}\n"
        q += "null"

        
        names = [_get_name(x) for x in types]
        from thunderdome.connection import execute_query
        return execute_query(q, {'names': names})
Esempio n. 26
0
    def __call__(self, instance, *args, **kwargs):
        """
        Intercept attempts to call the GremlinMethod attribute and perform a
        gremlin query returning the results.

        :param instance: The class instance the method was called on
        :type instance: object

        """
        self._setup()

        args = list(args)
        if not self.classmethod:
            args = [instance.eid] + args

        params = self.defaults.copy()
        if len(args + kwargs.values()) > len(self.arg_list):
            raise TypeError('{}() takes {} args, {} given'.format(self.attr_name, len(self.arg_list), len(args)))

        #check for and calculate callable defaults
        for k,v in params.items():
            if callable(v):
                params[k] = v()

        arglist = self.arg_list[:]
        for arg in args:
            params[arglist.pop(0)] = arg

        for k,v in kwargs.items():
            if k not in arglist:
                an = self.attr_name
                if k in params:
                    raise TypeError(
                        "{}() got multiple values for keyword argument '{}'".format(an, k))
                else:
                    raise TypeError(
                        "{}() got an unexpected keyword argument '{}'".format(an, k))
            arglist.pop(arglist.index(k))
            params[k] = v

        params = self.transform_params_to_database(params)

        try:
            from thunderdome import Vertex
            from thunderdome import Edge
            
            if hasattr(instance, 'get_element_type'):
                context = "vertices.{}".format(instance.get_element_type())
            elif hasattr(instance, 'get_label'):
                context = "edges.{}".format(instance.get_label())
            else:
                context = "other"

            context = "{}.{}".format(context, self.method_name)

            tmp = execute_query(self.function_body, params, transaction=self.transaction, context=context)
        except ThunderdomeQueryError as tqe:
            import pprint
            msg  = "Error while executing Gremlin method\n\n"
            msg += "[Method]\n{}\n\n".format(self.method_name)
            msg += "[Params]\n{}\n\n".format(pprint.pformat(params))
            msg += "[Function Body]\n{}\n".format(self.function_body)
            msg += "\n[Error]\n{}\n".format(tqe)
            msg += "\n[Raw Response]\n{}\n".format(tqe.raw_response)
            raise ThunderdomeGremlinException(msg)
        return tmp
Esempio n. 27
0
    def __call__(self, instance, *args, **kwargs):
        """
        Intercept attempts to call the GremlinMethod attribute and perform a
        gremlin query returning the results.

        :param instance: The class instance the method was called on
        :type instance: object

        """
        self._setup()

        args = list(args)
        if not self.classmethod:
            args = [instance.eid] + args

        params = self.defaults.copy()
        if len(args + kwargs.values()) > len(self.arg_list):
            raise TypeError('{}() takes {} args, {} given'.format(
                self.attr_name, len(self.arg_list), len(args)))

        #check for and calculate callable defaults
        for k, v in params.items():
            if callable(v):
                params[k] = v()

        arglist = self.arg_list[:]
        for arg in args:
            params[arglist.pop(0)] = arg

        for k, v in kwargs.items():
            if k not in arglist:
                an = self.attr_name
                if k in params:
                    raise TypeError(
                        "{}() got multiple values for keyword argument '{}'".
                        format(an, k))
                else:
                    raise TypeError(
                        "{}() got an unexpected keyword argument '{}'".format(
                            an, k))
            arglist.pop(arglist.index(k))
            params[k] = v

        params = self.transform_params_to_database(params)

        try:
            from thunderdome import Vertex
            from thunderdome import Edge

            if hasattr(instance, 'get_element_type'):
                context = "vertices.{}".format(instance.get_element_type())
            elif hasattr(instance, 'get_label'):
                context = "edges.{}".format(instance.get_label())
            else:
                context = "other"

            context = "{}.{}".format(context, self.method_name)

            tmp = execute_query(self.function_body,
                                params,
                                transaction=self.transaction,
                                context=context)
        except ThunderdomeQueryError as tqe:
            import pprint
            msg = "Error while executing Gremlin method\n\n"
            msg += "[Method]\n{}\n\n".format(self.method_name)
            msg += "[Params]\n{}\n\n".format(pprint.pformat(params))
            msg += "[Function Body]\n{}\n".format(self.function_body)
            msg += "\n[Error]\n{}\n".format(tqe)
            msg += "\n[Raw Response]\n{}\n".format(tqe.raw_response)
            raise ThunderdomeGremlinException(msg)
        return tmp