Quelle est la méthode recommandée pour gérer les paramètres du développement local et du serveur de production? Certains d'entre eux (comme les constantes, etc.) peuvent être modifiés / accessibles dans les deux, mais certains d'entre eux (comme les chemins d'accès aux fichiers statiques) doivent rester différents, et ne doivent donc pas être remplacés à chaque fois que le nouveau code est déployé.
Actuellement, j'ajoute toutes les constantes à settings.py
. Mais chaque fois que je change une constante localement, je dois la copier sur le serveur de production et éditer le fichier pour des changements spécifiques à la production ... :(
Edit: il semble qu'il n'y ait pas de réponse standard à cette question, j'ai accepté la méthode la plus populaire.
Réponses:
Dans
settings.py
:Vous pouvez remplacer ce qui est nécessaire dans
local_settings.py
; il devrait alors rester hors de votre contrôle de version. Mais comme vous mentionnez la copie, je suppose que vous n'en utilisez pas;)la source
settings_local
plutôt quelocal_settings
de le regroupersettings.py
dans des listes de dossiers alphabétiques. Gardezsettings_local.py
hors de contrôle de version en utilisant.gitignore
comme informations d'identification n'appartiennent pas à Git. Imaginez que vous les approvisionniez par accident. Je garde dans git un fichier modèle appelé à lasettings_local.py.txt
place.Two Scoops of Django: Best Practices for Django 1.5 suggère d'utiliser le contrôle de version pour vos fichiers de paramètres et de stocker les fichiers dans un répertoire séparé:
Le
base.py
fichier contient des paramètres communs (tels que MEDIA_ROOT ou ADMIN),local.py
etproduction.py
possède des paramètres spécifiques au site:Dans le fichier de base
settings/base.py
:Dans le fichier des paramètres de développement local
settings/local.py
:Dans le fichier de paramètres de production de fichiers
settings/production.py
:Ensuite, lorsque vous exécutez django, vous ajoutez l'
--settings
option:Les auteurs du livre ont également mis en place un exemple de modèle de mise en page de projet sur Github.
la source
--settings
chaque fois, vous pouvez définir laDJANGO_SETTINGS_MODULE
variable envvar. Cela fonctionne bien avec, par exemple, Heroku: définissez-le globalement en production, puis remplacez-le par dev dans votre fichier .env.DJANGO_SETTINGS_MODULE
env var est la meilleure idée ici, merci Simon.BASE_DIR
paramètres pouros.path.dirname(os.path.realpath(os.path.dirname(__file__) + "/.."))
from django.conf import settings
qui est un objet qui résume l'interface et découple le code de l'emplacement des paramètres, docs.djangoproject.com/en/dev/topics/settings/…Au lieu de
settings.py
, utilisez cette disposition:common.py
est l'endroit où vit la majeure partie de votre configuration.prod.py
importe tout de commun et remplace tout ce dont il a besoin pour remplacer:De même,
dev.py
importe toutcommon.py
et remplace tout ce dont il a besoin pour remplacer.Enfin,
__init__.py
c'est là que vous décidez quels paramètres charger, et c'est aussi où vous stockez les secrets (par conséquent, ce fichier ne doit pas être versionné):Ce que j'aime dans cette solution c'est:
common.py
.prod.py
, les choses spécifiques au développeur entrentdev.py
. C'est simple.common.py
dansprod.py
oudev.py
, et vous pouvez remplacer n'importe quoi dans__init__.py
.la source
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "foobar.settings")
foobar est un dossier avec un__init__.py
fichier et les paramètres est un dossier avec un__init__.py
fichier qui contient mes secrets et importe dev.py, qui importe ensuite common.py. EDIT Nevermind, je n'avais pas un module installé qui était nécessaire. Ma faute! Cela fonctionne très bien !!J'utilise une version légèrement modifiée du style de paramètres "if DEBUG" publié par Harper Shelby. Évidemment, en fonction de l'environnement (win / linux / etc.), Le code devra peut-être être légèrement modifié.
J'utilisais par le passé "if DEBUG" mais j'ai trouvé que de temps en temps je devais faire des tests avec DEUBG réglé sur False. Ce que je voulais vraiment distinguer si l'environnement était la production ou le développement, ce qui m'a donné la liberté de choisir le niveau DEBUG.
Je considérerais toujours cette méthode de configuration comme un travail en cours. Je n'ai vu aucune façon de gérer les paramètres de Django qui couvrait toutes les bases et en même temps, je n'ai pas été très compliqué à configurer (je ne suis pas en panne avec les méthodes des fichiers de paramètres 5x).
la source
os.environ['COMPUTERNAME']
ne fonctionne malheureusement pas sur PythonAnywhere. Vous obtenez une KeyError.J'utilise un settings_local.py et un settings_production.py. Après avoir essayé plusieurs options, j'ai constaté qu'il est facile de perdre du temps avec des solutions complexes lorsque le simple fait d'avoir deux fichiers de paramètres semble facile et rapide.
Lorsque vous utilisez mod_python / mod_wsgi pour votre projet Django, vous devez le 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, la vie devient facile. Modifiez simplement le fichier de paramètres approprié et redémarrez le serveur (le serveur de développement Django redémarrera automatiquement).
la source
python manage.py runserver
), quel fichier de paramètres utiliser?TL; DR: L'astuce est de modifier
os.environment
avant d'importersettings/base.py
n'importe quoisettings/<purpose>.py
, cela simplifiera grandement les choses.Le simple fait de penser à tous ces fichiers entrelacés me donne mal à la tête. Combiner, importer (parfois de manière conditionnelle), remplacer, corriger ce qui était déjà défini au cas où le
DEBUG
paramètre serait modifié ultérieurement. Quel cauchemard!Au fil des ans, je suis passé par toutes les différentes solutions. Ils fonctionnent tous un peu , mais sont si pénibles à gérer. WTF! Avons-nous vraiment besoin de tout ce tracas? Nous avons commencé avec un seul
settings.py
fichier. Maintenant, nous avons besoin d'une documentation juste pour combiner correctement tous ces éléments dans un ordre correct!J'espère que j'ai finalement atteint le (mon) sweet spot avec la solution ci-dessous.
Récapitulons les objectifs (certains communs, certains miens)
Gardez les secrets secrets - ne les stockez pas dans un repo!
Définissez / lisez les clés et les secrets via les paramètres d'environnement, style 12 facteurs .
Avoir des valeurs par défaut de secours raisonnables. Idéalement pour le développement local, vous n'avez besoin de rien de plus que les valeurs par défaut.
… Mais essayez de sécuriser la production par défaut. Il vaut mieux manquer un remplacement de paramètre localement, que de se rappeler de régler les paramètres par défaut en toute sécurité pour la production.
Avoir la possibilité de changer
DEBUG
/ désactiver d'une manière qui peut avoir un effet sur d'autres paramètres (par exemple en utilisant javascript compressé ou non).Le basculement entre les paramètres d'objectif, comme local / test / mise en scène / production, doit être basé uniquement sur
DJANGO_SETTINGS_MODULE
rien de plus.… Mais permettre un paramétrage plus poussé via des paramètres d'environnement tels que
DATABASE_URL
.… Leur permet également d'utiliser différents paramètres de finalité et de les exécuter localement côte à côte, par exemple. configuration de la production sur la machine du développeur local, pour accéder à la base de données de production ou aux feuilles de style compressées du test de fumée.
Échec si une variable d'environnement n'est pas explicitement définie (nécessitant une valeur vide au minimum), en particulier en production, par exemple.
EMAIL_HOST_PASSWORD
.Répondre à l'
DJANGO_SETTINGS_MODULE
ensemble par défaut dans manage.py pendant le démarrage du projet django-adminGardez les conditions au minimum, si la condition est le type d'environnement prévu (par exemple, pour le fichier journal de l'ensemble de production et sa rotation), remplacez les paramètres dans le fichier de paramètres proposé.
Ne pas
Ne laissez pas django lire le paramètre DJANGO_SETTINGS_MODULE dans un fichier.
Pouah! Pensez à quel point c'est méta. Si vous avez besoin d'un fichier (comme docker env), lisez-le dans l'environnement avant de démarrer un processus django.
Ne remplacez pas DJANGO_SETTINGS_MODULE dans votre code de projet / application, par exemple. basé sur le nom d'hôte ou le nom du processus.
Si vous êtes paresseux pour définir la variable d'environnement (comme pour
setup.py test
), faites-le dans l'outillage juste avant d'exécuter votre code de projet.Évitez la magie et la correction de la façon dont django lit ses paramètres, prétraitez les paramètres mais n'interférez pas par la suite.
Pas de bêtises logiques compliquées. La configuration doit être fixe et matérialisée et non calculée à la volée. Fournir un défaut par défaut est juste assez logique ici.
Voulez-vous vraiment déboguer, pourquoi localement vous avez un ensemble de paramètres correct mais en production sur un serveur distant, sur une centaine de machines, quelque chose de calculé différemment? Oh! Tests unitaires? Pour les paramètres? Sérieusement?
Solution
Ma stratégie consiste en un excellent environnement django utilisé avec
ini
des fichiers de style, fournissant desos.environment
valeurs par défaut pour le développement local, quelquessettings/<purpose>.py
fichiers minimaux et courts qui ont unimport settings/base.py
APRÈS leos.environment
a été créée à partir d' unINI
fichier. Cela nous donne effectivement une sorte d'injection de paramètres.L'astuce consiste à modifier
os.environment
avant d'importersettings/base.py
.Pour voir l'exemple complet, faites le repo: https://github.com/wooyek/django-settings-strategy
settings / .env
A par défaut pour le développement local. Un fichier secret, pour définir principalement les variables d'environnement requises. Définissez-les sur des valeurs vides si elles ne sont pas requises dans le développement local. Nous fournissons des valeurs par défaut ici et ne
settings/base.py
pas échouer sur une autre machine si elles sont absentes de l'environnement.settings / local.py
Ce qui se passe ici, c'est charger l'environnement depuis
settings/.env
, puis importer les paramètres communs depuissettings/base.py
. Après cela, nous pouvons en remplacer quelques-uns pour faciliter le développement local.settings / production.py
Pour la production, nous ne devons pas nous attendre à un fichier d'environnement, mais il est plus facile d'en avoir un si nous testons quelque chose. Mais de toute façon, de peur de fournir peu de valeurs par défaut en ligne, vous
settings/base.py
pouvez donc réagir en conséquence.Le principal point d'intérêt ici est
DEBUG
etASSETS_DEBUG
remplace, ils seront appliqués au pythonos.environ
UNIQUEMENT s'ils sont MANQUANTS de l'environnement et du fichier.Ce seront nos valeurs par défaut de production, pas besoin de les mettre dans l'environnement ou le fichier, mais elles peuvent être remplacées si nécessaire. Soigné!
settings / base.py
Ce sont vos paramètres de django principalement vanille, avec quelques conditions et beaucoup de lecture à partir de l'environnement. Presque tout est là, en gardant tous les environnements prévus cohérents et aussi similaires que possible.
Les principales différences sont ci-dessous (j'espère qu'elles sont explicites):
Le dernier bit montre la puissance ici.
ASSETS_DEBUG
a une valeur par défaut raisonnable, qui peut être remplacéesettings/production.py
et même celle qui peut être remplacée par un paramètre d'environnement! Yay!En effet, nous avons une hiérarchie mixte d'importance:
la source
Je gère mes configurations à l'aide de django-split-settings .
Il s'agit d'un remplacement direct pour les paramètres par défaut. C'est simple, mais configurable. Et la refactorisation de vos paramètres existants n'est pas nécessaire.
Voici un petit exemple (fichier
example/settings/__init__.py
):C'est tout.
Mettre à jour
J'ai écrit un article de blog sur la gestion
django
des paramètres avecdjango-split-sttings
. Regarde!la source
uwsgi.ini
fichier a des paramètres différents dans dev / prod .. une idée de la façon de lui faire choisir des valeurs dans mon fichier de paramètres?Le problème avec la plupart de ces solutions est que vos paramètres locaux sont appliqués avant les plus courants ou après eux.
Il est donc impossible de remplacer des choses comme
en même temps.
Une solution peut être implémentée en utilisant des fichiers de configuration de style "ini" avec la classe ConfigParser. Il prend en charge plusieurs fichiers, l'interpolation de chaînes paresseuses, les valeurs par défaut et de nombreux autres avantages. Une fois un certain nombre de fichiers chargés, d'autres fichiers peuvent être chargés et leurs valeurs remplaceront les précédentes, le cas échéant.
Vous chargez un ou plusieurs fichiers de configuration, selon l'adresse de la machine, les variables d'environnement et même les valeurs des fichiers de configuration précédemment chargés. Ensuite, vous utilisez simplement 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 remplaçant éventuellement les valeurs de la précédente). Ce compte également pour les machines des développeurs, afin que chacun puisse configurer son pilote de base de données préféré, etc. pour le développement localcluster.cluster_name.ini
, qui peut définir des choses comme la base de données et les IP de cacheComme exemple de quelque chose que vous pouvez réaliser avec cela, vous pouvez définir une valeur de "sous-domaine" par env, qui est ensuite utilisée dans les paramètres par défaut (comme
hostname: %(subdomain).whatever.net
) pour définir tous les noms d'hôte et les cookies nécessaires que django doit fonctionner.C'est aussi sec que j'ai pu obtenir, la plupart des fichiers (existants) n'avaient que 3 ou 4 paramètres. En plus de cela, je devais gérer la configuration du client, donc un ensemble supplémentaire de fichiers de configuration (avec des choses comme les noms de base de données, les utilisateurs et les mots de passe, le sous-domaine attribué, etc.) existait, un ou plusieurs par client.
On peut faire évoluer cela aussi bas ou aussi haut que nécessaire, il vous suffit de mettre dans le fichier de configuration les clés que vous souhaitez configurer par environnement, et une fois qu'il y a besoin d'une nouvelle configuration, mettez la valeur précédente dans la configuration par défaut et remplacez-la Où il faut.
Ce système s'est révélé fiable et fonctionne bien avec le contrôle de version. Il est utilisé depuis longtemps pour gérer deux clusters d'applications distincts (15 instances distinctes ou plus du site django par machine), avec plus de 50 clients, où les clusters changeaient de taille et de membres en fonction de l'humeur de l'administrateur système. .
la source
config = ConfigParser.ConfigParser()
puis lire vos fichiersconfig.read(array_of_filenames)
et obtenir des valeurs en utilisantconfig.get(section, option)
. Vous commencez donc par charger votre configuration, puis vous l'utilisez pour lire les valeurs des paramètres.Je travaille également avec Laravel et j'aime l'implémentation là-bas. J'ai essayé de l'imiter et de le combiner avec la solution proposée par T. Stone (regardez ci-dessus):
Peut-être que quelque chose comme ça pourrait vous aider.
la source
N'oubliez pas que settings.py est un fichier de code en direct. En supposant que DEBUG n'est pas défini sur la production (ce qui est une bonne pratique), vous pouvez faire quelque chose comme:
Assez basique, mais vous pourriez, en théorie, aller jusqu'à n'importe quel niveau de complexité basé uniquement sur la valeur de DEBUG - ou toute autre variable ou vérification de code que vous vouliez utiliser.
la source
Pour la plupart de mes projets, j'utilise le modèle suivant:
from settings_base import *
)(Pour exécuter manage.py avec des paramètres personnalisés fichier que vous utilisez simplement --settings option de commande:
manage.py <command> --settings=settings_you_wish_to_use.py
)la source
Ma solution à ce problème est également un mélange de solutions déjà énoncées ici:
local_settings.py
qui a le contenuUSING_LOCAL = True
en dev etUSING_LOCAL = False
en prodsettings.py
je fais une importation sur ce fichier pour obtenir leUSING_LOCAL
réglageJe base ensuite tous mes paramètres dépendants de l'environnement sur celui-ci:
Je préfère cela à deux fichiers settings.py distincts que je dois conserver car je peux garder mes paramètres structurés dans un seul fichier plus facilement que de les répartir sur plusieurs fichiers. Ainsi, lorsque je mets à jour un paramètre, je n'oublie pas de le faire pour les deux environnements.
Bien sûr, chaque méthode a ses inconvénients et celle-ci ne fait pas exception. Le problème ici est que je ne peux pas écraser le
local_settings.py
fichier chaque fois que je pousse mes modifications en production, ce qui signifie que je ne peux pas simplement copier tous les fichiers à l'aveugle, mais c'est quelque chose avec lequel je peux vivre.la source
J'utilise une variation de ce que jpartogi a mentionné ci-dessus, que je trouve un peu plus courte:
Fondamentalement, sur chaque ordinateur (développement ou production), j'ai le fichier hostname_settings.py approprié qui est chargé dynamiquement.
la source
Il existe également des paramètres Django Classy. Personnellement, j'en suis un grand fan. Il est construit par l'une des personnes les plus actives du Django IRC. Vous utiliseriez des variables d'environnement pour définir les choses.
http://django-classy-settings.readthedocs.io/en/latest/
la source
1 - Créez un nouveau dossier dans votre application et nommez-y les paramètres.
2 - Maintenant, créez un nouveau
__init__.py
fichier dedans et écrivez dedans3 - Créez trois nouveaux fichiers dans le nom du dossier des paramètres
local.py
etproduction.py
etbase.py
.4 - À l'intérieur
base.py
, copiez tout le contenu dusettings.py
dossier précédent et renommez-le avec quelque chose de différent, disonsold_settings.py
.5 - Dans base.py, changez votre chemin BASE_DIR pour pointer vers votre nouveau chemin de réglage
Ancien chemin->
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
Nouveau chemin ->
BASE_DIR = os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
De cette façon, le répertoire du projet peut être structuré et gérable entre la production et le développement local.
la source
Afin d'utiliser une
settings
configuration différente sur un environnement différent, créez un fichier de paramètres différent. Et dans votre script de déploiement, démarrez le serveur en utilisant un--settings=<my-settings.py>
paramètre, via lequel vous pouvez utiliser différents paramètres sur un environnement différent.Avantages de l'utilisation de cette approche :
Vos paramètres seront modulaires en fonction de chaque environnement
Vous pouvez importer le
master_settings.py
contenant la configuration de base dans leenvironmnet_configuration.py
et remplacer les valeurs que vous souhaitez modifier dans cet environnement.Si vous avez une énorme équipe, chaque développeur peut avoir le sien
local_settings.py
qu'il peut ajouter au référentiel de code sans risque de modifier la configuration du serveur. Vous pouvez ajouter ces paramètres locaux.gitnore
si vous utilisez git ou.hginore
si vous Mercurial pour le contrôle de version (ou tout autre). De cette façon, les paramètres locaux ne feront même pas partie de la base de code réelle en le maintenant propre.la source
J'ai eu mes paramètres divisés comme suit
Nous avons 3 environnements
Désormais, la mise en scène et la production devraient avoir le plus grand environnement similaire possible. Nous avons donc gardé
prod.py
deux.Mais il y a eu un cas où j'ai dû identifier le serveur en cours d'exécution comme un serveur de production. @T. La réponse de Stone m'a aidé à écrire le chèque comme suit.
la source
Je le différencie dans manage.py et j'ai créé deux fichiers de paramètres distincts: local_settings.py et prod_settings.py.
Dans manage.py, je vérifie si le serveur est un serveur local ou un serveur de production. S'il s'agit d'un serveur local, il chargerait local_settings.py et c'est un serveur de production qu'il chargerait prod_settings.py. En gros, voici à quoi cela ressemblerait:
J'ai trouvé qu'il était plus facile de séparer le fichier de paramètres en deux fichiers distincts au lieu de faire beaucoup d'if à l'intérieur du fichier de paramètres.
la source
Comme alternative pour maintenir un fichier différent si vous voulez: Si vous utilisez git ou tout autre VCS pour pousser les codes du local vers le serveur, ce que vous pouvez faire est d'ajouter le fichier de paramètres au .gitignore.
Cela vous permettra d'avoir un contenu différent aux deux endroits sans aucun problème. SO sur le serveur, vous pouvez configurer une version indépendante de settings.py et toutes les modifications apportées sur le local ne se refléteront pas sur le serveur et vice versa.
De plus, cela supprimera également le fichier settings.py de github, le gros défaut, ce que j'ai vu de nombreux débutants faire.
la source
La création de plusieurs versions de settings.py est un anti modèle pour la méthodologie 12 Factor App . utilisez plutôt python- decouple ou django-environ .
la source
Je pense que la meilleure solution est suggérée par @T. Stone, mais je ne sais pas pourquoi n'utilisez pas le drapeau DEBUG dans Django. J'écris le code ci-dessous pour mon site Web:
Les solutions simples sont toujours meilleures que les solutions complexes.
la source
J'ai trouvé les réponses ici très utiles. (Cela a-t-il été résolu de manière plus définitive? La dernière réponse remonte à un an.) Après avoir examiné toutes les approches répertoriées, j'ai trouvé une solution que je ne voyais pas répertoriée ici.
Mes critères étaient:
Je pensais que l'allumage de la machine hôte avait un certain sens, mais j'ai compris que le vrai problème ici était différents paramètres pour différents environnements , et j'ai eu un moment ah. J'ai mis ce code à la fin de mon fichier settings.py:
De cette façon, l'application utilise par défaut les paramètres de production, ce qui signifie que vous "mettez sur liste blanche" votre environnement de développement. Il est beaucoup plus sûr d'oublier de définir la variable d'environnement localement que si c'était l'inverse et vous avez oublié de définir quelque chose en production et de laisser certains paramètres de développement être utilisés.
Lors du développement local, à partir du shell ou dans un .bash_profile ou n'importe où:
(Ou si vous développez sous Windows, défini via le Panneau de configuration ou quel que soit son nom de nos jours ... Windows l'a toujours rendu si obscur que vous pouvez définir des variables d'environnement.)
Avec cette approche, les paramètres de développement sont tous au même endroit (standard) et remplacent simplement ceux de production là où cela est nécessaire. Tout déblayage avec des paramètres de développement doit être complètement sûr de s'engager dans le contrôle des sources sans impact sur la production.
la source