Commit dc7aa25a by Carsten Brandt

Merge branch 'master' of github.com:yiisoft/yii2

* 'master' of github.com:yiisoft/yii2: (23 commits) datepicker should show empty field when value is empty string complete docs about Nav to include the style Update tutorial-mailing.md Reverted #3665 (reverted from commit 2aa39499) Unit test for `yii\console\controllers\AssetController` advanced Doc comments for `yii\console\controllers\AssetController` extended `yii\console\controllers\AssetController` now handles bundle files from external resources properly skip requirements checker test on HHVM Update README.md in guide-es [skip ci] Add helper-array.md in guide-es [skip ci] a note about database naming style Add syntax highlighting [skip ci] docs/guide-ja/tutorial-core-validators.md - completed [ci skip] docs/guide-ja/tutorial-core-validators.md - WIP [ci skip] docs/guide-ja/tutorial-core-validators.md - WIP [ci skip] Fixed `\yii\authclient\OAuth2::refreshAccessToken()` does not save fetched token `\yii\authclient\AuthAction::defaultCancelUrl()` changed to use `yii\web\User::loginUrl` MongoDB PHP extension min version raised up to 1.5.0 Были различные ссылки в русском гайде - привел все к английскому виду ссылки. Файлы по этим ссылкам еще не существуют поэтому переименовывать их и не нужно. Fixed typo. ...
parents fea4c8da 548e19ef
...@@ -168,7 +168,7 @@ Temas especiales ...@@ -168,7 +168,7 @@ Temas especiales
* **TBD** [Plantilla aplicación avanzada](tutorial-advanced-app.md) * **TBD** [Plantilla aplicación avanzada](tutorial-advanced-app.md)
* **TBD** [Creación de una aplicación desde cero](tutorial-start-from-scratch.md) * **TBD** [Creación de una aplicación desde cero](tutorial-start-from-scratch.md)
* **TBD** [Comandos de consola](tutorial-console.md) * **TBD** [Comandos de consola](tutorial-console.md)
* **TBD** [Validadores de base](tutorial-core-validators.md) * [Validadores del núcleo](tutorial-core-validators.md)
* **TBD** [Internacionalización](tutorial-i18n.md) * **TBD** [Internacionalización](tutorial-i18n.md)
* **TBD** [Envío de correos electrónicos](tutorial-mailing.md) * **TBD** [Envío de correos electrónicos](tutorial-mailing.md)
* **TBD** [Mejora del rendimiento](tutorial-performance-tuning.md) * **TBD** [Mejora del rendimiento](tutorial-performance-tuning.md)
...@@ -180,14 +180,14 @@ Temas especiales ...@@ -180,14 +180,14 @@ Temas especiales
Widgets Widgets
------- -------
* GridView: link to demo page * GridView: **TBD** link to demo page
* ListView: link to demo page * ListView: **TBD** link to demo page
* DetailView: link to demo page * DetailView: **TBD** link to demo page
* ActiveForm: link to demo page * ActiveForm: **TBD** link to demo page
* Pjax: link to demo page * Pjax: **TBD** link to demo page
* Menu: link to demo page * Menu: **TBD** link to demo page
* LinkPager: link to demo page * LinkPager: **TBD** link to demo page
* LinkSorter: link to demo page * LinkSorter: **TBD** link to demo page
* **TBD** [Bootstrap Widgets](bootstrap-widgets.md) * **TBD** [Bootstrap Widgets](bootstrap-widgets.md)
* **TBD** [Jquery UI Widgets](jui-widgets.md) * **TBD** [Jquery UI Widgets](jui-widgets.md)
...@@ -196,6 +196,6 @@ Clases auxiliares ...@@ -196,6 +196,6 @@ Clases auxiliares
----------------- -----------------
* [Información general](helper-overview.md) * [Información general](helper-overview.md)
* **TBD** [ArrayHelper](helper-array.md) * [ArrayHelper](helper-array.md)
* [Html](helper-html.md) * [Html](helper-html.md)
* [Url](helper-url.md) * [Url](helper-url.md)
ArrayHelper
===========
Adicionalmente al [rico conjunto de funciones para arrays de PHP](http://php.net/manual/es/book.array.php) Yii array helper proporciona
métodos estáticos adicionales permitiendo trabajar con arrays de manera más eficiente.
## Devolviendo Valores <a name="getting-values"></a>
Recuperar valores de un array, un objeto o una estructura compleja usando PHP estándar es bastante
repetitivo. Tienes que comprobar primero si una clave existe con `isset`, después devolver el valor si existe, si no,
devolver un valor por defecto:
```php
class User
{
public $name = 'Alex';
}
$array = [
'foo' => [
'bar' => new User(),
]
];
$value = isset($array['foo']['bar']->name) ? $array['foo']['bar']->name : null;
```
Yii proviene de un método muy conveniente para hacerlo:
```php
$value = ArrayHelper::getValue($array, 'foo.bar.name');
```
El primer argumento del método es de donde vamos a obtener el valor. El segundo argumento especifica como devolver el dato. Puede ser
de la siguiente manera:
- Nombre de la clave del array o de la propiedad del objeto para recuperar el valor.
- Conjunto de puntos separados por las claves del array o los nombres de las propiedades del objeto. Esto se ha usado en el ejemplo anterior.
- Un callback que devuelve un valor.
El callback se debería usar de la siguiente manera:
```php
$fullName = ArrayHelper::getValue($user, function ($user, $defaultValue) {
return $user->firstName . ' ' . $user->lastName;
});
```
El tercer argumento opcional es el valor por defecto el cual es `null` si no se especifica. Podría ser utilizado de la siguiente manera:
```php
$username = ArrayHelper::getValue($comment, 'user.username', 'Unknown');
```
En caso de que quieras coger un valor y luego removerlo inmediatamente del array puedes usar el método `remove`:
```php
$array = ['type' => 'A', 'options' => [1, 2]];
$type = ArrayHelper::remove($array, 'type');
```
Después de ejecutar el código el `$array` contendrá `['options' => [1, 2]]` y `$type` debe ser `A`. Tenga en cuenta que a diferencia del método
`getValue`, `remove` solo soporta nombres clave simples.
## Comprobando la Existencia de Claves <a name="checking-existence-of-keys"></a>
`ArrayHelper::keyExists` funciona de la misma manera que [array_key_exists](http://php.net/manual/es/function.array-key-exists.php)
excepto que también soporta case-insensitive para la comparación de claves. Por ejemplo,
```php
$data1 = [
'userName' => 'Alex',
];
$data2 = [
'username' => 'Carsten',
];
if (!ArrayHelper::keyExists('username', $data1, false) || !ArrayHelper::keyExists('username', $data2, false)) {
echo "Please provide username.";
}
```
## Recuperando Columnas <a name="retrieving-columns"></a>
A menudo necesitas obtener unos valores de una columna de las filas de datos u objetos de un array. Un ejemplo común es obtener una lista de IDs.
```php
$data = [
['id' => '123', 'data' => 'abc'],
['id' => '345', 'data' => 'def'],
];
$ids = ArrayHelper::getColumn($array, 'id');
```
El resultado será `['123', '345']`.
Si se requieren transformaciones adicionales o la manera de obtener el valor es complejo, se podría especificar como segundo argumento
una función anónima :
```php
$result = ArrayHelper::getColumn($array, function ($element) {
return $element['id'];
});
```
## Re-indexar Arrays <a name="reindexing-arrays"></a>
Con el fin de indexar un array según una clave especificada, se puede usar el método `index`. La entrada del array debe ser
multidimensional o un array de objetos. La clave puede ser un nombre clave del sub-array, un nombre de una propiedad del objeto, o
una función anónima que retorne el valor de la clave dado el elemento del array.
Si el valor de la clave es null, el correspondiente elemento del array será desechado y no se pondrá en el resultado. Por ejemplo,
```php
$array = [
['id' => '123', 'data' => 'abc'],
['id' => '345', 'data' => 'def'],
];
$result = ArrayHelper::index($array, 'id');
// el resultado es:
// [
// '123' => ['id' => '123', 'data' => 'abc'],
// '345' => ['id' => '345', 'data' => 'def'],
// ]
// usando función anónima
$result = ArrayHelper::index($array, function ($element) {
return $element['id'];
});
```
## Construyendo Mapas (Maps) <a name="building-maps"></a>
Con el fin de construir un mapa (pareja clave-valor) de un array multidimensional o un array de objetos puedes usar el método `map`.
Los parámetros `$from` y `$to` especifican los nombres de las claves o los nombres de las propiedades que serán configuradas en el mapa. Opcionalmente, se puede
agrupar en el mapa de acuerdo al campo de agrupamiento `$group`. Por ejemplo,
```php
$array = [
['id' => '123', 'name' => 'aaa', 'class' => 'x'],
['id' => '124', 'name' => 'bbb', 'class' => 'x'],
['id' => '345', 'name' => 'ccc', 'class' => 'y'],
);
$result = ArrayHelper::map($array, 'id', 'name');
// el resultado es:
// [
// '123' => 'aaa',
// '124' => 'bbb',
// '345' => 'ccc',
// ]
$result = ArrayHelper::map($array, 'id', 'name', 'class');
// el resultado es:
// [
// 'x' => [
// '123' => 'aaa',
// '124' => 'bbb',
// ],
// 'y' => [
// '345' => 'ccc',
// ],
// ]
```
## Ordenamiento Multidimensional <a name="multidimensional-sorting"></a>
El método `multisort` ayuda a ordenar un array de objetos o arrays anidados por una o varias claves. Por ejemplo,
```php
$data = [
['age' => 30, 'name' => 'Alexander'],
['age' => 30, 'name' => 'Brian'],
['age' => 19, 'name' => 'Barney'],
];
ArrayHelper::multisort($data, ['age', 'name'], [SORT_ASC, SORT_DESC]);
```
Después del ordenado obtendremos lo siguiente en `$data`:
```php
[
['age' => 19, 'name' => 'Barney'],
['age' => 30, 'name' => 'Brian'],
['age' => 30, 'name' => 'Alexander'],
];
```
El segundo argumento que especifica las claves para ordenar puede ser una cadena si se trata de una clave, un array en caso de que tenga múltiples claves
o una función anónima como la siguiente
```php
ArrayHelper::multisort($data, function($item) {
return isset($item['age']) ? ['age', 'name'] : 'name';
});
```
El tercer argumento es la dirección. En caso de ordenar por una clave podría ser `SORT_ASC` o
`SORT_DESC`. Si ordenas por múltiples valores puedes ordenar cada valor diferentemente proporcionando un array de
direcciones de ordenación.
El último argumento es un PHP sort flag que toma los mismos valores que los pasados a
PHP [sort()](http://php.net/manual/es/function.sort.php).
## Detectando Tipos de Array <a name="detecting-array-types"></a>
Es muy útil saber si un array es indexado o asociativo. He aquí un ejemplo:
```php
// sin claves especificadas
$indexed = ['Qiang', 'Paul'];
echo ArrayHelper::isIndexed($indexed);
// todas las claves son strings
$associative = ['framework' => 'Yii', 'version' => '2.0'];
echo ArrayHelper::isAssociative($associative);
```
## Codificación y Decodificación de Valores HTML <a name="html-encoding-values"></a>
Con el fin de codificar o decodificar caracteres especiales en un array de strings con entidades HTML puedes usar lo siguiente:
```php
$encoded = ArrayHelper::htmlEncode($data);
$decoded = ArrayHelper::htmlDecode($data);
```
Solo los valores se codifican por defecto. Pasando como segundo argumento `false` puedes codificar un array de claves también.
La codificación utilizará el charset de la aplicación y podría ser cambiado pasandole un tercer argumento.
## Fusionando Arrays <a name="merging-arrays"></a>
```php
/**
* Merges two or more arrays into one recursively.
* If each array has an element with the same string key value, the latter
* will overwrite the former (different from array_merge_recursive).
* Recursive merging will be conducted if both arrays have an element of array
* type and are having the same key.
* For integer-keyed elements, the elements from the latter array will
* be appended to the former array.
* @param array $a array to be merged to
* @param array $b array to be merged from. You can specify additional
* arrays via third argument, fourth argument etc.
* @return array the merged array (the original arrays are not changed.)
*/
public static function merge($a, $b)
```
## Convirtiendo Objetos a Arrays <a name="converting-objects-to-arrays"></a>
A menudo necesitas convertir un objeto o un array de objetos a un array. El caso más común es convertir los modelos de
active record con el fin de servir los arrays de datos vía API REST o utilizarlos de otra manera. El siguiente código
se podría utilizar para hacerlo:
```php
$posts = Post::find()->limit(10)->all();
$data = ArrayHelper::toArray($post, [
'app\models\Post' => [
'id',
'title',
// el nombre de la clave del resultado del array => nombre de la propiedad
'createTime' => 'created_at',
// el nombre de la clave del resultado del array => función anónima
'length' => function ($post) {
return strlen($post->content);
},
],
]);
```
El primer argumento contiene el dato que queremos convertir. En nuestro caso queremos convertir un modelo AR `Post`.
El segundo argumento es el mapeo de conversión por clase. Estamos configurando un mapeo para el modelo `Post`.
Cada array de mapeo contiene un conjunto de mapeos. Cada mapeo podría ser:
- Un campo nombre para incluir como está.
- Un par clave-valor del array deseado con un nombre clave y el nombre de la columna del modelo que tomará el valor.
- Un par clave-valor del array deseado con un nombre clave y una función anónima que retorne el valor.
El resultado de la conversión anterior será:
```php
[
'id' => 123,
'title' => 'test',
'createTime' => '2013-01-01 12:00AM',
'length' => 301,
]
```
Es posible proporcionar una manera predeterminada de convertir un objeto a un array para una clase especifica
mediante la implementación de la interfaz [[yii\base\Arrayable|Arrayable]] en esa clase.
...@@ -164,7 +164,7 @@ RESTful ウェブサービス ...@@ -164,7 +164,7 @@ RESTful ウェブサービス
* [アドバンストアプリケーションテンプレート](tutorial-advanced-app.md) * [アドバンストアプリケーションテンプレート](tutorial-advanced-app.md)
* [アプリケーションを一から構築する](tutorial-start-from-scratch.md) * [アプリケーションを一から構築する](tutorial-start-from-scratch.md)
* [コンソールコマンド](tutorial-console.md) * [コンソールコマンド](tutorial-console.md)
* **翻訳中** [コアのバリデータ](tutorial-core-validators.md) * [コアバリデータ](tutorial-core-validators.md)
* **翻訳中** [国際化](tutorial-i18n.md) * **翻訳中** [国際化](tutorial-i18n.md)
* **翻訳中** [メール](tutorial-mailing.md) * **翻訳中** [メール](tutorial-mailing.md)
* **翻訳中** [パフォーマンスチューニング](tutorial-performance-tuning.md) * **翻訳中** [パフォーマンスチューニング](tutorial-performance-tuning.md)
......
コアバリデータ
==============
Yii は、一般的に使われる一連のコアバリデータを提供しています。
コアバリデータは、主として、`yii\validators` 名前空間の下にあります。
長ったらしいバリデータクラス名を使う代りに、*エイリアス* を使って使用するコアバリデータを指定することが出来ます。
例えば、[[yii\validators\RequiredValidator]] クラスを参照するのに `required` というエイリアスを使うことが出来ます。
```php
public function rules()
{
return [
[['email', 'password'], 'required'],
];
}
```
[[yii\validators\Validator::builtInValidators]] プロパティがサポートされている全てのコアバリデータのエイリアスを宣言しています。
以下では、全てのコアバリデータについて、主な使用方法とプロパティを説明します。
## [[yii\validators\BooleanValidator|boolean]] <a name="boolean"></a>
```php
[
// データ型にかかわらず、"selected" が 0 または 1 であるかどうかチェック
['selected', 'boolean'],
// "deleted" が boolean 型であり、true または false であるかどうかチェック
['deleted', 'boolean', 'trueValue' => true, 'falseValue' => false, 'strict' => true],
]
```
このバリデータは、入力値が真偽値であるかどうかをチェックします。
- `trueValue`: *true* を表す値。デフォルト値は `'1'`
- `falseValue`: *false* を表す値。デフォルト値は `'0'`
- `strict`: 入力値の型が `trueValue``falseValue` の型と一致しなければならないかどうか。デフォルト値は `false`
> Note|注意: HTML フォームで送信されたデータ入力値は全て文字列であるため、通常は、[[yii\validators\BooleanValidator::strict|strict]] プロパティは false のままにすべきです。
## [[yii\captcha\CaptchaValidator|captcha]] <a name="captcha"></a>
```php
[
['verificationCode', 'captcha'],
]
```
このバリデータは、通常、[[yii\captcha\CaptchaAction]] および [[yii\captcha\Captcha]] と一緒に使われ、入力値が [[yii\captcha\Captcha|CAPTCHA]] ウィジェットによって表示された検証コードと同じであることを確認します。
- `caseSensitive`: 検証コードの比較で大文字と小文字を区別するかどうか。デフォルト値は false。
- `captchaAction`: CAPTCHA 画像を表示する [[yii\captcha\CaptchaAction|CAPTCHA action]] に対応する [ルート](structure-controllers.md#routes)。デフォルト値は `'site/captcha'`
- `skipOnEmpty`: 入力値が空のときに検証をスキップできるかどうか。デフォルト値は false で、入力が必須であることを意味します。
## [[yii\validators\CompareValidator|compare]] <a name="compare"></a>
```php
[
// "password" 属性の値が "password_repeat" 属性の値と同じであるかどうか検証する
['password', 'compare'],
// "age" が 30 以上であるかどうか検証する
['age', 'compare', 'compareValue' => 30, 'operator' => '>='],
]
```
このバリデータは指定された入力値を他の値と比較し、両者の関係が `operator` プロパティで指定されたものであることを確認します。
- `compareAttribute`: その値が比較対象となる属性の名前。
このバリデータが属性を検証するのに使用されるとき、このプロパティのデフォルト値はその属性の名前に接尾辞 `_repeat` を付けた名前になります。
例えば、検証される属性が `password` であれば、このプロパティのデフォルト値は `password_repeat` となります。
- `compareValue`: 入力値が比較される定数値。
このプロパティと `compareAttribute` の両方が指定された場合は、このプロパティが優先されます。
- `operator`: 比較演算子。デフォルト値は `==` で、入力値が `compareAttribute` の値または `compareValue` と等しいことを検証することを意味します。
次の演算子がサポートされています。
* `==`: 二つの値が等しいことを検証。厳密でない比較を行う。
* `===`: 二つの値が等しいことを検証。厳密な比較を行う。
* `!=`: 二つの値が等しくないことを検証。厳密でない比較を行う。
* `!==`: 二つの値が等しくないことを検証。厳密な比較を行う。
* `>`: 検証される値が比較される値よりも大きいことを検証する。
* `>=`: 検証される値が比較される値よりも大きいか等しいことを検証する。
* `<`: 検証される値が比較される値よりも小さいことを検証する。
* `<=`: 検証される値が比較される値よりも小さいか等しいことを検証する。
## [[yii\validators\DateValidator|date]] <a name="date"></a>
```php
[
[['from_date', 'to_date'], 'date'],
]
```
このバリデータは、入力値が正しい書式の date、time、または datetime であるかどうかをチェックします。
オプションとして、入力値を UNIX タイムスタンプに変換して、[[yii\validators\DateValidator::timestampAttribute|timestampAttribute]] によって指定された属性に保存することも出来ます。
- `format`: 検証される値が従っているべき日付・時刻の書式。
これには [ICU manual](http://userguide.icu-project.org/formatparse/datetime#TOC-Date-Time-Format-Syntax) で記述されている日付・時刻のパターンを使うことが出来ます。
あるいは、PHP の `Datetime` クラスによって認識される書式に接頭辞 `php:` を付けた文字列でも構いません。
サポートされている書式については、<http://php.net/manual/ja/datetime.createfromformat.php> を参照してください。
このプロパティが設定されていないときは、`Yii::$app->formatter->dateFormat` の値を取ります。
- `timestampAttribute`: このバリデータが入力された日付・時刻から変換した UNIX タイムスタンプを代入することが出来る属性の名前。
入力が必須でない場合には、date バリデータに加えて、default バリデータ (フィルタ) を追加すれば、空の入力値が `NULL` として保存されることを保証することが出来ます。
そうしないと、データベースに `0000-00-00` という日付が保存されたり、デートピッカーの入力フィールドが `1970-01-01` になったりしてしまいます。
```php
[['from_date', 'to_date'], 'default', 'value' => null],
```
## [[yii\validators\DefaultValueValidator|default]] <a name="default"></a>
```php
[
// 空のときは "age" を null にする
['age', 'default', 'value' => null],
// 空のときは "country" を "USA" にする
['country', 'default', 'value' => 'USA'],
// 空のときは "from" と "to" に今日から三日後・六日後の日付にする
[['from', 'to'], 'default', 'value' => function ($model, $attribute) {
return date('Y-m-d', strtotime($attribute === 'to' ? '+3 days' : '+6 days'));
}],
]
```
このバリデータはデータを検証しません。
その代りに、検証される属性が空のときに、その属性にデフォルト値を割り当てます。
- `value`: デフォルト値、または、デフォルト値を返す PHP コーラブル。
検証される属性が空のときにこのデフォルト値が割り当てられます。
PHP コーラブルのシグニチャは、次のものでなければなりません。
```php
function foo($model, $attribute) {
// ... $value を計算 ...
return $value;
}
```
> Info|情報: 値が空であるか否かを決定する方法については、独立したトピックとして、[空の入力値を扱う](input-validation.md#handling-empty-inputs) の節でカバーされています。
## [[yii\validators\NumberValidator|double]] <a name="double"></a>
```php
[
// "salary" が実数であるかどうかチェック
['salary', 'double'],
]
```
このバリデータは、入力値が実数値であるかどうかをチェックします。
[number](#number) バリデータと等価です。
- `max`: 上限値 (その値を含む)。
設定されていない場合は、バリデータが上限値をチェックしないことを意味します。
- `min`: 下限値 (その値を含む)。
設定されていない場合は、バリデータが下限値をチェックしないことを意味します。
## [[yii\validators\EmailValidator|email]] <a name="email"></a>
```php
[
// "email" が有効なメールアドレスであるかどうかチェック
['email', 'email'],
]
```
このバリデータは、入力値が有効なメールアドレスであるかどうかをチェックします。
- `allowName`: メールアドレスに表示名を許容するか否か (例えば、`John Smith <john.smith@example.com>`)。デフォルト値は false。
- `checkDNS`: メールのドメインが存在して A または MX レコードを持っているかどうかをチェックするか否か。
このチェックは、メールアドレスが実際には有効なものでも、一時的な DNS の問題によって失敗する場合があることに注意してください。
デフォルト値は false。
- `enableIDN`: 検証のプロセスが IDN (国際化ドメイン名) を考慮に入れるか否か。
デフォルト値は false。
IDN のバリデーションを使用するためには、`intl` PHP 拡張をインストールして有効化する必要があることに注意してください。そうしないと、例外が投げられます。
## [[yii\validators\ExistValidator|exist]] <a name="exist"></a>
```php
[
// a1 の値が属性 "a1" で表されるカラムに存在する必要がある
['a1', 'exist'],
// a1 の値が属性 "a2" で表されるカラムに存在する必要がある
['a1', 'exist', 'targetAttribute' => 'a2'],
// a1 の値が "a1" のカラム、a2 の値が "a2" のカラムに存在する必要がある
// 両者はともにエラーメッセージを受け取る
[['a1', 'a2'], 'exist', 'targetAttribute' => ['a1', 'a2']],
// a1 の値が "a1" のカラム、a2 の値が "a2" のカラムに存在する必要がある
// a1 のみがエラーメッセージを受け取る
['a1', 'exist', 'targetAttribute' => ['a1', 'a2']],
// a2 の値が "a2" のカラム、a1 の値が "a3" のカラムに存在する必要がある
// a1 がエラーメッセージを受け取る
['a1', 'exist', 'targetAttribute' => ['a2', 'a1' => 'a3']],
// a1 の値が "a1" のカラムに存在する必要がある
// a1 が配列である場合は、その全ての要素が "a1" のカラムに存在する必要がある
['a1', 'exist', 'allowArray' => true],
]
```
このバリデータは、入力値がテーブルのカラムに存在するかどうかをチェックします。
[アクティブレコード](db-active-record.md) モデルの属性に対してのみ働きます。
一つのカラムに対するバリデーションか、複数のカラムに対するバリデーションか、どちらかをサポートします。
- `targetClass`: 検証される入力値を探すために使用される [アクティブレコード](db-active-record.md) クラスの名前。
設定されていない場合は、現在検証されているモデルのクラスが使用されます。
- `targetAttribute`: `targetClass` において、入力値の存在を検証するために使用される属性の名前。
設定されていない場合は、現在検証されている属性の名前が使用されます。
複数のカラムの存在を同時に検証するために配列を使うことが出来ます。
配列の値は存在を検証するのに使用される属性であり、配列のキーはその値が検証される属性です。
キーと値が同じ場合は、値だけを指定することが出来ます。
- `filter`: 入力値の存在をチェックするのに使用される DB クエリに適用される追加のフィルタ。
これには、文字列、または、追加のクエリ条件を表現する配列を使うことが出来ます
(クエリ条件の書式については、[[yii\db\Query::where()]] を参照してください)。
または、`function ($query)` というシグニチャを持つ無名関数でも構いません。
`$query` は関数の中で修正できる [[yii\db\Query|Query]] オブジェクトです。
- `allowArray`: 入力値が配列であることを許容するか否か。
デフォルト値は false。
このプロパティが true で入力値が配列であった場合は、配列の全ての要素がターゲットのカラムに存在しなければなりません。
`targetAttribute` を配列で指定して複数のカラムに対して検証しようとしている場合は、このプロパティを true に設定することが出来ないことに注意してください。
## [[yii\validators\FileValidator|file]] <a name="file"></a>
```php
[
// "primaryImage" が PNG、JPG、または GIF 形式のアップロードされた
// 画像ファイルであり、ファイルサイズが 1MB 以下であるかどうかチェック
['primaryImage', 'file', 'extensions' => ['png', 'jpg', 'gif'], 'maxSize' => 1024*1024*1024],
]
```
このバリデータは、入力値がアップロードされた有効なファイルであるかどうかをチェックします。
- `extensions`: アップロードを許可されるファイル名拡張子のリスト。
リストは、配列、または、空白かカンマで区切られたファイル名拡張子からなる文字列 (例えば、"gif, jpg") で指定することが出来ます。
拡張子名は大文字と小文字を区別しません。
デフォルト値は null であり、すべてのファイル名拡張子が許可されることを意味します。
- `mimeTypes`: アップロードを許可されるファイルの MIME タイプのリスト。
リストは、配列、または、空白かカンマで区切られたファイルの MIME タイプからなる文字列 (例えば、"image/jpeg, image/png") で指定することが出来ます。
MIME タイプ名は大文字と小文字を区別しません。
デフォルト値は null であり、すべての MIME タイプが許可されることを意味します。
- `minSize`: アップロードされるファイルに要求される最小限のバイト数。
デフォルト値は null であり、下限値が無いことを意味します。
- `maxSize`: アップロードされるファイルに許可される最大限のバイト数。
デフォルト値は null であり、上限値が無いことを意味します。
- `maxFiles`: 指定された属性が保持しうる最大限のファイル数。
デフォルト値は 1 であり、入力値がアップロードされた一つだけのファイルでなければならないことを意味します。
この値が 2 以上である場合は、入力値は最大で `maxFiles` 数のアップロードされたファイルからなる配列でなければなりません。
- `checkExtensionByMimeType`: ファイルの MIME タイプでファイル拡張子をチェックするか否か。
MIME タイプのチェックから導かれる拡張子がアップロードされたファイルの拡張子と違う場合に、そのファイルは無効であると見なされます。
デフォルト値は true であり、そのようなチェックが行われることを意味します。
`FileValidator`[[yii\web\UploadedFile]] と一緒に使用されます。
ファイルのアップロードおよびアップロードされたファイルのバリデーションの実行に関する完全な説明は、[ファイルをアップロードする](input-file-upload.md) の節を参照してください。
## [[yii\validators\FilterValidator|filter]] <a name="filter"></a>
```php
[
// "username" と "email" の入力値をトリムする
[['username', 'email'], 'filter', 'filter' => 'trim', 'skipOnArray' => true],
// "phone" の入力値を正規化する
['phone', 'filter', 'filter' => function ($value) {
// 電話番号の入力値をここで正規化する
return $value;
}],
]
```
このバリデータはデータを検証しません。
代りに、入力値にフィルタを適用して、それを検証される属性に書き戻します。
- `filter`: フィルタを定義する PHP コールバック。
これには、グローバル関数の名前、無名関数などを指定することが出来ます。
関数のシグニチャは ``function ($value) { return $newValue; }` でなければなりません。
このプロパティは必須項目です。
- `skipOnArray`: 入力値が配列である場合にフィルタをスキップするか否か。
デフォルト値は false。
フィルタが配列の入力を処理できない場合は、このプロパティを true に設定しなければなりません。
そうしないと、何らかの PHP エラーが生じ得ます。
> Tip|ヒント: 入力値をトリムしたい場合は、[trim](#trim) バリデータを直接使うことが出来ます。
> Tip|ヒント: `filter` のコールバックに期待されるシグニチャを持つ PHP 関数が多数存在します。
> 例えば、型キャストを適用して (例えば、[intval](http://php.net/manual/ja/function.intval.php) や [boolval](http://php.net/manual/ja/function.boolval.php) などを使って) 属性が特定の型になるように保証したい場合は、それらの関数をクロージャで包む必要はなく、単にフィルタの関数名を指定するだけで十分です。
>
> ```php
> ['property', 'filter', 'filter' => 'boolval'],
> ['property', 'filter', 'filter' => 'intval'],
> ```
## [[yii\validators\ImageValidator|image]] <a name="image"></a>
```php
[
// "primaryImage" が適切なサイズの有効な画像であることを検証
['primaryImage', 'image', 'extensions' => 'png, jpg',
'minWidth' => 100, 'maxWidth' => 1000,
'minHeight' => 100, 'maxHeight' => 1000,
],
]
```
このバリデータは、入力値が有効な画像ファイルであるかどうかをチェックします。
これは [file](#file) バリデータを拡張するものであり、従って、そのプロパティの全てを継承しています。
それに加えて、画像の検証の目的に特化した次のプロパティをサポートしています。
- `minWidth`: 画像の幅の最小値。デフォルト値は null であり、下限値がないことを意味します。
- `maxWidth`: 画像の幅の最大値。デフォルト値は null であり、上限値がないことを意味します。
- `minHeight`: 画像の高さの最小値。デフォルト値は null であり、下限値がないことを意味します。
- `maxHeight`: 画像の高さの最大値。デフォルト値は null であり、上限値がないことを意味します。
## [[yii\validators\RangeValidator|in]] <a name="in"></a>
```php
[
// "level" が 1, 2 または 3 であるかどうかチェック
['level', 'in', 'range' => [1, 2, 3]],
]
```
このバリデータは、入力値が所与の値のリストにあるかどうかをチェックします。
- `range`: 与えられた値のリスト。この中に、入力値がなければならない。
- `strict`: 入力値と所与の値の比較が厳密でなければならない (型と値の両方が同じでなければならない) かどうか。
デフォルト値は false。
- `not`: 検証結果を反転すべきか否か。デフォルト値は false。
このプロパティが true に設定されているときは、入力値が所与の値のリストにない場合に検証が成功したとされます。
- `allowArray`: 入力値が配列であることを許可するかどうか。
このプロパティが true であるときに、入力値が配列である場合は、配列の全ての要素が所与の値のリストにある必要があり、そうでなければ検証は失敗します。
## [[yii\validators\NumberValidator|integer]] <a name="integer"></a>
```php
[
// "age" が整数であるかどうかチェック
['age', 'integer'],
]
```
このバリデータは入力値が整数であるかどうかをチェックします。
- `max`: 上限値 (その値を含む)。設定されていないときは、バリデータは上限をチェックしません。
- `min`: 下限値 (その値を含む)。設定されていないときは、バリデータは下限をチェックしません。
## [[yii\validators\RegularExpressionValidator|match]] <a name="match"></a>
```php
[
// "username" が英字から始まり、英字、数字、アンダーバーだけで構成されているかどうかチェック
['username', 'match', 'pattern' => '/^[a-z]\w*$/i']
]
```
このバリデータは、入力値が指定された正規表現に一致するかどうかをチェックします。
- `pattern`: 入寮値が一致すべき正規表現。このプロパティを設定することは必須です。そうしないと、例外が投げられます。
- `not`: 検証結果を反転すべきかどうか。
デフォルト値は false で、入力値がパターンに一致したときにだけ検証が成功することを意味します。
このプロパティが true に設定されているときは、入力値がパターンに一致しない場合にだけ検証が成功したと見なされます。
## [[yii\validators\NumberValidator|number]] <a name="number"></a>
```php
[
// "salary" が数値であるかどうかチェック
['salary', 'number'],
]
```
このバリデータは、入力値が数値であるかどうかをチェックします。[double](#double) バリデータと等価です。
- `max`: 上限値 (その値を含む)。設定されていないときは、バリデータは上限をチェックしません。
- `min`: 下限値 (その値を含む)。設定されていないときは、バリデータは下限をチェックしません。
## [[yii\validators\RequiredValidator|required]] <a name="required"></a>
```php
[
// "username" と "password" がともに空ではないことをチェックする
[['username', 'password'], 'required'],
]
```
このバリデータは、入力値が提供されており、空ではないことをチェックします。
- `requiredValue`: 入力値として要求される値。
このプロパティが設定されていない場合は、入力値が空ではいけないことを意味します。
- `strict`: 値を検証するときに、データ型をチェックするかどうか。デフォルト値は false。
`requiredValue` が設定されていない場合、このプロパティが true であるときは、バリデータは入力値が厳密な意味で null であるかどうかをチェックします。
一方、このプロパティが false であるときは、値が空か否かの判断に緩い規則を使います。
`requiredValue` が設定されている場合、このプロパティが true であるときは、入力値と `requiredValue` を比較するときに型のチェックを行います。
> Info|情報: 値が空であるか否かを決定する方法については、独立したトピックとして、[空の入力値を扱う](input-validation.md#handling-empty-inputs) の節でカバーされています。
## [[yii\validators\SafeValidator|safe]] <a name="safe"></a>
```php
[
// "description" を安全な属性としてマーク
['description', 'safe'],
]
```
このバリデータは検証を実行しません。
その代りに、このバリデータは、属性を [安全な属性](structure-models.md#safe-attributes) としてマークするために使われます。
## [[yii\validators\StringValidator|string]] <a name="string"></a>
```php
[
// "username" が、長さが 4 以上 24 以下の文字列であるかどうかチェック
['username', 'string', 'length' => [4, 24]],
]
```
このバリデータは、入力値が一定の長さを持つ有効な文字列であるかどうかをチェックします。
- `length`: 検証される入力文字列の長さの制限を指定します。
これは、次のいずれかの形式で指定することが出来ます。
* 一つの整数: 文字列がちょうどその長さでなければならない、その長さ。
* 一つの要素を持つ配列: 入力文字列の長さの最小値 (例えば、`[8]`)。これは `min` を上書きします。
* 二つの要素を持つ配列: 入力文字列の長さの最小値と最大値 (例えば、`[8, 128]`)。これは `min` と `max` の両方を上書きします。
- `min`: 入力文字列の長さの最小値。設定されていない時は、長さの下限値がないことを意味します。
- `max`: 入力文字列の長さの最大値。設定されていない時は、長さの上限値がないことを意味します。
- `encoding`: 検証される入力文字列の文字エンコーディング。設定されていない時は、アプリケーションの [[yii\base\Application::charset|charset]] の値が使われ、デフォルトでは `UTF-8` となります。
## [[yii\validators\FilterValidator|trim]] <a name="trim"></a>
```php
[
// "username" と "email" の前後にあるホワイトスペースをトリムする
[['username', 'email'], 'trim'],
]
```
このバリデータはデータの検証を実行しません。
その代りに、入力値の前後にあるホワイトスペースをトリムします。
入力値が配列であるときは、このバリデータによって無視されることに注意してください。
## [[yii\validators\UniqueValidator|unique]] <a name="unique"></a>
```php
[
// a1 の値が属性 "a1" で表されるカラムにおいてユニークである必要がある
['a1', 'unique'],
// a1 の値が属性 "a2" で表されるカラムにおいてユニークである必要がある
['a1', 'unique', 'targetAttribute' => 'a2'],
// a1 の値が "a1" のカラム、a2 の値が "a2" のカラムにおいてユニークである必要がある
// 両者はともにエラーメッセージを受け取る
[['a1', 'a2'], 'unique', 'targetAttribute' => ['a1', 'a2']],
// a1 の値が "a1" のカラム、a2 の値が "a2" のカラムにおいてユニークである必要がある
// a1 のみがエラーメッセージを受け取る
['a1', 'unique', 'targetAttribute' => ['a1', 'a2']],
// a2 の値が "a2" のカラム、a1 の値が "a3" のカラムにおいてユニークである必要がある
// a1 がエラーメッセージを受け取る
['a1', 'unique', 'targetAttribute' => ['a2', 'a1' => 'a3']],
]
```
このバリデータは、入力値がテーブルのカラムにおいてユニークであるかどうかをチェックします。
[アクティブレコード](db-active-record.md) モデルの属性に対してのみ働きます。
一つのカラムに対するバリデーションか、複数のカラムに対するバリデーションか、どちらかをサポートします。
- `targetClass`: 検証される入力値を探すために使用される [アクティブレコード](db-active-record.md) クラスの名前。
設定されていない場合は、現在検証されているモデルのクラスが使用されます。
- `targetAttribute`: `targetClass` において、入力値がユニークであることを検証するために使用される属性の名前。
設定されていない場合は、現在検証されている属性の名前が使用されます。
複数のカラムのユニーク性を同時に検証するために配列を使うことが出来ます。
配列の値はユニーク性を検証するのに使用される属性であり、配列のキーはその値が検証される属性です。
キーと値が同じ場合は、値だけを指定することが出来ます。
- `filter`: 入力値のユニーク性をチェックするのに使用される DB クエリに適用される追加のフィルタ。
これには、文字列、または、追加のクエリ条件を表現する配列を使うことが出来ます
(クエリ条件の書式については、[[yii\db\Query::where()]] を参照してください)。
または、`function ($query)` というシグニチャを持つ無名関数でも構いません。
`$query` は関数の中で修正できる [[yii\db\Query|Query]] オブジェクトです。
## [[yii\validators\UrlValidator|url]] <a name="url"></a>
```php
[
// "website" が有効な URL であるかどうかをチェック。
// URI スキームを持たない場合は、"website" 属性に "http://" を前置する
['website', 'url', 'defaultScheme' => 'http'],
]
```
このバリデータは、入力値が有効な URL であるかどうかをチェックします。
- `validSchemes`: 有効と見なされるべき URI スキームを指定する配列。
デフォルト値は `['http', 'https']` であり、`http` と `https` の URL がともに有効と見なされることを意味します。
- `defaultScheme`: 入力値がスキームの部分を持たないときに前置されるデフォルトの URI スキーム。
デフォルト値は null であり、入力値を修正しないことを意味します。
- `enableIDN`: バリデータが IDN (国際化ドメイン名) を考慮すべきか否か。
デフォルト値は false。
IDN のバリデーションを使用するためには、`intl` PHP 拡張をインストールして有効化する必要があることに注意してください。
そうしないと、例外が投げられます。
...@@ -81,7 +81,7 @@ All Rights Reserved. ...@@ -81,7 +81,7 @@ All Rights Reserved.
* **TBD** [Sphinx](db-sphinx.md) * **TBD** [Sphinx](db-sphinx.md)
* **TBD** [Redis](db-redis.md) * **TBD** [Redis](db-redis.md)
* **TBD** [MongoDB](db-mongodb.md) * **TBD** [MongoDB](db-mongodb.md)
* **TBD** [ElasticSearch](db-elastic-search.md) * **TBD** [ElasticSearch](db-elasticsearch.md)
Получение данных от пользователя Получение данных от пользователя
...@@ -89,14 +89,14 @@ All Rights Reserved. ...@@ -89,14 +89,14 @@ All Rights Reserved.
* [Создание форм](input-forms.md) * [Создание форм](input-forms.md)
* [Валидация](input-validation.md) * [Валидация](input-validation.md)
* **TBD** [Загрузка файлов](input-file-uploading.md) * **TBD** [Загрузка файлов](input-file-upload.md)
* **TBD** [Работа с несколькими моделями](input-multiple-models.md) * **TBD** [Работа с несколькими моделями](input-multiple-models.md)
Отображение данных Отображение данных
------------------ ------------------
* **TBD** [Форматирование данных](output-formatting.md) * **TBD** [Форматирование данных](output-formatter.md)
* **TBD** [Постраничная разбивка](output-pagination.md) * **TBD** [Постраничная разбивка](output-pagination.md)
* **TBD** [Сортировка](output-sorting.md) * **TBD** [Сортировка](output-sorting.md)
* [Провайдеры данных](output-data-providers.md) * [Провайдеры данных](output-data-providers.md)
...@@ -191,8 +191,8 @@ All Rights Reserved. ...@@ -191,8 +191,8 @@ All Rights Reserved.
* Menu: link to demo page * Menu: link to demo page
* LinkPager: link to demo page * LinkPager: link to demo page
* LinkSorter: link to demo page * LinkSorter: link to demo page
* [Виджеты Bootstrap](bootstrap-widgets.md) * [Виджеты Bootstrap](widget-bootstrap.md)
* **TBD** [Виджеты Jquery UI](jui-widgets.md) * **TBD** [Виджеты Jquery UI](widget-jui.md)
Хелперы Хелперы
......
...@@ -69,7 +69,7 @@ ...@@ -69,7 +69,7 @@
Более детальная информация представлена в разделе [Обработка ошибок](runtime-handling-errors.md); Более детальная информация представлена в разделе [Обработка ошибок](runtime-handling-errors.md);
* [[yii\base\Formatter|formatter]]: форматирует данные для отображения их конечному пользователю. Например, число может * [[yii\base\Formatter|formatter]]: форматирует данные для отображения их конечному пользователю. Например, число может
быть отображено с различными разделителями, дата может быть отображена в формате `long`. быть отображено с различными разделителями, дата может быть отображена в формате `long`.
Более детальная информация представлена в разделе [Форматирование данных](output-formatting.md); Более детальная информация представлена в разделе [Форматирование данных](output-formatter.md);
* [[yii\i18n\I18N|i18n]]: используется для перевода сообщений и форматирования. * [[yii\i18n\I18N|i18n]]: используется для перевода сообщений и форматирования.
Более детальная информация представлена в разделе [Интернационализация](tutorial-i18n.md); Более детальная информация представлена в разделе [Интернационализация](tutorial-i18n.md);
* [[yii\log\Dispatcher|log]]: обработка и маршрутизация логов. * [[yii\log\Dispatcher|log]]: обработка и маршрутизация логов.
......
...@@ -96,6 +96,12 @@ $customer->email = 'jane@example.com'; ...@@ -96,6 +96,12 @@ $customer->email = 'jane@example.com';
$customer->save(); $customer->save();
``` ```
> Note: Obviously, because column names become attribute names of the active record class directly, you
> get attribute names with underscores if you have that kind of naming schema in your database. For example
> a column `user_name` will be accessed as `$user->user_name` on the active record object. If you are concerned about code style
> you should adopt your database naming schema to use camelCase too. However, camelCase if not a requirement, Yii can work
> well with any other naming style.
Connecting to Database Connecting to Database
---------------------- ----------------------
......
...@@ -239,6 +239,7 @@ Encoding will use application charset and could be changed via third argument. ...@@ -239,6 +239,7 @@ Encoding will use application charset and could be changed via third argument.
## Merging Arrays <a name="merging-arrays"></a> ## Merging Arrays <a name="merging-arrays"></a>
```php
/** /**
* Merges two or more arrays into one recursively. * Merges two or more arrays into one recursively.
* If each array has an element with the same string key value, the latter * If each array has an element with the same string key value, the latter
...@@ -253,6 +254,7 @@ Encoding will use application charset and could be changed via third argument. ...@@ -253,6 +254,7 @@ Encoding will use application charset and could be changed via third argument.
* @return array the merged array (the original arrays are not changed.) * @return array the merged array (the original arrays are not changed.)
*/ */
public static function merge($a, $b) public static function merge($a, $b)
```
## Converting Objects to Arrays <a name="converting-objects-to-arrays"></a> ## Converting Objects to Arrays <a name="converting-objects-to-arrays"></a>
......
...@@ -32,7 +32,7 @@ return [ ...@@ -32,7 +32,7 @@ return [
Basic usage Basic usage
----------- -----------
Once 'mailer' component is configured, you can use the following code to send an email message: Once the 'mailer' component is configured, you can use the following code to send an email message:
```php ```php
Yii::$app->mailer->compose() Yii::$app->mailer->compose()
...@@ -44,7 +44,7 @@ Yii::$app->mailer->compose() ...@@ -44,7 +44,7 @@ Yii::$app->mailer->compose()
->send(); ->send();
``` ```
In above example method `compose()` creates an instance of the mail message, which then is populated and sent. In the above example the method `compose()` creates an instance of the mail message, which then is populated and sent.
You may put more complex logic in this process if needed: You may put more complex logic in this process if needed:
```php ```php
......
...@@ -11,6 +11,7 @@ use yii\base\Action; ...@@ -11,6 +11,7 @@ use yii\base\Action;
use yii\base\Exception; use yii\base\Exception;
use yii\base\InvalidConfigException; use yii\base\InvalidConfigException;
use yii\base\NotSupportedException; use yii\base\NotSupportedException;
use yii\helpers\Url;
use yii\web\Response; use yii\web\Response;
use yii\web\HttpException; use yii\web\HttpException;
use yii\web\NotFoundHttpException; use yii\web\NotFoundHttpException;
...@@ -156,7 +157,7 @@ class AuthAction extends Action ...@@ -156,7 +157,7 @@ class AuthAction extends Action
*/ */
protected function defaultCancelUrl() protected function defaultCancelUrl()
{ {
return Yii::$app->getRequest()->getAbsoluteUrl(); return Url::to(Yii::$app->getUser()->loginUrl);
} }
/** /**
......
...@@ -4,7 +4,8 @@ Yii Framework 2 authclient extension Change Log ...@@ -4,7 +4,8 @@ Yii Framework 2 authclient extension Change Log
2.0.2 under development 2.0.2 under development
----------------------- -----------------------
- no changes in this release. - Bug #6502: Fixed `\yii\authclient\OAuth2::refreshAccessToken()` does not save fetched token (sebathi)
- Bug #6510: Fixed infinite redirect loop using default `\yii\authclient\AuthAction::cancelUrl` (klimov-paul)
2.0.1 December 07, 2014 2.0.1 December 07, 2014
......
...@@ -158,7 +158,10 @@ class OAuth2 extends BaseOAuth ...@@ -158,7 +158,10 @@ class OAuth2 extends BaseOAuth
$params = array_merge($token->getParams(), $params); $params = array_merge($token->getParams(), $params);
$response = $this->sendRequest('POST', $this->tokenUrl, $params); $response = $this->sendRequest('POST', $this->tokenUrl, $params);
return $response; $token = $this->createToken(['params' => $response]);
$this->setAccessToken($token);
return $token;
} }
/** /**
......
...@@ -50,6 +50,9 @@ class OAuthToken extends Object ...@@ -50,6 +50,9 @@ class OAuthToken extends Object
private $_params = []; private $_params = [];
/**
* @inheritdoc
*/
public function init() public function init()
{ {
if ($this->createTimestamp === null) { if ($this->createTimestamp === null) {
......
...@@ -35,6 +35,7 @@ use yii\helpers\Html; ...@@ -35,6 +35,7 @@ use yii\helpers\Html;
* ], * ],
* ], * ],
* ], * ],
* 'options' => ['class' =>'nav-pills'], // set this to nav-tab to get tab-styled navigation
* ]); * ]);
* ``` * ```
* *
......
...@@ -5,7 +5,6 @@ Yii Framework 2 gii extension Change Log ...@@ -5,7 +5,6 @@ Yii Framework 2 gii extension Change Log
----------------------- -----------------------
- Bug #6463: The Gii controller generator generates incorrect controller namespace (pana1990) - Bug #6463: The Gii controller generator generates incorrect controller namespace (pana1990)
- Enh #3665: Improved Gii CRUD generated code to support setting initial conditions via initializing search model (mdmunir, fsateler, samdark)
2.0.1 December 07, 2014 2.0.1 December 07, 2014
......
...@@ -69,7 +69,7 @@ class <?= $searchModelClass ?> extends <?= isset($modelAlias) ? $modelAlias : $m ...@@ -69,7 +69,7 @@ class <?= $searchModelClass ?> extends <?= isset($modelAlias) ? $modelAlias : $m
'query' => $query, 'query' => $query,
]); ]);
if ($this->load($params) && !$this->validate()) { if (!($this->load($params) && $this->validate())) {
return $dataProvider; return $dataProvider;
} }
......
...@@ -5,6 +5,7 @@ Yii Framework 2 jui extension Change Log ...@@ -5,6 +5,7 @@ Yii Framework 2 jui extension Change Log
----------------------- -----------------------
- Enh #6570: Datepicker now uses fallback to find language files, e.g. application language is `de-DE` and the translation files does not exists, it will use `de` instead (cebe) - Enh #6570: Datepicker now uses fallback to find language files, e.g. application language is `de-DE` and the translation files does not exists, it will use `de` instead (cebe)
- Enh #6471: Datepicker will now show an empty field when value is an empty string (cebe)
2.0.1 December 07, 2014 2.0.1 December 07, 2014
......
...@@ -169,7 +169,7 @@ class DatePicker extends InputWidget ...@@ -169,7 +169,7 @@ class DatePicker extends InputWidget
} else { } else {
$value = $this->value; $value = $this->value;
} }
if ($value !== null) { if ($value !== null && $value !== '') {
// format value according to dateFormat // format value according to dateFormat
try { try {
$value = Yii::$app->formatter->asDate($value, $this->dateFormat); $value = Yii::$app->formatter->asDate($value, $this->dateFormat);
......
...@@ -36,9 +36,10 @@ use yii\di\Instance; ...@@ -36,9 +36,10 @@ use yii\di\Instance;
class Cache extends \yii\caching\Cache class Cache extends \yii\caching\Cache
{ {
/** /**
* @var Connection|string the MongoDB connection object or the application component ID of the MongoDB connection. * @var Connection|array|string the MongoDB connection object or the application component ID of the MongoDB connection.
* After the Cache object is created, if you want to change this property, you should only assign it * After the Cache object is created, if you want to change this property, you should only assign it
* with a MongoDB connection object. * with a MongoDB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'mongodb'; public $db = 'mongodb';
/** /**
......
...@@ -34,8 +34,9 @@ use yii\helpers\Json; ...@@ -34,8 +34,9 @@ use yii\helpers\Json;
abstract class Migration extends Component implements MigrationInterface abstract class Migration extends Component implements MigrationInterface
{ {
/** /**
* @var Connection|string the MongoDB connection object or the application component ID of the MongoDB connection * @var Connection|array|string the MongoDB connection object or the application component ID of the MongoDB connection
* that this migration should work with. * that this migration should work with.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'mongodb'; public $db = 'mongodb';
......
...@@ -7,7 +7,7 @@ This extension provides the [MongoDB](http://www.mongodb.org/) integration for t ...@@ -7,7 +7,7 @@ This extension provides the [MongoDB](http://www.mongodb.org/) integration for t
Installation Installation
------------ ------------
This extension requires [MongoDB PHP Extension](http://us1.php.net/manual/en/book.mongo.php) version 1.4.0 or higher. This extension requires [MongoDB PHP Extension](http://us1.php.net/manual/en/book.mongo.php) version 1.5.0 or higher.
The preferred way to install this extension is through [composer](http://getcomposer.org/download/). The preferred way to install this extension is through [composer](http://getcomposer.org/download/).
......
...@@ -38,9 +38,10 @@ use yii\di\Instance; ...@@ -38,9 +38,10 @@ use yii\di\Instance;
class Session extends \yii\web\Session class Session extends \yii\web\Session
{ {
/** /**
* @var Connection|string the MongoDB connection object or the application component ID of the MongoDB connection. * @var Connection|array|string the MongoDB connection object or the application component ID of the MongoDB connection.
* After the Session object is created, if you want to change this property, you should only assign it * After the Session object is created, if you want to change this property, you should only assign it
* with a MongoDB connection object. * with a MongoDB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'mongodb'; public $db = 'mongodb';
/** /**
......
...@@ -8,6 +8,12 @@ if you want to upgrade from version A to version C and there is ...@@ -8,6 +8,12 @@ if you want to upgrade from version A to version C and there is
version B between A and C, you need to following the instructions version B between A and C, you need to following the instructions
for both A and B. for both A and B.
Upgrade from Yii 2.0.1
----------------------
* MongoDB PHP extension min version raised up to 1.5.0. You should upgrade your environment in case you are
using older version.
Upgrade from Yii 2.0.0 Upgrade from Yii 2.0.0
---------------------- ----------------------
......
...@@ -19,7 +19,7 @@ ...@@ -19,7 +19,7 @@
], ],
"require": { "require": {
"yiisoft/yii2": "*", "yiisoft/yii2": "*",
"ext-mongo": ">=1.4.0" "ext-mongo": ">=1.5.0"
}, },
"autoload": { "autoload": {
"psr-4": { "yii\\mongodb\\": "" } "psr-4": { "yii\\mongodb\\": "" }
......
...@@ -11,8 +11,11 @@ Yii Framework 2 Change Log ...@@ -11,8 +11,11 @@ Yii Framework 2 Change Log
- Bug #6648: Added explicit type casting to avoid dblib issues on SQL Server 2014 (o-rey) - Bug #6648: Added explicit type casting to avoid dblib issues on SQL Server 2014 (o-rey)
- Bug #6691: Fixed console help description parsing with UTF8 characters (cebe) - Bug #6691: Fixed console help description parsing with UTF8 characters (cebe)
- Bug #6717: Fixed issue with UrlManager not matching a route on url creation when it was prefixed with `/` and pattern was empty (cebe) - Bug #6717: Fixed issue with UrlManager not matching a route on url creation when it was prefixed with `/` and pattern was empty (cebe)
- Bug #6736: Removed `Content-Transfer-Encoding` from the list of default download headers (DaSourcerer)
- Enh #4502: Added alias support to URL route when calling `Url::toRoute()` and `Url::to()` (qiangxue, lynicidn) - Enh #4502: Added alias support to URL route when calling `Url::toRoute()` and `Url::to()` (qiangxue, lynicidn)
- Enh #5194: `yii\console\controllers\AssetController` now handles bundle files from external resources properly (klimov-paul)
- Enh #6247: Logger and error handler are now using slightly less memory (stepanselyuk, samdark) - Enh #6247: Logger and error handler are now using slightly less memory (stepanselyuk, samdark)
- Enh #6398: Added support for specifying dependent component in terms of a configuration array for classes such as `DbCache` (qiangxue)
- Enh #6434: Added `yii\behaviors\SluggableBehavior::immutable` to support keeping the generated slug unchanged (trntv) - Enh #6434: Added `yii\behaviors\SluggableBehavior::immutable` to support keeping the generated slug unchanged (trntv)
- Enh #6467: `ActiveForm` will scroll to the nearest visible element when the first error input is hidden (newartix) - Enh #6467: `ActiveForm` will scroll to the nearest visible element when the first error input is hidden (newartix)
- Enh #6488: Support changing `yii\base\Theme::basePath` during runtime (qiangxue) - Enh #6488: Support changing `yii\base\Theme::basePath` during runtime (qiangxue)
......
...@@ -37,9 +37,10 @@ use yii\di\Instance; ...@@ -37,9 +37,10 @@ use yii\di\Instance;
class DbCache extends Cache class DbCache extends Cache
{ {
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* After the DbCache object is created, if you want to change this property, you should only assign it * After the DbCache object is created, if you want to change this property, you should only assign it
* with a DB connection object. * with a DB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'db'; public $db = 'db';
/** /**
......
...@@ -12,6 +12,7 @@ use yii\console\Exception; ...@@ -12,6 +12,7 @@ use yii\console\Exception;
use yii\console\Controller; use yii\console\Controller;
use yii\helpers\Console; use yii\helpers\Console;
use yii\helpers\VarDumper; use yii\helpers\VarDumper;
use yii\web\AssetBundle;
/** /**
* Allows you to combine and compress your JavaScript and CSS files. * Allows you to combine and compress your JavaScript and CSS files.
...@@ -65,6 +66,37 @@ class AssetController extends Controller ...@@ -65,6 +66,37 @@ class AssetController extends Controller
* ~~~ * ~~~
* *
* File names can contain placeholder "{hash}", which will be filled by the hash of the resulting file. * File names can contain placeholder "{hash}", which will be filled by the hash of the resulting file.
*
* You may specify several target bundles in order to compress different groups of assets.
* In this case you should use 'depends' key to specify, which bundles should be covered with particular
* target bundle. You may leave 'depends' to be empty for single bundle, which will compress all remaining
* bundles in this case.
* For example:
*
* ~~~
* 'app\config\AllShared' => [
* 'js' => 'js/all-shared-{hash}.js',
* 'css' => 'css/all-shared-{hash}.css',
* 'depends' => [
* // Include all assets shared between 'backend' and 'frontend'
* 'yii\web\YiiAsset',
* 'app\assets\SharedAsset',
* ],
* ],
* 'app\config\AllBackEnd' => [
* 'js' => 'js/all-{hash}.js',
* 'css' => 'css/all-{hash}.css',
* 'depends' => [
* // Include only 'backend' assets:
* 'app\assets\AdminAsset'
* ],
* ],
* 'app\config\AllFrontEnd' => [
* 'js' => 'js/all-{hash}.js',
* 'css' => 'css/all-{hash}.css',
* 'depends' => [], // Include all remaining assets
* ],
* ~~~
*/ */
public $targets = []; public $targets = [];
/** /**
...@@ -298,9 +330,11 @@ class AssetController extends Controller ...@@ -298,9 +330,11 @@ class AssetController extends Controller
foreach ($target->depends as $name) { foreach ($target->depends as $name) {
if (isset($bundles[$name])) { if (isset($bundles[$name])) {
if (!$this->isBundleExternal($bundles[$name])) {
foreach ($bundles[$name]->$type as $file) { foreach ($bundles[$name]->$type as $file) {
$inputFiles[] = $bundles[$name]->basePath . '/' . $file; $inputFiles[] = $bundles[$name]->basePath . '/' . $file;
} }
}
} else { } else {
throw new Exception("Unknown bundle: '{$name}'"); throw new Exception("Unknown bundle: '{$name}'");
} }
...@@ -352,9 +386,14 @@ class AssetController extends Controller ...@@ -352,9 +386,14 @@ class AssetController extends Controller
} }
foreach ($map as $bundle => $target) { foreach ($map as $bundle => $target) {
$sourceBundle = $bundles[$bundle];
$depends = $sourceBundle->depends;
if (!$this->isBundleExternal($sourceBundle)) {
$depends[] = $target;
}
$targets[$bundle] = Yii::createObject([ $targets[$bundle] = Yii::createObject([
'class' => strpos($bundle, '\\') !== false ? $bundle : 'yii\\web\\AssetBundle', 'class' => strpos($bundle, '\\') !== false ? $bundle : 'yii\\web\\AssetBundle',
'depends' => [$target], 'depends' => $depends,
]); ]);
} }
...@@ -402,6 +441,9 @@ class AssetController extends Controller ...@@ -402,6 +441,9 @@ class AssetController extends Controller
'css' => $target->css, 'css' => $target->css,
]; ];
} else { } else {
if ($this->isBundleExternal($target)) {
$array[$name] = $this->composeBundleConfig($target);
} else {
$array[$name] = [ $array[$name] = [
'sourcePath' => null, 'sourcePath' => null,
'js' => [], 'js' => [],
...@@ -410,6 +452,7 @@ class AssetController extends Controller ...@@ -410,6 +452,7 @@ class AssetController extends Controller
]; ];
} }
} }
}
$array = VarDumper::export($array); $array = VarDumper::export($array);
$version = date('Y-m-d H:i:s', time()); $version = date('Y-m-d H:i:s', time());
$bundleFileContent = <<<EOD $bundleFileContent = <<<EOD
...@@ -683,4 +726,24 @@ EOD; ...@@ -683,4 +726,24 @@ EOD;
} }
return implode(DIRECTORY_SEPARATOR, $realPathParts); return implode(DIRECTORY_SEPARATOR, $realPathParts);
} }
/**
* @param AssetBundle $bundle
* @return boolean whether asset bundle external or not.
*/
private function isBundleExternal($bundle)
{
return (empty($bundle->sourcePath) && empty($bundle->basePath));
}
/**
* @param AssetBundle $bundle asset bundle instance.
* @return array bundle configuration.
*/
private function composeBundleConfig($bundle)
{
$config = Yii::getObjectVars($bundle);
$config['class'] = get_class($bundle);
return $config;
}
} }
...@@ -72,8 +72,9 @@ class ActiveDataProvider extends BaseDataProvider ...@@ -72,8 +72,9 @@ class ActiveDataProvider extends BaseDataProvider
*/ */
public $key; public $key;
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* If not set, the default DB connection will be used. * If not set, the default DB connection will be used.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db; public $db;
......
...@@ -64,7 +64,8 @@ use yii\di\Instance; ...@@ -64,7 +64,8 @@ use yii\di\Instance;
class SqlDataProvider extends BaseDataProvider class SqlDataProvider extends BaseDataProvider
{ {
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'db'; public $db = 'db';
/** /**
......
...@@ -39,10 +39,13 @@ use \yii\base\Component; ...@@ -39,10 +39,13 @@ use \yii\base\Component;
class Migration extends Component implements MigrationInterface class Migration extends Component implements MigrationInterface
{ {
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection * @var Connection|array|string the DB connection object or the application component ID of the DB connection
* that this migration should work with. Note that when a Migration object is created by * that this migration should work with. Starting from version 2.0.2, this can also be a configuration array
* the `migrate` command, this property will be overwritten by the command. If you do not want to * for creating the object.
* use the DB connection provided by the command, you may override the [[init()]] method like the following: *
* Note that when a Migration object is created by the `migrate` command, this property will be overwritten
* by the command. If you do not want to use the DB connection provided by the command, you may override
* the [[init()]] method like the following:
* *
* ```php * ```php
* public function init() * public function init()
......
...@@ -92,13 +92,14 @@ class Instance ...@@ -92,13 +92,14 @@ class Instance
* *
* // returns Yii::$app->db * // returns Yii::$app->db
* $db = Instance::ensure('db', Connection::className()); * $db = Instance::ensure('db', Connection::className());
* // or * // returns an instance of Connection using the given configuration
* $instance = Instance::of('db'); * $db = Instance::ensure(['dsn' => 'sqlite:path/to/my.db'], Connection::className());
* $db = Instance::ensure($instance, Connection::className());
* ``` * ```
* *
* @param object|string|static $reference an object or a reference to the desired object. * @param object|string|array|static $reference an object or a reference to the desired object.
* You may specify a reference in terms of a component ID or an Instance object. * You may specify a reference in terms of a component ID or an Instance object.
* Starting from version 2.0.2, you may also pass in a configuration array for creating the object.
* If the "class" value is not specified in the configuration array, it will use the value of `$type`.
* @param string $type the class/interface name to be checked. If null, type check will not be performed. * @param string $type the class/interface name to be checked. If null, type check will not be performed.
* @param ServiceLocator|Container $container the container. This will be passed to [[get()]]. * @param ServiceLocator|Container $container the container. This will be passed to [[get()]].
* @return object the object referenced by the Instance, or `$reference` itself if it is an object. * @return object the object referenced by the Instance, or `$reference` itself if it is an object.
...@@ -108,6 +109,13 @@ class Instance ...@@ -108,6 +109,13 @@ class Instance
{ {
if ($reference instanceof $type) { if ($reference instanceof $type) {
return $reference; return $reference;
} elseif (is_array($reference)) {
$class = isset($reference['class']) ? $reference['class'] : $type;
if (!$container instanceof Container) {
$container = Yii::$container;
}
unset($reference['class']);
return $container->get($class, [], $reference);
} elseif (empty($reference)) { } elseif (empty($reference)) {
throw new InvalidConfigException('The required component is not specified.'); throw new InvalidConfigException('The required component is not specified.');
} }
......
...@@ -57,7 +57,8 @@ use yii\web\ForbiddenHttpException; ...@@ -57,7 +57,8 @@ use yii\web\ForbiddenHttpException;
class AccessControl extends ActionFilter class AccessControl extends ActionFilter
{ {
/** /**
* @var User|string the user object representing the authentication status or the ID of the user application component. * @var User|array|string the user object representing the authentication status or the ID of the user application component.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $user = 'user'; public $user = 'user';
/** /**
......
...@@ -53,17 +53,19 @@ class DbMessageSource extends MessageSource ...@@ -53,17 +53,19 @@ class DbMessageSource extends MessageSource
const CACHE_KEY_PREFIX = 'DbMessageSource'; const CACHE_KEY_PREFIX = 'DbMessageSource';
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* After the DbMessageSource object is created, if you want to change this property, you should only assign * After the DbMessageSource object is created, if you want to change this property, you should only assign
* it with a DB connection object. * it with a DB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'db'; public $db = 'db';
/** /**
* @var Cache|string the cache object or the application component ID of the cache object. * @var Cache|array|string the cache object or the application component ID of the cache object.
* The messages data will be cached using this cache object. Note, this property has meaning only * The messages data will be cached using this cache object. Note, this property has meaning only
* in case [[cachingDuration]] set to non-zero value. * in case [[cachingDuration]] set to non-zero value.
* After the DbMessageSource object is created, if you want to change this property, you should only assign * After the DbMessageSource object is created, if you want to change this property, you should only assign
* it with a cache object. * it with a cache object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $cache = 'cache'; public $cache = 'cache';
/** /**
......
...@@ -32,9 +32,10 @@ use yii\helpers\VarDumper; ...@@ -32,9 +32,10 @@ use yii\helpers\VarDumper;
class DbTarget extends Target class DbTarget extends Target
{ {
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* After the DbTarget object is created, if you want to change this property, you should only assign it * After the DbTarget object is created, if you want to change this property, you should only assign it
* with a DB connection object. * with a DB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'db'; public $db = 'db';
/** /**
......
...@@ -50,9 +50,10 @@ class EmailTarget extends Target ...@@ -50,9 +50,10 @@ class EmailTarget extends Target
*/ */
public $message = []; public $message = [];
/** /**
* @var MailerInterface|string the mailer object or the application component ID of the mailer object. * @var MailerInterface|array|string the mailer object or the application component ID of the mailer object.
* After the EmailTarget object is created, if you want to change this property, you should only assign it * After the EmailTarget object is created, if you want to change this property, you should only assign it
* with a mailer object. * with a mailer object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $mailer = 'mailer'; public $mailer = 'mailer';
......
...@@ -23,9 +23,10 @@ use yii\di\Instance; ...@@ -23,9 +23,10 @@ use yii\di\Instance;
abstract class DbMutex extends Mutex abstract class DbMutex extends Mutex
{ {
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* After the Mutex object is created, if you want to change this property, you should only assign * After the Mutex object is created, if you want to change this property, you should only assign
* it with a DB connection object. * it with a DB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'db'; public $db = 'db';
......
...@@ -36,9 +36,10 @@ use yii\di\Instance; ...@@ -36,9 +36,10 @@ use yii\di\Instance;
class DbManager extends BaseManager class DbManager extends BaseManager
{ {
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* After the DbManager object is created, if you want to change this property, you should only assign it * After the DbManager object is created, if you want to change this property, you should only assign it
* with a DB connection object. * with a DB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'db'; public $db = 'db';
/** /**
......
...@@ -23,9 +23,10 @@ use yii\base\Object; ...@@ -23,9 +23,10 @@ use yii\base\Object;
abstract class DbFixture extends Fixture abstract class DbFixture extends Fixture
{ {
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* After the DbFixture object is created, if you want to change this property, you should only assign it * After the DbFixture object is created, if you want to change this property, you should only assign it
* with a DB connection object. * with a DB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'db'; public $db = 'db';
......
...@@ -39,11 +39,13 @@ use yii\di\Instance; ...@@ -39,11 +39,13 @@ use yii\di\Instance;
class CacheSession extends Session class CacheSession extends Session
{ {
/** /**
* @var Cache|string the cache object or the application component ID of the cache object. * @var Cache|array|string the cache object or the application component ID of the cache object.
* The session data will be stored using this cache object. * The session data will be stored using this cache object.
* *
* After the CacheSession object is created, if you want to change this property, * After the CacheSession object is created, if you want to change this property,
* you should only assign it with a cache object. * you should only assign it with a cache object.
*
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $cache = 'cache'; public $cache = 'cache';
......
...@@ -38,9 +38,10 @@ use yii\di\Instance; ...@@ -38,9 +38,10 @@ use yii\di\Instance;
class DbSession extends Session class DbSession extends Session
{ {
/** /**
* @var Connection|string the DB connection object or the application component ID of the DB connection. * @var Connection|array|string the DB connection object or the application component ID of the DB connection.
* After the DbSession object is created, if you want to change this property, you should only assign it * After the DbSession object is created, if you want to change this property, you should only assign it
* with a DB connection object. * with a DB connection object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $db = 'db'; public $db = 'db';
/** /**
......
...@@ -557,7 +557,6 @@ class Response extends \yii\base\Response ...@@ -557,7 +557,6 @@ class Response extends \yii\base\Response
->setDefault('Accept-Ranges', 'bytes') ->setDefault('Accept-Ranges', 'bytes')
->setDefault('Expires', '0') ->setDefault('Expires', '0')
->setDefault('Cache-Control', 'must-revalidate, post-check=0, pre-check=0') ->setDefault('Cache-Control', 'must-revalidate, post-check=0, pre-check=0')
->setDefault('Content-Transfer-Encoding', 'binary')
->setDefault('Content-Disposition', "$disposition; filename=\"$attachmentName\""); ->setDefault('Content-Disposition', "$disposition; filename=\"$attachmentName\"");
if ($mimeType !== null) { if ($mimeType !== null) {
......
...@@ -24,9 +24,10 @@ use yii\di\Instance; ...@@ -24,9 +24,10 @@ use yii\di\Instance;
class FragmentCache extends Widget class FragmentCache extends Widget
{ {
/** /**
* @var Cache|string the cache object or the application component ID of the cache object. * @var Cache|array|string the cache object or the application component ID of the cache object.
* After the FragmentCache object is created, if you want to change this property, * After the FragmentCache object is created, if you want to change this property,
* you should only assign it with a cache object. * you should only assign it with a cache object.
* Starting from version 2.0.2, this can also be a configuration array for creating the object.
*/ */
public $cache = 'cache'; public $cache = 'cache';
/** /**
......
...@@ -95,7 +95,9 @@ class AssetControllerTest extends TestCase ...@@ -95,7 +95,9 @@ class AssetControllerTest extends TestCase
*/ */
protected function createCompressConfig(array $bundles) protected function createCompressConfig(array $bundles)
{ {
$className = $this->declareAssetBundleClass(['class' => 'AssetBundleAll']); static $classNumber = 0;
$classNumber++;
$className = $this->declareAssetBundleClass(['class' => 'AssetBundleAll' . $classNumber]);
$baseUrl = '/test'; $baseUrl = '/test';
$config = [ $config = [
'bundles' => $bundles, 'bundles' => $bundles,
...@@ -283,7 +285,15 @@ EOL; ...@@ -283,7 +285,15 @@ EOL;
// Then : // Then :
$this->assertTrue(file_exists($bundleFile), 'Unable to create output bundle file!'); $this->assertTrue(file_exists($bundleFile), 'Unable to create output bundle file!');
$this->assertTrue(is_array(require($bundleFile)), 'Output bundle file has incorrect format!'); $compressedBundleConfig = require($bundleFile);
$this->assertTrue(is_array($compressedBundleConfig), 'Output bundle file has incorrect format!');
$this->assertCount(2, $compressedBundleConfig, 'Output bundle config contains wrong bundle count!');
$this->assertArrayHasKey($assetBundleClassName, $compressedBundleConfig, 'Source bundle is lost!');
$compressedAssetBundleConfig = $compressedBundleConfig[$assetBundleClassName];
$this->assertEmpty($compressedAssetBundleConfig['css'], 'Compressed bundle css is not empty!');
$this->assertEmpty($compressedAssetBundleConfig['js'], 'Compressed bundle js is not empty!');
$this->assertNotEmpty($compressedAssetBundleConfig['depends'], 'Compressed bundle dependency is invalid!');
$compressedCssFileName = $this->testAssetsBasePath . DIRECTORY_SEPARATOR . 'all.css'; $compressedCssFileName = $this->testAssetsBasePath . DIRECTORY_SEPARATOR . 'all.css';
$this->assertTrue(file_exists($compressedCssFileName), 'Unable to compress CSS files!'); $this->assertTrue(file_exists($compressedCssFileName), 'Unable to compress CSS files!');
...@@ -301,6 +311,73 @@ EOL; ...@@ -301,6 +311,73 @@ EOL;
} }
/** /**
* @depends testActionCompress
*
* @see https://github.com/yiisoft/yii2/issues/5194
*/
public function testCompressExternalAsset()
{
// Given :
$externalAssetConfig = [
'class' => 'ExternalAsset',
'sourcePath' => null,
'basePath' => null,
'js' => [
'//ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js',
],
'css' => [
'//ajax.googleapis.com/css/libs/jquery/2.1.1/jquery.ui.min.css'
],
];
$externalAssetBundleClassName = $this->declareAssetBundleClass($externalAssetConfig);
$cssFiles = [
'css/test.css' => 'body {
padding-top: 20px;
padding-bottom: 60px;
}',
];
$this->createAssetSourceFiles($cssFiles);
$jsFiles = [
'js/test.js' => "function test() {
alert('Test message');
}",
];
$this->createAssetSourceFiles($jsFiles);
$regularAssetBundleClassName = $this->declareAssetBundleClass([
'class' => 'RegularAsset',
'css' => array_keys($cssFiles),
'js' => array_keys($jsFiles),
'depends' => [
$externalAssetBundleClassName
],
]);
$bundles = [
$regularAssetBundleClassName
];
$bundleFile = $this->testFilePath . DIRECTORY_SEPARATOR . 'bundle.php';
$configFile = $this->testFilePath . DIRECTORY_SEPARATOR . 'config.php';
$this->createCompressConfigFile($configFile, $bundles);
// When :
$this->runAssetControllerAction('compress', [$configFile, $bundleFile]);
// Then :
$this->assertTrue(file_exists($bundleFile), 'Unable to create output bundle file!');
$compressedBundleConfig = require($bundleFile);
$this->assertTrue(is_array($compressedBundleConfig), 'Output bundle file has incorrect format!');
$this->assertArrayHasKey($externalAssetBundleClassName, $compressedBundleConfig, 'External bundle is lost!');
$compressedExternalAssetConfig = $compressedBundleConfig[$externalAssetBundleClassName];
$this->assertEquals($externalAssetConfig['js'], $compressedExternalAssetConfig['js'], 'External bundle js is lost!');
$this->assertEquals($externalAssetConfig['css'], $compressedExternalAssetConfig['css'], 'External bundle css is lost!');
$compressedRegularAssetConfig = $compressedBundleConfig[$regularAssetBundleClassName];
$this->assertContains($externalAssetBundleClassName, $compressedRegularAssetConfig['depends'], 'Dependency on external bundle is lost!');
}
/**
* Data provider for [[testAdjustCssUrl()]]. * Data provider for [[testAdjustCssUrl()]].
* @return array test data. * @return array test data.
*/ */
......
...@@ -8,6 +8,7 @@ ...@@ -8,6 +8,7 @@
namespace yiiunit\framework\di; namespace yiiunit\framework\di;
use yii\base\Component; use yii\base\Component;
use yii\db\Connection;
use yii\di\Container; use yii\di\Container;
use yii\di\Instance; use yii\di\Instance;
use yiiunit\TestCase; use yiiunit\TestCase;
...@@ -29,4 +30,20 @@ class InstanceTest extends TestCase ...@@ -29,4 +30,20 @@ class InstanceTest extends TestCase
$this->assertTrue(Instance::ensure($instance, $className, $container) instanceof Component); $this->assertTrue(Instance::ensure($instance, $className, $container) instanceof Component);
$this->assertTrue($instance->get($container) !== Instance::ensure($instance, $className, $container)); $this->assertTrue($instance->get($container) !== Instance::ensure($instance, $className, $container));
} }
public function testEnsure()
{
$container = new Container;
$container->set('db', [
'class' => 'yii\db\Connection',
'dsn' => 'test',
]);
$this->assertTrue(Instance::ensure('db', 'yii\db\Connection', $container) instanceof Connection);
$this->assertTrue(Instance::ensure(new Connection, 'yii\db\Connection', $container) instanceof Connection);
$this->assertTrue(Instance::ensure([
'class' => 'yii\db\Connection',
'dsn' => 'test',
], 'yii\db\Connection', $container) instanceof Connection);
}
} }
...@@ -129,6 +129,10 @@ class YiiRequirementCheckerTest extends TestCase ...@@ -129,6 +129,10 @@ class YiiRequirementCheckerTest extends TestCase
public function testCheckPhpExtensionVersion() public function testCheckPhpExtensionVersion()
{ {
if (defined('HHVM_VERSION')) {
$this->markTestSkipped('Can not test this on HHVM.');
}
$requirementsChecker = new YiiRequirementChecker(); $requirementsChecker = new YiiRequirementChecker();
$this->assertFalse($requirementsChecker->checkPhpExtensionVersion('some_unexisting_php_extension', '0.1'), 'No fail while checking unexisting extension!'); $this->assertFalse($requirementsChecker->checkPhpExtensionVersion('some_unexisting_php_extension', '0.1'), 'No fail while checking unexisting extension!');
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment