# Functions
#
+# GIT_DIR value cached
+__base_dir = None
+
def get_base_dir():
"""Different start-up variables read from the environment
"""
- if 'GIT_DIR' in os.environ:
- return os.environ['GIT_DIR']
- else:
- return _output_one_line('git-rev-parse --git-dir')
+ global __base_dir
+
+ if not __base_dir:
+ if 'GIT_DIR' in os.environ:
+ __base_dir = os.environ['GIT_DIR']
+ else:
+ __base_dir = _output_one_line('git-rev-parse --git-dir')
+
+ return __base_dir
def get_commit(id_hash):
"""Commit objects factory. Save/look-up them in the __commits
raise GitException, 'Could not update HEAD to "%s".' % val
__head = val
+ # only allow SHA1 hashes
+ assert(len(__head) == 40)
+
def __clear_head_cache():
"""Sets the __head to None so that a re-read is forced
"""
raise GitException, 'Unknown revision: %s' % git_id
def branch_exists(branch):
- """Existance check for the named branch
+ """Existence check for the named branch
"""
for line in _output_lines(['git-rev-parse', '--symbolic', '--all']):
if line.strip() == branch:
if not branch_exists(new_head):
raise GitException, 'Branch "%s" does not exist' % name
- tree_id = rev_parse(new_head + '^0')
+ tree_id = rev_parse(new_head + '^{commit}')
if tree_id != get_head():
refresh_index()
if __run('git-read-tree -u -m', [get_head(), tree_id]) != 0:
return commit_id
-def apply_diff(rev1, rev2):
+def apply_diff(rev1, rev2, check_index = True):
"""Apply the diff between rev1 and rev2 onto the current
index. This function doesn't need to raise an exception since it
is only used for fast-pushing a patch. If this operation fails,
the pushing would fall back to the three-way merge.
"""
- return os.system('git-diff-tree -p %s %s | git-apply --index 2> /dev/null'
- % (rev1, rev2)) == 0
+ if check_index:
+ index_opt = '--index'
+ else:
+ index_opt = ''
+ cmd = 'git-diff-tree -p %s %s | git-apply %s 2> /dev/null' \
+ % (rev1, rev2, index_opt)
+
+ return os.system(cmd) == 0
def merge(base, head1, head2):
"""Perform a 3-way merge between base, head1 and head2 into the
local tree
"""
refresh_index()
- if __run('git-read-tree -u -m', [base, head1, head2]) != 0:
+ if __run('git-read-tree -u -m --aggressive', [base, head1, head2]) != 0:
raise GitException, 'git-read-tree failed (local changes maybe?)'
# this can fail if there are conflicts
if not tree_id:
tree_id = get_head()
- cache_files = __tree_status(files, tree_id)
- rm_files = [x[1] for x in cache_files if x[0] in ['D']]
-
checkout(files, tree_id, True)
- # checkout doesn't remove files
- map(os.remove, rm_files)
# if the reset refers to the whole tree, switch the HEAD as well
if not files: