Simple piece of middleware that redirects all requests to settings.FIRSTRUN_APP_PATH, until a lockfile is created.
Tested on 1.3 only, but I do not believe it requires any special functionality beyond that provided in 1.1
This is useful if you need to force a user to run an installer, or do some configuration before your project can function fully.
At first glance, such a thing would generate a lot of hits on the disk. However, once the lockfile has been created, the middleware unloads itself, so when a project is in a production environment, the lockfile is only checked once per process invocation (with passenger or mod_wsgi, that's not very often at all).
Once your user has completed your FirstRun app, simply create the lockfile and the project will function as normal.
For it to function, the following settings must be configured:
- settings.PROJECT_PATH - absolute path to project on disk (e.g. /var/www/project/)
- settings.FIRSTRUN_LOCKFILE - relative path of the lockfile (e.g. /.lockfile)
- settings.FIRSTRUN_APP_ROOT - relative URL of the App you want to FirstRun (eg./firstrun/)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
from django.conf import settings from django.core.files.storage import FileSystemStorage from django.shortcuts import redirect import django.core.exceptions import logging import re import os # Check for the existance of a lockfile. If the lockfile doesn't exist, deny access to everywhere except settings.FIRSTRUN_APP_ROOT # If the lockfile exists, throw django.core.exceptions.MiddlewareNotUsed() so that this class is unloaded class FirstRunMiddleware: def __init__(self): if not self.is_first_run(): logging.debug('FirstRunMiddleware: FirstRun not required, unloading for process lifetime.') raise django.core.exceptions.MiddlewareNotUsed() self.p = re.compile(''.join(['^', settings.FIRSTRUN_APP_ROOT])) def process_request(self, request): if self.p.match(request.path) == None: if self.is_first_run(): logging.debug(''.join(['FirstRunMiddleware: Denying access to ', request.path, ' FirstRun needed.'])); return redirect(settings.FIRSTRUN_APP_ROOT) else: # Will only be executed between the time firstrun has been completed, until the process is regenerated (typically on the scale of mins). logging.debug('FirstRunMiddleware: FirstRun completed, resuming normal flow.') def is_first_run(self): return not os.path.exists(''.join([settings.PROJECT_PATH, settings.FIRSTRUN_LOCKFILE]))
More like this
- codigo alto nivel by MrRocklion 1 month ago
- Load template from specific app by Krzysiek555 1 month, 3 weeks ago
- PostgreSQL JSON subqueries by dolamroth 1 month, 3 weeks ago
- "Magic Link" Management Command by webology 6 months, 4 weeks ago
- Closest ORM models to a latitude/longitude point by simonw 6 months, 4 weeks ago