[#5230] Only post event when clone fails inside `clone` task
diff --git a/Allura/allura/tasks/repo_tasks.py b/Allura/allura/tasks/repo_tasks.py
index 369b3f9..ed1cabd 100644
--- a/Allura/allura/tasks/repo_tasks.py
+++ b/Allura/allura/tasks/repo_tasks.py
@@ -1,7 +1,7 @@
 import shutil
 import logging
 
-from pylons import c
+from pylons import c, g
 
 from allura.lib.decorators import task
 from allura.lib.repository import RepositoryApp
@@ -18,14 +18,18 @@
 @task
 def clone(cloned_from_path, cloned_from_name, cloned_from_url):
     from allura import model as M
-    c.app.repo.init_as_clone(
-        cloned_from_path,
-        cloned_from_name,
-        cloned_from_url)
-    M.Notification.post_user(
-        c.user, c.app.repo, 'created',
-        text='Repository %s/%s created' % (
-            c.project.shortname, c.app.config.options.mount_point))
+    try:
+        c.app.repo.init_as_clone(
+            cloned_from_path,
+            cloned_from_name,
+            cloned_from_url)
+        M.Notification.post_user(
+            c.user, c.app.repo, 'created',
+            text='Repository %s/%s created' % (
+                c.project.shortname, c.app.config.options.mount_point))
+    except Exception, e:
+        source_url = cloned_from_path or cloned_from_url
+        g.post_event('repo_clone_task_failed', source_url, str(e))
 
 @task
 def reclone(*args, **kwargs):
diff --git a/Allura/allura/tests/test_tasks.py b/Allura/allura/tests/test_tasks.py
index edb82f1..334d08c 100644
--- a/Allura/allura/tests/test_tasks.py
+++ b/Allura/allura/tests/test_tasks.py
@@ -23,9 +23,25 @@
 from allura.tasks import index_tasks
 from allura.tasks import mail_tasks
 from allura.tasks import notification_tasks
+from allura.tasks import repo_tasks
 from allura.tests import decorators as td
 from allura.lib.decorators import event_handler, task
 
+
+class TestRepoTasks(unittest.TestCase):
+    @mock.patch('allura.tasks.repo_tasks.c.app')
+    @mock.patch('allura.tasks.repo_tasks.g.post_event')
+    def test_clone_posts_event_on_failure(self, post_event, app):
+        fake_source_url = 'fake_source_url'
+        fake_traceback = 'fake_traceback'
+        app.repo.init_as_clone.side_effect = Exception(fake_traceback)
+        try:
+            repo_tasks.clone(None, None, fake_source_url)
+        except:
+            pass
+        post_event.assert_any_call('repo_clone_task_failed', fake_source_url, fake_traceback)
+
+
 class TestEventTasks(unittest.TestCase):
 
     def setUp(self):
diff --git a/ForgeGit/forgegit/model/git_repo.py b/ForgeGit/forgegit/model/git_repo.py
index d58b02d..56b7e80 100644
--- a/ForgeGit/forgegit/model/git_repo.py
+++ b/ForgeGit/forgegit/model/git_repo.py
@@ -108,10 +108,9 @@
             self.__dict__['_git'] = repo
             self._setup_special_files(source_url)
         except:
-            g.post_event('repo_clone_failed', source_url, traceback.format_exc())
             self._repo.status = 'ready'
             session(self._repo).flush(self._repo)
-            raise
+            raise Exception(traceback.format_exc())
         log.info('... %r cloned', self._repo)
         g.post_event('repo_cloned', source_url)
         self._repo.refresh(notify=False)
diff --git a/ForgeGit/forgegit/tests/model/test_repository.py b/ForgeGit/forgegit/tests/model/test_repository.py
index 756a36f..e31a82d 100644
--- a/ForgeGit/forgegit/tests/model/test_repository.py
+++ b/ForgeGit/forgegit/tests/model/test_repository.py
@@ -174,24 +174,6 @@
         self.assertIn('exec $DIR/post-receive-user\n', c)
         shutil.rmtree(dirname)
 
-    @mock.patch('forgegit.model.git_repo.g.post_event')
-    @mock.patch('forgegit.model.git_repo.traceback')
-    def test_clone_from_posts_event_on_failure(self, traceback, post_event):
-        fake_source_url = 'fake_source_url'
-        fake_traceback = 'fake_traceback'
-        traceback.format_exc.return_value = fake_traceback
-        repo = GM.Repository(
-            name='testgit.git',
-            fs_path='/tmp/',
-            url_path = '/test/',
-            tool = 'git',
-            status = 'creating')
-        try:
-            repo._impl.clone_from(fake_source_url)
-        except:
-            pass
-        post_event.assert_any_call('repo_clone_failed', fake_source_url, fake_traceback)
-
     def test_index(self):
         i = self.repo.index()
         assert i['type_s'] == 'Git Repository', i
diff --git a/ForgeHg/forgehg/model/hg.py b/ForgeHg/forgehg/model/hg.py
index 7e00971..6aed90a 100644
--- a/ForgeHg/forgehg/model/hg.py
+++ b/ForgeHg/forgehg/model/hg.py
@@ -95,10 +95,9 @@
             self.__dict__['_hg'] = repo
             self._setup_special_files(source_url)
         except:
-            g.post_event('repo_clone_failed', source_url, traceback.format_exc())
-            self._repo.status = 'raise'
+            self._repo.status = 'ready'
             session(self._repo).flush(self._repo)
-            raise
+            raise Exception(traceback.format_exc())
         log.info('... %r cloned', self._repo)
         g.post_event('repo_cloned', source_url)
         self._repo.refresh(notify=False)
diff --git a/ForgeHg/forgehg/tests/model/test_repository.py b/ForgeHg/forgehg/tests/model/test_repository.py
index ddedac2..99eb814 100644
--- a/ForgeHg/forgehg/tests/model/test_repository.py
+++ b/ForgeHg/forgehg/tests/model/test_repository.py
@@ -173,24 +173,6 @@
         assert not os.path.exists('/tmp/testrepo.hg/.hg/undo.branch')
         shutil.rmtree(dirname)
 
-    @mock.patch('forgehg.model.hg.g.post_event')
-    @mock.patch('forgehg.model.hg.traceback')
-    def test_clone_from_posts_event_on_failure(self, traceback, post_event):
-        fake_source_url = 'fake_source_url'
-        fake_traceback = 'fake_traceback'
-        traceback.format_exc.return_value = fake_traceback
-        repo = HM.Repository(
-            name='testrepo.hg',
-            fs_path='/tmp/',
-            url_path = '/test/',
-            tool = 'hg',
-            status = 'creating')
-        try:
-            repo._impl.clone_from(fake_source_url)
-        except:
-            pass
-        post_event.assert_any_call('repo_clone_failed', fake_source_url, fake_traceback)
-
     def test_index(self):
         i = self.repo.index()
         assert i['type_s'] == 'Hg Repository', i
diff --git a/ForgeSVN/forgesvn/model/svn.py b/ForgeSVN/forgesvn/model/svn.py
index 85b4670..eca7229 100644
--- a/ForgeSVN/forgesvn/model/svn.py
+++ b/ForgeSVN/forgesvn/model/svn.py
@@ -169,7 +169,6 @@
             p = Popen(cmd, stdin=PIPE, stdout=PIPE, stderr=PIPE)
             stdout, stderr = p.communicate(input='p\n')
             if p.returncode != 0:
-                g.post_event('repo_clone_failed', source_url, stderr)
                 self._repo.status = 'ready'
                 session(self._repo).flush(self._repo)
                 raise SVNCalledProcessError(cmd, p.returncode, stdout, stderr)
diff --git a/ForgeSVN/forgesvn/tests/model/test_repository.py b/ForgeSVN/forgesvn/tests/model/test_repository.py
index d317b70..d4385fc 100644
--- a/ForgeSVN/forgesvn/tests/model/test_repository.py
+++ b/ForgeSVN/forgesvn/tests/model/test_repository.py
@@ -174,26 +174,6 @@
         self.assertIn('exec $DIR/post-commit-user "$@"\n', c)
         shutil.rmtree(dirname)
 
-    @mock.patch('forgesvn.model.svn.g.post_event')
-    @mock.patch('forgesvn.model.svn.Popen')
-    def test_clone_from_posts_event_on_failure(self, popen, post_event):
-        fake_source_url = 'fake_source_url'
-        fake_traceback = 'fake_traceback'
-        popen_mock = mock.Mock(returncode=1)
-        popen_mock.communicate.return_value = '', fake_traceback
-        popen.return_value = popen_mock
-        repo = SM.Repository(
-            name='testsvn',
-            fs_path='/tmp/',
-            url_path = '/test/',
-            tool = 'svn',
-            status = 'creating')
-        try:
-            repo._impl.clone_from(fake_source_url)
-        except:
-            pass
-        post_event.assert_any_call('repo_clone_failed', fake_source_url, fake_traceback)
-
     def test_index(self):
         i = self.repo.index()
         assert i['type_s'] == 'SVN Repository', i