繁体   English   中英

如何使用SLIM处理多租户?

[英]How to handle multi tenancy with SLIM?

我正在使用SLIM编写API ,该API的目标是创建多租户结构。 到目前为止,我所做的是:

首先,我创建了一个数据库,其中包含我的所有客户(购买了我的软件),对于每个客户,我都有一个名为CUSTOMER_TOKEN的字段,该字段表示访问API的凭据。

基本上,我在这里有两个软件:

  • API:从租户数据库中读取数据。
  • 主要应用:使用API​​。

实际上,每个租户都有一个不同的数据库,我发现这种方式对我来说是最佳选择。

主应用程序获得一个JWT令牌,该令牌通过使用CUSTOMER_TOKENAPI发送请求,例如:

http://xxx.xxx.xxx.xxx/v1/auth/login

上面的路线将检查数据库上是否存在客户,如果存在,则将返回一个临时访问令牌以使用API (JWT)。

到目前为止一切都很好。 主要问题来了。 实际上,如果用户拥有JWT并且CUSTOMER_TOKEN有效,则API应该创建与tenant数据库而非数据库的连接。

目前,为了处理主连接,我使用了SLIM容器,特别是:

<?php
   use Slim\Container;

   $container = $app->getContainer();

   $container['pdo'] = function (Container $c) {
       $db = $c['settings']['db'];
        $pdo = new PDO(
            "mysql:host=" . $db['host'] . ";dbname=" . $db['dbname'],
            $db['user'],
            $db['pass']
        );
        return $pdo;
    };

如何从此处创建与租户数据库的其他连接? 我应该使用middleware吗? 是否应该检查请求的路由器以了解是否需要主数据库或租户数据库?

请注意,对于每个租户,我使用一个名称约定结构,例如:

app_name-tenant-tenant_name

所以我的前缀是app_name-tenant ,然后是tenant_name 因此,我只需要从数据库获取customer的名称即可组装连接。

您将如何处理这种情况? 谢谢。

出于安全和实用的原因,我建议使用两个不同的PDO连接(实例)。 第一个连接用于API(JWT)Auth,第二个数据库连接用于客户(租户)。 您不需要中间件,因为基础结构配置中的数据库连接部分位于中间件下方。

您可以使用多个选项来与容器一起管理数据库连接。

  1. 只需为容器条目添加第二pdo2名,例如pdo2db2或类似的东西对您有意义。
// API
$container['pdo'] = function (Container $container) {
// Customer database
$container['pdo2'] = function (Container $container) {
  1. 我希望您使用构造函数依赖项注入 如果是,则最好使用类或接口名称定义容器条目。

例:

class ApiDatabase extends PDO {}

$container[ApiDatabase::class] = function (Container $container) {
class CustomerDatabase extends PDO {}

$container[CustomerDatabase::class] = function (Container $container) {

名称约定

现在,您已经为客户建立了第二个数据库连接,不再需要表前缀,因为在技术上客户之间已经有了更好的隔离。 为什么? 数据库事务也完全分开,这对其他客户数据(和表)没有影响。 数据库迁移将更加容易,因为您不必担心前缀。 现在,您可以为每个客户部署新版本,而不会影响其他客户的数据库。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM