diff --git a/kwalitee/cli.py b/kwalitee/cli.py
index 80512166350249a43a9fa1ba0c9ddb3ced06dad3..f76d7e2ba61349949f1fca3d7aee5b9ba2fd2460 100644
--- a/kwalitee/cli.py
+++ b/kwalitee/cli.py
@@ -9,6 +9,14 @@ from .repo import Repo
 
 LOG = getLogger('kwalitee.cli')
 
+def _check_cloned(ctx):
+    uncloned = []
+    for repo in ctx.repos:
+        if not repo.is_cloned():
+            uncloned.append(repo)
+    if uncloned:
+        raise Exception("Some repos not yet cloned: %s" % [str(r) for r in uncloned])
+
 class CliCtx():
     def __init__(self, config_file):
         with open(config_file, 'r') as f_config_file:
@@ -23,6 +31,31 @@ pass_ctx = click.make_pass_decorator(CliCtx)
 def cli(ctx, config_file, **kwargs): # pylint: disable=unused-argument
     ctx.obj = CliCtx(config_file)
 
+@cli.command('clone', help='''
+
+        Clone all repos
+''')
+@pass_ctx
+def clone_all(ctx):
+    for repo in ctx.repos:
+        if repo.is_cloned():
+            LOG.info("Already cloned %s" % repo)
+        else:
+            LOG.info("Cloning %s" % repo)
+            repo.clone()
+
+@cli.command('pull', help='''
+
+        Pull all repos
+''')
+@pass_ctx
+def pull_all(ctx):
+    _check_cloned(ctx)
+    for repo in ctx.repos:
+        LOG.info("Pulling %s" % repo)
+        repo.pull()
+
+
 @cli.command('json', help='''
 
     Generate JSON
@@ -38,6 +71,7 @@ def generate_json(ctx, full, **kwargs):
     if full:
         for k in kwargs:
             kwargs[k] = True
+    _check_cloned(ctx)
     for repo in ctx.repos:
         LOG.info("# Assessing %s" % repo.name)
         repo.clone()
diff --git a/kwalitee/repo.py b/kwalitee/repo.py
index 1cd08cb3a23cc143efc7dee6d92c38c26fba32e1..1d055ea7c2314db756b2213106ef976dba1c9b25 100644
--- a/kwalitee/repo.py
+++ b/kwalitee/repo.py
@@ -15,8 +15,18 @@ class Repo():
         self.name = Path(url).name
         self.path = Path(self.config['repodir'], self.name)
 
+    def __str__(self):
+        return '<Repo %s @ %s>' % (self.url, self.path)
+
+    def is_cloned(self):
+        return self.path.is_dir()
+
+    def pull(self):
+        with pushd_popd(self.path):
+            self._run('git pull origin master')
+
     def clone(self):
-        if self.path.is_dir():
+        if self.is_cloned():
             LOG.debug("Already cloned: %s" % self.path)
             return
         with pushd_popd(self.config['repodir']):