私はまったく同じ問題を抱えています。ここでは、ユーザーごとに固有のデータベースを作成したいと考えています。これを行う理由は、ユーザーが複数のデータベースを必要とするサーバー上に格納されていないデータベースとの間で保存/アクセスする機能を提供しているためです。
この回答は、望ましい目標を達成するための推奨方法ではありません。私は、この問題に最善のアプローチで、どのようにジャンゴ・グールから聞くのが大好きです。しかし、これは私が使ってきた解決策であり、これまでのところうまくいきました。私はsqliteを使用していますが、どのデータベースでも簡単に変更できます。サーバーが再起動されたとき(実行時に)リロードのために、これらの設定を保存するためのファイルを作成します
- (実行時に)設定に新しいデータベースを追加
:
要するに
が、これはプロセスであり、
- ラン(サーバーが再起動されるたびに)保存した設定ファイルをロードするスクリプト今
、どのようにこれを達成するために:
1)まず、新しいユーザーが作成されると、設定で新しいデータベースが作成されます。このコードは、新しいユーザーが作成される私の視点にあります。
from YOUR_PROJECT_NAME import settings
database_id = user.username #just something unique
newDatabase = {}
newDatabase["id"] = database_id
newDatabase['ENGINE'] = 'django.db.backends.sqlite3'
newDatabase['NAME'] = '/path/to/db_%s.sql' % database_id
newDatabase['USER'] = ''
newDatabase['PASSWORD'] = ''
newDatabase['HOST'] = ''
newDatabase['PORT'] = ''
settings.DATABASES[database_id] = newDatabase
save_db_settings_to_file(newDatabase) #this is for step 2)
このスクリプトは、「実行時に」データベース設定をdjangoプロジェクト設定に読み込みます。ただし、サーバーを再起動すると、このデータベースは設定されなくなります。
2)サーバーを再起動するたびにこれらの設定を自動的に再読み込みするために、サーバーを起動するたびに読み込まれるデータベースごとにファイルを作成します。このファイルを作成する機能save_db_settings_to_file
によって実行されます。
def save_db_settings_to_file(db_settings):
path_to_store_settings = "/path/to/your/project/YOUR_PROJECT_NAME/database_settings/"
newDbString = """
DATABASES['%(id)s'] = {
'ENGINE': '%(ENGINE)s', # Add 'postgresql_psycopg2', 'mysql', 'sqlite3' or 'oracle'.
'NAME': '%(NAME)s', # Or path to database file if using sqlite3.
'USER': '', # Not used with sqlite3.
'PASSWORD': '', # Not used with sqlite3.
'HOST': '', # Set to empty string for localhost. Not used with sqlite3.
'PORT': '', # Set to empty string for default. Not used with sqlite3.
}
""" % db_settings
file_to_store_settings = os.path.join(path_to_store_settings, db_settings['id'] + ".py")
write_file(file_to_store_settings, newDbString) #psuedocode for compactness
3)実際にサーバが起動されたとき、私は設定フォルダ内の各ファイルをロードし/path/to/your/project/YOUR_PROJECT_NAME/settings.py
の一番下に単一の行を追加します。これらの設定をロードするにはそれを実行して、データベースの詳細を設定にロードする効果があります。
from settings import DATABASES
import os
path_to_store_settings = "/path/to/your/project/YOUR_PROJECT_NAME/database_settings/"
for fname in os.listdir(path_to_settings):
full_path = os.path.join(path_to_settings, fname)
f = open(full_path)
content = f.read()
f.close()
exec(content) #you'd better be sure that the file doesn't contain anything malicious
(注)import文の代わりにsettings.pyの下部に直接コードを入れることができます:
import settings_manager
その後、import settings_manager
は、次のコードが含まれています/path/to/your/project/YOUR_PROJECT_NAME/settings_manager.py
でファイルをロードしますimport文を使用すると、settings.pyの抽象レベルが一貫して保持されます。
これは、各データベース設定をロードする便利な方法です。設定からデータベースを削除するには、設定ファイルを削除し、次にサーバーを再起動してもその詳細を設定にロードしないためですデータベースにはアクセスできません。
私が言ったように、これはうまくいきましたが、今までそれを使って成功しましたが、これは理想的な解決策ではありません。私は誰かがより良い解決策を投稿できるかどうか本当に感謝します。
それについて悪い何ですか:
- それは明示的に実行時に設定を変更しないDjangoのチームからのアドバイスを挑みます。私はこのアドバイスが与えられた理由を知らない。
exec
ステートメントを使用してデータを設定に読み込みます。これは問題ありませんが、これらのファイルのいずれかに壊れたコードや悪質なコードが含まれていると、悲しいパンダになります。
私はまだauthとsessionsデータにデフォルトのデータベースを使用していますが、自分のアプリケーションのすべてのデータはユーザー固有のデータベースに保存されています。
なぜ複数のデータベースを使用する必要がありますか?各顧客の情報を保持するためにアプリモデルのスキーマを調整できない理由はありますか?顧客ごとに複数のデータベースを持つことは非常に不規則です。 –
私は現時点で適切なアーキテクチャを決定しようとしています。私は複数のデータベースを使用する必要はありませんが、ポータブル、オンライン、オフラインのサービスを提供するオプションの1つです。そして、この目的のために、私はそれが可能かどうかを知りたいのですが、それは概念的にはかなり簡単ですが、実際には一般的な枠組みでこれをサポートするのは難しいかもしれないので、誰かが前にこのようなことをしていれば、 – nickjb
[Django:dynamic database file](http://stackoverflow.com/questions/14254315/django-dynamic-database-file)の重複可能性があります(注:リンクされた質問は適切な解決策を提供するようですが、 – mgibsonbr