C# Connector

    TDengine.Connector 连接器支持通过 TDengine 客户端驱动(taosc)建立与 TDengine 运行实例的连接,提供数据写入、查询、数据订阅、schemaless 数据写入、参数绑定接口数据写入等功能。 TDengine.Connector 自 v3.0.1 起还支持 WebSocket,通过 DSN 建立 WebSocket 连接,提供数据写入、查询、参数绑定接口数据写入等功能。

    本文介绍如何在 Linux 或 Windows 环境中安装 TDengine.Connector,并通过 TDengine.Connector 连接 TDengine 集群,进行数据写入、查询等基本操作。

    注意:TDengine.Connector 3.x 不兼容 TDengine 2.x,如果在运行 TDengine 2.x 版本的环境下需要使用 C# 连接器请使用 TDengine.Connector 的 1.x 版本 。

    TDengine.Connector 的源码托管在 GitHub

    支持的平台和 TDengine 客户端驱动支持的平台一致。

    版本支持

    请参考

    支持的功能特性

    • 原生连接
    • WebSocket 连接
    1. 连接管理
    2. 普通查询
    3. 连续查询
    4. 参数绑定
    5. 数据订阅(TMQ)
    6. Schemaless

    7. 连接管理

    8. 普通查询
    9. 连续查询
    10. 参数绑定
    • 安装
    • Nuget 客户端 (可选安装)
    • 安装 TDengine 客户端驱动,具体步骤请参考

    安装 TDengine.Connector

    • 使用本地连接
    • 使用 WebSocket 连接

    可以在当前 .NET 项目的路径下,通过 dotnet CLI 添加 Nuget package TDengine.Connector 到当前项目。

    也可以修改当前项目的 .csproj 文件,添加如下 ItemGroup。

    1. <ItemGroup>
    2. <PackageReference Include="TDengine.Connector" Version="3.0.*" />
    3. </ItemGroup>

    需要修改目标项目的 .csproj 项目文件,将 .nupkg 中的 runtimes 目录中的动态库复制到当前项目的 $(OutDir) 目录下。

    1. <ItemGroup>
    2. <PackageReference Include="TDengine.Connector" Version="3.0.*" GeneratePathProperty="true" />
    3. </ItemGroup>
    4. <Target Name="copyDLLDependency" BeforeTargets="BeforeBuild">
    5. <ItemGroup>
    6. <DepDLLFiles Include="$(PkgTDengine_Connector)\runtimes\**\*.*" />
    7. </ItemGroup>
    8. <Copy SourceFiles="@(DepDLLFiles)" DestinationFolder="$(OutDir)" />
    9. </Target>

    建立连接

    • 原生连接
    • WebSocket 连接

    使用 host、username、password、port 等信息建立连接。

    1. using TDengineDriver;
    2. namespace TDengineExample
    3. {
    4. internal class EstablishConnection
    5. {
    6. static void Main(String[] args)
    7. {
    8. string host = "localhost";
    9. short port = 6030;
    10. string username = "root";
    11. string password = "taosdata";
    12. string dbname = "";
    13. var conn = TDengine.Connect(host, username, password, dbname, port);
    14. if (conn == IntPtr.Zero)
    15. {
    16. Console.WriteLine("Connect to TDengine failed");
    17. }
    18. else
    19. {
    20. Console.WriteLine("Connect to TDengine success");
    21. }
    22. TDengine.Close(conn);
    23. TDengine.Cleanup();
    24. }
    25. }
    26. }

    使用 DSN 建立 WebSocket 连接 DSN 连接。 描述字符串基本结构如下:

    1. [<protocol>]://[[<username>:<password>@]<host>:<port>][/<database>][?<p1>=<v1>[&<p2>=<v2>]]
    2. |------------|---|-----------|-----------|------|------|------------|-----------------------|
    3. | protocol | | username | password | host | port | database | params |

    各部分意义见下表:

    • protocol: 显示指定以何种方式建立连接,例如:ws://localhost:6041 指定以 Websocket 方式建立连接(支持 http/ws )。

    • username/password: 用于创建连接的用户名及密码(默认 root/taosdata )。

    • host/port: 指定创建连接的服务器及端口,WebSocket 连接默认为 localhost:6041

    • database: 指定默认连接的数据库名,可选参数。

    • params:其他可选参数。

    查看源码

    使用示例

    SQL 写入

    • 原生连接
    • WebSocket 连接
    1. using TDengineDriver;
    2. namespace TDengineExample
    3. {
    4. internal class SQLInsertExample
    5. {
    6. static void Main()
    7. {
    8. IntPtr conn = GetConnection();
    9. try
    10. {
    11. IntPtr res = TDengine.Query(conn, "CREATE DATABASE power");
    12. CheckRes(conn, res, "failed to create database");
    13. res = TDengine.Query(conn, "USE power");
    14. CheckRes(conn, res, "failed to change database");
    15. res = TDengine.Query(conn, "CREATE STABLE power.meters (ts TIMESTAMP, current FLOAT, voltage INT, phase FLOAT) TAGS (location BINARY(64), groupId INT)");
    16. CheckRes(conn, res, "failed to create stable");
    17. var sql = "INSERT INTO d1001 USING meters TAGS('California.SanFrancisco', 2) VALUES ('2018-10-03 14:38:05.000', 10.30000, 219, 0.31000) ('2018-10-03 14:38:15.000', 12.60000, 218, 0.33000) ('2018-10-03 14:38:16.800', 12.30000, 221, 0.31000) " +
    18. "d1002 USING power.meters TAGS('California.SanFrancisco', 3) VALUES('2018-10-03 14:38:16.650', 10.30000, 218, 0.25000) " +
    19. "d1003 USING power.meters TAGS('California.LosAngeles', 2) VALUES('2018-10-03 14:38:05.500', 11.80000, 221, 0.28000)('2018-10-03 14:38:16.600', 13.40000, 223, 0.29000) " +
    20. "d1004 USING power.meters TAGS('California.LosAngeles', 3) VALUES('2018-10-03 14:38:05.000', 10.80000, 223, 0.29000)('2018-10-03 14:38:06.500', 11.50000, 221, 0.35000)";
    21. res = TDengine.Query(conn, sql);
    22. CheckRes(conn, res, "failed to insert data");
    23. int affectedRows = TDengine.AffectRows(res);
    24. Console.WriteLine("affectedRows " + affectedRows);
    25. TDengine.FreeResult(res);
    26. }
    27. finally
    28. {
    29. TDengine.Close(conn);
    30. }
    31. }
    32. static IntPtr GetConnection()
    33. {
    34. string host = "localhost";
    35. short port = 6030;
    36. string username = "root";
    37. string password = "taosdata";
    38. string dbname = "";
    39. var conn = TDengine.Connect(host, username, password, dbname, port);
    40. if (conn == IntPtr.Zero)
    41. {
    42. throw new Exception("Connect to TDengine failed");
    43. }
    44. else
    45. {
    46. Console.WriteLine("Connect to TDengine success");
    47. }
    48. return conn;
    49. }
    50. static void CheckRes(IntPtr conn, IntPtr res, String errorMsg)
    51. {
    52. if (TDengine.ErrorNo(res) != 0)
    53. {
    54. throw new Exception($"{errorMsg} since: {TDengine.Error(res)}");
    55. }
    56. }
    57. }
    58. }
    59. // output:
    60. // Connect to TDengine success
    61. // affectedRows 8

    查看源码

    1. using System;
    2. using TDengineWS.Impl;
    3. namespace Examples
    4. {
    5. public class WSInsertExample
    6. {
    7. static int Main(string[] args)
    8. {
    9. string DSN = "ws://root:taosdata@127.0.0.1:6041/test";
    10. IntPtr wsConn = LibTaosWS.WSConnectWithDSN(DSN);
    11. // Assert if connection is validate
    12. if (wsConn == IntPtr.Zero)
    13. {
    14. Console.WriteLine("get WS connection failed");
    15. return -1;
    16. }
    17. else
    18. {
    19. Console.WriteLine("Establish connect success.");
    20. }
    21. string createTable = "CREATE STABLE test.meters (ts timestamp, current float, voltage int, phase float) TAGS (location binary(64), groupId int);";
    22. string insert = "INSERT INTO test.d1001 USING test.meters TAGS('California.SanFrancisco', 2) VALUES ('2018-10-03 14:38:05.000', 10.30000, 219, 0.31000) ('2018-10-03 14:38:15.000', 12.60000, 218, 0.33000) ('2018-10-03 14:38:16.800', 12.30000, 221, 0.31000)" +
    23. "test.d1002 USING test.meters TAGS('California.SanFrancisco', 3) VALUES('2018-10-03 14:38:16.650', 10.30000, 218, 0.25000)" +
    24. "test.d1003 USING test.meters TAGS('California.LosAngeles', 2) VALUES('2018-10-03 14:38:05.500', 11.80000, 221, 0.28000)('2018-10-03 14:38:16.600', 13.40000, 223, 0.29000) " +
    25. "test.d1004 USING test.meters TAGS('California.LosAngeles', 3) VALUES('2018-10-03 14:38:05.000', 10.80000, 223, 0.29000)('2018-10-03 14:38:06.500', 11.50000, 221, 0.35000)";
    26. IntPtr wsRes = LibTaosWS.WSQuery(wsConn, createTable);
    27. ValidInsert("create table", wsRes);
    28. LibTaosWS.WSFreeResult(wsRes);
    29. wsRes = LibTaosWS.WSQuery(wsConn, insert);
    30. ValidInsert("insert data", wsRes);
    31. LibTaosWS.WSFreeResult(wsRes);
    32. // close connection.
    33. LibTaosWS.WSClose(wsConn);
    34. return 0;
    35. }
    36. static void ValidInsert(string desc, IntPtr wsRes)
    37. {
    38. int code = LibTaosWS.WSErrorNo(wsRes);
    39. if (code != 0)
    40. {
    41. Console.WriteLine($"execute SQL failed: reason: {LibTaosWS.WSErrorStr(wsRes)}, code:{code}");
    42. }
    43. else
    44. {
    45. Console.WriteLine("{0} success affect {2} rows, cost {1} nanoseconds", desc, LibTaosWS.WSTakeTiming(wsRes), LibTaosWS.WSAffectRows(wsRes));
    46. }
    47. }
    48. }
    49. }
    50. // Establish connect success.
    51. // create table success affect 0 rows, cost 3717542 nanoseconds
    52. // insert data success affect 8 rows, cost 2613637 nanoseconds

    InfluxDB 行协议写入

    1. using TDengineDriver;
    2. namespace TDengineExample
    3. {
    4. internal class InfluxDBLineExample
    5. {
    6. static void Main()
    7. {
    8. IntPtr conn = GetConnection();
    9. PrepareDatabase(conn);
    10. string[] lines = {
    11. "meters,location=California.LosAngeles,groupid=2 current=11.8,voltage=221,phase=0.28 1648432611249",
    12. "meters,location=California.LosAngeles,groupid=2 current=13.4,voltage=223,phase=0.29 1648432611250",
    13. "meters,location=California.LosAngeles,groupid=3 current=10.8,voltage=223,phase=0.29 1648432611249",
    14. "meters,location=California.LosAngeles,groupid=3 current=11.3,voltage=221,phase=0.35 1648432611250"
    15. };
    16. IntPtr res = TDengine.SchemalessInsert(conn, lines, lines.Length, (int)TDengineSchemalessProtocol.TSDB_SML_LINE_PROTOCOL, (int)TDengineSchemalessPrecision.TSDB_SML_TIMESTAMP_MILLI_SECONDS);
    17. if (TDengine.ErrorNo(res) != 0)
    18. {
    19. throw new Exception("SchemalessInsert failed since " + TDengine.Error(res));
    20. }
    21. {
    22. int affectedRows = TDengine.AffectRows(res);
    23. Console.WriteLine($"SchemalessInsert success, affected {affectedRows} rows");
    24. }
    25. TDengine.FreeResult(res);
    26. }
    27. static IntPtr GetConnection()
    28. {
    29. string host = "localhost";
    30. short port = 6030;
    31. string username = "root";
    32. string password = "taosdata";
    33. string dbname = "";
    34. var conn = TDengine.Connect(host, username, password, dbname, port);
    35. if (conn == IntPtr.Zero)
    36. {
    37. throw new Exception("Connect to TDengine failed");
    38. }
    39. else
    40. Console.WriteLine("Connect to TDengine success");
    41. }
    42. return conn;
    43. }
    44. static void PrepareDatabase(IntPtr conn)
    45. {
    46. IntPtr res = TDengine.Query(conn, "CREATE DATABASE test");
    47. if (TDengine.ErrorNo(res) != 0)
    48. {
    49. throw new Exception("failed to create database, reason: " + TDengine.Error(res));
    50. }
    51. res = TDengine.Query(conn, "USE test");
    52. if (TDengine.ErrorNo(res) != 0)
    53. {
    54. throw new Exception("failed to change database, reason: " + TDengine.Error(res));
    55. }
    56. }
    57. }
    58. }

    OpenTSDB Telnet 行协议写入

    1. using TDengineDriver;
    2. namespace TDengineExample
    3. {
    4. internal class OptsTelnetExample
    5. {
    6. static void Main()
    7. {
    8. IntPtr conn = GetConnection();
    9. try
    10. {
    11. PrepareDatabase(conn);
    12. string[] lines = {
    13. "meters.current 1648432611249 10.3 location=California.SanFrancisco groupid=2",
    14. "meters.current 1648432611250 12.6 location=California.SanFrancisco groupid=2",
    15. "meters.current 1648432611249 10.8 location=California.LosAngeles groupid=3",
    16. "meters.current 1648432611250 11.3 location=California.LosAngeles groupid=3",
    17. "meters.voltage 1648432611249 219 location=California.SanFrancisco groupid=2",
    18. "meters.voltage 1648432611250 218 location=California.SanFrancisco groupid=2",
    19. "meters.voltage 1648432611249 221 location=California.LosAngeles groupid=3",
    20. "meters.voltage 1648432611250 217 location=California.LosAngeles groupid=3",
    21. };
    22. IntPtr res = TDengine.SchemalessInsert(conn, lines, lines.Length, (int)TDengineSchemalessProtocol.TSDB_SML_TELNET_PROTOCOL, (int)TDengineSchemalessPrecision.TSDB_SML_TIMESTAMP_NOT_CONFIGURED);
    23. if (TDengine.ErrorNo(res) != 0)
    24. {
    25. throw new Exception("SchemalessInsert failed since " + TDengine.Error(res));
    26. }
    27. else
    28. {
    29. int affectedRows = TDengine.AffectRows(res);
    30. Console.WriteLine($"SchemalessInsert success, affected {affectedRows} rows");
    31. }
    32. TDengine.FreeResult(res);
    33. }
    34. catch
    35. {
    36. TDengine.Close(conn);
    37. }
    38. }
    39. static IntPtr GetConnection()
    40. {
    41. string host = "localhost";
    42. short port = 6030;
    43. string username = "root";
    44. string password = "taosdata";
    45. string dbname = "";
    46. var conn = TDengine.Connect(host, username, password, dbname, port);
    47. if (conn == IntPtr.Zero)
    48. {
    49. throw new Exception("Connect to TDengine failed");
    50. }
    51. else
    52. {
    53. Console.WriteLine("Connect to TDengine success");
    54. }
    55. return conn;
    56. }
    57. static void PrepareDatabase(IntPtr conn)
    58. {
    59. IntPtr res = TDengine.Query(conn, "CREATE DATABASE test");
    60. if (TDengine.ErrorNo(res) != 0)
    61. {
    62. throw new Exception("failed to create database, reason: " + TDengine.Error(res));
    63. }
    64. res = TDengine.Query(conn, "USE test");
    65. if (TDengine.ErrorNo(res) != 0)
    66. {
    67. throw new Exception("failed to change database, reason: " + TDengine.Error(res));
    68. }
    69. }
    70. }
    71. }

    查看源码

    OpenTSDB JSON 行协议写入

    查看源码

    参数绑定

    • 原生连接
    • WebSocket 连接
    1. using TDengineDriver;
    2. namespace TDengineExample
    3. {
    4. internal class StmtInsertExample
    5. {
    6. private static IntPtr conn;
    7. private static IntPtr stmt;
    8. static void Main()
    9. {
    10. conn = GetConnection();
    11. try
    12. {
    13. PrepareSTable();
    14. // 1. init and prepare
    15. stmt = TDengine.StmtInit(conn);
    16. if (stmt == IntPtr.Zero)
    17. {
    18. throw new Exception("failed to init stmt.");
    19. }
    20. int res = TDengine.StmtPrepare(stmt, "INSERT INTO ? USING meters TAGS(?, ?) VALUES(?, ?, ?, ?)");
    21. CheckStmtRes(res, "failed to prepare stmt");
    22. // 2. bind table name and tags
    23. TAOS_MULTI_BIND[] tags = new TAOS_MULTI_BIND[2] { TaosMultiBind.MultiBindBinary(new string[] { "California.SanFrancisco" }), TaosMultiBind.MultiBindInt(new int?[] { 2 }) };
    24. res = TDengine.StmtSetTbnameTags(stmt, "d1001", tags);
    25. CheckStmtRes(res, "failed to bind table name and tags");
    26. // 3. bind values
    27. TAOS_MULTI_BIND[] values = new TAOS_MULTI_BIND[4] {
    28. TaosMultiBind.MultiBindTimestamp(new long[2] { 1648432611249, 1648432611749}),
    29. TaosMultiBind.MultiBindFloat(new float?[2] { 10.3f, 12.6f}),
    30. TaosMultiBind.MultiBindInt(new int?[2] { 219, 218}),
    31. TaosMultiBind.MultiBindFloat(new float?[2]{ 0.31f, 0.33f})
    32. };
    33. res = TDengine.StmtBindParamBatch(stmt, values);
    34. CheckStmtRes(res, "failed to bind params");
    35. // 4. add batch
    36. res = TDengine.StmtAddBatch(stmt);
    37. CheckStmtRes(res, "failed to add batch");
    38. // 5. execute
    39. res = TDengine.StmtExecute(stmt);
    40. CheckStmtRes(res, "failed to execute");
    41. // 6. free
    42. TaosMultiBind.FreeTaosBind(tags);
    43. TaosMultiBind.FreeTaosBind(values);
    44. }
    45. finally
    46. {
    47. TDengine.Close(conn);
    48. }
    49. }
    50. static IntPtr GetConnection()
    51. {
    52. string host = "localhost";
    53. short port = 6030;
    54. string username = "root";
    55. string password = "taosdata";
    56. string dbname = "";
    57. var conn = TDengine.Connect(host, username, password, dbname, port);
    58. if (conn == IntPtr.Zero)
    59. {
    60. throw new Exception("Connect to TDengine failed");
    61. }
    62. else
    63. {
    64. Console.WriteLine("Connect to TDengine success");
    65. }
    66. return conn;
    67. }
    68. static void PrepareSTable()
    69. {
    70. IntPtr res = TDengine.Query(conn, "CREATE DATABASE power");
    71. CheckResPtr(res, "failed to create database");
    72. res = TDengine.Query(conn, "USE power");
    73. CheckResPtr(res, "failed to change database");
    74. res = TDengine.Query(conn, "CREATE STABLE power.meters (ts TIMESTAMP, current FLOAT, voltage INT, phase FLOAT) TAGS (location BINARY(64), groupId INT)");
    75. CheckResPtr(res, "failed to create stable");
    76. }
    77. static void CheckStmtRes(int res, string errorMsg)
    78. {
    79. if (res != 0)
    80. {
    81. Console.WriteLine(errorMsg + ", " + TDengine.StmtErrorStr(stmt));
    82. int code = TDengine.StmtClose(stmt);
    83. if (code != 0)
    84. {
    85. throw new Exception($"failed to close stmt, {code} reason: {TDengine.StmtErrorStr(stmt)} ");
    86. }
    87. }
    88. }
    89. static void CheckResPtr(IntPtr res, string errorMsg)
    90. {
    91. if (TDengine.ErrorNo(res) != 0)
    92. {
    93. throw new Exception(errorMsg + " since:" + TDengine.Error(res));
    94. }
    95. }
    96. }
    97. }

    查看源码

    1. using System;
    2. using TDengineWS.Impl;
    3. using TDengineDriver;
    4. using System.Runtime.InteropServices;
    5. namespace Examples
    6. {
    7. public class WSStmtExample
    8. {
    9. static int Main(string[] args)
    10. {
    11. const string DSN = "ws://root:taosdata@127.0.0.1:6041/test";
    12. const string table = "meters";
    13. const string database = "test";
    14. const string childTable = "d1005";
    15. string insert = $"insert into ? using {database}.{table} tags(?,?) values(?,?,?,?)";
    16. const int numOfTags = 2;
    17. // Establish connection
    18. IntPtr wsConn = LibTaosWS.WSConnectWithDSN(DSN);
    19. if (wsConn == IntPtr.Zero)
    20. {
    21. Console.WriteLine($"get WS connection failed");
    22. return -1;
    23. }
    24. else
    25. {
    26. }
    27. // init stmt
    28. IntPtr wsStmt = LibTaosWS.WSStmtInit(wsConn);
    29. if (wsStmt != IntPtr.Zero)
    30. {
    31. int code = LibTaosWS.WSStmtPrepare(wsStmt, insert);
    32. ValidStmtStep(code, wsStmt, "WSStmtPrepare");
    33. TAOS_MULTI_BIND[] wsTags = new TAOS_MULTI_BIND[] { WSMultiBind.WSBindNchar(new string[] { "California.SanDiego" }), WSMultiBind.WSBindInt(new int?[] { 4 }) };
    34. code = LibTaosWS.WSStmtSetTbnameTags(wsStmt, $"{database}.{childTable}", wsTags, numOfTags);
    35. ValidStmtStep(code, wsStmt, "WSStmtSetTbnameTags");
    36. TAOS_MULTI_BIND[] data = new TAOS_MULTI_BIND[4];
    37. data[0] = WSMultiBind.WSBindTimestamp(new long[] { 1538548687000, 1538548688000, 1538548689000, 1538548690000, 1538548691000 });
    38. data[1] = WSMultiBind.WSBindFloat(new float?[] { 10.30F, 10.40F, 10.50F, 10.60F, 10.70F });
    39. data[2] = WSMultiBind.WSBindInt(new int?[] { 223, 221, 222, 220, 219 });
    40. data[3] = WSMultiBind.WSBindFloat(new float?[] { 0.31F, 0.32F, 0.33F, 0.35F, 0.28F });
    41. code = LibTaosWS.WSStmtBindParamBatch(wsStmt, data, numOfColumns);
    42. ValidStmtStep(code, wsStmt, "WSStmtBindParamBatch");
    43. code = LibTaosWS.WSStmtAddBatch(wsStmt);
    44. ValidStmtStep(code, wsStmt, "WSStmtAddBatch");
    45. IntPtr stmtAffectRowPtr = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(Int32)));
    46. code = LibTaosWS.WSStmtExecute(wsStmt, stmtAffectRowPtr);
    47. ValidStmtStep(code, wsStmt, "WSStmtExecute");
    48. Console.WriteLine("WS STMT insert {0} rows...", Marshal.ReadInt32(stmtAffectRowPtr));
    49. Marshal.FreeHGlobal(stmtAffectRowPtr);
    50. LibTaosWS.WSStmtClose(wsStmt);
    51. // Free unmanaged memory
    52. WSMultiBind.WSFreeTaosBind(wsTags);
    53. WSMultiBind.WSFreeTaosBind(data);
    54. //check result with SQL "SELECT * FROM test.d1005;"
    55. }
    56. else
    57. {
    58. Console.WriteLine("Init STMT failed...");
    59. }
    60. // close connection.
    61. LibTaosWS.WSClose(wsConn);
    62. return 0;
    63. }
    64. static void ValidStmtStep(int code, IntPtr wsStmt, string desc)
    65. {
    66. if (code != 0)
    67. {
    68. Console.WriteLine($"{desc} failed,reason: {LibTaosWS.WSErrorStr(wsStmt)}, code: {code}");
    69. }
    70. else
    71. {
    72. Console.WriteLine("{0} success...", desc);
    73. }
    74. }
    75. }
    76. }
    77. // WSStmtPrepare success...
    78. // WSStmtSetTbnameTags success...
    79. // WSStmtBindParamBatch success...
    80. // WSStmtAddBatch success...
    81. // WSStmtExecute success...
    82. // WS STMT insert 5 rows...

    查询数据

    同步查询

    • 原生连接
    • WebSocket 连接
    1. using TDengineDriver;
    2. using TDengineDriver.Impl;
    3. using System.Runtime.InteropServices;
    4. namespace TDengineExample
    5. {
    6. internal class QueryExample
    7. {
    8. static void Main()
    9. {
    10. IntPtr conn = GetConnection();
    11. try
    12. {
    13. // run query
    14. IntPtr res = TDengine.Query(conn, "SELECT * FROM meters LIMIT 2");
    15. if (TDengine.ErrorNo(res) != 0)
    16. {
    17. throw new Exception("Failed to query since: " + TDengine.Error(res));
    18. }
    19. // get filed count
    20. int fieldCount = TDengine.FieldCount(res);
    21. Console.WriteLine("fieldCount=" + fieldCount);
    22. // print column names
    23. List<TDengineMeta> metas = LibTaos.GetMeta(res);
    24. for (int i = 0; i < metas.Count; i++)
    25. {
    26. Console.Write(metas[i].name + "\t");
    27. }
    28. Console.WriteLine();
    29. // print values
    30. List<Object> resData = LibTaos.GetData(res);
    31. for (int i = 0; i < resData.Count; i++)
    32. {
    33. Console.Write($"|{resData[i].ToString()} \t");
    34. if (((i + 1) % metas.Count == 0))
    35. {
    36. Console.WriteLine("");
    37. }
    38. }
    39. Console.WriteLine();
    40. // Free result after use
    41. TDengine.FreeResult(res);
    42. }
    43. finally
    44. {
    45. TDengine.Close(conn);
    46. }
    47. }
    48. static IntPtr GetConnection()
    49. {
    50. string host = "localhost";
    51. short port = 6030;
    52. string username = "root";
    53. string password = "taosdata";
    54. string dbname = "power";
    55. var conn = TDengine.Connect(host, username, password, dbname, port);
    56. if (conn == IntPtr.Zero)
    57. {
    58. throw new Exception("Connect to TDengine failed");
    59. }
    60. else
    61. {
    62. Console.WriteLine("Connect to TDengine success");
    63. }
    64. return conn;
    65. }
    66. }
    67. }
    68. // output:
    69. // Connect to TDengine success
    70. // fieldCount=6
    71. // ts current voltage phase location groupid
    72. // 1648432611249 10.3 219 0.31 California.SanFrancisco 2
    73. // 1648432611749 12.6 218 0.33 California.SanFrancisco 2

    查看源码

    1. using System;
    2. using TDengineWS.Impl;
    3. using System.Collections.Generic;
    4. using TDengineDriver;
    5. namespace Examples
    6. {
    7. public class WSQueryExample
    8. {
    9. static int Main(string[] args)
    10. {
    11. string DSN = "ws://root:taosdata@127.0.0.1:6041/test";
    12. IntPtr wsConn = LibTaosWS.WSConnectWithDSN(DSN);
    13. if (wsConn == IntPtr.Zero)
    14. {
    15. Console.WriteLine("get WS connection failed");
    16. return -1;
    17. }
    18. else
    19. {
    20. Console.WriteLine("Establish connect success.");
    21. }
    22. string select = "select * from test.meters";
    23. // optional:wsRes = LibTaosWS.WSQuery(wsConn, select);
    24. IntPtr wsRes = LibTaosWS.WSQueryTimeout(wsConn, select, 1);
    25. // Assert if query execute success.
    26. int code = LibTaosWS.WSErrorNo(wsRes);
    27. if (code != 0)
    28. {
    29. Console.WriteLine($"execute SQL failed: reason: {LibTaosWS.WSErrorStr(wsRes)}, code:{code}");
    30. LibTaosWS.WSFreeResult(wsRes);
    31. return -1;
    32. }
    33. // get meta data
    34. List<TDengineMeta> metas = LibTaosWS.WSGetFields(wsRes);
    35. // get retrieved data
    36. List<object> dataSet = LibTaosWS.WSGetData(wsRes);
    37. // do something with result.
    38. foreach (var meta in metas)
    39. {
    40. Console.Write("{0} {1}({2}) \t|\t", meta.name, meta.TypeName(), meta.size);
    41. }
    42. Console.WriteLine("");
    43. for (int i = 0; i < dataSet.Count;)
    44. {
    45. for (int j = 0; j < metas.Count; j++)
    46. {
    47. Console.Write("{0}\t|\t", dataSet[i]);
    48. i++;
    49. }
    50. Console.WriteLine("");
    51. }
    52. // Free result after use.
    53. LibTaosWS.WSFreeResult(wsRes);
    54. // close connection.
    55. LibTaosWS.WSClose(wsConn);
    56. return 0;
    57. }
    58. }
    59. }
    60. // Establish connect success.
    61. // ts TIMESTAMP(8) | current FLOAT(4) | voltage INT(4) | phase FLOAT(4) | location BINARY(64) | groupid INT(4) |
    62. // 1538548685000 | 10.8 | 223 | 0.29 | California.LosAngeles | 3 |
    63. // 1538548686500 | 11.5 | 221 | 0.35 | California.LosAngeles | 3 |
    64. // 1538548685500 | 11.8 | 221 | 0.28 | California.LosAngeles | 2 |
    65. // 1538548696600 | 13.4 | 223 | 0.29 | California.LosAngeles | 2 |
    66. // 1538548685000 | 10.3 | 219 | 0.31 | California.SanFrancisco | 2 |
    67. // 1538548695000 | 12.6 | 218 | 0.33 | California.SanFrancisco | 2 |
    68. // 1538548696800 | 12.3 | 221 | 0.31 | California.SanFrancisco | 2 |
    69. // 1538548696650 | 10.3 | 218 | 0.25 | California.SanFrancisco | 3 |

    异步查询

    TDengine.Connector说明
    3.0.2支持 .NET Framework 4.5 及以上,支持 .NET standard 2.0。Nuget Package 包含 WebSocket 动态库。
    3.0.1支持 WebSocket 和 Cloud,查询,插入,参数绑定。
    3.0.0支持 TDengine 3.0.0.0,不兼容 2.x。新增接口TDengine.Impl.GetData(),解析查询结果。
    1.0.7修复 TDengine.Query()内存泄露。
    1.0.6修复 schemaless 在 1.0.4 和 1.0.5 中失效 bug。
    1.0.5修复 Windows 同步查询中文报错 bug。
    1.0.4新增异步查询,订阅等功能。修复绑定参数 bug。
    1.0.3新增参数绑定、schemaless、 json tag等功能。
    1.0.2新增连接管理、同步查询、错误信息等功能。

    其他说明

    第三方驱动

    IoTSharp.Data.Taos 是一个 TDengine 的 ADO.NET 连接器,其中包含了用于EntityFrameworkCore 的提供程序 IoTSharp.EntityFrameworkCore.Taos 和健康检查组件 IoTSharp.HealthChecks.Taos ,支持 Linux,Windows 平台。该连接器由社区贡献者麦壳饼@@maikebing 提供,具体请参考:

    常见问题

    1. “Unable to establish connection”,”Unable to resolve FQDN”

      一般是因为 FQDN 配置不正确。可以参考如何彻底搞懂 TDengine 的 FQDN解决。

    API 参考