对 Hyperf 做的那些事 1(定义规范)
- 作为一个PHPer一直思考PHP怎么做高性能(个人基础比较弱),怎么微服务,之前真不知道,不是概念而是怎么落地,谈概念有用但是不落地有点扯
- Swoole没有实际项目用过,swoole相关框架也没了解过也不知道,获取知道了可能对于之前的问题就可能有一些答案了
- Hyperf的出现简直就是太及时了,文档清晰,框架灵活等等等,简直不要太好
- 虽然Hyperf已经这么好了,但是还是希望把它稍微按着自己喜欢的规范改造一下,这里就把多有对它的改造都定义为自己的开发规范,如果大家觉得有道理可以沿用
- 感谢swoole团队(韩老师等……),感谢Hyperf团队(黄老师等……)
- 看完文章是否可以点个赞!!!!
工欲善其事,必先利其器,它有个名字
HyperfCMS
开整(1)
定义目录结构
├─app 应用目录 │ …… 框架其它目录 │ ├─Core 核心目录(都在这里面)框架的修改,业务的核心都放在这个目录下处理 │ │ ├─Facade 服务容器中可用的类提供了一个「静态」接口的类放在这个地方 │ │ ├─HF hyperf框架相关修改放于此 │ │ ├─LogHandler 日志处理 │ │ ├─Repositories 仓库目录,业务逻辑处理,区分业务模块 │ │ │ ├─Admin 后台业务 │ │ │ ├─Home 前台业务 │ │ │ ├─Api 接口业务 │ │ ├─Services 服务目录,业务逻辑处理,所有业务模块公用 │ │ ├─common.php 公共函数文件 │ │ ├─Response.php 统一响应处理出口
调用逻辑设计
- 控制器—–>仓库—–>服务—–>模型(Model),解释:http请求过来,通过路由找到控制器,控制器找到对应的仓库,仓库找到对应的服务,服务找到对应的模型,注意:为了规范,仓库不可直接操作模型。
- 虽然hyperf提供了多种方法注入,但是个人觉的还是比较麻烦,如果引用类过多需要写很多看着没有实际用途的代码。所以进行了修改,隐式注入。
- 隐式注入需要遵循约定的规范,如下:
- Controller需要继承BaseController,且如果用到哪个仓库需要在注释里
@property \APP\Core\Repositories\TestRepository $testRepo
目的是可以让phpstorm可以函数间跳转。- 控制器调用仓库的变量需要
Repo
或Repository
结尾,如:$testRepo
- 仓库的命名必须用Repository结尾,如:
TestRepository
,需要继承BaseRepository,如果用到服务需要@property \APP\Core\Services\TestService $testService
目的是可以让phpstorm可以函数间跳转- 仓内调用服务的变量需要
Service
结尾,如:$testService
- 服务的命名必须用Service结尾,如:
TestService
,需要继承BaseService,如果用到model需要@property \APP\Models\Category $categoryModel
, 目的是可以让phpstorm可以函数间跳转。- 服务调用model的变量需要
Model
结尾,如:$categoryModel
贴代码
class BaseController extends AbstractController { /** * __get * 隐式注入仓库类 * User:YM * Date:2019/11/21 * Time:上午9:27 * @param $key * @return \Psr\Container\ContainerInterface|void */ public function __get($key) { if ($key == 'app') { return $this->container; } else { $suffix = strstr($key,'Repo'); if ($suffix && ($suffix == 'Repo' || $suffix == 'Repository')) { $repoName = $suffix == 'Repo' ? $key.'sitory':$key; return $this->getRepositoriesInstance($repoName); } else { throw new \RuntimeException("仓库{$key}不存在,书写错误!", StatusCode::ERR_SERVER); } } /** * getRepositoriesInstance * 获取仓库类实例 * User:YM * Date:2019/11/21 * Time:上午10:30 * @param $key * @return mixed */ public function getRepositoriesInstance($key) { $key = ucfirst($key); $module = $this->getModuleName(); if (!empty($module)) { $module = "{$module}"; } else { $module = ""; } if ($module) { $filename = BASE_PATH."/app/Core/Repositories/{$module}/{$key}.php"; $classname = "App\\Core\\Repositories\\{$module}\\{$key}"; } else { $filename = BASE_PATH."/app/Core/Repositories/{$key}.php"; $classname = "App\\Core\\Repositories\\{$key}"; } if (file_exists($filename)) { return $this->container->get($classname); } else { throw new \RuntimeException("仓库{$key}不存在,文件不存在!", StatusCode::ERR_SERVER); } } /** * getModuleName * 获取所属模块 * User:YM * Date:2019/11/21 * Time:上午9:32 * @return string */ private function getModuleName() { $classname = get_called_class(); $name = substr($classname, 15); $space = explode('\\', $name); if(count($space) > 1){ return $space[0]; }else{ return ''; } } }
/** * IndexController * 类简介 * @package App\Controller * User:YM * Date:2019/11/12 * Time:下午5:03 * @property \APP\Core\Repositories\TestRepository $testRepo */ class IndexController extends BaseController { public function index() { $this->testRepo->test(); } }
namespace App\Core\Repositories; use Psr\Container\ContainerInterface; use Hyperf\Di\Annotation\Inject; use App\Constants\StatusCode; /** * BaseRepository * 仓库基类 * @package App\Core\Repositories * User:YM * Date:2019/11/21 * Time:下午2:36 */ class BaseRepository { /** * @Inject * @var ContainerInterface */ protected $container; /** * __get * 隐式注入服务类 * User:YM * Date:2019/11/21 * Time:上午9:27 * @param $key * @return \Psr\Container\ContainerInterface|void */ public function __get($key) { if ($key == 'app') { return $this->container; } elseif (substr($key, -7) == 'Service') { return $this->getServiceInstance($key); } else { throw new \RuntimeException("服务{$key}不存在,书写错误!", StatusCode::ERR_SERVER); } } /** * getServiceInstance * 获取服务类实例 * User:YM * Date:2019/11/21 * Time:上午10:30 * @param $key * @return mixed */ public function getServiceInstance($key) { $key = ucfirst($key); $fileName = BASE_PATH."/app/Core/Services/{$key}.php"; $className = "App\\Core\\Services\\{$key}"; if (file_exists($fileName)) { return $this->container->get($className); } else { throw new \RuntimeException("服务{$key}不存在,文件不存在!", StatusCode::ERR_SERVER); } } }
namespace App\Core\Repositories; /** * TestRepository * 类的介绍 * @package App\Core\Repositories * User:YM * Date:2019/11/21 * Time:上午10:25 * @property \APP\Core\Services\TestService $testService */ class TestRepository extends BaseRepository { public function test() { $tmp = $this->testService->test(); return $tmp; } }
namespace App\Core\Services; use Psr\Container\ContainerInterface; use Hyperf\Di\Annotation\Inject; use App\Constants\StatusCode; /** * BaseService * 服务基类 * @package App\Core\Services * User:YM * Date:2019/11/21 * Time:下午3:21 */ class BaseService { /** * @Inject * @var ContainerInterface */ protected $container; /** * __get * 隐式注入服务类 * User:YM * Date:2019/11/21 * Time:上午9:27 * @param $key * @return \Psr\Container\ContainerInterface|void */ public function __get($key) { if ($key == 'app') { return $this->container; } elseif (substr($key, -5) == 'Model') { $key = strstr($key,'Model',true); return $this->getModelInstance($key); } elseif (substr($key, -7) == 'Service') { return $this->getServiceInstance($key); } else { throw new \RuntimeException("服务/模型{$key}不存在,书写错误!", StatusCode::ERR_SERVER); } } /** * getModelInstance * 获取数据模型类实例 * User:YM * Date:2019/11/21 * Time:上午10:30 * @param $key * @return mixed */ public function getModelInstance($key) { $key = ucfirst($key); $fileName = BASE_PATH."/app/Models/{$key}.php"; $className = "App\\Models\\{$key}"; if (file_exists($fileName)) { return $this->container->get($className); } else { throw new \RuntimeException("服务/模型{$key}不存在,文件不存在!", StatusCode::ERR_SERVER); } } /** * getServiceInstance * 获取服务类实例 * User:YM * Date:2019/11/21 * Time:上午10:30 * @param $key * @return mixed */ public function getServiceInstance($key) { $key = ucfirst($key); $fileName = BASE_PATH."/app/Services/{$key}.php"; $className = "App\\Services\\{$key}"; if (file_exists($fileName)) { return $this->container->get($className); } else { throw new \RuntimeException("服务/模型{$key}不存在,文件不存在!", StatusCode::ERR_SERVER); } } }
namespace App\Core\Services;
/**
- TestServices
- 类的介绍
- @package App\Services
- User:YM
- Date:2019/11/21
- Time:下午2:46
- @property \APP\Models\Category $categoryModel
- /
class TestService extends BaseService
{
public function test()
{
}$tmp = $this->categoryModel->getList(); return $tmp;
}
本作品采用《CC 协议》,转载必须注明作者和本文链接
本帖由系统于 4年前 自动加精
推荐文章: