Plain Language Django Guide & Irreverent FAQ - JustFixNYC/tenants2 GitHub Wiki

FAQ

What's the deal with manage.py? And we also talk about django-admin, what's that?

  • Manage.py and django-admin are two different ways of running a bunch of different commands.
  • Manage.py is easier, and you can use it like:
docker-compose run app python manage.py <command> [options]
  • django-admin is a command line tool, not to be confused with the django admin page (django.contrib.admin app), which is only available to logged-in superusers (i.e. our staff).

COOL MANAGE.PY COMMANDS

  • Dbshell: this lets you run arbitrary SQL commands on your local database. Helpful for testing database migrations. e.g.

    $ docker-compose run app python manage.py dbshell
    justfix=# select lease_type, user_id from onboarding_onboardinginfo;
    lease_type     |    user_id
    ---------------------------------
    MARKET_RATE        |      1
    RENT_STABILIZED    |      2
    (2 rows)
    
  • Makemessages: this is used by dcra yarn django:makemessages for extracting messages for localization into all the messages.po files

  • Makemigrations: This creates all the new db migrations that result from changes you’ve made to django models and stuff

  • Migrate: Apply all unapplied migrations to your local db. Like if you want to change all the users with housing type “old type” to housing type “new type”, that’s a migration.

  • Shell: Don’t confuse it with dbshell. This just opens a python interpreter, but by doing it this way, you can import things from other parts of your app and play with them.

  • Test We only have 10 tests that django knows about. You probably want

    docker-compose run app pytest
    

    or

    docker-compose run app yarn test
    
  • Runserver This is what docker-compose up eventually runs under the hood to start the app.

SCHEDULED MANAGE.PY COMMANDS

Note that a bunch of manage.py commands are actually intended to be run regularly by some kind of scheduler.

An example of such a built-in management command is clearsessions, which clears expired sessions from the database. Atul didn't even know this one existed until he noticed that the database was using up a lot of space and he wondered where all of it was going! 😅

At the time of this writing (August 2021), we use Heroku Scheduler to schedule these tasks. Check its configuration on Heroku to see a full list of what's currently scheduled.

What's the difference between apps and projects?

  • App name is the basename of the package containing your modules.
  • We have lots of apps: onboarding, hpaction, issues, loc, norent, nycdb, nycha, nycx - some of them correspond to what we’d call an ‘app’ in normal parlance in terms of something users interact with but many don’t and are just package names.
  • Just in case you weren’t confused enough, check the “projects vs apps” description here

What's settings.py?

  • Settings.py is what configures a bunch of stuff so when you run things like manage.py dbshell, it knows what kind of db it is and whether to run mysql or postgresql, etc. We use Postgres. I haven’t had to change this stuff much yet.

How do you do routing?

  • If you wanna deal with routing, you need a url conf (url config). In tenants2, each of our apps (like evictionfree or docusign or hpaction has its own urls.py file.

Models!

  • Django models are what defines the data you store. The tutorial’s description of how models relate to python classes and database column names is actually pretty good.

  • Changing the model tells Django to change the database schema and the Python API for accessing data, and also to create a record of the change (that’s a migration file, which is really just instructions on how to create SQL commands to apply to the DB).

  • Django will realize when it has to make a new migration and let you know, but then there’s two more steps before it’s applied to the db:

    • Makemigrations
    • Migrate

Django admin

  • One of the biggest reasons we use django is because of the free UI it provides for changing data: the admin site.
  • To create a user who can log into the admin site, run python manage.py createsuperuser. You’ll need a username, email and password. Be sure to note these down in a password manager.
    • Most users in our db have autogenerated usernames, so admin accounts are partially distinguished by their human-readable usernames.
  • You can access the admin dashboard at localhost:8000/admin.
  • To change the editable fields on the admin dashboard, check out the admin_views.py files.

Site models

  • We use an optional part of Django called the ‘sites’ framework. It allows you to power multiple sites (in our case, app.justfix.nyc, NoRent, and evictionfreeny.org) with one Django installation.

  • This means you’ll use the same database for both sites. BUT you can filter database queries to only look for records associated with one site, so your queries don’t start taking forever with multiple sites.

  • To add a new site, check out site-choices.json, the SITE_CHOICES object, and project/util/site_util.py.

Magic filenames

In app directories, Django--and sometimes third-party libraries, and sometimes even our own code--treats certain specially-named files in special ways (as long as the app is listed in settings.INSTALLED_APPS, that is).

Here are some such special filenames:

  • models.py - Django always loads any model classes here and automatically generates migrations for them and things like that.

  • admin.py - Django always loads any administrative views defined in this file and makes them visible on the admin area of the site.

  • schema.py - Our own code loads this file automatically to register any GraphQL endpoints defined in it. For more details, see project/schema_registry.py.

  • tasks.py - Celery's Django integration automatically loads any tasks defined in this file. For more details, see Celery's guide on First steps with Django.

  • management/commands/*.py - Any Python files added in this directory will be registered as Django management commands. For more details, see Django's guide on Writing custom django-admin commands.

⚠️ **GitHub.com Fallback** ⚠️