Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Removed time.sleep()s, updated TBB version in Dockerfile #3870

Merged

Conversation

zenmonkeykstop
Copy link
Contributor

@zenmonkeykstop zenmonkeykstop commented Oct 12, 2018

Status

Ready for review

Description of Changes

Fixes #3486

Replaces time.sleep(self.sleep_time) calls with self.wait_for (, timeout=self.sleep_time), reducing the time it takes to run functional tests against the SD dev container.

Misc updates to functional and page layout tests to reduce flakiness:

  • increased alert wait timeout to 60s
  • wrapped problematic interactions with more wait_for()s and verification checks
  • for some still-flaky clicks, replaced click action with send_keys(Keys.ENTER), or explicitly set focus with move_to()s.

Updates TBB version to 8.0.3 in dev container dockerfile (previous versions had been removed from repos).

Testing

Run the functional tests with:

cd securedrop 
./bin/dev-shell ./bin/run-test tests/functional/

Docker build should complete successfully. Tests should complete without error.

Checklist

If you made non-trivial code changes:

  • I have written a test plan and validated it for this PR

@zenmonkeykstop zenmonkeykstop force-pushed the 3486-func-add-waitfors branch 4 times, most recently from 82e550d to c097595 Compare October 12, 2018 15:43
@zenmonkeykstop zenmonkeykstop force-pushed the 3486-func-add-waitfors branch 5 times, most recently from 6f98372 to bb3cc5c Compare October 15, 2018 04:21
@codecov-io
Copy link

codecov-io commented Oct 15, 2018

Codecov Report

Merging #3870 into tbb-0.9.0 will decrease coverage by 0.6%.
The diff coverage is n/a.

Impacted file tree graph

@@              Coverage Diff              @@
##           tbb-0.9.0    #3870      +/-   ##
=============================================
- Coverage      85.16%   84.56%   -0.61%     
=============================================
  Files             41       43       +2     
  Lines           2643     2767     +124     
  Branches         287      300      +13     
=============================================
+ Hits            2251     2340      +89     
- Misses           329      359      +30     
- Partials          63       68       +5
Impacted Files Coverage Δ
...op/securedrop/request_that_secures_file_uploads.py 80% <0%> (-20%) ⬇️
securedrop/securedrop/journalist_app/api.py 94.89% <0%> (-1.36%) ⬇️
securedrop/securedrop/journalist_app/main.py 74.48% <0%> (ø) ⬆️
securedrop/securedrop/i18n_tool.py 94.14% <0%> (ø) ⬆️
securedrop/securedrop/create-dev-data.py 0% <0%> (ø) ⬆️
...ns/f2833ac34bb6_add_uuid_column_for_users_table.py 42.85% <0%> (ø)
...op/alembic/versions/6db892e17271_add_reply_uuid.py 45% <0%> (ø)
securedrop/securedrop/source_app/main.py 93.75% <0%> (+0.08%) ⬆️
securedrop/securedrop/journalist_app/__init__.py 91.95% <0%> (+0.09%) ⬆️
securedrop/securedrop/crypto_util.py 96.22% <0%> (+0.1%) ⬆️
... and 6 more

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 8385369...3abc1c3. Read the comment docs.

@redshiftzero
Copy link
Contributor

@kushaldas want to review this one?

@kushaldas
Copy link
Contributor

Note: The latest Tor browser version is 8.0.3.

Copy link
Contributor

@kushaldas kushaldas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

_________________________________________________________ TestAdminInterface.test_admin_deletes_user _________________________________________________________

self = <tests.functional.test_admin_interface.TestAdminInterface object at 0x7ffb4b8f2390>

    def test_admin_deletes_user(self):
        self._admin_logs_in()
        self._admin_visits_admin_interface()
        self._admin_adds_a_user()
>       self._admin_deletes_user()

/home/kdas/code/securedrop/securedrop/tests/functional/test_admin_interface.py:28: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 
/home/kdas/code/securedrop/securedrop/tests/functional/journalist_navigation_steps.py:405: in _admin_deletes_user
    self._alert_wait()
/home/kdas/code/securedrop/securedrop/tests/functional/functional_test.py:383: in _alert_wait
    'Timed out waiting for confirmation popup.')

There are 13 other layout test failures.

@zenmonkeykstop
Copy link
Contributor Author

zenmonkeykstop commented Oct 29, 2018

Most of the page layout tests are failing because the "flag for reply" button is being displayed instead of the reply text field. It looked like a mocking problem but it's actually caused by the reply keys being generated asynchronously. Fixed by adding a delay after source submissions.

@zenmonkeykstop
Copy link
Contributor Author

Rebased and tidied up a bit.

Copy link
Contributor

@kushaldas kushaldas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A few more tests again failed.

tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_changes_logo[en_US] PASSED                                                      [ 74%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_changes_logo[ar] PASSED                                                         [ 74%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_changes_logo[fr_FR] PASSED                                                      [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_no_documents[en_US] PASSED                                                        [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_no_documents[ar] FAILED                                                           [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_no_documents[fr_FR] PASSED                                                        [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_has_no_key[en_US] PASSED                                                          [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_has_no_key[ar] PASSED                                                             [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_has_no_key[fr_FR] PASSED                                                          [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_flagged[en_US] PASSED                                                             [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_flagged[ar] PASSED                                                                [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_flagged[fr_FR] PASSED                                                             [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col[en_US] PASSED                                                                     [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col[ar] FAILED                                                                        [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col[fr_FR] PASSED                                                                     [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_javascript[en_US] PASSED                                                          [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_javascript[ar] PASSED                                                             [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_javascript[fr_FR] PASSED                                                          [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_journalist_composes_reply[en_US] PASSED                                               [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_journalist_composes_reply[ar] PASSED                                                  [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_journalist_composes_reply[fr_FR] PASSED                                               [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_uses_ossec_alert_button[en_US] PASSED                                           [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_uses_ossec_alert_button[ar] PASSED                                              [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_uses_ossec_alert_button[fr_FR] PASSED                                           [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_none[en_US] PASSED                                                             [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_none[ar] PASSED                                                                [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_none[fr_FR] PASSED                                                             [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one_confirmation[en_US] PASSED                                                 [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one_confirmation[ar] PASSED                                                    [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one_confirmation[fr_FR] FAILED                                                 [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all_confirmation[en_US] PASSED                                                 [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all_confirmation[ar] PASSED                                                    [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all_confirmation[fr_FR] FAILED                                                 [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one[en_US] PASSED                                                              [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one[ar] PASSED                                                                 [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one[fr_FR] PASSED                                                              [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all[en_US] PASSED                                                              [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all[ar] PASSED                                                                 [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all[fr_FR] PASSED                                                              [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_user[en_US] PASSED                                                       [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_user[ar] PASSED                                                          [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_user[fr_FR] PASSED                                                       [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_admin[en_US] PASSED                                                      [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_admin[ar] PASSED                                                         [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_admin[fr_FR] PASSED                                                      [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents_admin[en_US] PASSED                                                [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents_admin[ar] PASSED                                                   [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents_admin[fr_FR] PASSED                                                [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_interface_index[en_US] PASSED                                                   [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_interface_index[ar] PASSED                                                      [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_interface_index[fr_FR] PASSED                                                   [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_flag[en_US] FAILED                                                                    [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_flag[ar] PASSED                                                                       [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_flag[fr_FR] PASSED                                                                    [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents[en_US] PASSED                                                      [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents[ar] PASSED                                                         [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents[fr_FR] PASSED                                                      [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index[en_US] FAILED                                                                   [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index[ar] PASSED                                                                      [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index[fr_FR] FAILED                                                                   [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_javascript[en_US] FAILED                                                        [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_javascript[ar] PASSED                                                           [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_javascript[fr_FR] PASSED                                                        [ 87%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_entered_text[en_US] PASSED                                                      [ 87%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_entered_text[ar] PASSED                                                         [ 87%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_entered_text[fr_FR] PASSED                                                      [ 87%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_to_visit_admin[en_US] PASSED                                                     [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_to_visit_admin[ar] PASSED                                                        [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_to_visit_admin[fr_FR] PASSED                                                     [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login[en_US] PASSED                                                              [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login[ar] PASSED                                                                 [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login[fr_FR] PASSED                                                              [ 89%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login_many[en_US] PASSED                                                         [ 89%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login_many[ar] PASSED                                                            [ 89%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login_many[fr_FR] PASSED                                                         [ 89%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index[en_US] PASSED                                                                           [ 89%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index[ar] PASSED                                                                              [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index[fr_FR] PASSED                                                                           [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index_javascript[en_US] PASSED                                                                [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index_javascript[ar] PASSED                                                                   [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index_javascript[fr_FR] PASSED                                                                [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup[en_US] PASSED                                                                          [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup[ar] PASSED                                                                             [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup[fr_FR] PASSED                                                                          [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup_shows_codename[en_US] PASSED                                                           [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup_shows_codename[ar] FAILED                                                              [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup_shows_codename[fr_FR] PASSED                                                           [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_login[en_US] PASSED                                                                           [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_login[ar] PASSED                                                                              [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_login[fr_FR] PASSED                                                                           [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_enters_text_in_login_form[en_US] PASSED                                                       [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_enters_text_in_login_form[ar] PASSED                                                          [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_enters_text_in_login_form[fr_FR] PASSED                                                       [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_use_tor_browser[en_US] PASSED                                                                 [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_use_tor_browser[ar] PASSED                                                                    [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_use_tor_browser[fr_FR] PASSED                                                                 [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_generate[en_US] PASSED                                                                        [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_generate[ar] PASSED                                                                           [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_generate[fr_FR] PASSED                                                                        [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_logout_flashed_message[en_US] PASSED                                                          [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_logout_flashed_message[ar] PASSED                                                             [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_logout_flashed_message[fr_FR] PASSED                                                          [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_submission_entered_text[en_US] PASSED                                                         [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_submission_entered_text[ar] PASSED                                                            [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_submission_entered_text[fr_FR] PASSED                                                         [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_next_submission_flashed_message[en_US] PASSED                                                 [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_next_submission_flashed_message[ar] PASSED                                                    [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_next_submission_flashed_message[fr_FR] PASSED                                                 [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_checks_for_reply[en_US] FAILED                                                         [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_checks_for_reply[ar] PASSED                                                            [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_checks_for_reply[fr_FR] PASSED                                                         [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_flagged[en_US] PASSED                                                                  [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_flagged[ar] PASSED                                                                     [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_flagged[fr_FR] PASSED                                                                  [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_notfound[en_US] PASSED                                                                        [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_notfound[ar] PASSED                                                                           [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_notfound[fr_FR] PASSED                                                                        [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_tor2web_warning[en_US] PASSED                                                                 [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_tor2web_warning[ar] PASSED                                                                    [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_tor2web_warning[fr_FR] PASSED                                                                 [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_why_journalist_key[en_US] PASSED                                                              [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_why_journalist_key[ar] PASSED                                                                 [ 99%]
tests/pageslayout/test_source.py::TestSourceLayout::test_why_journalist_key[fr_FR] PASSED                                                              [ 99%]
tests/pageslayout/test_source.py::TestSourceSessionLayout::test_source_session_timeout[en_US] PASSED                                                   [ 99%]
tests/pageslayout/test_source.py::TestSourceSessionLayout::test_source_session_timeout[ar] PASSED                                                      [ 99%]
tests/pageslayout/test_source.py::TestSourceSessionLayout::test_source_session_timeout[fr_FR] PASSED                                                   [100%]

@zenmonkeykstop
Copy link
Contributor Author

@kushaldas any chance you could post or share the full output from the test run? I can't duplicate a lot of these failures.

@zenmonkeykstop zenmonkeykstop force-pushed the 3486-func-add-waitfors branch 4 times, most recently from f0b66a0 to c66aa7e Compare November 24, 2018 02:52
Copy link
Contributor

@kushaldas kushaldas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

$ make test
./bin/dev-shell ./bin/run-test -v ${TESTFILES:-tests}
Run with DOCKER_BUILD_VERBOSE=true for more information
Docker image build in progress  done !
DEPRECATION WARNING:
Sass 3.5 will no longer support Ruby 1.9.3.
Please upgrade to Ruby 2.0.0 or greater as soon as possible.

      write static/css/journalist.css
      write static/css/journalist.css.map
      write static/css/source.css
      write static/css/source.css.map
==================================================================== test session starts =====================================================================
platform linux2 -- Python 2.7.6, pytest-3.3.2, py-1.5.2, pluggy-0.6.0 -- /usr/bin/python
cachedir: tests/.cache
rootdir: /home/kdas/code/securedrop/securedrop/tests, inifile: pytest.ini
plugins: cov-2.5.1, mock-1.7.1
collected 492 items                                                                                                                                          

tests/test_2fa.py::test_totp_reuse_protections PASSED                                                                                                  [  0%]
tests/test_2fa.py::test_totp_reuse_protections2 PASSED                                                                                                 [  0%]
tests/test_2fa.py::test_bad_token_fails_to_verify_on_admin_new_user_two_factor_page PASSED                                                             [  0%]
tests/test_2fa.py::test_bad_token_fails_to_verify_on_new_user_two_factor_page PASSED                                                                   [  0%]
tests/test_alembic.py::test_alembic_head_matches_db_models PASSED                                                                                      [  1%]
tests/test_alembic.py::test_alembic_migration_upgrade[15ac9509fc68] PASSED                                                                             [  1%]
tests/test_alembic.py::test_alembic_migration_upgrade[2d0ce3ee5bdc] PASSED                                                                             [  1%]
tests/test_alembic.py::test_alembic_migration_upgrade[fccf57ceef02] PASSED                                                                             [  1%]
tests/test_alembic.py::test_alembic_migration_upgrade[e0a525cbab83] PASSED                                                                             [  1%]
tests/test_alembic.py::test_alembic_migration_upgrade[3d91d6948753] PASSED                                                                             [  2%]
tests/test_alembic.py::test_alembic_migration_upgrade[6db892e17271] PASSED                                                                             [  2%]
tests/test_alembic.py::test_alembic_migration_upgrade[faac8092c123] PASSED                                                                             [  2%]
tests/test_alembic.py::test_alembic_migration_upgrade[f2833ac34bb6] PASSED                                                                             [  2%]
tests/test_alembic.py::test_alembic_migration_downgrade[15ac9509fc68] PASSED                                                                           [  2%]
tests/test_alembic.py::test_alembic_migration_downgrade[2d0ce3ee5bdc] PASSED                                                                           [  3%]
tests/test_alembic.py::test_alembic_migration_downgrade[fccf57ceef02] PASSED                                                                           [  3%]
tests/test_alembic.py::test_alembic_migration_downgrade[e0a525cbab83] PASSED                                                                           [  3%]
tests/test_alembic.py::test_alembic_migration_downgrade[3d91d6948753] PASSED                                                                           [  3%]
tests/test_alembic.py::test_alembic_migration_downgrade[6db892e17271] PASSED                                                                           [  3%]
tests/test_alembic.py::test_alembic_migration_downgrade[faac8092c123] PASSED                                                                           [  4%]
tests/test_alembic.py::test_alembic_migration_downgrade[f2833ac34bb6] PASSED                                                                           [  4%]
tests/test_alembic.py::test_schema_unchanged_after_up_then_downgrade[15ac9509fc68] PASSED                                                              [  4%]
tests/test_alembic.py::test_schema_unchanged_after_up_then_downgrade[2d0ce3ee5bdc] PASSED                                                              [  4%]
tests/test_alembic.py::test_schema_unchanged_after_up_then_downgrade[fccf57ceef02] PASSED                                                              [  4%]
tests/test_alembic.py::test_schema_unchanged_after_up_then_downgrade[e0a525cbab83] PASSED                                                              [  5%]
tests/test_alembic.py::test_schema_unchanged_after_up_then_downgrade[3d91d6948753] PASSED                                                              [  5%]
tests/test_alembic.py::test_schema_unchanged_after_up_then_downgrade[6db892e17271] PASSED                                                              [  5%]
tests/test_alembic.py::test_schema_unchanged_after_up_then_downgrade[faac8092c123] PASSED                                                              [  5%]
tests/test_alembic.py::test_schema_unchanged_after_up_then_downgrade[f2833ac34bb6] PASSED                                                              [  5%]
tests/test_alembic.py::test_upgrade_with_data[15ac9509fc68] PASSED                                                                                     [  6%]
tests/test_alembic.py::test_upgrade_with_data[2d0ce3ee5bdc] PASSED                                                                                     [  6%]
tests/test_alembic.py::test_upgrade_with_data[fccf57ceef02] PASSED                                                                                     [  6%]
tests/test_alembic.py::test_upgrade_with_data[e0a525cbab83] PASSED                                                                                     [  6%]
tests/test_alembic.py::test_upgrade_with_data[3d91d6948753] PASSED                                                                                     [  6%]
tests/test_alembic.py::test_upgrade_with_data[6db892e17271] PASSED                                                                                     [  7%]
tests/test_alembic.py::test_upgrade_with_data[faac8092c123] PASSED                                                                                     [  7%]
tests/test_alembic.py::test_upgrade_with_data[f2833ac34bb6] PASSED                                                                                     [  7%]
tests/test_alembic.py::test_downgrade_with_data[15ac9509fc68] PASSED                                                                                   [  7%]
tests/test_alembic.py::test_downgrade_with_data[2d0ce3ee5bdc] PASSED                                                                                   [  7%]
tests/test_alembic.py::test_downgrade_with_data[fccf57ceef02] PASSED                                                                                   [  8%]
tests/test_alembic.py::test_downgrade_with_data[e0a525cbab83] PASSED                                                                                   [  8%]
tests/test_alembic.py::test_downgrade_with_data[3d91d6948753] PASSED                                                                                   [  8%]
tests/test_alembic.py::test_downgrade_with_data[6db892e17271] PASSED                                                                                   [  8%]
tests/test_alembic.py::test_downgrade_with_data[faac8092c123] PASSED                                                                                   [  8%]
tests/test_alembic.py::test_downgrade_with_data[f2833ac34bb6] PASSED                                                                                   [  9%]
tests/test_crypto_util.py::test_word_list_does_not_contain_empty_strings PASSED                                                                        [  9%]
tests/test_crypto_util.py::test_clean PASSED                                                                                                           [  9%]
tests/test_crypto_util.py::test_encrypt_success PASSED                                                                                                 [  9%]
tests/test_crypto_util.py::test_encrypt_failure PASSED                                                                                                 [  9%]
tests/test_crypto_util.py::test_encrypt_without_output PASSED                                                                                          [ 10%]
tests/test_crypto_util.py::test_encrypt_binary_stream PASSED                                                                                           [ 10%]
tests/test_crypto_util.py::test_encrypt_fingerprints_not_a_list_or_tuple PASSED                                                                        [ 10%]
tests/test_crypto_util.py::test_basic_encrypt_then_decrypt_multiple_recipients PASSED                                                                  [ 10%]
tests/test_crypto_util.py::test_genrandomid_default_locale_is_en PASSED                                                                                [ 10%]
tests/test_crypto_util.py::test_get_wordlist PASSED                                                                                                    [ 11%]
tests/test_crypto_util.py::test_hash_codename PASSED                                                                                                   [ 11%]
tests/test_crypto_util.py::test_display_id PASSED                                                                                                      [ 11%]
tests/test_crypto_util.py::test_genkeypair PASSED                                                                                                      [ 11%]
tests/test_crypto_util.py::test_delete_reply_keypair PASSED                                                                                            [ 11%]
tests/test_crypto_util.py::test_delete_reply_keypair_no_key PASSED                                                                                     [ 12%]
tests/test_crypto_util.py::test_getkey PASSED                                                                                                          [ 12%]
tests/test_db.py::test_source_public_key_setter_unimplemented PASSED                                                                                   [ 12%]
tests/test_db.py::test_source_public_key_delete_unimplemented PASSED                                                                                   [ 12%]
tests/test_db.py::test_get_one_or_else_returns_one PASSED                                                                                              [ 13%]
tests/test_db.py::test_get_one_or_else_multiple_results PASSED                                                                                         [ 13%]
tests/test_db.py::test_get_one_or_else_no_result_found PASSED                                                                                          [ 13%]
tests/test_db.py::test_throttle_login PASSED                                                                                                           [ 13%]
tests/test_db.py::test_submission_string_representation PASSED                                                                                         [ 13%]
tests/test_db.py::test_reply_string_representation PASSED                                                                                              [ 14%]
tests/test_db.py::test_journalist_string_representation PASSED                                                                                         [ 14%]
tests/test_db.py::test_source_string_representation PASSED                                                                                             [ 14%]
tests/test_i18n.py::test_get_supported_locales PASSED                                                                                                  [ 14%]
tests/test_i18n.py::test_i18n PASSED                                                                                                                   [ 14%]
tests/test_i18n.py::test_verify_default_locale_en_us_if_not_defined_in_config PASSED                                                                   [ 15%]
tests/test_i18n.py::test_locale_to_rfc_5646 PASSED                                                                                                     [ 15%]
tests/test_i18n.py::test_html_en_lang_correct PASSED                                                                                                   [ 15%]
tests/test_i18n.py::test_html_fr_lang_correct PASSED                                                                                                   [ 15%]
tests/test_i18n_tool.py::TestI18NTool::test_main PASSED                                                                                                [ 15%]
tests/test_i18n_tool.py::TestI18NTool::test_translate_desktop_l10n PASSED                                                                              [ 16%]
tests/test_i18n_tool.py::TestI18NTool::test_translate_messages_l10n PASSED                                                                             [ 16%]
tests/test_i18n_tool.py::TestI18NTool::test_translate_messages_compile_arg PASSED                                                                      [ 16%]
tests/test_i18n_tool.py::TestI18NTool::test_require_git_email_name PASSED                                                                              [ 16%]
tests/test_i18n_tool.py::TestI18NTool::test_update_docs PASSED                                                                                         [ 16%]
tests/test_i18n_tool.py::TestI18NTool::test_update_from_weblate PASSED                                                                                 [ 17%]
tests/test_integration.py::test_submit_message PASSED                                                                                                  [ 17%]
tests/test_integration.py::test_submit_file PASSED                                                                                                     [ 17%]
tests/test_integration.py::test_reply_normal PASSED                                                                                                    [ 17%]
tests/test_integration.py::test_unicode_reply_with_ansi_env PASSED                                                                                     [ 17%]
tests/test_integration.py::test_delete_collection PASSED                                                                                               [ 18%]
tests/test_integration.py::test_delete_collections PASSED                                                                                              [ 18%]
tests/test_integration.py::test_filenames PASSED                                                                                                       [ 18%]
tests/test_integration.py::test_filenames_delete PASSED                                                                                                [ 18%]
tests/test_integration.py::test_user_change_password PASSED                                                                                            [ 18%]
tests/test_integration.py::test_login_after_regenerate_hotp PASSED                                                                                     [ 19%]
tests/test_journalist.py::test_user_with_whitespace_in_username_can_login PASSED                                                                       [ 19%]
tests/test_journalist.py::test_make_password PASSED                                                                                                    [ 19%]
tests/test_journalist.py::test_reply_error_logging PASSED                                                                                              [ 19%]
tests/test_journalist.py::test_reply_error_flashed_message PASSED                                                                                      [ 19%]
tests/test_journalist.py::test_empty_replies_are_rejected PASSED                                                                                       [ 20%]
tests/test_journalist.py::test_nonempty_replies_are_accepted PASSED                                                                                    [ 20%]
tests/test_journalist.py::test_unauthorized_access_redirects_to_login PASSED                                                                           [ 20%]
tests/test_journalist.py::test_login_throttle PASSED                                                                                                   [ 20%]
tests/test_journalist.py::test_login_throttle_is_not_global PASSED                                                                                     [ 20%]
tests/test_journalist.py::test_login_invalid_credentials PASSED                                                                                        [ 21%]
tests/test_journalist.py::test_validate_redirect PASSED                                                                                                [ 21%]
tests/test_journalist.py::test_login_valid_credentials PASSED                                                                                          [ 21%]
tests/test_journalist.py::test_admin_login_redirects_to_index PASSED                                                                                   [ 21%]
tests/test_journalist.py::test_user_login_redirects_to_index PASSED                                                                                    [ 21%]
tests/test_journalist.py::test_admin_has_link_to_edit_account_page_in_index_page PASSED                                                                [ 22%]
tests/test_journalist.py::test_user_has_link_to_edit_account_page_in_index_page PASSED                                                                 [ 22%]
tests/test_journalist.py::test_admin_has_link_to_admin_index_page_in_index_page PASSED                                                                 [ 22%]
tests/test_journalist.py::test_user_lacks_link_to_admin_index_page_in_index_page PASSED                                                                [ 22%]
tests/test_journalist.py::test_admin_logout_redirects_to_index PASSED                                                                                  [ 22%]
tests/test_journalist.py::test_user_logout_redirects_to_index PASSED                                                                                   [ 23%]
tests/test_journalist.py::test_admin_index PASSED                                                                                                      [ 23%]
tests/test_journalist.py::test_admin_delete_user PASSED                                                                                                [ 23%]
tests/test_journalist.py::test_admin_cannot_delete_self PASSED                                                                                         [ 23%]
tests/test_journalist.py::test_admin_edits_user_password_success_response PASSED                                                                       [ 23%]
tests/test_journalist.py::test_admin_deletes_invalid_user_404 PASSED                                                                                   [ 24%]
tests/test_journalist.py::test_admin_edits_user_password_error_response PASSED                                                                         [ 24%]
tests/test_journalist.py::test_user_edits_password_success_response PASSED                                                                             [ 24%]
tests/test_journalist.py::test_user_edits_password_expires_session PASSED                                                                              [ 24%]
tests/test_journalist.py::test_user_edits_password_error_reponse PASSED                                                                                [ 25%]
tests/test_journalist.py::test_admin_add_user_when_username_already_taken PASSED                                                                       [ 25%]
tests/test_journalist.py::test_max_password_length PASSED                                                                                              [ 25%]
tests/test_journalist.py::test_min_password_length PASSED                                                                                              [ 25%]
tests/test_journalist.py::test_admin_edits_user_password_too_long_warning PASSED                                                                       [ 25%]
tests/test_journalist.py::test_user_edits_password_too_long_warning PASSED                                                                             [ 26%]
tests/test_journalist.py::test_admin_add_user_password_too_long_warning PASSED                                                                         [ 26%]
tests/test_journalist.py::test_admin_edits_user_invalid_username PASSED                                                                                [ 26%]
tests/test_journalist.py::test_admin_resets_user_hotp_format_non_hexa PASSED                                                                           [ 26%]
tests/test_journalist.py::test_admin_resets_user_hotp PASSED                                                                                           [ 26%]
tests/test_journalist.py::test_admin_resets_user_hotp_format_odd PASSED                                                                                [ 27%]
tests/test_journalist.py::test_admin_resets_user_hotp_error PASSED                                                                                     [ 27%]
tests/test_journalist.py::test_user_resets_hotp PASSED                                                                                                 [ 27%]
tests/test_journalist.py::test_user_resets_user_hotp_format_odd PASSED                                                                                 [ 27%]
tests/test_journalist.py::test_user_resets_user_hotp_format_non_hexa PASSED                                                                            [ 27%]
tests/test_journalist.py::test_user_resets_user_hotp_error PASSED                                                                                      [ 28%]
tests/test_journalist.py::test_admin_resets_user_totp PASSED                                                                                           [ 28%]
tests/test_journalist.py::test_user_resets_totp PASSED                                                                                                 [ 28%]
tests/test_journalist.py::test_admin_resets_hotp_with_missing_otp_secret_key PASSED                                                                    [ 28%]
tests/test_journalist.py::test_admin_new_user_2fa_redirect PASSED                                                                                      [ 28%]
tests/test_journalist.py::test_http_get_on_admin_new_user_two_factor_page PASSED                                                                       [ 29%]
tests/test_journalist.py::test_http_get_on_admin_add_user_page PASSED                                                                                  [ 29%]
tests/test_journalist.py::test_admin_add_user PASSED                                                                                                   [ 29%]
tests/test_journalist.py::test_admin_add_user_without_username PASSED                                                                                  [ 29%]
tests/test_journalist.py::test_admin_add_user_too_short_username PASSED                                                                                [ 29%]
tests/test_journalist.py::test_admin_add_user_yubikey_odd_length PASSED                                                                                [ 30%]
tests/test_journalist.py::test_admin_add_user_yubikey_valid_length PASSED                                                                              [ 30%]
tests/test_journalist.py::test_admin_add_user_yubikey_correct_length_with_whitespace PASSED                                                            [ 30%]
tests/test_journalist.py::test_admin_sets_user_to_admin PASSED                                                                                         [ 30%]
tests/test_journalist.py::test_admin_renames_user PASSED                                                                                               [ 30%]
tests/test_journalist.py::test_admin_add_user_integrity_error PASSED                                                                                   [ 31%]
tests/test_journalist.py::test_logo_upload_with_valid_image_succeeds PASSED                                                                            [ 31%]
tests/test_journalist.py::test_logo_upload_with_invalid_filetype_fails PASSED                                                                          [ 31%]
tests/test_journalist.py::test_creation_of_ossec_test_log_event PASSED                                                                                 [ 31%]
tests/test_journalist.py::test_logo_upload_with_empty_input_field_fails PASSED                                                                         [ 31%]
tests/test_journalist.py::test_admin_page_restriction_http_gets PASSED                                                                                 [ 32%]
tests/test_journalist.py::test_admin_page_restriction_http_posts PASSED                                                                                [ 32%]
tests/test_journalist.py::test_user_authorization_for_gets PASSED                                                                                      [ 32%]
tests/test_journalist.py::test_user_authorization_for_posts PASSED                                                                                     [ 32%]
tests/test_journalist.py::test_incorrect_current_password_change PASSED                                                                                [ 32%]
tests/test_journalist.py::test_passphrase_migration_on_verification PASSED                                                                             [ 33%]
tests/test_journalist.py::test_passphrase_migration_on_reset PASSED                                                                                    [ 33%]
tests/test_journalist.py::test_journalist_reply_view PASSED                                                                                            [ 33%]
tests/test_journalist.py::test_too_long_user_password_change PASSED                                                                                    [ 33%]
tests/test_journalist.py::test_valid_user_password_change PASSED                                                                                       [ 33%]
tests/test_journalist.py::test_regenerate_totp PASSED                                                                                                  [ 34%]
tests/test_journalist.py::test_edit_hotp PASSED                                                                                                        [ 34%]
tests/test_journalist.py::test_delete_source_deletes_submissions PASSED                                                                                [ 34%]
tests/test_journalist.py::test_delete_collection_updates_db PASSED                                                                                     [ 34%]
tests/test_journalist.py::test_delete_source_deletes_source_key PASSED                                                                                 [ 34%]
tests/test_journalist.py::test_delete_source_deletes_docs_on_disk PASSED                                                                               [ 35%]
tests/test_journalist.py::test_login_with_invalid_password_doesnt_call_argon2 PASSED                                                                   [ 35%]
tests/test_journalist.py::test_valid_login_calls_argon2 PASSED                                                                                         [ 35%]
tests/test_journalist.py::test_render_locales PASSED                                                                                                   [ 35%]
tests/test_journalist.py::test_download_selected_submissions_from_source PASSED                                                                        [ 35%]
tests/test_journalist.py::test_download_unread_all_sources PASSED                                                                                      [ 36%]
tests/test_journalist.py::test_download_all_selected_sources PASSED                                                                                    [ 36%]
tests/test_journalist.py::test_single_source_is_successfully_starred PASSED                                                                            [ 36%]
tests/test_journalist.py::test_single_source_is_successfully_unstarred PASSED                                                                          [ 36%]
tests/test_journalist.py::test_journalist_session_expiration PASSED                                                                                    [ 36%]
tests/test_journalist.py::test_csrf_error_page PASSED                                                                                                  [ 37%]
tests/test_journalist.py::test_col_process_aborts_with_bad_action PASSED                                                                               [ 37%]
tests/test_journalist.py::test_col_process_successfully_deletes_multiple_sources PASSED                                                                [ 37%]
tests/test_journalist.py::test_col_process_successfully_stars_sources PASSED                                                                           [ 37%]
tests/test_journalist.py::test_col_process_successfully_unstars_sources PASSED                                                                         [ 38%]
tests/test_journalist_api.py::test_unauthenticated_user_gets_all_endpoints PASSED                                                                      [ 38%]
tests/test_journalist_api.py::test_valid_user_can_get_an_api_token PASSED                                                                              [ 38%]
tests/test_journalist_api.py::test_user_cannot_get_an_api_token_with_wrong_password PASSED                                                             [ 38%]
tests/test_journalist_api.py::test_user_cannot_get_an_api_token_with_wrong_2fa_token PASSED                                                            [ 38%]
tests/test_journalist_api.py::test_user_cannot_get_an_api_token_with_no_passphase_field PASSED                                                         [ 39%]
tests/test_journalist_api.py::test_user_cannot_get_an_api_token_with_no_username_field PASSED                                                          [ 39%]
tests/test_journalist_api.py::test_user_cannot_get_an_api_token_with_no_otp_field PASSED                                                               [ 39%]
tests/test_journalist_api.py::test_authorized_user_gets_all_sources PASSED                                                                             [ 39%]
tests/test_journalist_api.py::test_user_without_token_cannot_get_protected_endpoints PASSED                                                            [ 39%]
tests/test_journalist_api.py::test_user_without_token_cannot_del_protected_endpoints PASSED                                                            [ 40%]
tests/test_journalist_api.py::test_attacker_cannot_create_valid_token_with_none_alg PASSED                                                             [ 40%]
tests/test_journalist_api.py::test_attacker_cannot_use_token_after_admin_deletes PASSED                                                                [ 40%]
tests/test_journalist_api.py::test_user_without_token_cannot_post_protected_endpoints PASSED                                                           [ 40%]
tests/test_journalist_api.py::test_api_404 PASSED                                                                                                      [ 40%]
tests/test_journalist_api.py::test_trailing_slash_cleanly_404s PASSED                                                                                  [ 41%]
tests/test_journalist_api.py::test_authorized_user_gets_single_source PASSED                                                                           [ 41%]
tests/test_journalist_api.py::test_get_non_existant_source_404s PASSED                                                                                 [ 41%]
tests/test_journalist_api.py::test_authorized_user_can_flag_a_source PASSED                                                                            [ 41%]
tests/test_journalist_api.py::test_authorized_user_can_star_a_source PASSED                                                                            [ 41%]
tests/test_journalist_api.py::test_authorized_user_can_unstar_a_source PASSED                                                                          [ 42%]
tests/test_journalist_api.py::test_disallowed_methods_produces_405 PASSED                                                                              [ 42%]
tests/test_journalist_api.py::test_authorized_user_can_get_all_submissions PASSED                                                                      [ 42%]
tests/test_journalist_api.py::test_authorized_user_get_source_submissions PASSED                                                                       [ 42%]
tests/test_journalist_api.py::test_authorized_user_can_get_single_submission PASSED                                                                    [ 42%]
tests/test_journalist_api.py::test_authorized_user_can_get_all_replies PASSED                                                                          [ 43%]
tests/test_journalist_api.py::test_authorized_user_get_source_replies PASSED                                                                           [ 43%]
tests/test_journalist_api.py::test_authorized_user_can_get_single_reply PASSED                                                                         [ 43%]
tests/test_journalist_api.py::test_authorized_user_can_delete_single_submission PASSED                                                                 [ 43%]
tests/test_journalist_api.py::test_authorized_user_can_delete_single_reply PASSED                                                                      [ 43%]
tests/test_journalist_api.py::test_authorized_user_can_delete_source_collection PASSED                                                                 [ 44%]
tests/test_journalist_api.py::test_authorized_user_can_download_submission PASSED                                                                      [ 44%]
tests/test_journalist_api.py::test_authorized_user_can_download_reply PASSED                                                                           [ 44%]
tests/test_journalist_api.py::test_authorized_user_can_get_current_user_endpoint PASSED                                                                [ 44%]
tests/test_journalist_api.py::test_request_with_missing_auth_header_triggers_403 PASSED                                                                [ 44%]
tests/test_journalist_api.py::test_request_with_auth_header_but_no_token_triggers_403 PASSED                                                           [ 45%]
tests/test_journalist_api.py::test_unencrypted_replies_get_rejected PASSED                                                                             [ 45%]
tests/test_journalist_api.py::test_authorized_user_can_add_reply PASSED                                                                                [ 45%]
tests/test_journalist_api.py::test_reply_without_content_400 PASSED                                                                                    [ 45%]
tests/test_journalist_api.py::test_reply_without_reply_field_400 PASSED                                                                                [ 45%]
tests/test_journalist_api.py::test_reply_without_json_400 PASSED                                                                                       [ 46%]
tests/test_journalist_api.py::test_reply_with_valid_curly_json_400 PASSED                                                                              [ 46%]
tests/test_journalist_api.py::test_reply_with_valid_square_json_400 PASSED                                                                             [ 46%]
tests/test_journalist_api.py::test_malformed_json_400 PASSED                                                                                           [ 46%]
tests/test_journalist_api.py::test_empty_json_400 PASSED                                                                                               [ 46%]
tests/test_journalist_api.py::test_empty_json_20X PASSED                                                                                               [ 47%]
tests/test_manage.py::test_parse_args PASSED                                                                                                           [ 47%]
tests/test_manage.py::test_not_verbose PASSED                                                                                                          [ 47%]
tests/test_manage.py::test_verbose PASSED                                                                                                              [ 47%]
tests/test_manage.py::test_get_username_success PASSED                                                                                                 [ 47%]
tests/test_manage.py::test_get_username_fail PASSED                                                                                                    [ 48%]
tests/test_manage.py::test_get_yubikey_usage_yes PASSED                                                                                                [ 48%]
tests/test_manage.py::test_get_yubikey_usage_no PASSED                                                                                                 [ 48%]
tests/test_manage.py::test_handle_invalid_secret PASSED                                                                                                [ 48%]
tests/test_manage.py::test_exception_handling_when_duplicate_username PASSED                                                                           [ 48%]
tests/test_manage.py::test_delete_user PASSED                                                                                                          [ 49%]
tests/test_manage.py::test_delete_non_existent_user PASSED                                                                                             [ 49%]
tests/test_manage.py::test_get_username_to_delete PASSED                                                                                               [ 49%]
tests/test_manage.py::test_reset PASSED                                                                                                                [ 49%]
tests/test_manage.py::test_get_username PASSED                                                                                                         [ 50%]
tests/test_manage.py::test_clean_tmp_do_nothing PASSED                                                                                                 [ 50%]
tests/test_manage.py::test_clean_tmp_too_young PASSED                                                                                                  [ 50%]
tests/test_manage.py::test_clean_tmp_removed PASSED                                                                                                    [ 50%]
tests/test_manage.py::test_were_there_submissions_today PASSED                                                                                         [ 50%]
tests/test_qa_loader.py::test_load_data PASSED                                                                                                         [ 51%]
tests/test_secure_tempfile.py::test_read_before_writing PASSED                                                                                         [ 51%]
tests/test_secure_tempfile.py::test_write_then_read_once PASSED                                                                                        [ 51%]
tests/test_secure_tempfile.py::test_write_twice_then_read_once PASSED                                                                                  [ 51%]
tests/test_secure_tempfile.py::test_write_then_read_twice PASSED                                                                                       [ 51%]
tests/test_secure_tempfile.py::test_write_then_read_then_write PASSED                                                                                  [ 52%]
tests/test_secure_tempfile.py::test_read_write_unicode PASSED                                                                                          [ 52%]
tests/test_secure_tempfile.py::test_file_seems_encrypted PASSED                                                                                        [ 52%]
tests/test_secure_tempfile.py::test_file_is_removed_from_disk PASSED                                                                                   [ 52%]
tests/test_secure_tempfile.py::test_SecureTemporaryFile_is_a_STREAMLIKE_TYPE PASSED                                                                    [ 52%]
tests/test_secure_tempfile.py::test_buffered_read PASSED                                                                                               [ 53%]
tests/test_secure_tempfile.py::test_tmp_file_id_omits_invalid_chars PASSED                                                                             [ 53%]
tests/test_source.py::test_page_not_found PASSED                                                                                                       [ 53%]
tests/test_source.py::test_index PASSED                                                                                                                [ 53%]
tests/test_source.py::test_all_words_in_wordlist_validate PASSED                                                                                       [ 53%]
tests/test_source.py::test_generate PASSED                                                                                                             [ 54%]
tests/test_source.py::test_generate_already_logged_in PASSED                                                                                           [ 54%]
tests/test_source.py::test_create_new_source PASSED                                                                                                    [ 54%]
tests/test_source.py::test_generate_too_long_codename PASSED                                                                                           [ 54%]
tests/test_source.py::test_create_duplicate_codename PASSED                                                                                            [ 54%]
tests/test_source.py::test_lookup PASSED                                                                                                               [ 55%]
tests/test_source.py::test_login_and_logout PASSED                                                                                                     [ 55%]
tests/test_source.py::test_user_must_log_in_for_protected_views PASSED                                                                                 [ 55%]
tests/test_source.py::test_login_with_whitespace PASSED                                                                                                [ 55%]
tests/test_source.py::test_initial_submission_notification PASSED                                                                                      [ 55%]
tests/test_source.py::test_submit_message PASSED                                                                                                       [ 56%]
tests/test_source.py::test_submit_empty_message PASSED                                                                                                 [ 56%]
tests/test_source.py::test_submit_big_message PASSED                                                                                                   [ 56%]
tests/test_source.py::test_submit_file PASSED                                                                                                          [ 56%]
tests/test_source.py::test_submit_both PASSED                                                                                                          [ 56%]
tests/test_source.py::test_submit_message_with_low_entropy PASSED                                                                                      [ 57%]
tests/test_source.py::test_submit_message_with_enough_entropy PASSED                                                                                   [ 57%]
tests/test_source.py::test_delete_all_successfully_deletes_replies PASSED                                                                              [ 57%]
tests/test_source.py::test_delete_all_replies_deleted_by_source_but_not_journalist PASSED                                                              [ 57%]
tests/test_source.py::test_delete_all_replies_already_deleted_by_journalists PASSED                                                                    [ 57%]
tests/test_source.py::test_submit_sanitizes_filename PASSED                                                                                            [ 58%]
tests/test_source.py::test_tor2web_warning_headers PASSED                                                                                              [ 58%]
tests/test_source.py::test_tor2web_warning PASSED                                                                                                      [ 58%]
tests/test_source.py::test_why_use_tor_browser PASSED                                                                                                  [ 58%]
tests/test_source.py::test_why_journalist_key PASSED                                                                                                   [ 58%]
tests/test_source.py::test_metadata_route PASSED                                                                                                       [ 59%]
tests/test_source.py::test_login_with_overly_long_codename PASSED                                                                                      [ 59%]
tests/test_source.py::test_failed_normalize_timestamps_logs_warning PASSED                                                                             [ 59%]
tests/test_source.py::test_source_is_deleted_while_logged_in PASSED                                                                                    [ 59%]
tests/test_source.py::test_login_with_invalid_codename PASSED                                                                                          [ 59%]
tests/test_source.py::test_source_session_expiration PASSED                                                                                            [ 60%]
tests/test_source.py::test_csrf_error_page PASSED                                                                                                      [ 60%]
tests/test_store.py::test_path_returns_filename_of_folder PASSED                                                                                       [ 60%]
tests/test_store.py::test_path_returns_filename_of_items_within_folder PASSED                                                                          [ 60%]
tests/test_store.py::test_verify_path_not_absolute PASSED                                                                                              [ 60%]
tests/test_store.py::test_verify_in_store_dir PASSED                                                                                                   [ 61%]
tests/test_store.py::test_verify_store_path_not_absolute PASSED                                                                                        [ 61%]
tests/test_store.py::test_verify_store_dir_not_absolute PASSED                                                                                         [ 61%]
tests/test_store.py::test_verify_store_temp_dir_not_absolute PASSED                                                                                    [ 61%]
tests/test_store.py::test_verify_flagged_file_in_sourcedir_returns_true PASSED                                                                         [ 61%]
tests/test_store.py::test_verify_invalid_file_extension_in_sourcedir_raises_exception PASSED                                                           [ 62%]
tests/test_store.py::test_verify_invalid_filename_in_sourcedir_raises_exception PASSED                                                                 [ 62%]
tests/test_store.py::test_get_zip PASSED                                                                                                               [ 62%]
tests/test_store.py::test_rename_valid_submission PASSED                                                                                               [ 62%]
tests/test_store.py::test_rename_submission_with_invalid_filename PASSED                                                                               [ 63%]
tests/test_template_filters.py::test_source_filters PASSED                                                                                             [ 63%]
tests/test_template_filters.py::test_journalist_filters PASSED                                                                                         [ 63%]
tests/functional/test_admin_interface.py::TestAdminInterface::test_admin_interface PASSED                                                              [ 63%]
tests/functional/test_admin_interface.py::TestAdminInterface::test_admin_edits_hotp_secret PASSED                                                      [ 63%]
tests/functional/test_admin_interface.py::TestAdminInterface::test_admin_deletes_user PASSED                                                           [ 64%]
tests/functional/test_admin_interface.py::TestAdminInterface::test_admin_updates_image PASSED                                                          [ 64%]
tests/functional/test_admin_interface.py::TestAdminInterface::test_ossec_alert_button PASSED                                                           [ 64%]
tests/functional/test_admin_interface.py::TestAdminInterface::test_admin_adds_admin_user PASSED                                                        [ 64%]
tests/functional/test_journalist.py::TestJournalist::test_journalist_verifies_deletion_of_one_submission_modal PASSED                                  [ 64%]
tests/functional/test_journalist.py::TestJournalist::test_journalist_uses_col_delete_collection_button_modal PASSED                                    [ 65%]
tests/functional/test_journalist.py::TestJournalist::test_journalist_uses_index_delete_collections_button_modal PASSED                                 [ 65%]
tests/functional/test_journalist.py::TestJournalist::test_journalist_interface_ui_with_modal PASSED                                                    [ 65%]
tests/functional/test_make_account_changes.py::TestMakeAccountChanges::test_admin_edit_account_html_template_rendering PASSED                          [ 65%]
tests/functional/test_source.py::TestSourceInterface::test_lookup_codename_hint PASSED                                                                 [ 65%]
tests/functional/test_source_notfound.py::TestSourceInterfaceNotFound::test_not_found PASSED                                                           [ 66%]
tests/functional/test_source_session_timeout.py::TestSourceSessions::test_source_session_timeout PASSED                                                [ 66%]
tests/functional/test_source_warnings.py::TestSourceInterfaceBannerWarnings::test_warning_appears_if_tor_browser_not_in_use xfail                      [ 66%]
tests/functional/test_source_warnings.py::TestSourceInterfaceBannerWarnings::test_warning_appears_if_orbot_is_used PASSED                              [ 66%]
tests/functional/test_source_warnings.py::TestSourceInterfaceBannerWarnings::test_warning_high_security PASSED                                         [ 66%]
tests/functional/test_submit_and_retrieve_file.py::TestSubmitAndRetrieveFile::test_submit_and_retrieve_happy_path PASSED                               [ 67%]
tests/functional/test_submit_and_retrieve_file.py::TestSubmitAndRetrieveFile::test_source_cancels_at_login_page PASSED                                 [ 67%]
tests/functional/test_submit_and_retrieve_file.py::TestSubmitAndRetrieveFile::test_source_cancels_at_submit_page PASSED                                [ 67%]
tests/functional/test_submit_and_retrieve_message.py::TestSubmitAndRetrieveMessage::test_submit_and_retrieve_happy_path PASSED                         [ 67%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_edit_hotp_secret[en_US] PASSED                                                [ 67%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_edit_hotp_secret[ar] PASSED                                                   [ 68%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_edit_hotp_secret[fr_FR] PASSED                                                [ 68%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_new_two_factor_hotp[en_US] PASSED                                             [ 68%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_new_two_factor_hotp[ar] PASSED                                                [ 68%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_new_two_factor_hotp[fr_FR] PASSED                                             [ 68%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_new_two_factor_totp[en_US] PASSED                                             [ 69%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_new_two_factor_totp[ar] PASSED                                                [ 69%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_account_new_two_factor_totp[fr_FR] PASSED                                             [ 69%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_add_user_hotp[en_US] PASSED                                                     [ 69%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_add_user_hotp[ar] PASSED                                                        [ 69%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_add_user_hotp[fr_FR] PASSED                                                     [ 70%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_add_user_totp[en_US] PASSED                                                     [ 70%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_add_user_totp[ar] PASSED                                                        [ 70%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_add_user_totp[fr_FR] PASSED                                                     [ 70%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_edit_hotp_secret[en_US] PASSED                                                  [ 70%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_edit_hotp_secret[ar] PASSED                                                     [ 71%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_edit_hotp_secret[fr_FR] PASSED                                                  [ 71%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_edit_totp_secret[en_US] PASSED                                                  [ 71%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_edit_totp_secret[ar] PASSED                                                     [ 71%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_edit_totp_secret[fr_FR] PASSED                                                  [ 71%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_login[en_US] PASSED                                                                   [ 72%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_login[ar] PASSED                                                                      [ 72%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_login[fr_FR] PASSED                                                                   [ 72%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin[en_US] PASSED                                                                   [ 72%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin[ar] PASSED                                                                      [ 72%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin[fr_FR] PASSED                                                                   [ 73%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_new_user_two_factor_hotp[en_US] PASSED                                          [ 73%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_new_user_two_factor_hotp[ar] PASSED                                             [ 73%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_new_user_two_factor_hotp[fr_FR] PASSED                                          [ 73%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_new_user_two_factor_totp[en_US] PASSED                                          [ 73%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_new_user_two_factor_totp[ar] PASSED                                             [ 74%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_new_user_two_factor_totp[fr_FR] PASSED                                          [ 74%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_changes_logo[en_US] PASSED                                                      [ 74%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_changes_logo[ar] PASSED                                                         [ 74%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_changes_logo[fr_FR] PASSED                                                      [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_no_documents[en_US] PASSED                                                        [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_no_documents[ar] PASSED                                                           [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_no_documents[fr_FR] PASSED                                                        [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_has_no_key[en_US] PASSED                                                          [ 75%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_has_no_key[ar] PASSED                                                             [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_has_no_key[fr_FR] PASSED                                                          [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_flagged[en_US] PASSED                                                             [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_flagged[ar] PASSED                                                                [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_flagged[fr_FR] PASSED                                                             [ 76%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col[en_US] PASSED                                                                     [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col[ar] PASSED                                                                        [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col[fr_FR] PASSED                                                                     [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_javascript[en_US] PASSED                                                          [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_javascript[ar] PASSED                                                             [ 77%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_col_javascript[fr_FR] PASSED                                                          [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_journalist_composes_reply[en_US] PASSED                                               [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_journalist_composes_reply[ar] PASSED                                                  [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_journalist_composes_reply[fr_FR] PASSED                                               [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_uses_ossec_alert_button[en_US] PASSED                                           [ 78%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_uses_ossec_alert_button[ar] PASSED                                              [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_uses_ossec_alert_button[fr_FR] PASSED                                           [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_none[en_US] PASSED                                                             [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_none[ar] PASSED                                                                [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_none[fr_FR] PASSED                                                             [ 79%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one_confirmation[en_US] PASSED                                                 [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one_confirmation[ar] PASSED                                                    [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one_confirmation[fr_FR] PASSED                                                 [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all_confirmation[en_US] PASSED                                                 [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all_confirmation[ar] PASSED                                                    [ 80%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all_confirmation[fr_FR] PASSED                                                 [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one[en_US] PASSED                                                              [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one[ar] PASSED                                                                 [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_one[fr_FR] PASSED                                                              [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all[en_US] PASSED                                                              [ 81%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all[ar] PASSED                                                                 [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all[fr_FR] PASSED                                                              [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_user[en_US] PASSED                                                       [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_user[ar] PASSED                                                          [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_user[fr_FR] PASSED                                                       [ 82%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_admin[en_US] PASSED                                                      [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_admin[ar] PASSED                                                         [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_edit_account_admin[fr_FR] PASSED                                                      [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents_admin[en_US] PASSED                                                [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents_admin[ar] PASSED                                                   [ 83%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents_admin[fr_FR] PASSED                                                [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_interface_index[en_US] PASSED                                                   [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_interface_index[ar] PASSED                                                      [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_admin_interface_index[fr_FR] PASSED                                                   [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_flag[en_US] PASSED                                                                    [ 84%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_flag[ar] PASSED                                                                       [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_flag[fr_FR] PASSED                                                                    [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents[en_US] PASSED                                                      [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents[ar] PASSED                                                         [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_no_documents[fr_FR] PASSED                                                      [ 85%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index[en_US] PASSED                                                                   [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index[ar] FAILED                                                                      [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index[fr_FR] PASSED                                                                   [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_javascript[en_US] PASSED                                                        [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_javascript[ar] FAILED                                                           [ 86%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_javascript[fr_FR] PASSED                                                        [ 87%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_entered_text[en_US] PASSED                                                      [ 87%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_entered_text[ar] PASSED                                                         [ 87%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_index_entered_text[fr_FR] PASSED                                                      [ 87%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_to_visit_admin[en_US] PASSED                                                     [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_to_visit_admin[ar] PASSED                                                        [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_to_visit_admin[fr_FR] PASSED                                                     [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login[en_US] PASSED                                                              [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login[ar] PASSED                                                                 [ 88%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login[fr_FR] PASSED                                                              [ 89%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login_many[en_US] PASSED                                                         [ 89%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login_many[ar] PASSED                                                            [ 89%]
tests/pageslayout/test_journalist.py::TestJournalistLayout::test_fail_login_many[fr_FR] PASSED                                                         [ 89%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index[en_US] PASSED                                                                           [ 89%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index[ar] PASSED                                                                              [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index[fr_FR] PASSED                                                                           [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index_javascript[en_US] PASSED                                                                [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index_javascript[ar] PASSED                                                                   [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_index_javascript[fr_FR] PASSED                                                                [ 90%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup[en_US] PASSED                                                                          [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup[ar] PASSED                                                                             [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup[fr_FR] PASSED                                                                          [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup_shows_codename[en_US] PASSED                                                           [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup_shows_codename[ar] PASSED                                                              [ 91%]
tests/pageslayout/test_source.py::TestSourceLayout::test_lookup_shows_codename[fr_FR] PASSED                                                           [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_login[en_US] PASSED                                                                           [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_login[ar] PASSED                                                                              [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_login[fr_FR] PASSED                                                                           [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_enters_text_in_login_form[en_US] PASSED                                                       [ 92%]
tests/pageslayout/test_source.py::TestSourceLayout::test_enters_text_in_login_form[ar] PASSED                                                          [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_enters_text_in_login_form[fr_FR] PASSED                                                       [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_use_tor_browser[en_US] PASSED                                                                 [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_use_tor_browser[ar] PASSED                                                                    [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_use_tor_browser[fr_FR] PASSED                                                                 [ 93%]
tests/pageslayout/test_source.py::TestSourceLayout::test_generate[en_US] PASSED                                                                        [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_generate[ar] PASSED                                                                           [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_generate[fr_FR] PASSED                                                                        [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_logout_flashed_message[en_US] PASSED                                                          [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_logout_flashed_message[ar] PASSED                                                             [ 94%]
tests/pageslayout/test_source.py::TestSourceLayout::test_logout_flashed_message[fr_FR] PASSED                                                          [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_submission_entered_text[en_US] PASSED                                                         [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_submission_entered_text[ar] PASSED                                                            [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_submission_entered_text[fr_FR] PASSED                                                         [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_next_submission_flashed_message[en_US] PASSED                                                 [ 95%]
tests/pageslayout/test_source.py::TestSourceLayout::test_next_submission_flashed_message[ar] PASSED                                                    [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_next_submission_flashed_message[fr_FR] PASSED                                                 [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_checks_for_reply[en_US] PASSED                                                         [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_checks_for_reply[ar] PASSED                                                            [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_checks_for_reply[fr_FR] PASSED                                                         [ 96%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_flagged[en_US] PASSED                                                                  [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_flagged[ar] PASSED                                                                     [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_source_flagged[fr_FR] PASSED                                                                  [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_notfound[en_US] PASSED                                                                        [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_notfound[ar] PASSED                                                                           [ 97%]
tests/pageslayout/test_source.py::TestSourceLayout::test_notfound[fr_FR] PASSED                                                                        [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_tor2web_warning[en_US] PASSED                                                                 [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_tor2web_warning[ar] PASSED                                                                    [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_tor2web_warning[fr_FR] PASSED                                                                 [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_why_journalist_key[en_US] PASSED                                                              [ 98%]
tests/pageslayout/test_source.py::TestSourceLayout::test_why_journalist_key[ar] PASSED                                                                 [ 99%]
tests/pageslayout/test_source.py::TestSourceLayout::test_why_journalist_key[fr_FR] PASSED                                                              [ 99%]
tests/pageslayout/test_source.py::TestSourceSessionLayout::test_source_session_timeout[en_US] PASSED                                                   [ 99%]
tests/pageslayout/test_source.py::TestSourceSessionLayout::test_source_session_timeout[ar] PASSED                                                      [ 99%]
tests/pageslayout/test_source.py::TestSourceSessionLayout::test_source_session_timeout[fr_FR] PASSED                                                   [100%]Coverage.py warning: Couldn't read data from '/home/kdas/code/securedrop/securedrop/.coverage.0be8308f48f6.62.544608': ValueError: Expecting object: line 1 column 9 (char 8)
Coverage.py warning: Couldn't read data from '/home/kdas/code/securedrop/securedrop/.coverage.0be8308f48f6.60.367389': CoverageException: Doesn't seem to be a coverage.py data file


------------------------------------------------------ generated xml file: /tmp/test-results/junit.xml -------------------------------------------------------

---------- coverage: platform linux2, python 2.7.6-final-0 -----------
Name                                                                       Stmts   Miss Branch BrPart  Cover   Missing
----------------------------------------------------------------------------------------------------------------------
alembic/versions/15ac9509fc68_init.py                                         20     12      0      0    40%   20-70, 82-87
alembic/versions/2d0ce3ee5bdc_added_passphrase_hash_column_to_.py             14      6      0      0    57%   20, 27-53
alembic/versions/3d91d6948753_create_source_uuid_column.py                    22     11      2      0    46%   23-64, 68-69
alembic/versions/6db892e17271_add_reply_uuid.py                               20     11      2      0    41%   22-63, 67-68
alembic/versions/e0a525cbab83_add_column_to_track_source_deletion_of_.py      19     11      2      0    38%   21-60, 64-65
alembic/versions/f2833ac34bb6_add_uuid_column_for_users_table.py              21     12      2      0    39%   22-69, 73-74
alembic/versions/faac8092c123_enable_security_pragmas.py                      12      4      0      0    67%   20-22, 26
alembic/versions/fccf57ceef02_create_submission_uuid_column.py                20     11      2      0    41%   22-60, 64-65
config.py                                                                     41      3      6      3    87%   52, 55-58, 50->52, 53->55, 59->69
create-dev-data.py                                                            58     58      8      0     0%   3-106
crypto_util.py                                                               103      2     36      2    97%   22, 86, 17->22, 85->86
db.py                                                                          2      0      0      0   100%
i18n.py                                                                       78      2     38      2    97%   55, 162, 54->55, 161->162
i18n_tool.py                                                                 188      5     54      6    95%   67, 116-117, 121, 357, 66->67, 112->121, 114->116, 201->205, 241->243, 353->357
journalist.py                                                                  3      0      0      0   100%
journalist_app/__init__.py                                                    86      4     22      3    94%   30, 51, 103-105, 25->30, 47->51, 102->103
journalist_app/account.py                                                     44      1     10      2    94%   69, 39->50, 62->69
journalist_app/admin.py                                                      150     17     38      2    90%   39-40, 76-77, 157-159, 163, 188-189, 221-228, 75->76, 162->163
journalist_app/api.py                                                        179      2     44      6    96%   50, 219, 47->50, 129->exit, 199->exit, 215->exit, 218->219, 257->exit
journalist_app/col.py                                                         49      5      8      3    86%   56-57, 74, 82-83, 55->56, 73->74, 77->86
journalist_app/decorators.py                                                  11      0      2      0   100%
journalist_app/forms.py                                                       23      0      4      0   100%
journalist_app/main.py                                                        98     23     30      2    73%   50-54, 148-154, 164, 168-183, 187-196, 147->148, 161->164
journalist_app/utils.py                                                      163     14     36      7    89%   27, 47-53, 108-109, 202, 211-213, 236, 312-314, 22->27, 43->exit, 103->111, 201->202, 210->211, 235->236, 311->312
manage.py                                                                    226     39     36      9    81%   45, 54-56, 60-61, 74-75, 90-91, 94-99, 104, 108, 132, 141-142, 182-183, 212-218, 233, 239-249, 277-281, 289, 44->45, 70->74, 93->94, 129->132, 160->167, 167->156, 179->182, 232->233, 285->289
management/__init__.py                                                         0      0      0      0   100%
management/run.py                                                             14      6      2      0    50%   17-43
models.py                                                                    306     15     64      7    92%   16-17, 259-262, 305-308, 402, 451, 458, 512, 540-541, 32->35, 94->91, 401->402, 448->451, 455->458, 505->512, 508->505
qa_loader.py                                                                 146     18     38      4    87%   35, 103, 146, 182-185, 225-231, 235-237, 241-245, 34->35, 102->103, 145->146, 240->241
request_that_secures_file_uploads.py                                          10      1      2      1    83%   27, 20->27
rm.py                                                                          4      2      0      0    50%   23-24
sdconfig.py                                                                  119     47      2      1    60%   12, 21-22, 27-28, 32-33, 57-58, 62-63, 67-68, 72-73, 77-78, 82-83, 87-88, 92-93, 97-98, 102-103, 107-108, 112-113, 118-119, 124-125, 129-130, 135-136, 140-141, 145-146, 150-151, 160-161, 7->12
secure_tempfile.py                                                            51      0     10      0   100%
source.py                                                                      3      0      0      0   100%
source_app/__init__.py                                                        89      4     14      3    93%   31, 52, 94-96, 26->31, 48->52, 93->94
source_app/api.py                                                             11      0      0      0   100%
source_app/decorators.py                                                      15      1      4      1    89%   22, 21->22
source_app/forms.py                                                            7      0      0      0   100%
source_app/info.py                                                            14      0      0      0   100%
source_app/main.py                                                           144      5     38      1    96%   44-48, 92-93, 260->270
source_app/utils.py                                                           57      5      8      1    91%   24-28, 91-92, 59->36
store.py                                                                      95      0     30      2    98%   182->196, 184->196
template_filters.py                                                           26      0      6      1    97%   22->24
version.py                                                                     1      0      0      0   100%
worker.py                                                                      7      0      0      0   100%
----------------------------------------------------------------------------------------------------------------------
TOTAL                                                                       2769    357    600     69    86%
Coverage annotated source written to dir /tmp/test-results/cov_annotate
Coverage HTML written to dir /tmp/test-results/cov_html
Coverage XML written to file /tmp/test-results/cov.xml

================================================================= slowest 10 test durations ==================================================================
50.22s call     functional/test_make_account_changes.py::TestMakeAccountChanges::test_admin_edit_account_html_template_rendering
45.74s call     functional/test_submit_and_retrieve_file.py::TestSubmitAndRetrieveFile::test_submit_and_retrieve_happy_path
42.98s call     functional/test_source.py::TestSourceInterface::test_lookup_codename_hint
41.06s call     functional/test_journalist.py::TestJournalist::test_journalist_verifies_deletion_of_one_submission_modal
36.26s call     functional/test_journalist.py::TestJournalist::test_journalist_uses_index_delete_collections_button_modal
30.65s call     test_i18n_tool.py::TestI18NTool::test_update_from_weblate
26.95s call     test_alembic.py::test_downgrade_with_data[15ac9509fc68]
25.78s call     functional/test_journalist.py::TestJournalist::test_journalist_uses_col_delete_collection_button_modal
24.38s call     functional/test_admin_interface.py::TestAdminInterface::test_admin_interface
16.91s call     pageslayout/test_journalist.py::TestJournalistLayout::test_delete_all_confirmation[fr_FR]
========================================================================== FAILURES ==========================================================================
____________________________________________________________ TestJournalistLayout.test_index[ar] _____________________________________________________________

self = <tests.pageslayout.test_journalist.TestJournalistLayout object at 0x7fc16aa6e3d0>

    def test_index(self):
        self._source_visits_source_homepage()
>       self._source_chooses_to_submit_documents()

/home/kdas/code/securedrop/securedrop/tests/pageslayout/test_journalist.py:309: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 
/home/kdas/code/securedrop/securedrop/tests/functional/source_navigation_steps.py:48: in _source_chooses_to_submit_documents
    self._source_clicks_submit_documents_on_homepage()
/home/kdas/code/securedrop/securedrop/tests/functional/source_navigation_steps.py:41: in _source_clicks_submit_documents_on_homepage
    submit_button_hover_icon).perform()
/usr/local/lib/python2.7/dist-packages/selenium/webdriver/common/action_chains.py:80: in perform
    self.w3c_actions.perform()
/usr/local/lib/python2.7/dist-packages/selenium/webdriver/common/actions/action_builder.py:76: in perform
    self.driver.execute(Command.W3C_ACTIONS, enc)
/usr/local/lib/python2.7/dist-packages/selenium/webdriver/remote/webdriver.py:320: in execute
    self.error_handler.check_response(response)
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 

self = <selenium.webdriver.remote.errorhandler.ErrorHandler object at 0x7fc16a333890>
response = {'status': 500, 'value': '{"value":{"error":"unknown error","message":"TypeError: rect is undefined","stacktrace":"ele...</req<@chrome://marionette/content/listener.js:491:14\ndispatch/<@chrome://marionette/content/listener.js:484:15\n"}}'}

    def check_response(self, response):
        """
            Checks that a JSON response from the WebDriver does not have an error.
    
            :Args:
             - response - The JSON response from the WebDriver server as a dictionary
               object.
    
            :Raises: If the response contains an error message.
            """
        status = response.get('status', None)
        if status is None or status == ErrorCode.SUCCESS:
            return
        value = None
        message = response.get("message", "")
        screen = response.get("screen", "")
        stacktrace = None
        if isinstance(status, int):
            value_json = response.get('value', None)
            if value_json and isinstance(value_json, basestring):
                import json
                try:
                    value = json.loads(value_json)
                    if len(value.keys()) == 1:
                        value = value['value']
                    status = value.get('error', None)
                    if status is None:
                        status = value["status"]
                        message = value["value"]
                        if not isinstance(message, basestring):
                            value = message
                            message = message.get('message')
                    else:
                        message = value.get('message', None)
                except ValueError:
                    pass
    
        exception_class = ErrorInResponseException
        if status in ErrorCode.NO_SUCH_ELEMENT:
            exception_class = NoSuchElementException
        elif status in ErrorCode.NO_SUCH_FRAME:
            exception_class = NoSuchFrameException
        elif status in ErrorCode.NO_SUCH_WINDOW:
            exception_class = NoSuchWindowException
        elif status in ErrorCode.STALE_ELEMENT_REFERENCE:
            exception_class = StaleElementReferenceException
        elif status in ErrorCode.ELEMENT_NOT_VISIBLE:
            exception_class = ElementNotVisibleException
        elif status in ErrorCode.INVALID_ELEMENT_STATE:
            exception_class = InvalidElementStateException
        elif status in ErrorCode.INVALID_SELECTOR \
                or status in ErrorCode.INVALID_XPATH_SELECTOR \
                or status in ErrorCode.INVALID_XPATH_SELECTOR_RETURN_TYPER:
            exception_class = InvalidSelectorException
        elif status in ErrorCode.ELEMENT_IS_NOT_SELECTABLE:
            exception_class = ElementNotSelectableException
        elif status in ErrorCode.ELEMENT_NOT_INTERACTABLE:
            exception_class = ElementNotInteractableException
        elif status in ErrorCode.INVALID_COOKIE_DOMAIN:
            exception_class = InvalidCookieDomainException
        elif status in ErrorCode.UNABLE_TO_SET_COOKIE:
            exception_class = UnableToSetCookieException
        elif status in ErrorCode.TIMEOUT:
            exception_class = TimeoutException
        elif status in ErrorCode.SCRIPT_TIMEOUT:
            exception_class = TimeoutException
        elif status in ErrorCode.UNKNOWN_ERROR:
            exception_class = WebDriverException
        elif status in ErrorCode.UNEXPECTED_ALERT_OPEN:
            exception_class = UnexpectedAlertPresentException
        elif status in ErrorCode.NO_ALERT_OPEN:
            exception_class = NoAlertPresentException
        elif status in ErrorCode.IME_NOT_AVAILABLE:
            exception_class = ImeNotAvailableException
        elif status in ErrorCode.IME_ENGINE_ACTIVATION_FAILED:
            exception_class = ImeActivationFailedException
        elif status in ErrorCode.MOVE_TARGET_OUT_OF_BOUNDS:
            exception_class = MoveTargetOutOfBoundsException
        elif status in ErrorCode.JAVASCRIPT_ERROR:
            exception_class = JavascriptException
        elif status in ErrorCode.SESSION_NOT_CREATED:
            exception_class = SessionNotCreatedException
        elif status in ErrorCode.INVALID_ARGUMENT:
            exception_class = InvalidArgumentException
        elif status in ErrorCode.NO_SUCH_COOKIE:
            exception_class = NoSuchCookieException
        elif status in ErrorCode.UNABLE_TO_CAPTURE_SCREEN:
            exception_class = ScreenshotException
        elif status in ErrorCode.ELEMENT_CLICK_INTERCEPTED:
            exception_class = ElementClickInterceptedException
        elif status in ErrorCode.INSECURE_CERTIFICATE:
            exception_class = InsecureCertificateException
        elif status in ErrorCode.INVALID_COORDINATES:
            exception_class = InvalidCoordinatesException
        elif status in ErrorCode.INVALID_SESSION_ID:
            exception_class = InvalidSessionIdException
        elif status in ErrorCode.UNKNOWN_METHOD:
            exception_class = UnknownMethodException
        else:
            exception_class = WebDriverException
        if value == '' or value is None:
            value = response['value']
        if isinstance(value, basestring):
            if exception_class == ErrorInResponseException:
                raise exception_class(response, value)
            raise exception_class(value)
        if message == "" and 'message' in value:
            message = value['message']
    
        screen = None
        if 'screen' in value:
            screen = value['screen']
    
        stacktrace = None
        if 'stackTrace' in value and value['stackTrace']:
            stacktrace = []
            try:
                for frame in value['stackTrace']:
                    line = self._value_or_default(frame, 'lineNumber', '')
                    file = self._value_or_default(frame, 'fileName', '<anonymous>')
                    if line:
                        file = "%s:%s" % (file, line)
                    meth = self._value_or_default(frame, 'methodName', '<anonymous>')
                    if 'className' in frame:
                        meth = "%s.%s" % (frame['className'], meth)
                    msg = "    at %s (%s)"
                    msg = msg % (meth, file)
                    stacktrace.append(msg)
            except TypeError:
                pass
        if exception_class == ErrorInResponseException:
            raise exception_class(response, message)
        elif exception_class == UnexpectedAlertPresentException:
            alert_text = None
            if 'data' in value:
                alert_text = value['data'].get('text')
            elif 'alert' in value:
                alert_text = value['alert'].get('text')
            raise exception_class(message, screen, stacktrace, alert_text)
>       raise exception_class(message, screen, stacktrace)
E       WebDriverException: Message: TypeError: rect is undefined

/usr/local/lib/python2.7/dist-packages/selenium/webdriver/remote/errorhandler.py:242: WebDriverException
------------------------------------------------------------------- Captured stdout setup --------------------------------------------------------------------
 * Serving Flask app "source_app" (lazy loading)
 * Environment: production
   WARNING: Do not use the development server in a production environment.
   Use a production WSGI server instead.
 * Debug mode: on
 * Serving Flask app "journalist_app" (lazy loading)
 * Environment: production
   WARNING: Do not use the development server in a production environment.
   Use a production WSGI server instead.
 * Debug mode: on
------------------------------------------------------------------- Captured stderr setup --------------------------------------------------------------------
2018-11-27 12:28:27,051 DEBUG Starting new HTTP connection (1): 127.0.0.1:60101
2018-11-27 12:28:27,058 INFO  * Running on http://127.0.0.1:60101/ (Press CTRL+C to quit)
2018-11-27 12:28:27,085 INFO  * Running on http://127.0.0.1:50527/ (Press CTRL+C to quit)
2018-11-27 12:28:28,056 DEBUG Starting new HTTP connection (1): 127.0.0.1:60101
2018-11-27 12:28:28,118 INFO 127.0.0.1 - - [27/Nov/2018 12:28:28] "GET / HTTP/1.1" 200 -
2018-11-27 12:28:28,119 DEBUG http://127.0.0.1:60101 "GET / HTTP/1.1" 200 5035
2018-11-27 12:28:28,121 DEBUG Starting new HTTP connection (1): 127.0.0.1:50527
2018-11-27 12:28:28,129 INFO 127.0.0.1 - - [27/Nov/2018 12:28:28] "GET / HTTP/1.1" 302 -
2018-11-27 12:28:28,129 DEBUG http://127.0.0.1:50527 "GET / HTTP/1.1" 302 219
2018-11-27 12:28:28,132 DEBUG Resetting dropped connection: 127.0.0.1
2018-11-27 12:28:28,178 INFO 127.0.0.1 - - [27/Nov/2018 12:28:28] "GET /login HTTP/1.1" 200 -
2018-11-27 12:28:28,179 DEBUG http://127.0.0.1:50527 "GET /login HTTP/1.1" 200 2685
--------------------------------------------------------------------- Captured log setup ---------------------------------------------------------------------
connectionpool.py          205 DEBUG    Starting new HTTP connection (1): 127.0.0.1:60101
connectionpool.py          205 DEBUG    Starting new HTTP connection (1): 127.0.0.1:60101
connectionpool.py          393 DEBUG    http://127.0.0.1:60101 "GET / HTTP/1.1" 200 5035
connectionpool.py          205 DEBUG    Starting new HTTP connection (1): 127.0.0.1:50527
connectionpool.py          393 DEBUG    http://127.0.0.1:50527 "GET / HTTP/1.1" 302 219
connectionpool.py          240 DEBUG    Resetting dropped connection: 127.0.0.1
connectionpool.py          393 DEBUG    http://127.0.0.1:50527 "GET /login HTTP/1.1" 200 2685
-------------------------------------------------------------------- Captured stderr call --------------------------------------------------------------------
2018-11-27 12:28:31,631 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET / HTTP/1.1" 200 -
2018-11-27 12:28:31,695 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/css/source.css HTTP/1.1" 200 -
2018-11-27 12:28:31,721 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /org-logo HTTP/1.1" 302 -
2018-11-27 12:28:31,726 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/font-awesome/times-white.png HTTP/1.1" 200 -
2018-11-27 12:28:31,731 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/font-awesome/cloud-upload-blue.png HTTP/1.1" 200 -
2018-11-27 12:28:31,731 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/font-awesome/cloud-upload-white.png HTTP/1.1" 200 -
2018-11-27 12:28:31,743 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/font-awesome/comments-white.png HTTP/1.1" 200 -
2018-11-27 12:28:31,747 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/font-awesome/fa-globe-black.png HTTP/1.1" 200 -
2018-11-27 12:28:31,748 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/font-awesome/comments-blue.png HTTP/1.1" 200 -
2018-11-27 12:28:31,750 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/toronion.png HTTP/1.1" 200 -
2018-11-27 12:28:31,757 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/custom_logo.png HTTP/1.1" 200 -
2018-11-27 12:28:31,778 INFO 127.0.0.1 - - [27/Nov/2018 12:28:31] "GET /static/i/favicon.png HTTP/1.1" 200 -
_______________________________________________________ TestJournalistLayout.test_index_javascript[ar] _______________________________________________________

self = <tests.pageslayout.test_journalist.TestJournalistLayout object at 0x7fc16940fad0>

    def test_index_javascript(self):
        self._javascript_toggle()
        self._source_visits_source_homepage()
>       self._source_chooses_to_submit_documents()

/home/kdas/code/securedrop/securedrop/tests/pageslayout/test_journalist.py:320: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 
/home/kdas/code/securedrop/securedrop/tests/functional/source_navigation_steps.py:48: in _source_chooses_to_submit_documents
    self._source_clicks_submit_documents_on_homepage()
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 

self = <tests.pageslayout.test_journalist.TestJournalistLayout object at 0x7fc16940fad0>

    def _source_clicks_submit_documents_on_homepage(self):
        # First move the cursor to a known position in case it happens to
        # be hovering over one of the buttons we are testing below.
        header_image = self.driver.find_element_by_css_selector('.header')
        ActionChains(self.driver).move_to_element(header_image).perform()
    
        # It's the source's first time visiting this SecureDrop site, so they
        # choose to "Submit Documents".
        submit_button = self.driver.find_element_by_id(
            'submit-documents-button')
    
        submit_button_icon = self.driver.find_element_by_css_selector(
            'a#submit-documents-button > img.off-hover')
        self.wait_for(lambda: submit_button_icon.is_displayed(),
                      timeout=self.sleep_time)
    
        # The source hovers their cursor over the button, and the visual style
        # of the button changes to encourage them to click it.
        ActionChains(self.driver).move_to_element(submit_button).perform()
    
        # Let's make sure toggling the icon image with the hover state
        # is working.
>       assert submit_button_icon.is_displayed() is False
E       AssertionError

/home/kdas/code/securedrop/securedrop/tests/functional/source_navigation_steps.py:37: AssertionError
------------------------------------------------------------------- Captured stdout setup --------------------------------------------------------------------
 * Serving Flask app "source_app" (lazy loading)
 * Environment: production
   WARNING: Do not use the development server in a production environment.
   Use a production WSGI server instead.
 * Debug mode: on
 * Serving Flask app "journalist_app" (lazy loading)
 * Environment: production
   WARNING: Do not use the development server in a production environment.
   Use a production WSGI server instead.
 * Debug mode: on
------------------------------------------------------------------- Captured stderr setup --------------------------------------------------------------------
2018-11-27 12:29:14,999 DEBUG Starting new HTTP connection (1): 127.0.0.1:47719
2018-11-27 12:29:15,022 INFO  * Running on http://127.0.0.1:47719/ (Press CTRL+C to quit)
2018-11-27 12:29:15,030 INFO  * Running on http://127.0.0.1:57079/ (Press CTRL+C to quit)
2018-11-27 12:29:16,005 DEBUG Starting new HTTP connection (1): 127.0.0.1:47719
2018-11-27 12:29:16,074 INFO 127.0.0.1 - - [27/Nov/2018 12:29:16] "GET / HTTP/1.1" 200 -
2018-11-27 12:29:16,074 DEBUG http://127.0.0.1:47719 "GET / HTTP/1.1" 200 5035
2018-11-27 12:29:16,078 DEBUG Starting new HTTP connection (1): 127.0.0.1:57079
2018-11-27 12:29:16,086 INFO 127.0.0.1 - - [27/Nov/2018 12:29:16] "GET / HTTP/1.1" 302 -
2018-11-27 12:29:16,087 DEBUG http://127.0.0.1:57079 "GET / HTTP/1.1" 302 219
2018-11-27 12:29:16,090 DEBUG Resetting dropped connection: 127.0.0.1
2018-11-27 12:29:16,140 INFO 127.0.0.1 - - [27/Nov/2018 12:29:16] "GET /login HTTP/1.1" 200 -
2018-11-27 12:29:16,141 DEBUG http://127.0.0.1:57079 "GET /login HTTP/1.1" 200 2685
--------------------------------------------------------------------- Captured log setup ---------------------------------------------------------------------
connectionpool.py          205 DEBUG    Starting new HTTP connection (1): 127.0.0.1:47719
connectionpool.py          205 DEBUG    Starting new HTTP connection (1): 127.0.0.1:47719
connectionpool.py          393 DEBUG    http://127.0.0.1:47719 "GET / HTTP/1.1" 200 5035
connectionpool.py          205 DEBUG    Starting new HTTP connection (1): 127.0.0.1:57079
connectionpool.py          393 DEBUG    http://127.0.0.1:57079 "GET / HTTP/1.1" 302 219
connectionpool.py          240 DEBUG    Resetting dropped connection: 127.0.0.1
connectionpool.py          393 DEBUG    http://127.0.0.1:57079 "GET /login HTTP/1.1" 200 2685
-------------------------------------------------------------------- Captured stderr call --------------------------------------------------------------------
2018-11-27 12:29:20,370 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET / HTTP/1.1" 200 -
2018-11-27 12:29:20,416 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/gen/source.js?f357239b HTTP/1.1" 200 -
2018-11-27 12:29:20,417 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/css/source.css HTTP/1.1" 200 -
2018-11-27 12:29:20,425 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/font-awesome/times-white.png HTTP/1.1" 200 -
2018-11-27 12:29:20,435 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/font-awesome/cloud-upload-white.png HTTP/1.1" 200 -
2018-11-27 12:29:20,441 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /org-logo HTTP/1.1" 302 -
2018-11-27 12:29:20,444 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/font-awesome/comments-white.png HTTP/1.1" 200 -
2018-11-27 12:29:20,450 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/font-awesome/cloud-upload-blue.png HTTP/1.1" 200 -
2018-11-27 12:29:20,453 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/font-awesome/comments-blue.png HTTP/1.1" 200 -
2018-11-27 12:29:20,454 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/font-awesome/fa-globe-black.png HTTP/1.1" 200 -
2018-11-27 12:29:20,459 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/toronion.png HTTP/1.1" 200 -
2018-11-27 12:29:20,520 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/custom_logo.png HTTP/1.1" 200 -
2018-11-27 12:29:20,525 INFO 127.0.0.1 - - [27/Nov/2018 12:29:20] "GET /static/i/favicon.png HTTP/1.1" 200 -
====================================================================== warnings summary ======================================================================
test_2fa.py::test_totp_reuse_protections
  /usr/local/lib/python2.7/dist-packages/flask/sessions.py:208: UserWarning: "localhost" is not a valid cookie domain, it must contain a ".". Add an entry to your hosts file, for example "localhost.localdomain", and use that instead.
    ' "{rv}.localdomain", and use that instead.'.format(rv=rv)

-- Docs: http://doc.pytest.org/en/latest/warnings.html
=============================================== 2 failed, 489 passed, 1 xfailed, 1 warnings in 2932.65 seconds ===============================================
Makefile:20: recipe for target 'test' failed
make: *** [test] Error 1

@redshiftzero redshiftzero force-pushed the 3486-func-add-waitfors branch from c66aa7e to 273044f Compare December 21, 2018 01:30
@redshiftzero redshiftzero force-pushed the tbb-0.9.0 branch 2 times, most recently from c996de9 to 8385369 Compare December 21, 2018 03:42
@redshiftzero redshiftzero force-pushed the 3486-func-add-waitfors branch from 834286e to c12babf Compare December 21, 2018 03:47
@redshiftzero
Copy link
Contributor

redshiftzero commented Jan 2, 2019

@kushaldas d48de8b should resolve flakiness you saw in your last report 🤞

A couple other questions:

  • why are the sleeps necessary for the lines including the # Long waits comment?
  • remind me: is there a special reason we have a time.sleep(5) after the modal related interaction steps?

Happy to help on these, just wanted to clarify if these are there intentionally there for some reason

[edit: asked directly in chat and indeed there is no special reason for these sleeps, so removing]

Copy link
Contributor

@redshiftzero redshiftzero left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

beautiful job on this @zenmonkeykstop! I think this is good to go, so approving. Take a look at the few commits I added on this PR and let me know if you disagree with anything (will wait for your 👍 prior to merge)

@redshiftzero
Copy link
Contributor

@kushaldas take another gander at this one and 👍 if you agree this looks good

Copy link
Contributor

@kushaldas kushaldas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Finally, the tests are passing locally on my system. Thank you @zenmonkeykstop @redshiftzero.

@zenmonkeykstop
Copy link
Contributor Author

@redshiftzero 👍 from me, thanks for help and advice!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants