---
tags: django, pytest
---
# Profiling and speeding up Django and Pytest

[Éloi](https://yaal.coop/) made [a pull request on
IHateMoney](https://github.com/spiral-project/ihatemoney/issues/1214) to
speedup the tests, with some great tooling for pytest that I wasn't aware of:

- [pytest-xdist](https://pypi.org/project/pytest-xdist/) allows to run tests in
  parallel, using `-n auto`
- [pytest-profiling](https://pypi.org/project/pytest-profiling/) makes it easy
  to get the call stack and time the function calls that take most of the time.
- You can them analyse the `.prof` files with
  [Snakeviz](https://pypi.org/project/snakeviz/)

So, I spent some time using these on the tests for [La
Chariotte](https://chariotte.fr), because they were slow.

I found two things :

- Login calls are costly in the test, and it's possible to speed things up ;
- On my machine, calls to resolve my hostname were slow, using 5s during the
  tests for a lookup that wasn't even useful.

## Changing the hashing algorithm to speedup tests

By default, Django uses a slow (but secure !) hashing mechanism for checking
the user credentials. In the tests, we don't need this security, but we need
the speed.

Changing them to use MD5 turns out to be a way to greatly speed them up! Here
is how to do it with a pytest fixture :

```python
@pytest.fixture(autouse=True)
def password_hasher_setup(settings):
    # Use a weaker password hasher during tests, for speed
    settings.PASSWORD_HASHERS = [
        "django.contrib.auth.hashers.MD5PasswordHasher",
    ]
```

## Speeding DNS lookups

I'm currently using a MacOSX machine, and for for whatever reason, the local
lookup was not configured properly on my machine. I don't think I did anything
specific to get this wrong, so it might be your case too. Calls to resolve the
local domain were tooking 5s.

If the answer to `scutil --get LocalHostName`, `hostname` and `scutil --get
HostName` differ, then you might be in this case. Here is the fix :

```bash
sudo scutil --set HostName <YourHostName>
```

