There are several ways to integrate with Salesforce that I am currently aware of:
- Outbound Messages
The Salesforce API allows you to create, query and edit records within Salesforce in all the ways that you would expect. This is a strong option for integrations that are either asychronous, batch or driven by events on another system.
The Dataloader lets you move data in both directions between Salesforce and JDBC/ODBC connections, databases, CSV files etc and can be invoked through a UI or command line application. This is great for quickly building batch operations.
Outbound Messages are used to invoke webservices at certain points in an object’s workflow (creation, approval etc) and are well suited to synchronous integrations with third party systems driven by events within Salesforce.
The use case I was looking into when I performed this integration was to create a Jira ticket for a production team to work against when an order came in so Outbound Messages was a good fit. In the end I went down a different route to satisfy the requirement as described in my last post but performing this integration was a good learning experience and I hope it will be of some use to someone.
At the Salesforce end I built a simple application roughly following the instructions provided and added an Outbound Message containing all the fields on a Custom Object, triggered by a simple workflow with one step (create).
The main hurdle I had to get over was the fact that Salesforce sends outbound messages as SOAP requests, this has several disadvantages:
- The messages include named fields so need to be edited every time you edit the custom object they relate to.
- You need to build a SOAP webservice to consume the messages rather than cobble together a web hook.
- You are given a WSDL file and have to build a webservice to conform to it so you need to either use a tool that can reverse engineer a SOAP server from a WSDL file (such as the .net svcutil) or manually create a webservice that is an exact match (no mean feat due to the inflexibility or automation in some frameworks).
- Salesforce supplies a WSDL contract which has strongly typed fields mapped to each property of the custom object so if you add or remove properties you will have to rebuild your webservice.
In order to circumvent these issues I opted to not use a SOAP framework but work with the raw request using an XML parser and return a manually constructed SOAP ack message. This allowed the script doing the integration to be decoupled from the message content, except for the target Jira project which it expects to find in a property called ‘Project’.
The integration into Jira was very straight forward thanks to the excellent jira-python library.
Initially I found the choice of XML parsing libraries for Python bewildering but once I decided that SAX parsing would be over kill and looked at how actively they were maintained ElementTree seemed a strong choice with decent XPath support.
There are a lot of web frameworks for Python but since all I needed was close to the wire access to the request and response cgi got the job done with no fuss.
This script is obviously not production ready – it doesn’t check the messages come from Salesforce and has no error handling but if anyone builds it out or ends up working on something similar please get in touch as I would love to be involved.