sancherie / annotations
为 Laravel 框架的路由提供注释。
Requires
- php: ^8.0
- doctrine/annotations: 1.13.2
- illuminate/console: 9.0
- illuminate/filesystem: 9.0
- illuminate/support: 9.
Requires (Dev)
- illuminate/database: 9.0
- mockery/mockery: ^1.0
- phpunit/phpunit: ^9.0
- 9.x-dev
- 9.0.0
- v8.1
- 8.0.x-dev
- dev-master / 8.0.x-dev
- v8.0.2
- v8.0.1
- v8.0
- 7.0.x-dev
- v7.0
- 6.0.x-dev
- v6.0.2
- 6.0.1
- v6.0
- 5.8.x-dev
- v5.8.1
- v5.8
- 5.7.x-dev
- v5.7.1
- v5.7
- 5.6.x-dev
- v5.6.1
- v5.6
- 5.5.x-dev
- v5.5.1
- v5.5
- 5.4.x-dev
- v5.4.3
- v5.4.2
- v5.4.1
- v5.4.0
- 5.3.x-dev
- v5.3.0
- 5.2.x-dev
- v5.2.1
- v5.2
- 5.1.x-dev
- v5.1.2
- v5.1.1
- v5.1.0
- 5.0.x-dev
- v5.0.9
- v5.0.8
- v5.0.7
- v5.0.6
- v5.0.5
- v5.0.4
- v5.0.3
- v5.0.2
- v5.0.1
- v5.0.0
This package is auto-updated.
Last update: 2024-09-24 12:11:38 UTC
README
注释
安装
如果您已将顶级命名空间更改为类似 'MyCompany' 的内容,那么您将使用新的命名空间而不是 'App'。
首先通过 Composer 安装此包。编辑您的项目 composer.json
文件以要求 laravelcollective/annotations
。
"require": {
"laravelcollective/annotations": "8.0.\*"
}
接下来,从终端更新 Composer
composer update
Composer 完成后,您需要在 app/Providers/AnnotationsServiceProvider.php
中创建一个 Service Provider。
<?php namespace App\Providers; use Collective\Annotations\AnnotationsServiceProvider as ServiceProvider; class AnnotationsServiceProvider extends ServiceProvider { /** * The classes to scan for event annotations. * * @var array */ protected $scanEvents = []; /** * The classes to scan for route annotations. * * @var array */ protected $scanRoutes = []; /** * The classes to scan for model annotations. * * @var array */ protected $scanModels = []; /** * Determines if we will auto-scan in the local environment. * * @var bool */ protected $scanWhenLocal = false; /** * Determines whether or not to automatically scan the controllers * directory (App\Http\Controllers) for routes * * @var bool */ protected $scanControllers = false; /** * Determines whether or not to automatically scan all namespaced * classes for event, route, and model annotations. * * @var bool */ protected $scanEverything = false; /** * Determines whether to use attributes for scanning. * * @var bool */ protected $useAttribute = false; }
最后,将新提供者添加到 config/app.php
的 providers
数组中
'providers' => [ // ... App\Providers\AnnotationsServiceProvider::class // ... ];
这不会替换 RouteServiceProvider
,它仍然需要,因为它处理路由缓存等的加载。
设置扫描
将事件处理器类添加到 protected $scanEvents
数组中以扫描事件注释。
/** * The classes to scan for event annotations. * * @var array */ protected $scanEvents = [ App\Handlers\Events\MailHandler::class, ];
将控制器添加到 protected $scanRoutes
数组中以扫描路由注释。
/** * The classes to scan for route annotations. * * @var array */ protected $scanRoutes = [ App\Http\Controllers\HomeController::class, ];
将模型添加到 protected $scanModels
数组中以扫描模型注释。
/** * The classes to scan for model annotations. * * @var array */ protected $scanModels = [ 'App\User', ];
或者,您可以将 protected $scanEverything
设置为 true
以自动扫描您应用程序命名空间内的所有类。 注意: 这可能会根据您应用程序的大小增加执行扫描器所需的时间。
您可以通过使用 php artisan event:scan
、php artisan route:scan
或 php artisan model:scan
分别手动扫描事件处理器、控制器和模型。在本地环境中,您可以通过设置 protected $scanWhenLocal = true
自动扫描它们。
事件注释
@Hears
@Hears
注释为特定事件注册一个事件监听器。对任何方法使用 @Hears("SomeEventName")
注释将注册一个事件监听器,当 SomeEventName
事件被触发时将调用该方法。
<?php namespace App\Handlers\Events; use App\User; class MailHandler { /** * Send welcome email to User * @Hears("UserWasRegistered") */ public function sendWelcomeEmail(User $user) { // send welcome email to $user } }
如果您更喜欢使用属性,请将 $useAttribute
设置为 true
并这样做。请注意,与注释不同,需要使用使用语句才能使用属性。
<?php namespace App\Handlers\Events; use App\User; use Collective\Annotations\Events\Attributes\Attributes\Hears; class MailHandler { #[Hears('UserWasRegistered')] public function sendWelcomeEmail(User $user) { // send welcome email to $user } }
路由注释
路由注释非常强大,但是您的路由定义顺序可能会影响您的应用程序匹配特定路由的方式,特别是任何通配符路由。如果 protected $scanEverything
设置为 true
,您将无法控制路由定义的顺序。
@Get
@Get
注释为 HTTP GET 请求注册一个路由。
<?php namespace App\Http\Controllers; class HomeController { /** * Show the Index Page * @Get("/") */ public function getIndex() { return view('index'); } }
您也可以设置路由名称。
/** * @Get("/", as="index") */ #[Get(path: '/', as: 'index')]
... 或者中间件。
/** * @Get("/", middleware="guest") */ #[Get(path: '/', middleware: 'guest')]
... 或者两者都设置。
/** * @Get("/", as="index", middleware="guest") */ #[Get(path: '/', as: 'index', middleware: 'guest')]
以下是一个使用所有可用的 @Get
注解参数的示例
/** * @Get("/profiles/{id}", as="profiles.show", middleware="guest", domain="foo.com", where={"id": "[0-9]+"}, no_prefix="true") */ #[Get(path: '/profiles/{id}', as: 'profiles.show', middleware: 'guest', domain: 'foo.com', where: ['id' => '[0-9]+'], noPrefix: true)]
no_prefix
允许忽略添加到该控制器中路由的任何前缀,对这条特定路由进行忽略。
@Post, @Options, @Put, @Patch, @Delete, @any
@Post
、@Options
、@Put
、@Patch
、@Delete
和 @Any
注释的语法与 @Get
注释相同,但它将注册一个针对相应 HTTP 动词的路由,而不是 GET 动词。
@Middleware
除了在路由定义标签中(如 @Get
、@Post
等)内联定义中间件外,您还可以使用 @Middleware
标签。它可以用于单个方法
/** * Show the Login Page * * @Get("login") * @Middleware("guest") */ public function login() { return view('index'); } #[Get(path: 'login')] #[Middleware(name: 'guest')] public function login() { return view('index'); }
或者整个控制器,使用与您在 Laravel 其他地方可以使用的相同的 only/exclude 过滤语法
/** * @Middleware("guest", except={"logout"}, prefix="/your/prefix") */ class AuthController extends Controller { /** * Log the user out. * * @Get("logout", as="logout") * @Middleware("auth") * * @return Response */ public function logout() { $this->auth->logout(); return redirect( route('login') ); } } #[Middleware(name: 'guest', except: ['logout'], prefix: '/your/prefix')] class AuthController extends Controller { #[Get(path: 'logout', as: 'logout')] #[Middleware(name: 'auth')] public function logout() { $this->auth->logout(); return redirect( route('login') ); } }
@Resource
在控制器上使用 @Resource
注释可以轻松设置资源控制器。
<?php /** * @Resource('users') */ class UsersController extends Controller { // index(), create(), store(), show($id), edit($id), update($id), destroy($id) }
您可以使用 only
和 except
参数,就像您可以使用常规 Route::resource()
命令一样。
/** * @Resource('users', only={"index", "show"}) */ #[Resource('users', only: ['index', 'show'])]
您还可以指定每个资源方法的路由名称。
/** * @Resource('users', names={"index"="user.all", "show"="user.view"}) */ #[Resource('users', names: ['index' => 'user.all', 'show' => 'user.view'])]
@Controller
在控制器上使用 @Controller
注解,可以设置其中包含的路由的各种选项
<?php /** * @Controller(prefix="admin", domain="foo.com") */ class AdminController extends Controller { // All routes will be prefixed by admin/ } #[Controller(prefix: 'admin', domain: 'foo.com')] class AdminController extends Controller { // All routes will be prefixed by admin/ }
扫描控制器目录
要递归扫描整个控制器命名空间(App\Http\Controllers
),可以将 $scanControllers
标志设置为 true。
它将自动将 App
调整为您的应用程序命名空间。
$scanControllers = true;
高级
如果您想使用任何逻辑将类添加到扫描列表中,可以重写 routeScans()
或 eventScans()
方法。
以下是一个示例,如果当前环境是 local
,则将控制器添加到扫描列表中
public function routeScans() { $classes = parent::routeScans(); if ( $this->app->environment('local') ) { $classes = array_merge($classes, [App\Http\Controllers\LocalOnlyController::class]); } return $classes; }
扫描命名空间
您可以使用 getClassesFromNamespace( $namespace )
方法递归地将命名空间添加到列表中。这将扫描给定的命名空间。它仅适用于 app
目录中的类,并且依赖于 PSR-4 命名空间标准。
这是 $scanControllers
标志与控制器目录一起使用的。
以下是一个示例,基于上一个示例 - 添加一个仅限本地的完整命名空间。
public function routeScans() { $classes = parent::routeScans(); if ( $this->app->environment('local') ) { $classes = array_merge( $classes, $this->getClassesFromNamespace( App\Http\Controllers\Local::class ) ); } return $classes; }
模型注释
您可以使用注解自动将模型绑定到路由参数,使用 路由模型绑定。为此,请使用 @Bind
注解。
/** * @Bind("users") */ class User extends Eloquent { // } #[Bind('users')] class User extends Eloquent { // }
这与调用 Route::model('users', 'App\Users')
相当。
自定义注释
请注意:版本 8.1 中已更新命名空间,以允许 PHP 8 属性支持。
如果您想注册自己的注解,创建一个包含 Collective\Annotations\Routing\Meta
的子类的命名空间 - 假设为 App\Http\Annotations
。
(对于版本 8.0 及更早版本,扩展 Collective\Annotations\Routing\Annotations\Annotations\Annotation
)
然后,在您的注解服务提供程序中,重写 addRoutingAnnotations( RouteScanner $scanner )
方法,并注册您的路由注解命名空间
<?php namespace App\Providers; use Collective\Annotations\Routing\Scanner as RouteScanner; # For version 8.0 and older use this instead of the above: # use Collective\Annotations\Routing\Annotations\Scanner as RouteScanner; /* ... then, in the class definition ... */ /** * Add annotation classes to the route scanner * * @param RouteScanner $namespace */ public function addRoutingAnnotations( RouteScanner $scanner ) { $scanner->addAnnotationNamespace( 'App\Http\Annotations' ); }
您的注解类必须具有 @Annotation
类注解(请参阅以下示例)。
对于事件注解也有一个等效方法:addEventAnnotations( EventScanner $scanner )
。
自定义注解示例
以下是一个示例,创建一个 @Auth
注解。它提供了与使用注解 @Middleware("auth")
相同的功能。
在一个命名空间中 - 在此示例中,App\Annotations
<?php namespace App\Http\Annotations; use Collective\Annotations\Routing\Meta; # For version 8.0 and older use this instead of the above: # use Collective\Annotations\Routing\Annotations\Annotations\Annotation; use Collective\Annotations\Routing\Annotations\MethodEndpoint; use ReflectionMethod; /** * @Annotation */ class Auth extends Annotation { /** * {@inheritdoc} */ public function modify(MethodEndpoint $endpoint, ReflectionMethod $method) { if ($endpoint->hasPaths()) { foreach ($endpoint->getPaths() as $path) { $path->middleware = array_merge($path->middleware, (array) 'auth'); } } else { $endpoint->middleware = array_merge($endpoint->middleware, (array) 'auth'); } } }