bead / framework
一个(处于开发中的)PHP应用程序框架
Requires
- php: ^8
- ext-dom: *
- ext-iconv: *
- ext-json: *
- ext-mbstring: *
- ext-pdo: *
- psr/container: ^2.0
- psr/http-message: ^1
- psr/log: ^3
Requires (Dev)
- ext-uopz: ^6||^7
- mockery/mockery: ^1.5
- phpunit/phpunit: ^9.5
Suggests
- ext-openssl: *
- ext-shmop: *
- ext-sodium: *
- dev-production
- 0.9.12
- 0.9.11
- 0.9.10
- 0.9.9
- 0.9.8
- 0.9.7
- 0.9.6
- 0.9.5
- 0.9.4
- 0.9.1
- dev-BEAD-218-Update-docker-test-containers-to-use-CLI-image
- dev-BEAD-217-Use-DateTimeInterface-in-Model-for-datetime-columns
- dev-BEAD-195-Move-responses-into-Web-namespace
- dev-BEAD-213-Update-UriSigner-to-use-ScrubsStrings-trait
- dev-BEAD-100-ConnectionInterface-and-StatementInterface
- dev-BEAD-207-Support-feature-flags-read-from-the-app-config-file
- dev-BEAD-203-Use-XRay-helpser-instead-of-Reflection-directly-in-tests-where-possible
- dev-BEAD-205-Update-necessary-GH-actions-to-use-node-20-versions
- dev-BEAD-211-Fix-namespace-of-ValidatorTest
- dev-BEAD-201-Fix-tests-that-have-a-tearDonw-method-instead-of-a-tearDown-method
- dev-BEAD-209-Catch-SessionDestroyed-exception-in-SessionFacade-start-and-initialise-a-new-session
- dev-BEAD-161-Refactor-ConsoleApplication
- dev-BEAD-202-Fix-static-analysis-issues-in-Facades
- dev-BEAD-198-Queue-support
- dev-BEAD-199-Type-hints-in-URI-Signer
- dev-BEAD-192-HTTP-reason-phrase-in-responses
- dev-BEAD-194-Add-PHP-8.3-to-unit-test-workflow-matrix
- dev-BEAD-193-PHP-8.3-test-image
- dev-BEAD-189-Hasher
- dev-BEAD-188-Clean-up-temp-log-files-in-Logger-binder-unit-test
- dev-BEAD-187-Fix-unit-test-class-names
- dev-BEAD-186-Configuration-of-log-level
- dev-BEAD-179-Expand-logging-config
- dev-BEAD-158-Fix-errors-in-StringStream
- dev-BEAD-185-Fix-incorrect-throws-attribute-on-Web-Application
- dev-BEAD-183-Remove-smoke-test-app-from-repo-now-has-its-own-repo
- dev-BEAD-184-Mail-facade
- dev-BEAD-137-Refactor-email-classes-for-modern-PHP
- dev-BEAD-182-Recursively-follow-config-keys-using-dot-syntax
- dev-BEAD-180-Fix-incorrect-return-type-in-Application-facade
- dev-BEAD-181-Support-exception-filtering-in-ErrorHandler
- dev-BEAD-177-Set-up-basic-environment-before-config-is-loaded
- dev-BEAD-155-Route-on-path-not-path-info
- dev-BEAD-153-Optional-plugins
- dev-BEAD-31-Router-dependency-injection
- dev-BEAD-19-function-mocking
- dev-Fix-imports-in-RouterTest
- dev-BEAD-151-Fix-incorrect-docblock-return-type-on-Validator-rules-
- dev-BEAD-149-Fix-Application-attempting-to-load-dot-and-dotdot-as-config-files
- dev-BEAD-141-static-analysis
- dev-Readme-status-badge
- dev-Rename-workflow
- dev-Bead-coding-standard
- dev-BEAD-145-remove-unnecessary-test-file
- dev-BEAD-140-use-matrix-for-test-workflow
- dev-BEAD-139-Encryption
- dev-BEAD-130-Default-logger-in-Application-class
- dev-BEAD-116-Use-dependency-injection-with-handler-for-session
- dev-BEAD-115-Unit-test-coverage-Exceptions-HttpException
- dev-BEAD-75-Unit-test-coverage-Validation-Validator
- dev-BEAD-26-implement-uploaded-file-interface-for-uploaded-files
- dev-BEAD-18-thread-class
This package is auto-updated.
Last update: 2024-09-29 20:51:09 UTC
README
一个基本的PHP MVC应用程序框架。
介绍
Bead是一个简单的MVC框架,适用于PHP 8.0及其以后的版本。
WebApplication
使用bead的每个Web应用程序都必须创建这个单例类的实例。它是应用程序的核心,提供了一组有用的功能,例如访问配置细节、插件加载、请求路由、事件注册和调度、错误处理以及发送响应。在大多数情况下,你可能想要创建一个子类,并重新实现构造函数和/或exec()
方法来执行应用程序特定的初始化。应用程序通过从主index.php
脚本中调用exec()
方法来执行。
在exec()
中的初始化期间,WebApplication
加载应用程序的配置、插件和路由。路由通过应用程序的路由器注册,默认情况下是一个\Bead\Router
的实例。你可以通过调用WebApplication::setRouter()
并传入一个实现了\Bead\Contracts\Router
接口的对象来提供自己的路由器,这可以在你的自定义WebApplication子类的构造函数中完成,或者在创建WebApplication
实例之后(显然是在调用exec()
之前)在你的index.php
文件中完成。
WebApplication单例总是可以通过WebApplication::instance()
静态方法访问。
路由
路由从应用程序源代码的子目录中加载的路线文件中加载,默认为/routes
。每个路线文件都是一个标准的PHP文件,其目的是将路由注册到路由器。路线文件通过匿名函数沙盒加载 - 路由文件可用的唯一变量是$app
,WebApplication实例(为了方便);$router
,路由器实例;以及PHP超级全局变量。
默认路由器使用HTTP方法和请求路径信息来路由请求。例如,你可以调用$router->registerGet()
来注册GET HTTP方法的路线,或者调用$router->registerPost()
来注册POST HTTP方法的路线。默认路由器中提供了以下注册方法
register($path, $methods, $handler)
- 为具有指定HTTP方法集的路径注册处理器registerGet($path, $handler)
- 仅使用GET HTTP方法为路径注册处理器registerPost($path, $handler)
- 仅使用POST HTTP方法为路径注册处理器registerPut($path, $handler)
- 仅使用PUT HTTP方法为路径注册处理器registerHead($path, $handler)
- 仅使用HEAD HTTP方法为路径注册处理器registerDelete($path, $handler)
- 仅使用DELETE HTTP方法为路径注册处理器registerConnect($path, $handler)
- 仅使用CONNECT HTTP方法为路径注册处理器registerOptions($path, $handler)
- 仅使用OPTIONS HTTP方法为路径注册处理器registerPatch($path, $handler)
- 仅使用PATCH HTTP方法为路径注册处理器registerPatch($path, $handler)
- 仅使用PATCH HTTP方法为路径注册处理器registerAny($path, $handler)
- 为任何HTTP方法为路径注册处理器
你可以根据项目的需要组织路线文件。你定义的路线文件数量没有人为限制。
路线处理器可以是任何可调用的。通常,你将定义控制器并使用方法作为路线处理器。如果提供一个形式的处理器
$router->registerGet("/some/path", [MyController::class, "theRequestHandler"]);
控制器必须有一个默认构造函数才能正常工作。如果您的控制器需要构造函数参数,或者您想使用控制器的特定实例,您可以这样做
$router->registerGet("/some/path", [new MyController($arg), "theRequestHandler"]);
任何其他可调用的表达式也可以使用
$router->registerGet("/", fn() => new View("home"));
$router->registerGet("/", "home_page_handler"); // home_page_handler() is a function defined by your app
默认路由器可以为您的路由处理程序提供参数。通过使用用花括号括起来的路径段,您可以从URL路径中提取部分内容,并将其作为参数传递给处理程序。路由器将匹配段名与处理程序中的参数名,并将从URL中提取的值作为该参数传递给处理程序。如果可能,它还会根据处理程序中参数的类型提示转换参数。例如,定义路由
$router->registerGet("/article/{articleId}/author/{authorId}/remove", function (int $articleId, int $authorId) {});
对于来自 /article/333/author/200/remove
的传入HTTP GET请求,将调用处理程序,并将 (int) 333 作为 $articleId
的参数,将 (int) 200 作为 $authorId
的参数。
在任何路由处理程序中,您还可以使用 \Bead\Request
类型为任何名称的参数提供类型提示,处理程序将接收传入的Request作为该参数的参数。
插件
这是用于增强应用程序功能的组件的基类。通常,插件会向 WebApplication
单例注册事件处理程序,以响应应用程序中的事件。例如,您可以使用插件来监听 "application.handlerequest.requestreceived" 事件,并在检测到请求来自被禁止的IP地址时抛出 NotAuthorisedException
。
您的插件目录(默认为 /app/plugins
)中的所有插件都将为应用程序的每个请求加载和实例化。因此,您应该将插件构造函数保持相对简单,以避免性能下降。
请求
客户端请求的封装。通过调用 WebApplication::exec()
,将根据 $_GET
、$_POST
、$_FILES
和 $_SERVER
超全局变量构建此类的实例。可以通过调用 WebApplication
对象的 originalRequest()
方法来始终获取传入的请求。
请求类提供了对客户端请求提供的URL参数、POST数据和上传文件的访问。它还提供了对HTTP头部的访问。
视图
视图是存储在 /views
目录中的普通PHP文件。您可以按照项目需要的任何方式组织视图。使用点符号标识视图。要实例化视图,请将其名称传递给 View
构造函数 - 例如,存储在 /views/users/edit.php
的视图将使用 new View("users.edit")
实例化。注意,基本 /views
目录名称不包括在内,.php
文件扩展名也不包括在内。
您可以使用构造函数的第二个参数向视图传递数据。数据作为关联数组传递。视图将接收一个名为数组键的变量集。所有视图也接收两个便利变量:$app
是当前运行的 WebApplication
实例;$data
是传递给构造函数的视图数据数组。视图由匿名函数沙盒渲染 - 视图中不可用全局变量,只有 $app
、视图数据和PHP超全局变量。
为了保持页面的一致性,每个视图都可以使用布局。布局与普通视图没有区别,但(为了有用),它们应该包含命名部分。打算用作布局的视图应该有一个或多个对View::yieldSection("section-name")
的调用。每个命名部分定义了视图可以添加内容的位置。视图通过在视图开头调用View::layout("layouts.layout-name")
来指示它们使用的布局,并通过在View::section("section-name")
和View::endSection()
之间放置内容来为布局的部分提供内容。当布局提供部分时,视图放入其中的内容将被渲染。布局可以定义任意多的命名部分。布局可以存储在您的/views
树中的任何位置,但为了清晰起见,建议您使用/views/layouts
。
您可以通过两种方式为视图构建可重用的部分:一种方式是调用View::include("view-name")
直接包含另一个视图的内容;另一种是调用View::component("component-name")
和View::endComponent()
将另一个视图的内容作为一个组件包含。使用includes和components之间只有很小的区别
- includes继承了包含它们的视图的所有视图数据
- components有它们自己的数据上下文,并且可以在槽中提供内容
通常,如果您想包含的视图片段是您页面的相对静态部分(例如,导航),并且您只是为了方便维护而对其进行了抽象,那么使用View::include()
可能是最合适的。如果您包含一个需要参数的可配置组件(例如,一种用户输入控件),您可能最好使用组件。有关详细信息,请参阅View
类的单独文档。
所有View
都满足Response
契约,因此您可以从您的处理方法中直接返回一个View
实例。
数据库和模型
该框架包含一个非常简单的ORM,以便在大多数情况下轻松查询和更新应用程序数据库中的数据。Bead\Database\Connection
类通过一些静态方法扩展了内置的PDO
类。Model
基类使创建数据库中存储的数据的代码表示变得简单。在最简单的情况下,您只需创建一个子类,将$properties
静态成员填充为模型所代表的表中列的名称和类型,将$table
静态成员填充为数据库表的名称。
验证
验证对使用过Laravel验证框架的人来说会感到熟悉。您通过创建一个Bead\Validation\Validator
并为其提供一个要应用和要应用它们的数据的规则集来验证数据。如果数据有效,验证器将从passes()
返回true
。如果它返回false
,它将提供一个从errors()
的错误信息集。