EzDevInfo.com

GitPython

GitPython is a python library used to interact with Git repositories. GitPython Documentation — GitPython 1.0.1 documentation

gitpython creating zip archive

How can I create an archive with gitpython, I tried the following which creates the file but I can't open it it tells me an error occurred reading archive the archive appears to be invalid or damaged

from git import *
repo = Repo(repo_path)
assert repo.bare == False
repo.archive(open("repo.tar",'w'))

I would like to create a zip file so then I tried this but here it creates an empty zip file (the path to repo is correct as when I use repo.clone it propery clones everything)

repo.archive(open("repo.zip",'w'), format="zip") 

Source: (StackOverflow)

Cloning a private Github repo using a script

How to clone a private repository from Github using python?

I found some good information about git and python, but I started learning python few days back.


Source: (StackOverflow)

Advertisements

get short sha of commit with gitpython

The long SHA can be gotten like below:

repo = git.Repo(search_parent_directories=True)
sha = repo.head.object.hexsha

How about short one? (short SHA is decided by the scale of the repo, so it should not be like sha[:7])


Source: (StackOverflow)

How can I pull a remote repository with GitPython?

I am trying to find the way to pull a git repository using gitPython. So far this is what I have taken from the official docs here.

test_remote = repo.create_remote('test', 'git@server:repo.git')
repo.delete_remote(test_remote) # create and delete remotes
origin = repo.remotes.origin    # get default remote by name
origin.refs                     # local remote references
o = origin.rename('new_origin') # rename remotes
o.fetch()                       # fetch, pull and push from and to the remote
o.pull()
o.push()

The fact is that I want to access the repo.remotes.origin to do a pull withouth renaming it's origin (origin.rename) How can I achieve this? Thanks.


Source: (StackOverflow)

GitPython: how to commit updated submodule

I have been at this for hours now, and although I have a feeling I'm close I can't seem to figure this out.

I'm trying to make a script that takes a git repository, updates a submodule in that repository to a specified version, and commits that change.

What works:

I can find the repository, get the submodule and check out the commit I want.

What doesn't work:

I can't seem to add the updated submodule hash so I can commit it.

My Code:

repos = Repo('path/to/repos')
submodule = repos.submodule('submodule-name')
submodule.module().git.checkout('wanted commit')

diff = repos.index.diff(None)

At this point I can see the submodule-change. If I check sourcetree, I can see the changed submodule in the 'unstaged files'. The thing is, I have no clue how to stage the change so I can commit it.

What I have tried:

  • If I commit using repos.index.commit(''), it creates an empty commit.
  • If I try to add the path of the submodule using repos.index.add([submodule.path]), all files in the submodule are added to the repository, which is definately not what I want.
  • If I try to add the submodule itself (which should be possible according to the docs) using repos.index.add([submodule]), nothing seems to happen.

Source: (StackOverflow)

git log -- works correct on terminal, but doing g.log(file_name) in git python shows error

For SOME files, it happens that in Git Python the g.log() instruction gives error, but for the same file if I do [$git log -- ] on terminal, that works correct. The following command on terminal works very well:

$git log -- org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/CompilationUnitVisitor.java

Here is my python code:

import git
from git import *
import sys
repo = Repo ("/home/directory/git/eclipse.jdt.core")
assert repo.bare == False
g=repo.git
loginfo = g.log('org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/CompilationUnitVisitor.java')

It shows the following error: Traceback (most recent call last): File "", line 1, in File "/usr/local/lib/python2.7/dist-packages/GitPython-0.3.2.RC1-py2.7.egg/git/cmd.py", line 227, in return lambda *args, **kwargs: self._call_process(name, *args, **kwargs) File "/usr/local/lib/python2.7/dist-packages/GitPython-0.3.2.RC1-py2.7.egg/git/cmd.py", line 456, in _call_process return self.execute(call, **_kwargs) File "/usr/local/lib/python2.7/dist-packages/GitPython-0.3.2.RC1-py2.7.egg/git/cmd.py", line 377, in execute raise GitCommandError(command, status, stderr_value) git.exc.GitCommandError: 'git log org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/CompilationUnitVisitor.java' returned exit status 128: fatal: ambiguous argument 'org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/CompilationUnitVisitor.java': unknown revision or path not in the working tree. Use '--' to separate paths from revisions, like this: 'git [...] -- [...]'

Can someone please suggest how to correct it?


Source: (StackOverflow)

Python: Get a list of changed files between two commits or branches

I'm a Python/Git newb but I'm trying to write a script that takes two branches or commits as parameters and shows a list of changed files between the two, not all the extraneous info that comes with a regular diff.

This was accomplished in bash scripting by using

git diff --name-only FIRSTBRANCH...SECONDBRANCH

but it isn't translating as easily to Python scripting using gitpython. If anyone has any idea how to do this, that'd be great.

edit: heres some code

user = str(sys.argv[1])
password = str(sys.argv[2])
currentBranch = str(sys.argv[3])
compBranch = str(sys.argv[4])

repo = Repo(directory)
currentCommit = repo.commit(currentBranch)
compCommit = repo.commit(compBranch)
diffed = repo.diff(currentBranch, compBranch)

print diff will return all the diff details when I only want a list of changed files


Source: (StackOverflow)

Any git hook to block merge conflict?

I am planning to write a git hook in python to protect my github repository. It will detect merge conflict markers (like >>>>>>) and block the commit.

I have some initial ideas but it will be very helpful if I get similar hook samples. Advise about implementation from experienced people will be appreciated too.


Source: (StackOverflow)

GitPython create local branch from remote branch

I have multiple lab machines and I need to make a copy of my remote branch on my local lab machine. I believe the git bash command for this is:

git checkout -b mybranch origin/mybranch

How do I do the equivalent in GitPython?

I may make changes and push the changes back to origin/mybranch and then pull the changes back on to other lab machines.


Source: (StackOverflow)

How to 'pipe' password to remote.update() with gitPython

I am trying to write a script (probably python) that needs to fetch a remote repo (housed with Stash via git), and checkout a specific commit (based on the hash). The problem is that this needs to happen 'blindly' to the user, but it pauses for a password. I need to figure out a way to pipe (or proc.communicate() (or something) the password to the repo.fetch() or origin.update() proc.

Currently, I have code that's something like this:

remoteUrl = 'http://uname@build:7990'
commitId = '9a5af460615'
pw = 'MyPassword'
repo = git.Repo('C:\\Myfolder\\MyRepo')
proc = subprocess.Popen('echo pw | repo.git.fetch()', shell=True, stdin = PIPE)

but it doesn't seem to work if I done try the echo/pipe, but follow repo.git.fetch() with proc.communicate(pw), I get error:

Traceback (most recent call last):
  File "<interactive input>", line 1, in <module>
  File "C:\Program Files (x86)\Python34\lib\subprocess.py", line 941, in communicate
    self.stdin.write(input)
TypeError: 'str' does not support the buffer interface

Finally, I've also tried adding:

o = repo.remotes.origin
proc = subprocess.Popen('o.update()', shell=True, stdin = PIPE)
proc.communicate(pw)
Traceback (most recent call last):
  File "<interactive input>", line 1, in <module>
  File "C:\Program Files (x86)\Python34\lib\subprocess.py", line 941, in communicate
    self.stdin.write(input)
TypeError: 'str' does not support the buffer interface

But to no avail, as you can see from the error.

I think I'm over-complicating this, as it seems gitpython probably has a good way to send the pw to o.update() or repo.git.fetch() without using the subprocess?

EDIT: I'm hoping for code something along these lines:

remoteUrl = 'http://uname@build:7990'
commitId = '9a5af460615'
pw = 'MyPassword'
repo = git.Repo('C:\\Myfolder\\MyRepo')
repo.fetch(remoteUrl)
repo.checkout(commitId) # or maybe repo.pull, or something?

That is more pseudocode than anything else, but it may help you see what I'm hoping for. Also, I want to force through any 'hiccups' I don't want detached head warnings or anything, I want to completely replace the local working copy with the remote at the specified commit.


Source: (StackOverflow)

gitpython error when checking if repo is dirty

I receive an error while trying to use gitpython to check if a repository is dirty, i.e. has uncommitted changed to tracked files:

import git
repo = git.Repo('')
print repo.is_dirty()

The error:

Traceback (most recent call last):
  File "C:\dev\my_prog\test.py", line 8, in <module>
    print repo.is_dirty()
  File "C:\Python27\lib\site-packages\gitpython-0.3.2.rc1-py2.7.egg\git\repo\base.py", line 502, in is_dirty
    len(self.git.diff('HEAD', '--cached', *default_args)):
  File "C:\Python27\lib\site-packages\gitpython-0.3.2.rc1-py2.7.egg\git\cmd.py", line 227, in <lambda>
    return lambda *args, **kwargs: self._call_process(name, *args, **kwargs)
  File "C:\Python27\lib\site-packages\gitpython-0.3.2.rc1-py2.7.egg\git\cmd.py", line 456, in _call_process
    return self.execute(call, **_kwargs)
  File "C:\Python27\lib\site-packages\gitpython-0.3.2.rc1-py2.7.egg\git\cmd.py", line 377, in execute
    raise GitCommandError(command, status, stderr_value)
git.exc.GitCommandError: 'git diff HEAD --cached --abbrev=40 --full-index --raw' returned exit status 1:

How come? What could be the problem?
Notice I'm working on Windows 7 with msysgit


Source: (StackOverflow)

GitPython tags sorted

I am trying to get the last tag in the repo using GitPython lib. Usually I was dong it this way:

repo = Repo(project_root)
last_tag = str(repo.tags[-1])

But once version 1.10 was released, I am always getting 1.9 ;( I know it's related to output git tag -l being listing same order. So it will be 1.1, 1.10, 1.2, ..., 1.9

The qustion is how to get the latest tag using GitPython? (I am aware of git tag -l | sort -V and I know how to solve this not using the repo object. But maybe someone knows what am I missing in getting sorted tags list in this lib)

Custom sorting function is always an option too, but still, I wonder if there a way to do it with GitPython?


Source: (StackOverflow)

How to get staged files using GitPython?

I'm counting staged files in git using gitpython.

For modified files, I can use

repo = git.Repo()
modified_files = len(repo.index.diff(None))

But for staged files I can't find the solution.

I know git status --porcelain but I'm looking for other solution which is better. (I hope using gitpython not git command, the script will be faster)


Source: (StackOverflow)

How to get count of unpublished commit with GitPython?

With git status I can get information about count of unpublished commits:

ยป git status             
# On branch master
# Your branch is ahead of 'origin/master' by 2 commits.
#   (use "git push" to publish your local commits)
#
nothing to commit, working directory clean

I want to get unpublished commits (or count) with GitPython. I docs I found repo.git.status(), but this is not what I want.


Source: (StackOverflow)

Git Python Cannot find Commit

I am not able to find a commit that a tag points to by navigating the commit tree. For this specific example, I am using the Tornado Web repository cloned directly from Github.

import sys
import git

if len(sys.argv) < 2:
    print 'python git_test.py <repo path>'
    sys.exit(0)

repo = git.Repo(sys.argv[1])
commits = {}

for git_commit in repo.iter_commits():
    commits[git_commit.hexsha] = git_commit

print len(commits)

for git_tag in repo.tags:
    print 'Tag %s points to Commit %s' % (
        git_tag.name,
        commits[git_tag.commit.hexsha]
    )

This is suppose to find all commits in git's direct acyclic graph, however, I tried another approach that recursively navigated the dag through a recursive function and it delivered the same results.

ian@ian-EP45-UD3L:~/code/playground$ python git_test.py ~/code/tornado/
459
Tag v1.0.0 points to Commit eb5b3d8df7a305ac1ffa0a12c813e5d7ee4d6cd3
Traceback (most recent call last):
  File "git_test.py", line 19, in <module>
    commits[git_tag.commit.hexsha]
KeyError: '2b5064b7ed962603ade0db0c8e21846a9879e30e'

Am I doing something incorrectly, how can I work around this problem? Any help is appreciated!

I am using git-python v0.3.1.


Source: (StackOverflow)