发布 pl/dotnet,版本 0.99 (beta)

发布于 2024-04-09,作者:Brick Abode
相关开源

发布 pl/dotnet,版本 0.99 (beta)

pl/dotnet 为 PostgreSQL 添加了对 C# 和 F# 的完整支持。0.99 是我们的公开测试版;我们希望与世界分享它的卓越之处。

  • 我们支持所有 PL 操作:函数、过程、DO、SPI、触发器、记录、SRF、OUT/INOUT、表函数等。
  • 我们原生支持 46 种标准用户类型中的 40 种,是所有外部 PL 中最多的。
  • 完全兼容 NPGSQL,并且 SPI 通过 NPGSQL API 公开,以实现最大兼容性。
  • 在我们的基准测试中,C# 和 F# 是 PostrgreSQL 中最快的过程语言。
  • 所有功能都针对 C# 和 F# 进行了全面测试,共有 1013 个单元测试。
  • 在 PostgreSQL 许可下 100% 免费软件。

这是一个测试版本;我们欢迎使用并接受反馈。

如何获取

更多详细信息如下。

使用示例

pl/dotnet 使您能够在 PostgreSQL 的过程、函数和触发器中充分利用 C# 和 F# 的强大功能。

CREATE OR REPLACE FUNCTION dynamic_record_generator_srf(lim INT8)  
RETURNS SETOF record  
AS $$  
    upperLimit = lim.HasValue ? lim : System.Int32.MaxValue;  
    for(long i=0;i<upperLimit;i++){ yield return new object?[] { i, $"Number is {i}" }; }  
$$ LANGUAGE plcsharp;

CREATE OR REPLACE FUNCTION dynamic_record_generator_srf_fsharp(lim INT8)  
RETURNS SETOF record  
AS $$  
    let upperLimit = Option.defaultValue (int64 System.Int32.MaxValue) lim  
    seq { for i in 0L .. upperLimit - 1L do yield [| box i; $"Number is {i}" |] }  
$$ LANGUAGE plfsharp;

SQL 功能

我们支持所有 SQL 函数模式

  • 普通过程和函数
  • 触发器函数,具有完整的触发器支持:触发器参数、旧/新行、行重写(在允许的情况下)以及所有标准触发器信息。
  • 设置返回函数,很好地映射到 C# 中的迭代器和 F# 中的序列。
  • 表函数,以及返回记录或记录集的函数。
  • 完全支持 IN/OUT/INOUT 函数

数据类型支持

我们支持 40 种 PostgreSQL 类型,所有这些类型都映射到其 NPGSQL 标准的 dotnet 类型。唯一的例外是 multirange、enum 和 struct 类型,我们希望将来添加它们。所有数据类型都是可空的,具有完整的数组支持,并且针对 C# 和 F# 进行了全面的单元测试。(出于技术原因,格式为(PostgreSQL 类型:Dotnet 类型)列表,而不是表格。)

  • bit: BitArray
  • bool: Bool
  • box: NpgsqlBox
  • bpchar: String
  • bytea: Byte[]
  • cidr: (IPAddress Address, Int Netmask)
  • circle: NpgsqlCircle
  • date: DateOnly
  • daterange: NpgsqlRange<DateOnly>
  • float4: Float
  • float8: Double
  • inet: (IPAddress Address, Int Netmask)
  • int2: Short
  • int4: Int
  • int4range: NpgsqlRange<Int>
  • int8: Long
  • int8range: NpgsqlRange<Long>
  • interval: NpgsqlInterval
  • json: String
  • line: NpgsqlLine
  • lseg: NpgsqlLSeg
  • macaddr8: PhysicalAddress
  • macaddr: PhysicalAddress
  • money: Decimal
  • path: NpgsqlPath
  • point: NpgsqlPoint
  • polygon: NpgsqlPolygon
  • record: Object?[]
  • text: String
  • timestamp: DateTime
  • timestamptz: DateTime
  • time: TimeOnly
  • timetz: DateTimeOffset
  • tsrange: NpgsqlRange<DateTime>
  • tstzrange: NpgsqlRange<DateTime>
  • uuid: Guid
  • varbit: BitArray
  • varchar: String
  • void: Void
  • xml: String

SPI

我们的 SPI 利用 NPGSQL 客户端库提供原生的 dotnet 实现,该实现与现有的客户端代码最大程度地兼容。我们在非常低的级别拦截了 NPGSQL 调用,以将客户端协议处理替换为 SPI 调用;否则,NPGSQL 未被修改。我们导入了 NPGSQL 测试套件作为存储过程,并将其用于我们的测试,这使我们对兼容性级别有了非常好的了解。

仍然需要进行改进以提高兼容性并添加功能。我们持续失败的最大 NPGSQL 测试类别是错误映射,因为 SPI 引发异常的方式与 NPGSQL 不同。这种不兼容性是次要但数量众多;我们正在继续努力改进它们。

以下是我们当前测试的 SPI 操作

  • 数据操作语言 (DML) 操作
    • 选择
    • 插入
    • 更新
    • 删除
  • 数据定义语言 (DDL) 操作
    • 创建表
    • 修改表
    • 删除表
    • 截断
    • 创建索引
    • 删除索引
    • 创建视图
    • 删除视图
    • 创建函数
    • 调用函数
    • 删除函数
    • 创建过程
    • 调用过程
    • 删除过程
  • 事务控制
    • 开始事务
    • 提交
    • 回滚
  • 支持的数据类型:所有 pl/dotnet 类型
    • 基本类型(包括范围)
    • 数组类型
    • 记录

我们没有的功能

我们缺乏对 multirange、enum 和复合/表类型的支持。我们打算添加它们。

我们的 SPI 实现缺少一些次要功能,例如子事务,并且我们有时会以与 NPGSQL 不同的(因此略有不兼容的)方式引发错误。

我们的构建系统,包括 dpkg 和二进制输出,是可用的,但不如我们希望的那样整洁。

我们欢迎提交代码以解决任何这些问题,并且我们希望随着时间的推移改进所有这些问题。

在哪里获取

我们的操作系统支持

  • 我们完全支持 Linux,并为 Debian 和 Ubuntu 提供 dpkg。(详情请参阅我们的安装页面
  • 我们已经在 OSX (arm 和 x86) 上构建和测试了该系统,但我们尚未对其进行打包。
  • 我们期待尽快获得 Windows 支持;如果您愿意提供帮助,请联系我们。

取得联系

我们欢迎社区的反馈。您可以通过我们的 GitHub 讨论论坛或通过电子邮件 pldotnet@brickabode.com 与我们联系。