Download - Introduction to CodeIgniter
Introduction to CodeIgniter A Fully Baked PHP Framework
@ IDSL - Dept. of IM - NTUST
Chun-Kai Wang (王雋凱)
Overview
▪ About Framework
▪ CodeIgniter Basics
▪ Coding Hello World
▪ Implementing a Simple Guestbook
2
About Framework 首先 我們來談談什麼是 Framework
What is Framework? ▪ Definition from Wikipedia:
框架就是制定一套規範或者規則(思想),
大家(程式設計師)在該規範或者規則(思想)下工作,
或者說就是使用別人搭好的舞台,你來做表演。
▪ 更簡單的說法?
4
Framework 在有限制的條件下
提供使用者在更短時間內
開發出品質更佳
Why use Framework? ▪ Code and File Organization
▪ 提供良好、便於維護的網站架構
▪ Utilities and Libraries ▪ 站在巨人的肩膀上寫程式
▪ The MVC Pattern ▪ 將程式邏輯、資料內容與顯示畫面分離
▪ Security ▪ 解決安全性問題 (e.g. SQL Injection, XSS, CSRF)
▪ Less Code & Faster Development ▪ 使用更少的程式碼,提高開發速度
6
使用 Framework
就像在別人打好的地基下蓋房子
不需要自己全部重新來過
CodeIgniter is a PHP Framework ▪ A Lightweight PHP Framework
▪ 麻雀雖小但五臟俱全
▪ High Performance
▪ 效能佳
▪ Easy to Use
▪ 使用簡單,無須複雜的設定
▪ Clear and Thorough Documentation
▪ 有豐富的中文文件,易於學習
8
CodeIgniter Basics CodeIgniter 快速入門
How to install?
▪懶人安裝:下載 + 解壓縮 = 安裝完成!
1. 下載檔案
▪ http://www.codeigniter.org.tw/downloads
2. 解壓縮至網頁根目錄
▪ unzip CodeIgniter_2.x.x
3. 輸入網址
▪ http://your_host/codeigniter/
10
Welcome to CodeIgniter
▪ CodeIgniter 安裝完成畫面
11
CodeIgniter 目錄
application 網站主目錄
system CodeIgniter 核心目錄
user_guide CodeIgniter 使用手冊
index.php 網站主程式
▪ 一般來說不會更動核心目錄內容
▪ 升級版本更換 system 資料夾即可
12
CodeIgniter 架構
13
------------------------------------------------------ 網站主目錄
------------------------------------------------------------ 快取檔案目錄
------------------------------------------------------------ 網站設定檔
------------------------------------------------------------ MVC之Controller,繼承 CI_Controller
------------------------------------------------------------ 擴充核心類別
------------------------------------------------------------ 404、403 網頁
------------------------------------------------------------ 擴充輔助函式
------------------------------------------------------------ 擴充核心程式
------------------------------------------------------------ 擴充語系檔
------------------------------------------------------------ 擴充函式庫
------------------------------------------------------------ 日誌
------------------------------------------------------------ MVC之Model,一般繼承 CI_Model
------------------------------------------------------------ 第三方函式庫
------------------------------------------------------------ MVC之View
------------------------------------------------------ 核心目錄
------------------------------------------------------------ 核心程式:核心類別、初始化
------------------------------------------------------------ 資料庫操作相關程式
------------------------------------------------------------ 字體
------------------------------------------------------------ 輔助函式
------------------------------------------------------------ 語系檔
------------------------------------------------------------ 函式庫
MVC (Model-View-Controller)
14
Controller View
Model
Database
V Present Data to User 畫面呈現
C Application Logic 處理邏輯
M Manage Date 處理資料
CodeIgniter 運作流程
▪ index.php 供做前端的控制器(controller),載入執行 CodeIgniter 所需的基本的資源。
▪ Routing 檢驗 HTTP request 來決定有哪些東西需要被處理。
▪ 假如快取檔(caching file)存在的話,它會直接把快去送給瀏覽器,跳過後續正常的處理。
▪ Security 是在應用程式控制器(application controller)被載入之前,由 HTTP request 以及任何使用者送出的資料,都會在 security 進行過慮。
▪ 應用程式控制器(application controller)則負責載入各種不同的 request 所需的模型(model)、核心函式庫(core libraries)、補助函數(helpers)、以及所有其他資源等。
▪ 最後的檢視(View)建立出來,並送給網頁瀏覽器。假如快取功能有啟動的話,那麼檢視(View)會先被快取(Caching)下來,然後送給網頁瀏覽器。
15
控制器 (Controller) ▪ 控制器(Controller) 為一類別,繼承 CI_Controller,處理 URI。
▪ e.g. http://example.com/index.php/blog/
▪ Controller 預設載入 function index()
16
<?php class Blog extends CI_Controller { public function index() { echo 'Hello World!'; } } ?>
模型 (Model) ▪ 模型(Model) 是設計處理資料庫的類別,繼承 CI_Model。
▪ 在 Model 中撰寫函式以定義對資料庫 CRUD 的操作。
▪ CURD:Create(新增)、Read(讀取)、Update(修改)、Delete(刪除)
▪ 在控制器(Controller)中,呼叫 Model 的方法:
17
<?php class Model_name extends CI_Model { // some function here ...... } ?>
$this->load->model('model_name'); $this->model_name->function();
檢視 (View) ▪ 檢視(View) 負責畫面的呈現,可以是網頁或頁面的片斷。
▪ e.g. header, footer, sidebar.
▪ 在控制器(Controller)中,載入 View 的方法:
18
<html> <head> <title>My Blog</title> </head> <body> <h1>Welcome to my Blog!</h1> </body> </html>
$this->load->view('view_name');
以上為 MVC 模式的基礎介紹
接下來我們看看 CodeIgniter
與傳統 PHP 寫法的不同
CodeIgniter URL ▪ http://example.com/index.php/class/function/id
▪ 控制器(controller)啟動的類別(class)
▪ 類別的函式(function)被呼叫使用
▪ 任何變數要傳給控制器(controller)所使用
▪ 傳遞的參數可以當作 GET 方式使用,相當於:
▪ http://example.com/news.php?mode=edit&id=10
20
移除網址列 index.php
▪ Appache mod_rewrite module
▪ 利用 .htaccess 移除 URL 包含的 index.php
▪ 將 .htaccess 放置於 CodeIgniter index.php 所在目錄:
▪ 修改設定檔 ▪ application/config/config.php ▪ $config['index_page'] = 'index.php'; $config['index_page'] = ' ';
21
<IfModule mod_rewrite.c> RewriteEngine On RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d RewriteRule ^(.*)$ index.php/$1 [L] </IfModule>
改為
URL 加入副檔名
▪ http://example.com/news.html
▪修改設定檔
▪ application/config/config.php
▪ $config['url_suffix'] = '.html';
▪ $config['url_suffix'] = '.aspx';
▪ 這樣就可以偽裝成 ASP.NET
22
處理 $_POST 與 $_GET 資料
傳統 PHP 寫法
24
if (!isset($_POST['user'])) { $user = false; } else { $user = $_POST['user']; } $user = !isset($_POST['user']) ? false : $_POST['user'];
CodeIgniter 一行就可以解決 ▪ $_POST 資料
▪ $_GET 資料
▪ 一起判斷
▪ 先找 $_POST['user'] 後找 $_GET['user']
25
$user = $this->input->post('user');
$user = $this->input->get('user');
$user = $this->input->get_post('user');
避免 XSS 攻擊
26
▪ $_POST 資料
▪ $_GET 資料
▪ 一起判斷
▪ 先找 $_POST['user'] 後找 $_GET['user']
$user = $this->input->post('user', TRUE);
$user = $this->input->get('user', TRUE);
$user = $this->input->get_post('user', TRUE);
連接資料庫
還在用 mysql_connect 嗎?
以前都是這麼寫
28
<?php
$link = mysql_connect($db_host, $db_username, $db_password);
if (!$link) {
die('Could not connect: ' . mysql_error());
}
mysql_select_db($db_name, $link);
$query = "SELECT id, name FROM mytable“;
$result = mysql_query($query);
while ($row = mysql_fetch_row($result)) {
// some code here ......
// ......
}
mysql_close($link);
?>
CodeIgniter 的作法
▪資料庫設定
▪ application/config/database.php
▪ Database Active Record
▪ 查詢資料 (Selecting)
▪ 新增資料 (Inserting)
▪ 更新資料 (Updating)
▪ 刪除資料 (Deleting)
29
Active Record (Selecting) ▪ 查詢資料
▪ 加入 WHERE 條件
30
$this->db->select('title, content, date'); $this->db->from('mytable'); $query = $this->db->get(); // 產生: SELECT title, content, date FROM mytable
$this->db->where('name', $name); $this->db->where('title', $title); $this->db->where('status', $status); // WHERE name = 'Joe' AND title = 'boss' AND status = 'active'
Active Record (Inserting) ▪ 新增資料
▪ 回傳ID值
31
$data = array( 'title' => 'My title' , 'name' => 'My Name' , 'date' => 'My date' ); $this->db->insert('mytable', $data); // 產生: INSERT INTO mytable (title, name, date) VALUES ('My title', 'My name', 'My date')
$this->db->insert_id()
Active Record (Updating) ▪ 更新資料
32
$data = array( 'title' => $title, 'name' => $name, 'date' => $date ); $this->db->where('id', $id); $this->db->update('mytable', $data); // 產生: // UPDATE mytable // SET title = '{$title}', name = '{$name}', date = '{$date}' // WHERE id = $id
Active Record (Deleting) ▪ 刪除資料
▪ 刪除多個資料表資料
33
$this->db->where('id', $id); $this->db->delete('mytable'); // 產生: // DELETE FROM mytable // WHERE id = $id
$tables = array('table1', 'table2', 'table3'); $this->db->where('id', '5'); $this->db->delete($tables);
亦可使用傳統 SQL 語法執行查詢 $this->db->query('YOUR QUERY HERE');
回傳查詢值 (Result)
▪單筆資料
▪ result() 回傳物件
▪ result_array() 回傳陣列
▪多筆資料
▪ row() 回傳物件
▪ row_array() 回傳陣列
顯示單筆資料 (物件版)
▪ result()
36
$query = $this->db->query("YOUR QUERY"); if ($query->num_rows() > 0) { foreach ($query->result() as $row) { echo $row->title; echo $row->name; echo $row->body; } }
顯示單筆資料 (陣列版)
▪ result_array()
37
$query = $this->db->query("YOUR QUERY"); if ($query->num_rows() > 0) { foreach ($query->result_array() as $row) { echo $row['title']; echo $row['name']; echo $row['body']; } }
顯示多筆資料 (物件版)
▪ row()
38
$query = $this->db->query("YOUR QUERY"); if ($query->num_rows() > 0) { $row = $query->row(); echo $row->title; echo $row->name; echo $row->body; }
顯示多筆資料 (陣列版)
▪ row_array()
39
$query = $this->db->query("YOUR QUERY"); if ($query->num_rows() > 0) { $row = $query->row_array(); echo $row['title']; echo $row['name']; echo $row['body']; }
CodeIgniter 預設
不會載入未使用模組
使用時請自行載入
High Performance Framework ▪ 載入 view
▪ 載入 model
▪ 載入 library
▪ 載入 helper
41
$this->load->view('file_name');
$this->load->model('model_name');
$this->load->helper('helper_name');
$this->load->library('library_name');
當然也可以設定為自動載入 ▪ application/config/autoload.php
42
/* 自動載入 Package */ $autoload['packages'] = array(); /* 自動載入 Library */ $autoload['libraries'] = array(); /* 自動載入 Helper */ $autoload['helper'] = array(); /* 自動載入 Model */ $autoload['model'] = array();
CodeIgniter 的基本介紹
到這邊告一段落
關於 CodeIgniter 的更多用法
請查閱 User Guide http://www.codeigniter.org.tw/user_guide/
Coding Hello World 使用 CodeIgniter 撰寫 PHP 程式
Controller (controllers/welcome.php)
▪ 安裝好的 CodeIgniter 在 application/controllers/ 目錄下已包含一個名為 welcome.php 的Controller。
▪ 現在,我們為 Controller 增加一個 function:
46
<?php class Welcome extends CI_Controller { public function index() { $this->load->view('welcome_message'); } // 新增的 function public function page($id = false) { $data['name'] = $id; $this->load->view('welcome', $data); } }
Views (views/welcome.php)
▪ 在 application/views/ 目錄下新增檔案,取名為 welcome.php。
▪ 這個檔案作為 Controller 載入的 View,用來呈現畫面內容。
47
<html> <head> <title>Hello World</title> </head> <body> hello <?php echo $name; ?> </body> </html>
打開瀏覽器並輸入網址 http://your_host/index.php/page/world
Hello World
▪瀏覽器畫面
49
Hello World 架構 View (views/welcome.php) <html> <head> <title>Hello World</title> </head> <body> hello <?php echo $name; ?> </body> </html> Controller (controllers/welcome.php) class welcomeome extends CI_Controller { public function page($id) { $data['name'] = $id; $this->load->view('welcome', $data); } }
View
Controller
• http://your_host/index.php/welcome/page/world (Controller) (function) (Argument)
50
恭喜你已經完成
第一個 CodeIgniter 程式
在下一個範例中
我們將學習結合資料庫
實作出動態網站
Implementing a Simple Guestbook
實戰演練!簡易留言板實作
資料庫設定 ▪ application/config/database.php
54
/* 連線資料庫伺服器,通常是本地端 "localhost" */ $db['default']['hostname'] = 'localhost'; /* 連線資料庫帳號 */ $db['default']['username'] = 'your_db_username'; /* 連線資料庫密碼 */ $db['default']['password'] = 'your_db_password'; /* 連線資料庫名稱 */ $db['default']['database'] = 'your_db_name'; /* 資料庫類型 */ $db['default']['dbdriver'] = 'mysql';
新增資料表 ▪ 連線至資料庫並執行以下 SQL 指令:
▪ 請試著增加幾筆資料,以測試查詢結果。
55
CREATE TABLE guestbook (
id int(11) NOT NULL AUTO_INCREMENT,
name varchar(128) NOT NULL,
text text NOT NULL,
time datetime NOT NULL,
PRIMARY KEY (id)
);
Controller (controllers/guestbook.php)
▪ 在 controllers/ 目錄下新增檔案,取名為 guestbook.php。
▪ 注意類別名稱必須第一個字母大寫。
56
<?php class Guestbook extends CI_Controller { public function __construct() { parent::__construct(); $this->load->model('guestbook_model'); // 載入model $this->load->helper(array('url', 'form')); // 載入輔助函式 } public function index() { $data['message'] = $this->guestbook_model->get_messages(); $this->load->view('guestbook/index', $data); } }
Model (models/guestbook_model.php)
▪ 在 models/ 目錄下新增檔案,取名為 guestbook_model.php。
▪ 類別名稱必須第一個字母大寫,model命名規則包含後綴字_model。
57
<?php class Guestbook_model extends CI_Model { public function __construct() { $this->load->database(); } /* 取得留言資料 */ public function get_messages() { $this->db->select('*'); $this->db->from('guestbook'); $this->db->order_by('id', 'desc'); $query = $this->db->get(); return $query->result_array(); } }
View (views/guestbook/index.php)
▪ 在 views/ 目錄下新增 guestbook/ 目錄。
▪ 為留言板撰寫主畫面,在此目錄下新增檔案取名為 index.php。
58
<html> <head> <title>Guestbook</title> </head> <body> <?php foreach ($message as $row): ?> <p> ID: <?php echo $row['id'] ?><br /> Name: <?php echo $row['name'] ?><br /> message: <?php echo $row[‘text'] ?><br /> Time: <?php echo $row['time'] ?><br /> </p> <?php endforeach ?> </body> </html>
留言板主畫面 ▪ http://your_host/index.php/guestbook
59
為留言板加入
新增、修改、刪除 功能
Controller (controllers/guestbook.php)
▪ 在 Guestbook 類別內撰寫 function post(),用以顯示新增留言表單。
61
<?php class Guestbook extends CI_Controller { // some code here ...... // ...... public function post() { $this->load->view('guestbook/post'); } }
Controller (controllers/guestbook.php)
▪ 在 Guestbook 類別內撰寫 function add(),接收 POST 資料,並透過
model 新增至資料庫。
62
<?php class Guestbook extends CI_Controller { // some code here ...... // ...... public function add() { $data['name'] = $this->input->post('name'); $data['text'] = $this->input->post('text'); $data['time'] = date('Y-m-d h:i:s'); $this->guestbook_model->add_message($data); // 呼叫model函式 redirect(‘guestbook’); // 返回主畫面 } }
Controller (controllers/guestbook.php)
▪ 在 Guestbook 類別內撰寫 function edit(),用以顯示修改留言表單。
63
<?php class Guestbook extends CI_Controller { // some code here ...... // ...... public function edit($id) { $data['message'] = $this->guestbook_model ->get_message_by_id($id); $this->load->view('guestbook/edit', $data); } }
Controller (controllers/guestbook.php)
▪ 在 Guestbook 類別內撰寫 function update(),接收 POST 資料,並透過
model 更新資料庫留言資料。
64
<?php class Guestbook extends CI_Controller { // some code here ...... // ...... public function update() { $id = $this->input->post('id'); $data['name'] = $this->input->post('name'); $data['text'] = $this->input->post('text'); $data['time'] = date('Y-m-d h:i:s'); $this->guestbook_model->update_message($id, $data); redirect(‘guestbook’); } }
Controller (controllers/guestbook.php)
▪ 在 Guestbook 類別內撰寫 function delete(),透過 model 刪除資料庫留
言資料。
65
<?php class Guestbook extends CI_Controller { // some code here ...... // ...... public function delete($id) { $this->guestbook_model->delete_message($id); redirect('guestbook'); } }
Model (models/guestbook_model.php)
▪ 在 Guestbook_model 類別內撰寫 function get_message_by_id($id) ,向
資料庫取得單筆留言資料。
66
<?php class Guestbook_model extends CI_Model { // some code here ...... // ...... public function get_message_by_id($id) { $this->db->select('*'); $this->db->from('guestbook'); $this->db->where('id', $id); $query = $this->db->get(); if ($query->num_rows() > 0) { return $query->row_array(); } return null; } }
Model (models/guestbook_model.php)
▪ 在 Guestbook_model 類別內撰寫 function add_message($data),向資料
庫新增留言資料。
67
<?php class Guestbook_model extends CI_Model { // some code here ...... // ...... public function add_message($data) { $this->db->insert('guestbook', $data); $id = $this->db->insert_id(); return $id; // 回傳 id } }
Model (models/guestbook_model.php)
▪ 在 Guestbook_model 類別內撰寫 function update_message($id, $data),
對資料庫更新留言資料。
68
<?php class Guestbook_model extends CI_Model { // some code here ...... // ...... public function update_message($id, $data) { $this->db->where('id', $id); $this->db->update('guestbook', $data); } }
Model (models/guestbook_model.php)
▪ 在 Guestbook_model 類別內撰寫 function delede_message($id),對資
料庫刪除留言資料。
69
<?php class Guestbook_model extends CI_Model { // some code here ...... // ...... public function delete_message($id) { $this->db->where('id', $id); $this->db->delete('guestbook'); } }
View (views/guestbook/index.php)
▪ 修改留言板主畫面,增加功能新增、修改、刪除功能連結:
70
<html> <head> <title>Guestbook</title> </head> <body> <h1>Guestbook</h1> <?php echo anchor('guestbook/post', 'Leave a Message') ?> <?php foreach ($message as $row): ?> <p> ID: <?php echo $row['id'] ?><br /> Name: <?php echo $row['name'] ?><br /> message: <?php echo $row[‘text'] ?><br /> Time: <?php echo $row['time'] ?><br /> <?php echo anchor('guestbook/edit/' . $row['id'], '[Edit]') ?> <?php echo anchor('guestbook/delete/' . $row['id'], '[Delete]') ?> </p> <?php endforeach ?> </body> </html>
View (views/guestbook/post.php)
▪ 在 views/guestbook/ 目錄下新增檔案,取名為 post.php。
▪ 此畫面為新增留言表單。
71
<html> <head> <title>Guestbook</title> </head> <body> <?php echo form_open('guestbook/add') ?> <label for="name">Name:</label> <input type="text" name="name" id="name" /><br /> <label for="text">Message:</label><br /> <textarea name="text" id="text" rows="3" cols="50"> Leave a Message! </textarea><br /> <input type="submit" value="Submit" /> <?php echo form_close() ?> </body> </html>
View (views/guestbook/edit.php)
▪ 在 views/guestbook/ 目錄下新增檔案,取名為 edit.php。
▪ 此畫面為修改留言表單。
72
<html> <head> <title>Guestbook</title> </head> <body> <?php echo form_open('guestbook/update') ?> <label for="name">Name:</label> <input type="text" name="name" id="name" value="<?php echo $message['name'] ?>" /><br /> <label for="text">Message:</label><br /> <textarea name="text" id="text" rows="3" cols="50"> <?php echo $message['text'] ?> </textarea><br /> <input type="hidden" name="id" value="<?php echo $message['id'] ?>" /> <input type="submit" value="Submit" /> <?php echo form_close() ?> </body> </html>
留言板功能已經完成了
打開瀏覽器看看畫面呈現
留言板主畫面 ▪ http://your_host/index.php/guestbook
74
新增留言表單 http://your_host/index.php/guestbook/post
75
修改留言表單 http://your_host/index.php/guestbook/edit/1
76
簡易留言板架構 ▪ View (views/guestbook/)
▪ index.php 留言板主畫面 ▪ post.php 新增留言表單 ▪ edit.php 修改留言表單
▪ Controller (controllers/guestbook.php)
▪ index() 顯示留言板主畫面 ▪ post() 顯示新增留言表單 ▪ add() 處理新增留言 ▪ edit() 顯示修改留言表單 ▪ update() 處理更新留言 ▪ delete() 處理刪除留言
▪ Model (models/guestbook_model.php) ▪ get_messages() 取得所有留言資料 ▪ get_message_by_id($id) 取得一筆留言資料 ▪ add_message($data) 新增留言資料 ▪ update_message($id, $data) 更新留言資料 ▪ delete_message($id) 刪除留言資料
77
View
Controller
Model
恭喜你已學會使用 CodeIgniter
與資料庫結合實作出動態網頁
以下介紹幾套好用的
Third-party Libraries
Useful Libraries
▪ codeigniter-template ▪ https://github.com/appleboy/CodeIgniter-Template
▪ 可為網站加入主樣板 (Template)
▪ 如 ASP.NET 中的 MasterPage
▪ 動態載入 CSS 或 JavaScript
▪ Ion_Auth ▪ https://github.com/benedmunds/CodeIgniter-Ion-Auth/
▪ 會員登入系統
▪ 支援單一帳號多重群組
▪ Email 啟動帳號、忘記密碼 … etc
還有更多 Libraries 在 Sparks
http://getsparks.org/
What is Sparks ▪ Package Management System for Codeigniter
▪ Making Code Easy to Find, Create, and Distribute
▪ How to install?
82
$ php -r "$(curl -fsSL http://getsparks.org/go-sparks)"
How to use Sparks? ▪ Using Sparks
▪ menu - The menu library is used to ...
▪ redies - A CodeIgniter library to ...
▪ Retrieving spark detail from getsparks.org ...
▪ Sparks installed to ./sparks/redis/0.3.0 - You're on fire!
▪ Using Package
83
$ php tools/spark search redis
$ php tools/spark install redis
$this->load->spark('redis/0.3.0'); $this->this->set('foo', 'bar');
Welcome to Codeigniter
Enjoy Coding!
References
▪ CodeIgniter User Guide
▪ http://www.codeigniter.org.tw/user_guide/
▪ CodeIgniter Sparks
▪ http://getsparks.org/
▪ AppleBOY 部落格技術教學
▪ http://blog.wu-boy.com/tag/codeigniter/
85
Thank you!