From 1c097a146a6d67ec759d574d9f83b2b0ef7300d0 Mon Sep 17 00:00:00 2001 From: Chase Sterling Date: Sat, 9 Jul 2016 12:56:26 -0400 Subject: [PATCH 1/5] Remove gittle dependency and use dulwich directly --- realms/modules/wiki/models.py | 62 +++++++++++++---------------------- realms/modules/wiki/views.py | 1 - setup.py | 2 +- 3 files changed, 24 insertions(+), 41 deletions(-) diff --git a/realms/modules/wiki/models.py b/realms/modules/wiki/models.py index 318b7ae..e23632a 100644 --- a/realms/modules/wiki/models.py +++ b/realms/modules/wiki/models.py @@ -2,11 +2,9 @@ import os import posixpath import re import ghdiff -import gittle.utils import yaml -from gittle import Gittle from dulwich.object_store import tree_lookup_path -from dulwich.repo import NotGitRepository +from dulwich.repo import Repo, NotGitRepository from realms.lib.util import cname_to_filename, filename_to_cname from realms import cache from realms.lib.hook import HookMixin @@ -23,17 +21,13 @@ class Wiki(HookMixin): default_committer_name = 'Anon' default_committer_email = 'anon@anon.anon' index_page = 'home' - gittle = None repo = None def __init__(self, path): try: - self.gittle = Gittle(path) + self.repo = Repo(path) except NotGitRepository: - self.gittle = Gittle.init(path) - - # Dulwich repo - self.repo = self.gittle.repo + self.repo = Repo.init(path, mkdir=True) self.path = path @@ -46,20 +40,20 @@ class Wiki(HookMixin): :param name: Committer name :param email: Committer email :param message: Commit message - :param files: list of file names that should be committed + :param files: list of file names that will be staged for commit :return: """ - # Dulwich and gittle seem to want us to encode ourselves at the moment. see #152 if isinstance(name, unicode): name = name.encode('utf-8') if isinstance(email, unicode): email = email.encode('utf-8') if isinstance(message, unicode): message = message.encode('utf-8') - return self.gittle.commit(name=name, - email=email, - message=message, - files=files) + author = committer = "%s <%s>" % (name, email) + self.repo.stage(files) + return self.repo.do_commit(message=message, + committer=committer, + author=author) def get_page(self, name, sha='HEAD'): """Get page data, partials, commit info. @@ -104,7 +98,8 @@ class WikiPage(HookMixin): if cached: return cached - data = self.wiki.gittle.get_commit_files(self.sha, paths=[self.filename]).get(self.filename).get('data') + mode, sha = tree_lookup_path(self.wiki.repo.get_object, self.wiki.repo[self.sha].tree, self.filename) + data = self.wiki.repo[sha].data cache.set(cache_key, data) return data @@ -126,20 +121,20 @@ class WikiPage(HookMixin): :return: list -- List of dicts """ - if not len(self.wiki.repo.open_index()): - # Index is empty, no commits - return [] - versions = [] - walker = self.wiki.repo.get_walker(paths=[self.filename], max_entries=limit) + try: + walker = self.wiki.repo.get_walker(paths=[self.filename], max_entries=limit, follow=True) + except KeyError: + # We don't have a head, no commits + return [] + for entry in walker: change_type = None for change in entry.changes(): - if change.old.path == self.filename: - change_type = change.type - elif change.new.path == self.filename: - change_type = change.type + # Changes should already be filtered to only the one affecting our file + change_type = change.type + break author_name, author_email = entry.commit.author.rstrip('>').split('<') versions.append(dict( author=author_name.strip(), @@ -211,9 +206,7 @@ class WikiPage(HookMixin): if not message: message = "Deleted %s" % self.name - # gittle.rm won't actually remove the file, have to do it ourselves os.remove(os.path.join(self.wiki.path, self.filename)) - self.wiki.gittle.rm(self.filename) commit = self.wiki.commit(name=username, email=email, message=message, @@ -232,7 +225,7 @@ class WikiPage(HookMixin): """ assert self.sha == 'HEAD' old_filename, new_filename = self.filename, cname_to_filename(new_name) - if old_filename not in self.wiki.gittle.index: + if old_filename not in self.wiki.repo.open_index(): # old doesn't exist return None elif old_filename == new_filename: @@ -247,10 +240,6 @@ class WikiPage(HookMixin): message = "Moved %s to %s" % (self.name, new_name) os.rename(os.path.join(self.wiki.path, old_filename), os.path.join(self.wiki.path, new_filename)) - - self.wiki.gittle.add(new_filename) - self.wiki.gittle.rm(old_filename) - commit = self.wiki.commit(name=username, email=email, message=message, @@ -264,12 +253,11 @@ class WikiPage(HookMixin): return commit - def write(self, content, message=None, create=False, username=None, email=None): + def write(self, content, message=None, username=None, email=None): """Write page to git repo :param content: Content of page. :param message: Commit message. - :param create: Perform git add operation? :param username: Commit Name. :param email: Commit Email. :return: Git commit sha1. @@ -283,9 +271,6 @@ class WikiPage(HookMixin): with open(self.wiki.path + "/" + self.filename, 'w') as f: f.write(content) - if create: - self.wiki.gittle.add(self.filename) - if not message: message = "Updated %s" % self.name @@ -315,8 +300,7 @@ class WikiPage(HookMixin): raise PageNotFound('Commit not found') if not message: - commit_info = gittle.utils.git.commit_info(self.wiki.gittle[commit_sha.encode('latin-1')]) - message = commit_info['message'] + message = "Revert '%s' to %s" % (self.name, commit_sha[:7]) return self.write(new_page.data, message=message, username=username, email=email) diff --git a/realms/modules/wiki/views.py b/realms/modules/wiki/views.py index 40571b2..d9e7fab 100644 --- a/realms/modules/wiki/views.py +++ b/realms/modules/wiki/views.py @@ -168,7 +168,6 @@ def page_write(name): sha = g.current_wiki.get_page(cname).write(request.form['content'], message=request.form['message'], - create=True, username=current_user.username, email=current_user.email) diff --git a/setup.py b/setup.py index 82eada6..50ecce4 100644 --- a/setup.py +++ b/setup.py @@ -35,10 +35,10 @@ setup(name='realms-wiki', 'bcrypt==1.0.2', 'beautifulsoup4==4.3.2', 'click==3.3', + 'dulwich==0.14.1', 'flask-ldap-login==0.3.0', 'gevent==1.0.2', 'ghdiff==0.4', - 'gittle==0.5.0', 'gunicorn==19.3', 'itsdangerous==0.24', 'markdown2==2.3.1', From 2d3de77bf61ec6e0571006a893f956196d2b3e5b Mon Sep 17 00:00:00 2001 From: Chase Sterling Date: Wed, 13 Jul 2016 22:47:24 -0400 Subject: [PATCH 2/5] Use github's anonymous email standin when github auth user has email as private --- realms/modules/auth/oauth/models.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/realms/modules/auth/oauth/models.py b/realms/modules/auth/oauth/models.py index 72f0470..d7f7680 100644 --- a/realms/modules/auth/oauth/models.py +++ b/realms/modules/auth/oauth/models.py @@ -40,7 +40,7 @@ providers = { 'field_map': { 'id': 'id', 'username': 'login', - 'email': 'email' + 'email': lambda(data): data.get('email') or data['login'] + '@users.noreply.github.com' }, 'token_name': 'access_token' }, @@ -118,6 +118,8 @@ class User(BaseUser): def get_value(d, key): if isinstance(key, basestring): return d.get(key) + elif callable(key): + return key(d) # key should be list here val = d.get(key.pop(0)) if len(key) == 0: From d6800f9c4ed25de8265a7c45d597024ef36556dc Mon Sep 17 00:00:00 2001 From: Chase Sterling Date: Mon, 25 Jul 2016 21:50:49 -0400 Subject: [PATCH 3/5] Update flask-sqlalchemy connection format link. fix #165 --- realms/config/__init__.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/realms/config/__init__.py b/realms/config/__init__.py index 8a3f0b0..4150a3d 100644 --- a/realms/config/__init__.py +++ b/realms/config/__init__.py @@ -23,7 +23,7 @@ class Config(object): BASE_URL = 'http://localhost' SITE_TITLE = "Realms" - # https://pythonhosted.org/Flask-SQLAlchemy/config.html#connection-uri-format + # http://flask-sqlalchemy.pocoo.org/config/#connection-uri-format DB_URI = 'sqlite:////tmp/wiki.db' # DB_URI = 'mysql://scott:tiger@localhost/mydatabase' # DB_URI = 'postgresql://scott:tiger@localhost/mydatabase' From 2a8bf2c511ecd5d3fb6e1c138a5b1e3d1f32f0e9 Mon Sep 17 00:00:00 2001 From: Chase Sterling Date: Mon, 1 Aug 2016 11:25:56 -0400 Subject: [PATCH 4/5] Fix crash with docker setting read only config val. --- docker/Dockerfile | 1 - 1 file changed, 1 deletion(-) diff --git a/docker/Dockerfile b/docker/Dockerfile index f805e2d..3a5ef95 100644 --- a/docker/Dockerfile +++ b/docker/Dockerfile @@ -28,7 +28,6 @@ ENV GEVENT_RESOLVER=ares ENV REALMS_ENV=docker ENV REALMS_WIKI_PATH=/home/wiki/data/repo ENV REALMS_DB_URI='sqlite:////home/wiki/data/wiki.db' -ENV REALMS_SQLALCHEMY_DATABASE_URI=${REALMS_DB_URI} RUN mkdir /home/wiki/data && touch /home/wiki/data/.a VOLUME /home/wiki/data From 241d763937b845dc1e99fc5d593bb22bc0cb80ae Mon Sep 17 00:00:00 2001 From: Matthew Scragg Date: Wed, 3 Aug 2016 11:53:29 -0500 Subject: [PATCH 5/5] version: 0.8.1 --- realms/version.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/realms/version.py b/realms/version.py index 32a90a3..ef72cc0 100644 --- a/realms/version.py +++ b/realms/version.py @@ -1 +1 @@ -__version__ = '0.8.0' +__version__ = '0.8.1'