Skip to content

Conversation

@StevenMaude
Copy link
Contributor

Fixes #1014.

@StevenMaude
Copy link
Contributor Author

StevenMaude commented Dec 11, 2025

This was a quick experiment to see how good ChatGPT is at this kind of replacement.

It did OK. It introduced its own bug, which it then fixed when prompted, making:

assert url not in wrapper.client.session.cache.urls()

into:

assert url not in wrapper.client.session.session.cache.urls()

yield _httpretty
_httpretty.disable()
def http_responses():
with responses.RequestsMock(assert_all_requests_are_fired=False) as rsps:
Copy link
Contributor Author

Choose a reason for hiding this comment

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

thought: The override on assert_all_requests_are_fired is required because not all the mocked responses are used for some tests:

================================================================= short test summary info ==================================================================
ERROR tests/reports/test_job_server.py::test_get_published_html_from_job_server - AssertionError: Not all requests have been executed [('GET', 'https://jobs.opensafely.org/org/project/workspace/published/file_id/')]
ERROR tests/reports/test_job_server.py::test_last_updated - AssertionError: Not all requests have been executed [('GET', 'https://jobs.opensafely.org/org/project/workspace/published/file_id/')]
ERROR tests/reports/test_job_server.py::test_report_last_updated_after_fetching - AssertionError: Not all requests have been executed [('GET', 'https://jobs.opensafely.org/org/project/workspace/published/file_id/')]
ERROR tests/reports/test_models.py::test_report_uses_github - AssertionError: Not all requests have been executed [('GET', 'http://example.com/')]
ERROR tests/reports/test_models.py::test_report_with_published_job_server_url_adds_trailing_slash - AssertionError: Not all requests have been executed [('HEAD', 'http://example.com/published/foo')]
========================================================= 98 passed, 1 warning, 5 errors in 19.55s =========================================================

It may be one or more of:

  • there are responses added because of misunderstandings of the author at the time
  • the behaviour has changed subsequently
  • the tests is not really testing what was intended

Copy link
Contributor Author

@StevenMaude StevenMaude Dec 11, 2025

Choose a reason for hiding this comment

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

thought: I've fixed these up for now

  • Some responses were either mistakenly added or the behaviour has since changed.
  • Others weren't being retrieved because of caching.

We may want to rethink how we use the caching in tests, or ensure that the caches are created per-test, instead of being a global state.

* `test_report_uses_github` only checks for a URL stored on the report,
  not that the URL is accessed.
*
This is a little bit messy, but some tests were not actually
using the mocked HTTP responses provided in tests.

`JobServerReport`, by default, uses a `requests_cache` session
that stores HTTP responses.

This, by default, does not have a default expiry time for requests,
as `expires_after` is set to `-1`.

Some of the tests were therefore using the cached responses on
`JobServerReport(report).get_html()`, which is probably not was
intended:

* the expected value was being provided anyway, with a response that
  used it, so the intent was that the response should populate the
  resulting data value
* it would mean that the behaviour of tests could be influenced by
  the ordering of other tests (the result gets cached and then reused;
  and sharing of state this way seems like it can create or mask other
  problems)

This was masked by all the expected HTML content being the same here,
and there's an argument that perhaps the content should be the name of
the test function or something else unique.

Alternative fixes:

* name the cache and therefore have a unique cache for each test
  (however, this is currently set as a class attribute, configured by
  environment variable; it would be better if we could also specify
  it when creating the object, maybe)
* maybe make the caching less aggressive by default, and use a frozen
  time to expire the cache.
We can do this now, having fixed the tests.
@StevenMaude StevenMaude force-pushed the steve/replace-httpretty-with-responses branch from de2780a to 5aea67d Compare December 11, 2025 13:42
@StevenMaude StevenMaude marked this pull request as ready for review December 11, 2025 13:42
@StevenMaude
Copy link
Contributor Author

thought: Alice used mocket as a replacement in a similar task earlier this year.

I don't know too much about mocket, but responses is:

  • owned by an organisation (Sentry) rather than an individual maintainer
  • has a default "fail if responses are not used" behaviour which is useful for check for unused responses, and can highlight issues with caching, as found here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

httpretty looks unmaintained

2 participants