如何从 T-SQL、SQL Server 调用 C# 代码

问题描述 投票:0回答:2

一点背景知识,我需要一种在不使用参数的情况下无损插入/选择/比较单精度和双精度浮点到 SQL Server 数据库中的方法,我想我会很聪明,并将 DLL 作为超快速函数调用。

我编写并测试了这个 C# 类(我已经对其进行了充分测试):

using System;
using System.Linq;
using System.Reflection;

namespace SqlServerCast
{
    public class SqlServerCast
    {
        static public char ByteOrder;

        public enum ByteOrderEnum {
            BigEndian = 1,     /*  The most significant byte (highest address) is stored first. */
            LittleEndian = 0   /*  The least significant byte (lowest address) is stored first. */}

        public static void Main()
        {
            Assembly assem = typeof(SqlServerCast).Assembly;
            Object o = assem.CreateInstance("SqlServerCast", false,
                BindingFlags.ExactBinding,
                null, new Object[] { 2 }, null, null); 
        }

        public SqlServerCast(char val)    //  constructor
        {
            if (val != 0) ByteOrder = (char) ByteOrderEnum.BigEndian;
            else ByteOrder = (char) ByteOrderEnum.LittleEndian;
        }

        public static double CastToDBL(string str) {return BitConverter.ToDouble(StringToByteArray(str), 0);}

        public static float CastToSGL(string str)  {return BitConverter.ToSingle(StringToByteArray(str), 0);}

        private static string Dash = "-", NullStr = null;
        public static string CastFromDBL(double dbl) {
            switch (ByteOrder)
            {
                case (char)ByteOrderEnum.BigEndian:   //  actually, network byte order, big endian
                    byte[] bytes = BitConverter.GetBytes(dbl);
                    return BitConverter.ToString(bytes.Reverse().ToArray()).Replace(Dash, NullStr);
                case (char)ByteOrderEnum.LittleEndian:
                    return BitConverter.ToString(BitConverter.GetBytes(dbl)).Replace(Dash, NullStr);
                default:
                    return null;
            }
         }

        public static string CastFromSGL(float sgl)
        {
            switch (ByteOrder)
            {
                case (char)ByteOrderEnum.BigEndian:   //  actually, network byte order, big endian
                    byte[] bytes = BitConverter.GetBytes(sgl);
                    return BitConverter.ToString(bytes.Reverse().ToArray()).Replace(Dash, NullStr);
                case (char)ByteOrderEnum.LittleEndian:
                    return BitConverter.ToString(BitConverter.GetBytes(sgl)).Replace(Dash, NullStr);
                default:
                    return null;
            }
        }

        private static byte[] StringToByteArray(String hex)
        {
            int NumberChars = hex.Length;
            byte[] bytes = new byte[NumberChars / 2];
            for (int i = 0; i < NumberChars; i += 2)
                bytes[i / 2] = Convert.ToByte(hex.Substring(i, 2), 16);
            switch (ByteOrder) {
                case (char) ByteOrderEnum.BigEndian:   //  actually, network byte order, big endian
                    return bytes.Reverse().ToArray();
                case (char) ByteOrderEnum.LittleEndian:
                    return bytes;
                default:
                    return null;
            }
        }
    }
}

...尝试遵循 SO 和 MSDN 上关于 T-SQL 可调用 DLL 的规定,到目前为止我收到此错误:

消息 6544,第 16 级,状态 1,第 1 行
为程序集“SqlServerCast”创建程序集失败,因为程序集“SqlServerCast”格式错误或不是纯 .NET 程序集。
无法验证的 PE 标头/本机存根。

有人可以给我一步一步的成功之路吗?我被困住了...

顺便说一句:我知道创建哈希值,但我认为这还不是问题。

c# sql-server dll
2个回答
0
投票

这些说明适用于 Microsoft SQL Server Management Studio 2014。

导入程序集

首先,您需要通过导航到“新建程序集”对话框窗口将该程序集导入到 SQL Server Management Studio 内的数据库中:

DatabaseName -> Programmability -> Assemblies -> (Right Click) 'New Assembly...'

在“新建程序集”对话框窗口中,选择

Browse
字段下的
Path to assembly
,然后选择要导入的程序集。调整权限并单击确定。

将汇编方法包装在 SQL 函数中

接下来您需要创建 sql 函数来包装您的汇编方法,如下所示:

CREATE FUNCTION [dbo].[fn_funcName](@str [varchar](max))
RETURNS 
   varchar(max) 
WITH EXECUTE AS CALLER
AS 
EXTERNAL NAME [YourSqlAssemblyName].[YourAssemblyName.Class1].[GetName]

如果您想从函数返回表,请阅读 .NET 中的 SqlFunctionAttribute。

创建Sql Server数据库项目并编译Sql Server中使用的dll的分步指南:

https://dbtut.com/index.php/2019/05/05/what-is-clr-and-how-to-import-dll-in-sql-server/


0
投票

之前的评论已失效,但该链接已失效。我有使用 4.8.0 .NET 的 SQL 2019 和 Visual Studios 2022,并且能够通过此链接让我的库正常工作。

https://learn.microsoft.com/en-us/sql/relational-databases/clr-integration/database-objects/getting-started-with-clr-integration?view=sql-server-ver16&tabs=cs
© www.soinside.com 2019 - 2024. All rights reserved.