イントロダクションIntroduction
最近のウェブアプリケーションは、ほとんどすべてデータベースを操作します。Laravelは、素のSQL、Fluentクエリビルダ、Eloquent ORMを使用し、サポートしている様々なデータベースの操作をとてもシンプルにしています。現在、Laravelは5つのデータベースのファーストパーティーサポートを提供しています。Almost every modern web application interacts with a database. Laravel makes interacting with databases extremely simple across a variety of supported databases using raw SQL, a fluent query builder[/docs/{{version}}/queries], and the Eloquent ORM[/docs/{{version}}/eloquent]. Currently, Laravel provides first-party support for five databases:
- MariaDB 10.3+ (Version Policy)MariaDB 10.3+ (Version Policy[https://mariadb.org/about/#maintenance-policy])
- MySQL5.7以上 (バージョンポリシー)MySQL 5.7+ (Version Policy[https://en.wikipedia.org/wiki/MySQL#Release_history])
- PostgreSQL10.0以上 (バージョンポリシー)PostgreSQL 10.0+ (Version Policy[https://www.postgresql.org/support/versioning/])
- SQLite3.8.8以上SQLite 3.8.8+
- SQL Server2017以上 (バージョンポリシー)SQL Server 2017+ (Version Policy[https://docs.microsoft.com/en-us/lifecycle/products/?products=sql-server])
設定Configuration
Laravelのデータベースサービスの設定は、アプリケーションのconfig/database.php
設定ファイルにあります。このファイルは、全データベース接続を定義し、デフォルトで使用する接続を指定できます。このファイル内のほとんどの設定オプションは、アプリケーションの環境変数の値によって決まります。Laravelがサポートしているデータベースシステムのほとんどの設定例をこのファイルに用意しています。The configuration for Laravel's database services is located in your application's config/database.php
configuration file. In this file, you may define all of your database connections, as well as specify which connection should be used by default. Most of the configuration options within this file are driven by the values of your application's environment variables. Examples for most of Laravel's supported database systems are provided in this file.
デフォルトのLaravelのサンプル環境設定は、Laravel Sailで使用できるようになっています。SailはローカルマシンでLaravelアプリケーションを開発するためのDocker環境です。しかし、ローカルデータベースの必要に応じ、データベース設定を自由に変更してください。By default, Laravel's sample environment configuration[/docs/{{version}}/configuration#environment-configuration] is ready to use with Laravel Sail[/docs/{{version}}/sail], which is a Docker configuration for developing Laravel applications on your local machine. However, you are free to modify your database configuration as needed for your local database.
SQLite設定SQLite Configuration
SQLiteデータベースは、ファイルシステム上の単一ファイルに含まれます。ターミナルでtouch
コマンドを使用して新しいSQLiteデータベースを作成できます。(touch database/database.sqlite
)データベースを作成したあと、データベースへの絶対パスをDB_DATABASE
環境変数で指定することにより、このデータベースを使用するよう簡単に設定できます。SQLite databases are contained within a single file on your filesystem. You can create a new SQLite database using the touch
command in your terminal: touch database/database.sqlite
. After the database has been created, you may easily configure your environment variables to point to this database by placing the absolute path to the database in the DB_DATABASE
environment variable:
DB_CONNECTION=sqlite
DB_DATABASE=/absolute/path/to/database.sqlite
SQLite接続の外部キー制約を有効にするには、DB_FOREIGN_KEYS
環境変数をtrue
に設定する必要があります。To enable foreign key constraints for SQLite connections, you should set the DB_FOREIGN_KEYS
environment variable to true
:
DB_FOREIGN_KEYS=true
Microsoft SQLサーバ設定Microsoft SQL Server Configuration
Microsoft SQL Serverデータベースを使用するには、sqlsrv
、pdo_sqlsrv
PHP拡張機能と、Microsoft SQL ODBCドライバなど必要な依存関係パッケージを確実にインストールしてください。To use a Microsoft SQL Server database, you should ensure that you have the sqlsrv
and pdo_sqlsrv
PHP extensions installed as well as any dependencies they may require such as the Microsoft SQL ODBC driver.
URLを使用した設定Configuration Using URLs
通常、データベース接続は、host
、database
、username
、password
などの複数の設定値により構成します。こうした設定値には、それぞれ対応する環境変数があります。これは、運用サーバでデータベース接続情報を設定するときに、複数の環境変数を管理する必要があることを意味します。Typically, database connections are configured using multiple configuration values such as host
, database
, username
, password
, etc. Each of these configuration values has its own corresponding environment variable. This means that when configuring your database connection information on a production server, you need to manage several environment variables.
AWSやHerokuなどの一部のマネージドデータベースプロバイダは、データベースのすべての接続情報を単一の文字カラムで含む単一のデータベース「URL」を提供しています。データベースURLの例は、次のようになります。Some managed database providers such as AWS and Heroku provide a single database "URL" that contains all of the connection information for the database in a single string. An example database URL may look something like the following:
mysql://root:password@127.0.0.1/forge?charset=UTF-8
こうしたURLは通常、標準のスキーマ規約に従います。These URLs typically follow a standard schema convention:
driver://username:password@host:port/database?options
利便性のため、Laravelは複数の設定オプションを使用してデータベースを構成する代わりに、こうしたURLをサポートしています。url
(または対応するDATABASE_URL
環境変数)設定オプションが存在する場合は、データベース接続と接続情報を抽出するためにそれを使用します。For convenience, Laravel supports these URLs as an alternative to configuring your database with multiple configuration options. If the url
(or corresponding DATABASE_URL
environment variable) configuration option is present, it will be used to extract the database connection and credential information.
読み/書き接続Read & Write Connections
SELECTステートメントに1つのデータベース接続を使用し、INSERT、UPDATE、およびDELETEステートメントに別のデータベース接続を使用したい場合があるでしょう。Laravelでは簡単に、素のクエリ、クエリビルダ、もしくはEloquent ORMのいずれを使用していても常に適切な接続が使用されます。Sometimes you may wish to use one database connection for SELECT statements, and another for INSERT, UPDATE, and DELETE statements. Laravel makes this a breeze, and the proper connections will always be used whether you are using raw queries, the query builder, or the Eloquent ORM.
読み取り/書き込み接続を設定する方法を確認するため、以下の例を見てみましょう。To see how read / write connections should be configured, let's look at this example:
'mysql' => [
'read' => [
'host' => [
'192.168.1.1',
'196.168.1.2',
],
],
'write' => [
'host' => [
'196.168.1.3',
],
],
'sticky' => true,
'driver' => 'mysql',
'database' => 'database',
'username' => 'root',
'password' => '',
'charset' => 'utf8mb4',
'collation' => 'utf8mb4_unicode_ci',
'prefix' => '',
],
設定配列には、read
、write
、sticky
の3キーが追加されていることに注目してください。read
キーとwrite
キーには、単一のキーとしてhost
を含む配列値があります。read
およびwrite
接続の残りのデータベースオプションは、メインのmysql
設定配列からマージされます。Note that three keys have been added to the configuration array: read
, write
and sticky
. The read
and write
keys have array values containing a single key: host
. The rest of the database options for the read
and write
connections will be merged from the main mysql
configuration array.
メインのmysql
配列の値をオーバーライドする場合にのみ、read
配列とwrite
配列へ項目を配置する必要があります。したがって、この場合、192.168.1.1
は「読み取り」接続のホストとして使用し、192.168.1.3
は「書き込み」接続に使用します。データベースの接続情報、プレフィックス、文字セット、およびメインのmysql
配列内の他のすべてのオプションは、両方の接続で共有されます。host
設定配列に複数の値が存在する場合、リクエストごとランダムにデータベースホストを選択します。You only need to place items in the read
and write
arrays if you wish to override the values from the main mysql
array. So, in this case, 192.168.1.1
will be used as the host for the "read" connection, while 192.168.1.3
will be used for the "write" connection. The database credentials, prefix, character set, and all other options in the main mysql
array will be shared across both connections. When multiple values exist in the host
configuration array, a database host will be randomly chosen for each request.
sticky
オプションThe sticky
Option
sticky
オプションは、現在のリクエストサイクル中にデータベースへ書き込まれたレコードをすぐに読み取るため使用するオプション値です。sticky
オプションが有効になっており、現在のリクエストサイクル中にデータベースへ対し「書き込み」操作が実行された場合、それ以降の「読み取り」操作では「書き込み」接続が使用されます。これにより、要求サイクル中に書き込まれたデータを、同じ要求中にデータベースからすぐに読み戻すことができます。これがアプリケーションにとって望ましい動作であるかどうかを判断するのは使用者の皆さん次第です。The sticky
option is an optional value that can be used to allow the immediate reading of records that have been written to the database during the current request cycle. If the sticky
option is enabled and a "write" operation has been performed against the database during the current request cycle, any further "read" operations will use the "write" connection. This ensures that any data written during the request cycle can be immediately read back from the database during that same request. It is up to you to decide if this is the desired behavior for your application.
SQLクエリの実行Running SQL Queries
データベース接続を設定したら、DB
ファサードを使用してクエリが実行できます。DB
ファサードは、クエリのタイプごとにselect
、update
、insert
、delete
、statement
メソッドを提供しています。Once you have configured your database connection, you may run queries using the DB
facade. The DB
facade provides methods for each type of query: select
, update
, insert
, delete
, and statement
.
SELECTクエリの実行Running A Select Query
基本的なSELECTクエリを実行するには、DB
ファサードでselect
メソッドを使用します。To run a basic SELECT query, you may use the select
method on the DB
facade:
<?php
namespace App\Http\Controllers;
use App\Http\Controllers\Controller;
use Illuminate\Support\Facades\DB;
class UserController extends Controller
{
/**
* アプリケーションの全ユーザーのリストを表示
*
* @return \Illuminate\Http\Response
*/
public function index()
{
$users = DB::select('select * from users where active = ?', [1]);
return view('user.index', ['users' => $users]);
}
}
select
メソッドの最初の引数はSQLクエリであり、2番目の引数はクエリにバインドする必要のあるパラメータバインディングです。通常、これらは where
句の制約の値です。パラメータバインディングは、SQLインジェクションに対する保護を提供します。The first argument passed to the select
method is the SQL query, while the second argument is any parameter bindings that need to be bound to the query. Typically, these are the values of the where
clause constraints. Parameter binding provides protection against SQL injection.
select
メソッドは常に結果の配列
を返します。配列内の各結果は、データベースのレコードを表すPHPのstdClass
オブジェクトになります。The select
method will always return an array
of results. Each result within the array will be a PHP stdClass
object representing a record from the database:
use Illuminate\Support\Facades\DB;
$users = DB::select('select * from users');
foreach ($users as $user) {
echo $user->name;
}
スカラー値のセレクトSelecting Scalar Values
データベースへの問い合わせの結果が、単一のスカラー値であることがあります。Laravelでは、クエリのスカラー結果をレコードオブジェクトから取得する代わりに、scalar
メソッドを使用し、この値を直接取得できます。Sometimes your database query may result in a single, scalar value. Instead of being required to retrieve the query's scalar result from a record object, Laravel allows you to retrieve this value directly using the scalar
method:
$burgers = DB::scalar(
"select count(case when food = 'burger' then 1 end) as burgers from menu"
);
名前付きバインディングの使用Using Named Bindings
パラメータバインディングを表すために?
を使用する代わりに、名前付きバインディングを使用してクエリを実行できます。Instead of using ?
to represent your parameter bindings, you may execute a query using named bindings:
$results = DB::select('select * from users where id = :id', ['id' => 1]);
INSERT文の実行Running An Insert Statement
insert
ステートメントを実行するには、DB
ファサードでinsert
メソッドを使用します。select
と同様に、このメソッドはSQLクエリを最初の引数に取り、バインディングを2番目の引数に取ります。To execute an insert
statement, you may use the insert
method on the DB
facade. Like select
, this method accepts the SQL query as its first argument and bindings as its second argument:
use Illuminate\Support\Facades\DB;
DB::insert('insert into users (id, name) values (?, ?)', [1, 'Marc']);
更新文の実行Running An Update Statement
データベース内の既存のレコードを更新するには、update
メソッドを使用する必要があります。メソッドは実行の影響を受けた行数を返します。The update
method should be used to update existing records in the database. The number of rows affected by the statement is returned by the method:
use Illuminate\Support\Facades\DB;
$affected = DB::update(
'update users set votes = 100 where name = ?',
['Anita']
);
DELETE文の実行Running A Delete Statement
データベースからレコードを削除するには、delete
メソッドを使用する必要があります。update
と同様に、メソッドは影響を受けた行数を返します。The delete
method should be used to delete records from the database. Like update
, the number of rows affected will be returned by the method:
use Illuminate\Support\Facades\DB;
$deleted = DB::delete('delete from users');
一般的な文の実行Running A General Statement
一部のデータベース操作文は値を返しません。こうしたタイプの操作では、DB
ファサードでstatement
メソッドを使用します。Some database statements do not return any value. For these types of operations, you may use the statement
method on the DB
facade:
DB::statement('drop table users');
プリペアドではない文の実行Running An Unprepared Statement
値をバインドせずSQL文を実行したい場合があります。それには、DB
ファサードのunprepared
メソッドを使用します。Sometimes you may want to execute an SQL statement without binding any values. You may use the DB
facade's unprepared
method to accomplish this:
DB::unprepared('update users set votes = 100 where name = "Dries"');
Warning
Warning! プリペアドではない文はパラメーターをバインドしないため、SQLインジェクションに対して脆弱である可能性があります。プリペアドではない文内では、ユーザーの値のコントロールを許可しないでください。
Since unprepared statements do not bind parameters, they may be vulnerable to SQL injection. You should never allow user controlled values within an unprepared statement.
暗黙のコミットImplicit Commits
トランザクション内でDB
ファサードのstatement
およびunprepared
メソッドを使用する場合、暗黙のコミットを引き起こすステートメントを回避するように注意する必要があります。これらのステートメントにより、データベースエンジンはトランザクション全体を間接的にコミットし、Laravelはデータベースのトランザクションレベルを認識しなくなります。このようなステートメントの例は、データベーステーブルの作成です。When using the DB
facade's statement
and unprepared
methods within transactions you must be careful to avoid statements that cause implicit commits[https://dev.mysql.com/doc/refman/8.0/en/implicit-commit.html]. These statements will cause the database engine to indirectly commit the entire transaction, leaving Laravel unaware of the database's transaction level. An example of such a statement is creating a database table:
DB::unprepared('create table a (col varchar(1) null)');
暗黙的なコミットを引き起こす、すべてのステートメントのリストは、MySQLのマニュアルを参照してください。Please refer to the MySQL manual for a list of all statements[https://dev.mysql.com/doc/refman/8.0/en/implicit-commit.html] that trigger implicit commits.
複数データベース接続の使用Using Multiple Database Connections
アプリケーションがconfig/database.php
設定ファイルで複数の接続を定義している場合、DB
ファサードが提供するconnection
メソッドを介して各接続にアクセスできます。connection
メソッドに渡される接続名は、config/database.php
設定ファイルにリストしている接続、または実行時にconfig
ヘルパを使用して設定した接続の1つに対応している必要があります。If your application defines multiple connections in your config/database.php
configuration file, you may access each connection via the connection
method provided by the DB
facade. The connection name passed to the connection
method should correspond to one of the connections listed in your config/database.php
configuration file or configured at runtime using the config
helper:
use Illuminate\Support\Facades\DB;
$users = DB::connection('sqlite')->select(/* ... */);
接続インスタンスでgetPdo
メソッドを使用して、接続の基になる素のPDOインスタンスにアクセスできます。You may access the raw, underlying PDO instance of a connection using the getPdo
method on a connection instance:
$pdo = DB::connection()->getPdo();
クエリイベントのリッスンListening For Query Events
アプリケーションが実行するSQLクエリごとに呼び出すクロージャを指定する場合は、DB
ファサードのlisten
メソッドを使用します。このメソッドは、クエリのログ記録やデバッグに役立ちます。クエリリスナクロージャは、サービスプロバイダのboot
メソッドで登録します。If you would like to specify a closure that is invoked for each SQL query executed by your application, you may use the DB
facade's listen
method. This method can be useful for logging queries or debugging. You may register your query listener closure in the boot
method of a service provider[/docs/{{version}}/providers]:
<?php
namespace App\Providers;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\ServiceProvider;
class AppServiceProvider extends ServiceProvider
{
/**
* アプリケーションの全サービスの登録
*
* @return void
*/
public function register()
{
//
}
/**
* アプリケーションの全サービスの起動初期処理
*
* @return void
*/
public function boot()
{
DB::listen(function ($query) {
// $query->sql;
// $query->bindings;
// $query->time;
});
}
}
累積クエリ時間の監視Monitoring Cumulative Query Time
モダンなWebアプリケーションの一般的なパフォーマンスボトルネックは、データベースのクエリに費やす時間の長さです。幸いなことに、Laravelは、単一のリクエスト中にデータベースのクエリに時間がかかりすぎる場合、選んだクロージャやコールバックを呼び出せます。これを使うには、whenQueryingForLongerThan
メソッドへ、クエリ時間しきい値(ミリ秒単位)とクロージャを指定します。このメソッドは、サービスプロバイダのboot
メソッドで呼び出しますA common performance bottleneck of modern web applications is the amount of time they spend querying databases. Thankfully, Laravel can invoke a closure or callback of your choice when it spends too much time querying the database during a single request. To get started, provide a query time threshold (in milliseconds) and closure to the whenQueryingForLongerThan
method. You may invoke this method in the boot
method of a service provider[/docs/{{version}}/providers]:
<?php
namespace App\Providers;
use Illuminate\Database\Connection;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\ServiceProvider;
use Illuminate\Database\Events\QueryExecuted;
class AppServiceProvider extends ServiceProvider
{
/**
* アプリケーションの全サービスの登録
*
* @return void
*/
public function register()
{
//
}
/**
* アプリケーションの全サービスの初期起動
*
* @return void
*/
public function boot()
{
DB::whenQueryingForLongerThan(500, function (Connection $connection, QueryExecuted $event) {
// 開発チームへ通知を送る…
});
}
}
データベーストランザクションDatabase Transactions
DB
ファサードが提供するtransaction
メソッドを使用して、データベーストランザクション内で一連の操作を実行できます。トランザクションクロージャ内で例外が投げられた場合、トランザクションを自動的にロールバックし、その例外を再度投げます。クロージャが正常に実行されると、トランザクションを自動的にコミットします。transaction
メソッドの使用中にロールバックやコミットを手作業で実行する心配はありません。You may use the transaction
method provided by the DB
facade to run a set of operations within a database transaction. If an exception is thrown within the transaction closure, the transaction will automatically be rolled back and the exception is re-thrown. If the closure executes successfully, the transaction will automatically be committed. You don't need to worry about manually rolling back or committing while using the transaction
method:
use Illuminate\Support\Facades\DB;
DB::transaction(function () {
DB::update('update users set votes = 1');
DB::delete('delete from posts');
});
デッドロックの処理Handling Deadlocks
transaction
メソッドは、デッドロックが発生したときにトランザクションを再試行する回数をオプションとして、2番目の引数に取ります。試行回数が終了した場合は、例外を投げます。The transaction
method accepts an optional second argument which defines the number of times a transaction should be retried when a deadlock occurs. Once these attempts have been exhausted, an exception will be thrown:
use Illuminate\Support\Facades\DB;
DB::transaction(function () {
DB::update('update users set votes = 1');
DB::delete('delete from posts');
}, 5);
トランザクションを手作業で使用Manually Using Transactions
トランザクションを手作業で開始し、ロールバックとコミットを自分で完全にコントロールしたい場合は、DB
ファサードが提供するbeginTransaction
メソッドを使用します。If you would like to begin a transaction manually and have complete control over rollbacks and commits, you may use the beginTransaction
method provided by the DB
facade:
use Illuminate\Support\Facades\DB;
DB::beginTransaction();
rollBack
メソッドにより、トランザクションをロールバックできます。You can rollback the transaction via the rollBack
method:
DB::rollBack();
commit
メソッドにより、トランザクションをコミットできます。Lastly, you can commit a transaction via the commit
method:
DB::commit();
Note:
DB
ファサードのトランザクションメソッドは、クエリビルダとEloquent ORMの両方のトランザクションを制御します。Note
TheDB
facade's transaction methods control the transactions for both the query builder[/docs/{{version}}/queries] and Eloquent ORM[/docs/{{version}}/eloquent].
データベースCLIへの接続Connecting To The Database CLI
データベースのCLIに接続する場合は、db
Artisanコマンドを使用します。If you would like to connect to your database's CLI, you may use the db
Artisan command:
php artisan db
必要に応じて、データベース接続名を指定して、デフォルト接続以外のデータベースへ接続できます。If needed, you may specify a database connection name to connect to a database connection that is not the default connection:
php artisan db mysql
データベースの調査Inspecting Your Databases
Artisanのdb:show
コマンドと、db:table
コマンドを使用すると、データベースのサイズや種類、開いている接続の数、テーブルの概要など、データベースと関連するテーブルの貴重な情報を取得できます。データベースの概要を確認するには、db:show
コマンドを使用します。Using the db:show
and db:table
Artisan commands, you can get valuable insight into your database and its associated tables. To see an overview of your database, including its size, type, number of open connections, and a summary of its tables, you may use the db:show
command:
php artisan db:show
このコマンドで、どのデータベース接続を検査するかを--database
オプションを使い接続名で指定できます。You may specify which database connection should be inspected by providing the database connection name to the command via the --database
option:
php artisan db:show --database=pgsql
もし、このコマンドの出力にテーブルの行数とデータベースのビューの詳細を含めたい場合は、それぞれ--counts
と--views
オプションを指定します。大きなデータベースでは、行数やビューの詳細の取得に時間がかかることがあります。If you would like to include table row counts and database view details within the output of the command, you may provide the --counts
and --views
options, respectively. On large databases, retrieving row counts and view details can be slow:
php artisan db:show --counts --views
テーブルの概要Table Overview
データベース内の個々のテーブルの概要を知りたい場合には、db:table
Artisanコマンドを実行してください。このコマンドは、カラム、タイプ、属性、キー、インデックスを含む、データベーステーブルの一般的な概要を表示します。If you would like to get an overview of an individual table within your database, you may execute the db:table
Artisan command. This command provides a general overview of a database table, including its columns, types, attributes, keys, and indexes:
php artisan db:table users
データベースの監視Monitoring Your Databases
DB:monitor
Artisanコマンドを使用すると、データベースが指定した数以上の接続を開いて管理している場合、LaravelにIlluminate\Database\Events\DatabaseBusy
イベントを発行するように指示できます。Using the db:monitor
Artisan command, you can instruct Laravel to dispatch an Illuminate\Database\Events\DatabaseBusy
event if your database is managing more than a specified number of open connections.
利用するには、db:monitor
コマンドを毎分実行するようにタスクスケジュールしてください。このコマンドは、監視したいデータベース接続設定の名前と、イベントを発行するまで許容するオープン中の最大接続数を引数に取ります。To get started, you should schedule the db:monitor
command to run every minute[/docs/{{version}}/scheduling]. The command accepts the names of the database connection configurations that you wish to monitor as well as the maximum number of open connections that should be tolerated before dispatching an event:
php artisan db:monitor --databases=mysql,pgsql --max=100
このコマンドをスケジューリングするだけでは、オープン中接続数の警告通知を発行するには足りません。このコマンドは閾値を超えるオープン中接続数を持つデータベースと遭遇したとき、DatabaseBusy
イベントを発行します。あなたや開発チームに通知を送るために、アプリケーションのEventServiceProvider
内で、このイベントをリッスンする必要があります。Scheduling this command alone is not enough to trigger a notification alerting you of the number of open connections. When the command encounters a database that has an open connection count that exceeds your threshold, a DatabaseBusy
event will be dispatched. You should listen for this event within your application's EventServiceProvider
in order to send a notification to you or your development team:
use App\Notifications\DatabaseApproachingMaxConnections;
use Illuminate\Database\Events\DatabaseBusy;
use Illuminate\Support\Facades\Event;
use Illuminate\Support\Facades\Notification;
/**
* アプリケーションのその他の全イベントの登録
*
* @return void
*/
public function boot()
{
Event::listen(function (DatabaseBusy $event) {
Notification::route('mail', 'dev@example.com')
->notify(new DatabaseApproachingMaxConnections(
$event->connectionName,
$event->connections
));
});
}