8天学会PHP之day6 数据库应用

这一章主要讲解PHP操做数据库的应用。须要具有一些数据库前置知识,至少掌握mysql和redis的crud操做。就算不懂数据库的知识也无所谓,数据库语言都很是简单,从字面意义就能明白是在作什么。php

 

1、PDO

PHP链接数据库的方式有2种:mysql

  • MySQLi extension ("i" 意为 improved)laravel

  • PDO (PHP Data Objects)redis

二者的区别在于MySQLi只支持mysql,而PDO支持12种数据库。sql

为了方便,咱们只学习PDO的使用便可。由于咱们不能只会链接MySQL。这样会让咱们投入的时间性价比更高。数据库

PDO和go的go-sql-driver,Java的JDBC做用是同样的,连使用方法几乎都很是一致。作法都是建立一个链接实例,经过链接实例执行sql。api

查看PDO是否受支持

PHP7以后,php自动具有了PDO,可使用phpinfo函数查看是否开启了PDO。数组

利用上一章学习到的路由和控制器知识,写一个RESTfulAPI来查看php环境。浏览器

建立路由composer

Route::get('phpinfo', 'EnvironmentController');

建立控制器

class EnvironmentController extends Controller
{
    public function __invoke()
    {
        // 注意须要链接一个空字符串,由于phpinfo没有toString
        return phpinfo() . '';
    }
}

而后在浏览器访问http://homestead.test/api/v1/phpinfo。你应该会看到很是多的数据,能够直接搜索PDO关键字,看到以下内容就表示当前运行环境的PDO是支持的。

链接数据库

建立一个PDO实例,传入3个构造参数。第1个是数据库链接,第2个是用户名,第3个是用户密码。

function connDB($dbname = 'test')
{
    $servername = "localhost";
    $username = "homestead";
    $password = "secret";
    try {
        $conn = new PDO("mysql:host=$servername;dbname=$dbname", $username, $password);
    } catch (PDOException $e) {
        return $e->getMessage();
    }
}

建立数据库

使用建立出来的PDO实例conn来调用query方法,传入要执行的sql做为参数。

query方法返回bool值,成功为true,失败为false。

失败时还能够经过conn访问errorCode和errorInfo来获取错误信息。

$sql = "CREATE DATABASE test";
if ($conn->query($sql) == true) {
    return "数据库建立成功";
} else {
    return [
        'errorCode' => $conn->errorCode(),
        'errorInfo:' => $conn->errorInfo()
    ];
}

建立表

建立表和建立数据库的操做同样,只是执行的sql不一样。

操做数据(CRUD)

插入insert、查询select、修改update、删除delete四种操做均可以使用exec方法来执行,可是这个方法不返回任何值。只能经过try/catch来捕获异常来验证是否成功。

$conn->exec($sql);

设置错误模式

设置错误模式,用于抛出异常。若是不设置,sql执行失败也不会抛出异常。

$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

事务

开启事务$conn->beginTransaction();

提交事务$conn->commit();

回滚事务$conn->rollback();

开启事务后开始执行sql语句,执行完毕提交事务。开启异常捕获,若是出现异常,执行回滚操做。

预处理语句/SQL模板

预处理语句就是定义模板,预留?标记。例如:

insert into user (name, age, email) VALUES(?, ?, ?)

使用方法:

1.使用conn的prepare方法建立模板并返回一个对象stmt。其中字符串模板的填充字段用:前缀来修饰。

2.调用stmt的bindParam方法来绑定字段和值。接受2个参数,第1个参数是字段,第2个参数是值的变量名。

3.绑定后,执行stmt的方法execute来执行模板sql。

4.以后再次修改值时,直接修改变量的值,再次执行stmt的方法execute便可。

try {
            $stmt = $conn->prepare("insert into user (name, age, email, gender) VALUES(:name, :age, :email, :gender)");
​
            $name = "张三";
            $age = 134;
            $email = "@@@.@";
            $gender = "男";
​
            $stmt->bindParam(':name', $name);
            $stmt->bindParam(':age', $age);
            $stmt->bindParam(':email', $email);
            $stmt->bindParam(':gender', $gender);
​
            $stmt->execute();
​
            // 再次插入行
            $name = "李四";
            $age = 22;
            $email = "lisi@gmail.com";
            $stmt->execute();
            return "插入成功";
        } catch (PDOException $e) {
            return $e->getMessage();
        }

 

 

2、使用框架操做Mysql

这部分其实没什么可讲的东西,框架作的事,无非就是在PDO或mysqli基础上进行封装,简化咱们的操做而已。若是你是一直读过来的同窗,应该发现了一个问题。从学框架应用开始,讲的内容愈来愈含糊了。其实,这些框架的API我并非死记硬背的。大多数状况下,我都是先读一遍官方文档,而后针对经常使用的API写一些Demo测试。以后就是实战了。在实战中,若是发现有些需求处理的不够优雅,就会在去官方文档和社区寻找对应的更优解决方案。对我来说,学习框架的各类API是一件吃力不讨好的事。

Laravel 能使用原生 SQL、流畅的查询构造器Eloquent ORM 在各类数据库后台与数据库进行很是简单的交互。

运行原生查询

使用DBuse Illuminate\Support\Facades\DB;.

执行查询DB::select('select * from users where active = ?', [1]);,返回值始终是数组。

执行插入DB::insert('insert into users (id, name) values (?, ?)', [1, 'Dayle']);

执行更新$affected = DB::update('update users set votes = 100 where name = ?', ['John']);,返回更新的行数。

执行删除$deleted = DB::delete('delete from users');,返回删除的行数。

运行普通语句DB::statement('drop table users');无返回值。

事务

使用db的transaction方法,参数是个函数,在里面执行sql。

DB::transaction(function () {
    DB::table('users')->update(['votes' => 1]);
​   // 这里写sql
    DB::table('posts')->delete();
});

看到这里,你应该发现,咱们用框架作的事,和前面学的PDO作的事基本上是同样的,区别只是写法不一样。

那为何还要再学一遍呢?由于咱们要使用框架,框架帮助咱们处理了不少异常问题和边界问题,简化咱们的操做。

这里我不想再讲下去了,由于我不必把官方文档的API挨个演示一遍。至于更高级的操做,如构造器和eloquent ORM,若是感兴趣,建议你去中文社区进行学习这一部分的内容。https://learnku.com/docs/laravel/5.8/database/3925

 

3、使用框架操做Redis

其实在咱们目前的项目中,关于redis的使用颇有限。这里不说redis集群的使用方式,只说下redis的单机应用。

这里假设你已经在本机安装好redis。

关于redis的可视化管理工具,推荐 Redis Desktop Manager

首先在项目中安装predis包

composer require predis/predis

安装predis的过程当中可能会遇到一个异常信息:

the requested PHP extension fileinfo is missing from your system

意思是没有开启fileinfo扩展,须要在你PHP环境的php.ini文件中修改一行配置,若是没有这行配置那么就添加上。

extension=php_fileinfo.dll

若是你的redis默认配置没有修改,那么项目中的配置也都不须要修改。

若是你的redis不是本机的,或者修改了端口等,须要在项目中的config/database.php和.env文件中分别修改配置。

database.php相关配置

'redis' => [

       'client' => env('REDIS_CLIENT', 'predis'),

       'options' => [
           'cluster' => env('REDIS_CLUSTER', 'predis'),
           'prefix' => Str::slug(env('APP_NAME', 'laravel'), '_').'_database_',
      ],

       'default' => [
           'host' => env('REDIS_HOST', '127.0.0.1'),
           'password' => env('REDIS_PASSWORD', null),
           'port' => env('REDIS_PORT', 6379),
           'database' => env('REDIS_DB', 0),
      ],

       'cache' => [
           'host' => env('REDIS_HOST', '127.0.0.1'),
           'password' => env('REDIS_PASSWORD', null),
           'port' => env('REDIS_PORT', 6379),
           'database' => env('REDIS_CACHE_DB', 1),
      ],

  ],

.evn相关配置。

REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379

predis的相关操做仍是很是简单的,基本上都和redis的原生操做一致。

存值Redis::set('key', 'value');

取值Redis::get('key');

检测某值是否存在Redis::exists('user_key')

设置过时时间Redis::setex('str', 10, 'bar');

删除Redis::del('key');

redis的操做多达十几种,这里就再也不继续罗列,更多操做可查阅:https://packagist.org/packages/predis/predis

 

4、总结

这一章学习了在原生PHP和框架中操做mysql和redis的方式

相关文章
相关标签/搜索