示例#1
0
文件: repo.py 项目: roscoeZA/GeoSync
    def synced(self, branch=geogig.HEAD, credentials=None):
        '''
        Returns a tuple with number of (ahead, behind) commits between this repo and a remote
        It uses the passed branch or, if not passed, the current branch
        If the repository is headless, or if not remote is defined, it will throw an exception 
        It uses the "origin" remote if it exists, otherwise it uses the first remote available.
        If the remote requires authentication, a tuple of (username,password) must be passed
        in the credentials parameter
        '''
        if (branch == geogig.HEAD and self.isdetached()):
            raise GeoGigException(
                "Cannot use current branch. The repository has a detached HEAD"
            )

        remotes = self.remotes
        if remotes:
            if "origin" in remotes:
                remote = remotes["origin"]
                remotename = "origin"
            else:
                remotename = remotes.keys()[0]
                remote = remotes.values()[0]
        else:
            raise GeoGigException("No remotes defined")

        if isremoteurl(remote):
            repo = Repository(remote, GeoGigServerConnector(credentials))
        else:
            conn = self.connector.__class__()
            repo = Repository(remote[len("file:/"):], conn)

        localtip = self.revparse(branch)
        remotetip = repo.revparse(branch)
        if remotetip == localtip:
            return 0, 0

        if remotetip == geogig.NULL_ID:
            log = self.log(branch)
            push = len(log)
            pull = 0
        else:
            trackedbranchhead = self.revparse("refs/remotes/" + remotename +
                                              "/" + branch)
            log = self.log(branch, trackedbranchhead)
            push = len(log)
            log = repo.log(branch, trackedbranchhead)
            pull = len(log)
        return push, pull
示例#2
0
 def revparse(self, rev):
     commands = ['rev-parse', rev]
     output = self.run(commands)
     id = output[0].strip()
     if len(id) != 40:
         raise GeoGigException("Cannot resolve the provided reference")
     return id
示例#3
0
 def setascurrent(self):
     '''Sets this version of the feature as the current one in the working tree and index'''
     if self.exists():
         self.repo.updatepathtoref(self.ref, [self.path])
     else:
         raise GeoGigException(
             "Feature at the specified path does not exist")
示例#4
0
 def query(self):
     data = self.repo.featuredata(self.ref, self.path)
     if len(data) == 0:
         raise GeoGigException(
             "Feature at the specified path does not exist")
     self._attributes = dict(((k, v[0]) for k, v in data.iteritems()))
     self._featuretype = dict(((k, v[1]) for k, v in data.iteritems()))
示例#5
0
def _runGateway(_commands, url, addcolor = True):    
    commands = list(_commands)
    gc.collect()    
    if addcolor:
        commands.extend(["--color", "never"])
    command = " ".join(commands)
    command = command.replace("\r", "")   

    strclass = _javaGateway().jvm.String
    array = _javaGateway().new_array(strclass,len(commands))
    for i, c in enumerate(commands):
        array[i] = c
    start = time.clock()
    returncode = _javaGateway().entry_point.runCommand(url, array)
    end = time.clock()
    diff = end - start
    _logger.debug("Executed " + hidePassword(command)  + " in " + str(diff) + " millisecs")
    output = [""]    
    page = _javaGateway().entry_point.nextOutputPage()
    while page is not None:
        output.append(page)
        page = _javaGateway().entry_point.nextOutputPage()
    output = "".join(output)            
    output = output.strip("\r\n").splitlines()
    output = [s.strip("\r\n") for s in output]        
    if returncode:                             
        errormsg = "\n".join(output)
        _logger.error("Error running command '%s': %s" % (hidePassword(command), errormsg))
        raise GeoGigException("\n".join(output))
         
    return output 
示例#6
0
 def revparse(self, rev):
     try:
         url = self.repo.url + '/refparse'
         r = requests.get(url, params={'name': rev}, auth=self.credentials)
         root = ET.fromstring(r.text)
         id = root.iter('objectId').next().text
         return id
     except Exception, e:
         raise GeoGigException("Reference %s not found" % rev)
示例#7
0
 def commitatdate(self, t):
     '''Returns a Commit corresponding to a given instant, which is passed as a datetime.datetime'''
     epoch = datetime.datetime.utcfromtimestamp(0)
     delta = t - epoch
     milisecs = int(delta.total_seconds()) * 1000
     log = self.connector.log(geogig.HEAD, until = str(milisecs), n = 1)
     if log:
         return log[0]
     else:
         raise GeoGigException("Invalid date for this repository")
示例#8
0
 def featuredata(self, ref, path):
     '''
     Returns the attributes of a given feature, as a dict with attributes 
     names as keys and tuples of (attribute_value, attribute_type_name) as values.
     Values are converted to appropriate types when possible, otherwise they are stored
     as the string representation of the attribute
     '''
     data = self.connector.featuredata(_resolveref(ref), path)
     if len(data) == 0:
         raise GeoGigException("The specified feature does not exist")
     return data
示例#9
0
 def push(self, remote, branch = None, all = False):
     '''
     Pushes to the specified remote and specified branch. 
     If no branch is provided, it will use the name of the current branch, unless the repo is headless.        
     In that case, and exception will be raised.
     if all == True, it will push all branches and ignore the branch. 
     '''
     if branch is None and self.isdetached():
         raise GeoGigException("HEAD is detached. Cannot push")
     branch = branch or self.head.ref
     return self.connector.push(remote, branch, all)
示例#10
0
 def pull(self, remote = geogig.ORIGIN, branch = None, rebase = False):
     '''
     Pulls from the specified remote and specified branch.
     If no branch is provided, it will use the name of the current branch, unless the repo is headless. 
     In that case, and exception will be raised
     If rebase == True, it will do a rebase instead of a merge
     '''
     if branch == None and self.isdetached():
         raise GeoGigException("HEAD is detached. Cannot pull")
     branch = branch or self.head.ref
     self.connector.pull(remote, branch, rebase)
     self.cleancache()
示例#11
0
 def solveconflicts(self, paths, version=geogig.OURS):
     commands = ["checkout"]
     if version == geogig.OURS:
         commands.append("--ours")
     elif version == geogig.THEIRS:
         commands.append("--theirs")
     else:
         raise GeoGigException("Unknown option:" + version)
     commands.append("-p")
     commands.extend(paths)
     self.run(commands)
     self.add(paths)
示例#12
0
 def geomfieldname(self):
     '''
     Returns the name of the geometry field of this feature.
     It assumes that the feature contains one and only one geometry.
     If there is no geometry, an exception is raised.
     If there are several of them, the first one found is returned.
     '''
     attrs = self.attributes 
     for k, v in attrs.iteritems():
         if isinstance(v, Geometry):
             return k
     raise GeoGigException("Feature has no geometry")
示例#13
0
 def __init__(self, url, connector = None, init = False, initParams = None):
     '''
     url: The url of the repository. Only file paths are supported so far. Remote repos are not supported
     
     connector: the connector to use to communicate with the repository
     
     init: True if the repository should be initialized
     '''
     self.url = url
     self.connector = Py4JCLIConnector() if connector is None else connector
     if init:
         try:
             mkdir(url)
         except Exception, e:
             raise GeoGigException("Cannot create repository folder.\nCheck that path is correct and you have permission")
示例#14
0
def _run(command, addcolor=True):
    command = ['geogig'] + command
    if addcolor:
        command.extend(["--color", "never"])
    commandstr = " ".join(command)
    if os.name != 'nt':
        command = commandstr
    output = []
    proc = subprocess.Popen(command,
                            shell=True,
                            stdout=subprocess.PIPE,
                            stdin=subprocess.PIPE,
                            stderr=subprocess.STDOUT,
                            universal_newlines=True)
    for line in iter(proc.stdout.readline, ""):
        line = line.strip("\n")
        output.append(line)
    proc.wait()
    returncode = proc.returncode
    if returncode:
        logging.error("Error running " + commandstr + "\n" + " ".join(output))
        raise GeoGigException(output)
    logging.info("Executed " + commandstr + "\n" + " ".join(output[:5]))
    return output
示例#15
0
 def diff(self, feature):
     if feature.path != self.path:
         raise GeoGigException("Cannot compare feature with different path")
     return self.repo.featurediff(self.ref, feature.ref, self.path)
示例#16
0
 def continue_(self):
     if self.isrebasing():
         commands = ["rebase", "--continue"]
         self.run(commands)
         if self.isrebasing():
             raise GeoGigException("Could not continue rebasing")
示例#17
0
        if init:
            try:
                mkdir(url)
            except Exception, e:
                raise GeoGigException("Cannot create repository folder.\nCheck that path is correct and you have permission")

        self.connector.setRepository(self)
        try:
            self.connector.checkisrepo()
            isAlreadyRepo = True
        except GeoGigException, e:
            isAlreadyRepo = False

        if init:
            if isAlreadyRepo:
                raise GeoGigException("Cannot init, the folder is already a geogig repository")
            else:
                self.init(initParams)
        self.connector.checkisrepo()

        self.cleancache()

    @staticmethod
    def newrepofromclone(url, path, connector = None, username = None, password = None):
        '''
        Clones a given repository into a local folder and returns a repository object representing it
        
        url: the url of the repo to clone
        
        path: the path to clone the repo into
        
示例#18
0
 def checkisrepo(self):
     if not os.path.exists(os.path.join(self.repo.url, '.geogig')):
         raise GeoGigException("Not a valid GeoGig repository: " +
                               self.repo.url)