おそらく、新しい機能を有効にする際の最大のリスクは、新しいコードに必要なデータベースの変更にあります。Rails では、開発ホストをプログラムで変更し、改訂されたスキーマを使用するコードと共に同じ変更をライブにできる「移行」があると思います。必要に応じて、両方を同期してロールバックします。
PHP/MySQL 用の同様のツールセットを見つけた人はいますか? それについて、またはリスクを軽減するのに役立つプログラムまたはプロセスソリューションについて聞きたいです...
私はその仕事をするツールに出くわしたことがありません。代わりに、実行する順序がわかるように番号が付けられた個々のファイルを使用しました。基本的に、Rails移行の手動バージョンですが、ロールバックはありません。
これが私が話しているようなものです:
000-clean.sql # wipe out everything in the DB
001-schema.sql # create the initial DB objects
002-fk.sql # apply referential integrity (simple if kept separate)
003-reference-pop.sql # populate reference data
004-release-pop.sql # populate release data
005-add-new-table.sql # modification
006-rename-table.sql # another modification...
私は実際にこれを行うのに問題に遭遇したことはありませんが、それはあまりエレガントではありません。特定の更新に対してどのスクリプトを実行する必要があるかを追跡するのはあなた次第です(よりスマートな番号付けスキームが役立つ場合があります)。また、ソース管理でも正常に機能します。
本番データベースは開発DBとは異なる値を持つ可能性が高いため、(自動番号列からの)代理キー値の処理は面倒な場合があります。そのため、可能な限り、変更スクリプトでリテラルの代理キー値を参照しないようにしています。
プログラムによる移行は信用できません。NULLable 列を追加するなどの単純な変更の場合は、ライブ サーバーに直接追加するだけです。より複雑な場合やデータの変更が必要な場合は、SQL 移行ファイルのペアを作成し、レプリカ データベースに対してテストします。
移行を使用する場合は、常にロールバック移行をテストしてください。それはあなたの非常用の「クソ」ボタンです。
以前にこのツールを使用したことがあり、完全に機能しました。
DB 接続または SQL ファイルのいずれかを入力として取り、それを同じもの (別の DB 接続または別の SQL ファイル) と比較します。SQL を吐き出して変更を加えたり、変更を加えたりすることができます。
@[ユーコンデュード]
私自身 Perl を使用しており、Rails スタイルの移行も同様に半手動で行ってきました。
私がしたことは、現在のスキーマ バージョンである 1 つの数字の 1 つの行を含む、1 つの列「バージョン」を持つ 1 つのテーブル「バージョン」を持つことでした。次に、その番号を読み取り、特定のディレクトリを調べ、番号付きのすべての移行を適用してそこからここに移動する (そして番号を更新する) スクリプトを作成するのは (非常に) 簡単でした。
私の開発/ステージ環境では、頻繁に (別のスクリプトを介して) 運用データをステージング データベースにプルし、移行スクリプトを実行します。ライブに移行する前にこれを行うと、移行が確実に機能するようになります。明らかに、ステージング環境で広範囲にテストします。
新しいコードと必要な移行を 1 つのバージョン管理タグの下にタグ付けします。ステージまたはライブにデプロイするには、すべてをこのタグに更新し、移行スクリプトをかなり迅速に実行します。(本当に奇抜なスキーマ変更である場合は、短いダウンタイムを設定した方がよいかもしれません。)
私が使用する解決策 (元々は私の友人によって開発されたもの) は、yukondude の別の補遺です。
スキーマ ディレクトリ内のファイル:
0-init.sql 1-add-name-to-user.sql 2-add-bio.sql
典型的なファイルがどのように見えるか、すべての .sql ファイルの最後にある db_schema の更新に注意してください。
BEGIN;
-- comment about what this is doing
ALTER TABLE user ADD COLUMN bio text NULL;
UPDATE db_schema SET version = 2;
COMMIT;
「現在の」スクリプト (psql 用):
#!/bin/sh
VERSION=`psql -q -t <<EOF
\set ON_ERROR_STOP on
SELECT version FROM db_schema;
EOF
`
[ $? -eq 0 ] && {
echo $VERSION
exit 0
}
echo 0
更新スクリプト (psql も):
#!/bin/sh
CURRENT=`./current`
LATEST=`ls -vr *.sql |egrep -o "^[0-9]+" |head -n1`
echo current is $CURRENT
echo latest is $LATEST
[[ $CURRENT -gt $LATEST ]] && {
echo That seems to be a problem.
exit 1
}
[[ $CURRENT -eq $LATEST ]] && exit 0
#SCRIPT_SET="-q"
SCRIPT_SET=""
for (( I = $CURRENT + 1 ; I <= $LATEST ; I++ )); do
SCRIPT=`ls $I-*.sql |head -n1`
echo "Adding '$SCRIPT'"
SCRIPT_SET="$SCRIPT_SET $SCRIPT"
done
echo "Applying updates..."
echo $SCRIPT_SET
for S in $SCRIPT_SET ; do
psql -v ON_ERROR_STOP=TRUE -f $S || {
echo FAIL
exit 1
}
done
echo OK
私の 0-init.sql には、最初の「UPDATE db_schema SET version = 0;」とともに完全な初期スキーマ構造があります。これらのスクリプトを MySQL 用に変更するのはそれほど難しいことではありません。私の場合、私も持っています
export PGDATABASE="dbname" export PGUSER="mike"
私の.bashrcで。また、実行中のファイルごとにパスワードの入力を求めます。
SQLyogを使用して構造をコピーします。常に、最初にバックアップを作成することを繰り返します。
Lot105が説明したものとほぼ同じです。
各移行には適用およびロールバック スクリプトが必要であり、適用する必要がある移行をチェックして適切な順序で適用する何らかの制御スクリプトがあります。
各開発者は、このスキームを使用してデータベースの同期を維持し、本番環境に適用されると、関連する変更が適用されます。ロールバック スクリプトは、必要に応じて変更を取り消すために保持できます。
一部の変更は、sqldiff のようなツールが生成する単純な ALTER スクリプトでは実行できません。一部の変更では、スキーマの変更は必要ありませんが、既存のデータに対するプログラムによる変更が必要です。したがって、一般化することはできません。そのため、人間が編集したスクリプトが必要です。
Symfony には、基本的な移行を処理する sfMigrationsLight というプラグインがあります。CakePHP にはマイグレーションもあります。
何らかの理由で、移行サポートは、PHP フレームワークや ORM のほとんどで最優先事項ではありませんでした。
私は常に、開発サイトがライブサイトと同じDBを指すようにすることを好みました。これは最初は危険に聞こえるかもしれませんが、実際には多くの問題を解決します。同じサーバー上に同じDBを指す2つのサイトがある場合、ユーザーが稼働したときに表示される内容をリアルタイムで正確に表示できます。
データベースは1つだけであり、テーブルから列を削除しないというポリシーを設定している限り、新しいコードが使用しているデータベースと一致することがわかります。
また、移行時の混乱も大幅に少なくなります。PHPスクリプトを移動するだけで、同じDBを使用してすでにテストされています。
また、ユーザーのアップロードのターゲットとなるフォルダーへのシンボリックリンクを作成する傾向があります。これは、どのユーザーファイルが更新されたかについて混乱がないことを意味します。
もう1つの副作用は、「ベータテスター」の小グループを移植して、サイトを日常的に使用するオプションです。これは、一般公開前に実装できる多くのフィードバックにつながる可能性があります。
これはすべての場合に機能するとは限りませんが、すべての更新をこのモデルに移動し始めました。これにより、開発とリリースがはるかにスムーズになりました。
過去に、移行を XML ファイルとして構成する Java ベースのツールであるLiquiBaseを使用しました。必要な SQL を生成できます。
今日は、Ruby に似た移行機能を持つDoctrine 2ライブラリを使用します。
Symfony 2フレームワークには、スキーマの変更を処理する優れた方法もあります。そのコマンド ライン ツールは、既存のスキーマを分析し、SQL を生成してデータベースを変更されたスキーマ定義に一致させることができます。