簡體   English   中英

如何在CodeIgniter 2.1的數據庫API中實現搜索和分頁?

[英]How to implement search and pagination in CodeIgniter 2.1's database API?

我在使用Codeigniter 2.1構建的網站上無法使用搜索功能。 具體來說,我在分頁上遇到麻煩,每頁限制為15個項目。

我的控制器:

              public function program_search()
          {
      if ($this->input->post('term')){
        $this->front->set('title', 'Search Results');
        $this->front->set('res' ,  $this->wc_search->search($this->input->post('term')));

        $this->load->library('pagination');

        $config['base_url'] = base_url().'/site/program_search_results/';

        $this->db->where('JobRef',$this->input->post('term'));
        $this->db->or_where('WorkType',$this->input->post('term'));
        $this->db->or_where('Parish',$this->input->post('term'));
        $this->db->or_where('Location',$this->input->post('term'));

        $config['total_rows'] = $this->db->count_all_results('wc_program');
        $config['per_page'] = 10;
        $config['num_links'] = 20;
        $config['full_tag_open'] = '<div id="pagination">';
        $config['full_tag_close'] = '</div>';

        $this->pagination->initialize($config);     

        $this->front->buffer('content', 'site/program_search_results');
        $this->front->render();
    }
    else
    {
        $this->front->set('title', 'Program Search');
        $this->front->buffer('content', 'site/program_search');
        $this->front->render();
    }
}

然后在我的模型中,我有:

            public function search($term)
        {
    $data = array();
    $this->default_select();
    $this->db->like('JobRef', $term);
    $this->db->or_like('Area', $term);
    $this->db->or_like('Parish', $term);
    $this->db->or_like('WorkType', $term);
    $this->db->or_like('Location', $term);

    $this->default_order_by();
    //$this->db->limit(15);
    $q = $this->db->get('wc_program');
        if ($q->num_rows() > 0)
        {
            foreach ($q->result_array() as $row)
            {
                $data[] = $row;
            }
        }
    $q->free_result();
    return $data;
}

如何根據此代碼進行分頁工作? 我真的不想更改已經存在的代碼,因為搜索效果很好。 我只需要它在每頁搜索中顯示15條記錄即可。

讓我們看看我是否可以指導您解決這些問題:

  1. 您的搜索查詢需要一個LIMIT(您已將其注釋掉...並且缺少偏移量...)。
  2. 您需要將POST頁面參數( $ this-> input-> post('page') )傳遞給搜索模型,以便知道您所在的頁面,以便計算搜索模型查詢的LIMIT部分。 假設您在模型中將其稱為$ current_page
  3. 為什么您的count_all_results查詢搜索模型的查詢不匹配 它們應與相同的WHERE條件匹配(除了count查詢不具有要添加到搜索模型查詢中的LIMIT)。
  4. 計算 LIMIT(極限和偏移量):
    1. $ limit = 15;
    2. $ offset = $ limit * $ current_page-$ limit;
    3. if($ offset <0){$ offset = 0;}
  5. 現在您的限制為: $ this-> db-> limit($ offset,$ limit); 搜索模型的查詢。

希望有幫助!

將您的per_page和num_links傳遞到search()中以計算查詢的LIMIT&OFFSET

您需要做一些簡單的數學計算偏移量

正如David Graham所說,您錯過了LIMIT和OFFSET。 CodeIgniter分頁是相當基本的,因為底層的“ ActiveRecord”本身是非常基本的(本質上是查詢生成器,而不是ORM)。

因此,您需要在SQL級別上思考如何獲得所需結果的“頁面”。

下面,我包括一個項目的示例代碼。

控制器:

    // set up pagination

    $itemsPerPage = 20;
    $totalItems = $this->Location_model->count_locations( $locationName, $locationType, $locationParent );

    // get itemStartIndex from URL if specified, otherwise default to 0
    if ( $this->uri->segment(3) )
    {
        $itemStartIndex = $this->uri->segment(3);
    }
    else
    {
        $itemStartIndex = '0';
    }

    $this->load->library('pagination');

    $config['base_url'] = site_url('admin/locations');
    $config['total_rows'] = $totalItems;
    $config['per_page'] = $itemsPerPage;
    $config['uri_segment'] = 3;

    // store offset in case user triggers a function and we want to come back to same page
    $this->session->set_flashdata('pagination_offset', $itemStartIndex);

    $this->pagination->initialize($config); 

    $data['pagination'] = $this->pagination->create_links();

    // get current locations from database
    $records = $this->Location_model->get_locations( $locationName, $locationType, $locationParent, $itemStartIndex, $itemsPerPage );

    ...

    // now $records gets passed to view for display

模型:

function count_locations($locationName = '', $locationType = '', $locationParent = '')
{
    $this->db->select('id');
    if ( $locationName != '' )
    {
        $this->db->like('name', $locationName);
    }
    if ( $locationType != '')
    {
        $this->db->where('location_type', $locationType);
    }
    if ( $locationParent != '')
    {
        $this->db->where('parent_id', $locationParent);
    }

    $query = $this->db->get('locations');

    return $query->num_rows();
}

function get_locations($locationName = '', $locationType = '', $locationParent = '', $startIndex = '0', $limit = '')
{
    $this->db->select('*');
    if ( $locationName != '' )
    {
        $this->db->like('name', $locationName);
    }
    if ( $locationType != '')
    {
        $this->db->where('location_type', $locationType);
    }
    if ( $locationParent != '')
    {
        $this->db->where('parent_id', $locationParent);
    }

    $this->db->order_by('name', 'asc');
    $query = $this->db->get('locations', $limit, $startIndex);

    if ($query->num_rows() > 0)
    {
        return $query;
    }
    else
    {
        return FALSE;
    }
}

請注意,我執行查詢的方法具有可選參數$ startIndex和$ limit。 這些是分頁工作所必需的。 URI段(在我的情況下為段3)將直接告訴您的控制器要使用的OFFSET,並且您指定的per_page轉換為LIMIT(在我的情況下,我使用$ itemsPerPage進行存儲,因為它多次被引用-實際上,我在我的情況下使用的是全局值,但我在此處對其進行了硬編碼,以便於參考。

請注意,您還需要一個count方法。 您可以只使用相同的查詢,加載所有結果,然后在控制器中對它進行計數,但是我想使用單獨的計數方法,該方法僅使用WHERE限制並僅選擇COUNT('id')即可生成最小查詢它大大增加了。 (當然,缺點是它對DRY不利,因為必須將相同的查詢代碼定義兩次,一次用於您的count方法,一次用於數據查詢方法)

請注意您的代碼

與其在控制器中指定這些or_where語句,不如將它們放在描述您的搜索的方法下的模型中。 這種搜索邏輯肯定應該在模型中-控制器應該只接受路由,將輸入傳遞給模型,然后設置分頁並查看結果。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM