亚洲国产日韩欧美一区二区三区,精品亚洲国产成人av在线,国产99视频精品免视看7,99国产精品久久久久久久成人热,欧美日韩亚洲国产综合乱

?? ??? ??
閱讀前篇 簡介 Yii 是什么 從 Yii 1.1 升級 入門 安裝 Yii 運行應用 第一次問候 使用Forms 數據庫應用 使用 Gii 生成代碼 進階 應用結構 概述 入口腳本 應用(Applications) 應用組件(Application Components) 控制器(Controllers) 模型(Models) 視圖(views) 模塊(Modules) 過濾器(Filters) 小部件(Widgets) 前端資源(Assets) 擴展(Extensions) 請求處理 運行概述 啟動引導(Bootstrapping) 路由和創(chuàng)建URL 請求(Requests) 響應(Responses) Sessions 和 Cookies 錯誤處理(Handling Errors) 日志(Logging) 關鍵概念 組件(Component) 屬性(Property) 事件(Events) 行為(Behaviors) 配置(Configurations) 別名(Aliases) 類自動加載(Autoloading) 服務定位器(Service Locator) 依賴注入容器(Dependency Injection Container) 配合數據庫工作 數據庫訪問 (Data Access Objects) 查詢生成器(Query Builder) 活動記錄(Active Record) 數據庫遷移(Migrations) Sphinx Redis MongoDB Elasticsearch 接收用戶數據 創(chuàng)建表單(Creating Forms) 輸入驗證(Validating Input) 文件上傳(Uploading Files) 收集列表輸入(Collecting Tabular Input) 多模型的復合表單(Getting Data for Multiple Models) 顯示數據 格式化輸出數據(Data Formatting) 分頁(Pagination) 排序(Sorting) 數據提供器(Data Providers) 數據小部件(Data Widgets) 客戶端腳本使用(Working with Client Scripts) 主題(Theming) 安全 認證(Authentication) 授權(Authorization) 處理密碼(Working with Passwords) 客戶端認證(Auth Clients) 最佳安全實踐(Best Practices) 緩存 概述 數據緩存 片段緩存 頁面緩存 HTTP 緩存 RESTfull Web服務 快速入門(Quick Start) 資源(Resources) 控制器(Controllers) 路由(Routing) 格式化響應(Response Formatting) 授權認證(Authentication) 速率限制(Rate Limiting) 版本(Versioning) 錯誤處理(Error Handling) 開發(fā)工具 調試工具欄和調試器 使用Gii生成代碼 生成API文檔 測試 概述(Overview) 配置測試環(huán)境(Testing environment setup) 單元測試(Unit Tests) 功能測試(Function Tests) 驗收測試(Acceptance Tests) 測試夾具(Fixtures) 高級專題 高級應用模板 創(chuàng)建自定義應用程序結構 控制臺命令 核心驗證器(Core Validators) 國際化 收發(fā)郵件 性能優(yōu)化 共享主機環(huán)境 模板引擎 集成第三方代碼 小部件 Bootstrap 小部件 Jquery UI 助手類 概述 Array 助手(ArrayHelper) Html 助手(Html) Url 助手(Url)
??

數據提供者

數據提供者

在?Pagination?和?Sorting?部分, 我們已經介紹了如何允許終端用戶選擇一個特定的數據頁面,根據一些字段對它們進行展現與排序。 因為分頁和排序數據的任務是很常見的,所以Yii提供了一組封裝好的data provider類。

數據提供者是一個實現了 yii\data\DataProviderInterface 接口的類。 它主要用于獲取分頁和數據排序。它經常用在?data widgets?小物件里,方便終端用戶進行分頁與數據排序。

下面的數據提供者類都包含在Yii的發(fā)布版本里面:

  • yii\data\ActiveDataProvider:使用 yii\db\Query 或者 yii\db\ActiveQuery 從數據庫查詢數據并且以數組項的方式或者?Active Record實例的方式返回。
  • yii\data\SqlDataProvider:執(zhí)行一段SQL語句并且將數據庫數據作為數組返回。
  • yii\data\ArrayDataProvider:將一個大的數組依據分頁和排序規(guī)格返回一部分數據。

所有的這些數據提供者遵守以下模式:

// 根據配置的分頁以及排序屬性來創(chuàng)建一個數據提供者$provider = new XyzDataProvider([
    'pagination' => [...],
    'sort' => [...],
]);

// 獲取分頁和排序數據$models = $provider->getModels();

// 在當前頁獲取數據項的數目$count = $provider->getCount();

// 獲取所有頁面的數據項的總數$totalCount = $provider->getTotalCount();

你可以通過配置 yii\data\BaseDataProvider::pagination 和 yii\data\BaseDataProvider::sort 的屬性來設定數據提供者的分頁和排序行為。屬性分別對應于 yii\data\Pagination 和 yii\data\Sort。 你也可以對它們配置false來禁用分頁和排序特性。

Data widgets,諸如 yii\grid\GridView,有一個屬性名叫?dataProvider?,這個屬性能夠提供一個 數據提供者的示例并且可以顯示所提供的數據,例如,

echo yii\grid\GridView::widget([
    'dataProvider' => $dataProvider,
]);

這些數據提供者的主要區(qū)別在于數據源的指定方式上。在下面的部分,我們將詳細介紹這些數據提供者的使用方法。

活動數據提供者

為了使用 yii\data\ActiveDataProvider,你應該配置其 yii\data\ActiveDataProvider::query 的屬性。 它既可以是一個 yii\db\Query 對象,又可以是一個 yii\db\ActiveQuery 對象。假如是前者,返回的數據將是數組; 如果是后者,返回的數據可以是數組也可以是?Active Record?對象。 例如,

use yii\data\ActiveDataProvider;

$query = Post::find()->where(['status' => 1]);

$provider = new ActiveDataProvider([
    'query' => $query,
    'pagination' => [
        'pageSize' => 10,
    ],
    'sort' => [
        'defaultOrder' => [
            'created_at' => SORT_DESC,
            'title' => SORT_ASC,
        ]
    ],
]);

// 返回一個Post實例的數組$posts = $provider->getModels();

假如在上面的例子中,$query?用下面的代碼來創(chuàng)建,則數據提供者將返回原始數組。

use yii\db\Query;

$query = (new Query())->from('post')->where(['status' => 1]);

注意:假如查詢已經指定了?orderBy?從句,則終端用戶給定的新的排序說明(通過?sort?來配置的)將被添加到已經存在的從句中。 任何已經存在的?limit?和?offset?從句都將被終端用戶所請求的分頁(通過?pagination?所配置的)所重寫。

默認情況下,yii\data\ActiveDataProvider使用?db?應用組件來作為數據庫連接。你可以通過配置 yii\data\ActiveDataProvider::db 的屬性來使用不同數據庫連接。

SQL數據提供者

yii\data\SqlDataProvider 應用的時候需要結合需要獲取數據的SQL語句?;?yii\data\SqlDataProvider::sort 和 yii\data\SqlDataProvider::pagination 規(guī)格,數據提供者會根據所請求的數據頁面(期望的順序)來調整?ORDER BY?和?LIMIT?的SQL從句。

為了使用 yii\data\SqlDataProvider,你應該指定 yii\data\SqlDataProvider::sql 屬性以及 yii\data\SqlDataProvider::totalCount 屬性,例如,

use yii\data\SqlDataProvider;

$count = Yii::$app->db->createCommand('
    SELECT COUNT(*) FROM post WHERE status=:status
', [':status' => 1])->queryScalar();

$provider = new SqlDataProvider([
    'sql' => 'SELECT * FROM post WHERE status=:status',
    'params' => [':status' => 1],
    'totalCount' => $count,
    'pagination' => [
        'pageSize' => 10,
    ],
    'sort' => [
        'attributes' => [
            'title',
            'view_count',
            'created_at',
        ],
    ],
]);

// 返回包含每一行的數組$models = $provider->getModels();

說明:yii\data\SqlDataProvider::totalCount 的屬性只有你需要分頁數據的時候才會用到。 這是因為通過 yii\data\SqlDataProvider::sql 指定的SQL語句將被數據提供者所修改并且只返回當前頁面數據。 數據提供者為了正確計算可用頁面的數量仍舊需要知道數據項的總數。

數組數據提供者

yii\data\ArrayDataProvider 非常適用于大的數組。數據提供者允許你返回一個經過一個或者多個字段排序的數組數據頁面。 為了使用 yii\data\ArrayDataProvider,你應該指定 yii\data\ArrayDataProvider::allModels 屬性 作為一個大的數組。 這個大數組的元素既可以是一些關聯數組(例如:DAO查詢出來的結果)也可以是一些對象(例如:Active Record實例) 例如,

use yii\data\ArrayDataProvider;

$data = [
    ['id' => 1, 'name' => 'name 1', ...],
    ['id' => 2, 'name' => 'name 2', ...],
    ...
    ['id' => 100, 'name' => 'name 100', ...],
];

$provider = new ArrayDataProvider([
    'allModels' => $data,
    'pagination' => [
        'pageSize' => 10,
    ],
    'sort' => [
        'attributes' => ['id', 'name'],
    ],
]);

// 獲取當前請求頁的每一行數據$rows = $provider->getModels();

注意:數組數據提供者與?Active Data Provider?和?SQL Data Provider?這兩者進行比較的話, 會發(fā)現數組數據提供者沒有后面那兩個高效,這是因為數組數據提供者需要加載所有的數據到內存中。

數據鍵的使用

當使用通過數據提供者返回的數據項的時候,你經常需要使用一個唯一鍵來標識每一個數據項。 舉個例子,假如數據項代表的是一些自定義的信息,你可能會使用自定義ID作為鍵去標識每一個自定義數據。 數據提供者能夠返回一個通過 yii\data\DataProviderInterface::getModels() 返回的鍵與數據項相對應的列表。 例如,

use yii\data\ActiveDataProvider;

$query = Post::find()->where(['status' => 1]);

$provider = new ActiveDataProvider([
    'query' => Post::find(),
]);

// 返回包含Post對象的數組$posts = $provider->getModels();

// 返回與$posts相對應的主鍵值$ids = $provider->getKeys();

在上面的例子中,因為你提供給 yii\data\ActiveDataProvider 一個 yii\db\ActiveQuery 對象, 它是足夠智能地返回一些主鍵值作為鍵。你也可以明確指出鍵值應該怎樣被計算出來,計算的方式是通過使用一個字段名或者一個可調用的計算鍵值來配置。 例如,

// 使用 "slug" 字段作為鍵值$provider = new ActiveDataProvider([
    'query' => Post::find(),
    'key' => 'slug',
]);

// 使用md5(id)的結果作為鍵值$provider = new ActiveDataProvider([
    'query' => Post::find(),
    'key' => function ($model) {
        return md5($model->id);
    }
]);

創(chuàng)建自定義數據提供者

為了創(chuàng)建自定義的數據提供者類,你應該實現 yii\data\DataProviderInterface 接口。 一個簡單的方式是從 yii\data\BaseDataProvider 去擴展,這種方式允許你關注數據提供者的核心邏輯。 這時,你主要需要實現下面的一些方法:

  • yii\data\BaseDataProvider::prepareModels():準備好在當前頁面可用的數據模型,并且作為一個數組返回它們。

  • yii\data\BaseDataProvider::prepareKeys():接受一個當前可用的數據模型的數組,并且返回一些與它們相關聯的鍵。

  • yii\data\BaseDataProvider::prepareTotalCount(): 在數據提供者中返回一個標識出數據模型總數的值。

下面是一個數據提供者的例子,這個數據提供者可以高效地讀取CSV數據:

<?phpuse?yii\data\BaseDataProvider;

class?CsvDataProvider?extends?BaseDataProvider{
? ? /**
? ? ?*?@var?string?name?of?the?CSV?file?to?read
? ? ?*/

? ? public?$filename;

? ? /**
? ? ?*?@var?string|callable?name?of?the?key?column?or?a?callable?returning?it
? ? ?*/

? ? public?$key;

? ? /**
? ? ?*?@var?SplFileObject
? ? ?*/

? ? protected?$fileObject;?//?SplFileObject?is?very?convenient?for?seeking?to?particular?line?in?a?file


? ? /**
? ? ?*?@inheritdoc
? ? ?*/

? ? public?function?init()
? ?
{
? ? ? ? parent::init();

? ? ? ? //?open?file
? ? ? ? $this->fileObject?=?new?SplFileObject($this->filename);
? ? }

? ? /**
? ? ?*?@inheritdoc
? ? ?*/

? ? protected?function?prepareModels()
? ?
{
? ? ? ? $models?=?[];
? ? ? ? $pagination?=?$this->getPagination();

? ? ? ? if?($pagination?===?false)?{
? ? ? ? ? ? //?in?case?there's?no?pagination,?read?all?lines
? ? ? ? ? ? while?(!$this->fileObject->eof())?{
? ? ? ? ? ? ? ? $models[]?=?$this->fileObject->fgetcsv();
? ? ? ? ? ? ? ? $this->fileObject->next();
? ? ? ? ? ? }
? ? ? ? }?else?{
? ? ? ? ? ? //?in?case?there's?pagination,?read?only?a?single?page
? ? ? ? ? ? $pagination->totalCount?=?$this->getTotalCount();
? ? ? ? ? ? $this->fileObject->seek($pagination->getOffset());
? ? ? ? ? ? $limit?=?$pagination->getLimit();

? ? ? ? ? ? for?($count?=?0;?$count?<?$limit;?++$count)?{
? ? ? ? ? ? ? ? $models[]?=?$this->fileObject->fgetcsv();
? ? ? ? ? ? ? ? $this->fileObject->next();
? ? ? ? ? ? }
? ? ? ? }

? ? ? ? return?$models;
? ? }

? ? /**
? ? ?*?@inheritdoc
? ? ?*/

? ? protected?function?prepareKeys($models)
? ?
{
? ? ? ? if?($this->key?!==?null)?{
? ? ? ? ? ? $keys?=?[];

? ? ? ? ? ? foreach?($models?as?$model)?{
? ? ? ? ? ? ? ? if?(is_string($this->key))?{
? ? ? ? ? ? ? ? ? ? $keys[]?=?$model[$this->key];
? ? ? ? ? ? ? ? }?else?{
? ? ? ? ? ? ? ? ? ? $keys[]?=?call_user_func($this->key,?$model);
? ? ? ? ? ? ? ? }
? ? ? ? ? ? }

? ? ? ? ? ? return?$keys;
? ? ? ? }?else?{
? ? ? ? ? ? return?array_keys($models);
? ? ? ? }
? ? }

? ? /**
? ? ?*?@inheritdoc
? ? ?*/

? ? protected?function?prepareTotalCount()
? ?
{
? ? ? ? $count?=?0;

? ? ? ? while?(!$this->fileObject->eof())?{
? ? ? ? ? ? $this->fileObject->next();
? ? ? ? ? ? ++$count;
? ? ? ? }

? ? ? ? return?$count;
? ? }
}
?? ??: ?? ??: