---
id: dmtplient
title: 创建Dmtp客户端
---

import Tag from "@site/src/components/Tag.js";

### 定义

命名空间：TouchSocket.Dmtp <br/>
程序集：[TouchSocket.Dmtp.dll](https://www.nuget.org/packages/TouchSocket.Dmtp)<br/>
程序集：[TouchSocketPro.Dmtp.dll](https://www.nuget.org/packages/TouchSocketPro.Dmtp) <Tag>Pro</Tag>

## 一、说明

Dmtp客户端对应的，也有不同协议的版本。各个版本之间功能基本一致。

## 二、可配置项

<details>
<summary>可配置项</summary>
<div>

#### SetDmtpOption
设置Dmtp相关配置。其中包含：

- VerifyToken：设置验证口令。 
- Id：连接时指定Id。
- Metadata：连接时指定元数据。可以在连接时，指定一些字符串键值对。

</div>
</details>

## 三、支持插件接口

声明自定义插件类，实现`IPlugin`接口，或者继承`PluginBase`，然后实现所需插件接口，即可实现事务的触发。

|  插件方法 | 功能 |
| --- | --- |
| IDmtpHandshakingPlugin | 客户端在验证连接。默认情况下，框架会首先验证连接Token是否正确，如果不正确则直接拒绝。不会有任何投递。用户也可以使用Metadata进行动态验证。 |
| IDmtpHandshakedPlugin | 客户端完成握手连接验证 |
| IDmtpReceivedPlugin | 在收到Dmtp格式的数据包时触发 |
| IDmtpRoutingPlugin | 当需要路由数据时触发，并且必须返回e.IsPermitOperation=true时，才允许路由 |
| IDmtpCreatedChannelPlugin | 在收到创建通道的请求时候触发。 |
| IDmtpClosingPlugin | 即将断开连接时触发（仅主动断开时、或收到了Close报文时有效）。 |
| IDmtpClosedPlugin | 在Dmtp连接断开时触发。 |


## 四、创建

### 4.1 TcpDmtpClient

`TcpDmtpClient`对应`TcpDmtpService`服务器。基本创建如下，支持[创建TcpClient](./tcpclient.mdx)的所有配置。

```csharp showLineNumbers
var client = new TcpDmtpClient();
await client.SetupAsync(new TouchSocketConfig()
    .SetRemoteIPHost("127.0.0.1:7789")
    .SetDmtpOption(new DmtpOption()
    {
        VerifyToken = "Dmtp"
    }));
await client.ConnectAsync();
```

### 4.2 UdpDmtp

`UdpDmtp`对应`UdpDmtp`服务器，即`UdpDmtp`即是服务器，又是客户端。基本创建如下，支持[创建UdpSession](./udpsession.mdx)的所有配置。

```csharp {1,4-6,11} showLineNumbers
var client = new UdpDmtp();

 await client.SetupAsync(new TouchSocketConfig()
     .SetRemoteIPHost("127.0.0.1:7797")
     .UseUdpReceive()
     .SetDmtpOption(new DmtpOption()
     {
         VerifyToken = "Dmtp"
     })
     .ConfigureContainer(a =>
     {
     })
     .ConfigurePlugins(a =>
     {
     }));
 client.Start();
```

:::info 备注

`UdpDmtp`作为客户端时，需要设定默认的`SetRemoteIPHost`，同时需要主动`UseUdpReceive`，以开启udp接收。如果需要固定监听端口，可使用`SetBindIPHost`。

:::  

### 4.3 HttpDmtpClient

`HttpDmtpClient`对应`HttpDmtpService`，或者`HttpMiddlewareDmtpService`服务器。基本创建如下，支持[创建HttpClient](./httpclient.mdx)的所有配置。

```csharp showLineNumbers
var client = new HttpDmtpClient();
await client.SetupAsync(new TouchSocketConfig()
   .SetRemoteIPHost("127.0.0.1:7789")
   .SetDmtpOption(new DmtpOption()
   {
       VerifyToken = "Dmtp"
   }));
await client.ConnectAsync();
```

### 4.4 WebSocketDmtpClient

```csharp showLineNumbers
var websocketDmtpClient = new WebSocketDmtpClient();
websocketDmtpClient.Setup(new TouchSocketConfig()
    .SetDmtpOption(new DmtpOption()
    {
        VerifyToken = "Dmtp"
    })
    .SetRemoteIPHost("ws://localhost:5174/WebSocketDmtp"));
await websocketDmtpClient.ConnectAsync();
```

[基于Aspnetcore的Dmtp示例Demo](https://gitee.com/RRQM_Home/TouchSocket/tree/master/examples/Dmtp/DmtpWebApplication)


### 4.5 DmtpClient工厂 <Tag>Pro</Tag>

DmtpClient工厂工作模式是一种，由单个主通讯连接和多个传输通讯连接组成的连接池。默认提供了两种类型的客户端工厂，分别为`TcpDmtpClientFactory`，`HttpDmtpClientFactory`。两者工作流程及配置基本相同，下面以`TcpDmtpClientFactory`为例。

【创建】
```csharp showLineNumbers
var clientFactory = new TcpDmtpClientFactory()
{
    MinCount = 5,//最小数量，在主连接器成功建立以后，会检测可用连接是否大于该值，否的话会自动建立。
    MaxCount = 10,//最大数量，当超过该数量的连接后，会等待指定时间，或者永久等待。
    OnGetTransferConfig = () => //配置辅助通信
    {
        return new TouchSocketConfig()
           .SetRemoteIPHost("tcp://127.0.0.1:7789");
    }
};

clientFactory.MainConfig
        .SetRemoteIPHost("tcp://127.0.0.1:7789");//配置主通信

//检测主通信器连接，然后如果没有连接，会自动建立连接
Result result = clientFactory.CheckStatus();
```

:::tip 提示

一般的，主通讯器最好启用心跳插件，而传输通讯器，可以根据自己业务决定。

:::  

:::info 备注

主通讯器的配置和传输通讯器的配置是分离的，所以可以分开配置。

:::  

【使用】

```csharp showLineNumbers
var clientFactory = CreateTcpClientFactory();
var client = clientFactory.GetTransferClient();
try
{
    //client.Invoke();//这里可以让得到的通讯器进行业务交流
}
finally
{
    //重中之重，必须要释放通讯器
    clientFactory.ReleaseTransferClient(client);
}
```

### 4.6 NamedPipeDmtpClient

`NamedPipeDmtpClient`对应`NamedPipeDmtpService`服务器。基本创建如下，支持[创建NamedPipeClient](./namedpipeclient.mdx)的所有配置。

```csharp showLineNumbers
var client = new NamedPipeDmtpClient();
await client.SetupAsync(new TouchSocketConfig()
      .SetPipeName("TouchSocketPipe")//设置管道名称
      .SetDmtpOption(new DmtpOption()
      {
           VerifyToken = "Dmtp"
      }));
await client.ConnectAsync();
```

[基于NamedPipe的Dmtp示例Demo](https://gitee.com/RRQM_Home/TouchSocket/tree/master/examples/Dmtp/NamedPipeDmtpConsoleApp)