使用 OData 实施 SAP 系统与第三方系统集成的步骤概述
以前笔者曾经介绍过 SAP C/4HANA 的五朵云到底包含哪些具体产品,其实在 SAP官网上有更权威的中文解释:
其中明确提到销售云包含 SAP Cloud for Customer(C4C),SAP Revenue Cloud 和 Callidus Cloud。
有 Partner 询问有没有更详细的步骤介绍,关于如何在第三方系统里调用 SAP C4C 暴露出的 Restful API 进行集成。本文就给出一个具体的例子,将 SAP C4C 销售订单的创建功能通过自定义的 OData 服务暴露出来,然后 Partner 可以根据项目需要选择合适的编程语言(本文选择 JavaScript)来消费。
Jerry 以前发布过一个视频,演示了如何在 SAP C4C 里手动创建一个销售订单,步骤可以说简单易懂。
现在我们通过 OData 的方式将销售订单的创建功能暴露出来,就能在第三方系统或者应用里完成 C4C 的订单创建。
大家如果对 SAP OData 还不太了解,可以先读一读我这篇文章开头的部分:
下面是详细步骤。
登录 C4C 系统,访问工作中心 Administrator,工作中心视图 OData Service Explorer,这里可以在 SAP 发布的标准 OData 服务和客户自定义的 OData 服务之间切换。
因为客户自定义 OData 服务能够允许客户自行决定从哪一个 Business Object 的哪一些节点,选择哪一些字段来生成 OData 模型,通过这种灵活的方式可以避免 Business Object 上客户业务场景里不需要的字段出现在 OData 模型中。
点击 New 按钮新建一个 OData 服务:
给 Work Center View 字段指定一个用来做权限控制的视图,只有分配了这个视图的用户才有权限访问这个 OData 服务。
点击 Select Business Object 从弹出对话框中选择基于哪一个 Business Object 创建 OData 模型。
下图就是一个已经创建好并处于 Active 状态的 OData 服务。左边显示的是 CustomerQuote 这个 BO 的 Root 节点的所有字段,每个字段都有一个可以勾选或取消的 Select 属性,勾选则该 BO 字段会出现在右侧的 OData 模型里。
除了 Root 节点之外,BO 的其他子节点上的字段当然也是可以出现在 OData 模型里的,比如我上图右边 OData 模型的子节点 CustomerQuoteItem, CustomerQuoteParty 和 CustomerQuoteText 等,就是分别从左边 BO 的同名节点选中后自动带到右边的 OData 模型中去的。
理论上,完成基于 BO 模型进行 OData 模型的创建并激活后,这个 OData 服务就可以使用了,这体现了 SAP C4C OData 服务自定义框架的强大之处。然而我也收到了一些朋友从后台给我提的一些问题,罗列如下。
问题 1: 仍然以本文销售订单创建这一场景为例,假设我希望我创建的 OData 服务能够允许消费者调用时指定 External Reference 的值,但是我找遍整个 BO 列表,也没发现销售订单的 BO 上有叫这个名称的字段啊?
Jerry 答:External Reference 是 UI 文本,不是 BO 字段的技术名称。
给 C4C 系统在浏览器里的 url 添加参数 debugMode=true, 然后刷新页面,按住 Ctrl 键再单击 External Reference 字段,
就能看到这个 UI 字段绑定到 UI 模型上哪一个字段了。
在这个 UI 模型字段上再点击 Show Model,就能看到这个 UI 模型字段绑定到的 BO 字段名称为 BuyerID。
所以我们在 OData 开发工具里,只需把 BO 字段 BuyerID 选中,移动到右边的 OData 模型里即可。
问题 2:我想让我的 OData 服务支持行项目数据的创建,比如指定产品 ID,描述和购买数量等等。我怎么知道哪些 BO 节点上的字段需要添加到 OData 模型中去?
Jerry 答:现在我们换一种方法,打开 Cloud Application Studio 的 UI Designer,定位到销售订单创建页面的 UI 模型 COD_SALESORDER_QC, 找到 Product ID 字段,在它的 Properties 面板里即可看到这个 Product ID 字段绑定的 BO 字段的名称和完整路径:
Root-.ItemProposal-~ProductUUID-~content
因此我们需要将 BO 对应路径下面的 ProductUUID 字段添加到 OData 模型中去。这里能观察到 ProductID 的 Create 和 Update 是没有勾选上的,而 ProductUUID 则支持 Create 和 Update,这个行为和 C4C 销售订单行项目创建的标准实现有关——消费者需要提供待创建行项目包含的产品 UUID,然后 C4C 会根据 UUID 到系统中查询出对应的产品,显示其 ID 到 UI 上。如果消费者在调用 OData 服务时,没有指定 ProductUUID,则行项目创建逻辑不会执行。
OData 模型创建好之后,在用编程语言消费之前,我们可以先用工具 Postman(或者 C4C 自带的测试工具)进行测试。
因为 SAP C4C 后台对 Cross-site request forgery(跨站请求伪造)这种攻击采取的防御实现和 SAP CRM,SAP S/4HANA 一样,采取的是 CSRF token 验证机制,因此我们在调用 OData 服务进行销售订单创建时,需要将一个合法的 CSRF token 一并传递给 C4C 系统。
如何得到一个合法的 CSRF token 呢?在 Postman 里构造一个 HTTP GET 请求,头部字段名为
x-csrf-token, 值为 fetch:
发送这个 HTTP GET 请求,服务器端会生成一个 CSRF token,通过 HTTP 响应结构头部字段 x-csrf-token 返回给消费者:
sNwnYC9cV4xeGSYZmJ8Dtw==
下面我们再在 Postman 里新建一个 HTTP Post 请求,将之前通过 HTTP GET 拿到的 CSRF token,以 HTTP Post 请求头部字段的方式发送给 C4C 系统。
关键在于 HTTP Post 请求的请求体。下图高亮部分是我在 HTTP Post 请求里指定的创建销售订单的输入数据:
在 Postman 里发送这个 Post 请求,几秒钟后得到 C4C 的响应,订单创建成功,ID 为 9000000451:
为了方便大家对比,下面是我用 Postman 消费我创建的 OData 服务生成的销售订单在系统里的显示。字段 1~6 对应的 Postman 输入字段可以在前文找到。
蓝色区域高亮显示的字段,我在 Postman 里构造的输入里并没有维护,而是通过 SAP C4C 系统的各种 determination 配置,自动决定出来的。最典型的有 SAP 老司机们天天打交道的 Partner determination,Organization determination,Pricing determination 等。
Postman 里测试通过后,就可以写代码消费了。
如果想直接复制粘贴我下面列出的代码,可以从我的 github 上获得:
https://github.com/i042416/KnowlegeRepository/blob/master/ABAP/C4COData/create_SalesOrder.js
注意本代码只用于演示目的,缺少健壮的出错处理,不能直接用于生产环境中。
下面的代码使用 nodejs 提供的 request 模块向 C4C 请求 CSRF token。注意第 3 行的 url 和第 11 行的 Authorization 头部的值,我都是用的虚假值,请大家替换成自己实际使用的 C4C url 和认证信息。
Token 拿到之后,将其放入第 41 行构造的 HTTP Post 请求的头部结构中,作为字段 x-csrf-token 的值。第 47 行发送该 POST 请求,C4C 响应的数据存放于 JavaScript 变量 data 中。
最后我通过简单的 console.log 打印出创建成功的销售订单 ID:
在命令行里用 node 执行这个 js 文件,会打印出从 C4C 获取到的 CSRF token,以及成功创建的订单 ID。
总结
我们再回顾一下用 SAP C/4HANA Sales Cloud 中的 C4C OData 同外部系统做集成的三个主要步骤:
1. 在 C4C 的 OData 模型编辑页面里,根据业务需要,从对应的 BO 节点里选择合适的字段,添加到 OData 模型中。
2. 用 Postman 或者 C4C 自带的 OData 测试工具对 OData 模型进行测试,确保其正常工作。
3. 根据项目需要选择合适的编程语言消费 OData 服务。
如果对于 SAP C4C OData 与第三方系统的集成有更多的问题需要讨论,欢迎留言。感谢阅读。
版权声明: 本文为 InfoQ 作者【Jerry Wang】的原创文章。
原文链接:【http://xie.infoq.cn/article/150687bbdcbae362220c4311c】。文章转载请联系作者。
评论