如何通过T-SQL调用Web服务更新PrestaShop产品?
解决T-SQL通过POST调用PrestaShop Web服务传递XML的问题
看你提供的代码,核心问题是重复调用了send方法——第一次传空字符串提前发送了空请求,第二次再传XML就完全无效了。另外还有几个配置细节需要调整,下面是修正后的完整代码和关键点说明:
修正后的完整代码
DECLARE @xmlRIA XML SET @xmlRIA = CAST('<?xml version="1.0" encoding="UTF-8"?> <prestashop> <customer> <id></id> <id_default_group>3</id_default_group> <id_lang>1</id_lang> <newsletter_date_add>0000-00-00 00:00:00</newsletter_date_add> <ip_registration_newsletter></ip_registration_newsletter> <last_passwd_gen>2017-04-29 05:34:22</last_passwd_gen> <secure_key></secure_key> <deleted>0</deleted> <passwd></passwd> <lastname>test</lastname> <firstname>test</firstname> <email>kow@testde.com</email> <id_gender>2</id_gender> <birthday>0000-00-00</birthday> <newsletter>0</newsletter> <optin>0</optin> <website></website> <company></company> <siret></siret> <ape></ape> <outstanding_allow_amount>0.000000</outstanding_allow_amount> <show_public_prices>0</show_public_prices> <id_risk>0</id_risk> <max_payment_days>0</max_payment_days> <active>1</active> <note></note> <is_guest>0</is_guest> <id_shop>1</id_shop> <id_shop_group>1</id_shop_group> <date_add>2017-04-29 11:34:22</date_add> <date_upd>2017-04-29 11:34:22</date_upd> <reset_password_token></reset_password_token> <reset_password_validity>0000-00-00 00:00:00</reset_password_validity> <associations> <groups> <group> <id>3</id> </group> </groups> </associations> </customer> </prestashop> ' AS XML) DECLARE @ret INT, @token INT, @MessageError NVARCHAR(MAX) DECLARE @url NVARCHAR(200) = 'https://your-prestashop-domain.com/api/customers' -- 替换为你的PrestaShop API地址 DECLARE @authHeader NVARCHAR(200) = 'Basic ' + CONVERT(NVARCHAR(MAX), CAST('YOUR_API_KEY:' AS VARBINARY(MAX)), 1) -- 替换为你的API Key DECLARE @contentType NVARCHAR(50) = 'text/xml; charset=utf-8' DECLARE @status INT, @statusText NVARCHAR(100), @responseText NVARCHAR(MAX) -- 打开连接 EXEC @ret = sp_OACreate 'MSXML2.ServerXMLHTTP', @token OUT; IF @ret <> 0 BEGIN SET @MessageError = 'sp_OACreate MSXML2.ServerXMLHttp failed' GOTO final END -- 初始化POST请求 EXEC @ret = sp_OAMethod @token, 'open', NULL, 'POST', @url, 'false'; IF @ret <> 0 BEGIN SET @MessageError = 'sp_OAMethod open failed' GOTO final END -- 设置认证头(注意是Authorization而非Authentication) EXEC @ret = sp_OAMethod @token, 'setRequestHeader', NULL, 'Authorization', @authHeader; IF @ret <> 0 BEGIN SET @MessageError = 'sp_OAMethod set Authorization header failed' GOTO final END -- 设置Content-Type,匹配XML编码 EXEC @ret = sp_OAMethod @token, 'setRequestHeader', NULL, 'Content-type', @contentType; IF @ret <> 0 BEGIN SET @MessageError = 'sp_OAMethod set Content-type failed' GOTO final END -- 仅调用一次send,传递XML内容(转成字符串类型) EXEC @ret = sp_OAMethod @token, 'send', NULL, CONVERT(NVARCHAR(MAX), @xmlRIA); IF @ret <> 0 BEGIN SET @MessageError = 'sp_OAMethod send failed' GOTO final END -- 处理响应 EXEC @ret = sp_OAGetProperty @token, 'status', @status OUT; IF @ret <> 0 BEGIN SET @MessageError = 'sp_OAGetProperty status failed' GOTO final END EXEC @ret = sp_OAGetProperty @token, 'statusText', @statusText OUT; IF @ret <> 0 BEGIN SET @MessageError = 'sp_OAGetProperty statusText failed' GOTO final END -- 获取响应内容(用于调试PrestaShop返回的错误信息) EXEC @ret = sp_OAMethod @token, 'responseText', @responseText OUT; IF @ret <> 0 BEGIN SET @MessageError = 'sp_OAMethod get responseText failed' GOTO final END PRINT 'Status: ' + CAST(@status AS NVARCHAR(10)) + ' - ' + @statusText PRINT 'Response: ' + @responseText final: -- 清理COM对象 IF @token IS NOT NULL EXEC sp_OADestroy @token IF @MessageError IS NOT NULL RAISERROR(@MessageError, 10, 1);
关键修正&注意事项
- 移除重复的
send调用:原代码两次调用send会导致请求异常,必须只调用一次并传入XML内容。 - 修正认证头名称:HTTP标准认证头是
Authorization,不是Authentication,这会导致PrestaShop拒绝你的请求。 - XML转字符串传递:
send方法需要字符串类型参数,所以要把XML变量@xmlRIA转换为NVARCHAR(MAX)。 - 更新产品的PUT请求:如果是更新现有产品,只需把
open方法的请求方法改成'PUT',XML里填写对应产品的<id>,API地址指向具体产品(比如https://your-domain.com/api/products/123)。
内容的提问来源于stack exchange,提问作者alirot
相关产品推荐
相关产品推荐

