Maison  >  Article  >  développement back-end  >  [DTM] La version bêta du client coroutine PHP v0.1 est disponible !

[DTM] La version bêta du client coroutine PHP v0.1 est disponible !

藏色散人
藏色散人avant
2022-02-15 15:19:484403parcourir

Bonne nouvelle ! Sortie de la version bêta du client coroutine PHP v0.1 de DTM Distributed Transaction Manager ! ! !
→ github.com/dtm-php/dtm-client

Introduction

dtm/dtm-client est le client PHP du gestionnaire de transactions distribué DTM, qui prend déjà en charge le mode TCC, Saga et le message en deux phases Mode de transaction distribué et réalise la communication avec le serveur DTM via le protocole HTTP ou le protocole gRPC respectivement. Le client peut fonctionner en toute sécurité dans les environnements de coroutine PHP-FPM et Swoole, et fournit également une prise en charge fonctionnelle plus facile à utiliser pour Hyperf. [Recommandation : Tutoriel vidéo PHP]

À propos de DTM

DTM est un gestionnaire de transactions distribué open source basé sur le langage Go, offrant des fonctions puissantes de combinaison de transactions entre langages et moteurs de stockage. DTM résout avec élégance les problèmes de transactions distribuées tels que l'idempotence, la compensation nulle et la suspension, et fournit également une solution de transactions distribuées facile à utiliser, hautes performances et facile à développer horizontalement.

Points forts

  • Facile à démarrer
    • Service de démarrage sans configuration, fournissant une interface HTTP très simple, réduisant considérablement la difficulté de démarrer avec des transactions distribuées
  • Multilingue
    • Convient aux entreprises avec piles multilingues. Pratique pour utiliser Go, Python, PHP, NodeJs, Ruby, C# et d'autres langages.
  • Facile à utiliser
    • Les développeurs ne se soucient plus de divers problèmes tels que le blocage, la compensation nulle, l'exponentiation, etc. La première technologie de barrière de sous-transaction le gère pour vous
  • Facile à déployer et à développer
    • Uniquement s'appuie sur MySQL/Redis, déploiement simple, facile à regrouper, facile à développer horizontalement
  • Prise en charge de plusieurs protocoles de transactions distribuées
    • TCC, SAGA, XA, messagerie en deux phases, solution unique à divers problèmes de transactions distribuées

Comparaison

Dans les langages non Java, il n'existe pas de gestionnaire de transactions distribuées mature autre que DTM, voici donc une comparaison entre DTM et Seata, le projet open source le plus mature en Java :

Il est recommandé d'utiliser nombre d'étoilesDTM publié 0 à partir du 04/06/2021 version .1, en développement rapide

À en juger par les caractéristiques comparées ci-dessus, le DTM présente de grands avantages à bien des égards. Si vous envisagez la prise en charge multilingue et la prise en charge du moteur multi-stockage, alors DTM est sans aucun doute votre premier choix

Installation

Il est très pratique d'installer le client dtm via Composer

composer require dtm/dtm-client
  • N'oubliez pas de commencer. le serveur DTM lors de son utilisation Oh

Configuration

Fichier de configuration

Si vous l'utilisez dans le framework Hyperf, après avoir installé le composant, vous pouvez utiliser le vendor:publishsuivant > commande pour publier le fichier de configuration en un seul morceau ./config/autoload/dtm.phpvendor:publish 命令一件发布配置文件于 ./config/autoload/dtm.php

php bin/hyperf.php vendor:publish dtm/dtm-client

如果您是在非 Hyperf 框架中使用,可复制 ./vendor/dtm/dtm-client/publish/dtm.php 文件到对应的配置目录中。

use DtmClient\Constants\Protocol;
use DtmClient\Constants\DbType;

return [
    // 客户端与 DTM Server 通讯的协议,支持 Protocol::HTTP 和 Protocol::GRPC 两种
    'protocol' => Protocol::HTTP,
    // DTM Server 的地址
    'server' => '127.0.0.1',
    // DTM Server 的端口
    'port' => [
        'http' => 36789,
        'grpc' => 36790,
    ],
    // 子事务屏障配置
    'barrier' => [
        // DB 模式下的子事务屏障配置
        'db' => [
            'type' => DbType::MySQL
        ],
        // Redis 模式下的子事务屏障配置
        'redis' => [
            // 子事务屏障记录的超时时间
            'expire_seconds' => 7 * 86400,
        ],
        // 非 Hyperf 框架下应用子事务屏障的类
        'apply' => [],
    ],
    // HTTP 协议下 Guzzle 客户端的通用配置
    'guzzle' => [
        'options' => [],
    ],
];

配置中间件

在使用之前,需要配置 DtmClientMiddlewareDtmMiddleware

<?php
namespace App\Controller;

use DtmClient\TCC;
use DtmClient\TransContext;
use Hyperf\Di\Annotation\Inject;
use Hyperf\HttpServer\Annotation\Controller;
use Hyperf\HttpServer\Annotation\GetMapping;
use Throwable;

#[Controller(prefix: &#39;/tcc&#39;)]
class TccController
{

    protected string $serviceUri = &#39;http://127.0.0.1:9501&#39;;

    #[Inject]
    protected TCC $tcc;

    #[GetMapping(path: &#39;successCase&#39;)]
    public function successCase()
    {
        try {

            $this->tcc->globalTransaction(function (TCC $tcc) {
                // 创建子事务 A 的调用数据
                $tcc->callBranch(
                    // 调用 Try 方法的参数
                    [&#39;amount&#39; => 30],
                    // Try 方法的 URL
                    $this->serviceUri . &#39;/tcc/transA/try&#39;,
                    // Confirm 方法的 URL
                    $this->serviceUri . &#39;/tcc/transA/confirm&#39;,
                    // Cancel 方法的 URL
                    $this->serviceUri . &#39;/tcc/transA/cancel&#39;
                );
                // 创建子事务 B 的调用数据,以此类推
                $tcc->callBranch(
                    [&#39;amount&#39; => 30],
                    $this->serviceUri . &#39;/tcc/transB/try&#39;,
                    $this->serviceUri . &#39;/tcc/transB/confirm&#39;,
                    $this->serviceUri . &#39;/tcc/transB/cancel&#39;
                );
            });
        } catch (Throwable $e) {
            var_dump($e->getMessage(), $e->getTraceAsString());
        }
        // 通过 TransContext::getGid() 获得 全局事务ID 并返回
        return TransContext::getGid();
    }
}

Si vous l'utilisez dans un framework non-Hyperf, vous pouvez copier ./vendor /dtm/dtm-client/publish/dtm.php dans le répertoire de configuration correspondant.

namespace App\Controller;

use DtmClient\Saga;
use DtmClient\TransContext;
use Hyperf\Di\Annotation\Inject;
use Hyperf\HttpServer\Annotation\Controller;
use Hyperf\HttpServer\Annotation\GetMapping;

#[Controller(prefix: &#39;/saga&#39;)]
class SagaController
{

    protected string $serviceUri = &#39;http://127.0.0.1:9501&#39;;

    #[Inject]
    protected Saga $saga;

    #[GetMapping(path: &#39;successCase&#39;)]
    public function successCase(): string
    {
        $payload = [&#39;amount&#39; => 50];
        // 初始化 Saga 事务
        $this->saga->init();
        // 增加转出子事务
        $this->saga->add(
            $this->serviceUri . &#39;/saga/transOut&#39;, 
            $this->serviceUri . &#39;/saga/transOutCompensate&#39;, 
            $payload
        );
        // 增加转入子事务
        $this->saga->add(
            $this->serviceUri . &#39;/saga/transIn&#39;, 
            $this->serviceUri . &#39;/saga/transInCompensate&#39;, 
            $payload
        );
        // 提交 Saga 事务
        $this->saga->submit();
        // 通过 TransContext::getGid() 获得 全局事务ID 并返回
        return TransContext::getGid();
    }
}

Configurer le middlewareAvant utilisation, vous devez configurer le middleware DtmClientMiddlewareDtmMiddleware comme middleware global du serveur. Ce middleware prend en charge la spécification PSR-15 et peut être appliqué à divers frameworks qui la prennent en charge. spécification.

Pour la configuration du middleware dans Hyperf, veuillez vous référer au chapitre Documentation Hyperf - Middleware.


Utilisationdtm-client est très simple à utiliser. Nous fournissons un exemple de projet dtm-php/dtm-sample pour vous aider à mieux comprendre et déboguer.

Avant d'utiliser ce composant, il est également fortement recommandé de lire la documentation officielle du DTM pour une compréhension plus détaillée.

Mode TCC

Le mode TCC est une solution de transaction flexible très populaire. Le concept de TCC se compose des acronymes de Try-Confirm-Cancel. Il a été publié pour la première fois par Pat Helland en 2007. Proposé dans un article intitulé "Life". au-delà des transactions distribuées : l'opinion d'un apostat".



Trois phases du TCC

Phase d'essai : essayer d'exécuter, terminer tous les contrôles commerciaux (cohérence), réserver les ressources commerciales nécessaires (quasi-isolement)

Phase de confirmation : si l'essai de toutes les branches est réussi, alors allez à l’étape Confirmer. Confirm exécute en fait l'activité sans aucun contrôle commercial et utilise uniquement les ressources métier réservées lors de la phase d'essai d'annulation : si l'un des essais de toutes les branches échoue, il passe à la phase d'annulation. Annuler libère les ressources métier réservées lors de la phase Try. [DTM] La version bêta du client coroutine PHP v0.1 est disponible !

Si nous voulons mener une activité similaire à un virement interbancaire, le transfert (TransOut) et le transfert (TransIn) sont dans des microservices différents. Le diagramme de séquence typique d'une transaction TCC terminée avec succès est le suivant :

.

Exemples de code

Ce qui suit montre comment l'utiliser dans le framework Hyperf D'autres frameworks sont similaires

rrreee

Mode Saga

Le mode Saga est l'une des solutions les plus connues dans le domaine des transactions distribuées et est également très. populaire dans les grands systèmes, apparu pour la première fois dans l'article SAGAS de 1987 par Hector Garcaa-Molrna et Kenneth Salem. Saga est une transaction finalement cohérente et flexible. Elle est également appelée transaction de longue durée et est composée d'une série de transactions locales. Après que chaque transaction locale met à jour la base de données, celle-ci publiera un message ou un événement pour déclencher l'exécution de la prochaine transaction locale dans la transaction globale Saga. Si une transaction locale échoue parce que certaines règles métier ne peuvent pas être satisfaites, Saga effectuera des opérations de compensation pour toutes les transactions qui ont été validées avec succès avant l'échec de la transaction. Par conséquent, lorsque l’on compare le mode Saga au mode TCC, il devient souvent plus difficile de mettre en œuvre une logique de restauration en raison du manque d’étapes de réservation de ressources.

    Répartition des sous-transactions Saga
  • Par exemple, nous souhaitons effectuer une opération similaire à un virement interbancaire, en transférant 30 yuans du compte A au compte B. Selon le principe des transactions Saga, nous divisons la totalité transaction globale Pour les services suivants :
  • Service TransOut, où l'opération sera effectuée pour déduire 30 yuans du compte A
  • Service TransOutCompensate, annulez l'opération de transfert ci-dessus, c'est-à-dire que le compte A augmentera de 30 yuans
Service TransIn, ici le compte B sera augmenté de 30 yuans

Service de compensation de transfert (TransInCompensate), l'opération de transfert ci-dessus sera annulée, c'est-à-dire que le compte B sera réduit de 30 yuans

La logique de l'ensemble de la transaction est :

Exécuter le transfert avec succès => Exécuter le transfert avec succès => La transaction globale est terminée

Si une erreur survient au milieu, comme une erreur de transfert vers le compte B, l'opération de compensation de la branche exécutée sera appelée, c'est-à-dire :

🎜Exécuter le transfert sortant avec succès => Échec de l'exécution du transfert entrant => Transfert exécuté avec succès en compensation => Compensation du transfert sortant exécuté avec succès => Annulation globale de la transaction terminée 🎜🎜Ce qui suit est un chronogramme typique d'une SAGA terminée avec succès transaction : 🎜

[DTM] La version bêta du client coroutine PHP v0.1 est disponible !

代码示例

以下展示在 Hyperf 框架中的使用方法,其它框架类似

namespace App\Controller;

use DtmClient\Saga;
use DtmClient\TransContext;
use Hyperf\Di\Annotation\Inject;
use Hyperf\HttpServer\Annotation\Controller;
use Hyperf\HttpServer\Annotation\GetMapping;

#[Controller(prefix: &#39;/saga&#39;)]
class SagaController
{

    protected string $serviceUri = &#39;http://127.0.0.1:9501&#39;;

    #[Inject]
    protected Saga $saga;

    #[GetMapping(path: &#39;successCase&#39;)]
    public function successCase(): string
    {
        $payload = [&#39;amount&#39; => 50];
        // 初始化 Saga 事务
        $this->saga->init();
        // 增加转出子事务
        $this->saga->add(
            $this->serviceUri . &#39;/saga/transOut&#39;, 
            $this->serviceUri . &#39;/saga/transOutCompensate&#39;, 
            $payload
        );
        // 增加转入子事务
        $this->saga->add(
            $this->serviceUri . &#39;/saga/transIn&#39;, 
            $this->serviceUri . &#39;/saga/transInCompensate&#39;, 
            $payload
        );
        // 提交 Saga 事务
        $this->saga->submit();
        // 通过 TransContext::getGid() 获得 全局事务ID 并返回
        return TransContext::getGid();
    }
}
Caractéristiques DTM SEATA Remarques
Langages pris en charge Go, C#, Java, Python, PHP... Java DTM peut être Facilement connecté à une porte nouvelle langue
Storage moteur upport Base de données, redis, mongo, etc. "Traitement manuel" Deuxième- message de phase
Message minimal architecture de cohérence éventuelle Transactions TCC
Transactions XA
Transactions AT
Protocoles de communication HTTP, et d'autres protocolesDTM est plus convivial que le cloud natif

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Cet article est reproduit dans:. en cas de violation, veuillez contacter admin@php.cn Supprimer