laravel-commode / common
laravel-commode 的通用助手/实用工具/服务
Requires
- php: >=5.4.0
- illuminate/routing: 4.2.*
- illuminate/support: 4.2.*
Requires (Dev)
- mockery/mockery: dev-master
- satooshi/php-coveralls: dev-master
This package is not auto-updated.
Last update: 2024-09-14 15:52:55 UTC
README
#Commode: Common
laravel-commode/common 是所有 commode 包的通用 utils/services 包。其中一些只应在 laravel-commode 内部使用,而另一些可能对开发有用。
####内容
##安装
您可以使用 composer 安装 laravel-commode/common。
"require": {
"laravel-commode/common": "dev-master"
}
要启用包,您需要注册 LaravelCommode\Common\CommodeCommonServiceProvider
服务提供者。实际上,注册 CommodeCommonServiceProvider
有两种方式 - 第一种适用于所有服务提供者 - 您只需将其添加到 Laravel 应用程序配置的提供者列表中
<?php
// ./yourLaravelApplication/app/config/app.php
return [
// ... config code
'providers' => [
// ... providers
'LaravelCommode\Common\CommodeCommonServiceProvider'
]
];
或者,您可以开始使用 GhostService 服务提供者,只需实现一个,因为每个 GhostService 服务提供者都会检查 CommodeCommonServiceProvider
是否已注册,如果没有,则自动注册它。例如,它可以是您的中央应用程序服务提供者,它会加载依赖的服务提供者
<?php namespace MyApp\ServiceProviders;
use LaravelCommode\Common\GhostService;
class ApplicationServiceProvider extends GhostService
{
// your ghost service code
public function uses()
{
return [
'MyApp\ServiceProviders\DomainLogicServiceProvider', // your domain logic service provider,
'MyApp\ServiceProviders\DALServiceProvider', // your data access layer service provider,
// ... e.t.c.
];
}
}
然后,在您的配置中,您可以简单地添加 ApplicationServiceProvider
而无需提及 CommodeCommonServiceProvider
、DomainLogicServiceProvider
等等...
<?php
// ./yourLaravelApplication/app/config/app.php
return [
// ... config code
'providers' => [
// ... providers,
/**
/* will load all dependent services returned from uses()
/* method and CommodeCommonServiceProvider as well
**/
'MyApp\ServiceProviders\ApplicationServiceProvider'
]
];
GhostService 是一个继承自 Illuminate\Support\ServiceProvider
的类,具有一些有用的功能。要创建一个鬼服务,您只需扩展 LaravelCommode\Common\GhostService
类并实现两个基本受保护方法:registering()
和 launching()
。
<?php namespace MyApp\ServiceProviders;
use LaravelCommode\Common\GhostService;
class YourServiceProvider extends GhostService
{
/**
* Will be triggered when the app is booting
**/
protected function launching() { }
/**
* Triggered when service is being registered
**/
protected function registering() { }
}
GhostService 的一项最有用的功能是它加载依赖的服务提供者。当您的应用程序配置文件很大或者您正在开发自定义包,并且不希望滥用后续的开发者/用户实现依赖的服务提供者时,这可能很有用。
对于服务自动加载,您可以通过重写方法 public function uses()
来实现,该方法必须返回服务提供者名称的数组。如果已加载依赖的服务提供者,则将在加载链中忽略它。
<?php namespace MyApp\ServiceProviders;
use LaravelCommode\Common\GhostService;
class YourServiceProvider extends GhostService
{
public function uses()
{
return [
'MyApp\ServiceProviders\DALServiceProvider',
'Illuminate\Hashing\HashServiceProvider',
'Vendor\Package\UsefulServiceProvider'
];
}
/**
* Will be triggered when the app is booting
**/
protected function launching() { }
/**
* Triggered when service is being registered
**/
protected function registering() { }
}
对于那些在 'Laravel 中的 Facades' 主题上提出很多批评的 Laravel 用户,GhostService 提供者的解析方法 protected function with($resolvable, callable $do)
。该方法期望 $resolvable
参数为 string
或 array
的字符串,其中包含已注册在 IoC 容器中或在运行时可以解析的绑定,而 $do
参数为 callable
。
<?php namespace MyApp\ServiceProviders;
use LaravelCommode\Common\GhostService;
class YourServiceProvider extends GhostService
{
/**
* @var Illuminate\View\Factory|null
*/
protected $viewFactory = null;
public function uses()
{
return [
'MyApp\ServiceProviders\DALServiceProvider',
'Illuminate\Hashing\HashServiceProvider',
'Vendor\Package\UsefulServiceProvider'
];
}
/**
* Will be triggered when the app is booting
**/
protected function launching() { }
private function doSomethingWithHash(\Illuminate\Hashing\BcryptHasher $hash)
{
//do something with $hash
}
private function doSomethingWithUseful(\Vendor\UsefulPackage\IUsefulBoundInterface $useful)
{
//do something with $useful
}
/**
* Triggered when service is being registered
**/
protected function registering()
{
$usings = ['hash', \Vendor\UsefulPackage\IUsefulBoundInterface::class, 'view'];
$this->with($usings, function ($hash, $useful, $view)
{
$this->doSomethingWithHash($hash);
$this->doSomethingWithUseful($useful);
$this->viewFactory = $view;
});
}
}
如果您的服务提供者需要注册一个 facade 或 facade 列表,您可以通过重写 protected $aliases = [];
并将其分配给一个数组来实现,其中键是 facade 名称,值是绑定的 facade 类名。
protected $aliases = [
'MyFacade' => \MyVendor\MyPackage\Facades\MyFacade::class
];
Resolver
Resolver 是一个小巧但有用的类,用于构建灵活的或需要解析的东西。它可以通过 CommodeResolver
facade 使用,或者如果您不喜欢 facade,您可以在 IoC 容器中通过别名 "commode.common.resolver" 或以 new \LaravelCommode\Common\Resolver\Resolver($laravelApplication)
的形式初始化新实例找到它。
例如,假设您有一个安全模块的结构,例如 ISecurityUser,它绑定到您配置的 eloquent 身份验证模型。
<?php namespace App\System\Security\Abstractions;
interface ISecurityUser
{
public function hasPermission($permission);
public function hasPermissions(array $permissions);
}
<?php namespace App\DAL\Concrete\Eloquent\Models;
use Illuminate\Database\Eloquent\Model;
class Account extends Model implements ISecurityUser
{
/* your eloquent model code */
}
<?php namespace App\ServiceProviders;
use LaravelCommode\Common\GhostService\GhostService;
use MyApp\System\Security\Abstractions\ISecurityUser;
class ACLServiceProvider extends GhostService
{
public function launching() {}
public function registering()
{
$this->app->bind(ISecurityUser::class, function ($app)
{
return app('auth')->user(); // note that returned value might be null
});
}
}
Resolver
可以解析闭包和类方法,或将它们转换为可解析的闭包。下面是使用它的一个示例。
### Resolver 和闭包
<?php
use App\System\Security\Abstractions\ISecurityUser;
$closureThatNeedsToBeResolved = function ($knownParameter1, $knownParameterN, ISecurityUser $needsToBeResolved = null)
{
return func_get_args();
};
$resolver = new \LaravelCommode\Common\Resolver\Resolver(); // or app('commode.resolver');
$knownParameter1 = 'Known';
$knownParameter2 = 'Parameter';
/**
* Resolving closure and running it
**/
$result = $resolver->closure($closureThatNeedsToBeResolved, [$knownParameter1, $knownParameter2]);
$resultClosure = $resolver->makeClosure($closureThatNeedsToBeResolved);
var_dump(
$result, $resultClosure($knownParameter1, $knownParameter2),
$result === $resultClosure($knownParameter1, $knownParameter2)
);
// outputs
// array (size=3)
// 0 => string 'Known' (length=5)
// 1 => string 'Parameter' (length=9)
// 2 => object(MyApp\DAL\Concrete\Eloquent\Models\Account)
// array (size=3)
// 0 => string 'Known' (length=5)
// 1 => string 'Parameter' (length=9)
// 2 => object(MyApp\DAL\Concrete\Eloquent\Models\Account)
// boolean true
### Resolver 和类方法
<?php
use App\System\Security\Abstractions\ISecurityUser;
class SomeClass
{
public function methodThatNeedsToBeResolved($knownParameter1, $knownParameterN, ISecurityUser $needsToBeResolved = null)
{
return func_get_args();
}
}
$resolver = new \LaravelCommode\Common\Resolver\Resolver(); // or app('commode.resolver');
$someClass = new SomeClass();
$knownParameter1 = 'Known';
$knownParameter2 = 'Parameter';
$result = $resolver->method($someClass, 'methodThatNeedsToBeResolved', [$knownParameter1, $knownParameter2]);
// or ->method(SomeClass::class, ..., ...) for calling static method or resolving class through
// app IOC
$resultClosure = $resolver->methodToClosure($someClass, 'methodThatNeedsToBeResolved');
// or ->method(SomeClass::class, ..., ...) for calling static method or resolving class through
// app IOC
var_dump(
$result, $resultClosure($knownParameter1, $knownParameter2),
$result === $resultClosure($knownParameter1, $knownParameter2)
);
// outputs
// array (size=3)
// 0 => string 'Known' (length=5)
// 1 => string 'Parameter' (length=9)
// 2 => object(MyApp\DAL\Concrete\Eloquent\Models\Account)
// array (size=3)
// 0 => string 'Known' (length=5)
// 1 => string 'Parameter' (length=9)
// 2 => object(MyApp\DAL\Concrete\Eloquent\Models\Account)
// boolean true
Controller
laravel-commode/common 提供了一个简单的控制器,它并没有太多改变默认控制器,但它提供了在 Laravel 4.0-4.2 版本中常常在 StackOverflow 等资源上被提问的功能。
LaravelCommode\Common\Controllers\CommodeController
提供了可解析的方法调用,可以将 AJAX 调用分离到不同的方法中,或者完全禁止 AJAX 调用。
默认情况下,方法解析器是启用的,但你可以通过重写 protected $resolveMethods
并将其设置为 protected $resolveMethods = false;
来禁用它。当安装了 laravel-commode/viewmodel 包时,这个功能非常有用。示例
<?php namespace MyApp\Domain\Areas\Administrator\Controllers;
use LaravelCommode\Common\Controllers\CommodeController;
use LaravelCommode\ViewModel\Interfaces\IRequestBag;
class AccountController extends CommodeController
{
/* some controller code */
protected function returnBack()
{
return \Redirect::to(\URL::current())->withInput();
}
public function getSearch(IRequestBag $searchParams)
{
$collection = $this->accountService->search($searchParams->toArray());
return \View::make('Administrator::account.search', compact('collection'));
}
public function postEdit($id, AccountViewModel $viewModel)
{
if (!$viewModel->isValid())
{
return $this->returnBack()->withErrors($viewModel->getValidator());
}
if (!$this->accountStrategy->updateFromViewModel($viewMode))
{
return $this->returnBack()->with('error.strategy', $this->accountStrategy->getState());
}
return \Redirect::action(__CLASS__.'@getIndex');
}
}
默认情况下,AJAX 分离调用是禁用的,但你可以通过重写 protected $separateRequests
并将其设置为 protected $separateRequests = true;
来启用它。要定义一个 AJAX 方法,只需在方法名前添加 'ajax' 前缀。示例
<?php namespace MyApp\Domain\Areas\Site\Controllers;
use LaravelCommode\ViewModel\Interfaces\IRequestBag;
class PostsController extends CommodeController
{
protected $separateRequests = true;
/* some controller code */
/**
* Returns JSONable results when ajax is triggered
**/
public function ajaxgetLatest($lastId = null)
{
return $this->postService->getLatest($lastId);
}
/**
* Returns same collection as ::ajaxgetLatest() method,
* but wraps it with view
**/
public function getLatest()
{
return \View::make('Site::posts.list', [
'posts' => $this->ajaxgetLatest()
]);
}
}
你可以通过重写 protected $allowAjax
并将其设置为 protected $allowAjax = false;
来禁止 AJAX 调用——这将返回 404 HTTP 状态码。