Comment gérer les vs les paramètres de production dans Django?
Quelle est la méthode recommandée pour la manipulation de paramètres pour le développement local et le serveur de production? Certains d'entre eux (comme des constantes,...) peut être changé/accessible dans les deux, mais certains d'entre eux (comme les chemins d'accès aux fichiers statiques) doivent rester différents, et par conséquent ne devrait pas être écrasé à chaque fois le nouveau code est déployé.
Actuellement, je suis en ajoutant toutes les constantes de settings.py
. Mais à chaque fois que je change certains constante localement, j'ai copier sur le serveur de production et de modifier le fichier de la production de changements spécifiques... 🙁
Edit: regarde comme il n'y a pas de réponse standard à cette question, j'ai accepté la méthode la plus populaire.
- Voir stackoverflow.com/questions/88259/...
- Jetez un oeil à django-configurations.
- La méthode acceptée est pas le plus populaire.
- django-split-settings est très facile à utiliser. Il ne nécessite pas de réécrire les paramètres par défaut.
- yo devez utiliser base.py fichier et dans votre local.py "à partir de .de base à l'importation *", de même dans votre production.py "à partir de .de base à l'importation *", vous devez exécuter votre projet avec: python manage.py runserver --paramètres=nom_du_projet.les paramètres.local
Vous devez vous connecter pour publier un commentaire.
Dans
settings.py
:Vous pouvez remplacer ce qu'il y avait dans
local_settings.py
; il devrait rester en dehors de votre contrôle de version alors. Mais puisque vous parlez de la copie, je devine que vous utilisez none 😉settings_local
par opposition àlocal_settings
de groupe avecsettings.py
alphabétique des listes de dossiers. Gardersettings_local.py
de contrôle de version à l'aide de.gitignore
que les informations d'identification n'appartiennent pas à Git. Imaginez l'approvisionnement ouvert par accident. Je garde dans git d'un fichier de modèle appelésettings_local.py.txt
à la place.except ImportError as e:
?? n'est-ce pasexcept ImportError:
juste assez?local_settings.py
appartient à l'environnement local? Aussi, avoir ce fichier dans la production, ont un effet sur la performance et la cause involontaire de comportement?INSTALLED_APPS
), vous pouvez les importer dans l'local_settings.py comme:from .settings import INSTALLED_APPS
puis dans local_settings.py:INSTALLED_APPS += ['autotranslate']
project.settings
module de compter sur les tirant deos.environ
.Deux Cuillères de Django: les Meilleures Pratiques pour Django 1.5 suggère d'utiliser le contrôle de version de vos fichiers de paramètres et de stocker les fichiers dans un répertoire distinct:
La
base.py
fichier contient les paramètres (tels que les MEDIA_ROOT ou ADMIN), tandis quelocal.py
etproduction.py
de site, les paramètres spécifiques:Dans le fichier de base
settings/base.py
:Dans le développement local fichier de paramètres
settings/local.py
:Dans le fichier de paramètres de production de fichier
settings/production.py
:Puis lorsque vous exécutez django, vous ajoutez le
--settings
option:Les auteurs du livre ont également mis en place un exemple de projet modèle de mise en page sur Github.
--settings
à chaque fois, vous pouvez définir laDJANGO_SETTINGS_MODULE
envvar. Cela fonctionne très bien avec, par exemple, Heroku: définir à l'échelle mondiale de la production, puis de la remplacer par dev dans votre .fichier env.DJANGO_SETTINGS_MODULE
env var est la meilleure idée ici, merci Simon.ImportError: Could not import settings 'project.settings.local' (Is it on sys.path?): No module named settings.local
. Ne savais pas que vous aviez besoin de__init__.py
dans le répertoire pour l'importation de travailler.__init__.py
fichier dans la liste du répertoire ci-dessus!BASE_DIR
paramètres deos.path.dirname(os.path.realpath(os.path.dirname(__file__) + "/.."))
from django.conf import settings
qui est un objet qui fait abstraction de l'interface et découple le code de l'emplacement des paramètres, docs.djangoproject.com/en/dev/topics/settings/...alias django-settings="path=\$(pwd);dir=\$(basename \$path); export DJANGO_SETTINGS_MODULE=\$dir\".settings.dev\""
dans votre .bashrc (ou similaire), vous pouvez simplement taperdjango-settings
dans le répertoire racine de tout projet django qui utilise ce modèle. @rsp, cela vous aidera à vous aussi, je suppose, n'ont tout simplement pas le type dedjango-settings
pour ceux d'autres projets.BASE_DIR = os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
Au lieu de
settings.py
, utiliser cette mise en page:common.py
est où la plupart de la configuration des vies.prod.py
importations de tout, de la commune, et qui remplace ce qu'il doit remplacer:De même,
dev.py
les importations de tout, decommon.py
et qui remplace ce qu'il doit remplacer.Enfin,
__init__.py
est l'endroit où vous décidez de paramètres à charger, et c'est aussi là où vous stockez des secrets (par conséquent, ce fichier ne doit pas être versionné):Ce que j'aime à propos de cette solution est:
common.py
.prod.py
, dev spécifique les choses vont dansdev.py
. C'est simple.common.py
dansprod.py
oudev.py
, et vous pouvez remplacer quoi que ce soit dans__init__.py
.os.environ.setdefault("DJANGO_SETTINGS_MODULE", "foobar.settings")
foobar est un dossier avec un__init__.py
de fichiers et de paramètres est un dossier avec un__init__.py
fichier qui contient mes secrets et les importations dev.py qui importe ensuite common.py. MODIFIER tant pis, je n'ai pas de module installé qui était nécessaire. Mon mauvais! Cela fonctionne très bien!!J'utilise une version légèrement modifiée de la "si DEBUG" style de paramètres que Harper Shelby posté. Évidemment, en fonction de l'environnement (win/linux/etc.) le code peut-être besoin d'être modifié un peu.
J'ai été dans le passé à l'aide de la "si DEBUG" mais j'ai trouvé que, parfois, j'avais besoin de faire des tests avec DEUBG définie sur False. Ce que je voulais vraiment distinguer si l'environnement de production ou de développement, ce qui m'a donné la liberté de choisir le niveau de DÉBOGAGE.
Je serais encore considérer cette façon de paramètres d'un travail en cours. Je n'ai pas vu un moyen de manipulation de Django paramètres couvert toutes les bases et en même temps n'était pas un total compliqué à mettre en place (je ne suis pas vers le bas avec le 5x fichiers de paramètres des méthodes).
os.environ['COMPUTERNAME']
ne fonctionne malheureusement pas sur PythonAnywhere. Vous obtenez un KeyError.- Je utiliser un settings_local.py et un settings_production.py. Après avoir essayé plusieurs options, j'ai trouvé qu'il est facile de perdre de temps avec des solutions complexes quand il suffit d'avoir deux fichiers de paramètres se sent facile et rapide.
Lorsque vous utilisez mod_python/mod_wsgi pour votre projet Django, vous devez pointer vers votre fichier de paramètres. Si vous le pointez sur app/settings_local.py sur votre serveur local et app/settings_production.py sur votre serveur de production, alors la vie devient facile. Il suffit de modifier les paramètres appropriés de fichier et redémarrez le serveur (serveur de développement de Django va redémarrer automatiquement).
python manage.py runserver
), les paramètres de fichier à utiliser?- Je gérer mes configurations avec l'aide de django-split-paramètres.
C'est une baisse-dans le remplacement pour les paramètres par défaut. C'est simple, mais configurable. Et la refonte de votre existant paramètres n'est pas nécessaire.
Voici un petit exemple (fichier
example/settings/__init__.py
):Que c'est.
Mise à jour
J'ai écrit un post de blog sur la gestion des
django
's paramètres avecdjango-split-sttings
. Avoir un coup d'oeil!uwsgi.ini
fichier de paramètres différents à travers dev/prod.. aucune idée de comment le faire choisir les valeurs de mon fichier de paramètres?Le problème avec la plupart de ces solutions est que soit vous avez vos paramètres locaux appliqué avant le commun, ou après eux.
Il est donc impossible de remplacer les choses comme les
en même temps.
Une solution peut être implémentée à l'aide de "ini"style fichiers de configuration avec le ConfigParser classe. Il prend en charge plusieurs fichiers, paresseux chaîne d'interpolation, les valeurs par défaut et beaucoup d'autres goodies.
Une fois un certain nombre de dossiers ont été chargées, plusieurs fichiers peuvent être chargés et leurs valeurs remplacent les précédents, le cas échéant.
Vous charger un ou plusieurs fichiers de configuration, en fonction de la machine, l'adresse, les variables d'environnement et les même valeurs que vous venez de charger des fichiers de configuration. Ensuite, il vous suffit d'utiliser les valeurs analysées pour remplir les paramètres.
Une stratégie que j'ai utilisée avec succès a été:
defaults.ini
fichiernet.ini
, puisnet.domain.ini
, puisnet.domain.webserver01.ini
, chacun en surchargeant les valeurs de la précédente). Cela compte aussi pour les développeurs de machines, de sorte que chacun peut mettre en place son préféré pilote de base de données, etc. pour le développement localcluster.cluster_name.ini
, qui peut définir des choses comme la base de données et le cache IPsComme un exemple de quelque chose que vous pouvez obtenir avec cela, vous pouvez définir un "sous-domaine" valeur par env, qui est ensuite utilisé dans les paramètres par défaut (comme
hostname: %(subdomain).whatever.net
) pour définir tous les noms d'hôtes et témoin des choses django besoin de travailler.C'est aussi SEC que j'ai pu obtenir, la majorité (existant) des fichiers a tout juste 3 ou 4 paramètres. Sur le dessus de cela, j'ai eu à gérer de configuration du client, donc un ensemble de fichiers de configuration (avec des choses comme la base de données de noms d'utilisateurs et mots de passe attribués sous-domaine, etc) existait, au moins une par client.
On peut l'appliquer à grande échelle comme bas ou aussi haut que nécessaire, il vous suffit de mettre dans le fichier de config les touches que vous souhaitez configurer par l'environnement, et une fois qu'il y a un besoin pour une nouvelle config, mettre la valeur précédente dans la configuration par défaut, et le remplacer si nécessaire.
Ce système a fait ses preuves et fonctionne bien avec le contrôle de version. Il a été utilisé pendant longtemps, la gestion de deux groupes distincts d'applications (15 ou de plusieurs instances distinctes du site django par machine), avec plus de 50 clients, où les grappes ont été la modification de la taille et des membres selon l'humeur de la sysadmin...
config = ConfigParser.ConfigParser()
alors lire vos fichiersconfig.read(array_of_filenames)
et obtenir les valeurs à l'aide deconfig.get(section, option)
. Alors d'abord vous chargez votre config, et puis vous pouvez l'utiliser pour lire les valeurs des paramètres.Je travaille aussi avec Laravel et j'aime la mise en oeuvre il. J'ai essayé de l'imiter et de le combiner avec la solution proposée par T. de Pierre (voir plus haut):
Peut-être quelque chose comme cela peut vous aider.
TL;DR: L'astuce consiste à modifier
os.environment
avant d'importersettings/base.py
dans toutesettings/<purpose>.py
, cela va grandement simplifier les choses.Viens de penser à tous ces entrelacs fichiers me donne mal à la tête.
La combinaison, à l'importation (parfois sous certaines conditions), en remplaçant, l'application des correctifs de ce qui a déjà été dans le cas
DEBUG
paramètre modifié par la suite.Ce qu'est un cauchemar!
À travers les années, je suis passé par toutes les différentes solutions. Ils ont tous un peu de travail, mais sont tellement pénible à gérer.
WTF! Avons-nous vraiment besoin de tous ces tracas? Nous avons commencé avec un seul
settings.py
fichier.Maintenant nous avons besoin d'une documentation simplement à combiner correctement, tout cela réuni dans un ordre correct!
J'espère que j'ai enfin touché le (mon) sweet spot avec la solution ci-dessous.
Récapitulons les objectifs (certaines communes, certains le mien)
Garder un secret un secret — ne pas stocker dans un repo.
Définir/lire les clés et les secrets à travers les paramètres de l'environnement, 12 facteur de style.
Ont judicieux de secours par défaut. Idéalement pour le développement local, vous n'avez besoin de rien de plus à côté des valeurs par défaut.
...mais essayez de garder les valeurs par défaut de la production de sécurité. Il vaut mieux rater un paramètre de remplacer localement,
que d'avoir à se rappeler de régler les paramètres par défaut de sécurité pour la production.
Ont la possibilité de changer de
DEBUG
on/off dans une manière qui peut avoir un effet sur d'autres paramètres (par exemple. à l'aide de javascript compressé ou non).De commutation entre l'objectif de paramètres, comme local/test/mise en scène/production, doivent être fondés uniquement sur
DJANGO_SETTINGS_MODULE
, rien de plus....mais permettre la poursuite de l'ensemble de paramètres par le biais de paramètres d'environnement comme
DATABASE_URL
....également leur permettre d'utiliser différents des paramètres et de les exécuter localement côte à côte, par exemple. la production de l'installation locale sur l'ordinateur du développeur, de l'accès base de données de production ou de test de fumée comprimé feuilles de style.
Échouer si une variable d'environnement n'est pas explicitement défini (nécessitant une valeur vide au minimum), en particulier dans la production, par exemple.
EMAIL_HOST_PASSWORD
.Répondre à défaut
DJANGO_SETTINGS_MODULE
ensemble dans manage.py au cours de django-admin startprojectGarder conditionnelles à un minimum, si la condition est la dessein type d'environnement (par exemple. pour la production de fichier journal et c'est la rotation), remplacent les paramètres associés dessein fichier de paramètres.
N'est
Ne laissez pas django lire DJANGO_SETTINGS_MODULE réglage de la forme d'un fichier.
Pouah! Pensez à comment les méta c'est. Si vous avez besoin d'un fichier (comme docker
env) de lire que dans l'environnement avant de lancer un django processus.
Ne remplacent pas les DJANGO_SETTINGS_MODULE dans votre projet/le code de l'application, par exemple. basé sur le nom d'hôte ou nom du processus.
Si vous êtes paresseux pour définir la variable d'environnement (comme pour
setup.py test
) le faire dans l'outillage juste avant de lancer votre projet de code.Éviter de la magie et de la correction de la façon dont django, il lit les paramètres de prétraiter les paramètres, mais n'interfèrent pas par la suite.
Pas compliqué logique de l'absurde. La Configuration doit être fixe et matérialisée pas calculée à la volée.
Fournir une solution de secours par défaut est juste assez logique ici.
Voulez-vous vraiment de débogage, pourquoi localement vous avez la bonne série de paramètres, mais en production sur un serveur distant,
sur l'une des centaines de machines, quelque chose de calculé différemment? Oh! Les tests unitaires? Pour les réglages? Sérieusement?
Solution
Ma stratégie consiste excellent django-environ utilisé avec
ini
des fichiers de style,fournir
os.environment
les valeurs par défaut pour le développement local, quelques minimes et de courtesettings/<purpose>.py
les fichiers qui ont unimport settings/base.py
APRÈS laos.environment
a été créé à partir d'unINI
fichier. De cette manière efficace de nous donner une sorte de paramètres d'injection.L'astuce ici est de modifier
os.environment
avant d'importersettings/base.py
.Voir l'exemple complet d'aller faire le repo: https://github.com/wooyek/django-settings-strategy
paramètres/.env
Un défaut de développement local. Un dossier secret, la plupart du temps de définir des variables d'environnement requises.
Les mettre à des valeurs vides si elles ne sont pas nécessaires dans le développement local.
Nous fournissent les valeurs par défaut ici, et pas dans
settings/base.py
échouer sur une autre machine si le manque de l'environnement.settings/local.py
Ce qui se passe ici, est un environnement de chargement de
settings/.env
, puis l'importation de paramètres communsde
settings/base.py
. Après, on peut remplacer un peu à la facilité de développement local.settings/production.py
Pour la production, nous ne devrions pas nous attendre à un fichier d'environnement, mais il est plus facile d'avoir un si nous sommes en train de tester quelque chose.
Mais de toute façon, de peur que de fournir quelques défauts inline, donc
settings/base.py
peut réagir en conséquence.Le principal point d'intérêt ici sont
DEBUG
etASSETS_DEBUG
remplace,ils seront appliqués à l'python
os.environ
SEULEMENT s'ils sont absents de l'environnement et le fichier.Ces sera notre production par défaut, pas besoin de les mettre dans l'environnement ou dans un fichier, mais ils peuvent être remplacés si nécessaire. Neat!
settings/base.py
Ce sont pour la plupart à la vanille django paramètres, avec quelques conditions et beaucoup de lecture de l'environnement.
Presque tout est ici, en gardant tout le dessein des environnements cohérents et aussi semblables que possible.
Les principales différences sont ci-dessous (j'espère que ces sont explicites):
Le dernier bit montre le pouvoir ici.
ASSETS_DEBUG
a une valeur par défaut raisonnable,qui peut être remplacée dans les
settings/production.py
et même ce qui peut être remplacée par un paramètre d'environnement! Yay!!!En effet, nous avons un mélange de hiérarchie d'importance:
Rappelez-vous que settings.py est un fichier de code. En supposant que vous n'avez pas de DÉBOGAGE ensemble sur la production (qui est une bonne pratique), vous pouvez faire quelque chose comme:
Assez basique, mais vous pouvez, en théorie, aller à n'importe quel niveau de complexité basée sur la valeur de DÉBOGAGE ou de toute autre variable ou un code de vérification vous vouliez l'utiliser.
Ma solution à ce problème est aussi un peu un mélange de certaines solutions déjà dit ici:
local_settings.py
qui a le contenuUSING_LOCAL = True
en dev etUSING_LOCAL = False
en prod,settings.py
je fais une importation sur ce fichier pour obtenir leUSING_LOCAL
réglageJ'ai ensuite la base de tous mes dépendant de l'environnement des paramètres sur celui-ci:
Je préfère cela à avoir deux settings.py les fichiers que j'ai besoin de maintenir tant que je peux garder mes réglages structuré en un seul fichier plus facile que d'avoir réparti sur plusieurs fichiers. Comme ça, quand je mettre à jour un paramètre je n'oublie pas de le faire pour les deux environnements.
Bien sûr que chaque méthode a ses inconvénients et celui-ci ne fait pas exception. Le problème ici est que je ne peux pas remplacer le
local_settings.py
fichier à chaque fois que je pousse mes modifications dans la production, ce qui signifie que je ne peux pas il suffit de copier tous les fichiers à l'aveuglette, mais c'est quelque chose que je peux vivre avec.Pour la plupart de mes projets, j'utilise le motif suivant:
from settings_base import *
)(À exécuter manage.py avec fichier de paramètres personnalisés, vous utilisez simplement --paramètres de l'option de commande:
manage.py <command> --settings=settings_you_wish_to_use.py
)J'utilise une variation de ce que jpartogi mentionné ci-dessus, que je trouve un peu plus court:
Essentiellement sur chaque ordinateur (de développement ou de production), j'ai l'appropriées hostname_settings.py fichier qui obtient chargé dynamiquement.
Il y a aussi Django Chic Paramètres. Je suis personnellement un grand fan de lui. Il est construit par l'un des la plupart des personnes actives sur le Django IRC. Vous serait d'utiliser des variables d'environnement pour définir les choses.
http://django-classy-settings.readthedocs.io/en/latest/
Afin d'utiliser différents
settings
de configuration sur l'environnement différent, de créer différents paramètres de fichier. Et dans votre script de déploiement, démarrer le serveur à l'aide de--paramètres=<ma-paramètres.py>
paramètre, par l'intermédiaire de laquelle vous pouvez utiliser différents paramètres sur l'environnement différent.Avantages de l'utilisation de cette approche:
Vos réglages seront modulaire en fonction de chaque environnement
Vous pouvez importer les
master_settings.py
contenant la configuration de base dans leenvironmnet_configuration.py
et remplacer les valeurs que vous souhaitez modifier dans l'environnement.Si vous avez énorme équipe, chaque développeur peut avoir leur propre
local_settings.py
qui ils peuvent ajouter au référentiel de code, sans aucun risque de modification de la configuration du serveur. Vous pouvez ajouter ces paramètres locaux à.gitnore
si vous utilisez git ou.hginore
si vous Mercurial pour de Contrôle de Version (ou tout autre). De cette façon, local settings ne seront pas de la partie réelle de la base de code de la garder propre.Je différencier dans manage.py et créé deux fichier de paramètres: local_settings.py et prod_settings.py.
Dans manage.py -je vérifier si le serveur est serveur local ou un serveur de production. Si c'est un serveur local, il serait de charger jusqu'local_settings.py et c'est un serveur de production, il serait de charger jusqu'prod_settings.py. Fondamentalement, c'est la façon dont il devrait ressembler à:
Je trouve qu'il est plus facile de séparer le fichier de settings dans deux fichier séparé au lieu de faire beaucoup de ifs à l'intérieur du fichier de paramètres.
Comme une alternative à maintenir fichier différent si vous obtiendrez:
Si vous utilisez git, ou de toute autre VCS pour pousser les codes du local au serveur, ce que vous pouvez faire est d'ajouter le fichier de paramètres .gitignore.
Cela vous permettra d'avoir un contenu différent dans les deux endroits, sans aucun problème. DONC sur le serveur, vous pouvez configurer une version autonome de settings.py et toutes les modifications effectuées dans les locaux de l'habitude de réfléchir sur le serveur et vice versa.
En outre, il supprime les settings.py fichier à partir de github aussi, le gros défaut, j'ai vu beaucoup de débutants font.
J'ai eu mes paramètres réparti comme suit
Nous avons 3 environnements
Maintenant, évidemment, de production et de transfert doit avoir le maximum d'environnement similaire. Si nous avons gardé
prod.py
pour les deux.Mais il y avait un cas où j'ai eu à identifier serveur est un serveur de production. @T. Pierre 's réponse m'a aidé à écrire vérifier comme suit.
1 - Créer un nouveau dossier à l'intérieur de votre application et les paramètres de nom à elle.
2 - Maintenant, créez un nouveau init.py fichier et à l'intérieur d'écrire
3 - la création de trois nouveaux fichiers dans le dossier paramètres de nom local.py et production.py et base.py
4 - à l'Intérieur base.py copiez l'intégralité du contenu des paramètres précédents.p dossier et renommez-le avec quelque chose de différent, disons old_settings.py
5 - Dans base.py changer votre BASE_DIR chemin pour pointer vers votre nouveau chemin de réglage
Vieux-chemin-> BASE_DIR = os.chemin d'accès.dirname(os.chemin d'accès.dirname(os.chemin d'accès.abspath(fichier)))
Nouveau chemin d'accès -> BASE_DIR = os.chemin d'accès.dirname(os.chemin d'accès.dirname(os.chemin d'accès.dirname(os.chemin d'accès.abspath(fichier)))
maintenant de cette façon, le projet dir peuvent être structurés et peuvent être gérable entre la production et le développement local.
De faire plusieurs versions de settings.py est un anti-modèle pour 12 Facteur d'Application de la méthodologie.
utilisation python-découpler ou django-environ à la place.
Je pense que la meilleure solution est suggéré par @T. Pierre, mais je ne sais pas pourquoi, il suffit de ne pas utiliser l'indicateur de DÉBOGAGE dans Django. J'Écris le code ci-dessous pour mon site:
Toujours les solutions les plus simples sont mieux que complexes.
J'ai trouvé les réponses ici très utile. (Cela a été plus définitivement résolu? La dernière réponse il y a un an.) Après avoir tenu compte de toutes les approches présentées, j'ai trouvé une solution que je n'ai pas la liste ici.
Mes critères étaient les suivants:
Je pensais que la commutation sur la machine hôte avait un sens, mais alors pensé que la vraie question ici est différents réglages pour environnements, et a un moment aha. J'ai mis ce code à la fin de mon settings.py fichier:
De cette façon, l'application par défaut pour les paramètres de production, ce qui signifie que vous sont explicitement "liste blanche" de votre environnement de développement. Il est beaucoup plus sûr d'oublier de définir la variable d'environnement au niveau local que si c'était l'autre manière autour de vous et vous avez oublié de mettre quelque chose dans la production et la laisser certains dev paramètres utilisés.
Lors de l'élaboration localement, soit à partir de la coquille ou dans un .bash_profile ou l'endroit d'où:
(Ou si vous êtes en développement sur Windows, réglée par l'intermédiaire du Panneau de Contrôle ou quelle que soit sa appelé ces jours... Windows a toujours fait si obscur que vous pouvez définir des variables d'environnement.)
Avec cette approche, la dev paramètres sont tous dans un (standard) place, et il suffit de remplacer la production en cas de besoin. Tout autour de déblayage avec les paramètres de développement devrait être totalement à l'abri de commettre à la source de contrôle n'ayant pas d'impact sur la production.