在Sql Server中调用外部EXE执行程序引发的问题

1. 先来了解一下调用外部EXE执行程序的方式

在Sql Server中,调用外部exe程序,通常是通过xp_cmdshell来执行,例如:

EXEC xp_cmdshell 'dir'

上面的代码演示了如何在Sql Server中执行系统命令dir。

2. 外部程序执行时遇到的问题

2.1 外部程序权限不够的问题

有时,外部程序的执行需要更高的权限,但是xp_cmdshell是在Sql Server的权限下运行的,因此可能会因为权限问题而无法执行。

2.2 外部程序执行时间过长的问题

因为Sql Server是一个事务性数据库,所以xp_cmdshell执行的过程会被放到数据库的一个事务中,在执行完毕之前,该事务会一直处于等待状态,如果外部程序执行时间过长,可能会导致事务的阻塞。

2.3 外部程序执行结果不可预测的问题

由于外部程序的执行过程不受Sql Server的控制,因此不可预计外部程序的执行结果。

3. 如何解决这些问题

3.1 在xp_cmdshell中指定账户拥有更高的权限

为了解决外部程序权限不够的问题,可以在xp_cmdshell中指定拥有更高权限的账户来执行外部程序,例如:

EXEC xp_cmdshell 'runas /user:Domain\UserName "c:\path\to\your\exe"'

上面的代码演示了如何使用runas来指定执行外部程序的账户。

3.2 将xp_cmdshell的执行放在单独的线程中

为了解决xp_cmdshell执行过程阻塞的问题,可以将其执行放在单独的线程中,例如:

CREATE PROCEDURE sp_execute_cmd

@cmd varchar(1000)

AS

BEGIN

SET NOCOUNT ON;

DECLARE @result int, @errmsg varchar(1000);

EXEC @result = sp_OACreate 'WScript.Shell', @errmsg OUT;

IF @result = 0

BEGIN

EXEC @result = sp_OAMethod @errmsg, 'Run', NULL, @cmd, 0, 1;

EXEC @result = sp_OADestroy @errmsg;

END

END

GO

EXEC sp_execute_cmd 'c:\path\to\your\exe'

上面的代码演示了如何使用sp_OACreate和sp_OAMethod来在单独的线程中执行外部程序。

3.3 获取外部程序执行结果

为了解决外部程序执行结果不可预测的问题,可以通过xp_cmdshell返回值来获取外部程序执行结果,例如:

DECLARE @result int;

EXEC @result = xp_cmdshell 'c:\path\to\your\exe';

SELECT @result;

上面的代码演示了如何使用xp_cmdshell返回值来获取外部程序执行结果。

4. 结论

在Sql Server中调用外部EXE执行程序的方式虽然简单,但是在执行过程中可能会出现权限不够、执行时间过长、执行结果不可预测等问题。为了解决这些问题,可以使用指定账户拥有更高的权限、将执行放在单独的线程中、获取外部程序执行结果等方法来进行处理。

数据库标签