laravel 架构解析

date: 2016-03-16 14:27

第一次写貌似有点深度的 blog , 有点想到哪写到哪的感觉, 勿怪.

一次请求的生命周期

请求 -> 服务器

环境: nginx + php-fpm + laravel
简单讲, 我们在浏览器输入了 url,浏览器发起了一次 http 请求
首先要知道一点 http 的基础知识:

  • 构成
  1. 协议: http / https, 当然 https 是大势所趋, 未来的 http2( 应用层 )
  2. ip, 或者 域名, 这样才能在网络上找到你的服务器 ( ip + 端口 就是 网络层)
  3. 端口, http 默认 80, https 默认 443, 也可以使用不同端口,在 nginx 中配置即可
  4. path(路径) 或者 route(路由), 在nginx这里其实是 path,通过 server 配置,根据域名定位到不同的项目路径,然后将请求转发给 fpm,框架层都统一到入口脚本index.php 中,之后的 path 被框架层解析为 route
  5. http method(get、post )、restful、get params、post body data

假如我是浏览器中输入url: 首先,浏览器会帮我补上http协议,然后根据 ip(dns会帮我把域名转成ip) 找到服务器, 再根据端口找到服务器上面的服务(这里是 nginx 的 server 配置), 然后根据 nginx 的配置到项目的根目录, 然后 nginx 把请求交给 fpm,fpm 其实是执行框架的入口脚本index.php ,然后根据 path 去找 route。

一个 nginx + php-fpm 的实例:

server {
        listen       80; # 端口
        server_name  laravel.dev laravel.dev; # 域名
        root   /data/web/laravel/public; # 项目根目录
        index  index.html index.htm index.php; # 默认执行文件
        autoindex  on; # 开启目录浏览功能
        location / { # 所有文件的执行规则
            try_files $uri $uri/ /index.php?$query_string; # 转换url, 不显示 index.php
        }
        location ~ \.php(.*)$ { # php 后缀文件的执行规则, 其实就是交给 php-fpm 来执行
            fastcgi_pass   127.0.0.1:9000; # 也可以使用 unix socket
            fastcgi_index  index.php;
            fastcgi_param  SCRIPT_FILENAME  $document_root$fastcgi_script_name;
            include        fastcgi_params;
        }
}

这里有一点要注意: nginx 是先 执行文件 , 比如你有一个 url为 http://xxx.com/test, 根目录下刚好有一个名为 test 的文件, 那么nginx就直接去下载这个文件了, 而不会到你项目中 test 对应的 controller/action

请求 -> laravel 框架

通过上面可以知道 请求public/index.php 文件来执行.
index.php 这个文件干了 3 件事[1]:

  1. 实现 composer 的 类的自动加载
  2. 载入 laravel app, 核心是一个 service container, 这个后面慢慢分析
  3. return response, 返回 http response
  • 关于类的自动加载, 可以参考下面2个教程:
  1. 站在巨人的肩膀上写代码—SPL: http://www.imooc.com/learn/150, 里面详细的讲了类的自动加载是如何 发展&实现
  2. PHP实现手机归属地查询: http://www.imooc.com/learn/604, 类的自动加载的 简单 实现
  • laravel 处理请求的简单流程
  1. 创建 laravel app / service container 实例
  2. 请求交给 app/Http/Kernel.php 处理
  3. app/Http/Kernel.php 扩展自 Illuminate\Foundation\Http\Kernel, 里面定义了 bootstrappers, 在请求执行前运行; 还定义了 middleware, 类似 管道 的作用.
  4. 请求经过 app/Http/Route.php 文件进行匹配, 找到相应的执行方法, 执行后获取 response

service container

service container 用来关联 service provider, 用来为应用提供各种服务, 比如: db/队列/缓存 等等, 创建应用时, 会执行所有 service provider 的 register 方法, 用来绑定 service provider 到 service container 中, 当所有 service provider 都 注册 后, 执行 boot 方法.

  • laravel5 应用结构
app/                    你写的主要代码都在这里
    console/            php artisan 脚本
        commands/       php artisan 脚本
        Kernel.php      cli 内核, 添加的 php artisan 指令需要在这里注册
    events/
    exceptions/
    Http/               http request
        Controllers/    控制器
        Middleware/     中间件
        Requests/       自定义请求, 可以将表单验证独立出来到这里
        Kernel.php      http 内核, middleware 需要在这里注册
    Jobs/               可以从 controller 中抽取一部分代码到这里
    Listeners/
    Policies/           达到颗粒化权限认证的效果
    Providers/
    User.php            自带 auth 认证使用的 ORM 模型
bootstrap/
    cache/              启动优化的缓存文件
config/                 配置文件, 注意这里的文件是被直接 require 的, 所以只使用配置数组, 不要使用语句
database/               数据库相关文件, 也可以将 sqlite 搭建在此目录下
    factories/          数据工厂, 用来 db:seed 使用
    migrations/         数据库迁移文件
    seeds/              数据生成, 比如生成测试数据, 创建 admin 账号
public/                 asset(js/css/font)
resources/              raw resource(原生资源)
    assets/             LESS, SASS, CoffeeScript 等
    lang/               多语音配置文件
    views/              视图文件
storage/                文件存储目录
    framework/          包括使用 file 作为驱动的 session / cookie, blade模板编译后的文件
    logs/               日志文件
tests/
vendor/                 composer 资源, 包括 laravel 框架源码
index.php               入口脚本
  • service provider

为框架提供各种各样的服务, 比如 db / cache / 文件存储, service provider 简单而言就实现了2件事: 绑定服务到服务容器; 按需加载

  • service container

laravel的核心, 本质上是一个高级的 Ioc 容器, 能轻松的实现 依赖注入控制反转, 这样就可以轻松的解决 类&类 之间的依赖的关系, 写出更 优雅 的代码.

why

其实整个请求进入laravel的过程, 框架实例化一个 app 类, 然后这个 app 类的调用各种服务 request / response / db / cache 来完成各种事务.
为什么要采取这样一种方式呢?

  1. 扩展性: 需要什么功能, 添加服务即可.
  2. 面向接口编程: 订立契约精神, app 不用管服务的具体实现, 只要自己需要的服务器能被提供就行了, 不同的实现方式可以通过实现接口来实现.

推荐一篇讲解 laravel 服务容器的干货: http://laravelacademy.org/post/769.html [2]


  1. 这里只讨论 http 请求, 不讨论 cli (控制台)

  2. laravel 学院

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,293评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,604评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,958评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,729评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,719评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,630评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,000评论 3 397
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,665评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,909评论 1 299
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,646评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,726评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,400评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,986评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,959评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,197评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,996评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,481评论 2 342

推荐阅读更多精彩内容

  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,594评论 18 139
  • 0 系列目录# WEB请求处理 WEB请求处理一:浏览器请求发起处理 WEB请求处理二:Nginx请求反向代理 本...
    七寸知架构阅读 13,876评论 22 190
  • git clone https://github.com/laradock/laradock.git 例子:运行 ...
    啊吖优品阅读 3,431评论 2 6
  • 第一章 Nginx简介 Nginx是什么 没有听过Nginx?那么一定听过它的“同行”Apache吧!Ngi...
    JokerW阅读 32,636评论 24 1,002
  • 司马懿生快生快困死了睡说申请洗洗澡撒咋啊
    瓢根儿阅读 491评论 0 0