I have a working stored procedure:
USE [DB_NAME]
GO
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
ALTER PROCEDURE [dbo].[INSERT_XML]
-- Add the parameters for the stored procedure here
@XML XML
AS
BEGIN
-- SET NOCOUNT ON added to prevent extra result sets from
-- interfering with SELECT statements.
SET NOCOUNT ON;
-- Insert statements for procedure here
DECLARE @Order AS INT
SELECT @Order = MAX([order_id])+1
FROM [DB_NAME].[dbo].[TABLE_NAME]
INSERT INTO [DB_NAME].[dbo].[TABLE_NAME] ([Status]
,[error_message]
,[start_date_time]
,[end_date_time]
,[SystemId]
,[bundle_name]
,[doc_xml]
,[order_id]
,[batch_load_date])
VALUES (0,'',GETDATE(),GETDATE(),'tmpltst','TEST',@XML,@Order,GETDATE());
END
I have tested this as working with the XML provided by my other application (after doubling all the single quotes) to populate the @XML parameter, it produces the expected results, adding the XML provided into a single cell of a new row in the table.
The source of the XML is a file provided by another application. I need to execute the stored procedure using the XML contents of the provided file on a periodic basis. I have been working on a PowerShell script to do this.
$server = "server.address.com"
$database = "DB_NAME"
$XMLFile = Get-ChildItem C:\local\*.xml | select -First 1
[string]$XMLString = (Get-Content $XMLFile.FullName).replace('`n','').replace('`r','').replace("'","\'")
Invoke-Sqlcmd -ServerInstance $server -Database $database -Query "[dbo].[INSERT_XML] @XML = '$($XMLString)'" -credential $PSCred -TrustServerCertificate
This results in the error:
Invoke-Sqlcmd : Incorrect syntax near 's'.
Msg 102, Level 15, State 1, Procedure , Line 1.
At line:1 char:1
+ Invoke-Sqlcmd -ServerInstance $server -Database $database -Query "[db ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidOperation: (:) [Invoke-Sqlcmd], SqlPowerShellSqlExecutionException
+ FullyQualifiedErrorId : SqlError,Microsoft.SqlServer.Management.PowerShell.GetScriptCommand
I have tried a number of different ways of formatting that -Query and of escaping the $XMLString. I expect that this is an issue of not properly escaping the contents of the $XMLString which will have slashes, single quotes, double quotes, newlines, etc. I am stripping the newlines and replacing the single quotes with ' in the Get-Content, but I am thinking the single quotes are still throwing off the PowerShell command?
Any help getting this working is appreciated. Thanks!
Edit: Okay, I verified that the variable is my issue. I removed all single-quotes from the string and it processed as expected. So the remaining question is: How can I get it to run without removing all the single-quotes. This might be more of a PowerShell question than a DB question at this point.
Edit2: Thanks to Peter's recommendation below, I ended up using Invoke-SqlCmd2 and modifying my PowerShell use it.
$server = "server.address.com"
$database = "DB_NAME"
$XMLFile = Get-ChildItem C:\local\*.xml | select -First 1
[string]$XMLString = Get-Content $XMLFile.FullName
Invoke-SqlCmd2 `
-ServerInstance $server `
-Database $database `
-Query "[dbo].[INSERT_XML] @XML;" `
-SqlParameters @{XML=$XMLString} `
-Credential $Credential