You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@allura.apache.org by di...@apache.org on 2022/09/23 18:43:31 UTC

[allura] 06/10: [#8455] ran nose2pytest on Forge* and AlluraTest modules

This is an automated email from the ASF dual-hosted git repository.

dill0wn pushed a commit to branch dw/8455-part2
in repository https://gitbox.apache.org/repos/asf/allura.git

commit 2ae7e7c8be7b1b0089511de3c153e6daa87f4d33
Author: Dillon Walls <di...@slashdotmedia.com>
AuthorDate: Fri Sep 16 13:33:22 2022 +0000

    [#8455] ran nose2pytest on Forge* and AlluraTest modules
---
 Allura/allura/tests/functional/test_admin.py       |   2 +-
 Allura/allura/tests/functional/test_auth.py        |   2 +-
 Allura/allura/tests/functional/test_discuss.py     |   2 +-
 Allura/allura/tests/functional/test_feeds.py       |   2 +-
 Allura/allura/tests/functional/test_gravatar.py    |   2 +-
 Allura/allura/tests/functional/test_home.py        |   2 +-
 Allura/allura/tests/functional/test_nav.py         |   2 +-
 .../allura/tests/functional/test_neighborhood.py   |   2 +-
 Allura/allura/tests/functional/test_newforge.py    |   2 +-
 .../tests/functional/test_personal_dashboard.py    |   2 +-
 Allura/allura/tests/functional/test_rest.py        |   2 +-
 Allura/allura/tests/functional/test_root.py        |   2 +-
 Allura/allura/tests/functional/test_search.py      |   2 +-
 Allura/allura/tests/functional/test_site_admin.py  |   2 +-
 Allura/allura/tests/functional/test_static.py      |   2 +-
 Allura/allura/tests/functional/test_subscriber.py  |   2 +-
 Allura/allura/tests/functional/test_tool_list.py   |   2 +-
 .../allura/tests/functional/test_trovecategory.py  |   2 +-
 .../allura/tests/functional/test_user_profile.py   |   2 +-
 Allura/allura/tests/model/test_auth.py             |   2 +-
 Allura/allura/tests/model/test_filesystem.py       |   2 +-
 Allura/allura/tests/model/test_notification.py     |   2 +-
 Allura/allura/tests/model/test_repo.py             |   2 +-
 Allura/allura/tests/model/test_timeline.py         |   2 +-
 .../tests/scripts/test_create_sitemap_files.py     |   2 +-
 .../allura/tests/scripts/test_delete_projects.py   |   2 +-
 Allura/allura/tests/scripts/test_misc_scripts.py   |   2 +-
 Allura/allura/tests/scripts/test_reindexes.py      |   2 +-
 .../tests/templates/jinja_master/test_lib.py       |   2 +-
 Allura/allura/tests/test_app.py                    |   2 +-
 Allura/allura/tests/test_commands.py               |   2 +-
 Allura/allura/tests/test_decorators.py             |   2 +-
 Allura/allura/tests/test_diff.py                   |   2 +-
 Allura/allura/tests/test_dispatch.py               |   2 +-
 Allura/allura/tests/test_globals.py                |   2 +-
 Allura/allura/tests/test_helpers.py                |   2 +-
 Allura/allura/tests/test_mail_util.py              |   2 +-
 Allura/allura/tests/test_markdown.py               |   2 +-
 Allura/allura/tests/test_middlewares.py            |   2 +-
 Allura/allura/tests/test_multifactor.py            |   2 +-
 Allura/allura/tests/test_plugin.py                 |   2 +-
 Allura/allura/tests/test_scripttask.py             |   2 +-
 Allura/allura/tests/test_security.py               |   2 +-
 Allura/allura/tests/test_tasks.py                  |   2 +-
 Allura/allura/tests/test_utils.py                  |   2 +-
 Allura/allura/tests/test_validators.py             |   2 +-
 Allura/allura/tests/test_webhooks.py               |   2 +-
 .../test_discussion_moderation_controller.py       |   2 +-
 Allura/allura/tests/unit/phone/test_nexmo.py       |   2 +-
 .../allura/tests/unit/phone/test_phone_service.py  |   2 +-
 Allura/allura/tests/unit/spam/test_akismet.py      |   2 +-
 Allura/allura/tests/unit/spam/test_spam_filter.py  |   2 +-
 .../allura/tests/unit/spam/test_stopforumspam.py   |   2 +-
 Allura/allura/tests/unit/test_app.py               |   2 +-
 Allura/allura/tests/unit/test_artifact.py          |   2 +-
 Allura/allura/tests/unit/test_discuss.py           |   2 +-
 Allura/allura/tests/unit/test_helpers/test_ago.py  |   2 +-
 .../tests/unit/test_helpers/test_set_context.py    |   2 +-
 .../allura/tests/unit/test_ldap_auth_provider.py   |   2 +-
 Allura/allura/tests/unit/test_mixins.py            |   2 +-
 .../allura/tests/unit/test_package_path_loader.py  |   2 +-
 Allura/allura/tests/unit/test_post_model.py        |   2 +-
 Allura/allura/tests/unit/test_project.py           |   2 +-
 Allura/allura/tests/unit/test_repo.py              |   2 +-
 Allura/allura/tests/unit/test_session.py           |   2 +-
 Allura/allura/tests/unit/test_sitemapentry.py      |   2 +-
 Allura/allura/tests/unit/test_solr.py              |   2 +-
 AlluraTest/alluratest/controller.py                |   2 +-
 .../alluratest}/pytest_helpers.py                  |   0
 .../forgeactivity/tests/functional/test_rest.py    |  18 +-
 .../forgeactivity/tests/functional/test_root.py    |  82 +--
 ForgeBlog/forgeblog/tests/functional/test_feeds.py |  12 +-
 ForgeBlog/forgeblog/tests/functional/test_rest.py  |  92 ++--
 ForgeBlog/forgeblog/tests/functional/test_root.py  |  12 +-
 ForgeBlog/forgeblog/tests/test_app.py              |  26 +-
 ForgeBlog/forgeblog/tests/test_commands.py         |  18 +-
 ForgeBlog/forgeblog/tests/unit/test_blog_post.py   |  20 +-
 ForgeChat/forgechat/tests/functional/test_root.py  |   6 +-
 .../forgediscussion/tests/functional/test_forum.py |  92 ++--
 .../tests/functional/test_import.py                |  20 +-
 .../forgediscussion/tests/functional/test_rest.py  | 176 +++----
 ForgeDiscussion/forgediscussion/tests/test_app.py  |  40 +-
 .../forgefeedback/tests/functional/test_root.py    |  12 +-
 .../forgefeedback/tests/test_feedback_roles.py     |   8 +-
 .../forgefeedback/tests/unit/test_feedback.py      |  10 +-
 .../tests/unit/test_root_controller.py             |   2 +-
 .../forgefiles/tests/functional/test_root.py       |   8 +-
 ForgeFiles/forgefiles/tests/model/test_files.py    |  16 +-
 ForgeFiles/forgefiles/tests/test_files_roles.py    |   8 +-
 ForgeGit/forgegit/tests/functional/test_auth.py    |   4 +-
 .../forgegit/tests/functional/test_controllers.py  | 204 ++++----
 ForgeGit/forgegit/tests/model/test_repository.py   | 148 +++---
 ForgeGit/forgegit/tests/test_git_app.py            |   2 +-
 .../forgeimporters/github/tests/test_utils.py      |  36 +-
 .../forgeimporters/github/tests/test_wiki.py       | 140 +++---
 .../tests/github/functional/test_github.py         |  14 +-
 ForgeImporters/forgeimporters/tests/test_base.py   |  14 +-
 ForgeLink/forgelink/tests/functional/test_rest.py  |  26 +-
 ForgeLink/forgelink/tests/functional/test_root.py  |  30 +-
 ForgeLink/forgelink/tests/test_app.py              |   2 +-
 ForgeSVN/forgesvn/tests/functional/test_auth.py    |  14 +-
 .../forgesvn/tests/functional/test_controllers.py  |  64 +--
 ForgeSVN/forgesvn/tests/model/test_repository.py   | 131 +++--
 .../forgesvn/tests/model/test_svnimplementation.py |  30 +-
 ForgeSVN/forgesvn/tests/test_svn_app.py            |   4 +-
 ForgeSVN/forgesvn/tests/test_tasks.py              |   2 +-
 .../forgeshorturl/tests/functional/test.py         |  12 +-
 .../tests/command/test_fix_discussion.py           |  16 +-
 .../forgetracker/tests/functional/test_rest.py     |  54 +-
 .../forgetracker/tests/functional/test_root.py     | 548 ++++++++++-----------
 ForgeTracker/forgetracker/tests/test_app.py        |  38 +-
 .../forgetracker/tests/unit/test_globals_model.py  |  40 +-
 .../tests/unit/test_milestone_controller.py        |   2 +-
 .../tests/unit/test_root_controller.py             |   2 +-
 .../forgetracker/tests/unit/test_search.py         |   4 +-
 .../forgetracker/tests/unit/test_ticket_model.py   | 112 ++---
 ForgeWiki/forgewiki/tests/functional/test_rest.py  |  50 +-
 ForgeWiki/forgewiki/tests/functional/test_root.py  | 100 ++--
 ForgeWiki/forgewiki/tests/test_app.py              |  28 +-
 ForgeWiki/forgewiki/tests/test_wiki_roles.py       |  18 +-
 120 files changed, 1351 insertions(+), 1352 deletions(-)

diff --git a/Allura/allura/tests/functional/test_admin.py b/Allura/allura/tests/functional/test_admin.py
index b5f39a393..a140f1701 100644
--- a/Allura/allura/tests/functional/test_admin.py
+++ b/Allura/allura/tests/functional/test_admin.py
@@ -32,7 +32,7 @@ import six
 
 import allura
 from allura.tests import TestController
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 from allura.tests import decorators as td
 from allura.tests.decorators import audits, out_audits
 from alluratest.controller import TestRestApiBase, setup_trove_categories
diff --git a/Allura/allura/tests/functional/test_auth.py b/Allura/allura/tests/functional/test_auth.py
index 47a5013a0..0acf610e3 100644
--- a/Allura/allura/tests/functional/test_auth.py
+++ b/Allura/allura/tests/functional/test_auth.py
@@ -47,7 +47,7 @@ from tg import tmpl_context as c, app_globals as g
 from allura.tests import TestController
 from allura.tests import decorators as td
 from allura.tests.decorators import audits, out_audits, assert_logmsg
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 from alluratest.controller import setup_trove_categories, TestRestApiBase, oauth1_webtest
 from allura import model as M
 from allura.model.oauth import dummy_oauths
diff --git a/Allura/allura/tests/functional/test_discuss.py b/Allura/allura/tests/functional/test_discuss.py
index a2442074a..8adb1a1af 100644
--- a/Allura/allura/tests/functional/test_discuss.py
+++ b/Allura/allura/tests/functional/test_discuss.py
@@ -25,7 +25,7 @@ from allura.tests import TestController
 from allura import model as M
 from allura.lib import helpers as h
 from tg import config
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_feeds.py b/Allura/allura/tests/functional/test_feeds.py
index 4baf5f9d0..e795f95a9 100644
--- a/Allura/allura/tests/functional/test_feeds.py
+++ b/Allura/allura/tests/functional/test_feeds.py
@@ -20,7 +20,7 @@ from formencode.variabledecode import variable_encode
 from allura.tests import TestController
 from allura.tests import decorators as td
 from allura.lib import helpers as h
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_gravatar.py b/Allura/allura/tests/functional/test_gravatar.py
index fdec13eb1..2886df357 100644
--- a/Allura/allura/tests/functional/test_gravatar.py
+++ b/Allura/allura/tests/functional/test_gravatar.py
@@ -23,7 +23,7 @@ from mock import patch
 
 from allura.tests import TestController
 import allura.lib.gravatar as gravatar
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_home.py b/Allura/allura/tests/functional/test_home.py
index 07a149dbb..a27febbea 100644
--- a/Allura/allura/tests/functional/test_home.py
+++ b/Allura/allura/tests/functional/test_home.py
@@ -27,7 +27,7 @@ import allura
 from allura.tests import TestController
 from allura.tests import decorators as td
 from allura import model as M
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_nav.py b/Allura/allura/tests/functional/test_nav.py
index 840a97969..e7113cc77 100644
--- a/Allura/allura/tests/functional/test_nav.py
+++ b/Allura/allura/tests/functional/test_nav.py
@@ -22,7 +22,7 @@ from tg import app_globals as g
 
 from allura.tests import TestController
 from allura.lib import helpers as h
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_neighborhood.py b/Allura/allura/tests/functional/test_neighborhood.py
index ac7ee3c9d..b123cb7eb 100644
--- a/Allura/allura/tests/functional/test_neighborhood.py
+++ b/Allura/allura/tests/functional/test_neighborhood.py
@@ -37,7 +37,7 @@ from allura.tests import decorators as td
 from allura.lib import helpers as h
 from allura.lib import utils
 from alluratest.controller import setup_trove_categories
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_newforge.py b/Allura/allura/tests/functional/test_newforge.py
index 1e95a38cb..83470c1e4 100644
--- a/Allura/allura/tests/functional/test_newforge.py
+++ b/Allura/allura/tests/functional/test_newforge.py
@@ -21,7 +21,7 @@ from six.moves.urllib.parse import quote
 from allura.tests import TestController
 from allura.tests import decorators as td
 from allura import model as M
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_personal_dashboard.py b/Allura/allura/tests/functional/test_personal_dashboard.py
index 428afb029..c1f7d3cb3 100644
--- a/Allura/allura/tests/functional/test_personal_dashboard.py
+++ b/Allura/allura/tests/functional/test_personal_dashboard.py
@@ -30,7 +30,7 @@ from allura.tests import TestController
 from allura.tests import decorators as td
 from alluratest.controller import setup_global_objects, setup_unit_test
 from forgetracker.tests.functional.test_root import TrackerTestController
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_rest.py b/Allura/allura/tests/functional/test_rest.py
index 0be71b396..c2a8cef8b 100644
--- a/Allura/allura/tests/functional/test_rest.py
+++ b/Allura/allura/tests/functional/test_rest.py
@@ -31,7 +31,7 @@ from alluratest.controller import TestRestApiBase
 from allura.lib import helpers as h
 from allura.lib.exceptions import Invalid
 from allura import model as M
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_root.py b/Allura/allura/tests/functional/test_root.py
index 95a1ea15b..0b2af9c99 100644
--- a/Allura/allura/tests/functional/test_root.py
+++ b/Allura/allura/tests/functional/test_root.py
@@ -41,7 +41,7 @@ from allura.tests import TestController
 from allura import model as M
 from allura.lib import helpers as h
 from alluratest.controller import setup_trove_categories
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_search.py b/Allura/allura/tests/functional/test_search.py
index 52fba8d7f..a24bc0497 100644
--- a/Allura/allura/tests/functional/test_search.py
+++ b/Allura/allura/tests/functional/test_search.py
@@ -24,7 +24,7 @@ from allura.tests import TestController
 from allura.tests.decorators import with_tool
 
 from forgewiki.model import Page
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_site_admin.py b/Allura/allura/tests/functional/test_site_admin.py
index 7ca541362..ec743bb1f 100644
--- a/Allura/allura/tests/functional/test_site_admin.py
+++ b/Allura/allura/tests/functional/test_site_admin.py
@@ -33,7 +33,7 @@ from allura.lib import helpers as h
 from allura.lib.decorators import task
 from allura.lib.plugin import LocalAuthenticationProvider
 import six
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_static.py b/Allura/allura/tests/functional/test_static.py
index 7912e425c..38e4ba760 100644
--- a/Allura/allura/tests/functional/test_static.py
+++ b/Allura/allura/tests/functional/test_static.py
@@ -17,7 +17,7 @@
 
 
 from allura.tests import TestController
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_subscriber.py b/Allura/allura/tests/functional/test_subscriber.py
index 02a273cfc..32333f92d 100644
--- a/Allura/allura/tests/functional/test_subscriber.py
+++ b/Allura/allura/tests/functional/test_subscriber.py
@@ -19,7 +19,7 @@ from allura.tests import TestController
 from allura.tests import decorators as td
 from allura.model.notification import Mailbox
 from allura import model as M
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_tool_list.py b/Allura/allura/tests/functional/test_tool_list.py
index 8e4bfafb1..3562463b4 100644
--- a/Allura/allura/tests/functional/test_tool_list.py
+++ b/Allura/allura/tests/functional/test_tool_list.py
@@ -17,7 +17,7 @@
 
 from allura.tests import TestController
 from allura.tests import decorators as td
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_trovecategory.py b/Allura/allura/tests/functional/test_trovecategory.py
index 8588607aa..76473d3d7 100644
--- a/Allura/allura/tests/functional/test_trovecategory.py
+++ b/Allura/allura/tests/functional/test_trovecategory.py
@@ -26,7 +26,7 @@ from allura.lib import helpers as h
 from allura.tests import TestController
 from alluratest.controller import setup_trove_categories
 from allura.tests import decorators as td
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/functional/test_user_profile.py b/Allura/allura/tests/functional/test_user_profile.py
index e4df160e1..353a99fa7 100644
--- a/Allura/allura/tests/functional/test_user_profile.py
+++ b/Allura/allura/tests/functional/test_user_profile.py
@@ -23,7 +23,7 @@ from alluratest.controller import TestRestApiBase
 from allura.model import Project, User
 from allura.tests import decorators as td
 from allura.tests import TestController
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 class TestUserProfileSections(TestController):
diff --git a/Allura/allura/tests/model/test_auth.py b/Allura/allura/tests/model/test_auth.py
index 7f48c49bc..b4e5e80de 100644
--- a/Allura/allura/tests/model/test_auth.py
+++ b/Allura/allura/tests/model/test_auth.py
@@ -42,7 +42,7 @@ from allura.lib import helpers as h
 from allura.lib import plugin
 from allura.tests import decorators as td
 from alluratest.controller import setup_basic_test, setup_global_objects, setup_functional_test
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 def setup_method():
diff --git a/Allura/allura/tests/model/test_filesystem.py b/Allura/allura/tests/model/test_filesystem.py
index df0e5b7d5..fe88d8aa7 100644
--- a/Allura/allura/tests/model/test_filesystem.py
+++ b/Allura/allura/tests/model/test_filesystem.py
@@ -28,7 +28,7 @@ from webob import Request, Response
 
 from allura import model as M
 from alluratest.controller import setup_unit_test
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 class File(M.File):
diff --git a/Allura/allura/tests/model/test_notification.py b/Allura/allura/tests/model/test_notification.py
index 7e0b8ed3d..33d2547fd 100644
--- a/Allura/allura/tests/model/test_notification.py
+++ b/Allura/allura/tests/model/test_notification.py
@@ -31,7 +31,7 @@ from allura.model.notification import MailFooter
 from allura.lib import helpers as h
 from allura.tests import decorators as td
 from forgewiki import model as WM
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/model/test_repo.py b/Allura/allura/tests/model/test_repo.py
index 873b411c8..84d26bdf2 100644
--- a/Allura/allura/tests/model/test_repo.py
+++ b/Allura/allura/tests/model/test_repo.py
@@ -29,7 +29,7 @@ from tg import config
 from alluratest.controller import setup_basic_test, setup_global_objects
 from allura import model as M
 from allura.lib import helpers as h
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/model/test_timeline.py b/Allura/allura/tests/model/test_timeline.py
index 3d8bc26e7..00e7ea069 100644
--- a/Allura/allura/tests/model/test_timeline.py
+++ b/Allura/allura/tests/model/test_timeline.py
@@ -20,7 +20,7 @@ from alluratest.tools import assert_equal
 from allura import model as M
 from allura.tests import decorators as td
 from alluratest.controller import setup_basic_test, setup_global_objects
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/scripts/test_create_sitemap_files.py b/Allura/allura/tests/scripts/test_create_sitemap_files.py
index c5835109f..13c853940 100644
--- a/Allura/allura/tests/scripts/test_create_sitemap_files.py
+++ b/Allura/allura/tests/scripts/test_create_sitemap_files.py
@@ -27,7 +27,7 @@ from alluratest.controller import setup_basic_test
 from allura import model as M
 from allura.lib import helpers as h
 from allura.scripts.create_sitemap_files import CreateSitemapFiles
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/scripts/test_delete_projects.py b/Allura/allura/tests/scripts/test_delete_projects.py
index 57c219f54..d9414358f 100644
--- a/Allura/allura/tests/scripts/test_delete_projects.py
+++ b/Allura/allura/tests/scripts/test_delete_projects.py
@@ -25,7 +25,7 @@ from allura.tests.decorators import audits, out_audits, with_user_project
 from allura import model as M
 from allura.scripts import delete_projects
 from allura.lib import plugin
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/scripts/test_misc_scripts.py b/Allura/allura/tests/scripts/test_misc_scripts.py
index 8ebbba848..83c8c145e 100644
--- a/Allura/allura/tests/scripts/test_misc_scripts.py
+++ b/Allura/allura/tests/scripts/test_misc_scripts.py
@@ -22,7 +22,7 @@ from allura.scripts.clear_old_notifications import ClearOldNotifications
 from alluratest.controller import setup_basic_test
 from allura import model as M
 from ming.odm import session
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/scripts/test_reindexes.py b/Allura/allura/tests/scripts/test_reindexes.py
index 53a51f04a..c6da7ad62 100644
--- a/Allura/allura/tests/scripts/test_reindexes.py
+++ b/Allura/allura/tests/scripts/test_reindexes.py
@@ -22,7 +22,7 @@ from allura.scripts.reindex_users import ReindexUsers
 from allura.tests.decorators import assert_logmsg_and_no_warnings_or_errors
 from alluratest.controller import setup_basic_test
 from allura import model as M
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/templates/jinja_master/test_lib.py b/Allura/allura/tests/templates/jinja_master/test_lib.py
index f3eea9edd..8c46da06b 100644
--- a/Allura/allura/tests/templates/jinja_master/test_lib.py
+++ b/Allura/allura/tests/templates/jinja_master/test_lib.py
@@ -22,7 +22,7 @@ from alluratest.tools import assert_equal
 import ming
 from allura.config.app_cfg import ForgeConfig, AlluraJinjaRenderer
 from alluratest.controller import setup_basic_test
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 def strip_space(s):
diff --git a/Allura/allura/tests/test_app.py b/Allura/allura/tests/test_app.py
index b93170a8e..024c12fd3 100644
--- a/Allura/allura/tests/test_app.py
+++ b/Allura/allura/tests/test_app.py
@@ -26,7 +26,7 @@ from alluratest.tools import with_setup
 from allura import app
 from allura.lib.app_globals import Icon
 from allura.lib import mail_util
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 def setup_method():
diff --git a/Allura/allura/tests/test_commands.py b/Allura/allura/tests/test_commands.py
index 84bac7a10..f7440e3a1 100644
--- a/Allura/allura/tests/test_commands.py
+++ b/Allura/allura/tests/test_commands.py
@@ -36,7 +36,7 @@ from allura.command import base, script, set_neighborhood_features, \
 from allura import model as M
 from allura.lib.exceptions import InvalidNBFeatureValueError
 from allura.tests import decorators as td
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 test_config = pkg_resources.resource_filename(
diff --git a/Allura/allura/tests/test_decorators.py b/Allura/allura/tests/test_decorators.py
index 033e5c41a..71b70d019 100644
--- a/Allura/allura/tests/test_decorators.py
+++ b/Allura/allura/tests/test_decorators.py
@@ -21,7 +21,7 @@ import random
 import gc
 
 from alluratest.tools import assert_equal, assert_not_equal
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 from allura.lib.decorators import task, memoize
 from alluratest.controller import setup_basic_test, setup_global_objects
 
diff --git a/Allura/allura/tests/test_diff.py b/Allura/allura/tests/test_diff.py
index d128386b0..1485bc1a8 100644
--- a/Allura/allura/tests/test_diff.py
+++ b/Allura/allura/tests/test_diff.py
@@ -18,7 +18,7 @@
 import unittest
 
 from allura.lib.diff import HtmlSideBySideDiff
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/test_dispatch.py b/Allura/allura/tests/test_dispatch.py
index 265fdd187..983ffac72 100644
--- a/Allura/allura/tests/test_dispatch.py
+++ b/Allura/allura/tests/test_dispatch.py
@@ -16,7 +16,7 @@
 #       under the License.
 
 from allura.tests import TestController
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 app = None
 
diff --git a/Allura/allura/tests/test_globals.py b/Allura/allura/tests/test_globals.py
index 389c7a228..29b318027 100644
--- a/Allura/allura/tests/test_globals.py
+++ b/Allura/allura/tests/test_globals.py
@@ -43,7 +43,7 @@ from allura import model as M
 from allura.lib import helpers as h
 from allura.lib.app_globals import ForgeMarkdown
 from allura.tests import decorators as td
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 from forgewiki import model as WM
 from forgeblog import model as BM
diff --git a/Allura/allura/tests/test_helpers.py b/Allura/allura/tests/test_helpers.py
index dbd359e33..6e03cb8c5 100644
--- a/Allura/allura/tests/test_helpers.py
+++ b/Allura/allura/tests/test_helpers.py
@@ -37,7 +37,7 @@ from allura.lib.search import inject_user
 from allura.lib.security import has_access
 from allura.lib.security import Credentials
 from allura.tests import decorators as td
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 from alluratest.controller import setup_basic_test
 import six
 
diff --git a/Allura/allura/tests/test_mail_util.py b/Allura/allura/tests/test_mail_util.py
index f1ad21d09..33e80bfb0 100644
--- a/Allura/allura/tests/test_mail_util.py
+++ b/Allura/allura/tests/test_mail_util.py
@@ -37,7 +37,7 @@ from allura.lib.mail_util import (
     _parse_message_id,
 )
 from allura.lib.exceptions import AddressException
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 from allura.tests import decorators as td
 import six
 
diff --git a/Allura/allura/tests/test_markdown.py b/Allura/allura/tests/test_markdown.py
index 5334aa4d6..6878143f1 100644
--- a/Allura/allura/tests/test_markdown.py
+++ b/Allura/allura/tests/test_markdown.py
@@ -19,7 +19,7 @@ import unittest
 import mock
 
 from allura.lib import markdown_extensions as mde
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/test_middlewares.py b/Allura/allura/tests/test_middlewares.py
index 1f8e78a79..b48e27603 100644
--- a/Allura/allura/tests/test_middlewares.py
+++ b/Allura/allura/tests/test_middlewares.py
@@ -19,7 +19,7 @@ from mock import MagicMock, patch
 from datadiff.tools import assert_equal
 from alluratest.tools import assert_not_equal
 from allura.lib.custom_middleware import CORSMiddleware
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/test_multifactor.py b/Allura/allura/tests/test_multifactor.py
index e007b0adf..ba7780f3b 100644
--- a/Allura/allura/tests/test_multifactor.py
+++ b/Allura/allura/tests/test_multifactor.py
@@ -32,7 +32,7 @@ from allura.lib.multifactor import GoogleAuthenticatorFile, TotpService, Mongodb
 from allura.lib.multifactor import GoogleAuthenticatorPamFilesystemTotpService
 from allura.lib.multifactor import RecoveryCodeService, MongodbRecoveryCodeService
 from allura.lib.multifactor import GoogleAuthenticatorPamFilesystemRecoveryCodeService
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/test_plugin.py b/Allura/allura/tests/test_plugin.py
index f11eae8d7..cfe441693 100644
--- a/Allura/allura/tests/test_plugin.py
+++ b/Allura/allura/tests/test_plugin.py
@@ -45,7 +45,7 @@ from allura.lib.exceptions import ProjectConflict, ProjectShortnameInvalid
 from allura.tests.decorators import audits
 from allura.tests.exclude_from_rewrite_hook import ThemeProviderTestApp
 from alluratest.controller import setup_basic_test, setup_global_objects
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 def setup_module(module):
diff --git a/Allura/allura/tests/test_scripttask.py b/Allura/allura/tests/test_scripttask.py
index f8576bbf8..ae284a1e9 100644
--- a/Allura/allura/tests/test_scripttask.py
+++ b/Allura/allura/tests/test_scripttask.py
@@ -19,7 +19,7 @@ import unittest
 import mock
 
 from allura.scripts.scripttask import ScriptTask
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/test_security.py b/Allura/allura/tests/test_security.py
index 5fe92b964..f6771f3aa 100644
--- a/Allura/allura/tests/test_security.py
+++ b/Allura/allura/tests/test_security.py
@@ -28,7 +28,7 @@ from forgewiki import model as WM
 from allura.lib.security import HIBPClientError, HIBPClient
 from mock import Mock, patch
 from requests.exceptions import Timeout
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 def _allow(obj, role, perm):
diff --git a/Allura/allura/tests/test_tasks.py b/Allura/allura/tests/test_tasks.py
index 429effd80..2aeef658d 100644
--- a/Allura/allura/tests/test_tasks.py
+++ b/Allura/allura/tests/test_tasks.py
@@ -52,7 +52,7 @@ from allura.tasks import repo_tasks
 from allura.tasks import export_tasks
 from allura.tasks import admin_tasks
 from allura.tests import decorators as td
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 from allura.tests.exclude_from_rewrite_hook import raise_compound_exception
 from allura.lib.decorators import event_handler, task
 
diff --git a/Allura/allura/tests/test_utils.py b/Allura/allura/tests/test_utils.py
index 6e7fca1cc..4c22c1a93 100644
--- a/Allura/allura/tests/test_utils.py
+++ b/Allura/allura/tests/test_utils.py
@@ -44,7 +44,7 @@ from alluratest.controller import setup_unit_test
 from allura import model as M
 from allura.lib import utils
 from allura.lib import helpers as h
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @patch.dict('allura.lib.utils.tg.config', clear=True, foo='bar', baz='true')
diff --git a/Allura/allura/tests/test_validators.py b/Allura/allura/tests/test_validators.py
index 2e0f5af65..a9c011368 100644
--- a/Allura/allura/tests/test_validators.py
+++ b/Allura/allura/tests/test_validators.py
@@ -24,7 +24,7 @@ from allura.lib import validators as v
 from allura.lib.decorators import task
 from alluratest.controller import setup_basic_test
 from allura.websetup.bootstrap import create_user
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 def _setup_method():
diff --git a/Allura/allura/tests/test_webhooks.py b/Allura/allura/tests/test_webhooks.py
index 8237847d6..3b11f5e05 100644
--- a/Allura/allura/tests/test_webhooks.py
+++ b/Allura/allura/tests/test_webhooks.py
@@ -49,7 +49,7 @@ from alluratest.controller import (
     TestRestApiBase,
 )
 import six
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 # important to be distinct from 'test' and 'test2' which ForgeGit and
diff --git a/Allura/allura/tests/unit/controllers/test_discussion_moderation_controller.py b/Allura/allura/tests/unit/controllers/test_discussion_moderation_controller.py
index 72abd8ed4..3ad4ed8df 100644
--- a/Allura/allura/tests/unit/controllers/test_discussion_moderation_controller.py
+++ b/Allura/allura/tests/unit/controllers/test_discussion_moderation_controller.py
@@ -24,7 +24,7 @@ from allura.tests.unit.factories import create_post, create_discussion
 from allura import model
 from allura.controllers.discuss import ModerationController
 from allura.tests.unit import patches
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/phone/test_nexmo.py b/Allura/allura/tests/unit/phone/test_nexmo.py
index 2bcff5cfa..290273946 100644
--- a/Allura/allura/tests/unit/phone/test_nexmo.py
+++ b/Allura/allura/tests/unit/phone/test_nexmo.py
@@ -19,7 +19,7 @@ import json
 from mock import patch
 from datadiff.tools import assert_equal
 from alluratest.tools import assert_in, assert_not_in
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 from allura.lib.phone.nexmo import NexmoPhoneService
 
diff --git a/Allura/allura/tests/unit/phone/test_phone_service.py b/Allura/allura/tests/unit/phone/test_phone_service.py
index fe5b2844e..e4af19908 100644
--- a/Allura/allura/tests/unit/phone/test_phone_service.py
+++ b/Allura/allura/tests/unit/phone/test_phone_service.py
@@ -19,7 +19,7 @@ from alluratest.tools import assert_true
 from datadiff.tools import assert_equal
 
 from allura.lib.phone import PhoneService
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 class MockPhoneService(PhoneService):
diff --git a/Allura/allura/tests/unit/spam/test_akismet.py b/Allura/allura/tests/unit/spam/test_akismet.py
index bee8403cd..2c6e2af31 100644
--- a/Allura/allura/tests/unit/spam/test_akismet.py
+++ b/Allura/allura/tests/unit/spam/test_akismet.py
@@ -26,7 +26,7 @@ from datetime import datetime
 from bson import ObjectId
 
 from allura.lib.spam.akismetfilter import AKISMET_AVAILABLE, AkismetSpamFilter
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @unittest.skipIf(not AKISMET_AVAILABLE, "Akismet not available")
diff --git a/Allura/allura/tests/unit/spam/test_spam_filter.py b/Allura/allura/tests/unit/spam/test_spam_filter.py
index 99f6ce1a9..f907b41ef 100644
--- a/Allura/allura/tests/unit/spam/test_spam_filter.py
+++ b/Allura/allura/tests/unit/spam/test_spam_filter.py
@@ -26,7 +26,7 @@ from allura import model as M
 from allura.model.artifact import SpamCheckResult
 from alluratest.controller import setup_basic_test
 from forgewiki import model as WM
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 class MockFilter(SpamFilter):
diff --git a/Allura/allura/tests/unit/spam/test_stopforumspam.py b/Allura/allura/tests/unit/spam/test_stopforumspam.py
index 2037ddde8..7a1bd31d7 100644
--- a/Allura/allura/tests/unit/spam/test_stopforumspam.py
+++ b/Allura/allura/tests/unit/spam/test_stopforumspam.py
@@ -22,7 +22,7 @@ from bson import ObjectId
 from alluratest.tools import assert_equal
 
 from allura.lib.spam.stopforumspamfilter import StopForumSpamSpamFilter
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_app.py b/Allura/allura/tests/unit/test_app.py
index 2a374f415..65d000fae 100644
--- a/Allura/allura/tests/unit/test_app.py
+++ b/Allura/allura/tests/unit/test_app.py
@@ -22,7 +22,7 @@ from allura import model
 from allura.tests.unit import WithDatabase
 from allura.tests.unit.patches import fake_app_patch
 from allura.tests.unit.factories import create_project, create_app_config
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_artifact.py b/Allura/allura/tests/unit/test_artifact.py
index 801a29fef..1cbe17f47 100644
--- a/Allura/allura/tests/unit/test_artifact.py
+++ b/Allura/allura/tests/unit/test_artifact.py
@@ -18,7 +18,7 @@
 import unittest
 
 from allura import model as M
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_discuss.py b/Allura/allura/tests/unit/test_discuss.py
index 9cb225e40..6078dff49 100644
--- a/Allura/allura/tests/unit/test_discuss.py
+++ b/Allura/allura/tests/unit/test_discuss.py
@@ -18,7 +18,7 @@
 from allura import model as M
 from allura.tests.unit import WithDatabase
 from allura.tests.unit.patches import fake_app_patch
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_helpers/test_ago.py b/Allura/allura/tests/unit/test_helpers/test_ago.py
index 7fef39014..a8e4c9044 100644
--- a/Allura/allura/tests/unit/test_helpers/test_ago.py
+++ b/Allura/allura/tests/unit/test_helpers/test_ago.py
@@ -21,7 +21,7 @@ from mock import patch
 from alluratest.tools import assert_equal
 
 from allura.lib import helpers
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_helpers/test_set_context.py b/Allura/allura/tests/unit/test_helpers/test_set_context.py
index 3468ceed0..9e6999231 100644
--- a/Allura/allura/tests/unit/test_helpers/test_set_context.py
+++ b/Allura/allura/tests/unit/test_helpers/test_set_context.py
@@ -26,7 +26,7 @@ from allura.tests.unit import patches
 from allura.tests.unit.factories import (create_project,
                                          create_app_config,
                                          create_neighborhood)
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_ldap_auth_provider.py b/Allura/allura/tests/unit/test_ldap_auth_provider.py
index d94430188..bc17ce9a5 100644
--- a/Allura/allura/tests/unit/test_ldap_auth_provider.py
+++ b/Allura/allura/tests/unit/test_ldap_auth_provider.py
@@ -32,7 +32,7 @@ from allura.lib import plugin
 from allura.lib import helpers as h
 from allura import model as M
 import six
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_mixins.py b/Allura/allura/tests/unit/test_mixins.py
index f4e50aafe..775ff0358 100644
--- a/Allura/allura/tests/unit/test_mixins.py
+++ b/Allura/allura/tests/unit/test_mixins.py
@@ -17,7 +17,7 @@
 
 from mock import Mock
 from allura.model import VotableArtifact
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_package_path_loader.py b/Allura/allura/tests/unit/test_package_path_loader.py
index 5c39771f6..5aec5fea2 100644
--- a/Allura/allura/tests/unit/test_package_path_loader.py
+++ b/Allura/allura/tests/unit/test_package_path_loader.py
@@ -25,7 +25,7 @@ import mock
 from tg import config
 
 from allura.lib.package_path_loader import PackagePathLoader
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_post_model.py b/Allura/allura/tests/unit/test_post_model.py
index e1f7504ed..eca936d1e 100644
--- a/Allura/allura/tests/unit/test_post_model.py
+++ b/Allura/allura/tests/unit/test_post_model.py
@@ -22,7 +22,7 @@ from allura import model as M
 from allura.tests.unit import WithDatabase
 from allura.tests.unit import patches
 from allura.tests.unit.factories import create_post
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_project.py b/Allura/allura/tests/unit/test_project.py
index 3fefa5fe1..2fb093643 100644
--- a/Allura/allura/tests/unit/test_project.py
+++ b/Allura/allura/tests/unit/test_project.py
@@ -23,7 +23,7 @@ from tg import config
 from allura import model as M
 from allura.lib import helpers as h
 from allura.app import SitemapEntry
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_repo.py b/Allura/allura/tests/unit/test_repo.py
index df862d547..a33d8c644 100644
--- a/Allura/allura/tests/unit/test_repo.py
+++ b/Allura/allura/tests/unit/test_repo.py
@@ -31,7 +31,7 @@ from allura.model.repository import zipdir, prefix_paths_union
 from allura.model.repo_refresh import (
     _group_commits,
 )
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_session.py b/Allura/allura/tests/unit/test_session.py
index cb7f02f7d..d7899302f 100644
--- a/Allura/allura/tests/unit/test_session.py
+++ b/Allura/allura/tests/unit/test_session.py
@@ -28,7 +28,7 @@ from allura.model.session import (
     ArtifactSessionExtension,
     substitute_extensions,
 )
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 def test_extensions_cm():
diff --git a/Allura/allura/tests/unit/test_sitemapentry.py b/Allura/allura/tests/unit/test_sitemapentry.py
index e4e56deec..ea38b10b7 100644
--- a/Allura/allura/tests/unit/test_sitemapentry.py
+++ b/Allura/allura/tests/unit/test_sitemapentry.py
@@ -19,7 +19,7 @@ import unittest
 from mock import Mock
 
 from allura.app import SitemapEntry
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/Allura/allura/tests/unit/test_solr.py b/Allura/allura/tests/unit/test_solr.py
index cc73cdb6f..fa23bc135 100644
--- a/Allura/allura/tests/unit/test_solr.py
+++ b/Allura/allura/tests/unit/test_solr.py
@@ -26,7 +26,7 @@ from allura.tests import decorators as td
 from alluratest.controller import setup_basic_test
 from allura.lib.solr import Solr, escape_solr_arg
 from allura.lib.search import search_app, SearchIndexable
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 @with_nose_compatibility
diff --git a/AlluraTest/alluratest/controller.py b/AlluraTest/alluratest/controller.py
index 362c8ee54..f0011a74b 100644
--- a/AlluraTest/alluratest/controller.py
+++ b/AlluraTest/alluratest/controller.py
@@ -19,7 +19,7 @@
 from __future__ import annotations
 
 import os
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 import six.moves.urllib.request
 import six.moves.urllib.parse
 import six.moves.urllib.error
diff --git a/Allura/allura/tests/pytest_helpers.py b/AlluraTest/alluratest/pytest_helpers.py
similarity index 100%
rename from Allura/allura/tests/pytest_helpers.py
rename to AlluraTest/alluratest/pytest_helpers.py
diff --git a/ForgeActivity/forgeactivity/tests/functional/test_rest.py b/ForgeActivity/forgeactivity/tests/functional/test_rest.py
index cb11dc9b2..d20166d5f 100644
--- a/ForgeActivity/forgeactivity/tests/functional/test_rest.py
+++ b/ForgeActivity/forgeactivity/tests/functional/test_rest.py
@@ -42,13 +42,13 @@ class TestActivityHasAccessAPI(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/activity/has_access?user=babadook&perm=read',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
         r = self.api_get(
             '/rest/p/test/activity/has_access?user=test-user&perm=jump',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
     def test_has_access_not_admin(self):
         """
@@ -64,15 +64,15 @@ class TestActivityHasAccessAPI(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/activity/has_access?user=test-admin&perm=admin',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], True)
+        assert r.status_int == 200
+        assert r.json['result'] == True
         r = self.api_get(
             '/rest/p/test/activity/has_access?user=test-user&perm=admin',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
 
     def test_user_api(self):
         r = self.api_get('/rest/u/test-user/activity')
-        assert_equal(r.status_int, 200)
\ No newline at end of file
+        assert r.status_int == 200
\ No newline at end of file
diff --git a/ForgeActivity/forgeactivity/tests/functional/test_root.py b/ForgeActivity/forgeactivity/tests/functional/test_root.py
index 2948e560b..cb90360d1 100644
--- a/ForgeActivity/forgeactivity/tests/functional/test_root.py
+++ b/ForgeActivity/forgeactivity/tests/functional/test_root.py
@@ -95,9 +95,9 @@ class TestActivityController(TestController):
         })]
         r = self.app.get('/p/test/activity/')
         timeline = r.html.find('ul', 'timeline')
-        assert_equal(1, len(timeline.findAll('li')))
+        assert 1 == len(timeline.findAll('li'))
         activity = timeline.find('li')
-        assert_equal(activity.time['title'], "2013-12-04 21:48:19")
+        assert activity.time['title'] == "2013-12-04 21:48:19"
         h1 = """\
         <h1>
          <img alt="Administrator 1" class="emboss x32 avatar" src="/u/test-admin/user_icon" title="Administrator 1"/>
@@ -114,13 +114,13 @@ class TestActivityController(TestController):
          </a>
         </h1>
         """
-        assert_equal(dedent(h1), activity.h1.prettify())
+        assert dedent(h1) == activity.h1.prettify()
         p = """\
         <p>
          Just wanted to leave a comment on this...
         </p>
         """
-        assert_equal(dedent(p), activity.p.prettify())
+        assert dedent(p) == activity.p.prettify()
 
     @td.with_tool('u/test-user-1', 'activity')
     @td.with_user_project('test-user-1')
@@ -170,11 +170,11 @@ class TestActivityController(TestController):
             create_timeline.side_effect = orig_create_timeline
             M.MonQTask.run_ready()
             # 3 aggregations: 1 actor, 1 follower, 1 project
-            assert_equal(create_timeline.call_count, 3)
+            assert create_timeline.call_count == 3
             create_timeline.reset_mock()
             self.app.get('/u/test-admin/activity/')
             self.app.get('/u/test-user-1/activity/')
-            assert_equal(create_timeline.call_count, 0)
+            assert create_timeline.call_count == 0
 
     @td.with_tool('test', 'activity')
     @patch('forgeactivity.main.g.director')
@@ -213,17 +213,17 @@ class TestActivityController(TestController):
         })]
         r = self.app.get('/p/test/activity/feed.rss')
         timeline = r.xml.find('channel')
-        assert_equal(1, len(timeline.findall('item')))
+        assert 1 == len(timeline.findall('item'))
         activity = timeline.find('item')
-        assert_equal(activity.find('pubDate').text,
+        assert (activity.find('pubDate').text ==
                      'Wed, 04 Dec 2013 21:48:19 -0000')
-        assert_equal(activity.find('title').text,
+        assert (activity.find('title').text ==
                      'Administrator 1 posted a comment on ticket #34')
-        assert_equal(activity.find('description').text,
+        assert (activity.find('description').text ==
                      'Just wanted to leave a comment on this...')
-        assert_equal(activity.find('guid').text,
+        assert (activity.find('guid').text ==
                      'http://localhost/p/test/unicode•º/?limit=25#ed7c')
-        assert_equal(activity.find('link').text,
+        assert (activity.find('link').text ==
                      'http://localhost/p/test/unicode%E2%80%A2%C2%BA/?limit=25#ed7c')
 
     @td.with_tool('test', 'activity')
@@ -244,10 +244,10 @@ class TestActivityController(TestController):
 
         r = self.app.get('/p/test/activity/feed.rss')
         timeline = r.xml.find('channel')
-        assert_equal(1, len(timeline.findall('item')))
+        assert 1 == len(timeline.findall('item'))
         activity = timeline.find('item')
 
-        assert_equal(activity.find('title').text, 'Administrator 1 created ticket #34')
+        assert activity.find('title').text == 'Administrator 1 created ticket #34'
 
     @td.with_tool('u/test-user-1', 'activity')
     @td.with_user_project('test-user-1')
@@ -287,15 +287,15 @@ class TestActivityController(TestController):
         })]
         r = self.app.get('/u/test-user-1/activity/feed.rss')
         timeline = r.xml.find('channel')
-        assert_equal(1, len(timeline.findall('item')))
+        assert 1 == len(timeline.findall('item'))
         activity = timeline.find('item')
-        assert_equal(activity.find('pubDate').text,
+        assert (activity.find('pubDate').text ==
                      'Wed, 04 Dec 2013 21:48:19 -0000')
-        assert_equal(activity.find('title').text,
+        assert (activity.find('title').text ==
                      'Administrator 1 posted a comment on ticket #34')
-        assert_equal(activity.find('description').text,
+        assert (activity.find('description').text ==
                      'Just wanted to leave a comment on this...')
-        assert_equal(activity.find('link').text,
+        assert (activity.find('link').text ==
                      'http://localhost/p/test/tickets/34/?limit=25#ed7c')
 
     @td.with_tool('test', 'activity')
@@ -335,20 +335,20 @@ class TestActivityController(TestController):
         })]
         r = self.app.get('/p/test/activity/feed.atom')
         timeline = r.xml
-        assert_equal(1, len(timeline.findall(
-            '{http://www.w3.org/2005/Atom}entry')))
+        assert 1 == len(timeline.findall(
+            '{http://www.w3.org/2005/Atom}entry'))
         activity = timeline.find('{http://www.w3.org/2005/Atom}entry')
-        assert_equal(
-            activity.find('{http://www.w3.org/2005/Atom}published').text,
+        assert (
+            activity.find('{http://www.w3.org/2005/Atom}published').text ==
             '2013-12-04T21:48:19Z')
-        assert_equal(
-            activity.find('{http://www.w3.org/2005/Atom}title').text,
+        assert (
+            activity.find('{http://www.w3.org/2005/Atom}title').text ==
             'Administrator 1 posted a comment on ticket #34')
-        assert_equal(
-            activity.find('{http://www.w3.org/2005/Atom}summary').text,
+        assert (
+            activity.find('{http://www.w3.org/2005/Atom}summary').text ==
             'Just wanted to leave a comment on this...')
-        assert_equal(
-            activity.find('{http://www.w3.org/2005/Atom}link').get('href'),
+        assert (
+            activity.find('{http://www.w3.org/2005/Atom}link').get('href') ==
             'http://localhost/p/test/tickets/34/?limit=25#ed7c')
 
     @td.with_tool('u/test-user-1', 'activity')
@@ -389,20 +389,20 @@ class TestActivityController(TestController):
         })]
         r = self.app.get('/u/test-user-1/activity/feed.atom')
         timeline = r.xml
-        assert_equal(1, len(timeline.findall(
-            '{http://www.w3.org/2005/Atom}entry')))
+        assert 1 == len(timeline.findall(
+            '{http://www.w3.org/2005/Atom}entry'))
         activity = timeline.find('{http://www.w3.org/2005/Atom}entry')
-        assert_equal(
-            activity.find('{http://www.w3.org/2005/Atom}published').text,
+        assert (
+            activity.find('{http://www.w3.org/2005/Atom}published').text ==
             '2013-12-04T21:48:19Z')
-        assert_equal(
-            activity.find('{http://www.w3.org/2005/Atom}title').text,
+        assert (
+            activity.find('{http://www.w3.org/2005/Atom}title').text ==
             'Administrator 1 posted a comment on ticket #34')
-        assert_equal(
-            activity.find('{http://www.w3.org/2005/Atom}summary').text,
+        assert (
+            activity.find('{http://www.w3.org/2005/Atom}summary').text ==
             'Just wanted to leave a comment on this...')
-        assert_equal(
-            activity.find('{http://www.w3.org/2005/Atom}link').get('href'),
+        assert (
+            activity.find('{http://www.w3.org/2005/Atom}link').get('href') ==
             'http://localhost/p/test/tickets/34/?limit=25#ed7c')
 
     @td.with_tool('u/test-user-1', 'activity')
@@ -459,7 +459,7 @@ class TestActivityController(TestController):
         activity3 = Activity(**dict(activity_data, node_id='User:abc', owner_id='User:abc'))
         ThreadLocalODMSession.flush_all()
         activity_id = str(activity._id)
-        assert_equal(Activity.query.find({'obj.activity_extras.summary': 'Sensitive private info, oops'}).count(), 3)
+        assert Activity.query.find({'obj.activity_extras.summary': 'Sensitive private info, oops'}).count() == 3
 
         self.app.post('/u/test-user-1/activity/delete_item',
                       {'activity_id': activity_id},
@@ -467,4 +467,4 @@ class TestActivityController(TestController):
                       status=200)
         ThreadLocalODMSession.flush_all()
 
-        assert_equal(Activity.query.find({'obj.activity_extras.summary': 'Sensitive private info, oops'}).count(), 0)
+        assert Activity.query.find({'obj.activity_extras.summary': 'Sensitive private info, oops'}).count() == 0
diff --git a/ForgeBlog/forgeblog/tests/functional/test_feeds.py b/ForgeBlog/forgeblog/tests/functional/test_feeds.py
index fde0322f4..530f8bdb4 100644
--- a/ForgeBlog/forgeblog/tests/functional/test_feeds.py
+++ b/ForgeBlog/forgeblog/tests/functional/test_feeds.py
@@ -68,10 +68,10 @@ class TestFeeds(TestController):
     def test_rss_feed_contains_self_link(self):
         r = self.app.get('/blog/feed.rss')
         # atom namespace included
-        assert_in('<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">', r)
+        assert '<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">' in r
         # ...and atom:link points to feed url
-        assert_in('<atom:link href="http://localhost/blog/feed.rss" '
-                  'rel="self" type="application/rss+xml"></atom:link>', r)
+        assert ('<atom:link href="http://localhost/blog/feed.rss" '
+                  'rel="self" type="application/rss+xml"></atom:link>' in r)
 
     def test_post_feeds(self):
         self._post()
@@ -82,7 +82,7 @@ class TestFeeds(TestController):
         assert 'Nothing to see' in response
         self._post(title='test', text='*sometext*')
         response = self.app.get('/blog/feed')
-        assert_in('&lt;div class="markdown_content"&gt;&lt;p&gt;&lt;em&gt;sometext&lt;/em&gt;&lt;/p&gt;&lt;/div&gt;',
+        assert ('&lt;div class="markdown_content"&gt;&lt;p&gt;&lt;em&gt;sometext&lt;/em&gt;&lt;/p&gt;&lt;/div&gt;' in
                   response)
 
     def test_related_artifacts(self):
@@ -142,7 +142,7 @@ class TestFeeds(TestController):
         ThreadLocalORMSession.flush_all()
 
         resp = self.app.get(h.urlquote("/blog/" + self._blog_date() + "/my-pôst/feed.rss"))
-        assert_in('boring comment', resp)
+        assert 'boring comment' in resp
 
         resp = self.app.get("/blog/feed.rss")
-        assert_not_in('boring comment', resp)
\ No newline at end of file
+        assert 'boring comment' not in resp
\ No newline at end of file
diff --git a/ForgeBlog/forgeblog/tests/functional/test_rest.py b/ForgeBlog/forgeblog/tests/functional/test_rest.py
index a5219f2c3..9e8a87756 100644
--- a/ForgeBlog/forgeblog/tests/functional/test_rest.py
+++ b/ForgeBlog/forgeblog/tests/functional/test_rest.py
@@ -45,21 +45,21 @@ class TestBlogApi(TestRestApiBase):
             'labels': 'label1, label2'
         }
         r = self.api_post('/rest/p/test/blog/', **data)
-        assert_equal(
-            r.location, 'http://localhost/rest/p/test/blog/%s/%s/test/' %
+        assert (
+            r.location == 'http://localhost/rest/p/test/blog/%s/%s/test/' %
             (date.today().strftime("%Y"), date.today().strftime("%m")))
-        assert_equal(r.status_int, 201)
+        assert r.status_int == 201
         url = '/rest' + BM.BlogPost.query.find().first().url()
         r = self.api_get('/rest/p/test/blog/')
-        assert_equal(r.json['posts'][0]['title'], 'test')
-        assert_in(url, r.json['posts'][0]['url'])
+        assert r.json['posts'][0]['title'] == 'test'
+        assert url in r.json['posts'][0]['url']
 
         r = self.api_get(url)
-        assert_equal(r.json['title'], data['title'])
-        assert_equal(r.json['text'], data['text'])
-        assert_equal(r.json['author'], 'test-admin')
-        assert_equal(r.json['state'], data['state'])
-        assert_equal(r.json['labels'], data['labels'].split(','))
+        assert r.json['title'] == data['title']
+        assert r.json['text'] == data['text']
+        assert r.json['author'] == 'test-admin'
+        assert r.json['state'] == data['state']
+        assert r.json['labels'] == data['labels'].split(',')
 
     def test_update_post(self):
         data = {
@@ -69,7 +69,7 @@ class TestBlogApi(TestRestApiBase):
             'labels': 'label1, label2'
         }
         r = self.api_post('/rest/p/test/blog/', **data)
-        assert_equal(r.status_int, 201)
+        assert r.status_int == 201
         url = '/rest' + BM.BlogPost.query.find().first().url()
         data = {
             'text': 'test text2',
@@ -78,10 +78,10 @@ class TestBlogApi(TestRestApiBase):
         }
         self.api_post(url, **data)
         r = self.api_get(url)
-        assert_equal(r.json['title'], 'test')
-        assert_equal(r.json['text'], data['text'])
-        assert_equal(r.json['state'], data['state'])
-        assert_equal(r.json['labels'], data['labels'].split(','))
+        assert r.json['title'] == 'test'
+        assert r.json['text'] == data['text']
+        assert r.json['state'] == data['state']
+        assert r.json['labels'] == data['labels'].split(',')
 
     def test_delete_post(self):
         data = {
@@ -90,7 +90,7 @@ class TestBlogApi(TestRestApiBase):
             'labels': 'label1, label2'
         }
         r = self.api_post('/rest/p/test/blog/', **data)
-        assert_equal(r.status_int, 201)
+        assert r.status_int == 201
         url = '/rest' + BM.BlogPost.query.find().first().url()
         self.api_post(url, delete='')
         r = self.api_get(url, status=404)
@@ -149,16 +149,16 @@ class TestBlogApi(TestRestApiBase):
                       extra_environ={'username': '*anonymous'},
                       status=200)
         r = self.api_get(url)
-        assert_equal(r.json['title'], 'test2')
-        assert_equal(r.json['text'], 'test text2')
-        assert_equal(r.json['state'], 'published')
+        assert r.json['title'] == 'test2'
+        assert r.json['text'] == 'test text2'
+        assert r.json['state'] == 'published'
 
     def test_permission_draft_post(self):
         self.api_post('/rest/p/test/blog/', title='test',
                       text='test text', state='draft')
         r = self.app.get('/rest/p/test/blog/',
                          extra_environ={'username': '*anonymous'})
-        assert_equal(r.json['posts'], [])
+        assert r.json['posts'] == []
         url = '/rest' + BM.BlogPost.query.find().first().url()
         self.app.post(url,
                       params=dict(title='test2', text='test text2',
@@ -172,19 +172,19 @@ class TestBlogApi(TestRestApiBase):
         acl.append(anon_write)
         r = self.app.get('/rest/p/test/blog/',
                          extra_environ={'username': '*anonymous'})
-        assert_equal(r.json['posts'][0]['title'], 'test')
+        assert r.json['posts'][0]['title'] == 'test'
 
     def test_draft_post(self):
         self.api_post('/rest/p/test/blog/', title='test',
                       text='test text', state='draft')
         r = self.app.get('/rest/p/test/blog/',
                          extra_environ={'username': '*anonymous'})
-        assert_equal(r.json['posts'], [])
+        assert r.json['posts'] == []
         url = '/rest' + BM.BlogPost.query.find().first().url()
         self.api_post(url, state='published')
         r = self.app.get('/rest/p/test/blog/',
                          extra_environ={'username': '*anonymous'})
-        assert_equal(r.json['posts'][0]['title'], 'test')
+        assert r.json['posts'][0]['title'] == 'test'
 
     def test_pagination(self):
         self.api_post('/rest/p/test/blog/', title='test1',
@@ -194,23 +194,23 @@ class TestBlogApi(TestRestApiBase):
         self.api_post('/rest/p/test/blog/', title='test3',
                       text='test text3', state='published')
         r = self.api_get('/rest/p/test/blog/', limit='1', page='0')
-        assert_equal(r.json['posts'][0]['title'], 'test3')
-        assert_equal(len(r.json['posts']), 1)
-        assert_equal(r.json['count'], 3)
-        assert_equal(r.json['limit'], 1)
-        assert_equal(r.json['page'], 0)
+        assert r.json['posts'][0]['title'] == 'test3'
+        assert len(r.json['posts']) == 1
+        assert r.json['count'] == 3
+        assert r.json['limit'] == 1
+        assert r.json['page'] == 0
         r = self.api_get('/rest/p/test/blog/', limit='2', page='0')
-        assert_equal(r.json['posts'][0]['title'], 'test3')
-        assert_equal(r.json['posts'][1]['title'], 'test2')
-        assert_equal(len(r.json['posts']), 2)
-        assert_equal(r.json['count'], 3)
-        assert_equal(r.json['limit'], 2)
-        assert_equal(r.json['page'], 0)
+        assert r.json['posts'][0]['title'] == 'test3'
+        assert r.json['posts'][1]['title'] == 'test2'
+        assert len(r.json['posts']) == 2
+        assert r.json['count'] == 3
+        assert r.json['limit'] == 2
+        assert r.json['page'] == 0
         r = self.api_get('/rest/p/test/blog/', limit='1', page='2')
-        assert_equal(r.json['posts'][0]['title'], 'test1')
-        assert_equal(r.json['count'], 3)
-        assert_equal(r.json['limit'], 1)
-        assert_equal(r.json['page'], 2)
+        assert r.json['posts'][0]['title'] == 'test1'
+        assert r.json['count'] == 3
+        assert r.json['limit'] == 1
+        assert r.json['page'] == 2
 
     def test_has_access_no_params(self):
         self.api_get('/rest/p/test/blog/has_access', status=404)
@@ -222,13 +222,13 @@ class TestBlogApi(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/blog/has_access?user=babadook&perm=read',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
         r = self.api_get(
             '/rest/p/test/blog/has_access?user=test-user&perm=jump',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
     def test_has_access_not_admin(self):
         """
@@ -244,13 +244,13 @@ class TestBlogApi(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/blog/has_access?user=test-admin&perm=post&access_token=ABCDEF',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], True)
+        assert r.status_int == 200
+        assert r.json['result'] == True
         r = self.api_get(
             '/rest/p/test/blog/has_access?user=*anonymous&perm=admin',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
     def test_create_post_limit_by_project(self):
         data = {
diff --git a/ForgeBlog/forgeblog/tests/functional/test_root.py b/ForgeBlog/forgeblog/tests/functional/test_root.py
index 11d5a7467..c0b18e42d 100644
--- a/ForgeBlog/forgeblog/tests/functional/test_root.py
+++ b/ForgeBlog/forgeblog/tests/functional/test_root.py
@@ -257,15 +257,15 @@ class Test(TestController):
         with h.push_config(tg.config, **{'forgeblog.rate_limits': '{"3600": 0}'}):
             r = self._post()
             wf = json.loads(self.webflash(r))
-            assert_equal(wf['status'], 'error')
-            assert_equal(wf['message'], 'Create/edit rate limit exceeded. Please try again later.')
+            assert wf['status'] == 'error'
+            assert wf['message'] == 'Create/edit rate limit exceeded. Please try again later.'
 
     def test_rate_limit_form(self):
         with h.push_config(tg.config, **{'forgeblog.rate_limits': '{"3600": 0}'}):
             r = self.app.get('/blog/new')
             wf = json.loads(self.webflash(r))
-            assert_equal(wf['status'], 'error')
-            assert_equal(wf['message'], 'Create/edit rate limit exceeded. Please try again later.')
+            assert wf['status'] == 'error'
+            assert wf['message'] == 'Create/edit rate limit exceeded. Please try again later.'
 
     def test_admin_external_feed_invalid(self):
         r = self.app.get('/blog/')
@@ -273,7 +273,7 @@ class Test(TestController):
         form = r.forms[0]
         form['new_exfeed'].value = 'asdfasdf'
         r = form.submit()
-        assert_in('Invalid', self.webflash(r))
+        assert 'Invalid' in self.webflash(r)
 
     def test_admin_external_feed_ok(self):
         # sidebar menu doesn't expose link to this, unless "forgeblog.exfeed" config is true, but can use form anyway
@@ -282,7 +282,7 @@ class Test(TestController):
         form = r.forms[0]
         form['new_exfeed'].value = 'https://example.com/feed.rss'
         r = form.submit()
-        assert_in('External feeds updated', self.webflash(r))
+        assert 'External feeds updated' in self.webflash(r)
 
         r = self.app.get('/admin/blog/exfeed')
         r.mustcontain('https://example.com/feed.rss')
diff --git a/ForgeBlog/forgeblog/tests/test_app.py b/ForgeBlog/forgeblog/tests/test_app.py
index 98cc59fda..bb224a057 100644
--- a/ForgeBlog/forgeblog/tests/test_app.py
+++ b/ForgeBlog/forgeblog/tests/test_app.py
@@ -51,26 +51,26 @@ class TestApp:
 
     @td.with_tool('test', 'Blog', 'blog')
     def test_sitemap_xml(self):
-        assert_equal([], c.app.sitemap_xml())
+        assert [] == c.app.sitemap_xml()
         BM.BlogPost.new(
             title='Blog Title',
             state='draft',
             text='This is my first blog Post',
         )
-        assert_equal([], c.app.sitemap_xml())
+        assert [] == c.app.sitemap_xml()
         BM.BlogPost.new(
             title='Blog Title',
             state='published',
             text='This is my first blog Post',
             deleted=True
         )
-        assert_equal([], c.app.sitemap_xml())
+        assert [] == c.app.sitemap_xml()
         BM.BlogPost.new(
             title='Blog Title',
             state='published',
             text='This is my first blog Post',
         )
-        assert_equal(1, len(c.app.sitemap_xml()))
+        assert 1 == len(c.app.sitemap_xml())
 
 
 class TestBulkExport:
@@ -107,14 +107,14 @@ class TestBulkExport:
         blog = json.loads(f.read())
         blog['posts'] = sorted(
             blog['posts'], key=lambda x: x['title'], reverse=True)
-        assert_equal(blog['posts'][0]['title'], 'Test2 title')
-        assert_equal(blog['posts'][0]['text'], 'test2 post')
-        assert_equal(blog['posts'][1]['title'], 'Test title')
-        assert_equal(blog['posts'][1]['text'], 'test post')
-        assert_equal(blog['posts'][1]['labels'],
+        assert blog['posts'][0]['title'] == 'Test2 title'
+        assert blog['posts'][0]['text'] == 'test2 post'
+        assert blog['posts'][1]['title'] == 'Test title'
+        assert blog['posts'][1]['text'] == 'test post'
+        assert (blog['posts'][1]['labels'] ==
                      ['the firstlabel', 'the second label'])
-        assert_equal(blog['posts'][1]['discussion_thread']
-                     ['posts'][0]['text'], 'test comment')
+        assert (blog['posts'][1]['discussion_thread']
+                     ['posts'][0]['text'] == 'test comment')
 
     @td.with_tool('test', 'Blog', 'blog')
     def test_export_with_attachments(self):
@@ -148,6 +148,6 @@ class TestBulkExport:
             post.discussion_thread._id,
             list(post.discussion_thread.post_class().query.find())[0].slug
         )
-        assert_equal(blog['posts'][0]['discussion_thread']['posts'][0]
-                     ['attachments'][0]['path'], file_path)
+        assert (blog['posts'][0]['discussion_thread']['posts'][0]
+                     ['attachments'][0]['path'] == file_path)
         assert os.path.exists(os.path.join(temp_dir, file_path))
\ No newline at end of file
diff --git a/ForgeBlog/forgeblog/tests/test_commands.py b/ForgeBlog/forgeblog/tests/test_commands.py
index 2e86b18ed..b1aa45196 100644
--- a/ForgeBlog/forgeblog/tests/test_commands.py
+++ b/ForgeBlog/forgeblog/tests/test_commands.py
@@ -122,14 +122,14 @@ def test_pull_rss_feeds(parsefeed):
     parsefeed.assert_called_with('http://example.com/news/feed/')
     posts = BM.BlogPost.query.find(
         {'app_config_id': tmp_app._id}).sort('timestamp', 1)
-    assert_equal(posts.count(), 4)
+    assert posts.count() == 4
     posts = posts.all()
-    assert_equal(posts[0].title, 'Test')
-    assert_equal(posts[0].text, 'This is a test [link](http://example.com/)')
-    assert_equal(posts[1].title, 'Default Title 2')
-    assert_equal(posts[1].text, 'Test feed [link](http://example.com/)')
-    assert_equal(posts[2].title, 'Default Title 3')
-    assert_equal(posts[2].text, rendered_html_content)
-    assert_equal(posts[3].title, 'Default Title 4')
-    assert_equal(posts[3].text, rendered_html_content)
+    assert posts[0].title == 'Test'
+    assert posts[0].text == 'This is a test [link](http://example.com/)'
+    assert posts[1].title == 'Default Title 2'
+    assert posts[1].text == 'Test feed [link](http://example.com/)'
+    assert posts[2].title == 'Default Title 3'
+    assert posts[2].text == rendered_html_content
+    assert posts[3].title == 'Default Title 4'
+    assert posts[3].text == rendered_html_content
 
diff --git a/ForgeBlog/forgeblog/tests/unit/test_blog_post.py b/ForgeBlog/forgeblog/tests/unit/test_blog_post.py
index 7d5e20108..56c5e2930 100644
--- a/ForgeBlog/forgeblog/tests/unit/test_blog_post.py
+++ b/ForgeBlog/forgeblog/tests/unit/test_blog_post.py
@@ -33,11 +33,11 @@ class TestBlogPost(BlogTestWithModel):
     def test_new(self):
         post = M.BlogPost.new(
             title='test', text='test message', state='published')
-        assert_equal(post.title, 'test')
-        assert_equal(post.text, 'test message')
-        assert_equal(post.state, 'published')
-        assert_equal(post.activity_extras['summary'], post.title)
-        assert_true('allura_id' in post.activity_extras)
+        assert post.title == 'test'
+        assert post.text == 'test message'
+        assert post.state == 'published'
+        assert post.activity_extras['summary'] == post.title
+        assert 'allura_id' in post.activity_extras
 
 
 class TestFeed(BlogTestWithModel):
@@ -57,7 +57,7 @@ class TestFeed(BlogTestWithModel):
             description=post.text,
             author=post.author(),
             pubdate=post.timestamp)
-        assert_equal(f.pubdate, datetime(2012, 10, 29, 9, 57, 21, 465000))
+        assert f.pubdate == datetime(2012, 10, 29, 9, 57, 21, 465000)
 
 
 class TestHtmlPreview(BlogTestWithModel):
@@ -77,14 +77,14 @@ class TestHtmlPreview(BlogTestWithModel):
                 "esse cillum dolore eu fugiat nulla pariatur. Excepteur sint "
                 "occaecat cupidatat non proident, sunt in culpa qui officia "
                 "deserunt mollit anim id est laborum.")
-        assert_equal(self._make_post(text).html_text_preview, wrapped(text))
+        assert self._make_post(text).html_text_preview == wrapped(text)
 
     def test_single_short_paragraph(self):
         text = ("Lorem ipsum dolor sit amet, consectetur adipisicing elit, "
                 "sed do eiusmod tempor incididunt ut labore et dolore magna "
                 "aliqua. Ut enim ad minim veniam, quis nostrud exercitation "
                 "ullamco laboris nisi ut aliquip ex ea commodo consequat.")
-        assert_equal(self._make_post(text).html_text_preview, wrapped(text))
+        assert self._make_post(text).html_text_preview == wrapped(text)
 
     def test_multi_paragraph_short(self):
         text = ("Lorem ipsum dolor sit amet, consectetur adipisicing elit, "
@@ -100,7 +100,7 @@ class TestHtmlPreview(BlogTestWithModel):
                     '<p>Ut enim ad minim veniam, quis nostrud exercitation '
                     'ullamco laboris nisi ut aliquip ex ea commodo '
                     'consequat.</p></div>')
-        assert_equal(self._make_post(text).html_text_preview, expected)
+        assert self._make_post(text).html_text_preview == expected
 
     def test_multi_paragraph_long(self):
         text = ("Lorem ipsum dolor sit amet, consectetur adipisicing elit, "
@@ -134,4 +134,4 @@ class TestHtmlPreview(BlogTestWithModel):
                     'anim id est laborum.... '
                     '<a class="" href="/p/test/blog/%s/%02i/untitled/">'
                     'read more</a></p></div>') % (now.year, now.month)
-        assert_equal(self._make_post(text).html_text_preview, expected)
+        assert self._make_post(text).html_text_preview == expected
diff --git a/ForgeChat/forgechat/tests/functional/test_root.py b/ForgeChat/forgechat/tests/functional/test_root.py
index 96426c140..024e3a460 100644
--- a/ForgeChat/forgechat/tests/functional/test_root.py
+++ b/ForgeChat/forgechat/tests/functional/test_root.py
@@ -39,9 +39,9 @@ class TestRootController(TestController):
         data = {'channel': 'test channel',
                 '_session_id': self.app.cookies['_session_id']}
         ch = CM.ChatChannel.query.get()
-        assert_equal(ch.channel, '')
+        assert ch.channel == ''
         resp = self.app.post('/p/test/admin/chat/configure', data)
         expected = {'status': 'ok', 'message': 'Chat options updated'}
-        assert_equal(json.loads(self.webflash(resp)), expected)
+        assert json.loads(self.webflash(resp)) == expected
         ch = CM.ChatChannel.query.get()
-        assert_equal(ch.channel, 'test channel')
+        assert ch.channel == 'test channel'
diff --git a/ForgeDiscussion/forgediscussion/tests/functional/test_forum.py b/ForgeDiscussion/forgediscussion/tests/functional/test_forum.py
index bc4a0373a..a20cb16e9 100644
--- a/ForgeDiscussion/forgediscussion/tests/functional/test_forum.py
+++ b/ForgeDiscussion/forgediscussion/tests/functional/test_forum.py
@@ -156,8 +156,8 @@ class TestForumMessageHandling(TestController):
         self.user = M.User.query.get(username='root')
 
     def test_has_access(self):
-        assert_false(c.app.has_access(M.User.anonymous(), 'testforum'))
-        assert_true(c.app.has_access(M.User.query.get(username='root'), 'testforum'))
+        assert not c.app.has_access(M.User.anonymous(), 'testforum')
+        assert c.app.has_access(M.User.query.get(username='root'), 'testforum')
 
     def test_post(self):
         self._post('testforum', 'Test Thread', 'Nothing here')
@@ -168,19 +168,19 @@ class TestForumMessageHandling(TestController):
     def test_reply(self):
         self._post('testforum', 'Test Thread', 'Nothing here',
                    message_id='test_reply@domain.net')
-        assert_equal(FM.ForumThread.query.find().count(), 1)
+        assert FM.ForumThread.query.find().count() == 1
         posts = FM.ForumPost.query.find()
-        assert_equal(posts.count(), 1)
-        assert_equal(FM.ForumThread.query.get().num_replies, 1)
-        assert_equal(FM.ForumThread.query.get().first_post_id, 'test_reply@domain.net')
+        assert posts.count() == 1
+        assert FM.ForumThread.query.get().num_replies == 1
+        assert FM.ForumThread.query.get().first_post_id == 'test_reply@domain.net'
 
         post = posts.first()
         self._post('testforum', 'Test Reply', 'Nothing here, either',
                    message_id='test_reply-msg2@domain.net',
                    in_reply_to=['test_reply@domain.net'])
-        assert_equal(FM.ForumThread.query.find().count(), 1)
-        assert_equal(FM.ForumPost.query.find().count(), 2)
-        assert_equal(FM.ForumThread.query.get().first_post_id, 'test_reply@domain.net')
+        assert FM.ForumThread.query.find().count() == 1
+        assert FM.ForumPost.query.find().count() == 2
+        assert FM.ForumThread.query.get().first_post_id == 'test_reply@domain.net'
 
     def test_reply_using_references_headers(self):
         self._post('testforum', 'Test Thread', 'Nothing here',
@@ -193,8 +193,8 @@ class TestForumMessageHandling(TestController):
                    message_id='second-message-id',
                    in_reply_to=['some-other-id@not.helpful.com'],
                    references=refs)
-        assert_equal(FM.ForumThread.query.find().count(), 1)
-        assert_equal(FM.ForumPost.query.find().count(), 2)
+        assert FM.ForumThread.query.find().count() == 1
+        assert FM.ForumPost.query.find().count() == 2
 
         prev_post = FM.ForumPost.query.find().sort('timestamp', pymongo.DESCENDING).first()
         refs = M.Notification._references(thread, prev_post) + ['second-message-id']
@@ -202,8 +202,8 @@ class TestForumMessageHandling(TestController):
                    message_id='third-message-id',
                    # missing in_reply_to altogether
                    references=refs)
-        assert_equal(FM.ForumThread.query.find().count(), 1)
-        assert_equal(FM.ForumPost.query.find().count(), 3)
+        assert FM.ForumThread.query.find().count() == 1
+        assert FM.ForumPost.query.find().count() == 3
 
     def test_attach(self):
         # runs handle_artifact_message() with filename field
@@ -367,7 +367,7 @@ class TestForum(TestController):
         form['add_forum.description'] = '<a href="http://cnn.com">This is CNN</a>'
         form.submit()
         r = self.app.get('/discussion/')
-        assert_equal(len(r.html.findAll('a', rel='nofollow')), 2)
+        assert len(r.html.findAll('a', rel='nofollow')) == 2
 
     def test_forum_search(self):
         self.app.get('/discussion/search')
@@ -459,13 +459,13 @@ class TestForum(TestController):
             params[f.find('input', {'style': 'width: 90%'})['name']] = "this is my post"
             r = self.app.post('/discussion/save_new_topic', params=params)
 
-        assert_equal(5, FM.ForumPost.query.find({'status': 'ok'}).count())
+        assert 5 == FM.ForumPost.query.find({'status': 'ok'}).count()
 
         r = self.app.post('/discussion/testforum/moderate/save_moderation_bulk_user', params={
             'username': 'test-admin',
             'spam': '1'})
-        assert_in('5 posts marked as spam', self.webflash(r))
-        assert_equal(5, FM.ForumPost.query.find({'status': 'spam'}).count())
+        assert '5 posts marked as spam' in self.webflash(r)
+        assert 5 == FM.ForumPost.query.find({'status': 'spam'}).count()
 
     def test_posting(self):
         r = self.app.get('/discussion/create_topic/')
@@ -514,7 +514,7 @@ class TestForum(TestController):
         r = self.app.post('/discussion/save_new_topic', params=params)
         n = M.Notification.query.find(
             dict(subject="[test:discussion] this is <h2> o'clock")).first()
-        assert_in('---\n\n[this is &lt;h2&gt; o&#39;clock]', n.text)
+        assert '---\n\n[this is &lt;h2&gt; o&#39;clock]' in n.text
 
     def _set_anon_allowed(self):
         r = self.app.get('/admin/discussion/permissions')
@@ -557,7 +557,7 @@ class TestForum(TestController):
         assert 'name="approve"' not in r
         assert 'name="spam"' not in r
         assert "Post content" not in r
-        assert_equal(spam_checker.check.call_args[0][0], 'Test Thread\nPost content')
+        assert spam_checker.check.call_args[0][0] == 'Test Thread\nPost content'
 
         # assert unapproved thread replies do not appear
         f = thread.html.find('div', {'class': 'comment-row reply_post_form'}).find('form')
@@ -572,7 +572,7 @@ class TestForum(TestController):
         r = self.app.get(thread.request.url,
                          extra_environ=dict(username='*anonymous'))
         assert 'anon reply to anon post' not in r
-        assert_equal(spam_checker.check.call_args[0][0], 'anon reply to anon post content')
+        assert spam_checker.check.call_args[0][0] == 'anon reply to anon post content'
 
         # assert moderation controls appear for admin
         r = self.app.get(thread.request.url)
@@ -619,8 +619,8 @@ class TestForum(TestController):
         ThreadLocalORMSession.flush_all()
         t = M.Thread()
         p = M.Post(thread=t)
-        assert_in('TestRole', [r.name for r in c.project.named_roles])
-        assert_false(t.is_spam(p))
+        assert 'TestRole' in [r.name for r in c.project.named_roles]
+        assert not t.is_spam(p)
 
     def test_thread(self):
         r = self.app.get('/discussion/create_topic/')
@@ -717,7 +717,7 @@ class TestForum(TestController):
     def check_announcement_table(self, response, topic_name):
         assert response.html.find(text='Announcements')
         rows = self.get_table_rows(response, 'announcements')
-        assert_equal(len(rows), 1)
+        assert len(rows) == 1
         cell = rows[0].findAll('td', {'class': 'topic'})
         assert topic_name in str(cell)
 
@@ -739,7 +739,7 @@ class TestForum(TestController):
             flags='Announcement',
             discussion='testforum'))
         thread2 = FM.ForumThread.query.get(_id=thread_id)
-        assert_equal(thread2.flags, ['Announcement'])
+        assert thread2.flags == ['Announcement']
 
         # Check that announcements are on front discussion page
         r = self.app.get('/discussion/')
@@ -804,7 +804,7 @@ class TestForum(TestController):
         # Check that threads are ordered in reverse creation order
         r = self.app.get('/discussion/testforum/')
         rows = self.get_table_rows(r, 'forum_threads')
-        assert_equal(len(rows), 2)
+        assert len(rows) == 2
         assert 'topic2' in str(rows[0])
         assert 'topic1' in str(rows[1])
 
@@ -813,12 +813,12 @@ class TestForum(TestController):
             flags='Sticky',
             discussion='testforum'))
         thread1 = FM.ForumThread.query.get(_id=tid1)
-        assert_equal(thread1.flags, ['Sticky'])
+        assert thread1.flags == ['Sticky']
 
         # Check that Sticky thread is at the top
         r = self.app.get('/discussion/testforum/')
         rows = self.get_table_rows(r, 'forum_threads')
-        assert_equal(len(rows), 2)
+        assert len(rows) == 2
         assert 'topic1' in rows[0].text
         assert 'topic2' in rows[1].text
 
@@ -827,14 +827,14 @@ class TestForum(TestController):
             flags='',
             discussion='testforum'))
         thread1 = FM.ForumThread.query.get(_id=tid1)
-        assert_equal(thread1.flags, [])
+        assert thread1.flags == []
 
         # Would check that threads are again in reverse creation order,
         # but so far we actually sort by mod_date, and resetting a flag
         # updates it
         r = self.app.get('/discussion/testforum/')
         rows = self.get_table_rows(r, 'forum_threads')
-        assert_equal(len(rows), 2)
+        assert len(rows) == 2
         # assert 'topic2' in str(rows[0])
         # assert 'topic1' in str(rows[1])
 
@@ -868,7 +868,7 @@ class TestForum(TestController):
         # make sure the posts are in the original thread
         posts = thread.html.find('div', {'id': 'comment'}).findAll(
             'div', {'class': 'discussion-post'})
-        assert_equal(len(posts), 2)
+        assert len(posts) == 2
         # move the thread
         r = self.app.post(url + 'moderate', params=dict(
             flags='',
@@ -876,7 +876,7 @@ class TestForum(TestController):
         # make sure all the posts got moved
         posts = r.html.find('div', {'id': 'comment'}).findAll(
             'div', {'class': 'discussion-post'})
-        assert_equal(len(posts), 2)
+        assert len(posts) == 2
 
     def test_rename_thread(self):
         # make the topic
@@ -914,11 +914,11 @@ class TestForum(TestController):
         sidebar = r.html.find('div', {'id': 'sidebar'})
         sidebar_menu = str(sidebar)
         sidebar_links = [i['href'] for i in sidebar.findAll('a')]
-        assert_in("/p/test/discussion/create_topic/", sidebar_links)
-        assert_in("/p/test/discussion/new_forum", sidebar_links)
-        assert_in('<h3 class="">Help</h3>', sidebar_menu)
-        assert_in("/nf/markdown_syntax", sidebar_links)
-        assert_not_in("flag_as_spam", sidebar_links)
+        assert "/p/test/discussion/create_topic/" in sidebar_links
+        assert "/p/test/discussion/new_forum" in sidebar_links
+        assert '<h3 class="">Help</h3>' in sidebar_menu
+        assert "/nf/markdown_syntax" in sidebar_links
+        assert "flag_as_spam" not in sidebar_links
         r = self.app.get('/discussion/create_topic/')
         f = r.html.find('form', {'action': '/p/test/discussion/save_new_topic'})
         params = dict()
@@ -931,18 +931,18 @@ class TestForum(TestController):
         params[f.find('input', {'style': 'width: 90%'})['name']] = 'AAA'
         thread = self.app.post('/discussion/save_new_topic', params=params).follow()
         thread_sidebarmenu = str(thread.html.find('div', {'id': 'sidebar'}))
-        assert_in("flag_as_spam", thread_sidebarmenu)
+        assert "flag_as_spam" in thread_sidebarmenu
 
     def test_sidebar_menu_anon(self):
         r = self.app.get('/discussion/')
         sidebar = r.html.find('div', {'id': 'sidebar'})
         sidebar_menu = str(sidebar)
         sidebar_links = [i['href'] for i in sidebar.findAll('a')]
-        assert_in("/p/test/discussion/create_topic/", sidebar_links)
-        assert_in("/p/test/discussion/new_forum", sidebar_links)
-        assert_in('<h3 class="">Help</h3>', sidebar_menu)
-        assert_in("/nf/markdown_syntax", sidebar_links)
-        assert_not_in("flag_as_spam", sidebar_menu)
+        assert "/p/test/discussion/create_topic/" in sidebar_links
+        assert "/p/test/discussion/new_forum" in sidebar_links
+        assert '<h3 class="">Help</h3>' in sidebar_menu
+        assert "/nf/markdown_syntax" in sidebar_links
+        assert "flag_as_spam" not in sidebar_menu
         r = self.app.get('/discussion/create_topic/')
         f = r.html.find('form', {'action': '/p/test/discussion/save_new_topic'})
         params = dict()
@@ -956,7 +956,7 @@ class TestForum(TestController):
         thread = self.app.post('/discussion/save_new_topic',
                                params=params).follow(extra_environ=dict(username='*anonymous'))
         thread_sidebar_menu = str(thread.html.find('div', {'id': 'sidebar'}))
-        assert_not_in("flag_as_spam", thread_sidebar_menu)
+        assert "flag_as_spam" not in thread_sidebar_menu
 
     def test_feed(self):
         for ext in ['', '.rss', '.atom']:
@@ -1006,7 +1006,7 @@ class TestForum(TestController):
         # View the thread and make sure project last_updated is not updated
         self.app.get(url)
         timestamp_after = M.Project.query.get(shortname='test').last_updated
-        assert_equal(timestamp_before, timestamp_after)
+        assert timestamp_before == timestamp_after
 
 
 class TestForumStats(TestController):
@@ -1042,7 +1042,7 @@ class TestForumStats(TestController):
         ])
         r = self.app.get(
             '/discussion/stats_data?begin=2013-01-01&end=2013-01-06')
-        assert_equal(r.json, {
+        assert r.json == {
             'begin': '2013-01-01 00:00:00',
             'end': '2013-01-06 00:00:00',
             'data': [
@@ -1053,4 +1053,4 @@ class TestForumStats(TestController):
                 [1357344000000, 2],
                 [1357430400000, 0],
             ]
-        })
+        }
diff --git a/ForgeDiscussion/forgediscussion/tests/functional/test_import.py b/ForgeDiscussion/forgediscussion/tests/functional/test_import.py
index 8a49ae218..ff7449d1e 100644
--- a/ForgeDiscussion/forgediscussion/tests/functional/test_import.py
+++ b/ForgeDiscussion/forgediscussion/tests/functional/test_import.py
@@ -109,15 +109,15 @@ class TestImportController(TestRestApiBase):  # TestController):
         return t.replace('T', ' ').replace('Z', '')
 
     def verify_ticket(self, from_api, org):
-        assert_equal(from_api['status'], org['status'])
-        assert_equal(from_api['description'], org['description'])
-        assert_equal(from_api['summary'], org['summary'])
-        assert_equal(from_api['ticket_num'], org['id'])
-        assert_equal(from_api['created_date'],
+        assert from_api['status'] == org['status']
+        assert from_api['description'] == org['description']
+        assert from_api['summary'] == org['summary']
+        assert from_api['ticket_num'] == org['id']
+        assert (from_api['created_date'] ==
                      self.time_normalize(org['date']))
-        assert_equal(from_api['mod_date'],
+        assert (from_api['mod_date'] ==
                      self.time_normalize(org['date_updated']))
-        assert_equal(from_api['custom_fields']
-                     ['_resolution'], org['resolution'])
-        assert_equal(from_api['custom_fields']['_cc'], org['cc'])
-        assert_equal(from_api['custom_fields']['_private'], org['private'])
+        assert (from_api['custom_fields']
+                     ['_resolution'] == org['resolution'])
+        assert from_api['custom_fields']['_cc'] == org['cc']
+        assert from_api['custom_fields']['_private'] == org['private']
diff --git a/ForgeDiscussion/forgediscussion/tests/functional/test_rest.py b/ForgeDiscussion/forgediscussion/tests/functional/test_rest.py
index 5f42de636..b20d610a2 100644
--- a/ForgeDiscussion/forgediscussion/tests/functional/test_rest.py
+++ b/ForgeDiscussion/forgediscussion/tests/functional/test_rest.py
@@ -66,55 +66,55 @@ class TestRootRestController(TestDiscussionApiBase):
     def test_forum_list(self):
         forums = self.api_get('/rest/p/test/discussion/')
         forums = forums.json['forums']
-        assert_equal(len(forums), 2)
+        assert len(forums) == 2
         forums = sorted(forums, key=lambda x: x['name'])
-        assert_equal(forums[0]['name'], 'General Discussion')
-        assert_equal(
-            forums[0]['description'], 'Forum about anything you want to talk about.')
-        assert_equal(forums[0]['num_topics'], 2)
-        assert_equal(
-            forums[0]['url'], 'http://localhost/rest/p/test/discussion/general/')
-        assert_equal(forums[0]['last_post']['subject'], 'Hi guys')
-        assert_equal(forums[0]['last_post']['author'], 'test-admin')
-        assert_equal(forums[0]['last_post']['text'], 'Hi boys and girls')
-        assert_equal(forums[1]['name'], 'Say Héllo')
-        assert_equal(forums[1]['description'], 'Say héllo here')
-        assert_equal(forums[1]['num_topics'], 0)
-        assert_equal(
-            forums[1]['url'], 'http://localhost/rest/p/test/discussion/h%C3%A9llo/')
-        assert_equal(forums[1]['last_post'], None)
+        assert forums[0]['name'] == 'General Discussion'
+        assert (
+            forums[0]['description'] == 'Forum about anything you want to talk about.')
+        assert forums[0]['num_topics'] == 2
+        assert (
+            forums[0]['url'] == 'http://localhost/rest/p/test/discussion/general/')
+        assert forums[0]['last_post']['subject'] == 'Hi guys'
+        assert forums[0]['last_post']['author'] == 'test-admin'
+        assert forums[0]['last_post']['text'] == 'Hi boys and girls'
+        assert forums[1]['name'] == 'Say Héllo'
+        assert forums[1]['description'] == 'Say héllo here'
+        assert forums[1]['num_topics'] == 0
+        assert (
+            forums[1]['url'] == 'http://localhost/rest/p/test/discussion/h%C3%A9llo/')
+        assert forums[1]['last_post'] == None
 
     def test_forum(self):
         forum = self.api_get('/rest/p/test/discussion/general/')
         forum = forum.json['forum']
-        assert_equal(forum['name'], 'General Discussion')
-        assert_equal(
-            forum['description'], 'Forum about anything you want to talk about.')
+        assert forum['name'] == 'General Discussion'
+        assert (
+            forum['description'] == 'Forum about anything you want to talk about.')
         topics = forum['topics']
-        assert_equal(len(topics), 2)
-        assert_equal(topics[0]['subject'], 'Hi guys')
-        assert_equal(topics[0]['num_views'], 0)
-        assert_equal(topics[0]['num_replies'], 1)
-        assert_equal(topics[0]['last_post']['author'], 'test-admin')
-        assert_equal(topics[0]['last_post']['text'], 'Hi boys and girls')
+        assert len(topics) == 2
+        assert topics[0]['subject'] == 'Hi guys'
+        assert topics[0]['num_views'] == 0
+        assert topics[0]['num_replies'] == 1
+        assert topics[0]['last_post']['author'] == 'test-admin'
+        assert topics[0]['last_post']['text'] == 'Hi boys and girls'
         t = ForumThread.query.find({'subject': 'Hi guys'}).first()
         url = 'http://localhost/rest/p/test/discussion/general/thread/%s/' % t._id
-        assert_equal(topics[0]['url'], url)
-        assert_equal(topics[1]['subject'], 'Let\'s talk')
-        assert_equal(topics[1]['num_views'], 0)
-        assert_equal(topics[1]['num_replies'], 1)
-        assert_equal(topics[1]['last_post']['author'], 'test-admin')
-        assert_equal(topics[1]['last_post']['text'], '1st post')
+        assert topics[0]['url'] == url
+        assert topics[1]['subject'] == 'Let\'s talk'
+        assert topics[1]['num_views'] == 0
+        assert topics[1]['num_replies'] == 1
+        assert topics[1]['last_post']['author'] == 'test-admin'
+        assert topics[1]['last_post']['text'] == '1st post'
         t = ForumThread.query.find({'subject': 'Let\'s talk'}).first()
         url = 'http://localhost/rest/p/test/discussion/general/thread/%s/' % t._id
-        assert_equal(topics[1]['url'], url)
+        assert topics[1]['url'] == url
 
     def test_forum_show_ok_topics(self):
         forum = self.api_get('/rest/p/test/discussion/general/')
         forum = forum.json['forum']
-        assert_equal(forum['name'], 'General Discussion')
+        assert forum['name'] == 'General Discussion'
         topics = forum['topics']
-        assert_equal(len(topics), 2)
+        assert len(topics) == 2
         self.create_topic('general', 'Hi again', 'It should not be shown')
         t = ForumThread.query.find({'subject': 'Hi again'}).first()
         first_post = t.first_post
@@ -122,57 +122,57 @@ class TestRootRestController(TestDiscussionApiBase):
         first_post.commit()
         forum = self.api_get('/rest/p/test/discussion/general/')
         forum = forum.json['forum']
-        assert_equal(forum['name'], 'General Discussion')
+        assert forum['name'] == 'General Discussion'
         topics = forum['topics']
-        assert_equal(len(topics), 2)
+        assert len(topics) == 2
 
     def test_topic(self):
         forum = self.api_get('/rest/p/test/discussion/general/')
         forum = forum.json['forum']
-        assert_equal(forum['name'], 'General Discussion')
-        assert_equal(
-            forum['description'], 'Forum about anything you want to talk about.')
+        assert forum['name'] == 'General Discussion'
+        assert (
+            forum['description'] == 'Forum about anything you want to talk about.')
         topics = forum['topics']
         topic = self.api_get(topics[0]['url'][len('http://localhost'):])
         topic = topic.json['topic']
-        assert_equal(len(topic['posts']), 1)
-        assert_equal(topic['subject'], 'Hi guys')
-        assert_equal(topic['posts'][0]['text'], 'Hi boys and girls')
-        assert_equal(topic['posts'][0]['subject'], 'Hi guys')
-        assert_in('timestamp', topic['posts'][0])
-        assert_in('last_edited', topic['posts'][0])
+        assert len(topic['posts']) == 1
+        assert topic['subject'] == 'Hi guys'
+        assert topic['posts'][0]['text'] == 'Hi boys and girls'
+        assert topic['posts'][0]['subject'] == 'Hi guys'
+        assert 'timestamp' in topic['posts'][0]
+        assert 'last_edited' in topic['posts'][0]
 
     def test_forum_list_pagination(self):
         resp = self.app.get('/rest/p/test/discussion/?limit=1')
         forums = resp.json['forums']
-        assert_equal(len(forums), 1)
-        assert_equal(forums[0]['name'], 'General Discussion')
-        assert_equal(resp.json['count'], 2)
-        assert_equal(resp.json['page'], 0)
-        assert_equal(resp.json['limit'], 1)
+        assert len(forums) == 1
+        assert forums[0]['name'] == 'General Discussion'
+        assert resp.json['count'] == 2
+        assert resp.json['page'] == 0
+        assert resp.json['limit'] == 1
         resp = self.app.get('/rest/p/test/discussion/?limit=1&page=1')
         forums = resp.json['forums']
-        assert_equal(len(forums), 1)
-        assert_equal(forums[0]['name'], 'Say Héllo')
-        assert_equal(resp.json['count'], 2)
-        assert_equal(resp.json['page'], 1)
-        assert_equal(resp.json['limit'], 1)
+        assert len(forums) == 1
+        assert forums[0]['name'] == 'Say Héllo'
+        assert resp.json['count'] == 2
+        assert resp.json['page'] == 1
+        assert resp.json['limit'] == 1
 
     def test_forum_pagination(self):
         resp = self.app.get('/rest/p/test/discussion/general/?limit=1')
         topics = resp.json['forum']['topics']
-        assert_equal(len(topics), 1)
-        assert_equal(topics[0]['subject'], 'Hi guys')
-        assert_equal(resp.json['count'], 2)
-        assert_equal(resp.json['page'], 0)
-        assert_equal(resp.json['limit'], 1)
+        assert len(topics) == 1
+        assert topics[0]['subject'] == 'Hi guys'
+        assert resp.json['count'] == 2
+        assert resp.json['page'] == 0
+        assert resp.json['limit'] == 1
         resp = self.app.get('/rest/p/test/discussion/general/?limit=1&page=1')
         topics = resp.json['forum']['topics']
-        assert_equal(len(topics), 1)
-        assert_equal(topics[0]['subject'], 'Let\'s talk')
-        assert_equal(resp.json['count'], 2)
-        assert_equal(resp.json['page'], 1)
-        assert_equal(resp.json['limit'], 1)
+        assert len(topics) == 1
+        assert topics[0]['subject'] == 'Let\'s talk'
+        assert resp.json['count'] == 2
+        assert resp.json['page'] == 1
+        assert resp.json['limit'] == 1
 
     def test_topic_pagination(self):
         thread = ForumThread.query.find({'subject': 'Hi guys'}).first()
@@ -180,25 +180,25 @@ class TestRootRestController(TestDiscussionApiBase):
         url = '/rest/p/test/discussion/general/thread/%s/' % thread._id
         resp = self.app.get(url + '?limit=1')
         posts = resp.json['topic']['posts']
-        assert_equal(len(posts), 1)
-        assert_equal(posts[0]['text'], 'Hi boys and girls')
-        assert_equal(resp.json['count'], 2)
-        assert_equal(resp.json['page'], 0)
-        assert_equal(resp.json['limit'], 1)
+        assert len(posts) == 1
+        assert posts[0]['text'] == 'Hi boys and girls'
+        assert resp.json['count'] == 2
+        assert resp.json['page'] == 0
+        assert resp.json['limit'] == 1
         resp = self.app.get(url + '?limit=1&page=1')
         posts = resp.json['topic']['posts']
-        assert_equal(len(posts), 1)
-        assert_equal(posts[0]['text'], 'I am second post')
-        assert_equal(resp.json['count'], 2)
-        assert_equal(resp.json['page'], 1)
-        assert_equal(resp.json['limit'], 1)
+        assert len(posts) == 1
+        assert posts[0]['text'] == 'I am second post'
+        assert resp.json['count'] == 2
+        assert resp.json['page'] == 1
+        assert resp.json['limit'] == 1
 
     def test_topic_show_ok_only(self):
         thread = ForumThread.query.find({'subject': 'Hi guys'}).first()
         url = '/rest/p/test/discussion/general/thread/%s/' % thread._id
         resp = self.app.get(url)
         posts = resp.json['topic']['posts']
-        assert_equal(len(posts), 1)
+        assert len(posts) == 1
         thread.post('Hello', 'I am not ok post')
         last_post = thread.last_post
         last_post.status = 'pending'
@@ -206,7 +206,7 @@ class TestRootRestController(TestDiscussionApiBase):
         ThreadLocalORMSession.flush_all()
         resp = self.app.get(url)
         posts = resp.json['topic']['posts']
-        assert_equal(len(posts), 1)
+        assert len(posts) == 1
 
     def test_security(self):
         p = M.Project.query.get(shortname='test')
@@ -240,11 +240,11 @@ class TestRootRestController(TestDiscussionApiBase):
             form['forum-1.members_only'] = True
         form.submit()
         r = self.api_get('/rest/p/test/discussion/')
-        assert_equal(len(r.json['forums']), 2)
+        assert len(r.json['forums']) == 2
         r = self.app.get('/rest/p/test/discussion/',
                          extra_environ={'username': '*anonymous'})
-        assert_equal(len(r.json['forums']), 1)
-        assert_equal(r.json['forums'][0]['shortname'], 'general')
+        assert len(r.json['forums']) == 1
+        assert r.json['forums'][0]['shortname'] == 'general'
 
     def test_has_access_no_params(self):
         self.api_get('/rest/p/test/discussion/has_access', status=404)
@@ -256,13 +256,13 @@ class TestRootRestController(TestDiscussionApiBase):
         r = self.api_get(
             '/rest/p/test/discussion/has_access?user=babadook&perm=read',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
         r = self.api_get(
             '/rest/p/test/discussion/has_access?user=test-user&perm=jump',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
     def test_has_access_not_admin(self):
         """
@@ -278,10 +278,10 @@ class TestRootRestController(TestDiscussionApiBase):
         r = self.api_get(
             '/rest/p/test/discussion/has_access?user=test-admin&perm=post',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], True)
+        assert r.status_int == 200
+        assert r.json['result'] == True
         r = self.api_get(
             '/rest/p/test/discussion/has_access?user=*anonymous&perm=admin',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
diff --git a/ForgeDiscussion/forgediscussion/tests/test_app.py b/ForgeDiscussion/forgediscussion/tests/test_app.py
index b93666e48..bb0b8d64b 100644
--- a/ForgeDiscussion/forgediscussion/tests/test_app.py
+++ b/ForgeDiscussion/forgediscussion/tests/test_app.py
@@ -48,7 +48,7 @@ class TestApp(TestDiscussionApiBase):  # creates some sample data
     @td.with_discussion
     def test_tickets_stats_24hr(self):
         # invoked normally via entry point
-        assert_equal(2, posts_24hr())
+        assert 2 == posts_24hr()
 
 
 class TestAppSitemap:
@@ -60,27 +60,27 @@ class TestAppSitemap:
 
     @td.with_discussion
     def test_sitemap_xml(self):
-        assert_equal([], c.app.sitemap_xml())
+        assert [] == c.app.sitemap_xml()
         forum = utils.create_forum(c.app, dict(
             shortname='test-forum',
             name="Test Forum",
             description="Test Forum Description",
         ))
         ThreadLocalORMSession.flush_all()
-        assert_equal([], c.app.sitemap_xml())
+        assert [] == c.app.sitemap_xml()
         thread = ForumThread(
             subject='test-thread',
         )
         thread.set_forum(forum)
         ThreadLocalORMSession.flush_all()
 
-        assert_equal([], c.app.sitemap_xml())
+        assert [] == c.app.sitemap_xml()
         thread.post(
             subject='test-post',
             text='this is a test post.',
         )
         ThreadLocalORMSession.flush_all()
-        assert_equal(1, len(c.app.sitemap_xml()))
+        assert 1 == len(c.app.sitemap_xml())
 
 
 class TestBulkExport(TestDiscussionApiBase):
@@ -98,22 +98,22 @@ class TestBulkExport(TestDiscussionApiBase):
         discussion = json.loads(f.read())
         forums = sorted(discussion['forums'], key=lambda x: x['name'])
 
-        assert_equal(forums[0]['shortname'], 'general')
-        assert_equal(
-            forums[0]['description'], 'Forum about anything you want to talk about.')
-        assert_equal(forums[0]['name'], 'General Discussion')
+        assert forums[0]['shortname'] == 'general'
+        assert (
+            forums[0]['description'] == 'Forum about anything you want to talk about.')
+        assert forums[0]['name'] == 'General Discussion'
         forums[0]['threads'] = sorted(forums[0]['threads'],
                                       key=lambda x: x['posts'][0]['subject'])
-        assert_equal(
-            forums[0]['threads'][0]['posts'][0]['text'], 'Hi boys and girls')
-        assert_equal(
-            forums[0]['threads'][0]['posts'][0]['subject'], 'Hi guys')
-        assert_equal(forums[0]['threads'][1]['posts'][0]['text'], '1st post')
-        assert_equal(
-            forums[0]['threads'][1]['posts'][0]['subject'], "Let's talk")
-        assert_equal(forums[1]['shortname'], 'héllo')
-        assert_equal(forums[1]['description'], 'Say héllo here')
-        assert_equal(forums[1]['name'], 'Say Héllo')
+        assert (
+            forums[0]['threads'][0]['posts'][0]['text'] == 'Hi boys and girls')
+        assert (
+            forums[0]['threads'][0]['posts'][0]['subject'] == 'Hi guys')
+        assert forums[0]['threads'][1]['posts'][0]['text'] == '1st post'
+        assert (
+            forums[0]['threads'][1]['posts'][0]['subject'] == "Let's talk")
+        assert forums[1]['shortname'] == 'héllo'
+        assert forums[1]['description'] == 'Say héllo here'
+        assert forums[1]['name'] == 'Say Héllo'
 
     def test_export_with_attachments(self):
         project = M.Project.query.get(shortname='test')
@@ -142,5 +142,5 @@ class TestBulkExport(TestDiscussionApiBase):
             post.slug,
             'test_file'
         )
-        assert_equal(threads[0]['posts'][0]['attachments'][0]['path'], file_path)
+        assert threads[0]['posts'][0]['attachments'][0]['path'] == file_path
         os.path.exists(file_path)
diff --git a/ForgeFeedback/forgefeedback/tests/functional/test_root.py b/ForgeFeedback/forgefeedback/tests/functional/test_root.py
index 371d491b6..37866f797 100644
--- a/ForgeFeedback/forgefeedback/tests/functional/test_root.py
+++ b/ForgeFeedback/forgefeedback/tests/functional/test_root.py
@@ -38,31 +38,31 @@ class TestFeedback(TestController):
         self.app.get('/feedback/')
         r = self.app.get('/p/test/feedback')
         assert 'test' in r
-        assert_in('<a href="/p/test/feedback/new_feedback">Feedback</a>', r)
+        assert '<a href="/p/test/feedback/new_feedback">Feedback</a>' in r
 
     def test_new_feedback(self):
         c.user = M.User.by_username('test-admin')
         self.app.get('/feedback/')
         r = self.app.get('/p/test/feedback/new_feedback/')
-        assert_in('Provide your feedback for <b> Test Project</b>', r)
-        assert_in('Enter your feedback here', r)
+        assert 'Provide your feedback for <b> Test Project</b>' in r
+        assert 'Enter your feedback here' in r
 
     def test_create_feedback(self):
         resp = post_feedback(self)
         resp = resp.follow()
-        assert_in('Good tool', resp)
+        assert 'Good tool' in resp
 
     def test_edit_feedback(self):
         post_feedback(self)
         data = {'rating': '2', 'description': 'Not useful'}
         resp = self.app.post('/p/test/feedback/edit_user_review', data)
         resp = resp.follow()
-        assert_in('Not useful', resp)
+        assert 'Not useful' in resp
 
     def test_delete_feedback(self):
         post_feedback(self)
         resp = self.app.post('/p/test/feedback/delete_feedback')
-        assert_in('Success', resp)
+        assert 'Success' in resp
 
 
 def post_feedback(self):
diff --git a/ForgeFeedback/forgefeedback/tests/test_feedback_roles.py b/ForgeFeedback/forgefeedback/tests/test_feedback_roles.py
index 19d335dd9..39ba76c70 100644
--- a/ForgeFeedback/forgefeedback/tests/test_feedback_roles.py
+++ b/ForgeFeedback/forgefeedback/tests/test_feedback_roles.py
@@ -48,7 +48,7 @@ def test_role_assignments():
     def check_access(perm):
         pred = security.has_access(c.app, perm)
         return pred(user=admin), pred(user=user), pred(user=anon)
-    assert_equal(check_access('read'), (True, True, True))
-    assert_equal(check_access('create'), (True, True, False))
-    assert_equal(check_access('update'), (True, False, False))
-    assert_equal(check_access('delete'), (True, False, False))
+    assert check_access('read') == (True, True, True)
+    assert check_access('create') == (True, True, False)
+    assert check_access('update') == (True, False, False)
+    assert check_access('delete') == (True, False, False)
diff --git a/ForgeFeedback/forgefeedback/tests/unit/test_feedback.py b/ForgeFeedback/forgefeedback/tests/unit/test_feedback.py
index b4996b310..a5863d3d4 100644
--- a/ForgeFeedback/forgefeedback/tests/unit/test_feedback.py
+++ b/ForgeFeedback/forgefeedback/tests/unit/test_feedback.py
@@ -29,14 +29,14 @@ class TestFeedback(FeedbackTestWithModel):
         feedback = M.Feedback()
         feedback.rating = '4'
         feedback.description = 'Very good tool'
-        assert_equal(feedback.rating, '4')
-        assert_equal(feedback.description, 'Very good tool')
-        assert_equal(feedback.activity_extras['summary'], feedback.description)
-        assert_true('allura_id' in feedback.activity_extras)
+        assert feedback.rating == '4'
+        assert feedback.description == 'Very good tool'
+        assert feedback.activity_extras['summary'] == feedback.description
+        assert 'allura_id' in feedback.activity_extras
 
     def test_index(self):
         feedback = M.Feedback()
         feedback.rating = '4'
         feedback.description = 'Good tool'
         result = feedback.index()
-        assert_equal(result["text"], 'Good tool')
+        assert result["text"] == 'Good tool'
diff --git a/ForgeFeedback/forgefeedback/tests/unit/test_root_controller.py b/ForgeFeedback/forgefeedback/tests/unit/test_root_controller.py
index a4ac76124..d636594a8 100644
--- a/ForgeFeedback/forgefeedback/tests/unit/test_root_controller.py
+++ b/ForgeFeedback/forgefeedback/tests/unit/test_root_controller.py
@@ -56,7 +56,7 @@ class TestFeedbackApp(FeedbackTestWithModel):
     def test_getRating(self):
         create_feedbacks()
         rating = feedback_main.RootController().getRating()
-        assert_equal(rating, 3.5)
+        assert rating == 3.5
 
     def test_edit_feedback(self):
         create_feedbacks()
diff --git a/ForgeFiles/forgefiles/tests/functional/test_root.py b/ForgeFiles/forgefiles/tests/functional/test_root.py
index da6b6754a..999fd5367 100644
--- a/ForgeFiles/forgefiles/tests/functional/test_root.py
+++ b/ForgeFiles/forgefiles/tests/functional/test_root.py
@@ -77,7 +77,7 @@ class TestFiles(TestController):
         data1 = {'folder_id': str(folder_object._id), 'remarks': 'Publishing new Version'}
         self.app.post('/p/test/files/publish_folder', data1)
         resp = self.app.get('/files/')
-        assert_equals(folder_object.published, True)
+        assert folder_object.published == True
 
     def test_link_file(self):
         file_object = upload_file(self)
@@ -85,7 +85,7 @@ class TestFiles(TestController):
         data1 = {'file_id': str(db_file_object._id)}
         self.app.post('/p/test/files/link_file', data1)
         resp = self.app.get('/files/')
-        assert_true(str(db_file_object.linked_to_download) in resp)
+        assert str(db_file_object.linked_to_download) in resp
 
     def test_disable_folder(self):
         create_folder(self)
@@ -93,7 +93,7 @@ class TestFiles(TestController):
         data1 = {'folder_id': str(folder_object._id), 'status': 'True'}
         self.app.post('/p/test/files/disable_folder', data1)
         resp = self.app.get('/files/')
-        assert_true(str(folder_object.disabled) in resp)
+        assert str(folder_object.disabled) in resp
 
     def test_disable_file(self):
         file_object = upload_file(self)
@@ -101,7 +101,7 @@ class TestFiles(TestController):
         data1 = {'file_id': str(db_file_object._id), 'status': 'True'}
         self.app.post('/p/test/files/disable_file', data1)
         resp = self.app.get('/files/')
-        assert_true(str(db_file_object.disabled) in resp)
+        assert str(db_file_object.disabled) in resp
 
     def test_delete_folder(self):
         create_folder(self)
diff --git a/ForgeFiles/forgefiles/tests/model/test_files.py b/ForgeFiles/forgefiles/tests/model/test_files.py
index a9a6b5eb3..38929e68e 100644
--- a/ForgeFiles/forgefiles/tests/model/test_files.py
+++ b/ForgeFiles/forgefiles/tests/model/test_files.py
@@ -34,10 +34,10 @@ class TestUpload(FilesTestWithModel):
         upload_folder.published = True
         upload_folder.remark = 'Publishing new Version'
         upload_folder.disabled = False
-        assert_equal(upload_folder.folder_name, 'testFolder')
-        assert_true(upload_folder.published)
-        assert_equal(upload_folder.remark, 'Publishing new Version')
-        assert_false(upload_folder.disabled)
+        assert upload_folder.folder_name == 'testFolder'
+        assert upload_folder.published
+        assert upload_folder.remark == 'Publishing new Version'
+        assert not upload_folder.disabled
 
     def test_upload_file(self):
         '''Creates an object of the UploadFiles Collection and tests its fields'''
@@ -48,7 +48,7 @@ class TestUpload(FilesTestWithModel):
         upload_file.file_url = 'TestFolder/testFile'
         upload_file.linked_to_download = True
         upload_file.published = False
-        assert_equal(upload_file.filename, 'testFile')
-        assert_equal(upload_file.filetype, 'project_file')
-        assert_true(upload_file.linked_to_download)
-        assert_false(upload_file.published)
+        assert upload_file.filename == 'testFile'
+        assert upload_file.filetype == 'project_file'
+        assert upload_file.linked_to_download
+        assert not upload_file.published
diff --git a/ForgeFiles/forgefiles/tests/test_files_roles.py b/ForgeFiles/forgefiles/tests/test_files_roles.py
index 203f331ce..2675a3e51 100644
--- a/ForgeFiles/forgefiles/tests/test_files_roles.py
+++ b/ForgeFiles/forgefiles/tests/test_files_roles.py
@@ -47,7 +47,7 @@ def test_role_assignments():
     def check_access(perm):
         pred = security.has_access(c.app, perm)
         return pred(user=admin), pred(user=user), pred(user=anon)
-    assert_equal(check_access('read'), (True, True, True))
-    assert_equal(check_access('create'), (True, False, False))
-    assert_equal(check_access('update'), (True, False, False))
-    assert_equal(check_access('delete'), (True, False, False))
+    assert check_access('read') == (True, True, True)
+    assert check_access('create') == (True, False, False)
+    assert check_access('update') == (True, False, False)
+    assert check_access('delete') == (True, False, False)
diff --git a/ForgeGit/forgegit/tests/functional/test_auth.py b/ForgeGit/forgegit/tests/functional/test_auth.py
index c5bb1cdab..d0bacfa6d 100644
--- a/ForgeGit/forgegit/tests/functional/test_auth.py
+++ b/ForgeGit/forgegit/tests/functional/test_auth.py
@@ -86,6 +86,6 @@ class TestGitUserPermissions(TestController):
     def test_list_repos(self):
         r = self.app.get('/auth/repo_permissions',
                          params=dict(username='test-admin'), status=200)
-        assert_equal(json.loads(r.text), {"allow_write": [
+        assert json.loads(r.text) == {"allow_write": [
             '/git/test/src-git',
-        ]})
+        ]}
diff --git a/ForgeGit/forgegit/tests/functional/test_controllers.py b/ForgeGit/forgegit/tests/functional/test_controllers.py
index 0a966d04e..cabeb2b0c 100644
--- a/ForgeGit/forgegit/tests/functional/test_controllers.py
+++ b/ForgeGit/forgegit/tests/functional/test_controllers.py
@@ -109,7 +109,7 @@ class TestUIController(TestController):
                         'added', 'eee.txt',
                         'added', 'ggg.txt']
         for i, item in enumerate(sortedCommits):
-            assert_equal(actualCommit[i], ''.join(item.findAll(text=True)).strip())
+            assert actualCommit[i] == ''.join(item.findAll(text=True)).strip()
 
 
 class TestRootController(_TestCase):
@@ -156,8 +156,8 @@ class TestRootController(_TestCase):
     def test_commit_browser_data(self):
         resp = self.app.get('/src-git/commit_browser_data')
         data = json.loads(resp.text)
-        assert_equal(
-            data['built_tree']['df30427c488aeab84b2352bdf88a3b19223f9d7a'],
+        assert (
+            data['built_tree']['df30427c488aeab84b2352bdf88a3b19223f9d7a'] ==
             {'url': '/p/test/src-git/ci/df30427c488aeab84b2352bdf88a3b19223f9d7a/',
              'oid': 'df30427c488aeab84b2352bdf88a3b19223f9d7a',
              'short_id': '[df3042]',
@@ -175,7 +175,7 @@ class TestRootController(_TestCase):
         assert '<div class="markdown_content"><p>Change README</div>' in resp, resp
         assert 'tree/README?format=raw">Download</a>' not in resp
         assert 'Tree' in resp.html.findAll('td')[2].text, resp.html.findAll('td')[2].text
-        assert_in('by Rick Copeland', squish_spaces(resp.html.findAll('td')[0].text))
+        assert 'by Rick Copeland' in squish_spaces(resp.html.findAll('td')[0].text)
         resp = self.app.get('/src-git/ci/1e146e67985dcd71c74de79613719bef7bddca4a/log/?path=/README')
         assert 'View' in resp.html.findAll('td')[2].text
         assert 'Change README' in resp
@@ -230,29 +230,29 @@ class TestRootController(_TestCase):
             r = self.app.get('/src-git/feed%s' % ext)
             channel = r.xml.find('channel')
             title = channel.find('title').text
-            assert_equal(title, 'test Git changes')
+            assert title == 'test Git changes'
             description = channel.find('description').text
-            assert_equal(description,
+            assert (description ==
                          'Recent changes to Git repository in test project')
             link = channel.find('link').text
-            assert_equal(link, 'http://localhost/p/test/src-git/')
+            assert link == 'http://localhost/p/test/src-git/'
             earliest_commit = channel.findall('item')[-1]
-            assert_equal(earliest_commit.find('title').text, 'Initial commit')
+            assert earliest_commit.find('title').text == 'Initial commit'
             link = 'http://localhost/p/test/src-git/ci/9a7df788cf800241e3bb5a849c8870f2f8259d98/'
-            assert_equal(earliest_commit.find('link').text, link)
-            assert_equal(earliest_commit.find('guid').text, link)
+            assert earliest_commit.find('link').text == link
+            assert earliest_commit.find('guid').text == link
 
         # .atom has slightly different structure
         prefix = '{http://www.w3.org/2005/Atom}'
         r = self.app.get('/src-git/feed.atom')
         title = r.xml.find(prefix + 'title').text
-        assert_equal(title, 'test Git changes')
+        assert title == 'test Git changes'
         link = r.xml.find(prefix + 'link').attrib['href']
-        assert_equal(link, 'http://localhost/p/test/src-git/')
+        assert link == 'http://localhost/p/test/src-git/'
         earliest_commit = r.xml.findall(prefix + 'entry')[-1]
-        assert_equal(earliest_commit.find(prefix + 'title').text, 'Initial commit')
+        assert earliest_commit.find(prefix + 'title').text == 'Initial commit'
         link = 'http://localhost/p/test/src-git/ci/9a7df788cf800241e3bb5a849c8870f2f8259d98/'
-        assert_equal(earliest_commit.find(prefix + 'link').attrib['href'], link)
+        assert earliest_commit.find(prefix + 'link').attrib['href'] == link
 
     def test_tree(self):
         ci = self._get_ci()
@@ -288,26 +288,26 @@ class TestRootController(_TestCase):
         ci = self._get_ci(repo='/p/test/weird-chars/')
         url = ci + 'tree/' + h.urlquote('привіт.txt') + '?format=raw'
         resp = self.app.get(url)
-        assert_in('Привіт!\nWhich means Hello!', resp.text)
-        assert_equal(six.ensure_text(resp.headers.get('Content-Disposition')),
+        assert 'Привіт!\nWhich means Hello!' in resp.text
+        assert (six.ensure_text(resp.headers.get('Content-Disposition')) ==
                      'attachment;filename="%D0%BF%D1%80%D0%B8%D0%B2%D1%96%D1%82.txt"')
 
         url = ci + 'tree/' + h.urlquote('with space.txt') + '?format=raw'
         resp = self.app.get(url)
-        assert_in('with space', resp.text)
-        assert_equal(six.ensure_text(resp.headers.get('Content-Disposition')),
+        assert 'with space' in resp.text
+        assert (six.ensure_text(resp.headers.get('Content-Disposition')) ==
                      'attachment;filename="with%20space.txt"')
 
         url = ci + 'tree/' + h.urlquote('with%2Furlquote-literal.txt') + '?format=raw'
         resp = self.app.get(url)
-        assert_in('%2F means /', resp.body.decode('utf-8'))
-        assert_equal(resp.headers.get('Content-Disposition'),
+        assert '%2F means /' in resp.body.decode('utf-8')
+        assert (resp.headers.get('Content-Disposition') ==
                      'attachment;filename="with%252Furlquote-literal.txt"')
 
         url = ci + 'tree/' + h.urlquote('with"&:specials.txt') + '?format=raw'
         resp = self.app.get(url)
-        assert_in('"&: encodes as %22%26%3A', resp.body.decode('utf-8'))
-        assert_equal(resp.headers.get('Content-Disposition'),
+        assert '"&: encodes as %22%26%3A' in resp.body.decode('utf-8')
+        assert (resp.headers.get('Content-Disposition') ==
                      'attachment;filename="with%22%26%3Aspecials.txt"')
 
     def test_file_too_large(self):
@@ -336,17 +336,17 @@ class TestRootController(_TestCase):
         ci = self._get_ci(repo='/p/test/weird-chars/')
         resp = self.app.get(h.urlquote(ci + 'tree/привіт.txt') + '?diff=407950e8fba4dbc108ffbce0128ed1085c52cfd7')
         diffhtml = str(resp.html.select_one('.diffbrowser'))
-        assert_in(textwrap.dedent('''\
+        assert (textwrap.dedent('''\
                     <span class="gd">--- a/привіт.txt</span><span class="w"></span>
                     <span class="gi">+++ b/привіт.txt</span><span class="w"></span>
                     <span class="gu">@@ -1 +1,2 @@</span><span class="w"></span>
                     <span class="w"> </span>Привіт!<span class="w"></span>
-                    <span class="gi">+Which means Hello!</span><span class="w"></span>'''),
+                    <span class="gi">+Which means Hello!</span><span class="w"></span>''') in
                   diffhtml)
 
         resp = self.app.get(h.urlquote(ci + 'tree/привіт.txt') + '?diff=407950e8fba4dbc108ffbce0128ed1085c52cfd7&diformat=sidebyside')
         diffhtml = str(resp.html.select_one('.diffbrowser'))
-        assert_in(textwrap.dedent('''\
+        assert (textwrap.dedent('''\
                     <thead>
                     <th class="lineno"></th>
                     <th>a/привіт.txt</th>
@@ -367,7 +367,7 @@ class TestRootController(_TestCase):
                     </pre></td>
                     <td class="lineno">2</td>
                     <td class="diff-add"><pre>Which means Hello!
-                    </pre></td>'''),
+                    </pre></td>''') in
                   diffhtml)
 
     def test_diff_view_mode(self):
@@ -434,31 +434,31 @@ class TestRootController(_TestCase):
         r = self.app.get(ci + 'tree/',
                          extra_environ={'username': str(user.username)})
         opts = self.subscription_options(r)
-        assert_equal(opts['subscribed'], False)
+        assert opts['subscribed'] == False
 
         # subscribe
         r = self.app.post(str(ci + 'tree/subscribe'),
                           {'subscribe': 'True'},
                           extra_environ={'username': str(user.username)})
-        assert_equal(r.json, {'status': 'ok', 'subscribed': True})
+        assert r.json == {'status': 'ok', 'subscribed': True}
         # user is subscribed
         assert M.Mailbox.subscribed(user_id=user._id)
         r = self.app.get(ci + 'tree/',
                          extra_environ={'username': str(user.username)})
         opts = self.subscription_options(r)
-        assert_equal(opts['subscribed'], True)
+        assert opts['subscribed'] == True
 
         # unsubscribe
         r = self.app.post(str(ci + 'tree/subscribe'),
                           {'unsubscribe': 'True'},
                           extra_environ={'username': str(user.username)})
-        assert_equal(r.json, {'status': 'ok', 'subscribed': False})
+        assert r.json == {'status': 'ok', 'subscribed': False}
         # user is not subscribed
         assert not M.Mailbox.subscribed(user_id=user._id)
         r = self.app.get(ci + 'tree/',
                          extra_environ={'username': str(user.username)})
         opts = self.subscription_options(r)
-        assert_equal(opts['subscribed'], False)
+        assert opts['subscribed'] == False
 
     def test_timezone(self):
         ci = self._get_ci()
@@ -501,15 +501,15 @@ class TestRootController(_TestCase):
         self.setup_testgit_index_repo()
         r = self.app.get('/p/test/testgit-index/ci/master/tree/index/')
         form = r.html.find('form', 'tarball')
-        assert_equal(form.get('action'), '/p/test/testgit-index/ci/master/tarball')
-        assert_equal(form.input.get('value'), '/index')
+        assert form.get('action') == '/p/test/testgit-index/ci/master/tarball'
+        assert form.input.get('value') == '/index'
 
     def test_default_branch(self):
-        assert_equal(c.app.default_branch_name, 'master')
+        assert c.app.default_branch_name == 'master'
         c.app.repo.set_default_branch('zz')
-        assert_equal(c.app.default_branch_name, 'zz')
+        assert c.app.default_branch_name == 'zz'
         c.app.repo.set_default_branch('master')
-        assert_equal(c.app.default_branch_name, 'master')
+        assert c.app.default_branch_name == 'master'
 
     def test_set_default_branch(self):
         r = self.app.get('/p/test/admin/src-git/set_default_branch_name')
@@ -521,41 +521,41 @@ class TestRootController(_TestCase):
         r = self.app.get('/p/test/src-git/').follow().follow()
         assert '<span class="scm-branch-label">zz</span>' in r
         # 'bad' is a file name which in zz, but not in master
-        assert_in('bad</a>', r)
+        assert 'bad</a>' in r
 
         self.app.post('/p/test/admin/src-git/set_default_branch_name',
                       params={'branch_name': 'master'})
         r = self.app.get('/p/test/src-git/').follow().follow()
-        assert_not_in('bad</a>', r)
-        assert_in('README</a>', r)
+        assert 'bad</a>' not in r
+        assert 'README</a>' in r
 
     def test_set_checkout_url(self):
         r = self.app.get('/p/test/admin/src-git/checkout_url')
         r.form['external_checkout_url'].value = 'http://foo.bar/baz'
         r.form['merge_disabled'].checked = True
         r = r.form.submit()
-        assert_equal(json.loads(self.webflash(r))['message'],
+        assert (json.loads(self.webflash(r))['message'] ==
                      "External checkout URL successfully changed. One-click merge disabled.")
         # for some reason c.app.config.options has old values still
         app_config = M.AppConfig.query.get(_id=c.app.config._id)
-        assert_equal(app_config.options['external_checkout_url'], 'http://foo.bar/baz')
-        assert_equal(app_config.options['merge_disabled'], True)
+        assert app_config.options['external_checkout_url'] == 'http://foo.bar/baz'
+        assert app_config.options['merge_disabled'] == True
 
     def test_refresh(self):
         r = self.app.get('/p/test/src-git/refresh')
-        assert_in('refresh queued', r)
-        assert_equal(1, M.MonQTask.query.find(dict(task_name='allura.tasks.repo_tasks.refresh')).count())
+        assert 'refresh queued' in r
+        assert 1 == M.MonQTask.query.find(dict(task_name='allura.tasks.repo_tasks.refresh')).count()
 
         r = self.app.get('/p/test/src-git/refresh', extra_environ={'HTTP_REFERER': '/p/test/src-git/'},
                          status=302)
-        assert_in('is being refreshed', self.webflash(r))
-        assert_equal(2, M.MonQTask.query.find(dict(task_name='allura.tasks.repo_tasks.refresh')).count())
+        assert 'is being refreshed' in self.webflash(r)
+        assert 2 == M.MonQTask.query.find(dict(task_name='allura.tasks.repo_tasks.refresh')).count()
 
 
 class TestRestController(_TestCase):
     def test_index(self):
         resp = self.app.get('/rest/p/test/src-git/', status=200)
-        assert_equal(resp.json, {
+        assert resp.json == {
             'api_url': 'http://localhost/rest/p/test/src-git/',
             'url': 'http://localhost/p/test/src-git/',
             'mount_label': 'Git',
@@ -563,7 +563,7 @@ class TestRestController(_TestCase):
             'name': 'git',
             'clone_url_file': '/srv/git/p/test/testgit',  # should be "src-git" but test data is weird?
             'commit_count': 5,
-        })
+        }
 
     def test_commits(self):
         self.app.get('/rest/p/test/src-git/commits', status=200)
@@ -588,13 +588,13 @@ class TestHasAccessAPI(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/src-git/has_access?user=babadook&perm=read',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
         r = self.api_get(
             '/rest/p/test/src-git/has_access?user=test-user&perm=jump',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
     def test_has_access_not_admin(self):
         """
@@ -610,13 +610,13 @@ class TestHasAccessAPI(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/src-git/has_access?user=test-admin&perm=create',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], True)
+        assert r.status_int == 200
+        assert r.json['result'] == True
         r = self.api_get(
             '/rest/p/test/src-git/has_access?user=test-user&perm=create',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
 
 class TestFork(_TestCase):
@@ -723,20 +723,20 @@ class TestFork(_TestCase):
 
     def test_merge_request_detail_view(self):
         r, mr_num = self._request_merge()
-        assert_in('wants to merge', r)
+        assert 'wants to merge' in r
 
         merge_instructions = r.html.findAll('textarea')[0].getText()
-        assert_in('git checkout master', merge_instructions)
-        assert_in('git fetch /srv/git/p/test2/code master', merge_instructions)
+        assert 'git checkout master' in merge_instructions
+        assert 'git fetch /srv/git/p/test2/code master' in merge_instructions
         c_id = self.forked_repo.get_heads()[0]['object_id']
-        assert_in(f'git merge {c_id}', merge_instructions)
+        assert f'git merge {c_id}' in merge_instructions
         assert_regexp_matches(str(r), r'[0-9]+ seconds? ago')
 
         merge_form = r.html.find('div', {'class': 'merge-help-text merge-ok'})
         assert merge_form
-        assert_in('Merge request has no conflicts. You can merge automatically.', merge_form.getText())
+        assert 'Merge request has no conflicts. You can merge automatically.' in merge_form.getText()
 
-        assert_not_in('Improve documentation', r)  # no details yet
+        assert 'Improve documentation' not in r  # no details yet
 
         # a task is busy/ready to compute
         r = self.app.get('/p/test/src-git/merge-requests/1/commits_html', status=202)  # 202 used for "busy"
@@ -746,16 +746,16 @@ class TestFork(_TestCase):
         ThreadLocalORMSession.close_all()  # close ming connections so that new data gets loaded later
 
         def assert_commit_details(r):
-            assert_in('Improve documentation', r.text)
+            assert 'Improve documentation' in r.text
             revs = r.html.findAll('tr', attrs={'class': 'rev'})
-            assert_equal(len(revs), 1)
+            assert len(revs) == 1
             rev_links = revs[0].findAll('a', attrs={'class': 'rev'})
             browse_links = revs[0].findAll('a', attrs={'class': 'browse'})
-            assert_equal(rev_links[0].get('href'), '/p/test2/code/ci/%s/' % c_id)
-            assert_equal(rev_links[0].getText(), '[%s]' % c_id[:6])
-            assert_equal(browse_links[0].get('href'),
+            assert rev_links[0].get('href') == '/p/test2/code/ci/%s/' % c_id
+            assert rev_links[0].getText() == '[%s]' % c_id[:6]
+            assert (browse_links[0].get('href') ==
                          '/p/test2/code/ci/%s/tree' % c_id)
-            assert_equal(browse_links[0].getText().strip(), 'Tree')
+            assert browse_links[0].getText().strip() == 'Tree'
 
         r = self.app.get('/p/test/src-git/merge-requests/1/commits_html', status=200)
         assert_commit_details(r)
@@ -764,16 +764,16 @@ class TestFork(_TestCase):
         assert_commit_details(r)
 
         r = self.app.get('/p/test/src-git/merge-requests/1/can_merge_task_status')
-        assert_equal(r.json, {'status': 'ready'})
+        assert r.json == {'status': 'ready'}
         r = self.app.get('/p/test/src-git/merge-requests/1/can_merge_result')
-        assert_equal(r.json, {'can_merge': None})
+        assert r.json == {'can_merge': None}
         r = self.app.get('/p/test/src-git/merge-requests/1/merge_task_status')
-        assert_equal(r.json, {'status': None})
+        assert r.json == {'status': None}
 
     def test_merge_request_detail_noslash(self):
         self._request_merge()
         r = self.app.get('/p/test/src-git/merge-requests/1', status=301)
-        assert_equal(r.location, 'http://localhost/p/test/src-git/merge-requests/1/')
+        assert r.location == 'http://localhost/p/test/src-git/merge-requests/1/'
 
     def test_merge_request_with_deleted_repo(self):
         self._request_merge()
@@ -811,19 +811,19 @@ class TestFork(_TestCase):
     def test_merge_request_default_branches(self):
         _select_val = lambda r, n: r.html.find('select', {'name': n}).find(selected=True).string
         r = self.app.get('/p/test2/code/request_merge')
-        assert_equal(_select_val(r, 'source_branch'), 'master')
-        assert_equal(_select_val(r, 'target_branch'), 'master')
+        assert _select_val(r, 'source_branch') == 'master'
+        assert _select_val(r, 'target_branch') == 'master'
         r = self.app.get('/p/test2/code/ci/zz/tree/').click('Request Merge')
-        assert_equal(_select_val(r, 'source_branch'), 'zz')
-        assert_equal(_select_val(r, 'target_branch'), 'master')
+        assert _select_val(r, 'source_branch') == 'zz'
+        assert _select_val(r, 'target_branch') == 'master'
         GM.Repository.query.get(_id=c.app.repo._id).default_branch_name = 'zz'
         ThreadLocalORMSession.flush_all()
         r = self.app.get('/p/test2/code/request_merge')
-        assert_equal(_select_val(r, 'source_branch'), 'master')
-        assert_equal(_select_val(r, 'target_branch'), 'zz')
+        assert _select_val(r, 'source_branch') == 'master'
+        assert _select_val(r, 'target_branch') == 'zz'
         r = self.app.get('/p/test2/code/ci/zz/tree/').click('Request Merge')
-        assert_equal(_select_val(r, 'source_branch'), 'zz')
-        assert_equal(_select_val(r, 'target_branch'), 'zz')
+        assert _select_val(r, 'source_branch') == 'zz'
+        assert _select_val(r, 'target_branch') == 'zz'
 
     def test_merge_request_with_branch(self):
         def get_mr_page(r):
@@ -955,7 +955,7 @@ class TestFork(_TestCase):
         mr_commits.side_effect = Exception
         r = self.app.get('/p/test/src-git/merge-requests/%s/' % mr_num)
         # errors don't show up on the page directly any more, so just assert that the bg task is there
-        assert_in('commits-loading', r)
+        assert 'commits-loading' in r
         self.app.get('/p/test/src-git/merge-requests/%s/commits_html' % mr_num, status=202)  # 202 used for "busy"
 
     def test_merge_request_validation_error(self):
@@ -1042,9 +1042,9 @@ class TestGitRename(TestController):
 
         # the diff portion of the output
         resp_no_ws = re.sub(r'\s+', '', str(resp))
-        assert_in('<a href="/p/test/src-git/ci/fbb0644603bb6ecee3ebb62efe8c86efc9b84ee6/tree/f.txt" rel="nofollow">f.txt</a>'
+        assert ('<a href="/p/test/src-git/ci/fbb0644603bb6ecee3ebb62efe8c86efc9b84ee6/tree/f.txt" rel="nofollow">f.txt</a>'
                   'to<a href="/p/test/src-git/ci/b120505a61225e6c14bee3e5b5862db81628c35c/tree/f2.txt" rel="nofollow">f2.txt</a>'
-                  .replace(' ', ''), resp_no_ws)
+                  .replace(' ', '') in resp_no_ws)
         assert '<span class="empty-diff">File was renamed.</span>' in resp
 
     def test_directory_changed_type(self):
@@ -1052,11 +1052,11 @@ class TestGitRename(TestController):
         resp = self.app.get('/src-git/ci/7b1c9ef214eb0ef8c06bada0966dd941f442beec/')
 
         resp_no_ws = re.sub(r'\s+', '', str(resp))
-        assert_in('<a href="/p/test/src-git/ci/7b1c9ef214eb0ef8c06bada0966dd941f442beec/tree/b_dir" rel="nofollow">b_dir</a>'
+        assert ('<a href="/p/test/src-git/ci/7b1c9ef214eb0ef8c06bada0966dd941f442beec/tree/b_dir" rel="nofollow">b_dir</a>'
                   '</h6>'
                   '<div id="diff-3" class="inline-diff-body">'
                   '<span class="empty-diff">Symlink.</span>'
-                  .replace(' ', ''), resp_no_ws)
+                  .replace(' ', '') in resp_no_ws)
 
     def test_symlink_in_tree(self):
         # change a_dir to a file; b_dir to a symlink
@@ -1085,7 +1085,7 @@ class TestGitBranch(TestController):
     def test_exotic_default_branch(self):
         r = self.app.get('/src-git/').follow().follow()
         assert 'README</a>' in r
-        assert_equal(c.app.repo.get_default_branch('master'), 'test')
+        assert c.app.repo.get_default_branch('master') == 'test'
 
     def test_branch_with_slashes(self):
         branches_page = self.app.get('/src-git/ref/master/branches/')
@@ -1126,19 +1126,19 @@ class TestIncludeMacro(_TestCase):
         setup_global_objects()
 
     def test_parse_repo(self):
-        assert_equal(macro.parse_repo('app'), None)
-        assert_equal(macro.parse_repo('proj:app'), None)
-        assert_equal(macro.parse_repo('nbhd:test:src-git'), None)
-        assert_equal(macro.parse_repo('a:b:c:d:e:f'), None)
-        assert_not_equal(macro.parse_repo('src-git'), None)
-        assert_not_equal(macro.parse_repo('test:src-git'), None)
-        assert_not_equal(macro.parse_repo('p:test:src-git'), None)
+        assert macro.parse_repo('app') == None
+        assert macro.parse_repo('proj:app') == None
+        assert macro.parse_repo('nbhd:test:src-git') == None
+        assert macro.parse_repo('a:b:c:d:e:f') == None
+        assert macro.parse_repo('src-git') != None
+        assert macro.parse_repo('test:src-git') != None
+        assert macro.parse_repo('p:test:src-git') != None
 
     def test_include_file_no_repo(self):
         expected = '[[include repo %s (not found)]]'
-        assert_equal(macro.include_file(None), expected % None)
-        assert_equal(macro.include_file('a:b'), expected % 'a:b')
-        assert_equal(macro.include_file('repo'), expected % 'repo')
+        assert macro.include_file(None) == expected % None
+        assert macro.include_file('a:b') == expected % 'a:b'
+        assert macro.include_file('repo') == expected % 'repo'
 
     def test_include_file_permissions(self):
         h.set_context('test', 'src-git', neighborhood='Projects')
@@ -1149,13 +1149,13 @@ class TestIncludeMacro(_TestCase):
             acl.remove(read_perm)
         c.user = M.User.anonymous()
         expected = "[[include: you don't have a read permission for repo src-git]]"
-        assert_equal(macro.include_file('src-git'), expected)
+        assert macro.include_file('src-git') == expected
 
     def test_include_file_cant_find_file(self):
         expected = "[[include can't find file %s in revision %s]]"
-        assert_equal(macro.include_file('src-git', 'a.txt'),
+        assert (macro.include_file('src-git', 'a.txt') ==
                      expected % ('a.txt', '1e146e67985dcd71c74de79613719bef7bddca4a'))
-        assert_equal(macro.include_file('src-git', 'a.txt', '6a45885ae7347f1cac5103b0050cc1be6a1496c8'),
+        assert (macro.include_file('src-git', 'a.txt', '6a45885ae7347f1cac5103b0050cc1be6a1496c8') ==
                      expected % ('a.txt', '6a45885ae7347f1cac5103b0050cc1be6a1496c8'))
 
     @patch('allura.model.repo.Blob.has_pypeline_view', new_callable=PropertyMock)
@@ -1164,9 +1164,9 @@ class TestIncludeMacro(_TestCase):
         has_html_view.return_value = False
         has_pypeline_view.return_value = False
         expected = "[[include can't display file README in revision 1e146e67985dcd71c74de79613719bef7bddca4a]]"
-        assert_equal(macro.include_file('src-git', 'README'), expected)
+        assert macro.include_file('src-git', 'README') == expected
 
     def test_include_file_display(self):
         result = macro.include_file('src-git', 'README')
-        assert_in('This is readme', result)
-        assert_in('Another Line', result)
+        assert 'This is readme' in result
+        assert 'Another Line' in result
diff --git a/ForgeGit/forgegit/tests/model/test_repository.py b/ForgeGit/forgegit/tests/model/test_repository.py
index 9fb886289..bb687b91b 100644
--- a/ForgeGit/forgegit/tests/model/test_repository.py
+++ b/ForgeGit/forgegit/tests/model/test_repository.py
@@ -85,8 +85,8 @@ class TestNewGit(unittest.TestCase):
         c.lcid_cache = {}
         self.rev.tree.ls()
         # print self.rev.tree.readme()
-        assert_equal(self.rev.tree.readme(), (
-            'README', 'This is readme\nAnother Line\n'))
+        assert self.rev.tree.readme() == (
+            'README', 'This is readme\nAnother Line\n')
         assert self.rev.tree.path() == '/'
         assert self.rev.tree.url() == (
             '/p/test/src-git/ci/'
@@ -109,17 +109,17 @@ class TestNewGit(unittest.TestCase):
                 '/p/test/src-git/ci/'
                 '1e146e67985dcd71c74de79613719bef7bddca4a/')
 
-        assert_equal(self.rev.authored_user, None)
-        assert_equal(self.rev.committed_user, None)
+        assert self.rev.authored_user == None
+        assert self.rev.committed_user == None
         user = M.User.upsert('rick')
         email = user.claim_address('rcopeland@geek.net')
         email.confirmed = True
         session(email).flush(email)
         rev = self.repo.commit(self.rev._id)  # to update cached values of LazyProperty
-        assert_equal(rev.authored_user, user)
-        assert_equal(rev.committed_user, user)
-        assert_equal(
-            sorted(rev.webhook_info.keys()),
+        assert rev.authored_user == user
+        assert rev.committed_user == user
+        assert (
+            sorted(rev.webhook_info.keys()) ==
             sorted(['id', 'url', 'timestamp', 'message', 'author',
                     'committer', 'added', 'removed', 'renamed', 'modified', 'copied']))
 
@@ -257,15 +257,15 @@ class TestGitRepo(unittest.TestCase, RepoImplTestBase):
 
     def test_log_id_only(self):
         entries = list(self.repo.log(id_only=True))
-        assert_equal(entries, [
+        assert entries == [
             '1e146e67985dcd71c74de79613719bef7bddca4a',
             'df30427c488aeab84b2352bdf88a3b19223f9d7a',
             '6a45885ae7347f1cac5103b0050cc1be6a1496c8',
-            '9a7df788cf800241e3bb5a849c8870f2f8259d98'])
+            '9a7df788cf800241e3bb5a849c8870f2f8259d98']
 
     def test_log(self):
         entries = list(self.repo.log(id_only=False))
-        assert_equal(entries, [
+        assert entries == [
             {'authored': {'date': datetime.datetime(2010, 10, 7, 18, 44, 11),
                           'email': 'rcopeland@geek.net',
                           'name': 'Rick Copeland'},
@@ -314,15 +314,15 @@ class TestGitRepo(unittest.TestCase, RepoImplTestBase):
              'refs': [],
              'size': None,
              'rename_details': {}},
-        ])
+        ]
 
     def test_log_unicode(self):
         entries = list(self.repo.log(path='völundr', id_only=False))
-        assert_equal(entries, [])
+        assert entries == []
 
     def test_log_file(self):
         entries = list(self.repo.log(path='README', id_only=False))
-        assert_equal(entries, [
+        assert entries == [
             {'authored': {'date': datetime.datetime(2010, 10, 7, 18, 44, 11),
                           'email': 'rcopeland@geek.net',
                           'name': 'Rick Copeland'},
@@ -347,7 +347,7 @@ class TestGitRepo(unittest.TestCase, RepoImplTestBase):
              'refs': [],
              'size': 15,
              'rename_details': {}},
-        ])
+        ]
 
     def test_commit(self):
         entry = self.repo.commit('HEAD')
@@ -379,13 +379,13 @@ class TestGitRepo(unittest.TestCase, RepoImplTestBase):
         domain = '.'.join(reversed(c.app.url[1:-1].split('/'))).replace('_', '-')
         common_suffix = tg.config['forgemail.domain']
         email = f'noreply@{domain}{common_suffix}'
-        assert_in(email, notification['reply_to_address'])
+        assert email in notification['reply_to_address']
 
         commit1_loc = notification.text.find('Initial commit')
         assert commit1_loc != -1
         commit2_loc = notification.text.find('Remove file')
         assert commit2_loc != -1
-        assert_less(commit1_loc, commit2_loc)
+        assert commit1_loc < commit2_loc
 
     def test_notification_email(self):
         send_notifications(
@@ -394,7 +394,7 @@ class TestGitRepo(unittest.TestCase, RepoImplTestBase):
 
         n = M.Notification.query.find({'subject': '[test:src-git] New commit [1e146e] by Rick Copeland'}).first()
         assert n
-        assert_in('Change README', n.text)
+        assert 'Change README' in n.text
 
     def test_notification_email_multiple_commits(self):
         send_notifications(self.repo, ['df30427c488aeab84b2352bdf88a3b19223f9d7a',
@@ -458,7 +458,7 @@ class TestGitRepo(unittest.TestCase, RepoImplTestBase):
             .get_payload(decode=True).decode('utf-8')
 
         # no extra HTML in commit messages
-        assert_in('''-----
+        assert '''-----
 
 Add foo.txt.  Commit ref [616d24f8dd4e95cadd8e93df5061f09855d1a066] *bold* <b>bold</b>
 
@@ -468,20 +468,20 @@ Add foo.txt.  Commit ref [616d24f8dd4e95cadd8e93df5061f09855d1a066] *bold* <b>bo
 
 http://example.com/
 
-By Dave Brondsema''', text_body)
+By Dave Brondsema''' in text_body
         # these bracketed links could look like HTML tags, ensure they don't get removed
-        assert_in('further messages, please visit <http://localhost/auth/subscriptions/>', text_body)
+        assert 'further messages, please visit <http://localhost/auth/subscriptions/>' in text_body
 
         # limited markdown handling of commit messages (see `markdown_commit`)
         # and HTML escaped
-        assert_in('''<hr/>
+        assert '''<hr/>
 <div class="markdown_content"><p>Add foo.txt.  Commit ref <a class="alink" href="http://localhost/p/test/weird-chars/ci/616d24f8dd4e95cadd8e93df5061f09855d1a066/">[616d24f8dd4e95cadd8e93df5061f09855d1a066]</a> *bold* &lt;b&gt;bold&lt;/b&gt;</p>
 <p>* one<br/>
 * two<br/>
 * three</p>
 <p>http://example.com/</p></div>
 
-<p>By Dave Brondsema''', html_body)
+<p>By Dave Brondsema''' in html_body
 
     def test_commit_artifact_references(self):
         self._setup_weird_chars_repo()
@@ -500,9 +500,9 @@ By Dave Brondsema''', text_body)
         if os.path.isfile(os.path.join(tmpdir, "git/t/te/test/testgit.git/test-src-git-HEAD.zip")):
             os.remove(
                 os.path.join(tmpdir, "git/t/te/test/testgit.git/test-src-git-HEAD.zip"))
-        assert_equal(self.repo.tarball_path,
+        assert (self.repo.tarball_path ==
                      os.path.join(tmpdir, 'git/t/te/test/testgit.git'))
-        assert_equal(self.repo.tarball_url('HEAD'),
+        assert (self.repo.tarball_url('HEAD') ==
                      'file:///git/t/te/test/testgit.git/test-src-git-HEAD.zip')
         self.repo.tarball('HEAD')
         assert os.path.isfile(
@@ -556,20 +556,20 @@ By Dave Brondsema''', text_body)
             os.removedirs(
                 os.path.join(tmpdir, "git/t/te/test/testgit.git/test-src-git-HEAD/"))
         self.repo.tarball('HEAD')
-        assert_equal(self.repo.get_tarball_status('HEAD'), 'complete')
+        assert self.repo.get_tarball_status('HEAD') == 'complete'
 
         os.remove(
             os.path.join(tmpdir, "git/t/te/test/testgit.git/test-src-git-HEAD.zip"))
-        assert_equal(self.repo.get_tarball_status('HEAD'), None)
+        assert self.repo.get_tarball_status('HEAD') == None
 
     def test_tarball_status_task(self):
-        assert_equal(self.repo.get_tarball_status('HEAD'), None)
+        assert self.repo.get_tarball_status('HEAD') == None
 
         # create tarball task in MonQTask and check get_tarball_status
         tarball.post('HEAD', '')
 
         # task created
-        assert_equal(self.repo.get_tarball_status('HEAD'), 'ready')
+        assert self.repo.get_tarball_status('HEAD') == 'ready'
 
         task = M.MonQTask.query.get(**{
             'task_name': 'allura.tasks.repo_tasks.tarball',
@@ -580,12 +580,12 @@ By Dave Brondsema''', text_body)
         # task is running
         task.state = 'busy'
         task.query.session.flush_all()
-        assert_equal(self.repo.get_tarball_status('HEAD'), 'busy')
+        assert self.repo.get_tarball_status('HEAD') == 'busy'
 
         # when state is complete, but file don't exists, then status is None
         task.state = 'complete'
         task.query.session.flush_all()
-        assert_equal(self.repo.get_tarball_status('HEAD'), None)
+        assert self.repo.get_tarball_status('HEAD') == None
 
     def test_is_empty(self):
         assert not self.repo.is_empty()
@@ -604,13 +604,13 @@ By Dave Brondsema''', text_body)
 
     def test_default_branch_set(self):
         self.repo.default_branch_name = 'zz'
-        assert_equal(self.repo.get_default_branch('master'), 'zz')
+        assert self.repo.get_default_branch('master') == 'zz'
 
     def test_default_branch_non_standard_unset(self):
         with mock.patch.object(self.repo, 'get_branches') as gb,\
              mock.patch.object(self.repo, 'set_default_branch') as set_db:
             gb.return_value = [Object(name='foo')]
-            assert_equal(self.repo.get_default_branch('master'), 'foo')
+            assert self.repo.get_default_branch('master') == 'foo'
             set_db.assert_called_once_with('foo')
 
     def test_default_branch_non_standard_invalid(self):
@@ -618,7 +618,7 @@ By Dave Brondsema''', text_body)
              mock.patch.object(self.repo, 'set_default_branch') as set_db:
             self.repo.default_branch_name = 'zz'
             gb.return_value = [Object(name='foo')]
-            assert_equal(self.repo.get_default_branch('master'), 'foo')
+            assert self.repo.get_default_branch('master') == 'foo'
             set_db.assert_called_once_with('foo')
 
     def test_default_branch_invalid(self):
@@ -626,28 +626,28 @@ By Dave Brondsema''', text_body)
              mock.patch.object(self.repo, 'set_default_branch') as set_db:
             self.repo.default_branch_name = 'zz'
             gb.return_value = [Object(name='foo'), Object(name='master')]
-            assert_equal(self.repo.get_default_branch('master'), 'master')
+            assert self.repo.get_default_branch('master') == 'master'
             set_db.assert_called_once_with('master')
 
     def test_default_branch_no_clobber(self):
         with mock.patch.object(self.repo, 'get_branches') as gb:
             gb.return_value = []
             self.repo.default_branch_name = 'zz'
-            assert_equal(self.repo.get_default_branch('master'), 'zz')
+            assert self.repo.get_default_branch('master') == 'zz'
 
     def test_default_branch_clobber_none(self):
         with mock.patch.object(self.repo, 'get_branches') as gb:
             gb.return_value = []
             self.repo.default_branch_name = None
-            assert_equal(self.repo.get_default_branch('master'), 'master')
+            assert self.repo.get_default_branch('master') == 'master'
 
     def test_clone_url(self):
-        assert_equal(
-            self.repo.clone_url('file', 'nobody'),
+        assert (
+            self.repo.clone_url('file', 'nobody') ==
             '/srv/git/p/test/testgit')
         with h.push_config(self.repo.app.config.options, external_checkout_url='https://$username@foo.com/'):
-            assert_equal(
-                self.repo.clone_url('https', 'user'),
+            assert (
+                self.repo.clone_url('https', 'user') ==
                 'https://user@foo.com/')
 
     def test_webhook_payload(self):
@@ -707,7 +707,7 @@ By Dave Brondsema''', text_body)
                 'url': 'http://localhost/p/test/src-git/',
             },
         }
-        assert_equals(payload, expected_payload)
+        assert payload == expected_payload
 
     def test_can_merge(self):
         mr = mock.Mock(downstream_repo=Object(full_fs_path='downstream-url'),
@@ -717,7 +717,7 @@ By Dave Brondsema''', text_body)
         git = mock.Mock()
         git.merge_tree.return_value = 'clean merge'
         self.repo._impl._git.git = git
-        assert_equal(self.repo.can_merge(mr), True)
+        assert self.repo.can_merge(mr) == True
         git.fetch.assert_called_once_with('downstream-url', 'source-branch')
         git.merge_base.assert_called_once_with('cid', 'target-branch')
         git.merge_tree.assert_called_once_with(
@@ -725,7 +725,7 @@ By Dave Brondsema''', text_body)
             'target-branch',
             'cid')
         git.merge_tree.return_value = '+<<<<<<<'
-        assert_equal(self.repo.can_merge(mr), False)
+        assert self.repo.can_merge(mr) == False
 
     @mock.patch('forgegit.model.git_repo.tempfile', autospec=True)
     @mock.patch('forgegit.model.git_repo.git', autospec=True)
@@ -748,13 +748,13 @@ By Dave Brondsema''', text_body)
             bare=False,
             shared=True)
         tmp_repo = GitImplementation.return_value._git
-        assert_equal(
-            tmp_repo.git.fetch.call_args_list,
+        assert (
+            tmp_repo.git.fetch.call_args_list ==
             [mock.call('origin', 'target-branch'),
              mock.call('downstream-url', 'source-branch')])
         tmp_repo.git.checkout.assert_called_once_with('target-branch')
-        assert_equal(
-            tmp_repo.git.config.call_args_list,
+        assert (
+            tmp_repo.git.config.call_args_list ==
             [mock.call('user.name', b'Test Admin'),
              mock.call('user.email', 'allura@localhost')])
         msg = 'Merge downstream-repo-url branch source-branch into target-branch'
@@ -802,7 +802,7 @@ By Dave Brondsema''', text_body)
             'copied': [],
             'total': 2,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
 
         diffs = repo.paged_diffs('f3de6a0e7601cdde326054a1cc708afdc1dbe70b')
         expected = {
@@ -813,7 +813,7 @@ By Dave Brondsema''', text_body)
             'changed': ['привіт.txt'],
             'total': 1,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
 
         # initial commit is special, but must work too
         diffs = repo.paged_diffs('afaa6d93eb5661fb04f8e10e9ba1039b7441a6c7')
@@ -825,7 +825,7 @@ By Dave Brondsema''', text_body)
             'renamed': [],
             'total': 1,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
 
         # pagination
         diffs = repo.paged_diffs('407950e8fba4dbc108ffbce0128ed1085c52cfd7', start=0, end=1)
@@ -837,7 +837,7 @@ By Dave Brondsema''', text_body)
             'changed': [],
             'total': 2,  # there are two total changes but result is limited to first
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
         diffs = repo.paged_diffs('407950e8fba4dbc108ffbce0128ed1085c52cfd7', start=1, end=2)
         expected = {
             'added': ['привіт.txt'],
@@ -847,7 +847,7 @@ By Dave Brondsema''', text_body)
             'changed': [],
             'total': 2,  # there are two total changes but result is limited to second
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
         diffs = repo.paged_diffs('346c52c1dddc729e2c2711f809336401f0ff925e')  # Test copy
         expected = {
             'added': ['README.copy'],
@@ -857,7 +857,7 @@ By Dave Brondsema''', text_body)
             'changed': ['README'],
             'total': 2,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
         diffs = repo.paged_diffs('3cb2bbcd7997f89060a14fe8b1a363f01883087f')  # Test rename
         expected = {
             'added': ['README'],
@@ -867,7 +867,7 @@ By Dave Brondsema''', text_body)
             'changed': [],
             'total': 2,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
         diffs = repo.paged_diffs('616d24f8dd4e95cadd8e93df5061f09855d1a066')  # Test type change
         expected = {
             'added': [],
@@ -877,7 +877,7 @@ By Dave Brondsema''', text_body)
             'changed': ['README.copy'],
             'total': 1,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
 
     @mock.patch.dict('allura.lib.app_globals.config',  {'scm.commit.git.detect_copies': 'true'})
     @td.with_tool('test', 'Git', 'src-weird', 'Git', type='git')
@@ -905,7 +905,7 @@ By Dave Brondsema''', text_body)
             'changed': ['README'],
             'total': 2,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
         diffs = repo.paged_diffs('3cb2bbcd7997f89060a14fe8b1a363f01883087f')  # Test rename
         expected = {
             'added': [],
@@ -915,11 +915,11 @@ By Dave Brondsema''', text_body)
             'changed': [],
             'total': 1,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
 
     def test_merge_base(self):
         res = self.repo._impl.merge_base(self.merge_request)
-        assert_equal(res, '1e146e67985dcd71c74de79613719bef7bddca4a')
+        assert res == '1e146e67985dcd71c74de79613719bef7bddca4a'
 
     def test_merge_request_commits(self):
         res = self.repo.merge_request_commits(self.merge_request)
@@ -938,7 +938,7 @@ By Dave Brondsema''', text_body)
              'refs': ['zz'],
              'rename_details': {},
              'size': None}]
-        assert_equals(res, expected)
+        assert res == expected
 
     def test_merge_request_commits_tmp_dir(self):
         """
@@ -950,19 +950,19 @@ By Dave Brondsema''', text_body)
         opt = {'scm.merge_list.git.use_tmp_dir': True}
         with h.push_config(tg.config, **opt):
             res_with_tmp = self.repo.merge_request_commits(mr)
-        assert_equals(res_without_tmp, res_with_tmp)
+        assert res_without_tmp == res_with_tmp
 
     def test_cached_branches(self):
         with mock.patch.dict('allura.lib.app_globals.config', {'repo_refs_cache_threshold': '0'}):
             rev = GM.Repository.query.get(_id=self.repo['_id'])
             branches = rev._impl._get_refs('branches')
-            assert_equal(rev.cached_branches, branches)
+            assert rev.cached_branches == branches
 
     def test_cached_tags(self):
         with mock.patch.dict('allura.lib.app_globals.config', {'repo_refs_cache_threshold': '0'}):
             rev = GM.Repository.query.get(_id=self.repo['_id'])
             tags = rev._impl._get_refs('tags')
-            assert_equal(rev.cached_tags, tags)
+            assert rev.cached_tags == tags
 
 
 class TestGitImplementation(unittest.TestCase):
@@ -1069,35 +1069,35 @@ class TestGitCommit(unittest.TestCase):
     def test_log(self):
         # path only
         commits = list(self.repo.log(id_only=True))
-        assert_equal(commits, [
+        assert commits == [
             "1e146e67985dcd71c74de79613719bef7bddca4a",
             "df30427c488aeab84b2352bdf88a3b19223f9d7a",
             "6a45885ae7347f1cac5103b0050cc1be6a1496c8",
             "9a7df788cf800241e3bb5a849c8870f2f8259d98",
-        ])
+        ]
         commits = list(self.repo.log(self.repo.head, 'README', id_only=True))
-        assert_equal(commits, [
+        assert commits == [
             "1e146e67985dcd71c74de79613719bef7bddca4a",
             "df30427c488aeab84b2352bdf88a3b19223f9d7a",
-        ])
+        ]
         commits = list(
             self.repo.log("df30427c488aeab84b2352bdf88a3b19223f9d7a", 'README', id_only=True))
-        assert_equal(commits, [
+        assert commits == [
             "df30427c488aeab84b2352bdf88a3b19223f9d7a",
-        ])
+        ]
         commits = list(self.repo.log(self.repo.head, '/a/b/c/', id_only=True))
-        assert_equal(commits, [
+        assert commits == [
             "6a45885ae7347f1cac5103b0050cc1be6a1496c8",
             "9a7df788cf800241e3bb5a849c8870f2f8259d98",
-        ])
+        ]
         commits = list(
             self.repo.log("9a7df788cf800241e3bb5a849c8870f2f8259d98", '/a/b/c/', id_only=True))
-        assert_equal(commits, [
+        assert commits == [
             "9a7df788cf800241e3bb5a849c8870f2f8259d98",
-        ])
+        ]
         commits = list(
             self.repo.log(self.repo.head, '/does/not/exist/', id_only=True))
-        assert_equal(commits, [])
+        assert commits == []
 
 
 class TestGitHtmlView(unittest.TestCase):
diff --git a/ForgeGit/forgegit/tests/test_git_app.py b/ForgeGit/forgegit/tests/test_git_app.py
index 80372039f..823004c40 100644
--- a/ForgeGit/forgegit/tests/test_git_app.py
+++ b/ForgeGit/forgegit/tests/test_git_app.py
@@ -40,7 +40,7 @@ class TestGitApp(unittest.TestCase):
         ThreadLocalORMSession.close_all()
 
     def test_admin_menu(self):
-        assert_equals(len(c.app.admin_menu()), 7)
+        assert len(c.app.admin_menu()) == 7
 
     def test_uninstall(self):
         from allura import model as M
diff --git a/ForgeImporters/forgeimporters/github/tests/test_utils.py b/ForgeImporters/forgeimporters/github/tests/test_utils.py
index 1ea4c761b..5e47bcefe 100644
--- a/ForgeImporters/forgeimporters/github/tests/test_utils.py
+++ b/ForgeImporters/forgeimporters/github/tests/test_utils.py
@@ -28,67 +28,67 @@ class TestGitHubMarkdownConverter:
     def test_convert_sha(self):
         text = '16c999e8c71134401a78d4d46435517b2271d6ac'
         result = self.conv.convert(text)
-        assert_equal(result, '[16c999]')
+        assert result == '[16c999]'
 
         text = 'some context  16c999e8c71134401a78d4d46435517b2271d6ac '
         result = self.conv.convert(text)
-        assert_equal(result, 'some context  [16c999] ')
+        assert result == 'some context  [16c999] '
 
     def test_convert_user_sha(self):
         text = 'user@16c999e8c71134401a78d4d46435517b2271d6ac'
         result = self.conv.convert(text)
-        assert_equal(result, '[16c999]')
+        assert result == '[16c999]'
 
         # Not an owner of current project
         text = 'another-user@16c999e8c71134401a78d4d46435517b2271d6ac'
         result = self.conv.convert(text)
-        assert_equal(result, text)
+        assert result == text
 
     def test_convert_user_repo_sha(self):
         text = 'user/project@16c999e8c71134401a78d4d46435517b2271d6ac'
         result = self.conv.convert(text)
-        assert_equal(result, '[16c999]')
+        assert result == '[16c999]'
 
         # Not a current project
         text = 'user/p@16c999e8c71134401a78d4d46435517b2271d6ac'
         result = self.conv.convert(text)
-        assert_equal(result, '[user/p@16c999]'
+        assert (result == '[user/p@16c999]'
                              '(https://github.com/user/p/commit/16c999e8c71134401a78d4d46435517b2271d6ac)')
 
     def test_convert_ticket(self):
         text = 'Ticket #1'
         result = self.conv.convert(text)
-        assert_equal(result, 'Ticket [#1]')
-        assert_equal(self.conv.convert('#1'), '[#1]')
+        assert result == 'Ticket [#1]'
+        assert self.conv.convert('#1') == '[#1]'
 
     def test_convert_user_ticket(self):
         text = 'user#1'
         result = self.conv.convert(text)
-        assert_equal(result, '[#1]')
+        assert result == '[#1]'
 
         # Not an owner of current project
         text = 'another-user#1'
         result = self.conv.convert(text)
-        assert_equal(result, 'another-user#1')
+        assert result == 'another-user#1'
 
     def test_convert_user_repo_ticket(self):
         text = 'user/project#1'
         result = self.conv.convert(text)
-        assert_equal(result, '[#1]')
+        assert result == '[#1]'
 
         # Not a current project
         text = 'user/p#1'
         result = self.conv.convert(text)
-        assert_equal(result, '[user/p#1](https://github.com/user/p/issues/1)')
+        assert result == '[user/p#1](https://github.com/user/p/issues/1)'
 
     def test_convert_strikethrough(self):
         text = '~~mistake~~'
-        assert_equal(self.conv.convert(text), '<s>mistake</s>')
+        assert self.conv.convert(text) == '<s>mistake</s>'
 
     def test_inline_code_block(self):
         text = 'This `~~some text~~` converts to this ~~strike out~~.'
         result = 'This `~~some text~~` converts to this <s>strike out</s>.'
-        assert_equal(self.conv.convert(text).strip(), result)
+        assert self.conv.convert(text).strip() == result
 
     def test_convert_code_blocks(self):
         text = '''```python
@@ -111,7 +111,7 @@ Two code blocks here!
         console.log(i);
     }'''
 
-        assert_equal(self.conv.convert(text).strip(), result)
+        assert self.conv.convert(text).strip() == result
 
     def test_code_blocks_without_newline_before(self):
         text = '''
@@ -126,9 +126,9 @@ There are some code snippet:
 
     print 'Hello'
 Pretty cool, ha?'''
-        assert_equal(self.conv.convert(text).strip(), result.strip())
+        assert self.conv.convert(text).strip() == result.strip()
         text = text.replace('```', '~~~')
-        assert_equal(self.conv.convert(text).strip(), result.strip())
+        assert self.conv.convert(text).strip() == result.strip()
 
         text = '''
 There are some code snippet:
@@ -143,4 +143,4 @@ There are some code snippet:
     :::python
     print 'Hello'
 Pretty cool, ha?'''
-        assert_equal(self.conv.convert(text).strip(), result.strip())
+        assert self.conv.convert(text).strip() == result.strip()
diff --git a/ForgeImporters/forgeimporters/github/tests/test_wiki.py b/ForgeImporters/forgeimporters/github/tests/test_wiki.py
index d99117d94..5afcebb17 100644
--- a/ForgeImporters/forgeimporters/github/tests/test_wiki.py
+++ b/ForgeImporters/forgeimporters/github/tests/test_wiki.py
@@ -118,7 +118,7 @@ class TestGitHubWikiImporter(TestCase):
             'project_name': 'me/project',
             'source_id': 'Page',
         }
-        assert_equal(page.import_id, import_id)
+        assert page.import_id == import_id
 
     @patch('forgeimporters.github.wiki.WM.Page.upsert')
     @patch('forgeimporters.github.wiki.h.render_any_markup')
@@ -132,11 +132,11 @@ class TestGitHubWikiImporter(TestCase):
         importer.app.url = '/p/test/wiki/'
         importer.rewrite_links = Mock(return_value='')
         importer._without_history(self.commit2)
-        assert_equal(upsert.call_args_list, [call('Home2'), call('Home3')])
+        assert upsert.call_args_list == [call('Home2'), call('Home3')]
 
-        assert_equal(render.call_args_list, [
+        assert render.call_args_list == [
             call('Home2.creole', '**test message**'),
-            call('Home3.rest', 'test message')])
+            call('Home3.rest', 'test message')]
 
     @patch('forgeimporters.github.wiki.git.Repo')
     @patch('forgeimporters.github.wiki.mkdtemp')
@@ -154,16 +154,16 @@ class TestGitHubWikiImporter(TestCase):
         repo = clone.return_value
         repo.iter_commits.return_value = [self.commit1, self.commit2]
         GitHubWikiImporter().import_pages('wiki_url', history=True)
-        assert_equal(with_history.call_count, 2)
-        assert_equal(without_history.call_count, 0)
+        assert with_history.call_count == 2
+        assert without_history.call_count == 0
 
     @patch('forgeimporters.github.wiki.GitHubWikiImporter._with_history')
     @patch('forgeimporters.github.wiki.GitHubWikiImporter._without_history')
     def test_get_commits_without_history(self, without_history, with_history):
         with patch('forgeimporters.github.wiki.git.Repo._clone'):
             GitHubWikiImporter().import_pages('wiki_url')
-            assert_equal(with_history.call_count, 0)
-            assert_equal(without_history.call_count, 1)
+            assert with_history.call_count == 0
+            assert without_history.call_count == 1
 
     @patch('forgeimporters.github.wiki.WM.Page.upsert')
     @patch('forgeimporters.github.wiki.h.render_any_markup')
@@ -178,8 +178,8 @@ class TestGitHubWikiImporter(TestCase):
         importer.app.url = '/p/test/wiki/'
         importer.rewrite_links = Mock(return_value='')
         importer._with_history(self.commit2)
-        assert_equal(upsert.call_args_list, [call('Home')])
-        assert_equal(render.call_args_list,
+        assert upsert.call_args_list == [call('Home')]
+        assert (render.call_args_list ==
                      [call('Home.rst', '# test message')])
 
     @skipIf(module_not_available('html2text'), 'html2text required')
@@ -198,8 +198,8 @@ class TestGitHubWikiImporter(TestCase):
         importer.rewrite_links = Mock(return_value='')
         importer.convert_gollum_tags = Mock(return_value='# test message')
         importer._with_history(self.commit2)
-        assert_equal(upsert.call_args_list, [call('Home')])
-        assert_equal(md2mkm.call_args_list, [call('# test message')])
+        assert upsert.call_args_list == [call('Home')]
+        assert md2mkm.call_args_list == [call('# test message')]
 
     def test_set_available_pages(self):
         importer = GitHubWikiImporter()
@@ -210,70 +210,70 @@ class TestGitHubWikiImporter(TestCase):
         blobs[2].name = 'code & fun.textile'
         commit.tree.traverse.return_value = blobs
         importer._set_available_pages(commit)
-        assert_equal(importer.available_pages, ['Home 42', 'code & fun'])
+        assert importer.available_pages == ['Home 42', 'code & fun']
 
     def test_gollum_page_links_case_insensitive(self):
         i = GitHubWikiImporter()
         i.available_pages = ['Home 42', 'code & fun']
-        assert_equal(i.convert_gollum_tags('[[Code & Fun]]'), '[code & fun]')
-        assert_equal(i.convert_gollum_tags('[[home-42]]'), '[Home 42]')
-        assert_equal(i.convert_gollum_tags('[[Unknown]]'), '[Unknown]')
+        assert i.convert_gollum_tags('[[Code & Fun]]') == '[code & fun]'
+        assert i.convert_gollum_tags('[[home-42]]') == '[Home 42]'
+        assert i.convert_gollum_tags('[[Unknown]]') == '[Unknown]'
 
     def test_convert_page_name(self):
         f = GitHubWikiImporter()._convert_page_name
-        assert_equal(f('Page Name'), 'Page Name')
-        assert_equal(f('Page-Name'), 'Page Name')
-        assert_equal(f('Page / Name'), 'Page   Name')
+        assert f('Page Name') == 'Page Name'
+        assert f('Page-Name') == 'Page Name'
+        assert f('Page / Name') == 'Page   Name'
 
     def test_convert_gollum_page_links(self):
         f = GitHubWikiImporter().convert_gollum_tags
-        assert_equal(f('[[Page]]'), '[Page]')
-        assert_equal(f('[[Page Title|Page]]'), '[Page Title](Page)')
-        assert_equal(f('[[Pagê Nâme]]'), '[Pagê Nâme]')
+        assert f('[[Page]]') == '[Page]'
+        assert f('[[Page Title|Page]]') == '[Page Title](Page)'
+        assert f('[[Pagê Nâme]]') == '[Pagê Nâme]'
         # Github always converts spaces and slashes in links to hyphens,
         # to lookup page in the filesystem. During import we're converting
         # all hyphens in page name to spaces, but still supporting both link
         # formats.
-        assert_equal(f('[[Page With Spaces]]'), '[Page With Spaces]')
-        assert_equal(f('[[Page-With-Spaces]]'), '[Page With Spaces]')
-        assert_equal(f('[[Page / 1]]'), '[Page   1]')
-        assert_equal(f('[[Title|Page With Spaces]]'),
+        assert f('[[Page With Spaces]]') == '[Page With Spaces]'
+        assert f('[[Page-With-Spaces]]') == '[Page With Spaces]'
+        assert f('[[Page / 1]]') == '[Page   1]'
+        assert (f('[[Title|Page With Spaces]]') ==
                      '[Title](Page With Spaces)')
-        assert_equal(f('[[Title|Page-With-Spaces]]'),
+        assert (f('[[Title|Page-With-Spaces]]') ==
                      '[Title](Page With Spaces)')
-        assert_equal(f('[[go here|Page / 1]]'), '[go here](Page   1)')
+        assert f('[[go here|Page / 1]]') == '[go here](Page   1)'
 
     def test_convert_gollum_page_links_escaped(self):
         f = GitHubWikiImporter().convert_gollum_tags
-        assert_equal(f("'[[Page]]"), '[[Page]]')
-        assert_equal(f("'[[Page Title|Page]]"), '[[Page Title|Page]]')
-        assert_equal(f("'[[Page With Spaces]]"), '[[Page With Spaces]]')
-        assert_equal(f("'[[Page-With-Spaces]]"), '[[Page-With-Spaces]]')
-        assert_equal(f("'[[Page / 1]]"), '[[Page / 1]]')
-        assert_equal(f("'[[Title|Page With Spaces]]"),
+        assert f("'[[Page]]") == '[[Page]]'
+        assert f("'[[Page Title|Page]]") == '[[Page Title|Page]]'
+        assert f("'[[Page With Spaces]]") == '[[Page With Spaces]]'
+        assert f("'[[Page-With-Spaces]]") == '[[Page-With-Spaces]]'
+        assert f("'[[Page / 1]]") == '[[Page / 1]]'
+        assert (f("'[[Title|Page With Spaces]]") ==
                      '[[Title|Page With Spaces]]')
-        assert_equal(f("'[[Title|Page-With-Spaces]]"),
+        assert (f("'[[Title|Page-With-Spaces]]") ==
                      '[[Title|Page-With-Spaces]]')
-        assert_equal(f("'[[go here|Page / 1]]"), '[[go here|Page / 1]]')
+        assert f("'[[go here|Page / 1]]") == '[[go here|Page / 1]]'
 
     def test_convert_gollum_external_links(self):
         f = GitHubWikiImporter().convert_gollum_tags
-        assert_equal(f('[[http://domain.net]]'), '<http://domain.net>')
-        assert_equal(f('[[https://domain.net]]'), '<https://domain.net>')
-        assert_equal(f('[[Site|http://domain.net]]'),
+        assert f('[[http://domain.net]]') == '<http://domain.net>'
+        assert f('[[https://domain.net]]') == '<https://domain.net>'
+        assert (f('[[Site|http://domain.net]]') ==
                      '[Site](http://domain.net)')
 
     def test_convert_gollum_external_links_escaped(self):
         f = GitHubWikiImporter().convert_gollum_tags
-        assert_equal(f("'[[http://domain.net]]"), '[[http://domain.net]]')
-        assert_equal(f("'[[https://domain.net]]"), '[[https://domain.net]]')
-        assert_equal(f("'[[Site|http://domain.net]]"),
+        assert f("'[[http://domain.net]]") == '[[http://domain.net]]'
+        assert f("'[[https://domain.net]]") == '[[https://domain.net]]'
+        assert (f("'[[Site|http://domain.net]]") ==
                      '[[Site|http://domain.net]]')
 
     def test_convert_gollum_toc(self):
         f = GitHubWikiImporter().convert_gollum_tags
-        assert_equal(f('[[_TOC_]]'), '[TOC]')
-        assert_equal(f("'[[_TOC_]]"), '[[_TOC_]]')
+        assert f('[[_TOC_]]') == '[TOC]'
+        assert f("'[[_TOC_]]") == '[[_TOC_]]'
 
     def test_convert_gollum_tags(self):
         f = GitHubWikiImporter().convert_gollum_tags
@@ -293,7 +293,7 @@ Our website is <http://domain.net>.
 
 [[Escaped Tag]]'''
 
-        assert_equal(f(source), result)
+        assert f(source) == result
 
     @skipIf(module_not_available('html2text'), 'html2text required')
     def test_convert_markup(self):
@@ -337,9 +337,9 @@ ticket [#1]
 [#1] header
 
 sha [aaaaaa]'''
-        assert_equal(f(source, 'test.md').strip(), result)
+        assert f(source, 'test.md').strip() == result
 
-        assert_equal(f('h1. Hello', 't.textile').strip(), '# Hello')
+        assert f('h1. Hello', 't.textile').strip() == '# Hello'
 
     @without_module('html2text')
     def test_convert_markup_without_html2text(self):
@@ -367,35 +367,35 @@ Our website is [[http://domain.net]].
 <p>[External link to the wiki page](https://github.com/a/b/wiki/Page)</p>
 <p>[External link](https://github.com/a/b/issues/1)</p>'''
 
-        assert_equal(f(source, 'test.textile').strip(), result)
+        assert f(source, 'test.textile').strip() == result
 
     def test_rewrite_links(self):
         f = GitHubWikiImporter().rewrite_links
         prefix = 'https://github/a/b/wiki'
         new = '/p/test/wiki/'
-        assert_equal(
+        assert (
             f('<a href="https://github/a/b/wiki/Test Page">Test Page</a>',
-              prefix, new),
+              prefix, new) ==
             '<a href="/p/test/wiki/Test Page">Test Page</a>')
-        assert_equal(
+        assert (
             f('<a href="https://github/a/b/wiki/Test-Page">Test-Page</a>',
-              prefix, new),
+              prefix, new) ==
             '<a href="/p/test/wiki/Test Page">Test Page</a>')
-        assert_equal(
+        assert (
             f('<a href="https://github/a/b/issues/1" class="1"></a>',
-              prefix, new),
+              prefix, new) ==
             '<a class="1" href="https://github/a/b/issues/1"></a>')
-        assert_equal(
+        assert (
             f('<a href="https://github/a/b/wiki/Test Page">https://github/a/b/wiki/Test Page</a>',
-              prefix, new),
+              prefix, new) ==
             '<a href="/p/test/wiki/Test Page">/p/test/wiki/Test Page</a>')
-        assert_equal(
+        assert (
             f('<a href="https://github/a/b/wiki/Test Page">Test blah blah</a>',
-              prefix, new),
+              prefix, new) ==
             '<a href="/p/test/wiki/Test Page">Test blah blah</a>')
-        assert_equal(
+        assert (
             f('<a href="https://github/a/b/wiki/Test Page">Test <b>Page</b></a>',
-              prefix, new),
+              prefix, new) ==
             '<a href="/p/test/wiki/Test Page">Test <b>Page</b></a>')
 
     @skipIf(module_not_available('html2text'), 'html2text required')
@@ -424,7 +424,7 @@ Our website is [[http://domain.net]].
 
 '''
 
-        assert_equal(f(source, 'test.mediawiki'), result)
+        assert f(source, 'test.mediawiki') == result
 
     @skipIf(module_not_available('html2text'), 'html2text required')
     def test_convert_textile_no_leading_tabs(self):
@@ -448,7 +448,7 @@ Some text 1.
 ## Header 2
 
 See [Page]'''
-        assert_equal(f(source, 'test.textile').strip(), result)
+        assert f(source, 'test.textile').strip() == result
 
     @skipIf(module_not_available('html2text'), 'html2text required')
     def test_convert_markup_with_amp_in_links(self):
@@ -460,7 +460,7 @@ See [Page]'''
         source = '[[Ticks & Leeches]]'
         result = '[Ticks & Leeches]'
         # markdown should be untouched
-        assert_equal(f(source, 'test.rst').strip(), result)
+        assert f(source, 'test.rst').strip() == result
 
     @skipIf(module_not_available('html2text'), 'html2text required')
     def test_convert_markup_textile(self):
@@ -485,12 +485,12 @@ See [Page]'''
 
 '''
 
-        assert_equal(f(source, 'test.textile'), result)
+        assert f(source, 'test.textile') == result
 
         # textile-style links converts normal
         source = '*"Textile":Troubleshooting*'
         result = '**[Textile](Troubleshooting)**\n\n'
-        assert_equal(f(source, 'test2.textile'), result)
+        assert f(source, 'test2.textile') == result
 
         # links with formatting converts normal in textile now
         source = '''*[[this checklist|Troubleshooting]]*
@@ -506,7 +506,7 @@ some text and **[Tips n\u2019 Tricks]**
 **[link](http://otherlink.com)**
 
 '''
-        assert_equal(f(source, 'test3.textile'), result)
+        assert f(source, 'test3.textile') == result
 
     @skipIf(module_not_available('html2text'), 'html2text required')
     def test_convert_textile_special_tag(self):
@@ -516,7 +516,7 @@ some text and **[Tips n\u2019 Tricks]**
         importer.app.url = '/p/test/wiki/'
         f = importer.convert_markup
         source = '*[[this checklist|Troubleshooting]]*'
-        assert_equal(f(source, 't.textile').strip(),
+        assert (f(source, 't.textile').strip() ==
                      '**[this checklist](Troubleshooting)**')
 
     @without_module('html2text')
@@ -528,7 +528,7 @@ some text and **[Tips n\u2019 Tricks]**
         f = importer.convert_markup
         source = '*[[this checklist|Troubleshooting]]*'
         result = '<p><strong>[[this checklist|Troubleshooting]]</strong></p>'
-        assert_equal(f(source, 't.textile').strip(), result)
+        assert f(source, 't.textile').strip() == result
 
     @patch('forgeimporters.github.wiki.mkdtemp', autospec=True)
     @patch('forgeimporters.github.wiki.rmtree', autospec=True)
@@ -536,7 +536,7 @@ some text and **[Tips n\u2019 Tricks]**
     def test_has_wiki_repo(self, repo, rmtree, mkdtemp):
         mkdtemp.return_value = 'fake path'
         i = GitHubWikiImporter()
-        assert_equal(i.has_wiki_repo('fake url'), True)
+        assert i.has_wiki_repo('fake url') == True
         repo.clone_from.assert_called_once_with(
             'fake url', to_path='fake path', bare=True)
         rmtree.assert_called_once_with('fake path')
@@ -544,7 +544,7 @@ some text and **[Tips n\u2019 Tricks]**
         def raise_error(*args, **kw):
             raise git.GitCommandError('bam', 'bam', 'bam')
         repo.clone_from.side_effect = raise_error
-        assert_equal(i.has_wiki_repo('fake url'), False)
+        assert i.has_wiki_repo('fake url') == False
 
 
 class TestGitHubWikiImportController(TestController, TestCase):
diff --git a/ForgeImporters/forgeimporters/tests/github/functional/test_github.py b/ForgeImporters/forgeimporters/tests/github/functional/test_github.py
index 57cb9b228..78dd617bf 100644
--- a/ForgeImporters/forgeimporters/tests/github/functional/test_github.py
+++ b/ForgeImporters/forgeimporters/tests/github/functional/test_github.py
@@ -62,16 +62,16 @@ class TestGitHubOAuth(TestController):
         oauth.return_value = oauth_instance
 
         user = M.User.by_username('test-admin')
-        assert_equal(user.get_tool_data('GitHubProjectImport', 'token'), None)
+        assert user.get_tool_data('GitHubProjectImport', 'token') == None
         r = self.app.get('/p/import_project/github/')
-        assert_equal(r.status_int, 302)
-        assert_equal(r.location, redirect)
+        assert r.status_int == 302
+        assert r.location == redirect
         session.__setitem__.assert_has_calls([
             call('github.oauth.state', 'state'),
             call('github.oauth.redirect',
                  'http://localhost/p/import_project/github/')
         ])
-        assert_equal(session.save.call_count, 1)
+        assert session.save.call_count == 1
 
         r = self.app.get(redirect)
         session.get.assert_has_calls([
@@ -79,14 +79,14 @@ class TestGitHubOAuth(TestController):
             call('github.oauth.redirect', '/')
         ])
         user = M.User.by_username('test-admin')
-        assert_equal(user.get_tool_data('GitHubProjectImport', 'token'), 'abc')
+        assert user.get_tool_data('GitHubProjectImport', 'token') == 'abc'
 
         with patch('forgeimporters.github.requests.post') as valid_access_token_post:
             valid_access_token_post.return_value = Mock(status_code=200)
             r = self.app.get('/p/import_project/github/')
 
         # token in user data, so oauth isn't triggered
-        assert_equal(r.status_int, 200)
+        assert r.status_int == 200
 
         valid_access_token_post.assert_called_once_with('https://api.github.com/applications/client_id/token',
                                                         auth=requests.auth.HTTPBasicAuth('client_id', 'secret'),
@@ -96,5 +96,5 @@ class TestGitHubOAuth(TestController):
 
     def test_project_import_login_required(self):
         r = self.app.get('/p/import_project/github/', extra_environ=dict(username='*anonymous'))
-        assert_equal(None, r.location)
+        assert None == r.location
         r.mustcontain('Login Required')
diff --git a/ForgeImporters/forgeimporters/tests/test_base.py b/ForgeImporters/forgeimporters/tests/test_base.py
index 44595cb86..b5d6dbe74 100644
--- a/ForgeImporters/forgeimporters/tests/test_base.py
+++ b/ForgeImporters/forgeimporters/tests/test_base.py
@@ -317,7 +317,7 @@ class TestProjectToolsImportController(TestController):
             import1_page = import_main_page.click('Import', href=r'importer1$')
         url = import1_page.request.path
         assert url.endswith('/admin/ext/import/importer1'), url
-        assert_equal(import1_page.text, 'test importer 1 controller webpage')
+        assert import1_page.text == 'test importer 1 controller webpage'
 
     @mock.patch.object(base.h, 'iter_entry_points')
     def test_hidden(self, iep):
@@ -344,16 +344,16 @@ def test_get_importer_upload_path():
         neighborhood=mock.Mock(url_prefix='p/'),
     )
     with h.push_config(config, importer_upload_path='path/{nbhd}/{project}'):
-        assert_equal(base.get_importer_upload_path(project), 'path/p/prefix')
+        assert base.get_importer_upload_path(project) == 'path/p/prefix'
         project.is_nbhd_project = True
-        assert_equal(base.get_importer_upload_path(project), 'path/p/n_url')
+        assert base.get_importer_upload_path(project) == 'path/p/n_url'
         project.is_nbhd_project = False
         project.is_user_project = True
-        assert_equal(base.get_importer_upload_path(project),
+        assert (base.get_importer_upload_path(project) ==
                      'path/p/shortname')
         project.is_user_project = False
         project.is_root = True
-        assert_equal(base.get_importer_upload_path(project),
+        assert (base.get_importer_upload_path(project) ==
                      'path/p/prefix/shortname')
 
 
@@ -385,7 +385,7 @@ class TestFile:
             'data': 'data',
         }
         f = base.File('http://example.com/barbaz.jpg')
-        assert_equal(f.type, 'image/jpeg')
+        assert f.type == 'image/jpeg'
 
         f = base.File('http://example.com/barbaz')
-        assert_equal(f.type, 'image/png')
+        assert f.type == 'image/png'
diff --git a/ForgeLink/forgelink/tests/functional/test_rest.py b/ForgeLink/forgelink/tests/functional/test_rest.py
index 4ec59b71e..d420d537a 100644
--- a/ForgeLink/forgelink/tests/functional/test_rest.py
+++ b/ForgeLink/forgelink/tests/functional/test_rest.py
@@ -34,20 +34,20 @@ class TestLinkApi(TestRestApiBase):
 
     def test_rest_link(self):
         r = self.api_get('/rest/p/test/link')
-        assert_equal(r.json['url'], None)
+        assert r.json['url'] == None
 
         r = self.api_post('/rest/p/test/link',
                           url='http://google.com')
-        assert_equal(r.json['url'], 'http://google.com')
+        assert r.json['url'] == 'http://google.com'
 
         self.api_post('/rest/p/test/link',
                       url='http://yahoo.com')
         r = self.api_get('/rest/p/test/link')
-        assert_equal(r.json['url'], 'http://yahoo.com')
+        assert r.json['url'] == 'http://yahoo.com'
 
         self.api_post('/rest/p/test/link')
         r = self.api_get('/rest/p/test/link')
-        assert_equal(r.json['url'], 'http://yahoo.com')
+        assert r.json['url'] == 'http://yahoo.com'
 
     def test_rest_link_get_permissions(self):
         self.app.get('/rest/p/test/link',
@@ -75,7 +75,7 @@ class TestLinkApi(TestRestApiBase):
                       extra_environ={'username': '*anonymous'},
                       status=200)
         r = self.api_get('/rest/p/test/link')
-        assert_equal(r.json['url'], 'http://yahoo.com')
+        assert r.json['url'] == 'http://yahoo.com'
 
 
 class TestLinkHasAccess(TestRestApiBase):
@@ -98,13 +98,13 @@ class TestLinkHasAccess(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/link/has_access?user=babadook&perm=read',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
         r = self.api_get(
             '/rest/p/test/link/has_access?user=test-user&perm=jump',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
     def test_has_access_not_admin(self):
         """
@@ -120,10 +120,10 @@ class TestLinkHasAccess(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/link/has_access?user=test-admin&perm=configure',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], True)
+        assert r.status_int == 200
+        assert r.json['result'] == True
         r = self.api_get(
             '/rest/p/test/link/has_access?user=test-user&perm=configure',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
diff --git a/ForgeLink/forgelink/tests/functional/test_root.py b/ForgeLink/forgelink/tests/functional/test_root.py
index 31b570d96..595c2aa46 100644
--- a/ForgeLink/forgelink/tests/functional/test_root.py
+++ b/ForgeLink/forgelink/tests/functional/test_root.py
@@ -37,7 +37,7 @@ class TestRootController(TestController):
         response.form['url'] = 'http://www.google.com/'
         response.form.submit()
         redir = self.app.get('/link/index', status=302)
-        assert_equal(redir.location, 'http://www.google.com/')
+        assert redir.location == 'http://www.google.com/'
 
     @td.with_link
     def test_root_with_url(self):
@@ -45,7 +45,7 @@ class TestRootController(TestController):
         response.form['url'] = 'http://www.google.com/'
         response.form.submit()
         redir = self.app.get('/link', status=302)
-        assert_equal(redir.location, 'http://www.google.com/')
+        assert redir.location == 'http://www.google.com/'
 
     @td.with_link
     def test_root_suffix_with_url_slash(self):
@@ -53,7 +53,7 @@ class TestRootController(TestController):
         response.form['url'] = 'http://www.google.com/'
         response.form.submit()
         redir = self.app.get('/link/service', status=302)
-        assert_equal(redir.location, 'http://www.google.com/service')
+        assert redir.location == 'http://www.google.com/service'
 
     @td.with_link
     def test_root_suffix_with_url_value(self):
@@ -61,7 +61,7 @@ class TestRootController(TestController):
         response.form['url'] = 'http://www.google.de/search?q='
         response.form.submit()
         redir = self.app.get(h.urlquote('/link/helpåß'), status=302)
-        assert_equal(redir.location, 'http://www.google.de/search?q=help%C3%A5%C3%9F')
+        assert redir.location == 'http://www.google.de/search?q=help%C3%A5%C3%9F'
 
 
 class TestConfigOptions(TestController):
@@ -72,7 +72,7 @@ class TestConfigOptions(TestController):
 
     def assert_url(self, mount_point, val):
         app = self.project.app_instance(mount_point)
-        assert_equal(app.config.options['url'], val)
+        assert app.config.options['url'] == val
 
     def test_sets_url_on_install(self):
         r = self.app.post('/p/test/admin/update_mounts', params={
@@ -93,17 +93,17 @@ class TestConfigOptions(TestController):
             'new.mount_label': 'Google',
             'url': 'invalid url'})
         flash = json.loads(self.webflash(r))
-        assert_equal(flash['status'], 'error')
-        assert_equal(flash['message'], 'ToolError: url: That is not a valid URL')
+        assert flash['status'] == 'error'
+        assert flash['message'] == 'ToolError: url: That is not a valid URL'
         app = self.project.app_instance('link-google')
-        assert_equal(app, None)
+        assert app == None
 
     @td.with_link
     def test_sets_url_on_config(self):
         self.assert_url('link', None)
         params = {'url': 'https://allura.apache.org'}
         r = self.app.post('/p/test/admin/link/configure', params=params)
-        assert_equal(self.webflash(r), '')
+        assert self.webflash(r) == ''
         self.assert_url('link', 'https://allura.apache.org')
 
     @td.with_link
@@ -112,28 +112,28 @@ class TestConfigOptions(TestController):
         params = {'url': 'invalid link'}
         r = self.app.post('/p/test/admin/link/configure', params=params)
         flash = json.loads(self.webflash(r))
-        assert_equal(flash['status'], 'error')
-        assert_equal(flash['message'], 'url: That is not a valid URL')
+        assert flash['status'] == 'error'
+        assert flash['message'] == 'url: That is not a valid URL'
         self.assert_url('link', None)
 
     @td.with_link
     def test_menu_url(self):
         resp = self.app.get('/p/test/admin/')
-        assert_in('/p/test/link/', str(resp.html.find(id='top_nav')))
+        assert '/p/test/link/' in str(resp.html.find(id='top_nav'))
 
         response = self.app.get('/admin/link/options')
         response.form['url'] = 'http://foo.bar/baz'
         response.form.submit()
 
         resp = self.app.get('/p/test/admin/')
-        assert_in('http://foo.bar/baz', str(resp.html.find(id='top_nav')))
+        assert 'http://foo.bar/baz' in str(resp.html.find(id='top_nav'))
 
     def _check_configurable(self, admin_nav_data):
         for menu_item in admin_nav_data['menu']:
             if menu_item['tool_name'] == 'link':
-                assert_in({'className': 'admin_modal',
+                assert ({'className': 'admin_modal',
                            'text': 'Options',
-                           'href': '/p/test/admin/link/options'},
+                           'href': '/p/test/admin/link/options'} in
                           menu_item['admin_options'])
                 break
         else:
diff --git a/ForgeLink/forgelink/tests/test_app.py b/ForgeLink/forgelink/tests/test_app.py
index 6ff4d5b1b..28efa0054 100644
--- a/ForgeLink/forgelink/tests/test_app.py
+++ b/ForgeLink/forgelink/tests/test_app.py
@@ -43,4 +43,4 @@ class TestBulkExport:
         f = tempfile.TemporaryFile('w+')
         link.bulk_export(f)
         f.seek(0)
-        assert_equal(json.loads(f.read())['url'], 'http://domain.net')
+        assert json.loads(f.read())['url'] == 'http://domain.net'
diff --git a/ForgeSVN/forgesvn/tests/functional/test_auth.py b/ForgeSVN/forgesvn/tests/functional/test_auth.py
index 992613e91..6ae98a74f 100644
--- a/ForgeSVN/forgesvn/tests/functional/test_auth.py
+++ b/ForgeSVN/forgesvn/tests/functional/test_auth.py
@@ -27,19 +27,19 @@ class TestSVNAuth(TestController):
     @with_svn
     def test_refresh_repo(self):
         r = self.app.get('/auth/refresh_repo')
-        assert_equal(r.text, 'No repo specified')
+        assert r.text == 'No repo specified'
 
         r = self.app.get('/auth/refresh_repo/p/gbalksdfh')
-        assert_equal(r.text, 'No project at /p/gbalksdfh')
+        assert r.text == 'No project at /p/gbalksdfh'
 
         r = self.app.get('/auth/refresh_repo/p/test')
-        assert_equal(r.text, '/p/test does not include a repo mount point')
+        assert r.text == '/p/test does not include a repo mount point'
 
         r = self.app.get('/auth/refresh_repo/p/test/blah/')
-        assert_equal(r.text, 'Cannot find repo at /p/test/blah')
+        assert r.text == 'Cannot find repo at /p/test/blah'
 
         r = self.app.get('/auth/refresh_repo/p/test/src/')
-        assert_equal(r.text,
+        assert (r.text ==
                      '<Repository /tmp/svn/p/test/src> refresh queued.\n')
 
 
@@ -52,6 +52,6 @@ class TestSVNUserPermissions(TestController):
     def test_list_repos(self):
         r = self.app.get('/auth/repo_permissions',
                          params=dict(username='test-admin'), status=200)
-        assert_equal(json.loads(r.text), {"allow_write": [
+        assert json.loads(r.text) == {"allow_write": [
             '/svn/test/src',
-        ]})
+        ]}
diff --git a/ForgeSVN/forgesvn/tests/functional/test_controllers.py b/ForgeSVN/forgesvn/tests/functional/test_controllers.py
index 1644b20cc..1a4cbe637 100644
--- a/ForgeSVN/forgesvn/tests/functional/test_controllers.py
+++ b/ForgeSVN/forgesvn/tests/functional/test_controllers.py
@@ -101,42 +101,42 @@ class TestRootController(SVNTestController):
     def test_commit_browser_data(self):
         resp = self.app.get('/src/commit_browser_data')
         data = json.loads(resp.text)
-        assert_equal(data['max_row'], 6)
-        assert_equal(data['next_column'], 1)
+        assert data['max_row'] == 6
+        assert data['next_column'] == 1
         for val in data['built_tree'].values():
             if val['url'] == '/p/test/src/1/':
-                assert_equal(val['short_id'], '[r1]')
-                assert_equal(val['column'], 0)
-                assert_equal(val['row'], 6)
-                assert_equal(val['message'], 'Create readme')
+                assert val['short_id'] == '[r1]'
+                assert val['column'] == 0
+                assert val['row'] == 6
+                assert val['message'] == 'Create readme'
 
     def test_feed(self):
         for ext in ['', '.rss']:
             r = self.app.get('/src/feed%s' % ext)
             channel = r.xml.find('channel')
             title = channel.find('title').text
-            assert_equal(title, 'test SVN changes')
+            assert title == 'test SVN changes'
             description = channel.find('description').text
-            assert_equal(description,
+            assert (description ==
                          'Recent changes to SVN repository in test project')
             link = channel.find('link').text
-            assert_equal(link, 'http://localhost/p/test/src/')
+            assert link == 'http://localhost/p/test/src/'
             earliest_commit = channel.findall('item')[-1]
-            assert_equal(earliest_commit.find('title').text, 'Create readme')
+            assert earliest_commit.find('title').text == 'Create readme'
             link = 'http://localhost/p/test/src/1/'
-            assert_equal(earliest_commit.find('link').text, link)
-            assert_equal(earliest_commit.find('guid').text, link)
+            assert earliest_commit.find('link').text == link
+            assert earliest_commit.find('guid').text == link
         # .atom has slightly different structure
         prefix = '{http://www.w3.org/2005/Atom}'
         r = self.app.get('/src/feed.atom')
         title = r.xml.find(prefix + 'title').text
-        assert_equal(title, 'test SVN changes')
+        assert title == 'test SVN changes'
         link = r.xml.find(prefix + 'link').attrib['href']
-        assert_equal(link, 'http://localhost/p/test/src/')
+        assert link == 'http://localhost/p/test/src/'
         earliest_commit = r.xml.findall(prefix + 'entry')[-1]
-        assert_equal(earliest_commit.find(prefix + 'title').text, 'Create readme')
+        assert earliest_commit.find(prefix + 'title').text == 'Create readme'
         link = 'http://localhost/p/test/src/1/'
-        assert_equal(earliest_commit.find(prefix + 'link').attrib['href'], link)
+        assert earliest_commit.find(prefix + 'link').attrib['href'] == link
 
     def test_commit(self):
         resp = self.app.get('/src/3/tree/')
@@ -146,7 +146,7 @@ class TestRootController(SVNTestController):
         resp = self.app.get('/src/6/')
         file_url = resp.html.find("a", string="/ЗРЯЧИЙ_ТА_ПОБАЧИТЬ")['href']
         resp = self.app.get(file_url)
-        assert_in('This is readme',  # same content as the README file actually
+        assert ('This is readme' in  # same content as the README file actually
                   resp.html.select_one('.codebrowser').text)
 
         resp = self.app.get('/src/7/')
@@ -154,22 +154,22 @@ class TestRootController(SVNTestController):
             '\n\t'.join(str(t) for t in resp.html.select('.inline-diff a'))))
         file_url = resp.html.find("a", string="/with%2Furlquote-literal.txt")['href']
         file_resp = self.app.get(file_url)
-        assert_in('%2F means /',
+        assert ('%2F means /' in
                   file_resp.html.select_one('.codebrowser').text)
 
         file_url = resp.html.find("a", string='/with-percent%.txt')['href']
         file_resp = self.app.get(file_url)
-        assert_in('%%%',
+        assert ('%%%' in
                   file_resp.html.select_one('.codebrowser').text)
 
         file_url = resp.html.find("a", string="/with space.txt")['href']
         file_resp = self.app.get(file_url)
-        assert_in('spaces',
+        assert ('spaces' in
                   file_resp.html.select_one('.codebrowser').text)
 
         file_url = resp.html.find("a", string='/with"&:specials.txt')['href']
         file_resp = self.app.get(file_url)
-        assert_in('"&: encodes as %22%26%3A',
+        assert ('"&: encodes as %22%26%3A' in
                   file_resp.html.select_one('.codebrowser').text)
 
     def test_tree(self):
@@ -262,39 +262,39 @@ class TestRootController(SVNTestController):
         shutil.rmtree(c.app.repo.tarball_path, ignore_errors=True)
         r = self.app.get('/p/test/svn-tags/19/tree/')
         form = r.html.find('form', 'tarball')
-        assert_equal(form.button.text, '\xa0Download Snapshot')
-        assert_equal(form.get('action'), '/p/test/svn-tags/19/tarball')
+        assert form.button.text == '\xa0Download Snapshot'
+        assert form.get('action') == '/p/test/svn-tags/19/tarball'
 
         r = self.app.get('/p/test/svn-tags/19/tree/tags/tag-1.0/')
         form = r.html.find('form', 'tarball')
-        assert_equal(form.button.text, '\xa0Download Snapshot')
-        assert_equal(form.get('action'), '/p/test/svn-tags/19/tarball')
-        assert_equal(form.find('input', attrs=dict(name='path')).get('value'), '/tags/tag-1.0')
+        assert form.button.text == '\xa0Download Snapshot'
+        assert form.get('action') == '/p/test/svn-tags/19/tarball'
+        assert form.find('input', attrs=dict(name='path')).get('value') == '/tags/tag-1.0'
 
         r = self.app.get('/p/test/svn-tags/19/tarball_status?path=/tags/tag-1.0')
-        assert_equal(r.json['status'], None)
+        assert r.json['status'] == None
         r = self.app.post('/p/test/svn-tags/19/tarball',
                           dict(path='/tags/tag-1.0')).follow()
         assert 'Generating snapshot...' in r
         M.MonQTask.run_ready()
         r = self.app.get('/p/test/svn-tags/19/tarball_status?path=/tags/tag-1.0')
-        assert_equal(r.json['status'], 'complete')
+        assert r.json['status'] == 'complete'
 
         r = self.app.get('/p/test/svn-tags/19/tarball_status?path=/trunk')
-        assert_equal(r.json['status'], None)
+        assert r.json['status'] == None
         r = self.app.post('/p/test/svn-tags/19/tarball',
                           dict(path='/trunk/')).follow()
         assert 'Generating snapshot...' in r
         M.MonQTask.run_ready()
         r = self.app.get('/p/test/svn-tags/19/tarball_status?path=/trunk')
-        assert_equal(r.json['status'], 'complete')
+        assert r.json['status'] == 'complete'
 
         r = self.app.get('/p/test/svn-tags/19/tarball_status?path=/branches/aaa/')
-        assert_equal(r.json['status'], None)
+        assert r.json['status'] == None
 
         # this is is the same as trunk snapshot, so it's ready already
         r = self.app.get('/p/test/svn-tags/19/tarball_status')
-        assert_equal(r.json['status'], 'complete')
+        assert r.json['status'] == 'complete'
 
 
 class TestImportController(SVNTestController):
diff --git a/ForgeSVN/forgesvn/tests/model/test_repository.py b/ForgeSVN/forgesvn/tests/model/test_repository.py
index 8451b4341..9d5e02856 100644
--- a/ForgeSVN/forgesvn/tests/model/test_repository.py
+++ b/ForgeSVN/forgesvn/tests/model/test_repository.py
@@ -82,25 +82,25 @@ class TestNewRepo(unittest.TestCase):
         assert self.rev.index_id().startswith('allura/model/repo/Commit#')
         self.rev.author_url
         self.rev.committer_url
-        assert_equal(self.rev.tree._id, self.rev.tree_id)
-        assert_equal(self.rev.shorthand_id(), f'[r{latest_rev}]')
-        assert_equal(self.rev.symbolic_ids, ([], []))
-        assert_equal(self.rev.url(), f'/p/test/src/{latest_rev}/')
+        assert self.rev.tree._id == self.rev.tree_id
+        assert self.rev.shorthand_id() == f'[r{latest_rev}]'
+        assert self.rev.symbolic_ids == ([], [])
+        assert self.rev.url() == f'/p/test/src/{latest_rev}/'
         all_cis = list(self.repo.log(self.rev._id, limit=25))
-        assert_equal(len(all_cis), latest_rev)
+        assert len(all_cis) == latest_rev
         self.rev.tree.ls()
-        assert_equal(self.rev.tree.readme(), ('README', 'This is readme\nAnother Line\n'))
-        assert_equal(self.rev.tree.path(), '/')
-        assert_equal(self.rev.tree.url(), f'/p/test/src/{latest_rev}/tree/')
+        assert self.rev.tree.readme() == ('README', 'This is readme\nAnother Line\n')
+        assert self.rev.tree.path() == '/'
+        assert self.rev.tree.url() == f'/p/test/src/{latest_rev}/tree/'
         self.rev.tree.by_name['README']
         assert self.rev.tree.is_blob('README') is True
-        assert_equal(self.rev.tree['a']['b']['c'].ls(), [])
+        assert self.rev.tree['a']['b']['c'].ls() == []
         self.assertRaises(KeyError, lambda: self.rev.tree['a']['b']['d'])
 
-        assert_equal(self.rev.authored_user, None)
-        assert_equal(self.rev.committed_user, None)
-        assert_equal(
-            sorted(self.rev.webhook_info.keys()),
+        assert self.rev.authored_user == None
+        assert self.rev.committed_user == None
+        assert (
+            sorted(self.rev.webhook_info.keys()) ==
             sorted(['id', 'url', 'timestamp', 'message', 'author',
                     'committer', 'added', 'removed', 'renamed', 'modified', 'copied']))
 
@@ -235,11 +235,11 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
 
     def test_log_id_only(self):
         entries = list(self.repo.log(id_only=True, limit=25))
-        assert_equal(entries, [7, 6, 5, 4, 3, 2, 1])
+        assert entries == [7, 6, 5, 4, 3, 2, 1]
 
     def test_log(self):
         entries = list(self.repo.log(id_only=False, limit=25))
-        assert_equal(entries[len(entries)-6:],  # only 6, so this test doesn't have to change when commits added
+        assert (entries[len(entries)-6:] ==  # only 6, so this test doesn't have to change when commits added
                      [
             {'parents': [5],
              'refs': [],
@@ -327,7 +327,7 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
 
     def test_log_file(self):
         entries = list(self.repo.log(path='/README', id_only=False, limit=25))
-        assert_equal(entries, [
+        assert entries == [
             {'authored': {'date': datetime(2010, 10, 8, 15, 32, 48, 272296),
                           'email': '',
                           'name': 'rick446'},
@@ -352,7 +352,7 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
              'refs': [],
              'size': 15,
              'rename_details': {}},
-        ])
+        ]
 
     def test_is_file(self):
         assert self.repo.is_file('/README')
@@ -407,9 +407,9 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
 
     def test_diff_copy(self):
         entry = self.repo.commit(next(self.repo.log(5, id_only=True, limit=1)))
-        assert_equals(dict(entry.diffs), dict(
+        assert dict(entry.diffs) == dict(
                 copied=[{'new': '/b', 'old': '/a', 'ratio': 1}],  renamed=[],
-                changed=[], removed=[], added=[], total=1))
+                changed=[], removed=[], added=[], total=1)
 
     def test_commit(self):
         entry = self.repo.commit(1)
@@ -432,16 +432,16 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
     @skipUnless(os.path.exists(tg.config.get('scm.repos.tarball.zip_binary', '/usr/bin/zip')), 'zip binary is missing')
     def test_tarball(self):
         tmpdir = tg.config['scm.repos.tarball.root']
-        assert_equal(self.repo.tarball_path,
+        assert (self.repo.tarball_path ==
                      os.path.join(tmpdir, 'svn/t/te/test/testsvn'))
-        assert_equal(self.repo.tarball_url('1'),
+        assert (self.repo.tarball_url('1') ==
                      'file:///svn/t/te/test/testsvn/test-src-r1.zip')
         self.repo.tarball('1')
         assert os.path.isfile(
             os.path.join(tmpdir, "svn/t/te/test/testsvn/test-src-r1.zip"))
         tarball_zip = ZipFile(
             os.path.join(tmpdir, 'svn/t/te/test/testsvn/test-src-r1.zip'), 'r')
-        assert_equal(tarball_zip.namelist(),
+        assert (tarball_zip.namelist() ==
                      ['test-src-r1/', 'test-src-r1/README'])
         shutil.rmtree(self.repo.tarball_path.encode('utf-8'),
                       ignore_errors=True)
@@ -461,7 +461,7 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
         tag_content = sorted(['test-svn-tags-r19-tags-tag-1.0/',
                               'test-svn-tags-r19-tags-tag-1.0/svn-commit.tmp',
                               'test-svn-tags-r19-tags-tag-1.0/README'])
-        assert_equal(sorted(snapshot.namelist()), tag_content)
+        assert sorted(snapshot.namelist()) == tag_content
         os.remove(fn)
 
         # a directory (of tags)
@@ -473,7 +473,7 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
                                'test-svn-tags-r19-tags/tag-1.0/',
                                'test-svn-tags-r19-tags/tag-1.0/svn-commit.tmp',
                                'test-svn-tags-r19-tags/tag-1.0/README'])
-        assert_equal(sorted(snapshot.namelist()), tags_content)
+        assert sorted(snapshot.namelist()) == tags_content
         os.remove(fn)
 
         # no path, but there are trunk in the repo
@@ -487,7 +487,7 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
                                 'test-svn-tags-r19-trunk/bbb.txt',
                                 'test-svn-tags-r19-trunk/ccc.txt',
                                 'test-svn-tags-r19-trunk/README'])
-        assert_equal(sorted(snapshot.namelist()), trunk_content)
+        assert sorted(snapshot.namelist()) == trunk_content
         os.remove(fn)
 
         # no path, and no trunk dir
@@ -497,7 +497,7 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
         self.repo.tarball('1')
         assert os.path.isfile(fn), fn
         snapshot = ZipFile(fn, 'r')
-        assert_equal(snapshot.namelist(), ['test-src-r1/', 'test-src-r1/README'])
+        assert snapshot.namelist() == ['test-src-r1/', 'test-src-r1/README']
         shutil.rmtree(os.path.join(tmpdir, 'svn/t/te/test/testsvn/'),
                       ignore_errors=True)
         shutil.rmtree(tarball_path, ignore_errors=True)
@@ -568,7 +568,7 @@ class TestSVNRepo(unittest.TestCase, RepoImplTestBase):
                 'url': 'http://localhost/p/test/src/',
             },
         }
-        assert_equals(payload, expected_payload)
+        assert payload == expected_payload
 
 
 class TestSVNRev(unittest.TestCase):
@@ -614,17 +614,17 @@ class TestSVNRev(unittest.TestCase):
     def test_log(self):
         # path only
         commits = list(self.repo.log(self.repo.head, id_only=True, limit=25))
-        assert_equal(commits, [7, 6, 5, 4, 3, 2, 1])
+        assert commits == [7, 6, 5, 4, 3, 2, 1]
         commits = list(self.repo.log(self.repo.head, 'README', id_only=True, limit=25))
-        assert_equal(commits, [3, 1])
+        assert commits == [3, 1]
         commits = list(self.repo.log(1, 'README', id_only=True, limit=25))
-        assert_equal(commits, [1])
+        assert commits == [1]
         commits = list(self.repo.log(self.repo.head, 'a/b/c/', id_only=True, limit=25))
-        assert_equal(commits, [4, 2])
+        assert commits == [4, 2]
         commits = list(self.repo.log(3, 'a/b/c/', id_only=True, limit=25))
-        assert_equal(commits, [2])
-        assert_equal(
-            list(self.repo.log(self.repo.head, 'does/not/exist', id_only=True, limit=25)), [])
+        assert commits == [2]
+        assert (
+            list(self.repo.log(self.repo.head, 'does/not/exist', id_only=True, limit=25)) == [])
 
     def test_notification_email(self):
         setup_global_objects()
@@ -644,8 +644,8 @@ class TestSVNRev(unittest.TestCase):
         n = M.Notification.query.find({'subject': '[test:src] New commit [r1] by rick446'}).first()
 
         assert n
-        assert_in('By rick446', n.text)
-        assert_in('Create readme', n.text)
+        assert 'By rick446' in n.text
+        assert 'Create readme' in n.text
 
 
 class _Test(unittest.TestCase):
@@ -770,12 +770,12 @@ class TestRepo(_TestWithRepo):
         assert i['name_s'] == 'test1', i
 
     def test_scm_host_url(self):
-        assert_equal(self.repo.clone_url('rw', 'nobody'),
+        assert (self.repo.clone_url('rw', 'nobody') ==
                      'svn+ssh://nobody@localhost:8022/scm-repo/p/test/test1/')
-        assert_equal(self.repo.clone_url('https', 'nobody'),
+        assert (self.repo.clone_url('https', 'nobody') ==
                      'https://nobody@localhost:8022/scm-repo/p/test/test1/')
         with h.push_config(self.repo.app.config.options, external_checkout_url='https://$username@foo.com/'):
-            assert_equal(self.repo.clone_url('https', 'user'),
+            assert (self.repo.clone_url('https', 'user') ==
                          'https://user@foo.com/')
 
     def test_guess_type(self):
@@ -821,8 +821,8 @@ class TestRepo(_TestWithRepo):
         notifications = M.Notification.query.find().all()
         for n in notifications:
             if '100 new commits' in n.subject:
-                assert_in('By Test Committer on 10/08/2010 15:32', n.text)
-                assert_in('http://localhost/ci/foo99/', n.text)
+                assert 'By Test Committer on 10/08/2010 15:32' in n.text
+                assert 'http://localhost/ci/foo99/' in n.text
                 break
         else:
             assert False, 'Did not find notification'
@@ -945,7 +945,7 @@ class TestCommit(_TestWithRepo):
             'removed': [],
             'total': 5,
         }
-        assert_equal(self.ci.diffs.added,
+        assert (self.ci.diffs.added ==
                      ['a', 'a/a', 'a/a/a', 'a/a/b', 'a/b'])
         assert (self.ci.diffs.copied
                 == self.ci.diffs.changed
@@ -969,8 +969,8 @@ class TestCommit(_TestWithRepo):
             'removed': ['a', 'a/a', 'a/a/a', 'a/a/b', 'a/b'],
             'total': 10,
         }
-        assert_equal(ci.diffs.added, ['b', 'b/a', 'b/a/a', 'b/a/b', 'b/b'])
-        assert_equal(ci.diffs.removed, ['a', 'a/a', 'a/a/a', 'a/a/b', 'a/b'])
+        assert ci.diffs.added == ['b', 'b/a', 'b/a/a', 'b/a/b', 'b/b']
+        assert ci.diffs.removed == ['a', 'a/a', 'a/a/a', 'a/a/b', 'a/b']
         assert (ci.diffs.copied
                 == ci.diffs.changed
                 == [])
@@ -1004,17 +1004,17 @@ class TestCommit(_TestWithRepo):
             'renamed': [],
             'total': 2
         }
-        assert_equal(ci.diffs.added, ['b/a/z', 'b/c'])
-        assert_equal(ci.diffs.changed, [])
-        assert_equal(ci.diffs.removed, ['/b/a/b', 'b/b'])
+        assert ci.diffs.added == ['b/a/z', 'b/c']
+        assert ci.diffs.changed == []
+        assert ci.diffs.removed == ['/b/a/b', 'b/b']
         # see mock for open_blob
-        assert_equal(len(ci.diffs.copied), 2)
-        assert_equal(ci.diffs.copied[1]['old'], 'b/a/b')
-        assert_equal(ci.diffs.copied[1]['new'], 'b/c')
-        assert_equal(ci.diffs.copied[1]['ratio'], 1)
-        assert_equal(ci.diffs.copied[1]['diff'], '')
-        assert_equal(ci.diffs.copied[0]['old'], 'b/b')
-        assert_equal(ci.diffs.copied[0]['new'], 'b/a/z')
+        assert len(ci.diffs.copied) == 2
+        assert ci.diffs.copied[1]['old'] == 'b/a/b'
+        assert ci.diffs.copied[1]['new'] == 'b/c'
+        assert ci.diffs.copied[1]['ratio'] == 1
+        assert ci.diffs.copied[1]['diff'] == ''
+        assert ci.diffs.copied[0]['old'] == 'b/b'
+        assert ci.diffs.copied[0]['new'] == 'b/a/z'
 
     def test_context(self):
         self.ci.context()
@@ -1042,19 +1042,18 @@ class TestRename(unittest.TestCase):
 
     def test_log_file_with_rename(self):
         entry = list(self.repo.log(path='/dir/b.txt', id_only=False, limit=1))[0]
-        assert_equal(entry['id'], 3)
-        assert_equal(entry['rename_details']['path'], '/dir/a.txt')
-        assert_equal(
-            entry['rename_details']['commit_url'],
-            self.repo.url_for_commit(2)  # previous revision
-        )
+        assert entry['id'] == 3
+        assert entry['rename_details']['path'] == '/dir/a.txt'
+        assert (
+            entry['rename_details']['commit_url'] ==
+            self.repo.url_for_commit(2))
 
     def test_check_changed_path(self):
         changed_path = {'copyfrom_path': '/test/path', 'path': '/test/path2'}
         result = self.repo._impl._check_changed_path(
             changed_path, '/test/path2/file.txt')
-        assert_equal({'path': '/test/path2/file.txt',
-                     'copyfrom_path': '/test/path/file.txt'}, result)
+        assert {'path': '/test/path2/file.txt',
+                     'copyfrom_path': '/test/path/file.txt'} == result
 
 
 class TestDirectRepoAccess:
@@ -1088,7 +1087,7 @@ class TestDirectRepoAccess:
             'renamed': [],
             'total': 1,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
 
         _id = self.repo._impl._oid(2)
         diffs = self.repo.commit(_id).diffs
@@ -1100,7 +1099,7 @@ class TestDirectRepoAccess:
             'copied': [],
             'total': 4,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
 
         _id = self.repo._impl._oid(3)
         diffs = self.repo.commit(_id).diffs
@@ -1112,7 +1111,7 @@ class TestDirectRepoAccess:
             'copied': [],
             'total': 1,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
 
         _id = self.repo._impl._oid(4)
         diffs = self.repo.commit(_id).diffs
@@ -1124,4 +1123,4 @@ class TestDirectRepoAccess:
             'copied': [],
             'total': 1,
         }
-        assert_equals(diffs, expected)
+        assert diffs == expected
diff --git a/ForgeSVN/forgesvn/tests/model/test_svnimplementation.py b/ForgeSVN/forgesvn/tests/model/test_svnimplementation.py
index 769ce1a82..0667d1fdc 100644
--- a/ForgeSVN/forgesvn/tests/model/test_svnimplementation.py
+++ b/ForgeSVN/forgesvn/tests/model/test_svnimplementation.py
@@ -51,8 +51,8 @@ class TestSVNImplementation:
 
         tree_id = impl.compute_tree_new(commit, path)
 
-        assert_equal(impl._svn.info2.call_args[0]
-                     [0], 'file://' + g.tmpdir + '/code/trunk/foo')
+        assert (impl._svn.info2.call_args[0]
+                     [0] == 'file://' + g.tmpdir + '/code/trunk/foo')
         assert lcd_partial.called
 
     def test_last_commit_ids(self):
@@ -73,9 +73,9 @@ class TestSVNImplementation:
         commit._id = '5057636b9c1040636b81e4b1:6'
         entries = impl.last_commit_ids(commit, [path])
 
-        assert_equal(entries, {path.strip('/'): '5057636b9c1040636b81e4b1:1'})
-        assert_equal(impl._svn.info2.call_args[0]
-                     [0], 'file://' + g.tmpdir + '/code/trunk')
+        assert entries == {path.strip('/'): '5057636b9c1040636b81e4b1:1'}
+        assert (impl._svn.info2.call_args[0]
+                     [0] == 'file://' + g.tmpdir + '/code/trunk')
 
     @patch('forgesvn.model.svn.svn_path_exists')
     def test__tarball_path_clean(self, path_exists):
@@ -85,16 +85,16 @@ class TestSVNImplementation:
         impl = SVNImplementation(repo)
         path_exists.return_value = False
         # edge cases
-        assert_equal(impl._tarball_path_clean(None), '')
-        assert_equal(impl._tarball_path_clean(''), '')
+        assert impl._tarball_path_clean(None) == ''
+        assert impl._tarball_path_clean('') == ''
         # common
-        assert_equal(impl._tarball_path_clean('/some/path/'), 'some/path')
-        assert_equal(impl._tarball_path_clean('some/path'), 'some/path')
-        assert_equal(impl._tarball_path_clean('/some/path/tags/1.0/some/dir'), 'some/path/tags/1.0/some/dir')
+        assert impl._tarball_path_clean('/some/path/') == 'some/path'
+        assert impl._tarball_path_clean('some/path') == 'some/path'
+        assert impl._tarball_path_clean('/some/path/tags/1.0/some/dir') == 'some/path/tags/1.0/some/dir'
         # with fallback to trunk
         path_exists.return_value = True
-        assert_equal(impl._tarball_path_clean(None), 'trunk')
-        assert_equal(impl._tarball_path_clean(''), 'trunk')
+        assert impl._tarball_path_clean(None) == 'trunk'
+        assert impl._tarball_path_clean('') == 'trunk'
 
     @patch('forgesvn.model.svn.svn_path_exists')
     def test_update_checkout_url(self, svn_path_exists):
@@ -104,14 +104,14 @@ class TestSVNImplementation:
         svn_path_exists.side_effect = lambda path: False
         opts['checkout_url'] = 'invalid'
         impl.update_checkout_url()
-        assert_equal(opts['checkout_url'], '')
+        assert opts['checkout_url'] == ''
 
         svn_path_exists.side_effect = lambda path: path.endswith('trunk')
         opts['checkout_url'] = 'invalid'
         impl.update_checkout_url()
-        assert_equal(opts['checkout_url'], 'trunk')
+        assert opts['checkout_url'] == 'trunk'
 
         svn_path_exists.side_effect = lambda path: path.endswith('trunk')
         opts['checkout_url'] = ''
         impl.update_checkout_url()
-        assert_equal(opts['checkout_url'], 'trunk')
+        assert opts['checkout_url'] == 'trunk'
diff --git a/ForgeSVN/forgesvn/tests/test_svn_app.py b/ForgeSVN/forgesvn/tests/test_svn_app.py
index b62a5cf5b..605ffe59c 100644
--- a/ForgeSVN/forgesvn/tests/test_svn_app.py
+++ b/ForgeSVN/forgesvn/tests/test_svn_app.py
@@ -40,8 +40,8 @@ class TestSVNApp(unittest.TestCase):
         ThreadLocalORMSession.close_all()
 
     def test_admin_menu(self):
-        assert_equals(len(c.app.admin_menu()), 7)
-        assert_equals(c.app.admin_menu()[0].label, 'Checkout URL')
+        assert len(c.app.admin_menu()) == 7
+        assert c.app.admin_menu()[0].label == 'Checkout URL'
 
     def test_uninstall(self):
         from allura import model as M
diff --git a/ForgeSVN/forgesvn/tests/test_tasks.py b/ForgeSVN/forgesvn/tests/test_tasks.py
index 3fa2c6d7c..e95899ecf 100644
--- a/ForgeSVN/forgesvn/tests/test_tasks.py
+++ b/ForgeSVN/forgesvn/tests/test_tasks.py
@@ -57,7 +57,7 @@ class TestRepoTasks(unittest.TestCase):
             repo_tasks.init()
             M.main_orm_session.flush()
             assert f.called_with()
-            assert_equal(ns, M.Notification.query.find().count())
+            assert ns == M.Notification.query.find().count()
 
     def test_clone(self):
         ns = M.Notification.query.find().count()
diff --git a/ForgeShortUrl/forgeshorturl/tests/functional/test.py b/ForgeShortUrl/forgeshorturl/tests/functional/test.py
index 704dcc78f..547ca8e01 100644
--- a/ForgeShortUrl/forgeshorturl/tests/functional/test.py
+++ b/ForgeShortUrl/forgeshorturl/tests/functional/test.py
@@ -43,7 +43,7 @@ class TestRootController(TestController):
         response.form['full_url'] = 'http://www.google.com/'
         response.form.submit()
         redir = self.app.get('/url/test', status=302)
-        assert_equal(redir.location, 'http://www.google.com/')
+        assert redir.location == 'http://www.google.com/'
 
     def test_shorturl_http_head(self):
         response = self.app.get('/admin/url/add')
@@ -51,7 +51,7 @@ class TestRootController(TestController):
         response.form['full_url'] = 'http://www.google.com/'
         response.form.submit()
         r = self.app.head('/url/test', status=302)
-        assert_equal(r.location, 'http://www.google.com/')
+        assert r.location == 'http://www.google.com/'
 
     def test_shorturl_update(self):
         response = self.app.get('/admin/url/add')
@@ -59,7 +59,7 @@ class TestRootController(TestController):
         response.form['full_url'] = 'http://www.google.com/'
         response.form.submit()
         redir = self.app.get('/url/g', status=302)
-        assert_equal(redir.location, 'http://www.google.com/')
+        assert redir.location == 'http://www.google.com/'
 
         response = self.app.get('/url/')
         form = response.forms['short-url-form']
@@ -69,7 +69,7 @@ class TestRootController(TestController):
         form.action = '/admin/url/add/'
         form.submit()
         redir = self.app.get('/url/g', status=302)
-        assert_equal(redir.location, 'http://www.yahoo.com/')
+        assert redir.location == 'http://www.yahoo.com/'
 
     def test_shorturl_not_found(self):
         self.app.post('/admin/url/add',
@@ -148,7 +148,7 @@ class TestRootController(TestController):
 
             url = ShortUrl.build_short_url(app, 's')
 
-            assert_equal(url, 'b:n:p:m:s')
+            assert url == 'b:n:p:m:s'
 
     def test_short_url(self):
         response = self.app.get('/admin/url/add')
@@ -162,4 +162,4 @@ class TestRootController(TestController):
                 'short_url.url_pattern': '{base_url}:{nbhd}:{project}:{mount_point}:{short_name}',
                 'base_url': 'b',
         }):
-            assert_equal(surl.short_url(), 'b:p:test:url:test')
+            assert surl.short_url() == 'b:p:test:url:test'
diff --git a/ForgeTracker/forgetracker/tests/command/test_fix_discussion.py b/ForgeTracker/forgetracker/tests/command/test_fix_discussion.py
index 7c82519a1..9074e46ff 100644
--- a/ForgeTracker/forgetracker/tests/command/test_fix_discussion.py
+++ b/ForgeTracker/forgetracker/tests/command/test_fix_discussion.py
@@ -70,18 +70,18 @@ def test_fix_discussion():
     tracker = M.AppConfig.query.find({'options.mount_point': 'bugs'}).first()
     t1 = TM.Ticket.query.get(ticket_num=1)
     t2 = TM.Ticket.query.get(ticket_num=2)
-    assert_not_equal(
-        t1.discussion_thread.discussion.app_config_id, tracker._id)
-    assert_not_equal(t2.discussion_thread.discussion_id, tracker.discussion_id)
+    assert (
+        t1.discussion_thread.discussion.app_config_id != tracker._id)
+    assert t2.discussion_thread.discussion_id != tracker.discussion_id
 
     cmd = fix_discussion.FixDiscussion('fix-discussion')
     cmd.run([test_config, 'test'])
 
     t1 = TM.Ticket.query.get(ticket_num=1)
     t2 = TM.Ticket.query.get(ticket_num=2)
-    assert_equal(t1.discussion_thread.discussion.app_config_id, tracker._id)
-    assert_equal(t2.discussion_thread.discussion_id, tracker.discussion_id)
+    assert t1.discussion_thread.discussion.app_config_id == tracker._id
+    assert t2.discussion_thread.discussion_id == tracker.discussion_id
     for p in t2.discussion_thread.posts:
-        assert_equal(p.app_config_id, tracker._id)
-        assert_equal(p.app_id, tracker._id)
-        assert_equal(p.discussion_id, tracker.discussion_id)
+        assert p.app_config_id == tracker._id
+        assert p.app_id == tracker._id
+        assert p.discussion_id == tracker.discussion_id
diff --git a/ForgeTracker/forgetracker/tests/functional/test_rest.py b/ForgeTracker/forgetracker/tests/functional/test_rest.py
index 0d1f4acc3..be72dd250 100644
--- a/ForgeTracker/forgetracker/tests/functional/test_rest.py
+++ b/ForgeTracker/forgetracker/tests/functional/test_rest.py
@@ -90,13 +90,13 @@ class TestRestNewTicket(TestTrackerApiBase):
             summary = 'Second ticket'
             self.create_ticket(summary=summary)
             t = TM.Ticket.query.get(summary=summary)
-            assert_not_equal(t, None)
+            assert t != None
         # Set rate limit to 1 in first hour of project
         with h.push_config(config, **{'forgetracker.rate_limits': '{"3600": 1}'}):
             summary = 'Third ticket'
             self.create_ticket(summary=summary, status=429)
             t = TM.Ticket.query.get(summary=summary)
-            assert_equal(t, None)
+            assert t == None
 
 
 class TestRestUpdateTicket(TestTrackerApiBase):
@@ -152,7 +152,7 @@ class TestRestIndex(TestTrackerApiBase):
         # make sure it didn't get removed from the db too
         ticket_config = M.AppConfig.query.get(
             project_id=c.project._id, tool_name='tickets')
-        assert_equal(ticket_config.options.get('TicketMonitoringEmail'),
+        assert (ticket_config.options.get('TicketMonitoringEmail') ==
                      'test@localhost')
 
     @td.with_tool('test', 'Tickets', 'dummy')
@@ -164,7 +164,7 @@ class TestRestIndex(TestTrackerApiBase):
             params={'tracker': str(dummy_tracker.config._id)}).follow()
 
         ticket = self.api_get('/rest/p/test/bugs/1/')
-        assert_equal(ticket.request.path, '/rest/p/test/dummy/1/')
+        assert ticket.request.path == '/rest/p/test/dummy/1/'
 
 
 class TestRestDiscussion(TestTrackerApiBase):
@@ -206,11 +206,11 @@ class TestRestSearch(TestTrackerApiBase):
     def test_no_criteria(self, paged_search):
         paged_search.return_value = dict(tickets=[self.ticket])
         r = self.api_get('/rest/p/test/bugs/search')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['tickets'][0]['summary'], 'our test ticket')
-        assert_equal(r.json['tickets'][0]['ticket_num'], 5)
-        assert_equal(r.json['tickets'][0]['status'], 'open')
-        assert_equal(r.json['tickets'][0]['labels'], ['tiny', 'minor'])
+        assert r.status_int == 200
+        assert r.json['tickets'][0]['summary'] == 'our test ticket'
+        assert r.json['tickets'][0]['ticket_num'] == 5
+        assert r.json['tickets'][0]['status'] == 'open'
+        assert r.json['tickets'][0]['labels'] == ['tiny', 'minor']
         assert 'description' not in r.json
         assert 'discussion_thread' not in r.json
 
@@ -227,16 +227,16 @@ class TestRestSearch(TestTrackerApiBase):
         )
         r = self.api_get('/rest/p/test/bugs/search',
                          q=q, sort='status', limit='2')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['limit'], 2)
-        assert_equal(r.json['q'], q)
-        assert_equal(r.json['sort'], 'status')
-        assert_equal(r.json['count'], 1)
-        assert_equal(r.json['page'], 0)
-        assert_equal(r.json['tickets'][0]['summary'], 'our test ticket')
-        assert_equal(r.json['tickets'][0]['ticket_num'], 5)
-        assert_equal(r.json['tickets'][0]['status'], 'open')
-        assert_equal(r.json['tickets'][0]['labels'], ['tiny', 'minor'])
+        assert r.status_int == 200
+        assert r.json['limit'] == 2
+        assert r.json['q'] == q
+        assert r.json['sort'] == 'status'
+        assert r.json['count'] == 1
+        assert r.json['page'] == 0
+        assert r.json['tickets'][0]['summary'] == 'our test ticket'
+        assert r.json['tickets'][0]['ticket_num'] == 5
+        assert r.json['tickets'][0]['status'] == 'open'
+        assert r.json['tickets'][0]['labels'] == ['tiny', 'minor']
         assert 'description' not in r.json
         assert 'discussion_thread' not in r.json
 
@@ -253,13 +253,13 @@ class TestRestHasAccess(TestTrackerApiBase):
         r = self.api_get(
             '/rest/p/test/bugs/has_access?user=babadook&perm=read',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
         r = self.api_get(
             '/rest/p/test/bugs/has_access?user=test-user&perm=jump',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
     def test_has_access_not_admin(self):
         """
@@ -275,10 +275,10 @@ class TestRestHasAccess(TestTrackerApiBase):
         r = self.api_get(
             '/rest/p/test/bugs/has_access?user=test-admin&perm=delete',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], True)
+        assert r.status_int == 200
+        assert r.json['result'] == True
         r = self.api_get(
             '/rest/p/test/bugs/has_access?user=test-user&perm=delete',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
diff --git a/ForgeTracker/forgetracker/tests/functional/test_root.py b/ForgeTracker/forgetracker/tests/functional/test_root.py
index 02ff29132..e0556322e 100644
--- a/ForgeTracker/forgetracker/tests/functional/test_root.py
+++ b/ForgeTracker/forgetracker/tests/functional/test_root.py
@@ -303,9 +303,9 @@ class TestFunctionalController(TrackerTestController):
     def test_new_ticket(self):
         summary = 'test new ticket'
         ticket_view = self.new_ticket(summary=summary).follow()
-        assert_true(summary in ticket_view)
+        assert summary in ticket_view
         opts = self.subscription_options(ticket_view)
-        assert_equal(opts['subscribed'], False)
+        assert opts['subscribed'] == False
 
     def test_ticket_get_markdown(self):
         self.new_ticket(summary='my ticket', description='my description')
@@ -350,17 +350,17 @@ class TestFunctionalController(TrackerTestController):
                 {'name': '1.0', 'count': 2},
                 {'name': '2.0', 'count': 0}
             ]}
-        assert_equal(r.text, json.dumps(counts))
+        assert r.text == json.dumps(counts)
         # Private tickets shouldn't be included in counts if user doesn't
         # have read access to private tickets.
         r = self.app.get('/bugs/milestone_counts',
                          extra_environ=dict(username='*anonymous'))
         counts['milestone_counts'][0]['count'] = 1
-        assert_equal(r.text, json.dumps(counts))
+        assert r.text == json.dumps(counts)
 
         self.app.post('/bugs/1/delete')
         r = self.app.get('/bugs/milestone_counts')
-        assert_equal(r.text, json.dumps(counts))
+        assert r.text == json.dumps(counts)
 
     def test_bin_counts(self):
         self.new_ticket(summary='test new')
@@ -368,9 +368,9 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
 
         r = self.app.get('/bugs/bin_counts')
-        assert_equal(r.json, {"bin_counts": [{"count": 2, "label": "Changes"},
+        assert r.json == {"bin_counts": [{"count": 2, "label": "Changes"},
                                              {"count": 0, "label": "Closed Tickets"},
-                                             {"count": 2, "label": "Open Tickets"}]})
+                                             {"count": 2, "label": "Open Tickets"}]}
 
         """
         forgetracker.model.ticket.Globals.bin_count doesn't do a permission check like corresponding milestone_count
@@ -409,13 +409,13 @@ class TestFunctionalController(TrackerTestController):
         response = self.app.get('/bugs/new/?summary=very buggy&description=descr&labels=label1,label2&private=true'
                                 '&assigned_to=test-user&_milestone=2.0&status=pending')
         form = self._find_new_ticket_form(response)
-        assert_equal(form['ticket_form.summary'].value, 'very buggy')
-        assert_equal(form['ticket_form.description'].value, 'descr')
-        assert_equal(form['ticket_form.labels'].value, 'label1,label2')
-        assert_equal(form['ticket_form.assigned_to'].value, 'test-user')
-        assert_equal(form['ticket_form._milestone'].value, '2.0')
-        assert_equal(form['ticket_form.status'].value, 'pending')
-        assert_equal(form['ticket_form.private'].checked, True)
+        assert form['ticket_form.summary'].value == 'very buggy'
+        assert form['ticket_form.description'].value == 'descr'
+        assert form['ticket_form.labels'].value == 'label1,label2'
+        assert form['ticket_form.assigned_to'].value == 'test-user'
+        assert form['ticket_form._milestone'].value == '2.0'
+        assert form['ticket_form.status'].value == 'pending'
+        assert form['ticket_form.private'].checked == True
 
     def test_mass_edit(self):
         self.new_ticket(summary='First Ticket').follow()
@@ -481,9 +481,9 @@ class TestFunctionalController(TrackerTestController):
         ticket1 = tm.Ticket.query.get(summary='Ticket1')
         ticket2 = tm.Ticket.query.get(summary='Ticket2')
         ticket3 = tm.Ticket.query.get(summary='Ticket3')
-        assert_equal(ticket1.labels, ['tag2', 'tag3'])
-        assert_equal(ticket2.labels, ['tag1', 'tag2', 'tag3'])
-        assert_equal(ticket3.labels, ['tag1', 'tag2', 'tag3'])
+        assert ticket1.labels == ['tag2', 'tag3']
+        assert ticket2.labels == ['tag1', 'tag2', 'tag3']
+        assert ticket3.labels == ['tag1', 'tag2', 'tag3']
         r = self.app.get('/p/test/bugs/3/')
         assert '<li><strong>Labels</strong>: tag1, tag2 --&gt; tag1, tag2, tag3</li>' in r
 
@@ -524,8 +524,8 @@ class TestFunctionalController(TrackerTestController):
             'summary': 'First Custom'}).first()
         ticket2 = tm.Ticket.query.find({
             'summary': 'Second Custom'}).first()
-        assert_equal(ticket1.custom_fields._major, False)
-        assert_equal(ticket2.custom_fields._major, False)
+        assert ticket1.custom_fields._major == False
+        assert ticket2.custom_fields._major == False
 
         self.app.post('/p/test/bugs/update_tickets', {
             '__search': '',
@@ -542,8 +542,8 @@ class TestFunctionalController(TrackerTestController):
         assert '<li><strong>Major</strong>: False --&gt; True</li>' in r
         ticket1 = tm.Ticket.query.find({'summary': 'First Custom'}).first()
         ticket2 = tm.Ticket.query.find({'summary': 'Second Custom'}).first()
-        assert_equal(ticket1.custom_fields._major, True)
-        assert_equal(ticket2.custom_fields._major, True)
+        assert ticket1.custom_fields._major == True
+        assert ticket2.custom_fields._major == True
 
         self.app.post('/p/test/bugs/update_tickets', {
             '__search': '',
@@ -554,7 +554,7 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
         ticket2 = tm.Ticket.query.find({
             'summary': 'Second Custom'}).first()
-        assert_equal(ticket2.custom_fields._major, False)
+        assert ticket2.custom_fields._major == False
         self.app.post('/p/test/bugs/update_tickets', {
             '__search': '',
             '__ticket_ids': (
@@ -566,8 +566,8 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
         ticket1 = tm.Ticket.query.find({'summary': 'First Custom'}).first()
         ticket2 = tm.Ticket.query.find({'summary': 'Second Custom'}).first()
-        assert_equal(ticket1.custom_fields._major, True)
-        assert_equal(ticket2.custom_fields._major, False)
+        assert ticket1.custom_fields._major == True
+        assert ticket2.custom_fields._major == False
 
     def test_mass_edit_select_options_split(self):
         params = dict(
@@ -585,12 +585,12 @@ class TestFunctionalController(TrackerTestController):
         r = self.app.get('/p/test/bugs/edit/')
         opts = r.html.find('select', attrs={'name': '_type'})
         opts = opts.findAll('option')
-        assert_equal(opts[0].get('value'), '')
-        assert_equal(opts[0].getText(), 'no change')
-        assert_equal(opts[1].get('value'), 'Bug')
-        assert_equal(opts[1].getText(), 'Bug')
-        assert_equal(opts[2].get('value'), 'Feature Request')
-        assert_equal(opts[2].getText(), 'Feature Request')
+        assert opts[0].get('value') == ''
+        assert opts[0].getText() == 'no change'
+        assert opts[1].get('value') == 'Bug'
+        assert opts[1].getText() == 'Bug'
+        assert opts[2].get('value') == 'Feature Request'
+        assert opts[2].getText() == 'Feature Request'
 
     def test_mass_edit_private_field(self):
         kw = {'private': True}
@@ -613,8 +613,8 @@ class TestFunctionalController(TrackerTestController):
         assert '<li><strong>Private</strong>: No --&gt; Yes</li>' not in r
         ticket1 = tm.Ticket.query.find({'summary': 'First'}).first()
         ticket2 = tm.Ticket.query.find({'summary': 'Second'}).first()
-        assert_equal(ticket1.private, False)
-        assert_equal(ticket2.private, False)
+        assert ticket1.private == False
+        assert ticket2.private == False
 
         self.app.post('/p/test/bugs/update_tickets', {
             '__search': '',
@@ -630,8 +630,8 @@ class TestFunctionalController(TrackerTestController):
         assert '<li><strong>Private</strong>: No --&gt; Yes</li>' in r
         ticket1 = tm.Ticket.query.find({'summary': 'First'}).first()
         ticket2 = tm.Ticket.query.find({'summary': 'Second'}).first()
-        assert_equal(ticket1.private, True)
-        assert_equal(ticket2.private, True)
+        assert ticket1.private == True
+        assert ticket2.private == True
 
         ticket2.private = False
         self.app.post('/p/test/bugs/update_tickets', {
@@ -644,15 +644,15 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
         ticket1 = tm.Ticket.query.find({'summary': 'First'}).first()
         ticket2 = tm.Ticket.query.find({'summary': 'Second'}).first()
-        assert_equal(ticket1.private, True)
-        assert_equal(ticket2.private, False)
+        assert ticket1.private == True
+        assert ticket2.private == False
 
     def test_private_ticket(self):
         ticket_view = self.new_ticket(summary='Public Ticket').follow()
-        assert_in('<label class="simple">Private:</label> No', squish_spaces(ticket_view.text))
+        assert '<label class="simple">Private:</label> No' in squish_spaces(ticket_view.text)
         ticket_view = self.new_ticket(summary='Private Ticket',
                                       private=True).follow()
-        assert_in('<label class="simple">Private:</label> Yes', squish_spaces(ticket_view.text))
+        assert '<label class="simple">Private:</label> Yes' in squish_spaces(ticket_view.text)
         M.MonQTask.run_ready()
         # Creator sees private ticket on list page...
         index_response = self.app.get('/p/test/bugs/')
@@ -699,12 +699,12 @@ class TestFunctionalController(TrackerTestController):
             'ticket_form.private': 'on',
         })
         response = self.app.get('/bugs/1/')
-        assert_true('<li><strong>private</strong>: No --&gt; Yes</li>' in response)
+        assert '<li><strong>private</strong>: No --&gt; Yes</li>' in response
 
     def test_discussion_disabled_ticket(self):
         response = self.new_ticket(summary='test discussion disabled ticket').follow()
         # New tickets will not show discussion disabled
-        assert_not_in('<span class="closed">Discussion Disabled</span>', response)
+        assert '<span class="closed">Discussion Disabled</span>' not in response
 
         ticket_params = {
             'ticket_form.summary': 'test discussion disabled ticket',
@@ -719,28 +719,28 @@ class TestFunctionalController(TrackerTestController):
 
         # Disable Discussion
         response = self.app.post('/bugs/1/update_ticket_from_widget', ticket_params).follow()
-        assert_in('<li><strong>discussion</strong>: enabled --&gt; disabled</li>', response)
-        assert_in('<span class="closed">Discussion Disabled</span>', response)
-        assert_in('edit_post_form reply', response)  # Make sure admin can still comment
+        assert '<li><strong>discussion</strong>: enabled --&gt; disabled</li>' in response
+        assert '<span class="closed">Discussion Disabled</span>' in response
+        assert 'edit_post_form reply' in response  # Make sure admin can still comment
 
         # Unauthorized user cannot comment or even see form fields
         env = dict(username='*anonymous')
         r = self.app.get('/p/test/bugs/1', extra_environ=env)
-        assert_not_in('edit_post_form reply', r)
+        assert 'edit_post_form reply' not in r
 
         # Test re-enabling discussions
         ticket_params['ticket_form.discussion_disabled'] = 'off'
         response = self.app.post('/bugs/1/update_ticket_from_widget', ticket_params).follow()
-        assert_in('<li><strong>discussion</strong>: disabled --&gt; enabled</li>', response)
-        assert_not_in('<span class="closed">Discussion Disabled</span>', response)
+        assert '<li><strong>discussion</strong>: disabled --&gt; enabled</li>' in response
+        assert '<span class="closed">Discussion Disabled</span>' not in response
 
         # Test solr search
         M.MonQTask.run_ready()
         ThreadLocalORMSession.flush_all()
         # At this point, there is one ticket and it has discussion_disabled set to False
         r = self.app.get('/bugs/search/?q=discussion_disabled_b:False')
-        assert_in('1 results', r)
-        assert_in('test discussion disabled ticket', r)
+        assert '1 results' in r
+        assert 'test discussion disabled ticket' in r
 
         # Set discussion_disabled to True and search again
         ticket_params['ticket_form.discussion_disabled'] = 'on'
@@ -748,12 +748,12 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
         ThreadLocalORMSession.flush_all()
         r = self.app.get('/bugs/search/?q=discussion_disabled_b:True')
-        assert_in('1 results', r)
-        assert_in('test discussion disabled ticket', r)
+        assert '1 results' in r
+        assert 'test discussion disabled ticket' in r
 
         # Make sure there are no other tickets or false positives for good measure.
         r = self.app.get('/bugs/search/?q=discussion_disabled_b:False')
-        assert_in('0 results', r)
+        assert '0 results' in r
 
     @td.with_tool('test', 'Tickets', 'doc-bugs')
     def test_two_trackers(self):
@@ -763,13 +763,13 @@ class TestFunctionalController(TrackerTestController):
         ThreadLocalORMSession.flush_all()
         M.MonQTask.run_ready()
         ThreadLocalORMSession.flush_all()
-        assert_true(summary in ticket_view)
+        assert summary in ticket_view
         index_view = self.app.get('/doc-bugs/')
-        assert_true(summary in index_view)
-        assert_true(sidebar_contains(index_view, '<span>1.0</span>'))
+        assert summary in index_view
+        assert sidebar_contains(index_view, '<span>1.0</span>')
         index_view = self.app.get('/bugs/')
-        assert_true(sidebar_contains(index_view, '<span>1.0</span>'))
-        assert_false(summary in index_view)
+        assert sidebar_contains(index_view, '<span>1.0</span>')
+        assert not summary in index_view
 
     def test_render_ticket(self):
         summary = 'test render ticket'
@@ -790,7 +790,7 @@ class TestFunctionalController(TrackerTestController):
         # Make sure the 'Create Ticket' button is disabled for user without 'create' perm
         r = self.app.get('/bugs/', extra_environ=dict(username='*anonymous'))
         create_button = r.html.find('a', attrs={'href': '/p/test/bugs/new/'})
-        assert_equal(create_button['class'], ['icon', 'sidebar-disabled'])
+        assert create_button['class'] == ['icon', 'sidebar-disabled']
 
     @patch.dict('allura.lib.app_globals.config', markdown_cache_threshold='0')
     def test_cached_convert(self):
@@ -811,11 +811,11 @@ class TestFunctionalController(TrackerTestController):
         # We want to make sure the 'last_updated' field isn't updated by the cache creation
         r = self.app.get('/bugs/1').follow()
         last_updated = r.html.find("span", {"id": "updated_id"}).text.strip()
-        assert_equal(last_updated, '2010-01-01')
+        assert last_updated == '2010-01-01'
 
         # Make sure the cache has been saved.
         t = tm.Ticket.query.find({'_id': ticket._id}).first()
-        assert_in('<h1 id="test-markdown-cached_convert">Test markdown cached_convert</h1>', t.description_cache.html)
+        assert '<h1 id="test-markdown-cached_convert">Test markdown cached_convert</h1>' in t.description_cache.html
 
     def test_ticket_diffs(self):
         self.new_ticket(summary='difftest', description='1\n2\n3\n')
@@ -834,8 +834,8 @@ class TestFunctionalController(TrackerTestController):
             'comment': 'user comment',
         })
         t = tm.Ticket.query.get(ticket_num=1)
-        assert_true(t.discussion_thread.first_post.is_meta)
-        assert_false(t.discussion_thread.last_post.is_meta)
+        assert t.discussion_thread.first_post.is_meta
+        assert not t.discussion_thread.last_post.is_meta
 
     def test_ticket_label_unlabel(self):
         summary = 'test labeling and unlabeling a ticket'
@@ -850,9 +850,9 @@ class TestFunctionalController(TrackerTestController):
             'comment': ''
         })
         response = self.app.get('/bugs/1/')
-        assert_true('yellow' in response)
-        assert_true('greén' in response)
-        assert_true('<li><strong>labels</strong>:  --&gt; yellow, greén</li>' in response)
+        assert 'yellow' in response
+        assert 'greén' in response
+        assert '<li><strong>labels</strong>:  --&gt; yellow, greén</li>' in response
         self.app.post('/bugs/1/update_ticket', {
             'summary': 'zzz',
             'description': 'bbb',
@@ -863,8 +863,8 @@ class TestFunctionalController(TrackerTestController):
             'comment': ''
         })
         response = self.app.get('/bugs/1/')
-        assert_true('yellow' in response)
-        assert_true('<li><strong>labels</strong>: yellow, greén --&gt; yellow</li>' in response)
+        assert 'yellow' in response
+        assert '<li><strong>labels</strong>: yellow, greén --&gt; yellow</li>' in response
         self.app.post('/bugs/1/update_ticket', {
             'summary': 'zzz',
             'description': 'bbb',
@@ -875,7 +875,7 @@ class TestFunctionalController(TrackerTestController):
             'comment': ''
         })
         response = self.app.get('/bugs/1/')
-        assert_true('<li><strong>labels</strong>: yellow --&gt; </li>' in response)
+        assert '<li><strong>labels</strong>: yellow --&gt; </li>' in response
 
     def test_new_attachment(self):
         file_name = 'test_root.py'
@@ -885,12 +885,12 @@ class TestFunctionalController(TrackerTestController):
         ticket_editor = self.app.post('/bugs/1/update_ticket', {
             'summary': 'zzz'
         }, upload_files=[upload]).follow()
-        assert_true(file_name in ticket_editor)
+        assert file_name in ticket_editor
         assert '<span>py</span>' not in ticket_editor
         ticket_page = self.app.get('/bugs/1/')
         diff = ticket_page.html.findAll('div', attrs={'class': 'codehilite'})
         added = diff[-1].findAll('span', attrs={'class': 'gi'})[-1]
-        assert_in('+test_root.py', added.getText())
+        assert '+test_root.py' in added.getText()
 
     def test_delete_attachment(self):
         file_name = 'test_root.py'
@@ -904,7 +904,7 @@ class TestFunctionalController(TrackerTestController):
         req = self.app.get('/bugs/1/')
         form = self._find_update_ticket_form(req)
         file_link = BeautifulSoup(form.text).findAll('a')[2]
-        assert_equal(file_link.string, file_name)
+        assert file_link.string == file_name
         self.app.post(str(file_link['href']), {
             'delete': 'True'
         })
@@ -912,7 +912,7 @@ class TestFunctionalController(TrackerTestController):
         assert '/p/test/bugs/1/attachment/test_root.py' not in ticket_page
         diff = ticket_page.html.findAll('div', attrs={'class': 'codehilite'})
         removed = diff[-1].findAll('span', attrs={'class': 'gd'})[-1]
-        assert_in('-test_root.py', removed.getText())
+        assert '-test_root.py' in removed.getText()
 
     def test_delete_attachment_from_comments(self):
         ticket_view = self.new_ticket(summary='test ticket').follow()
@@ -947,7 +947,7 @@ class TestFunctionalController(TrackerTestController):
         }, upload_files=[upload]).follow()
         form = self._find_update_ticket_form(ticket_editor)
         download = self.app.get(str(BeautifulSoup(form.text).findAll('a')[2]['href']))
-        assert_equal(download.body, file_data)
+        assert download.body == file_data
 
     def test_two_attachments(self):
         file_name1 = 'test_root1.py'
@@ -1043,12 +1043,12 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
         ThreadLocalORMSession.flush_all()
         r = self.app.get('/p/test/bugs/3/')
-        assert_in('Tickets: #1', r)
-        assert_not_in('Tickets: <s>#1</s>', r)
-        assert_in('Tickets: <s>#2</s>', r)
+        assert 'Tickets: #1' in r
+        assert 'Tickets: <s>#1</s>' not in r
+        assert 'Tickets: <s>#2</s>' in r
 
-        assert_in('<a class="alink" href="/p/test/bugs/1/">[#1]</a>', r.text)
-        assert_in('<a class="alink strikethrough" href="/p/test/bugs/2/">[#2]</a>', r.text)
+        assert '<a class="alink" href="/p/test/bugs/1/">[#1]</a>' in r.text
+        assert '<a class="alink strikethrough" href="/p/test/bugs/2/">[#2]</a>' in r.text
 
     def test_ticket_view_editable(self):
         summary = 'test ticket view page can be edited'
@@ -1299,22 +1299,22 @@ class TestFunctionalController(TrackerTestController):
         form['ticket_form.custom_fields._category'] = 'bugs'
         error_form = form.submit()
         form = self._find_new_ticket_form(error_form)
-        assert_equal(form['ticket_form.custom_fields._priority'].value, 'urgent')
-        assert_equal(form['ticket_form.custom_fields._category'].value, 'bugs')
+        assert form['ticket_form.custom_fields._priority'].value == 'urgent'
+        assert form['ticket_form.custom_fields._category'].value == 'bugs'
         # Test edit ticket form
         self.new_ticket(summary='Test ticket')
         response = self.app.get('/bugs/1/')
         form = self._find_update_ticket_form(response)
-        assert_equal(
-            form['ticket_form.custom_fields._priority'].value, 'normal')
-        assert_equal(form['ticket_form.custom_fields._category'].value, '')
+        assert (
+            form['ticket_form.custom_fields._priority'].value == 'normal')
+        assert form['ticket_form.custom_fields._category'].value == ''
         form['ticket_form.summary'] = ''
         form['ticket_form.custom_fields._priority'] = 'urgent'
         form['ticket_form.custom_fields._category'] = 'bugs'
         error_form = form.submit()
         form = self._find_update_ticket_form(error_form)
-        assert_equal(form['ticket_form.custom_fields._priority'].value, 'urgent')
-        assert_equal(form['ticket_form.custom_fields._category'].value, 'bugs')
+        assert form['ticket_form.custom_fields._priority'].value == 'urgent'
+        assert form['ticket_form.custom_fields._category'].value == 'bugs'
 
     def test_new_ticket_validation(self):
         summary = 'ticket summary'
@@ -1384,9 +1384,9 @@ class TestFunctionalController(TrackerTestController):
         response.mustcontain('results of 3')
         response.mustcontain('test second ticket')
         next_page_link = response.html.select('.page_list a')[0]
-        assert_equal(next_page_link.text, '2')
+        assert next_page_link.text == '2'
         # keep 'q' and zero-based page nums:
-        assert_equal(next_page_link['href'], '/p/test/bugs/search/?q=test&limit=2&page=1')
+        assert next_page_link['href'] == '/p/test/bugs/search/?q=test&limit=2&page=1'
 
         # 'filter' is special kwarg, don't let it cause problems
         r = self.app.get('/p/test/bugs/search/?q=test&filter=blah')
@@ -1550,8 +1550,8 @@ class TestFunctionalController(TrackerTestController):
         r = self.app.post(f['action'], params=params,
                           headers={'Referer': b'/bugs/1/'})
         r = self.app.get('/bugs/1/', dict(page='1'))
-        assert_true(post_content in r)
-        assert_true(len(r.html.findAll(attrs={'class': 'discussion-post'})) == 1)
+        assert post_content in r
+        assert len(r.html.findAll(attrs={'class': 'discussion-post'})) == 1
 
         new_summary = 'old ticket'
         for f in ticket_view.html.findAll('form'):
@@ -1566,8 +1566,8 @@ class TestFunctionalController(TrackerTestController):
         r = self.app.post(f['action'], params=params,
                           headers={'Referer': b'/bugs/1/'})
         r = self.app.get('/bugs/1/', dict(page='1'))
-        assert_true(summary + ' --&gt; ' + new_summary in r)
-        assert_true(len(r.html.findAll(attrs={'class': 'discussion-post meta_post'})) == 1)
+        assert summary + ' --&gt; ' + new_summary in r
+        assert len(r.html.findAll(attrs={'class': 'discussion-post meta_post'})) == 1
 
     def test_discussion_paging(self):
         summary = 'test discussion paging'
@@ -1585,17 +1585,17 @@ class TestFunctionalController(TrackerTestController):
         r = self.app.post(f['action'], params=params,
                           headers={'Referer': b'/bugs/1/'})
         r = self.app.get('/bugs/1/', dict(page='-1'))
-        assert_true(summary in r)
+        assert summary in r
         r = self.app.get('/bugs/1/', dict(page='1'))
-        assert_true(post_content in r)
+        assert post_content in r
         # no pager if just one page
-        assert_false('Page 1 of 1' in r)
+        assert not 'Page 1 of 1' in r
         # add some more posts and check for pager
         for i in range(2):
             r = self.app.post(f['action'], params=params,
                               headers={'Referer': b'/bugs/1/'})
         r = self.app.get('/bugs/1/', dict(page='1', limit='2'))
-        assert_true('Page 2 of 2' in r)
+        assert 'Page 2 of 2' in r
 
     def test_discussion_feed(self):
         summary = 'test discussion paging'
@@ -1643,16 +1643,16 @@ class TestFunctionalController(TrackerTestController):
         ThreadLocalORMSession.flush_all()
         response = self.app.get('/p/test/bugs/?sort=summary+asc')
         ticket_rows = response.html.find('table', {'class': 'ticket-list'}).find('tbody')
-        assert_in('test first ticket', ticket_rows.text)
-        assert_in('test second ticket', ticket_rows.text)
+        assert 'test first ticket' in ticket_rows.text
+        assert 'test second ticket' in ticket_rows.text
         edit_link = response.html.find('a', {'title': 'Bulk Edit'})
         expected_link = "/p/test/bugs/edit/?q=%21status%3Aclosed+%26%26+%21status%3Awont-fix"\
                         "&sort=snippet_s+asc&limit=25&filter=&page=0"
         assert_equivalent_urls(expected_link, edit_link['href'])
         response = self.app.get(edit_link['href'])
         ticket_rows = response.html.find('tbody', {'class': 'ticket-list'})
-        assert_in('test first ticket', ticket_rows.text)
-        assert_in('test second ticket', ticket_rows.text)
+        assert 'test first ticket' in ticket_rows.text
+        assert 'test second ticket' in ticket_rows.text
 
     def test_bulk_edit_milestone(self):
         self.new_ticket(summary='test first ticket',
@@ -1666,17 +1666,17 @@ class TestFunctionalController(TrackerTestController):
         ThreadLocalORMSession.flush_all()
         response = self.app.get('/p/test/bugs/milestone/1.0/?sort=ticket_num+asc')
         ticket_rows = response.html.find('table', {'class': 'ticket-list'}).find('tbody')
-        assert_in('test first ticket', ticket_rows.text)
-        assert_in('test second ticket', ticket_rows.text)
-        assert_in('test third ticket', ticket_rows.text)
+        assert 'test first ticket' in ticket_rows.text
+        assert 'test second ticket' in ticket_rows.text
+        assert 'test third ticket' in ticket_rows.text
         edit_link = response.html.find('a', {'title': 'Bulk Edit'})
         expected_link = "/p/test/bugs/edit/?q=_milestone%3A1.0&sort=ticket_num_i+asc&limit=25&filter=&page=0"
         assert_equivalent_urls(expected_link, edit_link['href'])
         response = self.app.get(edit_link['href'])
         ticket_rows = response.html.find('tbody', {'class': 'ticket-list'})
-        assert_in('test first ticket', ticket_rows.text)
-        assert_in('test second ticket', ticket_rows.text)
-        assert_in('test third ticket', ticket_rows.text)
+        assert 'test first ticket' in ticket_rows.text
+        assert 'test second ticket' in ticket_rows.text
+        assert 'test third ticket' in ticket_rows.text
 
     def test_bulk_edit_search(self):
         self.new_ticket(summary='test first ticket', status='open')
@@ -1687,17 +1687,17 @@ class TestFunctionalController(TrackerTestController):
         ThreadLocalORMSession.flush_all()
         response = self.app.get('/p/test/bugs/search/?q=status%3Aopen')
         ticket_rows = response.html.find('table', {'class': 'ticket-list'}).find('tbody')
-        assert_in('test first ticket', ticket_rows.text)
-        assert_in('test second ticket', ticket_rows.text)
-        assert_false('test third ticket' in ticket_rows.text)
+        assert 'test first ticket' in ticket_rows.text
+        assert 'test second ticket' in ticket_rows.text
+        assert not 'test third ticket' in ticket_rows.text
         edit_link = response.html.find('a', {'title': 'Bulk Edit'})
         expected_link = "/p/test/bugs/edit/?q=status%3Aopen&limit=25&filter=%7B%7D&page=0"
         assert_equivalent_urls(expected_link, edit_link['href'])
         response = self.app.get(edit_link['href'])
         ticket_rows = response.html.find('tbody', {'class': 'ticket-list'})
-        assert_in('test first ticket', ticket_rows.text)
-        assert_in('test second ticket', ticket_rows.text)
-        assert_false('test third ticket' in ticket_rows.text)
+        assert 'test first ticket' in ticket_rows.text
+        assert 'test second ticket' in ticket_rows.text
+        assert not 'test third ticket' in ticket_rows.text
 
     def test_bulk_edit_after_filtering(self):
         self.new_ticket(summary='test first ticket', status='open')
@@ -1713,7 +1713,7 @@ class TestFunctionalController(TrackerTestController):
         r = self.app.post('/bugs/save_ticket', {
             'ticket_form.summary': 'new ticket with attachment'
         }, upload_files=[upload]).follow()
-        assert_in(file_name, r)
+        assert file_name in r
         ThreadLocalORMSession.flush_all()
         M.MonQTask.run_ready()
         ThreadLocalORMSession.flush_all()
@@ -1724,7 +1724,7 @@ class TestFunctionalController(TrackerTestController):
             '**Attachments:**\n\n'
             '- [tést_root.py]'
             '(http://localhost/p/test/bugs/1/attachment/t%C3%A9st_root.py)')
-        assert_in(expected_text, email.kwargs['text'])
+        assert expected_text in email.kwargs['text']
 
     def test_ticket_notification_contains_milestones(self):
         params = dict(
@@ -1755,8 +1755,8 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
         ThreadLocalORMSession.flush_all()
         email = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).first()
-        assert_in('**Releases:** 1.0-beta', email.kwargs.text)
-        assert_in('**Milestone:** 2.0', email.kwargs.text)
+        assert '**Releases:** 1.0-beta' in email.kwargs.text
+        assert '**Milestone:** 2.0' in email.kwargs.text
 
     def test_bulk_edit_notifications(self):
         self.new_ticket(summary='test first ticket',
@@ -1788,26 +1788,26 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
 
         emails = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).all()
-        assert_equal(len(emails), 3)
+        assert len(emails) == 3
         for email in emails:
-            assert_equal(email.kwargs.subject, '[test:bugs] Mass edit changes by Test Admin')
+            assert email.kwargs.subject == '[test:bugs] Mass edit changes by Test Admin'
         first_user_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': str(first_user._id)
         }).all()
-        assert_equal(len(first_user_email), 1)
+        assert len(first_user_email) == 1
         first_user_email = first_user_email[0]
         second_user_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': str(second_user._id)
         }).all()
-        assert_equal(len(second_user_email), 1)
+        assert len(second_user_email) == 1
         second_user_email = second_user_email[0]
         admin_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': str(admin._id)
         }).all()
-        assert_equal(len(admin_email), 1)
+        assert len(admin_email) == 1
         admin_email = admin_email[0]
 
         # Expected data
@@ -1835,13 +1835,13 @@ class TestFunctionalController(TrackerTestController):
 - **Milestone**: 1.0 --> 2.0
 '''
         email = '\n'.join([email_header, first_ticket_changes, ''])
-        assert_equal(email, first_user_email.kwargs.text)
+        assert email == first_user_email.kwargs.text
         email = '\n'.join([email_header, second_ticket_changes, ''])
-        assert_equal(email, second_user_email.kwargs.text)
-        assert_in(email_header, admin_email.kwargs.text)
-        assert_in(first_ticket_changes, admin_email.kwargs.text)
-        assert_in(second_ticket_changes, admin_email.kwargs.text)
-        assert_in(third_ticket_changes, admin_email.kwargs.text)
+        assert email == second_user_email.kwargs.text
+        assert email_header in admin_email.kwargs.text
+        assert first_ticket_changes in admin_email.kwargs.text
+        assert second_ticket_changes in admin_email.kwargs.text
+        assert third_ticket_changes in admin_email.kwargs.text
 
     def test_bulk_edit_notifications_monitoring_email(self):
         self.app.post('/admin/bugs/set_options', params={
@@ -1862,9 +1862,9 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
         emails = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).all()
         # one for admin and one for monitoring email
-        assert_equal(len(emails), 2)
+        assert len(emails) == 2
         for email in emails:
-            assert_equal(email.kwargs.subject, '[test:bugs] Mass edit changes by Test Admin')
+            assert email.kwargs.subject == '[test:bugs] Mass edit changes by Test Admin'
         admin = M.User.by_username('test-admin')
         admin_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
@@ -1874,11 +1874,11 @@ class TestFunctionalController(TrackerTestController):
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': 'monitoring@email.com'
         }).all()
-        assert_equal(len(admin_email), 1)
-        assert_equal(len(monitoring_email), 1)
+        assert len(admin_email) == 1
+        assert len(monitoring_email) == 1
         admin_email_text = admin_email[0].kwargs.text
         monitoring_email_text = monitoring_email[0].kwargs.text
-        assert_equal(admin_email_text, monitoring_email_text)
+        assert admin_email_text == monitoring_email_text
 
     def test_bulk_edit_notifications_monitoring_email_public_only(self):
         """Test that private tickets are not included in bulk edit
@@ -1902,9 +1902,9 @@ class TestFunctionalController(TrackerTestController):
         M.MonQTask.run_ready()
         emails = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).all()
         # one for admin and one for monitoring email
-        assert_equal(len(emails), 2)
+        assert len(emails) == 2
         for email in emails:
-            assert_equal(email.kwargs.subject, '[test:bugs] Mass edit changes by Test Admin')
+            assert email.kwargs.subject == '[test:bugs] Mass edit changes by Test Admin'
         admin = M.User.by_username('test-admin')
         admin_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
@@ -1914,12 +1914,12 @@ class TestFunctionalController(TrackerTestController):
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': 'monitoring@email.com'
         }).all()
-        assert_equal(len(admin_email), 1)
-        assert_equal(len(monitoring_email), 1)
+        assert len(admin_email) == 1
+        assert len(monitoring_email) == 1
         admin_email_text = admin_email[0].kwargs.text
         monitoring_email_text = monitoring_email[0].kwargs.text
-        assert_in('second ticket', admin_email_text)
-        assert_not_in('second ticket', monitoring_email_text)
+        assert 'second ticket' in admin_email_text
+        assert 'second ticket' not in monitoring_email_text
 
     def test_bulk_edit_monitoring_email_all_private_edits(self):
         """Test that no monitoring email is sent if the "public only"
@@ -1942,9 +1942,9 @@ class TestFunctionalController(TrackerTestController):
             'status': 'accepted'})
         M.MonQTask.run_ready()
         emails = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).all()
-        assert_equal(len(emails), 1)  # only admin email sent
+        assert len(emails) == 1  # only admin email sent
         for email in emails:
-            assert_equal(email.kwargs.subject, '[test:bugs] Mass edit changes by Test Admin')
+            assert email.kwargs.subject == '[test:bugs] Mass edit changes by Test Admin'
         admin = M.User.by_username('test-admin')
         admin_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
@@ -1954,8 +1954,8 @@ class TestFunctionalController(TrackerTestController):
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': 'monitoring@email.com'
         }).all()
-        assert_equal(len(admin_email), 1)
-        assert_equal(len(monitoring_email), 0)
+        assert len(admin_email) == 1
+        assert len(monitoring_email) == 0
 
     def test_filtered_by_subscription(self):
         self.new_ticket(summary='test first ticket', status='open')
@@ -1991,50 +1991,50 @@ class TestFunctionalController(TrackerTestController):
         }
         filtered_changes = c.app.globals.filtered_by_subscription(changes)
         filtered_users = [uid for uid, data in filtered_changes.items()]
-        assert_equal(sorted(filtered_users),
+        assert (sorted(filtered_users) ==
                      sorted(u._id for u in users[:-1] + [admin]))
         ticket_ids = [t._id for t in tickets]
-        assert_equal(filtered_changes[users[0]._id], set(ticket_ids[0:1]))
-        assert_equal(filtered_changes[users[1]._id], set(ticket_ids[:-1]))
-        assert_equal(filtered_changes[admin._id], set(ticket_ids[:-1]))
+        assert filtered_changes[users[0]._id] == set(ticket_ids[0:1])
+        assert filtered_changes[users[1]._id] == set(ticket_ids[:-1])
+        assert filtered_changes[admin._id] == set(ticket_ids[:-1])
 
     def test_vote(self):
         r = self.new_ticket(summary='test vote').follow()
-        assert_true(r.html.find('div', {'id': 'vote'}))
+        assert r.html.find('div', {'id': 'vote'})
 
         # test vote form not visible to anon user
         r = self.app.get('/bugs/1/', extra_environ=dict(username='*anonymous'))
-        assert_false(r.html.find('div', {'id': 'vote'}))
+        assert not r.html.find('div', {'id': 'vote'})
 
         r = self.app.get('/bugs/1/')
         votes_up = r.html.find('span', {'class': 'votes-up'})
         votes_down = r.html.find('span', {'class': 'votes-down'})
-        assert_in('0', str(votes_up))
-        assert_in('0', str(votes_down))
+        assert '0' in str(votes_up)
+        assert '0' in str(votes_down)
 
         # invalid vote
         r = self.app.post('/bugs/1/vote', dict(vote='invalid'))
         expected_resp = json.dumps(dict(status='error', votes_up=0, votes_down=0, votes_percent=0))
-        assert_equal(r.response.text, expected_resp)
+        assert r.response.text == expected_resp
 
         # vote up
         r = self.app.post('/bugs/1/vote', dict(vote='u'))
         expected_resp = json.dumps(dict(status='ok', votes_up=1, votes_down=0, votes_percent=100))
-        assert_equal(r.response.text, expected_resp)
+        assert r.response.text == expected_resp
 
         # vote down by another user
         r = self.app.post('/bugs/1/vote', dict(vote='d'),
                           extra_environ=dict(username='test-user-0'))
 
         expected_resp = json.dumps(dict(status='ok', votes_up=1, votes_down=1, votes_percent=50))
-        assert_equal(r.response.text, expected_resp)
+        assert r.response.text == expected_resp
 
         # make sure that on the page we see the same result
         r = self.app.get('/bugs/1/')
         votes_up = r.html.find('span', {'class': 'votes-up'})
         votes_down = r.html.find('span', {'class': 'votes-down'})
-        assert_in('1', str(votes_up))
-        assert_in('1', str(votes_down))
+        assert '1' in str(votes_up)
+        assert '1' in str(votes_down)
 
         r = self.app.get('/bugs/')
         assert "Votes" in r
@@ -2075,7 +2075,7 @@ class TestFunctionalController(TrackerTestController):
         ticket_url = r.headers['Location']
         r = self.app.get(ticket_url, extra_environ=dict(username='*anonymous'))
         a = r.html.find('a', {'class': 'icon edit_ticket'})
-        assert_equal(a.text, '\xa0Edit')
+        assert a.text == '\xa0Edit'
 
     def test_ticket_creator_cant_edit_private_ticket_without_update_perm(self):
         p = M.Project.query.get(shortname='test')
@@ -2184,18 +2184,18 @@ class TestFunctionalController(TrackerTestController):
         tracker = p.app_instance('bugs2')
         r = self.app.post('/p/test/bugs/1/move/',
                           params={'tracker': str(tracker.config._id)}).follow()
-        assert_equal(r.request.path, '/p/test2/bugs2/1/')
+        assert r.request.path == '/p/test2/bugs2/1/'
         summary = r.html.findAll('h2', {'class': 'dark title'})[0].find('span').contents[0].strip()
-        assert_equal(summary, '#1 test')
+        assert summary == '#1 test'
         ac_id = tracker.config._id
         ticket = tm.Ticket.query.find({
             'app_config_id': ac_id,
             'ticket_num': 1}).first()
         assert ticket is not None, "Can't find moved ticket"
-        assert_equal(ticket.discussion_thread.app_config_id, ac_id)
-        assert_equal(ticket.discussion_thread.discussion.app_config_id, ac_id)
+        assert ticket.discussion_thread.app_config_id == ac_id
+        assert ticket.discussion_thread.discussion.app_config_id == ac_id
         post = ticket.discussion_thread.last_post
-        assert_equal(post.text, 'Ticket moved from /p/test/bugs/1/')
+        assert post.text == 'Ticket moved from /p/test/bugs/1/'
 
     @td.with_tool('test2', 'Tickets', 'bugs2')
     def test_move_ticket_feed(self):
@@ -2211,7 +2211,7 @@ class TestFunctionalController(TrackerTestController):
         post = ticket.discussion_thread.last_post
         ticket_link = '/p/test2/bugs2/1/?limit=25#' + post.slug
         msg = 'Ticket moved from /p/test/bugs/1/'
-        assert_equal(post.text, msg)
+        assert post.text == msg
         # auto comment content and link to it should be in a ticket's feed
         r = self.app.get('/p/test2/bugs2/1/feed')
         assert msg in r, r
@@ -2236,9 +2236,9 @@ class TestFunctionalController(TrackerTestController):
         r = self.app.post(f['action'], params=params,
                           headers={'Referer': b'/p/test2/bugs2/1/'})
         r = self.app.get('/p/test2/bugs2/1/', dict(page='1'))
-        assert_true(post_content in r)
+        assert post_content in r
         comments_cnt = len(r.html.findAll(attrs={'class': 'discussion-post'}))
-        assert_equal(comments_cnt, 2)  # moved auto comment + new comment
+        assert comments_cnt == 2  # moved auto comment + new comment
         post = ticket.discussion_thread.last_post
         # content and link to the ticket should be in a tracker's feed
         ticket_link = '/p/test2/bugs2/1/?limit=25#' + post.slug
@@ -2284,11 +2284,11 @@ class TestFunctionalController(TrackerTestController):
         dummy_tracker = p.app_instance('dummy')
         r = self.app.post('/p/test/bugs/1/move',
                           params={'tracker': str(dummy_tracker.config._id)}).follow()
-        assert_equal(r.request.path, '/p/test/dummy/1/')
+        assert r.request.path == '/p/test/dummy/1/'
 
         # test that old url redirects to moved ticket
         self.app.get('/p/test/bugs/1/', status=301).follow()
-        assert_equal(r.request.path, '/p/test/dummy/1/')
+        assert r.request.path == '/p/test/dummy/1/'
 
     @td.with_tool('test', 'Tickets', 'dummy')
     def test_move_ticket_and_delete_tool(self):
@@ -2304,7 +2304,7 @@ class TestFunctionalController(TrackerTestController):
         dummy_tracker = p.app_instance('dummy')
         r = self.app.post('/p/test/bugs/1/move',
                           params={'tracker': str(dummy_tracker.config._id)}).follow()
-        assert_equal(r.request.path, '/p/test/dummy/1/')
+        assert r.request.path == '/p/test/dummy/1/'
 
         # delete 'dummy' tracker
         p.uninstall_app('dummy')
@@ -2329,7 +2329,7 @@ class TestFunctionalController(TrackerTestController):
         dummy_tracker = p.app_instance('dummy')
         r = self.app.post('/p/test/bugs/1/move',
                           params={'tracker': str(dummy_tracker.config._id)}).follow()
-        assert_equal(r.request.path, '/p/test/dummy/1/')
+        assert r.request.path == '/p/test/dummy/1/'
 
         # comment ticket 2
         M.Notification.query.remove()
@@ -2346,8 +2346,8 @@ class TestFunctionalController(TrackerTestController):
         # notification for ticket 2 should reference [test:bugs], not
         # [test:dummy]
         n = M.Notification.query.find().all()[0]
-        assert_in('[test:bugs]', n.subject)
-        assert_in('[test:bugs]', n.reply_to_address)
+        assert '[test:bugs]' in n.subject
+        assert '[test:bugs]' in n.reply_to_address
 
     @td.with_tool('test2', 'Tickets', 'features')
     def test_move_ticket_subscriptions(self):
@@ -2380,7 +2380,7 @@ class TestFunctionalController(TrackerTestController):
         # move ticket to new project & tool: test/bugs/2 => test2/features/1
         r = self.app.post('/p/test/bugs/2/move',
                           params={'tracker': str(features.config._id)}).follow()
-        assert_equal(r.request.path, '/p/test2/features/1/')
+        assert r.request.path == '/p/test2/features/1/'
 
         # test-user should be subscribed to it
         assert M.Mailbox.query.get(user_id=user._id,
@@ -2425,16 +2425,16 @@ class TestFunctionalController(TrackerTestController):
         attach_comments = r.html.findAll('div', attrs={'class': 'attachment_item'})
         ta = str(attach_tickets)  # ticket's attachments
         ca = str(attach_comments)  # comment's attachments
-        assert_in('<a href="/p/test2/bugs2/1/attachment/neo-icon-set-454545-256x350.png"', ta)
-        assert_in('<img alt="Thumbnail" src="/p/test2/bugs2/1/attachment/neo-icon-set-454545-256x350.png/thumb"', ta)
+        assert '<a href="/p/test2/bugs2/1/attachment/neo-icon-set-454545-256x350.png"' in ta
+        assert '<img alt="Thumbnail" src="/p/test2/bugs2/1/attachment/neo-icon-set-454545-256x350.png/thumb"' in ta
         p = M.Post.query.find().sort('timestamp', 1).first()
-        assert_in(
+        assert (
             '<a href="/p/test2/bugs2/_discuss/thread/%s/%s/attachment/test.txt"' %
-            (p.thread_id, p.slug), ca)
+            (p.thread_id, p.slug) in ca)
         for attach in M.BaseAttachment.query.find():
-            assert_equal(attach.app_config_id, bugs2.config._id)
+            assert attach.app_config_id == bugs2.config._id
             if attach.attachment_type == 'DiscussionAttachment':
-                assert_equal(attach.discussion_id, bugs2.config.discussion_id)
+                assert attach.discussion_id == bugs2.config.discussion_id
 
     @td.with_tool('test', 'Tickets', 'dummy')
     def test_move_ticket_comments(self):
@@ -2450,14 +2450,14 @@ class TestFunctionalController(TrackerTestController):
         form.fields[field_name][0].value = 'I am comment'
         form.submit()
         r = self.app.get('/p/test/bugs/1/')
-        assert_in('I am comment', r)
+        assert 'I am comment' in r
 
         p = M.Project.query.get(shortname='test')
         dummy_tracker = p.app_instance('dummy')
         r = self.app.post('/p/test/bugs/1/move',
                           params={'tracker': str(dummy_tracker.config._id)}).follow()
-        assert_equal(r.request.path, '/p/test/dummy/1/')
-        assert_in('I am comment', r)
+        assert r.request.path == '/p/test/dummy/1/'
+        assert 'I am comment' in r
 
     def test_tags(self):
         p = M.Project.query.get(shortname='test')
@@ -2468,9 +2468,9 @@ class TestFunctionalController(TrackerTestController):
         # Testing only empty 'term', because mim doesn't support aggregation
         # calls
         r = self.app.get('/p/test/bugs/tags')
-        assert_equal(json.loads(r.text), [])
+        assert json.loads(r.text) == []
         r = self.app.get('/p/test/bugs/tags?term=')
-        assert_equal(json.loads(r.text), [])
+        assert json.loads(r.text) == []
 
     def test_rest_tickets(self):
         ticket_view = self.new_ticket(summary='test').follow()
@@ -2493,12 +2493,12 @@ class TestFunctionalController(TrackerTestController):
         discussion_url = r.html.findAll('form')[-1]['action'][:-4]
         r = self.app.get('/rest/p/test/bugs/1/')
         r = json.loads(r.text)
-        assert_equal(r['ticket']['discussion_thread_url'],
+        assert (r['ticket']['discussion_thread_url'] ==
                      'http://localhost/rest%s' % discussion_url)
         slug = r['ticket']['discussion_thread']['posts'][0]['slug']
-        assert_equal(r['ticket']['discussion_thread']['posts'][0]['attachments'][0]['url'],
+        assert (r['ticket']['discussion_thread']['posts'][0]['attachments'][0]['url'] ==
                      f'http://localhost{discussion_url}{slug}/attachment/test.txt')
-        assert_equal(r['ticket']['discussion_thread']['posts'][0]['attachments'][0]['bytes'],
+        assert (r['ticket']['discussion_thread']['posts'][0]['attachments'][0]['bytes'] ==
                      11)
 
         file_name = 'test_root.py'
@@ -2509,7 +2509,7 @@ class TestFunctionalController(TrackerTestController):
         }, upload_files=[upload]).follow()
         r = self.app.get('/rest/p/test/bugs/1/')
         r = json.loads(r.text)
-        assert_equal(r['ticket']['attachments'][0]['url'],
+        assert (r['ticket']['attachments'][0]['url'] ==
                      'http://localhost/p/test/bugs/1/attachment/test_root.py')
 
     def test_html_escaping(self):
@@ -2521,7 +2521,7 @@ class TestFunctionalController(TrackerTestController):
             ThreadLocalORMSession.flush_all()
             email = M.MonQTask.query.find(
                 dict(task_name='allura.tasks.mail_tasks.sendmail')).first()
-            assert_equal(email.kwargs.subject,
+            assert (email.kwargs.subject ==
                          '[test:bugs] #1 test <h2> ticket')
             text = email.kwargs.text
             assert '** [bugs:#1] test &lt;h2&gt; ticket**' in text
@@ -2532,17 +2532,17 @@ class TestFunctionalController(TrackerTestController):
                 reply_to=g.noreply,
                 subject=email.kwargs.subject,
                 message_id=h.gen_message_id())
-            assert_equal(_client.sendmail.call_count, 1)
+            assert _client.sendmail.call_count == 1
             return_path, rcpts, body = _client.sendmail.call_args[0]
             body = body.split('\n')
             # check subject
             assert 'Subject: [test:bugs] #1 test <h2> ticket' in body
             # check html, need tags escaped
-            assert_in('<p><strong> <a class="alink" href="http://localhost/p/test/bugs/1/">[bugs:#1]</a>'
-                      ' test &lt;h2&gt; ticket</strong></p>',
+            assert ('<p><strong> <a class="alink" href="http://localhost/p/test/bugs/1/">[bugs:#1]</a>'
+                      ' test &lt;h2&gt; ticket</strong></p>' in
                       body)
             # check plaintext (ok to have "html" tags)
-            assert_in('** [bugs:#1] test <h2> ticket**', body)
+            assert '** [bugs:#1] test <h2> ticket**' in body
 
     @patch('forgetracker.search.query_filter_choices', autospec=True)
     def test_multiselect(self, query_filter_choices):
@@ -2558,16 +2558,16 @@ class TestFunctionalController(TrackerTestController):
         # Set rate limit to unlimit
         with h.push_config(config, **{'forgetracker.rate_limits': '{}'}):
             r = self.app.get('/bugs/new/')
-            assert_equal(r.status_int, 200)
+            assert r.status_int == 200
         # Set rate limit to 1 in first hour of project
         with h.push_config(config, **{'forgetracker.rate_limits': '{"3600": 1}'}):
             r = self.app.get('/bugs/new/')
-            assert_equal(r.status_int, 302)
-            assert_equal(r.location, 'http://localhost/bugs/')
+            assert r.status_int == 302
+            assert r.location == 'http://localhost/bugs/'
             wf = json.loads(self.webflash(r))
-            assert_equal(wf['status'], 'error')
-            assert_equal(
-                wf['message'],
+            assert wf['status'] == 'error'
+            assert (
+                wf['message'] ==
                 'Ticket creation rate limit exceeded. Please try again later.')
 
     def test_rate_limit_save_ticket(self):
@@ -2576,24 +2576,24 @@ class TestFunctionalController(TrackerTestController):
             summary = 'Ticket w/o limit'
             post_data = {'ticket_form.summary': summary}
             r = self.app.post('/bugs/save_ticket', post_data).follow()
-            assert_in(summary, r)
+            assert summary in r
             t = tm.Ticket.query.get(summary=summary)
-            assert_not_equal(t, None)
+            assert t != None
         # Set rate limit to 1 in first hour of project
         with h.push_config(config, **{'forgetracker.rate_limits': '{"3600": 1}'}):
             summary = 'Ticket with limit'
             post_data = {'ticket_form.summary': summary}
             r = self.app.post('/bugs/save_ticket', post_data)
-            assert_equal(r.status_int, 302)
-            assert_equal(r.location, 'http://localhost/bugs/')
+            assert r.status_int == 302
+            assert r.location == 'http://localhost/bugs/'
             wf = json.loads(self.webflash(r))
-            assert_equal(wf['status'], 'error')
-            assert_equal(
-                wf['message'],
+            assert wf['status'] == 'error'
+            assert (
+                wf['message'] ==
                 'Ticket creation rate limit exceeded. Please try again later.')
-            assert_not_in(summary, r.follow())
+            assert summary not in r.follow()
             t = tm.Ticket.query.get(summary=summary)
-            assert_equal(t, None)
+            assert t == None
 
     def test_user_missing(self):
         # add test-user to project so it can be assigned the ticket
@@ -2904,7 +2904,7 @@ class TestCustomUserField(TrackerTestController):
         kw = {'custom_fields._code_review': ''}
         ticket_view = self.new_ticket(summary='test custom fields', **kw).follow()
         # summary header shows 'nobody'
-        assert_equal(squish_spaces(ticket_view.html.findAll('label', 'simple', text='Code Review:')[0].parent.text),
+        assert (squish_spaces(ticket_view.html.findAll('label', 'simple', text='Code Review:')[0].parent.text) ==
                      ' Code Review: nobody ')
         # form input is blank
         select = ticket_view.html.find('select',
@@ -2919,7 +2919,7 @@ class TestCustomUserField(TrackerTestController):
         kw = {'custom_fields._code_review': 'test-admin'}
         ticket_view = self.new_ticket(summary='test custom fields', **kw).follow()
         # summary header shows 'Test Admin'
-        assert_equal(squish_spaces(ticket_view.html.findAll('label', 'simple', text='Code Review:')[0].parent.text),
+        assert (squish_spaces(ticket_view.html.findAll('label', 'simple', text='Code Review:')[0].parent.text) ==
                      ' Code Review: Test Admin ')
         # form input is blank
         select = ticket_view.html.find('select',
@@ -2928,7 +2928,7 @@ class TestCustomUserField(TrackerTestController):
         for option in select.findChildren():
             if option.has_attr('selected'):
                 selected = option
-        assert_equal(selected['value'], 'test-admin')
+        assert selected['value'] == 'test-admin'
 
     def test_change_user_field(self):
         kw = {'custom_fields._code_review': ''}
@@ -2942,8 +2942,8 @@ class TestCustomUserField(TrackerTestController):
         kw = {'custom_fields._code_review': 'test-admin'}
         self.new_ticket(summary='test custom fields', **kw)
         r = self.app.get('/bugs/')
-        assert_equal(r.html.find('table', 'ticket-list').findAll('th')[7].text.strip()[:11], 'Code Review')
-        assert_equal(r.html.find('table', 'ticket-list').tbody.tr.findAll('td')[7].text, 'Test Admin')
+        assert r.html.find('table', 'ticket-list').findAll('th')[7].text.strip()[:11] == 'Code Review'
+        assert r.html.find('table', 'ticket-list').tbody.tr.findAll('td')[7].text == 'Test Admin'
 
 
 class TestHelpTextOptions(TrackerTestController):
@@ -3041,9 +3041,9 @@ class TestBulkMove(TrackerTestController):
         r = self.app.get('/bugs/move/?q=The')
         tickets_table = r.html.find('tbody', attrs={'class': 'ticket-list'})
         tickets = tickets_table.findAll('tr')
-        assert_equal(len(tickets), 2)
-        assert_in('The Empire Strikes Back', tickets_table.text)
-        assert_in('Return Of The Jedi', tickets_table.text)
+        assert len(tickets) == 2
+        assert 'The Empire Strikes Back' in tickets_table.text
+        assert 'Return Of The Jedi' in tickets_table.text
 
     @td.with_tool('test', 'Tickets', 'bugs2')
     @td.with_tool('test2', 'Tickets', 'bugs')
@@ -3053,7 +3053,7 @@ class TestBulkMove(TrackerTestController):
         trackers = r.html.find('select', {'name': 'tracker'}).findAll('option')
         trackers = {t.text for t in trackers}
         expected = {'test/bugs', 'test/bugs2', 'test2/bugs', 'test2/bugs2'}
-        assert_equal(trackers, expected)
+        assert trackers == expected
         move_btn = r.html.find('input', attrs={'type': 'submit', 'value': 'Move'})
         assert move_btn is not None
 
@@ -3078,16 +3078,16 @@ class TestBulkMove(TrackerTestController):
         original_ac_id = original_tracker.config._id
         moved_tickets = tm.Ticket.query.find({'app_config_id': ac_id}).all()
         original_tickets = tm.Ticket.query.find({'app_config_id': original_ac_id}).all()
-        assert_equal(len(moved_tickets), 2)
-        assert_equal(len(original_tickets), 1)
+        assert len(moved_tickets) == 2
+        assert len(original_tickets) == 1
         for ticket in moved_tickets:
-            assert_equal(ticket.discussion_thread.app_config_id, ac_id)
-            assert_equal(ticket.discussion_thread.discussion.app_config_id, ac_id)
+            assert ticket.discussion_thread.app_config_id == ac_id
+            assert ticket.discussion_thread.discussion.app_config_id == ac_id
             post = ticket.discussion_thread.last_post
-            assert_in('Ticket moved from /p/test/bugs/', post.text)
+            assert 'Ticket moved from /p/test/bugs/' in post.text
         for t in original_tickets:
-            assert_equal(t.discussion_thread.app_config_id, original_ac_id)
-            assert_equal(t.discussion_thread.discussion.app_config_id, original_ac_id)
+            assert t.discussion_thread.app_config_id == original_ac_id
+            assert t.discussion_thread.discussion.app_config_id == original_ac_id
             assert t.discussion_thread.last_post is None
 
     @td.with_tool('test2', 'Tickets', 'bugs2')
@@ -3112,46 +3112,46 @@ class TestBulkMove(TrackerTestController):
         })
         M.MonQTask.run_ready()
         emails = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).all()
-        assert_equal(len(emails), 3)
+        assert len(emails) == 3
         for email in emails:
-            assert_equal(email.kwargs.subject,
+            assert (email.kwargs.subject ==
                          '[test:bugs] Mass ticket moving by Test Admin')
         first_user_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': str(first_user._id)
         }).all()
-        assert_equal(len(first_user_email), 1)
+        assert len(first_user_email) == 1
         first_user_email = first_user_email[0]
         second_user_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': str(second_user._id)
         }).all()
-        assert_equal(len(second_user_email), 1)
+        assert len(second_user_email) == 1
         second_user_email = second_user_email[0]
         admin_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': str(admin._id)
         }).all()
-        assert_equal(len(admin_email), 1)
+        assert len(admin_email) == 1
         admin_email = admin_email[0]
 
         email_header = 'Tickets were moved from [test:bugs] to [test2:bugs2]\n'
         first_ticket_changes = 'A New Hope'
         second_ticket_changes = 'The Empire Strikes Back'
         third_ticket_changes = 'Return Of The Jedi'
-        assert_in(email_header, first_user_email.kwargs.text)
-        assert_in(first_ticket_changes, first_user_email.kwargs.text)
-        assert_in(email_header, second_user_email.kwargs.text)
-        assert_in(second_ticket_changes, second_user_email.kwargs.text)
-        assert_in(email_header, admin_email.kwargs.text)
-        assert_in(first_ticket_changes, admin_email.kwargs.text)
-        assert_in(second_ticket_changes, admin_email.kwargs.text)
-        assert_in(third_ticket_changes, admin_email.kwargs.text)
+        assert email_header in first_user_email.kwargs.text
+        assert first_ticket_changes in first_user_email.kwargs.text
+        assert email_header in second_user_email.kwargs.text
+        assert second_ticket_changes in second_user_email.kwargs.text
+        assert email_header in admin_email.kwargs.text
+        assert first_ticket_changes in admin_email.kwargs.text
+        assert second_ticket_changes in admin_email.kwargs.text
+        assert third_ticket_changes in admin_email.kwargs.text
         # After tickets moved, user should see a flash
         mbox = M.Mailbox.query.get(user_id=admin._id, is_flash=True)
         notification_id = mbox.queue[-1]
         notification = M.Notification.query.get(_id=notification_id)
-        assert_equal(notification.text,
+        assert (notification.text ==
                      'Tickets moved from test/bugs to test2/bugs2')
 
     @td.with_tool('test2', 'Tickets', 'bugs2')
@@ -3175,9 +3175,9 @@ class TestBulkMove(TrackerTestController):
         })
         M.MonQTask.run_ready()
         emails = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).all()
-        assert_equal(len(emails), 2)
+        assert len(emails) == 2
         for email in emails:
-            assert_equal(email.kwargs.subject,
+            assert (email.kwargs.subject ==
                          '[test:bugs] Mass ticket moving by Test Admin')
         admin_email = M.MonQTask.query.find({
             'task_name': 'allura.tasks.mail_tasks.sendmail',
@@ -3187,21 +3187,21 @@ class TestBulkMove(TrackerTestController):
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': 'monitoring@email.com'
         }).all()
-        assert_equal(len(admin_email), 1)
-        assert_equal(len(monitoring_email), 1)
+        assert len(admin_email) == 1
+        assert len(monitoring_email) == 1
         admin_email_text = admin_email[0].kwargs.text
-        assert_in('test:bugs:#1 --> test2:bugs2:#1 A New Hope',
+        assert ('test:bugs:#1 --> test2:bugs2:#1 A New Hope' in
                   admin_email_text)
-        assert_in('test:bugs:#2 --> test2:bugs2:#2 The Empire Strikes Back',
+        assert ('test:bugs:#2 --> test2:bugs2:#2 The Empire Strikes Back' in
                   admin_email_text)
-        assert_in('test:bugs:#3 --> test2:bugs2:#3 Return Of The Jedi',
+        assert ('test:bugs:#3 --> test2:bugs2:#3 Return Of The Jedi' in
                   admin_email_text)
         monitoring_email_text = monitoring_email[0].kwargs.text
-        assert_in('test:bugs:#1 --> test2:bugs2:#1 A New Hope',
+        assert ('test:bugs:#1 --> test2:bugs2:#1 A New Hope' in
                   monitoring_email_text)
-        assert_in('test:bugs:#2 --> test2:bugs2:#2 The Empire Strikes Back',
+        assert ('test:bugs:#2 --> test2:bugs2:#2 The Empire Strikes Back' in
                   monitoring_email_text)
-        assert_in('test:bugs:#3 --> test2:bugs2:#3 Return Of The Jedi',
+        assert ('test:bugs:#3 --> test2:bugs2:#3 Return Of The Jedi' in
                   monitoring_email_text)
 
     @td.with_tool('test2', 'Tickets', 'bugs2')
@@ -3232,9 +3232,9 @@ class TestBulkMove(TrackerTestController):
         M.MonQTask.run_ready()
         emails = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).all()
         # one for admin and one for monitoring email
-        assert_equal(len(emails), 2)
+        assert len(emails) == 2
         for email in emails:
-            assert_equal(email.kwargs.subject,
+            assert (email.kwargs.subject ==
                          '[test:bugs] Mass ticket moving by Test Admin')
         admin = M.User.by_username('test-admin')
         admin_email = M.MonQTask.query.find({
@@ -3245,12 +3245,12 @@ class TestBulkMove(TrackerTestController):
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': 'monitoring@email.com'
         }).all()
-        assert_equal(len(admin_email), 1)
-        assert_equal(len(monitoring_email), 1)
+        assert len(admin_email) == 1
+        assert len(monitoring_email) == 1
         admin_email_text = admin_email[0].kwargs.text
         monitoring_email_text = monitoring_email[0].kwargs.text
-        assert_in('second ticket', admin_email_text)
-        assert_not_in('second ticket', monitoring_email_text)
+        assert 'second ticket' in admin_email_text
+        assert 'second ticket' not in monitoring_email_text
 
     @td.with_tool('test2', 'Tickets', 'bugs2')
     def test_monitoring_email_all_private_moved(self):
@@ -3279,9 +3279,9 @@ class TestBulkMove(TrackerTestController):
         })
         M.MonQTask.run_ready()
         emails = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).all()
-        assert_equal(len(emails), 1)  # only admin email sent
+        assert len(emails) == 1  # only admin email sent
         for email in emails:
-            assert_equal(email.kwargs.subject,
+            assert (email.kwargs.subject ==
                          '[test:bugs] Mass ticket moving by Test Admin')
         admin = M.User.by_username('test-admin')
         admin_email = M.MonQTask.query.find({
@@ -3292,8 +3292,8 @@ class TestBulkMove(TrackerTestController):
             'task_name': 'allura.tasks.mail_tasks.sendmail',
             'kwargs.destinations': 'monitoring@email.com'
         }).all()
-        assert_equal(len(admin_email), 1)
-        assert_equal(len(monitoring_email), 0)
+        assert len(admin_email) == 1
+        assert len(monitoring_email) == 0
 
 
 def sidebar_contains(response, text):
@@ -3304,7 +3304,7 @@ def sidebar_contains(response, text):
 class TestStats(TrackerTestController):
     def test_stats(self):
         r = self.app.get('/bugs/stats/', status=200)
-        assert_in('# tickets: 0', r.text)
+        assert '# tickets: 0' in r.text
 
 
 class TestNotificationEmailGrouping(TrackerTestController):
@@ -3315,9 +3315,9 @@ class TestNotificationEmailGrouping(TrackerTestController):
         ThreadLocalORMSession.flush_all()
         email = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).first()
         ticket = tm.Ticket.query.get(ticket_num=1)
-        assert_equal(email.kwargs.message_id, ticket.message_id())
-        assert_equal(email.kwargs.in_reply_to, None)
-        assert_equal(email.kwargs.references, [])
+        assert email.kwargs.message_id == ticket.message_id()
+        assert email.kwargs.in_reply_to == None
+        assert email.kwargs.references == []
 
     def test_comments(self):
         ticket_view = self.new_ticket(summary='Test Ticket').follow()
@@ -3336,9 +3336,9 @@ class TestNotificationEmailGrouping(TrackerTestController):
         ticket = tm.Ticket.query.get(ticket_num=1)
         top_level_comment = ticket.discussion_thread.posts[0]
         top_level_comment_msg_id = ticket.url() + top_level_comment._id
-        assert_equal(email.kwargs.message_id, top_level_comment_msg_id)
-        assert_equal(email.kwargs.in_reply_to, ticket.message_id())
-        assert_equal(email.kwargs.references, [ticket.message_id()])
+        assert email.kwargs.message_id == top_level_comment_msg_id
+        assert email.kwargs.in_reply_to == ticket.message_id()
+        assert email.kwargs.references == [ticket.message_id()]
 
         ThreadLocalORMSession.flush_all()
         M.MonQTask.query.remove()
@@ -3356,9 +3356,9 @@ class TestNotificationEmailGrouping(TrackerTestController):
         email = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendmail')).first()
         ticket = tm.Ticket.query.get(ticket_num=1)
         reply = [post for post in ticket.discussion_thread.posts if post.text == reply_text][0]
-        assert_equal(email.kwargs.message_id, ticket.url() + reply._id)
-        assert_equal(email.kwargs.in_reply_to, top_level_comment_msg_id)
-        assert_equal(email.kwargs.references,
+        assert email.kwargs.message_id == ticket.url() + reply._id
+        assert email.kwargs.in_reply_to == top_level_comment_msg_id
+        assert (email.kwargs.references ==
                      [ticket.message_id(), top_level_comment_msg_id])
 
 
@@ -3370,10 +3370,10 @@ def test_status_passthru():
                           open_status_names='foo bar', closed_status_names='qux baz')
     ThreadLocalORMSession.flush_all()
     app = c.project.app_instance('tsp')
-    assert_equal(app.globals.set_of_open_status_names, {'foo', 'bar'})
-    assert_equal(app.globals.set_of_closed_status_names, {'qux', 'baz'})
-    assert_not_in('open_status_names', app.config.options)
-    assert_not_in('closed_status_names', app.config.options)
+    assert app.globals.set_of_open_status_names == {'foo', 'bar'}
+    assert app.globals.set_of_closed_status_names == {'qux', 'baz'}
+    assert 'open_status_names' not in app.config.options
+    assert 'closed_status_names' not in app.config.options
 
 
 class TestArtifactLinks(TrackerTestController):
@@ -3393,15 +3393,15 @@ class TestArtifactLinks(TrackerTestController):
         self.new_ticket('/features/', summary='Ticket 1 in features', _milestone='1.0').follow()
         ticket_bugs = tm.Ticket.query.get(summary='Ticket 1 in bugs')
         ticket_features = tm.Ticket.query.get(summary='Ticket 1 in features')
-        assert_equal(ticket_bugs.ticket_num, 1)
-        assert_equal(ticket_bugs.app.config._id, bugs.config._id)
-        assert_equal(ticket_features.ticket_num, 1)
-        assert_equal(ticket_features.app.config._id, features.config._id)
+        assert ticket_bugs.ticket_num == 1
+        assert ticket_bugs.app.config._id == bugs.config._id
+        assert ticket_features.ticket_num == 1
+        assert ticket_features.app.config._id == features.config._id
 
         c.app = bugs
         link = '<div class="markdown_content"><p><a class="alink" href="/p/test/bugs/1/">[#1]</a></p></div>'
-        assert_equal(g.markdown.convert('[#1]'), link)
+        assert g.markdown.convert('[#1]') == link
 
         c.app = features
         link = '<div class="markdown_content"><p><a class="alink" href="/p/test/features/1/">[#1]</a></p></div>'
-        assert_equal(g.markdown.convert('[#1]'), link)
+        assert g.markdown.convert('[#1]') == link
diff --git a/ForgeTracker/forgetracker/tests/test_app.py b/ForgeTracker/forgetracker/tests/test_app.py
index b67bdb969..aed0fb60b 100644
--- a/ForgeTracker/forgetracker/tests/test_app.py
+++ b/ForgeTracker/forgetracker/tests/test_app.py
@@ -33,7 +33,7 @@ from allura.tests import decorators as td
 from forgetracker import model as TM
 from forgetracker.site_stats import tickets_stats_24hr
 from forgetracker.tests.functional.test_root import TrackerTestController
-from allura.tests.pytest_helpers import with_nose_compatibility
+from alluratest.pytest_helpers import with_nose_compatibility
 
 
 class TestApp:
@@ -54,7 +54,7 @@ class TestApp:
         c.app.handle_message('1', msg)
         # message gets added as a post on the ticket
         post = M.Post.query.get(_id=message_id)
-        assert_equal(post["text"], message)
+        assert post["text"] == message
 
     @td.with_tracker
     def test_inbound_email_no_match(self):
@@ -66,7 +66,7 @@ class TestApp:
         c.app.handle_message('6789', msg)
         # no new message
         post = M.Post.query.get(_id=message_id)
-        assert_equal(post, None)
+        assert post == None
 
     @td.with_tracker
     def test_uninstall(self):
@@ -83,22 +83,22 @@ class TestApp:
         # invoked normally via entry point
         TM.Ticket.new()
         TM.Ticket.new()
-        assert_equal(2, tickets_stats_24hr())
+        assert 2 == tickets_stats_24hr()
 
     @td.with_tracker
     def test_sitemap_xml(self):
-        assert_equal([], c.app.sitemap_xml())
+        assert [] == c.app.sitemap_xml()
         TM.Ticket.new()
-        assert_equal(1, len(c.app.sitemap_xml()))
+        assert 1 == len(c.app.sitemap_xml())
 
     @td.with_tracker
     def test_sitemap_xml_ignored(self):
         TM.Ticket.new(form_fields=dict(deleted=True))
-        assert_equal([], c.app.sitemap_xml())
+        assert [] == c.app.sitemap_xml()
         # still add to sitemap even if only tickets are closed
         TM.Ticket.new(form_fields=dict(
             status=c.app.globals.closed_status_names[0]))
-        assert_equal(1, len(c.app.sitemap_xml()))
+        assert 1 == len(c.app.sitemap_xml())
 
 
 class TestBulkExport(TrackerTestController):
@@ -132,26 +132,26 @@ class TestBulkExport(TrackerTestController):
 
         tickets = sorted(tracker['tickets'],
                          key=operator.itemgetter('summary'))
-        assert_equal(len(tickets), 2)
+        assert len(tickets) == 2
         ticket_foo = tickets[1]
-        assert_equal(ticket_foo['summary'], 'foo')
-        assert_equal(ticket_foo['custom_fields']['_milestone'], '1.0')
+        assert ticket_foo['summary'] == 'foo'
+        assert ticket_foo['custom_fields']['_milestone'] == '1.0'
         posts_foo = ticket_foo['discussion_thread']['posts']
-        assert_equal(len(posts_foo), 1)
-        assert_equal(posts_foo[0]['text'], 'silly comment')
+        assert len(posts_foo) == 1
+        assert posts_foo[0]['text'] == 'silly comment'
 
         tracker_config = tracker['tracker_config']
-        assert_true('options' in list(tracker_config.keys()))
-        assert_equal(tracker_config['options']['mount_point'], 'bugs')
+        assert 'options' in list(tracker_config.keys())
+        assert tracker_config['options']['mount_point'] == 'bugs'
 
         milestones = sorted(tracker['milestones'],
                             key=operator.itemgetter('name'))
-        assert_equal(milestones[0]['name'], '1.0')
-        assert_equal(milestones[1]['name'], '2.0')
+        assert milestones[0]['name'] == '1.0'
+        assert milestones[1]['name'] == '2.0'
 
         saved_bins_summaries = [bin['summary']
                                 for bin in tracker['saved_bins']]
-        assert_true('Closed Tickets' in saved_bins_summaries)
+        assert 'Closed Tickets' in saved_bins_summaries
 
     def test_export_with_attachments(self):
 
@@ -169,5 +169,5 @@ class TestBulkExport(TrackerTestController):
             self.post.slug,
             'test_file'
         )
-        assert_equal(tickets[1]['discussion_thread']['posts'][0]['attachments'][0]['path'], file_path)
+        assert tickets[1]['discussion_thread']['posts'][0]['attachments'][0]['path'] == file_path
         os.path.exists(file_path)
diff --git a/ForgeTracker/forgetracker/tests/unit/test_globals_model.py b/ForgeTracker/forgetracker/tests/unit/test_globals_model.py
index 439e8a5ac..6c063c8f8 100644
--- a/ForgeTracker/forgetracker/tests/unit/test_globals_model.py
+++ b/ForgeTracker/forgetracker/tests/unit/test_globals_model.py
@@ -43,14 +43,14 @@ class TestGlobalsModel(TrackerTestWithModel):
 
     def test_next_ticket_number_increments(self):
         gl = Globals()
-        assert_equal(gl.next_ticket_num(), 1)
-        assert_equal(gl.next_ticket_num(), 2)
+        assert gl.next_ticket_num() == 1
+        assert gl.next_ticket_num() == 2
 
     def test_ticket_numbers_are_independent(self):
         with h.push_context('test', 'doc-bugs', neighborhood='Projects'):
-            assert_equal(c.app.globals.next_ticket_num(), 1)
+            assert c.app.globals.next_ticket_num() == 1
         with h.push_context('test', 'bugs', neighborhood='Projects'):
-            assert_equal(c.app.globals.next_ticket_num(), 1)
+            assert c.app.globals.next_ticket_num() == 1
 
     @mock.patch('forgetracker.model.ticket.datetime')
     def test_bin_count(self, mock_dt):
@@ -65,14 +65,14 @@ class TestGlobalsModel(TrackerTestWithModel):
         gbl.invalidate_bin_counts.reset_mock()
         gbl._bin_counts_expire = now + timedelta(minutes=5)
         bin = gbl.bin_count('bar')
-        assert_equal(bin['hits'], 2)
+        assert bin['hits'] == 2
         assert not gbl.invalidate_bin_counts.called
 
         # expired, returns value for missing bin
         gbl.invalidate_bin_counts.reset_mock()
         gbl._bin_counts_expire = now - timedelta(minutes=5)
         bin = gbl.bin_count('qux')
-        assert_equal(bin['hits'], 0)
+        assert bin['hits'] == 0
         assert gbl.invalidate_bin_counts.called
 
         # config set to no expiration
@@ -86,7 +86,7 @@ class TestGlobalsModel(TrackerTestWithModel):
         gbl.invalidate_bin_counts.reset_mock()
         gbl._bin_counts_expire = None
         bin = gbl.bin_count('qux')
-        assert_equal(bin['hits'], 0)
+        assert bin['hits'] == 0
         assert gbl.invalidate_bin_counts.called
 
     @mock.patch('forgetracker.tasks.update_bin_counts')
@@ -105,14 +105,14 @@ class TestGlobalsModel(TrackerTestWithModel):
         gbl._bin_counts_invalidated = now - timedelta(minutes=6)
         gbl.invalidate_bin_counts()
         assert mock_task.post.called
-        assert_equal(gbl._bin_counts_invalidated, now)
+        assert gbl._bin_counts_invalidated == now
 
         # never invalidated
         mock_task.reset_mock()
         gbl._bin_counts_invalidated = None
         gbl.invalidate_bin_counts()
         assert mock_task.post.called
-        assert_equal(gbl._bin_counts_invalidated, now)
+        assert gbl._bin_counts_invalidated == now
 
     @mock.patch('forgetracker.model.ticket.Bin')
     @mock.patch('forgetracker.model.ticket.search_artifact')
@@ -126,24 +126,24 @@ class TestGlobalsModel(TrackerTestWithModel):
             mock.Mock(summary='foo', terms='bar')]
         mock_search().hits = 5
 
-        assert_equal(gbl._bin_counts_data, [])  # sanity pre-check
+        assert gbl._bin_counts_data == []  # sanity pre-check
         gbl.update_bin_counts()
         assert mock_bin.query.find.called
         mock_search.assert_called_with(
             forgetracker.model.Ticket, 'bar', rows=0, short_timeout=False, fq=['-deleted_b:true'])
-        assert_equal(gbl._bin_counts_data, [{'summary': 'foo', 'hits': 5}])
-        assert_equal(gbl._bin_counts_expire, now + timedelta(minutes=60))
-        assert_equal(gbl._bin_counts_invalidated, None)
+        assert gbl._bin_counts_data == [{'summary': 'foo', 'hits': 5}]
+        assert gbl._bin_counts_expire == now + timedelta(minutes=60)
+        assert gbl._bin_counts_invalidated == None
 
     def test_append_new_labels(self):
         gbl = Globals()
-        assert_equal(gbl.append_new_labels([], ['tag1']), ['tag1'])
-        assert_equal(
-            gbl.append_new_labels(['tag1', 'tag2'], ['tag2']), ['tag1', 'tag2'])
-        assert_equal(gbl.append_new_labels(
-            ['tag1', 'tag2'], ['tag3']), ['tag1', 'tag2', 'tag3'])
-        assert_equal(gbl.append_new_labels(
-            ['tag1', 'tag2', 'tag3'], ['tag2']), ['tag1', 'tag2', 'tag3'])
+        assert gbl.append_new_labels([], ['tag1']) == ['tag1']
+        assert (
+            gbl.append_new_labels(['tag1', 'tag2'], ['tag2']) == ['tag1', 'tag2'])
+        assert gbl.append_new_labels(
+            ['tag1', 'tag2'], ['tag3']) == ['tag1', 'tag2', 'tag3']
+        assert gbl.append_new_labels(
+            ['tag1', 'tag2', 'tag3'], ['tag2']) == ['tag1', 'tag2', 'tag3']
 
 
 class TestCustomFields(TrackerTestWithModel):
diff --git a/ForgeTracker/forgetracker/tests/unit/test_milestone_controller.py b/ForgeTracker/forgetracker/tests/unit/test_milestone_controller.py
index f22f13eee..3bc0edd50 100644
--- a/ForgeTracker/forgetracker/tests/unit/test_milestone_controller.py
+++ b/ForgeTracker/forgetracker/tests/unit/test_milestone_controller.py
@@ -41,4 +41,4 @@ def test_unicode_lookup():
         mc = MilestoneController(root, field, milestone_urlparam)
 
     assert mc.milestone  # check that it is found
-    assert_equal(mc.milestone.name, 'Перспектива')
+    assert mc.milestone.name == 'Перспектива'
diff --git a/ForgeTracker/forgetracker/tests/unit/test_root_controller.py b/ForgeTracker/forgetracker/tests/unit/test_root_controller.py
index ac65449a1..8051cde32 100644
--- a/ForgeTracker/forgetracker/tests/unit/test_root_controller.py
+++ b/ForgeTracker/forgetracker/tests/unit/test_root_controller.py
@@ -49,7 +49,7 @@ class TestWhenSearchingWithCustomFields(WithUserAndBugsApp):
         expected = [dict(sortable_name='_iteration_number_s',
                          name='_iteration_number',
                          label='Iteration Number')]
-        assert_equal(self.response['sortable_custom_fields'], expected)
+        assert self.response['sortable_custom_fields'] == expected
 
     def test_that_tickets_are_listed(self):
         assert self.response['tickets'][0].summary == 'colors are wrong'
diff --git a/ForgeTracker/forgetracker/tests/unit/test_search.py b/ForgeTracker/forgetracker/tests/unit/test_search.py
index 9f34a03ad..c9bb4bdbf 100644
--- a/ForgeTracker/forgetracker/tests/unit/test_search.py
+++ b/ForgeTracker/forgetracker/tests/unit/test_search.py
@@ -35,7 +35,7 @@ def hit_mock():
 
 def test_get_facets():
     hit,expected = hit_mock()
-    assert_equal(get_facets(hit), expected)
+    assert get_facets(hit) == expected
 
 
 @mock.patch('forgetracker.search.search')
@@ -56,4 +56,4 @@ def test_query_filter_choices(c, search):
               'facet.sort': 'index',
               'facet.mincount': 1}
     search.assert_called_once_with(None, **params)
-    assert_equal(result, expected)
+    assert result == expected
diff --git a/ForgeTracker/forgetracker/tests/unit/test_ticket_model.py b/ForgeTracker/forgetracker/tests/unit/test_ticket_model.py
index c958094db..02744756b 100644
--- a/ForgeTracker/forgetracker/tests/unit/test_ticket_model.py
+++ b/ForgeTracker/forgetracker/tests/unit/test_ticket_model.py
@@ -91,27 +91,27 @@ class TestTicketModel(TrackerTestWithModel):
 
     def test_activity_extras(self):
         t = Ticket(summary='my ticket', ticket_num=12)
-        assert_in('allura_id', t.activity_extras)
-        assert_equal(t.activity_extras['summary'], t.summary)
+        assert 'allura_id' in t.activity_extras
+        assert t.activity_extras['summary'] == t.summary
 
     def test_has_activity_access(self):
         t = Ticket(summary='ticket', ticket_num=666)
-        assert_true(t.has_activity_access('read', c.user, 'activity'))
+        assert t.has_activity_access('read', c.user, 'activity')
         t.deleted = True
-        assert_false(t.has_activity_access('read', c.user, 'activity'))
+        assert not t.has_activity_access('read', c.user, 'activity')
 
     def test_comment_has_activity_access(self):
         t = Ticket(summary='ticket', ticket_num=666, deleted=True)
         p = t.discussion_thread.add_post(text='test post')
-        assert_equal(p.status, 'ok')
-        assert_true(p.has_activity_access('read', c.user, 'activity'))
+        assert p.status == 'ok'
+        assert p.has_activity_access('read', c.user, 'activity')
         p.status = 'spam'
-        assert_false(p.has_activity_access('read', c.user, 'activity'))
+        assert not p.has_activity_access('read', c.user, 'activity')
         p.status = 'pending'
-        assert_false(p.has_activity_access('read', c.user, 'activity'))
+        assert not p.has_activity_access('read', c.user, 'activity')
         p.status = 'ok'
         p.deleted = True
-        assert_false(p.has_activity_access('read', c.user, 'activity'))
+        assert not p.has_activity_access('read', c.user, 'activity')
 
     def test_private_ticket(self):
         from allura.model import ProjectRole
@@ -138,7 +138,7 @@ class TestTicketModel(TrackerTestWithModel):
         cred = Credentials.get().clear()
 
         t.private = True
-        assert_equal(t.acl, [
+        assert t.acl == [
             ACE.allow(role_developer, 'create'),
             ACE.allow(role_developer, 'delete'),
             ACE.allow(role_developer, 'moderate'),
@@ -151,7 +151,7 @@ class TestTicketModel(TrackerTestWithModel):
             ACE.allow(role_creator, 'post'),
             ACE.allow(role_creator, 'read'),
             ACE.allow(role_creator, 'unmoderated_post'),
-            DENY_ALL])
+            DENY_ALL]
         assert has_access(t, 'read', user=admin)()
         assert has_access(t, 'create', user=admin)()
         assert has_access(t, 'update', user=admin)()
@@ -192,15 +192,15 @@ class TestTicketModel(TrackerTestWithModel):
             summary='test ticket',
             description='test description',
             created_date=datetime(2012, 10, 29, 9, 57, 21, 465000))
-        assert_equal(t.created_date, datetime(2012, 10, 29, 9, 57, 21, 465000))
+        assert t.created_date == datetime(2012, 10, 29, 9, 57, 21, 465000)
         f = Feed.post(
             t,
             title=t.summary,
             description=t.description,
             pubdate=t.created_date)
-        assert_equal(f.pubdate, datetime(2012, 10, 29, 9, 57, 21, 465000))
-        assert_equal(f.title, 'test ticket')
-        assert_equal(f.description,
+        assert f.pubdate == datetime(2012, 10, 29, 9, 57, 21, 465000)
+        assert f.title == 'test ticket'
+        assert (f.description ==
                      '<div class="markdown_content"><p>test description</p></div>')
 
     @td.with_tool('test', 'Tickets', 'bugs', username='test-user')
@@ -215,33 +215,33 @@ class TestTicketModel(TrackerTestWithModel):
             ticket.assigned_to_id = User.by_username('test-user')._id
             ticket.discussion_thread.add_post(text='test comment')
 
-        assert_equal(
-            Ticket.query.find({'app_config_id': app1.config._id}).count(), 1)
-        assert_equal(
-            Ticket.query.find({'app_config_id': app2.config._id}).count(), 0)
-        assert_equal(
-            Post.query.find(dict(thread_id=ticket.discussion_thread._id)).count(), 1)
+        assert (
+            Ticket.query.find({'app_config_id': app1.config._id}).count() == 1)
+        assert (
+            Ticket.query.find({'app_config_id': app2.config._id}).count() == 0)
+        assert (
+            Post.query.find(dict(thread_id=ticket.discussion_thread._id)).count() == 1)
 
         t = ticket.move(app2.config)
-        assert_equal(
-            Ticket.query.find({'app_config_id': app1.config._id}).count(), 0)
-        assert_equal(
-            Ticket.query.find({'app_config_id': app2.config._id}).count(), 1)
-        assert_equal(t.summary, 'test ticket')
-        assert_equal(t.description, 'test description')
-        assert_equal(t.assigned_to.username, 'test-user')
-        assert_equal(t.url(), '/p/test/bugs2/1/')
+        assert (
+            Ticket.query.find({'app_config_id': app1.config._id}).count() == 0)
+        assert (
+            Ticket.query.find({'app_config_id': app2.config._id}).count() == 1)
+        assert t.summary == 'test ticket'
+        assert t.description == 'test description'
+        assert t.assigned_to.username == 'test-user'
+        assert t.url() == '/p/test/bugs2/1/'
 
         post = Post.query.find(dict(thread_id=ticket.discussion_thread._id,
                                     text={'$ne': 'test comment'})).first()
         assert post is not None, 'No comment about ticket moving'
         message = 'Ticket moved from /p/test/bugs/1/'
-        assert_equal(post.text, message)
+        assert post.text == message
 
         post = Post.query.find(dict(text='test comment')).first()
-        assert_equal(post.thread.discussion_id, app2.config.discussion_id)
-        assert_equal(post.thread.app_config_id, app2.config._id)
-        assert_equal(post.app_config_id, app2.config._id)
+        assert post.thread.discussion_id == app2.config.discussion_id
+        assert post.thread.app_config_id == app2.config._id
+        assert post.app_config_id == app2.config._id
 
     @td.with_tool('test', 'Tickets', 'bugs', username='test-user')
     @td.with_tool('test', 'Tickets', 'bugs2', username='test-user')
@@ -263,16 +263,16 @@ class TestTicketModel(TrackerTestWithModel):
             ticket.custom_fields['_test2'] = 'test val 2'
 
         t = ticket.move(app2.config)
-        assert_equal(t.summary, 'test ticket')
-        assert_equal(t.description, 'test description')
-        assert_equal(t.custom_fields['_test'], 'test val')
+        assert t.summary == 'test ticket'
+        assert t.description == 'test description'
+        assert t.custom_fields['_test'] == 'test val'
         post = Post.query.find(
             dict(thread_id=ticket.discussion_thread._id)).first()
         assert post is not None, 'No comment about ticket moving'
         message = 'Ticket moved from /p/test/bugs/1/'
         message += '\n\nCan\'t be converted:\n'
         message += '\n- **_test2**: test val 2'
-        assert_equal(post.text, message)
+        assert post.text == message
 
     @td.with_tool('test', 'Tickets', 'bugs', username='test-user')
     @td.with_tool('test', 'Tickets', 'bugs2', username='test-user')
@@ -300,9 +300,9 @@ class TestTicketModel(TrackerTestWithModel):
             ticket.assigned_to_id = User.by_username('test-user-0')._id
 
         t = ticket.move(app2.config)
-        assert_equal(t.assigned_to_id, None)
-        assert_equal(t.custom_fields['_user_field'], 'test-user')
-        assert_equal(t.custom_fields['_user_field_2'], '')
+        assert t.assigned_to_id == None
+        assert t.custom_fields['_user_field'] == 'test-user'
+        assert t.custom_fields['_user_field_2'] == ''
         post = Post.query.find(
             dict(thread_id=ticket.discussion_thread._id)).first()
         assert post is not None, 'No comment about ticket moving'
@@ -310,7 +310,7 @@ class TestTicketModel(TrackerTestWithModel):
         message += '\n\nCan\'t be converted:\n'
         message += '\n- **_user_field_2**: test-user-0 (user not in project)'
         message += '\n- **assigned_to**: test-user-0 (user not in project)'
-        assert_equal(post.text, message)
+        assert post.text == message
 
     @td.with_tool('test', 'Tickets', 'bugs', username='test-user')
     def test_attach_with_resettable_stream(self):
@@ -318,7 +318,7 @@ class TestTicketModel(TrackerTestWithModel):
             ticket = Ticket.new()
             ticket.summary = 'test ticket'
             ticket.description = 'test description'
-        assert_equal(len(ticket.attachments), 0)
+        assert len(ticket.attachments) == 0
         f = six.moves.urllib.request.urlopen('file://%s' % __file__)
         TicketAttachment.save_attachment(
             'test_ticket_model.py', ResettableStream(f),
@@ -327,15 +327,15 @@ class TestTicketModel(TrackerTestWithModel):
         # need to refetch since attachments are cached
         session(ticket).expunge(ticket)
         ticket = Ticket.query.get(_id=ticket._id)
-        assert_equal(len(ticket.attachments), 1)
-        assert_equal(ticket.attachments[0].filename, 'test_ticket_model.py')
+        assert len(ticket.attachments) == 1
+        assert ticket.attachments[0].filename == 'test_ticket_model.py'
 
     def test_json_parents(self):
         ticket = Ticket.new()
         json_keys = list(ticket.__json__().keys())
-        assert_in('related_artifacts', json_keys)  # from Artifact
-        assert_in('votes_up', json_keys)  # VotableArtifact
-        assert_in('ticket_num', json_keys)  # Ticket
+        assert 'related_artifacts' in json_keys  # from Artifact
+        assert 'votes_up' in json_keys  # VotableArtifact
+        assert 'ticket_num' in json_keys  # Ticket
         assert ticket.__json__()['assigned_to'] is None
 
     @mock.patch('forgetracker.model.ticket.tsearch')
@@ -349,20 +349,20 @@ class TestTicketModel(TrackerTestWithModel):
         filter = None
         Ticket.paged_query_or_search(app_cfg, user, mongo_query, solr_query, filter, **kw)
         query.assert_called_once_with(app_cfg, user, mongo_query, sort=None, limit=None, page=0, **kw)
-        assert_equal(tsearch.query_filter_choices.call_count, 1)
-        assert_equal(tsearch.query_filter_choices.call_args[0][0], 'solr query')
-        assert_equal(search.call_count, 0)
+        assert tsearch.query_filter_choices.call_count == 1
+        assert tsearch.query_filter_choices.call_args[0][0] == 'solr query'
+        assert search.call_count == 0
         query.reset_mock(), search.reset_mock(), tsearch.reset_mock()
 
         filter = {'status': 'unread'}
         Ticket.paged_query_or_search(app_cfg, user, mongo_query, solr_query, filter, **kw)
         search.assert_called_once_with(app_cfg, user, solr_query, filter=filter, sort=None, limit=None, page=0, **kw)
-        assert_equal(query.call_count, 0)
-        assert_equal(tsearch.query_filter_choices.call_count, 0)
+        assert query.call_count == 0
+        assert tsearch.query_filter_choices.call_count == 0
 
     def test_index(self):
         idx = Ticket(ticket_num=2, summary="ticket2", labels=["mylabel", "other"]).index()
-        assert_equal(idx['summary_t'], 'ticket2')
-        assert_equal(idx['labels_t'], 'mylabel other')
-        assert_equal(idx['reported_by_s'], 'test-user')
-        assert_equal(idx['assigned_to_s'], None)  # must exist at least
+        assert idx['summary_t'] == 'ticket2'
+        assert idx['labels_t'] == 'mylabel other'
+        assert idx['reported_by_s'] == 'test-user'
+        assert idx['assigned_to_s'] == None  # must exist at least
diff --git a/ForgeWiki/forgewiki/tests/functional/test_rest.py b/ForgeWiki/forgewiki/tests/functional/test_rest.py
index e2f2ecaa2..694275746 100644
--- a/ForgeWiki/forgewiki/tests/functional/test_rest.py
+++ b/ForgeWiki/forgewiki/tests/functional/test_rest.py
@@ -39,7 +39,7 @@ class TestWikiApi(TestRestApiBase):
 
     def test_get_root(self):
         r = self.app.get('/rest/p/test/wiki/')
-        assert_equal(r.json, {'pages': ['Home']})
+        assert r.json == {'pages': ['Home']}
 
     def test_get_page(self):
         r = self.app.get('/p/test/wiki/Home/')
@@ -49,17 +49,17 @@ class TestWikiApi(TestRestApiBase):
                       upload_files=[('file_info', 'test_root.py', content)])
         r = self.app.get('/rest/p/test/wiki/Home/')
         r = json.loads(r.text)
-        assert_equal(r['attachments'][0]['url'],
+        assert (r['attachments'][0]['url'] ==
                      'http://localhost/p/test/wiki/Home/attachment/test_root.py')
-        assert_equal(r['discussion_thread_url'], 'http://localhost/rest%s' %
+        assert (r['discussion_thread_url'] == 'http://localhost/rest%s' %
                      discussion_url)
-        assert_equal(r['discussion_thread']['_id'],
+        assert (r['discussion_thread']['_id'] ==
                      discussion_url.split('/')[-2])
         self.app.post('/wiki/Home/attach',
                       upload_files=[('file_info', '__init__.py', content), ])
         r = self.app.get('/rest/p/test/wiki/Home/')
         r = json.loads(r.text)
-        assert_equal(len(r['attachments']), 2)
+        assert len(r['attachments']) == 2
 
     def test_page_does_not_exist(self):
         r = self.api_get('/rest/p/test/wiki/fake/', status=404)
@@ -70,10 +70,10 @@ class TestWikiApi(TestRestApiBase):
             'labels': 'head hunting,dark side'
         }
         r = self.api_post('/rest/p/test/wiki/Home/', **data)
-        assert_equal(r.status_int, 200)
+        assert r.status_int == 200
         r = self.api_get('/rest/p/test/wiki/Home/')
-        assert_equal(r.json['text'], data['text'])
-        assert_equal(r.json['labels'], data['labels'].split(','))
+        assert r.json['text'] == data['text']
+        assert r.json['labels'] == data['labels'].split(',')
 
     def test_create_page(self):
         data = {
@@ -81,10 +81,10 @@ class TestWikiApi(TestRestApiBase):
             'labels': 'head hunting,dark side'
         }
         r = self.api_post(h.urlquote('/rest/p/test/wiki/tést/'), **data)
-        assert_equal(r.status_int, 200)
+        assert r.status_int == 200
         r = self.api_get(h.urlquote('/rest/p/test/wiki/tést/'))
-        assert_equal(r.json['text'], data['text'])
-        assert_equal(r.json['labels'], data['labels'].split(','))
+        assert r.json['text'] == data['text']
+        assert r.json['labels'] == data['labels'].split(',')
 
     def test_create_page_limit(self):
         data = {
@@ -95,12 +95,12 @@ class TestWikiApi(TestRestApiBase):
         with h.push_config(tg.config, **{'forgewiki.rate_limits': '{}'}):
             r = self.api_post('/rest/p/test/wiki/page1/', status=200, **data)
             p = Page.query.get(title='page1')
-            assert_not_equal(p, None)
+            assert p != None
         # Set rate limit to 1 in first hour of project
         with h.push_config(tg.config, **{'forgewiki.rate_limits': '{"3600": 1}'}):
             r = self.api_post('/rest/p/test/wiki/page2/', status=429, **data)
             p = Page.query.get(title='page2')
-            assert_equal(p, None)
+            assert p == None
 
     # http://blog.watchfire.com/wfblog/2011/10/json-based-xss-exploitation.html
     def test_json_encoding_security(self):
@@ -108,15 +108,15 @@ class TestWikiApi(TestRestApiBase):
                       text='foo <img src=x onerror=alert(1)> bar')
         r = self.api_get('/rest/p/test/wiki/foo.html')
         # raw text is not an HTML tag
-        assert_in(r'foo \u003Cimg src=x onerror=alert(1)> bar', r.text)
+        assert r'foo \u003Cimg src=x onerror=alert(1)> bar' in r.text
         # and json still is parsed into correct content
-        assert_equal(r.json['text'], 'foo <img src=x onerror=alert(1)> bar')
+        assert r.json['text'] == 'foo <img src=x onerror=alert(1)> bar'
 
     def test_json_encoding_directly(self):
         # used in @expose('json'), monkey-patched in our patches.py
-        assert_equal(tg.jsonify.encode('<'), r'"\u003C"')
+        assert tg.jsonify.encode('<') == r'"\u003C"'
         # make sure these are unchanged
-        assert_equal(json.dumps('<'), '"<"')
+        assert json.dumps('<') == '"<"'
 
 
 class TestWikiHasAccess(TestRestApiBase):
@@ -139,13 +139,13 @@ class TestWikiHasAccess(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/wiki/has_access?user=babadook&perm=read',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
         r = self.api_get(
             '/rest/p/test/wiki/has_access?user=test-user&perm=jump',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
 
     def test_has_access_not_admin(self):
         """
@@ -161,10 +161,10 @@ class TestWikiHasAccess(TestRestApiBase):
         r = self.api_get(
             '/rest/p/test/wiki/has_access?user=test-admin&perm=create',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], True)
+        assert r.status_int == 200
+        assert r.json['result'] == True
         r = self.api_get(
             '/rest/p/test/wiki/has_access?user=test-user&perm=create',
             user='root')
-        assert_equal(r.status_int, 200)
-        assert_equal(r.json['result'], False)
+        assert r.status_int == 200
+        assert r.json['result'] == False
diff --git a/ForgeWiki/forgewiki/tests/functional/test_root.py b/ForgeWiki/forgewiki/tests/functional/test_root.py
index 0c4ea7f0f..05e2b181e 100644
--- a/ForgeWiki/forgewiki/tests/functional/test_root.py
+++ b/ForgeWiki/forgewiki/tests/functional/test_root.py
@@ -80,7 +80,7 @@ class TestRootController(TestController):
 
     def test_root_new_page(self):
         response = self.app.get('/wiki/new_page?title=' + h.urlquote('tést'))
-        assert_equal(response.location, 'http://localhost/wiki/t%C3%A9st/')
+        assert response.location == 'http://localhost/wiki/t%C3%A9st/'
 
     def test_root_new_search(self):
         self.app.get(h.urlquote('/wiki/tést/'))
@@ -95,10 +95,10 @@ class TestRootController(TestController):
     @patch('allura.lib.search.search')
     def test_search(self, search):
         r = self.app.get('/wiki/search/?q=test')
-        assert_in(
-            '<a href="/wiki/search/?q=test&amp;sort=score+asc" class="strong">relevance</a>', r)
-        assert_in(
-            '<a href="/wiki/search/?q=test&amp;sort=mod_date_dt+desc" class="">date</a>', r)
+        assert (
+            '<a href="/wiki/search/?q=test&amp;sort=score+asc" class="strong">relevance</a>' in r)
+        assert (
+            '<a href="/wiki/search/?q=test&amp;sort=mod_date_dt+desc" class="">date</a>' in r)
 
         p = M.Project.query.get(shortname='test')
         r = self.app.get('/wiki/search/?q=test&sort=score+asc')
@@ -147,7 +147,7 @@ class TestRootController(TestController):
         assert btn is not None, "Can't find a help button"
         div = r.html.find('div', attrs={'id': 'lightbox_search_help_modal'})
         assert div is not None, "Can't find help text"
-        assert_in('To search for an exact phrase', div.text)
+        assert 'To search for an exact phrase' in div.text
 
     def test_nonexistent_page_edit(self):
         resp = self.app.get(h.urlquote('/wiki/tést/'))
@@ -188,7 +188,7 @@ class TestRootController(TestController):
                 'text': 'sometext',
                 'labels': 'test label',
                 }).follow()
-        assert_in('<a href="/p/test/wiki/search/?q=labels_t:%22test label%22&parser=standard">test label (1)</a>',
+        assert ('<a href="/p/test/wiki/search/?q=labels_t:%22test label%22&parser=standard">test label (1)</a>' in
                   response)
 
     def test_title_slashes(self):
@@ -347,14 +347,14 @@ class TestRootController(TestController):
                                             <script>alert(1)</script>""")
         self.app.post('/wiki/testdiff/update', params=d)
         response = self.app.get('/wiki/testdiff/diff?v1=1&v2=2')
-        assert_in('# Now fix <del> permissons. </del> <ins> permissions. </ins> '
-                  'Wrong permissions may cause <ins> a </ins> massive slowdown!',
+        assert ('# Now fix <del> permissons. </del> <ins> permissions. </ins> '
+                  'Wrong permissions may cause <ins> a </ins> massive slowdown!' in
                   response)
-        assert_not_in('<script>alert', response)
-        assert_in('&lt;script&gt;alert', response)
+        assert '<script>alert' not in response
+        assert '&lt;script&gt;alert' in response
         response = self.app.get('/wiki/testdiff/diff?v1=2&v2=1')
-        assert_in('# Now fix <del> permissions. </del> <ins> permissons. </ins> '
-                  'Wrong permissions may cause <del> a </del> massive slowdown!',
+        assert ('# Now fix <del> permissions. </del> <ins> permissons. </ins> '
+                  'Wrong permissions may cause <del> a </del> massive slowdown!' in
                   response)
 
     def test_page_raw(self):
@@ -405,8 +405,8 @@ class TestRootController(TestController):
                 'text': 'sometext',
                 'labels': '',
                 })
-        assert_equal(spam_checker.check.call_args[0][0], 'tést\nsometext')
-        assert_equal(response.location, 'http://localhost/wiki/t%C3%A9st/')
+        assert spam_checker.check.call_args[0][0] == 'tést\nsometext'
+        assert response.location == 'http://localhost/wiki/t%C3%A9st/'
 
     def test_page_get_markdown(self):
         self.app.post(
@@ -450,7 +450,7 @@ class TestRootController(TestController):
                 'text': 'sometext',
                 'labels': 'yellow,green',
                 })
-        assert_equal(response.location, 'http://localhost/wiki/t%C3%A9st/')
+        assert response.location == 'http://localhost/wiki/t%C3%A9st/'
         response = self.app.post(
             h.urlquote('/wiki/tést/update'),
             params={
@@ -458,7 +458,7 @@ class TestRootController(TestController):
                 'text': 'sometext',
                 'labels': 'yellow',
                 })
-        assert_equal(response.location, 'http://localhost/wiki/t%C3%A9st/')
+        assert response.location == 'http://localhost/wiki/t%C3%A9st/'
 
     def test_page_label_count(self):
         labels = "label"
@@ -539,7 +539,7 @@ class TestRootController(TestController):
         self.app.post(h.urlquote('/wiki/tést/attach'), upload_files=[upload])
         page_editor = self.app.get(h.urlquote('/wiki/tést/edit'))
         download = page_editor.click(description=file_name)
-        assert_true(download.body == file_data)
+        assert download.body == file_data
 
     def test_new_image_attachment_content(self):
         self.app.post('/wiki/TEST/update', params={
@@ -679,7 +679,7 @@ class TestRootController(TestController):
             'labels': '',
             })
         homepage_admin = self.app.get('/admin/wiki/home', validate_chunk=True)
-        assert_equal(homepage_admin.form['new_home'].value, 'Home')
+        assert homepage_admin.form['new_home'].value == 'Home'
         homepage_admin.form['new_home'].value = 'our_néw_home'
         homepage_admin.form.submit()
         root_path = self.app.get('/wiki/', status=301)
@@ -783,7 +783,7 @@ class TestRootController(TestController):
         # first request caches html, second serves from cache
         r = self.app.get('/wiki/cache/')
         r = self.app.get('/wiki/cache/')
-        assert_true(html in r)
+        assert html in r
 
     def test_page_delete(self):
         self.app.post('/wiki/aaa/update', params={
@@ -814,7 +814,7 @@ class TestRootController(TestController):
         # undelete it
         undelete_url = deletedpath + 'undelete'
         response = self.app.post(undelete_url)
-        assert_equal(response.json, {'location': './edit'})
+        assert response.json == {'location': './edit'}
         response = self.app.get(deletedpath + 'edit')
         assert 'Edit bbb' in response
 
@@ -877,20 +877,20 @@ class TestRootController(TestController):
         # Set rate limit to unlimit
         with h.push_config(config, **{'forgewiki.rate_limits': '{}'}):
             r = self.app.get('/p/test/wiki/new-page-title/')
-            assert_equal(r.status_int, 302)
-            assert_equal(
-                r.location,
+            assert r.status_int == 302
+            assert (
+                r.location ==
                 'http://localhost/p/test/wiki/new-page-title/edit')
-            assert_equal(self.webflash(r), '')
+            assert self.webflash(r) == ''
         # Set rate limit to 1 in first hour of project
         with h.push_config(config, **{'forgewiki.rate_limits': '{"3600": 1}'}):
             r = self.app.get('/p/test/wiki/new-page-title/')
-            assert_equal(r.status_int, 302)
-            assert_equal(r.location, 'http://localhost/p/test/wiki/')
+            assert r.status_int == 302
+            assert r.location == 'http://localhost/p/test/wiki/'
             wf = json.loads(self.webflash(r))
-            assert_equal(wf['status'], 'error')
-            assert_equal(
-                wf['message'],
+            assert wf['status'] == 'error'
+            assert (
+                wf['message'] ==
                 'Page create/edit rate limit exceeded. Please try again later.')
 
     def test_rate_limit_update(self):
@@ -899,23 +899,23 @@ class TestRootController(TestController):
             r = self.app.post(
                 '/p/test/wiki/page1/update',
                 dict(text='Some text', title='page1')).follow()
-            assert_in('Some text', r)
+            assert 'Some text' in r
             p = model.Page.query.get(title='page1')
-            assert_not_equal(p, None)
+            assert p != None
         # Set rate limit to 1 in first hour of project
         with h.push_config(config, **{'forgewiki.rate_limits': '{"3600": 1}'}):
             r = self.app.post(
                 '/p/test/wiki/page2/update',
                 dict(text='Some text', title='page2'))
-            assert_equal(r.status_int, 302)
-            assert_equal(r.location, 'http://localhost/p/test/wiki/')
+            assert r.status_int == 302
+            assert r.location == 'http://localhost/p/test/wiki/'
             wf = json.loads(self.webflash(r))
-            assert_equal(wf['status'], 'error')
-            assert_equal(
-                wf['message'],
+            assert wf['status'] == 'error'
+            assert (
+                wf['message'] ==
                 'Page create/edit rate limit exceeded. Please try again later.')
             p = model.Page.query.get(title='page2')
-            assert_equal(p, None)
+            assert p == None
 
     def test_rate_limit_by_user(self):
         # also test that multiple edits to a page counts as one page towards the limit
@@ -926,45 +926,45 @@ class TestRootController(TestController):
         with h.push_config(config, **{'forgewiki.rate_limits_per_user': '{"3600": 5}'}):
             r = self.app.post('/p/test/wiki/page123/update',  # page 4 (remember, 3 other projects' wiki pages)
                               dict(text='Starting a new page, ok', title='page123'))
-            assert_equal(self.webflash(r), '')
+            assert self.webflash(r) == ''
             r = self.app.post('/p/test/wiki/page123/update',
                               dict(text='Editing some', title='page123'))
-            assert_equal(self.webflash(r), '')
+            assert self.webflash(r) == ''
             r = self.app.post('/p/test/wiki/page123/update',
                               dict(text='Still editing', title='page123'))
-            assert_equal(self.webflash(r), '')
+            assert self.webflash(r) == ''
             r = self.app.post('/p/test/wiki/pageABC/update',  # page 5
                               dict(text='Another new page', title='pageABC'))
-            assert_equal(self.webflash(r), '')
+            assert self.webflash(r) == ''
             r = self.app.post('/p/test/wiki/pageZZZZZ/update',  # page 6
                               dict(text='This new page hits the limit', title='pageZZZZZ'))
             wf = json.loads(self.webflash(r))
-            assert_equal(wf['status'], 'error')
-            assert_equal(wf['message'], 'Page create/edit rate limit exceeded. Please try again later.')
+            assert wf['status'] == 'error'
+            assert wf['message'] == 'Page create/edit rate limit exceeded. Please try again later.'
 
     def test_sidebar_admin_menu(self):
         r = self.app.get('/p/test/wiki/Home/')
         menu = r.html.find('div', {'id': 'sidebar-admin-menu'})
-        assert_equal(menu['class'], ['hidden'])  # (not expanded)
+        assert menu['class'] == ['hidden']  # (not expanded)
         menu = [li.find('span').getText() for li in menu.findAll('li')]
-        assert_equal(
-            menu,
+        assert (
+            menu ==
             ['Set Home', 'Permissions', 'Options', 'Rename', 'Delete Everything'])
 
     def test_sidebar_admin_menu_is_expanded(self):
         r = self.app.get('/p/test/admin/wiki/permissions')
         menu = r.html.find('div', {'id': 'sidebar-admin-menu'})
-        assert_not_in('hidden', menu.get('class', []))  # expanded
+        assert 'hidden' not in menu.get('class', [])  # expanded
 
     def test_sidebar_admin_menu_invisible_to_not_admin(self):
         def assert_invisible_for(username):
             env = {'username': str(username)}
             r = self.app.get('/p/test/wiki/Home/', extra_environ=env)
             menu = r.html.find('div', {'id': 'sidebar-admin-menu'})
-            assert_equal(menu, None)
+            assert menu == None
         assert_invisible_for('*anonymous')
         assert_invisible_for('test-user')
 
     def test_no_index_tag_on_empty_wiki(self):
         r = self.app.get('/u/test-user/wiki/Home/')
-        assert_in('content="noindex, follow"', r.text)
+        assert 'content="noindex, follow"' in r.text
diff --git a/ForgeWiki/forgewiki/tests/test_app.py b/ForgeWiki/forgewiki/tests/test_app.py
index 86ad91743..3dc723c68 100644
--- a/ForgeWiki/forgewiki/tests/test_app.py
+++ b/ForgeWiki/forgewiki/tests/test_app.py
@@ -71,22 +71,22 @@ class TestBulkExport:
         f.seek(0)
         wiki = json.loads(f.read())
         pages = sorted(wiki['pages'], key=operator.itemgetter('title'))
-        assert_equal(len(pages), 3)
-        assert_equal(pages[0]['title'], 'A New Hope')
-        assert_equal(pages[0]['text'], 'Star Wars Episode IV: A New Hope')
-        assert_equal(pages[0]['mod_date'], '2013-07-05 00:00:00')
-        assert_equal(pages[0]['labels'], ['star wars', 'movies'])
-        assert_equal(len(pages[0]['discussion_thread']['posts']), 2)
-
-        assert_equal(pages[1]['title'], 'Return of the Jedi')
-        assert_equal(pages[1]['text'],
+        assert len(pages) == 3
+        assert pages[0]['title'] == 'A New Hope'
+        assert pages[0]['text'] == 'Star Wars Episode IV: A New Hope'
+        assert pages[0]['mod_date'] == '2013-07-05 00:00:00'
+        assert pages[0]['labels'] == ['star wars', 'movies']
+        assert len(pages[0]['discussion_thread']['posts']) == 2
+
+        assert pages[1]['title'] == 'Return of the Jedi'
+        assert (pages[1]['text'] ==
                      'Star Wars Episode VI: Return of the Jedi')
-        assert_equal(len(pages[1]['discussion_thread']['posts']), 0)
+        assert len(pages[1]['discussion_thread']['posts']) == 0
 
-        assert_equal(pages[2]['title'], 'The Empire Strikes Back')
-        assert_equal(pages[2]['text'],
+        assert pages[2]['title'] == 'The Empire Strikes Back'
+        assert (pages[2]['text'] ==
                      'Star Wars Episode V: The Empire Strikes Back')
-        assert_equal(len(pages[2]['discussion_thread']['posts']), 0)
+        assert len(pages[2]['discussion_thread']['posts']) == 0
 
     def add_page_with_attachmetns(self):
         self.page = WM.Page.upsert('ZTest_title')
@@ -159,7 +159,7 @@ class TestApp:
         msg = dict(payload=message, message_id=message_id, headers={'Subject': 'test'})
         self.wiki.handle_message('A_New_Hope', msg)
         post = M.Post.query.get(_id=message_id)
-        assert_equal(post["text"], message)
+        assert post["text"] == message
 
     def test_uninstall(self):
         assert WM.Page.query.get(title='A New Hope')
diff --git a/ForgeWiki/forgewiki/tests/test_wiki_roles.py b/ForgeWiki/forgewiki/tests/test_wiki_roles.py
index 605c4cedc..e03880976 100644
--- a/ForgeWiki/forgewiki/tests/test_wiki_roles.py
+++ b/ForgeWiki/forgewiki/tests/test_wiki_roles.py
@@ -44,12 +44,12 @@ def test_role_assignments():
     def check_access(perm):
         pred = security.has_access(c.app, perm)
         return pred(user=admin), pred(user=user), pred(user=anon)
-    assert_equal(check_access('configure'), (True, False, False))
-    assert_equal(check_access('read'), (True, True, True))
-    assert_equal(check_access('create'), (True, False, False))
-    assert_equal(check_access('edit'), (True, False, False))
-    assert_equal(check_access('delete'), (True, False, False))
-    assert_equal(check_access('unmoderated_post'), (True, True, False))
-    assert_equal(check_access('post'), (True, True, False))
-    assert_equal(check_access('moderate'), (True, False, False))
-    assert_equal(check_access('admin'), (True, False, False))
+    assert check_access('configure') == (True, False, False)
+    assert check_access('read') == (True, True, True)
+    assert check_access('create') == (True, False, False)
+    assert check_access('edit') == (True, False, False)
+    assert check_access('delete') == (True, False, False)
+    assert check_access('unmoderated_post') == (True, True, False)
+    assert check_access('post') == (True, True, False)
+    assert check_access('moderate') == (True, False, False)
+    assert check_access('admin') == (True, False, False)