Merge branch 'master' into next

This commit is contained in:
J. David Ibáñez
2013-03-09 21:17:09 +01:00
23 changed files with 386 additions and 333 deletions

1
.gitignore vendored
View File

@@ -2,6 +2,7 @@ MANIFEST
build build
dist dist
pygit2.so pygit2.so
_pygit2.so
test/*.pyc test/*.pyc
test/__pycache__ test/__pycache__
pygit2/*.pyc pygit2/*.pyc

View File

@@ -14,7 +14,9 @@ platform-specific instructions to build the library in the libgit2 website:
Also, make sure you have Python 2.6+ installed together with the Python Also, make sure you have Python 2.6+ installed together with the Python
development headers. development headers.
When those are installed, you can install pygit2:: When those are installed, you can install pygit2:
.. code-block:: sh
$ git clone git://github.com/libgit2/pygit2.git $ git clone git://github.com/libgit2/pygit2.git
$ cd pygit2 $ cd pygit2
@@ -36,7 +38,9 @@ using the default installation procedure (e.g. without specifying
``CMAKE_INSTALL_PREFIX``), you probably installed it under ``CMAKE_INSTALL_PREFIX``), you probably installed it under
``/usr/local/lib``. On some distributions (e.g. Ubuntu), ``/usr/local/lib``. On some distributions (e.g. Ubuntu),
``/usr/local/lib`` is not in the linker's default search path (see the ``/usr/local/lib`` is not in the linker's default search path (see the
`ld man page`_ for details), and you will get errors like:: `ld man page`_ for details), and you will get errors like:
.. code-block:: sh
$ python -c 'import pygit2' $ python -c 'import pygit2'
Traceback (most recent call last): Traceback (most recent call last):
@@ -47,7 +51,9 @@ using the default installation procedure (e.g. without specifying
The following recipe shows how to install libgit2 and pygit2 on these The following recipe shows how to install libgit2 and pygit2 on these
systems. First, download and install libgit2 (following the systems. First, download and install libgit2 (following the
instructions in the libgit2 ``README.md``):: instructions in the libgit2 ``README.md``):
.. code-block:: sh
$ git clone git://github.com/libgit2/libgit2.git $ git clone git://github.com/libgit2/libgit2.git
$ mkdir libgit2/build $ mkdir libgit2/build
@@ -59,7 +65,9 @@ instructions in the libgit2 ``README.md``)::
Now, download and install pygit2. You will probably have to set the Now, download and install pygit2. You will probably have to set the
``LIBGIT2`` environment variable so the compiler can find the libgit2 ``LIBGIT2`` environment variable so the compiler can find the libgit2
headers and libraries:: headers and libraries:
.. code-block:: sh
$ git clone git://github.com/libgit2/pygit2.git $ git clone git://github.com/libgit2/pygit2.git
$ cd pygit2 $ cd pygit2
@@ -72,7 +80,9 @@ This compiles the pygit2 libraries with a ``RUNPATH``, which bakes
extra library search paths directly into the binaries (see the `ld man extra library search paths directly into the binaries (see the `ld man
page`_ for details). With ``RUNPATH`` compiled in, you won't have to page`_ for details). With ``RUNPATH`` compiled in, you won't have to
use ``LD_LIBRARY_PATH``. You can check to ensure ``RUNPATH`` was set use ``LD_LIBRARY_PATH``. You can check to ensure ``RUNPATH`` was set
with readelf_:: with readelf_:
.. code-block:: sh
$ readelf --dynamic build/lib.linux-x86_64-3.2/_pygit2.cpython-32.so | grep PATH $ readelf --dynamic build/lib.linux-x86_64-3.2/_pygit2.cpython-32.so | grep PATH
0x000000000000000f (RPATH) Library rpath: [/usr/local/lib] 0x000000000000000f (RPATH) Library rpath: [/usr/local/lib]
@@ -90,7 +100,9 @@ in the ``LIBGIT2`` environment variable.
In addition, make sure that libgit2 is build in "__cdecl" mode. In addition, make sure that libgit2 is build in "__cdecl" mode.
The following recipe shows you how to do it, assuming you're working The following recipe shows you how to do it, assuming you're working
from a bash shell:: from a bash shell:
.. code-block:: sh
$ export LIBGIT2=C:/Dev/libgit2 $ export LIBGIT2=C:/Dev/libgit2
$ git clone git://github.com/libgit2/libgit2.git $ git clone git://github.com/libgit2/libgit2.git

View File

@@ -59,14 +59,20 @@ OBJECT_STRUCT(Index, git_index, index)
OBJECT_STRUCT(Walker, git_revwalk, walk) OBJECT_STRUCT(Walker, git_revwalk, walk)
OBJECT_STRUCT(Config, git_config, config) OBJECT_STRUCT(Config, git_config, config)
OBJECT_STRUCT(Remote, git_remote, remote) OBJECT_STRUCT(Remote, git_remote, remote)
OBJECT_STRUCT(Diff, git_diff_list, list)
typedef struct { typedef struct {
PyObject_HEAD PyObject_HEAD
Repository *repo; git_diff_list* list;
git_diff_list *diff; size_t i;
PyObject *diff_changes; size_t n;
} Diff; } DiffIter;
typedef struct {
PyObject_HEAD
PyObject* files;
PyObject* hunks;
} DiffEntry;
typedef struct { typedef struct {
PyObject_HEAD PyObject_HEAD
@@ -76,17 +82,17 @@ typedef struct {
typedef struct { typedef struct {
PyObject_HEAD PyObject_HEAD
char *header; const char *header;
int old_start; int old_start;
int old_lines; int old_lines;
PyObject *old_oid; char* old_oid;
int old_mode; int old_mode;
char* old_file; const char* old_file;
int new_start; int new_start;
int new_lines; int new_lines;
PyObject *new_oid; char* new_oid;
int new_mode; int new_mode;
char* new_file; const char* new_file;
PyObject *data; PyObject *data;
} Hunk; } Hunk;

View File

@@ -119,5 +119,21 @@ char * py_str_to_c_str(PyObject *value, const char *encoding);
#define MEMBER(type, attr, attr_type, docstr)\ #define MEMBER(type, attr, attr_type, docstr)\
{#attr, attr_type, offsetof(type, attr), 0, PyDoc_STR(docstr)} {#attr, attr_type, offsetof(type, attr), 0, PyDoc_STR(docstr)}
/* Helpers for memory allocation */
#define MALLOC(ptr, size, label) \
ptr = realloc(ptr, size * sizeof(char));\
if (ptr == NULL) {\
err = GIT_ERROR;\
giterr_set_oom();\
goto label;\
}\
#define FREE(to_free)\
if (to_free != NULL) { free(to_free); to_free = NULL; }
#define FREE_FUNC(to_free, fnct)\
if (to_free != NULL) { fnct(to_free); to_free = NULL; }
#endif #endif

View File

@@ -64,8 +64,9 @@ if libgit2_path is None:
libgit2_bin = os.path.join(libgit2_path, 'bin') libgit2_bin = os.path.join(libgit2_path, 'bin')
libgit2_include = os.path.join(libgit2_path, 'include') libgit2_include = os.path.join(libgit2_path, 'include')
libgit2_lib = os.getenv('LIBGIT2_LIB', os.path.join(libgit2_path, 'lib')) libgit2_lib = os.getenv('LIBGIT2_LIB', os.path.join(libgit2_path, 'lib'))
pygit2_exts = [ os.path.join('src', name) for name in os.listdir('src') pygit2_exts = [os.path.join('src', name) for name in os.listdir('src')
if name.endswith('.c') ] if name.endswith('.c')]
class TestCommand(Command): class TestCommand(Command):
"""Command for running unittests without install.""" """Command for running unittests without install."""
@@ -155,7 +156,6 @@ class sdist_files_from_git(sdist):
self.write_manifest() self.write_manifest()
cmdclass = { cmdclass = {
'test': TestCommand, 'test': TestCommand,
'sdist': sdist_files_from_git} 'sdist': sdist_files_from_git}
@@ -183,11 +183,11 @@ setup(name='pygit2',
maintainer=u('J. David Ibáñez'), maintainer=u('J. David Ibáñez'),
maintainer_email='jdavid.ibp@gmail.com', maintainer_email='jdavid.ibp@gmail.com',
long_description=long_description, long_description=long_description,
packages = ['pygit2'], packages=['pygit2'],
ext_modules=[ ext_modules=[
Extension('_pygit2', pygit2_exts, Extension('_pygit2', pygit2_exts,
include_dirs=[libgit2_include, 'include'], include_dirs=[libgit2_include, 'include'],
library_dirs=[libgit2_lib], library_dirs=[libgit2_lib],
libraries=['git2']), libraries=['git2']),
], ],
cmdclass=cmdclass) cmdclass=cmdclass)

View File

@@ -40,242 +40,263 @@ extern PyTypeObject IndexType;
extern PyTypeObject DiffType; extern PyTypeObject DiffType;
extern PyTypeObject HunkType; extern PyTypeObject HunkType;
static int diff_data_cb( PyTypeObject DiffEntryType;
const git_diff_delta *delta,
const git_diff_range *range, PyObject*
char line_origin, diff_get_patch_byindex(git_diff_list* list, size_t i)
const char *content,
size_t content_len,
void *cb_data)
{ {
PyObject *hunks, *data; const git_diff_delta* delta;
Hunk *hunk; const git_diff_range* range;
Py_ssize_t size; git_diff_patch* patch = NULL;
hunks = PyDict_GetItemString(cb_data, "hunks"); char buffer[41];
if (hunks == NULL) const char* hunk_content;
return -1; size_t hunk_amounts, j, hunk_header_len, hunk_lines;
int err;
size = PyList_Size(hunks); PyObject *file;
hunk = (Hunk *)PyList_GetItem(hunks, size - 1); Hunk *py_hunk;
if (hunk == NULL) DiffEntry *py_entry = NULL;
return -1;
data = Py_BuildValue("(s#,i)", err = git_diff_get_patch(&patch, &delta, list, i);
content, content_len,
line_origin
);
PyList_Append(hunk->data, data);
Py_DECREF(data);
return 0; if (err == GIT_OK) {
py_entry = (DiffEntry*) INSTANCIATE_CLASS(DiffEntryType, NULL);
if (py_entry != NULL) {
if (err == GIT_OK) {
file = Py_BuildValue("(s,s,i,i)",
delta->old_file.path,
delta->new_file.path,
delta->status,
delta->similarity
);
PyList_Append((PyObject*) py_entry->files, file);
}
hunk_amounts = git_diff_patch_num_hunks(patch);
for (j=0; j < hunk_amounts; ++j) {
err = git_diff_patch_get_hunk(&range, &hunk_content,
&hunk_header_len, &hunk_lines, patch, j);
if (err == GIT_OK) {
py_hunk = (Hunk*)PyType_GenericNew(&HunkType, NULL, NULL);
if (py_hunk != NULL) {
py_hunk->old_file = delta->old_file.path;
py_hunk->new_file = delta->new_file.path;
py_hunk->header = hunk_content;
py_hunk->old_start = range->old_start;
py_hunk->old_lines = range->old_lines;
py_hunk->new_start = range->new_start;
py_hunk->new_lines = range->new_lines;
git_oid_fmt(buffer, &delta->old_file.oid);
py_hunk->old_oid = calloc(41, sizeof(char));
memcpy(py_hunk->old_oid, buffer, 40);
git_oid_fmt(buffer, &delta->new_file.oid);
py_hunk->new_oid = calloc(41, sizeof(char));
memcpy(py_hunk->new_oid, buffer, 40);
py_hunk->data = Py_BuildValue("(s#,i)",
hunk_content, hunk_header_len,
hunk_lines);
PyList_Append((PyObject*) py_entry->hunks,
(PyObject*) py_hunk);
}
}
}
}
}
if (err < 0)
return Error_set(err);
return (PyObject*) py_entry;
} }
static int diff_hunk_cb(
const git_diff_delta *delta,
const git_diff_range *range,
const char *header,
size_t header_len,
void *cb_data)
{
PyObject *hunks;
Hunk *hunk;
int len;
char* old_path = NULL, *new_path = NULL;
char oid[GIT_OID_HEXSZ];
hunks = PyDict_GetItemString(cb_data, "hunks");
if (hunks == NULL) {
hunks = PyList_New(0);
PyDict_SetItemString(cb_data, "hunks", hunks);
Py_DECREF(hunks);
}
hunk = (Hunk*)PyType_GenericNew(&HunkType, NULL, NULL);
if (hunk == NULL)
return -1;
hunk->old_start = range->old_start;
hunk->old_lines = range->old_lines;
hunk->new_start = range->new_start;
hunk->new_lines = range->new_lines;
hunk->old_mode = delta->old_file.mode;
hunk->new_mode = delta->new_file.mode;
git_oid_fmt(oid, &delta->old_file.oid);
hunk->old_oid = PyUnicode_FromStringAndSize(oid, GIT_OID_HEXSZ);
git_oid_fmt(oid, &delta->new_file.oid);
hunk->new_oid = PyUnicode_FromStringAndSize(oid, GIT_OID_HEXSZ);
if (header) {
hunk->header = malloc(header_len+1);
if (hunk->header == NULL)
return -1;
memcpy(hunk->header, header, header_len);
hunk->header[header_len] = '\0';
}
if (delta->old_file.path != NULL) {
len = strlen(delta->old_file.path) + 1;
old_path = malloc(sizeof(char) * len);
if (old_path == NULL) {
free(hunk->header);
hunk->header = NULL;
return -1;
}
memcpy(old_path, delta->old_file.path, len);
hunk->old_file = old_path;
} else {
hunk->old_file = "";
}
if (delta->new_file.path != NULL) {
len = strlen(delta->new_file.path) + 1;
new_path = malloc(sizeof(char) * len);
if (new_path == NULL) {
free(hunk->header);
free(old_path);
return -1;
}
memcpy(new_path, delta->new_file.path, len);
hunk->new_file = new_path;
} else {
hunk->new_file = "";
}
if (hunk->data == NULL)
hunk->data = PyList_New(0);
if (PyList_Append(hunks, (PyObject *)hunk) == 0) {
Py_DECREF(hunk);
}
else {
return -1;
}
return 0;
};
static int
diff_file_cb(const git_diff_delta *delta, float progress, void *cb_data)
{
PyObject *files, *file;
if (delta->old_file.path != NULL && delta->new_file.path != NULL) {
files = PyDict_GetItemString(cb_data, "files");
if (files == NULL) {
files = PyList_New(0);
PyDict_SetItemString(cb_data, "files", files);
Py_DECREF(files);
}
file = Py_BuildValue("(s,s,i,i)",
delta->old_file.path,
delta->new_file.path,
delta->status,
delta->similarity
);
/* If success */
if (PyList_Append(files, file) == 0)
Py_DECREF(file);
}
return 0;
}
PyDoc_STRVAR(Diff_changes__doc__, "Raw changes.");
PyObject * PyObject *
Diff_changes__get__(Diff *self) DiffEntry_call(DiffEntry *self, PyObject *args, PyObject *kwds)
{ {
self->files = PyList_New(0);
if (self->diff_changes == NULL) { if (self->files == NULL) {
self->diff_changes = PyDict_New(); Py_XDECREF(self);
return NULL;
git_diff_foreach(
self->diff,
&diff_file_cb,
&diff_hunk_cb,
&diff_data_cb,
self->diff_changes
);
} }
return PyDict_Copy(self->diff_changes); self->hunks = PyList_New(0);
if (self->hunks == NULL) {
Py_XDECREF(self);
return NULL;
}
return (PyObject*) self;
} }
static int diff_print_cb( static void
const git_diff_delta *delta, DiffEntry_dealloc(DiffEntry *self)
const git_diff_range *range,
char usage,
const char *line,
size_t line_len,
void *cb_data)
{ {
PyObject *data = PyBytes_FromStringAndSize(line, line_len); Py_DECREF((PyObject*) self->files);
PyBytes_ConcatAndDel((PyObject **)cb_data, data); Py_DECREF((PyObject*) self->hunks);
PyObject_Del(self);
return 0;
} }
PyMemberDef DiffEntry_members[] = {
MEMBER(DiffEntry, files, T_OBJECT, "files"),
MEMBER(DiffEntry, hunks, T_OBJECT, "hunks"),
{NULL}
};
PyDoc_STRVAR(DiffEntry__doc__, "Diff entry object.");
PyTypeObject DiffEntryType = {
PyVarObject_HEAD_INIT(NULL, 0)
"_pygit2.DiffEntry", /* tp_name */
sizeof(DiffEntry), /* tp_basicsize */
0, /* tp_itemsize */
(destructor)DiffEntry_dealloc, /* tp_dealloc */
0, /* tp_print */
0, /* tp_getattr */
0, /* tp_setattr */
0, /* tp_compare */
0, /* tp_repr */
0, /* tp_as_number */
0, /* tp_as_sequence */
0, /* tp_as_mapping */
0, /* tp_hash */
(ternaryfunc) DiffEntry_call, /* tp_call */
0, /* tp_str */
0, /* tp_getattro */
0, /* tp_setattro */
0, /* tp_as_buffer */
Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
DiffEntry__doc__, /* tp_doc */
0, /* tp_traverse */
0, /* tp_clear */
0, /* tp_richcompare */
0, /* tp_weaklistoffset */
0, /* tp_iter */
0, /* tp_iternext */
0, /* tp_methods */
DiffEntry_members, /* tp_members */
0, /* tp_getset */
0, /* tp_base */
0, /* tp_dict */
0, /* tp_descr_get */
0, /* tp_descr_set */
0, /* tp_dictoffset */
0, /* tp_init */
0, /* tp_alloc */
0, /* tp_new */
};
PyObject *
DiffIter_iternext(DiffIter *self)
{
if (self->i < self->n)
return diff_get_patch_byindex(self->list, self->i++);
PyErr_SetNone(PyExc_StopIteration);
return NULL;
}
void
DiffIter_dealloc(DiffIter *self)
{
Py_CLEAR(self->list);
PyObject_Del(self);
}
PyDoc_STRVAR(DiffIter__doc__, "Diff iterator object.");
PyTypeObject DiffIterType = {
PyVarObject_HEAD_INIT(NULL, 0)
"_pygit2.DiffIter", /* tp_name */
sizeof(DiffIter), /* tp_basicsize */
0, /* tp_itemsize */
(destructor)DiffIter_dealloc, /* tp_dealloc */
0, /* tp_print */
0, /* tp_getattr */
0, /* tp_setattr */
0, /* tp_compare */
0, /* tp_repr */
0, /* tp_as_number */
0, /* tp_as_sequence */
0, /* tp_as_mapping */
0, /* tp_hash */
0, /* tp_call */
0, /* tp_str */
0, /* tp_getattro */
0, /* tp_setattro */
0, /* tp_as_buffer */
Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
DiffIter__doc__, /* tp_doc */
0, /* tp_traverse */
0, /* tp_clear */
0, /* tp_richcompare */
0, /* tp_weaklistoffset */
PyObject_SelfIter, /* tp_iter */
(iternextfunc) DiffIter_iternext, /* tp_iternext */
};
PyDoc_STRVAR(Diff_patch__doc__, "Patch."); PyDoc_STRVAR(Diff_patch__doc__, "Patch.");
PyObject * PyObject *
Diff_patch__get__(Diff *self) Diff_patch__get__(Diff *self)
{ {
PyObject *patch = PyBytes_FromString(""); const git_diff_delta* delta;
git_diff_patch* patch;
char* str = NULL, *buffer = NULL;
int err = 0;
size_t i, len, num, size;
PyObject *py_patch = NULL;
git_diff_print_patch(self->diff, &diff_print_cb, (void*) &patch); num = git_diff_num_deltas(self->list);
for (i = 0; i < num ; ++i) {
err = git_diff_get_patch(&patch, &delta, self->list, i);
return patch; if (err < 0 || (err = git_diff_patch_to_str(&str, patch)) < 0)
} goto error;
static int len = strlen(str) + 1;
Hunk_init(Hunk *self, PyObject *args, PyObject *kwds) size = (buffer == NULL) ? len : strlen(buffer) + len;
{ MALLOC(buffer, size, error);
self->header = NULL;
self->old_file = NULL; if (len == size)
self->old_start = 0; strcpy(buffer, str);
self->old_lines = 0; else
strcat(buffer, str);
self->new_file = NULL; FREE(str);
self->new_start = 0;
self->new_lines = 0;
self->old_oid = NULL;
self->new_oid = NULL;
self->data = PyList_New(0);
if (self->data == NULL) {
Py_XDECREF(self);
return -1;
} }
return 0; py_patch = PyUnicode_FromString(buffer);
error:
FREE(str);
FREE(buffer);
FREE_FUNC(patch, git_diff_patch_free);
return (err < 0) ? Error_set(err) : py_patch;
} }
static void static void
Hunk_dealloc(Hunk *self) Hunk_dealloc(Hunk *self)
{ {
if (self->header != NULL) { if (self->header != NULL) {
free(self->header); free((void*) self->header);
} }
if (self->new_file != NULL) { if (self->new_file != NULL) {
free(self->new_file); free((void*) self->new_file);
} }
if (self->old_file != NULL) { if (self->old_file != NULL) {
free(self->old_file); free((void*) self->old_file);
} }
Py_XDECREF(self->old_oid); Py_XDECREF(self->old_oid);
Py_XDECREF(self->new_oid); Py_XDECREF(self->new_oid);
@@ -289,12 +310,12 @@ PyMemberDef Hunk_members[] = {
MEMBER(Hunk, old_lines, T_INT, "Old lines."), MEMBER(Hunk, old_lines, T_INT, "Old lines."),
MEMBER(Hunk, old_mode, T_INT, "Old mode."), MEMBER(Hunk, old_mode, T_INT, "Old mode."),
MEMBER(Hunk, old_file, T_STRING, "Old file."), MEMBER(Hunk, old_file, T_STRING, "Old file."),
MEMBER(Hunk, old_oid, T_OBJECT, "Old oid."), MEMBER(Hunk, old_oid, T_STRING, "Old oid."),
MEMBER(Hunk, new_start, T_INT, "New start."), MEMBER(Hunk, new_start, T_INT, "New start."),
MEMBER(Hunk, new_lines, T_INT, "New lines."), MEMBER(Hunk, new_lines, T_INT, "New lines."),
MEMBER(Hunk, new_mode, T_INT, "New mode."), MEMBER(Hunk, new_mode, T_INT, "New mode."),
MEMBER(Hunk, new_file, T_STRING, "New file."), MEMBER(Hunk, new_file, T_STRING, "New file."),
MEMBER(Hunk, new_oid, T_OBJECT, "New oid."), MEMBER(Hunk, new_oid, T_STRING, "New oid."),
MEMBER(Hunk, data, T_OBJECT, "Data."), MEMBER(Hunk, data, T_OBJECT, "Data."),
{NULL} {NULL}
}; };
@@ -338,7 +359,7 @@ PyTypeObject HunkType = {
0, /* tp_descr_get */ 0, /* tp_descr_get */
0, /* tp_descr_set */ 0, /* tp_descr_set */
0, /* tp_dictoffset */ 0, /* tp_dictoffset */
(initproc)Hunk_init, /* tp_init */ 0, /* tp_init */
0, /* tp_alloc */ 0, /* tp_alloc */
0, /* tp_new */ 0, /* tp_new */
}; };
@@ -357,15 +378,14 @@ Diff_merge(Diff *self, PyObject *args)
if (!PyArg_ParseTuple(args, "O!", &DiffType, &py_diff)) if (!PyArg_ParseTuple(args, "O!", &DiffType, &py_diff))
return NULL; return NULL;
if (py_diff->repo->repo != self->repo->repo) if (py_diff->repo->repo != self->repo->repo)
return Error_set(GIT_ERROR); return Error_set(GIT_ERROR);
err = git_diff_merge(self->diff, py_diff->diff); err = git_diff_merge(self->list, py_diff->list);
if (err < 0) if (err < 0)
return Error_set(err); return Error_set(err);
Py_XDECREF(self->diff_changes);
self->diff_changes = NULL;
Py_RETURN_NONE; Py_RETURN_NONE;
} }
@@ -384,30 +404,61 @@ Diff_find_similar(Diff *self, PyObject *args)
if (!PyArg_ParseTuple(args, "|i", &opts.flags)) if (!PyArg_ParseTuple(args, "|i", &opts.flags))
return NULL; return NULL;
err = git_diff_find_similar(self->diff, &opts); err = git_diff_find_similar(self->list, &opts);
if (err < 0) if (err < 0)
return Error_set(err); return Error_set(err);
Py_XDECREF(self->diff_changes);
self->diff_changes = NULL;
Py_RETURN_NONE; Py_RETURN_NONE;
} }
PyObject *
Diff_iter(Diff *self)
{
DiffIter *iter;
iter = PyObject_New(DiffIter, &DiffIterType);
if (iter) {
Py_INCREF(self);
iter->list = self->list;
iter->i = 0;
iter->n = git_diff_num_deltas(self->list);
}
return (PyObject*)iter;
}
PyObject *
Diff_getitem(Diff *self, PyObject *value)
{
size_t i;
if (PyLong_Check(value) < 0)
return NULL;
i = PyLong_AsUnsignedLong(value);
return diff_get_patch_byindex(self->list, i);
}
static void static void
Diff_dealloc(Diff *self) Diff_dealloc(Diff *self)
{ {
git_diff_list_free(self->diff); git_diff_list_free(self->list);
Py_XDECREF(self->repo); Py_XDECREF(self->repo);
Py_XDECREF(self->diff_changes);
PyObject_Del(self); PyObject_Del(self);
} }
PyGetSetDef Diff_getseters[] = { PyGetSetDef Diff_getseters[] = {
GETTER(Diff, changes),
GETTER(Diff, patch), GETTER(Diff, patch),
{NULL} {NULL}
}; };
PyMappingMethods Diff_as_mapping = {
0, /* mp_length */
(binaryfunc)Diff_getitem, /* mp_subscript */
0, /* mp_ass_subscript */
};
static PyMethodDef Diff_methods[] = { static PyMethodDef Diff_methods[] = {
METHOD(Diff, merge, METH_VARARGS), METHOD(Diff, merge, METH_VARARGS),
METHOD(Diff, find_similar, METH_VARARGS), METHOD(Diff, find_similar, METH_VARARGS),
@@ -430,7 +481,7 @@ PyTypeObject DiffType = {
0, /* tp_repr */ 0, /* tp_repr */
0, /* tp_as_number */ 0, /* tp_as_number */
0, /* tp_as_sequence */ 0, /* tp_as_sequence */
0, /* tp_as_mapping */ &Diff_as_mapping, /* tp_as_mapping */
0, /* tp_hash */ 0, /* tp_hash */
0, /* tp_call */ 0, /* tp_call */
0, /* tp_str */ 0, /* tp_str */
@@ -443,7 +494,7 @@ PyTypeObject DiffType = {
0, /* tp_clear */ 0, /* tp_clear */
0, /* tp_richcompare */ 0, /* tp_richcompare */
0, /* tp_weaklistoffset */ 0, /* tp_weaklistoffset */
0, /* tp_iter */ (getiterfunc)Diff_iter, /* tp_iter */
0, /* tp_iternext */ 0, /* tp_iternext */
Diff_methods, /* tp_methods */ Diff_methods, /* tp_methods */
0, /* tp_members */ 0, /* tp_members */

View File

@@ -158,7 +158,7 @@ Index_diff(Index *self, PyObject *args)
if (py_diff) { if (py_diff) {
Py_INCREF(self->repo); Py_INCREF(self->repo);
py_diff->repo = self->repo; py_diff->repo = self->repo;
py_diff->diff = diff; py_diff->list = diff;
} }
return (PyObject*)py_diff; return (PyObject*)py_diff;

View File

@@ -41,6 +41,8 @@ extern PyTypeObject RepositoryType;
extern PyTypeObject ObjectType; extern PyTypeObject ObjectType;
extern PyTypeObject CommitType; extern PyTypeObject CommitType;
extern PyTypeObject DiffType; extern PyTypeObject DiffType;
extern PyTypeObject DiffIterType;
extern PyTypeObject DiffEntryType;
extern PyTypeObject HunkType; extern PyTypeObject HunkType;
extern PyTypeObject TreeType; extern PyTypeObject TreeType;
extern PyTypeObject TreeBuilderType; extern PyTypeObject TreeBuilderType;
@@ -197,6 +199,10 @@ moduleinit(PyObject* m)
if (PyType_Ready(&DiffType) < 0) if (PyType_Ready(&DiffType) < 0)
return NULL; return NULL;
if (PyType_Ready(&DiffIterType) < 0)
return NULL;
if (PyType_Ready(&DiffEntryType) < 0)
return NULL;
if (PyType_Ready(&HunkType) < 0) if (PyType_Ready(&HunkType) < 0)
return NULL; return NULL;
@@ -284,9 +290,9 @@ moduleinit(PyObject* m)
PyModule_AddIntConstant(m, "GIT_SORT_TOPOLOGICAL", GIT_SORT_TOPOLOGICAL); PyModule_AddIntConstant(m, "GIT_SORT_TOPOLOGICAL", GIT_SORT_TOPOLOGICAL);
PyModule_AddIntConstant(m, "GIT_SORT_TIME", GIT_SORT_TIME); PyModule_AddIntConstant(m, "GIT_SORT_TIME", GIT_SORT_TIME);
PyModule_AddIntConstant(m, "GIT_SORT_REVERSE", GIT_SORT_REVERSE); PyModule_AddIntConstant(m, "GIT_SORT_REVERSE", GIT_SORT_REVERSE);
PyModule_AddIntConstant(m, "GIT_REF_INVALID", GIT_REF_INVALID);
PyModule_AddIntConstant(m, "GIT_REF_OID", GIT_REF_OID); PyModule_AddIntConstant(m, "GIT_REF_OID", GIT_REF_OID);
PyModule_AddIntConstant(m, "GIT_REF_SYMBOLIC", GIT_REF_SYMBOLIC); PyModule_AddIntConstant(m, "GIT_REF_SYMBOLIC", GIT_REF_SYMBOLIC);
PyModule_AddIntConstant(m, "GIT_REF_PACKED", GIT_REF_PACKED);
PyModule_AddIntConstant(m, "GIT_REF_LISTALL", GIT_REF_LISTALL); PyModule_AddIntConstant(m, "GIT_REF_LISTALL", GIT_REF_LISTALL);
/* Git status flags */ /* Git status flags */
@@ -343,13 +349,6 @@ moduleinit(PyObject* m)
PyModule_AddIntConstant(m, "GIT_DIFF_FIND_AND_BREAK_REWRITES", PyModule_AddIntConstant(m, "GIT_DIFF_FIND_AND_BREAK_REWRITES",
GIT_DIFF_FIND_AND_BREAK_REWRITES); GIT_DIFF_FIND_AND_BREAK_REWRITES);
/* Flags for diffed files */
PyModule_AddIntConstant(m, "GIT_DIFF_FLAG_BINARY", GIT_DIFF_FLAG_BINARY);
PyModule_AddIntConstant(m, "GIT_DIFF_FLAG_NOT_BINARY",
GIT_DIFF_FLAG_NOT_BINARY);
PyModule_AddIntConstant(m, "GIT_DIFF_FLAG_VALID_OID",
GIT_DIFF_FLAG_VALID_OID);
/* Flags for diff deltas */ /* Flags for diff deltas */
PyModule_AddIntConstant(m, "GIT_DELTA_UNMODIFIED", GIT_DELTA_UNMODIFIED); PyModule_AddIntConstant(m, "GIT_DELTA_UNMODIFIED", GIT_DELTA_UNMODIFIED);
PyModule_AddIntConstant(m, "GIT_DELTA_ADDED", GIT_DELTA_ADDED); PyModule_AddIntConstant(m, "GIT_DELTA_ADDED", GIT_DELTA_ADDED);

View File

@@ -161,6 +161,7 @@ Reference_rename(Reference *self, PyObject *py_name)
{ {
char *c_name; char *c_name;
int err; int err;
git_reference *new_reference;
CHECK_REFERENCE(self); CHECK_REFERENCE(self);
@@ -170,33 +171,12 @@ Reference_rename(Reference *self, PyObject *py_name)
return NULL; return NULL;
/* Rename */ /* Rename */
err = git_reference_rename(self->reference, c_name, 0); err = git_reference_rename(&new_reference, self->reference, c_name, 0);
free(c_name); free(c_name);
if (err < 0) if (err < 0)
return Error_set(err); return Error_set(err);
Py_RETURN_NONE; self->reference = new_reference;
}
PyDoc_STRVAR(Reference_reload__doc__,
"reload()\n"
"\n"
"Reload the reference from the file-system.");
PyObject *
Reference_reload(Reference *self)
{
int err;
CHECK_REFERENCE(self);
err = git_reference_reload(self->reference);
if (err < 0) {
self->reference = NULL;
return Error_set(err);
}
Py_RETURN_NONE; Py_RETURN_NONE;
} }
@@ -214,13 +194,8 @@ Reference_resolve(Reference *self, PyObject *args)
CHECK_REFERENCE(self); CHECK_REFERENCE(self);
/* Direct: reload */ /* Direct: return myself */
if (git_reference_type(self->reference) == GIT_REF_OID) { if (git_reference_type(self->reference) == GIT_REF_OID) {
err = git_reference_reload(self->reference);
if (err < 0) {
self->reference = NULL;
return Error_set(err);
}
Py_INCREF(self); Py_INCREF(self);
return (PyObject *)self; return (PyObject *)self;
} }
@@ -263,6 +238,7 @@ Reference_target__set__(Reference *self, PyObject *py_name)
{ {
char *c_name; char *c_name;
int err; int err;
git_reference *new_ref;
CHECK_REFERENCE_INT(self); CHECK_REFERENCE_INT(self);
@@ -272,13 +248,14 @@ Reference_target__set__(Reference *self, PyObject *py_name)
return -1; return -1;
/* Set the new target */ /* Set the new target */
err = git_reference_symbolic_set_target(self->reference, c_name); err = git_reference_symbolic_set_target(&new_ref, self->reference, c_name);
free(c_name); free(c_name);
if (err < 0) { if (err < 0) {
Error_set(err); Error_set(err);
return -1; return -1;
} }
self->reference = new_ref;
return 0; return 0;
} }
@@ -320,6 +297,7 @@ Reference_oid__set__(Reference *self, PyObject *py_hex)
{ {
git_oid oid; git_oid oid;
int err; int err;
git_reference *new_ref;
CHECK_REFERENCE_INT(self); CHECK_REFERENCE_INT(self);
@@ -332,12 +310,13 @@ Reference_oid__set__(Reference *self, PyObject *py_hex)
} }
/* Set the oid */ /* Set the oid */
err = git_reference_set_target(self->reference, &oid); err = git_reference_set_target(&new_ref, self->reference, &oid);
if (err < 0) { if (err < 0) {
Error_set(err); Error_set(err);
return -1; return -1;
} }
self->reference = new_ref;
return 0; return 0;
} }
@@ -366,7 +345,7 @@ Reference_hex__get__(Reference *self)
PyDoc_STRVAR(Reference_type__doc__, PyDoc_STRVAR(Reference_type__doc__,
"Type (GIT_REF_OID, GIT_REF_SYMBOLIC or GIT_REF_PACKED)."); "Type (GIT_REF_OID or GIT_REF_SYMBOLIC).");
PyObject * PyObject *
Reference_type__get__(Reference *self) Reference_type__get__(Reference *self)
@@ -481,7 +460,6 @@ PyTypeObject RefLogEntryType = {
PyMethodDef Reference_methods[] = { PyMethodDef Reference_methods[] = {
METHOD(Reference, delete, METH_NOARGS), METHOD(Reference, delete, METH_NOARGS),
METHOD(Reference, rename, METH_O), METHOD(Reference, rename, METH_O),
METHOD(Reference, reload, METH_NOARGS),
METHOD(Reference, resolve, METH_NOARGS), METHOD(Reference, resolve, METH_NOARGS),
METHOD(Reference, log, METH_NOARGS), METHOD(Reference, log, METH_NOARGS),
{NULL} {NULL}

View File

@@ -902,24 +902,6 @@ Repository_git_reference_symbolic_create(Repository *self, PyObject *args,
} }
PyDoc_STRVAR(Repository_packall_references__doc__,
"packall_references()\n"
"\n"
"Pack all the loose references in the repository.");
PyObject *
Repository_packall_references(Repository *self, PyObject *args)
{
int err;
err = git_reference_packall(self->repo);
if (err < 0)
return Error_set(err);
Py_RETURN_NONE;
}
PyDoc_STRVAR(Repository_status__doc__, PyDoc_STRVAR(Repository_status__doc__,
"status() -> {str: int}\n" "status() -> {str: int}\n"
"\n" "\n"
@@ -1145,7 +1127,6 @@ PyMethodDef Repository_methods[] = {
METHOD(Repository, git_reference_symbolic_create, METH_VARARGS), METHOD(Repository, git_reference_symbolic_create, METH_VARARGS),
METHOD(Repository, listall_references, METH_VARARGS), METHOD(Repository, listall_references, METH_VARARGS),
METHOD(Repository, lookup_reference, METH_O), METHOD(Repository, lookup_reference, METH_O),
METHOD(Repository, packall_references, METH_NOARGS),
METHOD(Repository, revparse_single, METH_O), METHOD(Repository, revparse_single, METH_O),
METHOD(Repository, status, METH_NOARGS), METHOD(Repository, status, METH_NOARGS),
METHOD(Repository, status_file, METH_O), METHOD(Repository, status_file, METH_O),

View File

@@ -346,8 +346,7 @@ Tree_diff(Tree *self, PyObject *args)
if (py_diff) { if (py_diff) {
Py_INCREF(self->repo); Py_INCREF(self->repo);
py_diff->repo = self->repo; py_diff->repo = self->repo;
py_diff->diff = diff; py_diff->list = diff;
py_diff->diff_changes = NULL;
} }
return (PyObject*)py_diff; return (PyObject*)py_diff;

View File

@@ -1 +1 @@
056e626e51b1fc1ee2182800e399ed8d84c8f082 784855caf26449a1914d2cf62d12b9374d76ae78

View File

@@ -31,6 +31,7 @@ from __future__ import absolute_import
from __future__ import unicode_literals from __future__ import unicode_literals
import unittest import unittest
import pygit2 import pygit2
import itertools
from pygit2 import GIT_DIFF_INCLUDE_UNMODIFIED from pygit2 import GIT_DIFF_INCLUDE_UNMODIFIED
from . import utils from . import utils
@@ -40,8 +41,11 @@ COMMIT_SHA1_2 = 'c2792cfa289ae6321ecf2cd5806c2194b0fd070c'
COMMIT_SHA1_3 = '2cdae28389c059815e951d0bb9eed6533f61a46b' COMMIT_SHA1_3 = '2cdae28389c059815e951d0bb9eed6533f61a46b'
COMMIT_SHA1_4 = 'ccca47fbb26183e71a7a46d165299b84e2e6c0b3' COMMIT_SHA1_4 = 'ccca47fbb26183e71a7a46d165299b84e2e6c0b3'
COMMIT_SHA1_5 = '056e626e51b1fc1ee2182800e399ed8d84c8f082' COMMIT_SHA1_5 = '056e626e51b1fc1ee2182800e399ed8d84c8f082'
COMMIT_SHA1_6 = 'f5e5aa4e36ab0fe62ee1ccc6eb8f79b866863b87'
COMMIT_SHA1_7 = '784855caf26449a1914d2cf62d12b9374d76ae78'
PATCH = b"""diff --git a/a b/a
PATCH = """diff --git a/a b/a
index 7f129fd..af431f2 100644 index 7f129fd..af431f2 100644
--- a/a --- a/a
+++ b/a +++ b/a
@@ -86,16 +90,16 @@ class DiffDirtyTest(utils.DirtyRepoTestCase):
head = repo[repo.lookup_reference('HEAD').resolve().oid] head = repo[repo.lookup_reference('HEAD').resolve().oid]
diff = head.tree.diff(repo.index) diff = head.tree.diff(repo.index)
files = [x[1] for x in diff.changes['files']] files = [[x[0] for x in entry.files] for entry in diff]
self.assertEqual(DIFF_INDEX_EXPECTED, files) self.assertEqual(DIFF_INDEX_EXPECTED, list(itertools.chain(*files)))
def test_workdir_to_tree(self): def test_workdir_to_tree(self):
repo = self.repo repo = self.repo
head = repo[repo.lookup_reference('HEAD').resolve().oid] head = repo[repo.lookup_reference('HEAD').resolve().oid]
diff = head.tree.diff() diff = head.tree.diff()
files = [x[1] for x in diff.changes['files']] files = [[x[0] for x in entry.files] for entry in diff]
self.assertEqual(DIFF_WORKDIR_EXPECTED, files) self.assertEqual(DIFF_WORKDIR_EXPECTED, list(itertools.chain(*files)))
class DiffTest(utils.BareRepoTestCase): class DiffTest(utils.BareRepoTestCase):
@@ -109,8 +113,8 @@ class DiffTest(utils.BareRepoTestCase):
head = repo[repo.lookup_reference('HEAD').resolve().oid] head = repo[repo.lookup_reference('HEAD').resolve().oid]
diff = head.tree.diff(repo.index) diff = head.tree.diff(repo.index)
files = [x[0].split('/')[0] for x in diff.changes['files']] files = [[x[0].split('/')[0] for x in entry.files] for entry in diff]
self.assertEqual([x.name for x in head.tree], files) self.assertEqual([x.name for x in head.tree], list(itertools.chain(*files)))
def test_diff_tree(self): def test_diff_tree(self):
commit_a = self.repo[COMMIT_SHA1_1] commit_a = self.repo[COMMIT_SHA1_1]
@@ -121,10 +125,10 @@ class DiffTest(utils.BareRepoTestCase):
# self.assertIsNotNone is 2.7 only # self.assertIsNotNone is 2.7 only
self.assertTrue(diff is not None) self.assertTrue(diff is not None)
# self.assertIn is 2.7 only # self.assertIn is 2.7 only
self.assertTrue(('a', 'a', 3, 0) in diff.changes['files']) self.assertAny(lambda x: ('a', 'a', 3, 0) in x.files, diff)
self.assertEqual(2, len(diff.changes['hunks'])) self.assertEqual(2, sum(map(lambda x: len(x.hunks), diff)))
hunk = diff.changes['hunks'][0] hunk = diff[0].hunks[0]
self.assertEqual(hunk.old_start, 1) self.assertEqual(hunk.old_start, 1)
self.assertEqual(hunk.old_lines, 1) self.assertEqual(hunk.old_lines, 1)
self.assertEqual(hunk.new_start, 1) self.assertEqual(hunk.new_start, 1)
@@ -144,11 +148,11 @@ class DiffTest(utils.BareRepoTestCase):
pygit2.GIT_DIFF_IGNORE_WHITESPACE_EOL]: pygit2.GIT_DIFF_IGNORE_WHITESPACE_EOL]:
diff = commit_c.tree.diff(commit_d.tree, opt) diff = commit_c.tree.diff(commit_d.tree, opt)
self.assertTrue(diff is not None) self.assertTrue(diff is not None)
self.assertEqual(0, len(diff.changes.get('hunks', list()))) self.assertEqual(0, len(diff[0].hunks))
diff = commit_c.tree.diff(commit_d.tree) diff = commit_c.tree.diff(commit_d.tree)
self.assertTrue(diff is not None) self.assertTrue(diff is not None)
self.assertEqual(1, len(diff.changes.get('hunks', list()))) self.assertEqual(1, len(diff[0].hunks))
def test_diff_merge(self): def test_diff_merge(self):
commit_a = self.repo[COMMIT_SHA1_1] commit_a = self.repo[COMMIT_SHA1_1]
@@ -164,15 +168,15 @@ class DiffTest(utils.BareRepoTestCase):
self.assertTrue(diff_c is not None) self.assertTrue(diff_c is not None)
# assertIn / assertNotIn are 2.7 only # assertIn / assertNotIn are 2.7 only
self.assertTrue(('b', 'b', 3, 0) not in diff_b.changes['files']) self.assertAll(lambda x:('b', 'b', 3, 0) not in x.files, diff_b)
self.assertTrue(('b', 'b', 3, 0) in diff_c.changes['files']) self.assertAny(lambda x:('b', 'b', 3, 0) in x.files, diff_c)
diff_b.merge(diff_c) diff_b.merge(diff_c)
# assertIn is 2.7 only # assertIn is 2.7 only
self.assertTrue(('b', 'b', 3, 0) in diff_b.changes['files']) self.assertAny(lambda x:('b', 'b', 3, 0) in x.files, diff_b)
hunk = diff_b.changes['hunks'][1] hunk = diff_b[1].hunks[0]
self.assertEqual(hunk.old_start, 1) self.assertEqual(hunk.old_start, 1)
self.assertEqual(hunk.old_lines, 1) self.assertEqual(hunk.old_lines, 1)
self.assertEqual(hunk.new_start, 1) self.assertEqual(hunk.new_start, 1)
@@ -196,28 +200,29 @@ class DiffTest(utils.BareRepoTestCase):
commit_b = self.repo[COMMIT_SHA1_2] commit_b = self.repo[COMMIT_SHA1_2]
diff = commit_a.tree.diff(commit_b.tree) diff = commit_a.tree.diff(commit_b.tree)
self.assertEqual(diff.changes['hunks'][0].header, "@@ -1 +1 @@\n") self.assertEqual(diff[0].hunks[0].header, "@@ -1 +1 @@\n")
def test_diff_oids(self): def test_diff_oids(self):
commit_a = self.repo[COMMIT_SHA1_1] commit_a = self.repo[COMMIT_SHA1_1]
commit_b = self.repo[COMMIT_SHA1_2] commit_b = self.repo[COMMIT_SHA1_2]
diff = commit_a.tree.diff(commit_b.tree) diff = commit_a.tree.diff(commit_b.tree)
hunk = diff.changes['hunks'][0] hunk = diff[0].hunks[0]
self.assertEqual(hunk.old_oid, self.assertEqual(hunk.old_oid,
'7f129fd57e31e935c6d60a0c794efe4e6927664b') '7f129fd57e31e935c6d60a0c794efe4e6927664b')
self.assertEqual(hunk.new_oid, self.assertEqual(hunk.new_oid,
'af431f20fc541ed6d5afede3e2dc7160f6f01f16') 'af431f20fc541ed6d5afede3e2dc7160f6f01f16')
def test_find_similar(self): def test_find_similar(self):
commit_a = self.repo[COMMIT_SHA1_4] commit_a = self.repo[COMMIT_SHA1_6]
commit_b = self.repo[COMMIT_SHA1_5] commit_b = self.repo[COMMIT_SHA1_7]
#~ Must pass GIT_DIFF_INCLUDE_UNMODIFIED if you expect to emulate #~ Must pass GIT_DIFF_INCLUDE_UNMODIFIED if you expect to emulate
#~ --find-copies-harder during rename transformion... #~ --find-copies-harder during rename transformion...
diff = commit_a.tree.diff(commit_b.tree, GIT_DIFF_INCLUDE_UNMODIFIED) diff = commit_a.tree.diff(commit_b.tree, GIT_DIFF_INCLUDE_UNMODIFIED)
self.assertFalse(('a', 'a.copy', 5, 100) in diff.changes['files']) entry = ('lorem', 'ipsum', pygit2.GIT_DELTA_RENAMED, 100)
diff.find_similar(pygit2.GIT_DIFF_FIND_COPIES_FROM_UNMODIFIED) self.assertAll(lambda x: entry not in x.files, diff)
self.assertTrue(('a', 'a.copy', 5, 100) in diff.changes['files']) diff.find_similar()
self.assertAny(lambda x: entry in x.files, diff)
if __name__ == '__main__': if __name__ == '__main__':
unittest.main() unittest.main()

View File

@@ -142,16 +142,16 @@ class ReferencesTest(utils.RepoTestCase):
self.assertEqual(reference.name, 'refs/tags/version2') self.assertEqual(reference.name, 'refs/tags/version2')
def test_reload(self): # def test_reload(self):
name = 'refs/tags/version1' # name = 'refs/tags/version1'
repo = self.repo # repo = self.repo
ref = repo.create_reference(name, "refs/heads/master", symbolic=True) # ref = repo.create_reference(name, "refs/heads/master", symbolic=True)
ref2 = repo.lookup_reference(name) # ref2 = repo.lookup_reference(name)
ref.delete() # ref.delete()
self.assertEqual(ref2.name, name) # self.assertEqual(ref2.name, name)
self.assertRaises(KeyError, ref2.reload) # self.assertRaises(KeyError, ref2.reload)
self.assertRaises(GitError, getattr, ref2, 'name') # self.assertRaises(GitError, getattr, ref2, 'name')
def test_reference_resolve(self): def test_reference_resolve(self):
@@ -209,8 +209,8 @@ class ReferencesTest(utils.RepoTestCase):
self.assertEqual(reference.target, 'refs/heads/master') self.assertEqual(reference.target, 'refs/heads/master')
def test_packall_references(self): # def test_packall_references(self):
self.repo.packall_references() # self.repo.packall_references()
if __name__ == '__main__': if __name__ == '__main__':

View File

@@ -35,8 +35,8 @@ REMOTE_NAME = 'origin'
REMOTE_URL = 'git://github.com/libgit2/pygit2.git' REMOTE_URL = 'git://github.com/libgit2/pygit2.git'
REMOTE_FETCHSPEC_SRC = 'refs/heads/*' REMOTE_FETCHSPEC_SRC = 'refs/heads/*'
REMOTE_FETCHSPEC_DST = 'refs/remotes/origin/*' REMOTE_FETCHSPEC_DST = 'refs/remotes/origin/*'
REMOTE_REPO_OBJECTS = 19 REMOTE_REPO_OBJECTS = 24
REMOTE_REPO_BYTES = 1586 REMOTE_REPO_BYTES = 2253
class RepositoryTest(utils.RepoTestCase): class RepositoryTest(utils.RepoTestCase):
def test_remote_create(self): def test_remote_create(self):

View File

@@ -42,8 +42,8 @@ import pygit2
from . import utils from . import utils
HEAD_SHA = '056e626e51b1fc1ee2182800e399ed8d84c8f082' HEAD_SHA = '784855caf26449a1914d2cf62d12b9374d76ae78'
PARENT_SHA = 'ccca47fbb26183e71a7a46d165299b84e2e6c0b3' # HEAD^ PARENT_SHA = 'f5e5aa4e36ab0fe62ee1ccc6eb8f79b866863b87' # HEAD^
A_HEX_SHA = 'af431f20fc541ed6d5afede3e2dc7160f6f01f16' A_HEX_SHA = 'af431f20fc541ed6d5afede3e2dc7160f6f01f16'
A_BIN_SHA = binascii.unhexlify(A_HEX_SHA.encode('ascii')) A_BIN_SHA = binascii.unhexlify(A_HEX_SHA.encode('ascii'))

View File

@@ -83,6 +83,11 @@ class NoRepoTestCase(unittest.TestCase):
except: except:
self.assertEqual(exc_class, sys.exc_info()[0]) self.assertEqual(exc_class, sys.exc_info()[0])
def assertAll(self, func, entries):
return self.assertTrue(all(func(x) for x in entries))
def assertAny(self, func, entries):
return self.assertTrue(any(func(x) for x in entries))
def assertRaisesWithArg(self, exc_class, arg, func, *args, **kwargs): def assertRaisesWithArg(self, exc_class, arg, func, *args, **kwargs):
try: try: