Creazione automatica di un utente amministratore durante l'esecuzione syncdb ./manage.py di Django

StackOverflow https://stackoverflow.com/questions/1466827

Domanda

Il mio progetto è in fase di sviluppo iniziale. Mi capita spesso di eliminare il database ed eseguire manage.py syncdb per impostare la mia applicazione da zero.

Purtroppo, questo si apre sempre:

You just installed Django's auth system, which means you don't have any superusers defined.
Would you like to create one now? (yes/no): 

Poi si deve fornire un nome utente, indirizzo e-mail valido e una password. Questo è noioso. Mi sto stancando di digitare test\nx@x.com\ntest\ntest\n.

Come posso ignorare automaticamente questo passaggio e creare un utente programatically quando si esegue manage.py syncdb?

È stato utile?

Soluzione

So che la questione è stata risolta già ma ...

Un approccio molto più semplice è quello di eseguire il dump dei dati del modulo di autenticazione in un file JSON una volta che il super-utente è stata creata:

 ./manage.py dumpdata --indent=2 auth > initial_data.json

È possibile anche scaricare i dati di sessioni:

./manage.py dumpdata --indent=2 sessions

È possibile quindi aggiungere le informazioni di sessione alla discarica modulo auth (e probabilmente aumentare l'EXPIRE_DATE in modo che non scade mai ...; -).

Da allora, è possibile utilizzare

/manage.py syncdb --noinput

per caricare il superutente e la sua sessione quando si crea il db senza prompt interattivo che richiede circa un superutente.

Altri suggerimenti

Invece di eliminare l'intero database, basta eliminare le tabelle della vostra applicazione prima di eseguire lo syncdb

Questo porterà a compimento per voi in una singola linea (per app):

python manage.py sqlclear appname | python manage.py dbshell

Il primo comando esaminerà la vostra applicazione e generare il codice SQL necessario per eliminare le tabelle. Questa uscita viene poi reindirizzato al dbshell per eseguirlo.

Dopo il fatto, eseguire lo syncdb per ricreare le tabelle:

python manage.py syncdb

La chiave è quella di utilizzare --noinput al momento della syncdb & quindi utilizzare questo one liner per creare superutente

echo "from django.contrib.auth.models import User; User.objects.create_superuser('myadmin', 'myemail@example.com', 'hunter2')" | python manage.py shell

Credit: http://source.mihelac.org/ 2009/10/23 / django-evitando-digitazione della password-for-superuser /

Se si desidera che la possibilità - come me - di iniziare veramente con un database fresco senza essere chiesto che domanda superutente, allora si può solo de-registrare il gestore di segnale che pone questa domanda. Controlla la parte inferiore del file:

django/contrib/auth/management/__init__.py

per vedere come viene eseguita la registrazione della funzione di superutente. Ho scoperto che avrei potuto invertire questa registrazione, e non ottengo chiesto la questione durante la "syncdb", se ho messo questo codice nel mio "models.py":

from django.db.models import signals
from django.contrib.auth.management import create_superuser
from django.contrib.auth import models as auth_app

# Prevent interactive question about wanting a superuser created.  (This
# code has to go in this otherwise empty "models" module so that it gets
# processed by the "syncdb" command during database creation.)

signals.post_syncdb.disconnect(
    create_superuser,
    sender=auth_app,
    dispatch_uid = "django.contrib.auth.management.create_superuser")

Non sono sicuro di come garantire che questo codice venga eseguito dopo il codice di Django che fa la registrazione. Avevo pensato che sarebbe dipende dal fatto che la vostra applicazione o l'applicazione django.contrib.auth ottiene indicati per primi nella INSTALLED_APPS, ma sembra di lavorare per me a prescindere dall'ordine li ho messi in. Forse sono fatto in ordine alfabetico e sono fortuna che il nome di mia app inizia con una lettera al più tardi "d"? O è Django abbastanza intelligente da fare la propria roba, poi il mio in caso voglio fare muck con le loro impostazioni? Fatemi sapere se si scopre. : -)

ho superato questa funzione utilizzando sud

E 'un must per tutti gli sviluppatori Django.

Sud è uno strumento progettato per aiutare a migrare le modifiche verso il luogo in tensione senza distruggere informazioni o la struttura del database. Le modifiche risultanti possono essere monitorati da sud e utilizzando i file python generati - in grado di eseguire le stesse azioni in un database alternativo

.

Durante lo sviluppo, Io uso questo strumento per tenere traccia git mie modifiche del database -. E per effettuare una modifica al database senza la necessità di distruggerlo prima

  1. easy_install sud
  2. Aggiungi 'Sud' per le applicazioni installate

Proporre primo run ora a sud su un app.

$ python manage.py schemamigration appname --init

Questo avvierà il rilevamento schema su tale applicazione.

$ python manage.py migrate appname

Questa applicherà il modello cambia

  • Il database avrà i nuovi modelli.

Modifica un modello dopo la prima manche

$ python manage.py schemamigration appname --auto

$ python manage.py migrate appname


I modelli avranno cambiato - i dati non viene distrutta. Più a sud fa molto di più ...

Nota: dal comando versione 1.7 syncdb è deprecato . Utilizzare migrate invece .

Django anche 1.7 introdotto AppConfig come mezzi di personalizzazione processo di inizializzazione delle applicazioni.

In questo modo poiché Django 1.7 il modo più semplice per ottenere ciò che si desidera è di impiegare sottoclasse di un AppConfig.

diciamo, vi capita di avere il proprio example_app che viene aggiunto al vostro INSTALLED_APPS e si desidera creare e Ammin utente con Ammin la password ogni volta che si esegue ./manage.py migrate da zero . Suppongo inoltre che la creazione automatica di utente admin è richiesto solo in dev Ambiente -. Non in di produzione

Aggiungere il seguente codice a example_app/apps.py

# example_app/apps.py

from django.apps import AppConfig
from django.conf import settings
from django.db.models.signals import post_migrate
from django.contrib.auth.apps import AuthConfig


USERNAME = "admin"
PASSWORD = "admin"


def create_test_user(sender, **kwargs):
    if not settings.DEBUG:
        return
    if not isinstance(sender, AuthConfig):
        return
    from django.contrib.auth.models import User
    manager = User.objects
    try:
        manager.get(username=USERNAME)
    except User.DoesNotExist:
        manager.create_superuser(USERNAME, 'x@x.com', PASSWORD)


class ExampleAppConfig(AppConfig):
    name = __package__

    def ready(self):
        post_migrate.connect(create_test_user)

Anche aggiungere il seguente riferimento alla configurazione app all'interno apps example_app/__init__.py:

# example_app/__init__.py

default_app_config = 'example_app.apps.ExampleAppConfig'

Se il default_app_config è un percorso stringa Python alla sottoclasse AppConfig come detto qui .

Il comando manage.py reset ripristinerà il database senza distruggere il vostro super utente creato. I dati ha tuttavia bisogno di essere reimportati.

È possibile utilizzare django-finalware per fare questo per voi . Basta aggiungere finalware al vostro INSTALLED_APPS e includere la seguente nella vostra settings.py:

SITE_SUPERUSER_USERNAME = 'myadmin'
SITE_SUPERUSER_EMAIL = 'myadmin@example.com'
SITE_SUPERUSER_PASSWORD  = 'mypass'  # this can be set from a secret file.

# optional object id. Ensures that the superuser id is not set to `1`.
# you can use this as a simple security feature
SITE_SUPERUSER_ID = '343'

Poi basta eseguire ./manage.py syncdb (Django <1,7) o ./manage.py migrate (Django> = 1.7), e creerà automaticamente un superutente o aggiornare quello esistente per voi.

Non si è mai chiesto di creato più un superutente.

Dal Django 1.7 il modo suggerito di popolamento del database è attraverso migrazioni di dati. Per creare una migrazione dei dati per la creazione di un amministratore è necessario innanzitutto creare una migrazione vuota:

./manage.py makemigrations --empty myapp --name create-superuser

Ciò creerà una migrazione vuoto myapp/migrations/000x__create-superuser.py. Modificare il file per farlo sembrare come questo:

# -*- coding: utf-8 -*-
from __future__ import unicode_literals

from django.db import migrations, models
from django.contrib.auth.models import User


def create_superuser(apps, schema_editor):
    User.objects.create_superuser(username='myadmin', password='mypassword', email='myemail@gmail.com')


class Migration(migrations.Migration):

    dependencies = [('myapp', '000y_my-previous-migration-file'),]

    operations = [migrations.RunPython(create_superuser)]

ho deciso di creare uno script python come questo per ripristinare tutte le mie cose [versione aggiornata] [1.8 troppo]:

import os
import sys

os.environ.setdefault("DJANGO_SETTINGS_MODULE", "main.settings.dev")

from django.conf import settings
from django.core import management
from django import get_version

PROJECT_ROOT = os.path.abspath(os.path.join(os.path.dirname(__file__), os.pardir))
if PROJECT_ROOT not in sys.path:
    sys.path.append(PROJECT_ROOT)

yn = raw_input('Are you sure you want to reset everything? (y/n) ')
if yn == 'y':

    # Drops the db / creates the db
    if settings.DATABASES['default']['ENGINE'].find('mysql') != -1:
        os.system('mysqladmin -uroot -pIronlord0 -f drop db')
        os.system('mysqladmin -uroot -pIronlord0 -f create db')
    elif settings.DATABASES['default']['ENGINE'].find('psycopg2') != -1:
        os.system('psql -U postgres -c "DROP DATABASE db"')
        os.system('psql -U postgres -c "CREATE DATABASE db WITH OWNER = admin"')
    elif settings.DATABASES['default']['ENGINE'].find('sqlite3') != -1:
        try:
            os.remove(os.path.join(PROJECT_ROOT, 'data.db'))
        except:
            pass

    # Getting application handle here otherwise db gets allocated and it can not be destroyed.
    if get_version() > '1.6.10':
        from django.core.wsgi import get_wsgi_application
        application = get_wsgi_application()

    management.call_command('syncdb', interactive=False)

    # Creates admin/password
    from django.contrib.auth.management.commands import changepassword
    management.call_command('createsuperuser', interactive=False, username="admin", email="xxx@example.com")
    command = changepassword.Command()
    command._get_pass = lambda *args: 'password'
    if get_version() >= '1.8':
        command.execute(username="admin")
    else:
        command.execute("admin")


    # Creates the default site entry
    from django.contrib.sites.models import Site
    site = Site.objects.get_current()
    site.domain = 'www.example.com'
    site.name = ' xxx '
    site.save()

funziona come un fascino!

P.S .: Ricordarsi di arrestare il server (di prova), dove sopra db è responsabile prima di eseguire questo script!

Date un'occhiata al comando gestione dumpdata. Per esempio:

python manage.py dumpdata > initial_data.json

Se questo file, chiamato un appuntamento fisso, è chiamato initial_data (.xml o .json), quindi il comando syncdb lo pick up e popolare le tabelle di conseguenza. Sarà ancora chiederà se si desidera creare un utente, ma credo che si può tranquillamente rispondere "no", dopo di che punto sarà popolare il database in base al dispositivo.

Più informazioni su questo può essere trovato nel docs .

Sviluppare con SQLite. Cancella database di file cancellando. Carico di amministrazione da dispositivi.

cambiamento manage.py (Django 1.4):

# hack to prevent admin promt
if  len(sys.argv) == 2 and sys.argv[1] == 'syncdb':
    sys.argv.append('--noinput')

La mia soluzione a questo è stato non solo di eliminare le tabelle che Auth quando spazzare via il mio database.

Se si preferisce digitare l'inizializzazione del codice direttamente nel file sorgente Python, questo codice modificato manage.py potrebbe aiutare (e grazie per po 'di codice di Cjkjvfnby!):

#!/usr/bin/env python
import os
import sys

if __name__ == "__main__":
    # set your django setting module here
    os.environ.setdefault("DJANGO_SETTINGS_MODULE", "app.settings") 

    from django.core.management import execute_from_command_line

    # hack to prevent admin prompt
    if len(sys.argv) == 2 and sys.argv[1] == 'syncdb':
        sys.argv.append('--noinput')

    execute_from_command_line(sys.argv)

    # additional process for creation additional user, misc data, and anything
    for arg in sys.argv:
        # if syncdb occurs and users don't exist, create them
        if arg.lower() == 'syncdb':
            print 'syncdb post process...'
            from django.contrib.auth.models import User

            admin_id = 'admin'
            admin_email = 'superuser@mail.com'
            admin_password = 'superuser_password'
            additional_users = [
                                ['tempuser', 'user_email@mail.com', 'tempuser_password']
                                ]

            # admin exists?
            user_list = User.objects.filter(username=admin_id)
            if len(user_list) == 0: 
                print 'create superuser: ' + admin_id
                new_admin = User.objects.create_superuser(admin_id, admin_email, admin_password)

            # additional user exists?
            for additional_user in additional_users:
                user_list = User.objects.filter(username=additional_user[0])
                if len(user_list) == 0: 
                    print 'create additional user: ' + additional_user[0]
                    new_admin = User.objects.create_user(additional_user[0], additional_user[1], additional_user[2])

            # any other data

Sto solo mostrando il codice di creazione utente qui, ma è possibile migliorare questo codice più come si desidera.

sto usando SQLite come database dev. Dopo aver cambiato le classi del modello, basta semplicemente inserire le tabelle corrispondenti con SQLite Manager (un plugin per Firefox, aperto a esaminare i dati in ogni modo) ed eseguire manage.py syncdb di ricreare ciò che manca.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top