This is a rudimentary note describing how to do a sanity test of the Compliance Safety Net using a handful of JSON samples. You will need a valid license key to modify the samples shown here. We will explore these request/response pairs:
You will modify the JSON strings shown below and send them to these endpoints:
(The first two go to the former, and the last goes to the latter.)
To start you’ll need to generate a random string (e.g. a GUID) to serve as a session key. In this example, the session key is “d151bd4b-4e8b-4b5c-8ad7-b1c7f00b2c0b”. And you’ll need a license key satisfies the documentLibrary version, for instance “2017.95.0”. The transactionDat here is empty, but you’ll soon find your own TXL strings more satisfying.
{
"session": {
"key": "{{SESSION_KEY}}"
},
"documentLibraryVersion": "2017.95.0",
"client": {
"licenseKey": "{{license_key}}"
},
"transactionData": "<TransactionValues/>"
}
In response to this JSON request, the Compliance Safety Net will return a response that looks like this:
{
"url": "https://runtime.test.compliancesystems.cloud/Session/{{SESSION_KEY}}",
"documentLibraryVersion": "2017.95.0",
"messages": [
"Session * successfully started."
]
}
The url may vary. The session key you provided in the request will be reflected in the tail of the url, and should be mentioned in the messages.
Remember how I said it will be more satisfying to use your own TXL data? Consider this JSON request:
{
"session": {
"key": "{{SESSION_KEY}}"
},
"client": {
"licenseKey": "{{license_key}}"
},
"documentLibraryVersion": "2017.95.0",
"transactionData": "<TransactionValues><Entities><Entity id='1'><Roles><Role>TaxFavoredAccountOwner</Role></Roles><Phones><Phone Use='Primary'><Number>(586)5551212</Number><Extension>223</Extension></Phone></Phones><EntityType>1</EntityType><Individual><CitizenshipType>1</CitizenshipType><Date><Birth>10/12/1965</Birth></Date><Age>47</Age><Marital><StatusType>1</StatusType></Marital><EmailAddress>jeffrichards@email.com</EmailAddress><Identifications><Identification><UniqueIdentifierDescription>Unique ID 12345</UniqueIdentifierDescription><IssuingInformation><Agency>Secretary of State</Agency><LocationDescription>Wisconsin</LocationDescription></IssuingInformation><IssueDate>10/10/1985</IssueDate><Description>driver's license</Description><ExpirationDate>10/10/2017</ExpirationDate><IDNumber>99998789</IDNumber><VerificationNotation>Checked identification</VerificationNotation></Identification></Identifications></Individual><Name><First>Jeff</First><Middle>M.</Middle><Last>Richards</Last><Suffix>Sr.</Suffix></Name><TIN><SelectIfTINIsAnFEIN>0</SelectIfTINIsAnFEIN><TaxIDNumber>999887777</TaxIDNumber></TIN><Locations><Location Use='Primary'><City>Sterling Heights</City><SecondaryAddressLine>Apt.#3B</SecondaryAddressLine><State>WI</State><PrimaryAddressLine>557 Chesapeake Court</PrimaryAddressLine><PostalCode>40695</PostalCode></Location><Location Use='Residence'><State>WI</State></Location><Location Use='Citizenship'><Country>United States</Country></Location></Locations></Entity></Entities><Administrative><GoverningLawState>WI</GoverningLawState></Administrative><TermsAndProvisions><TodaysDate>April 1, 2015</TodaysDate><TaxFavoredAccount><PlanAccountNumber>123456</PlanAccountNumber><PlanType>1</PlanType></TaxFavoredAccount></TermsAndProvisions><DSL><TaxFavoredAccountActivities><TaxFavoredAccountActivity id='1'><ActivityType>1</ActivityType><Accounts><Account id='1'/></Accounts></TaxFavoredAccountActivity></TaxFavoredAccountActivities></DSL></TransactionValues>"
}
This will start the session with these data pre-defined. And you’ll want to inspect the response to verify it looks something like this:
{
"url": "https://runtime.test.compliancesystems.cloud/Session/{{SESSION_KEY}}",
"messages": [
"Session * successfully started."
]
}
This request sent to the Compliance Safety Net tells it to get data from the specified data session:
{
"session": {
"key": "{{SESSION_KEY}}"
},
"documentLibraryVersion": "2017.95.0",
"client": {
"licenseKey": "{{license_key}}"
}
}
In response to this JSON request, the Compliance Safety Net will return a response that looks like this:
{
"transactionData": "<TransactionValues>\n\t<datavalues />\n</TransactionValues>",
"documentLibraryVersion": "2017.95.0",
"messages": [
"Successfully retrieved session."
]
}
Unless you have a very boring session, transactionData will be much longer than is shown here. Your session data will be encoded in TXL format and hold the particulars of the session you specified.
Postman is a Chrome plug-in that enables you to paste in a string, POST it to a URL, and see the reply.
Launch Postman, select POST from the drop-down, and click Body from the radio buttons. This will reveal a drop-down for Text, XML, and JSON. You want JSON (application/json). You should see something like this:
Click that blue Send button and scroll the page down to see the response.
License keys are subject to change or revocation. Thus you want to set up Postman environment variables for them. When you create a Postman environment variable license_key, you can reference it in your POST request data by surrounding it with double curlie braces. Like this:
{
"documentLibraryVersion": "2017.95.0",
"client": {
"licenseKey": "{{license_key}}"
},
"notificationUrl": "http://compliancesystems.listener.com/workflowsave.asmx"
}
Click the gear in the upper-right hand corner of Postman. From the drop-down menu select “Manage Environments”. Click on the name of the environment (if one exists) or create a new environment. Add a key named license_key. Give that key a value consisting of a current license key.
If the license key changes, you’ll have one place to change it instead of all your JSON files.
CSiPoster is a command line utility that expects two parameters:
It then proceeds to POST the contents of the file to the URL. Then it writes the response to the console.
C:\> CSiPoster.py https://runtime.test.compliancesystems.cloud/1.0/api/startsession/tfa StartEmptySession-Request.json
The python program, CSiPoster.py, is shown here:
#!/usr/bin/python
'''post to URL the contents of a JSON file
'''
import argparse
import json
import os
import sys
import urllib3
def main():
'''this is the main module'''
parser = argparse.ArgumentParser(
description="read schema to get ui mapping paths")
parser.add_argument(
'--version',
action='version',
version='%(prog)s 1.0')
parser.add_argument('url', help='URL to POST to')
parser.add_argument('path', help='path to JSON file')
in_file = parser.parse_args().path
if not os.path.exists(in_file):
sys.exit("File '{}' does not exist"
.format(in_file))
url = parser.parse_args().url
if not url:
sys.exit("Url specified '{}' is falsy".format(url))
with open(in_file, "r") as myfile:
data = json.load(myfile)
http = urllib3.PoolManager()
req = http.request(
'POST',
url,
body=json.dumps(data, indent=4, sort_keys=True),
headers={
'Content-Type': 'application/json',
'Accept-Encoding': 'gzip, deflate'})
print(json.dumps(json.loads(
req.data.decode('utf-8')),
indent=4,
sort_keys=True))
sys.exit(0)
if __name__ == "__main__":
main()
Poster.cs is a C# class with one static method, GetData(), requiring two parameters:
It returns the response from the POST.
using System;
using System.Net.Http;
using System.Text;
namespace csharp
{
class Poster
{
public static string GetData(string url, string jsonRequest)
{
string result = string.Empty;
using (var client = new HttpClient())
{
var httpContent = new StringContent(jsonRequest, Encoding.UTF8, "application/json");
var uri = new Uri(url);
var response = client.PostAsync(uri, httpContent).Result;
if (response.Content != null)
{
response.EnsureSuccessStatusCode();
result = response.Content.ReadAsStringAsync().Result;
}
}
return result;
}
}
}
Poster.js is a JavaScript console application requiring two command-line parameters
It prints the response from the POST to the console.
#!/usr/bin/env node
var program = require('commander');
var request = require('request');
var fs = require('fs');
program
.version('0.1.0')
.arguments('<url> <path>')
.action(function(url, path) {
if ((typeof(url) != 'undefined') && (typeof(path) != 'undefined')) {
fs.readFile(path, 'utf8', function(err, jsonRequest) {
if (err) {
return console.error(err);
}
request({
headers: {
'content-type': 'application/json; charset=utf-8'
},
uri: url,
body: jsonRequest,
method: 'POST'
}, function(error, response, body) {
if (!error && response.statusCode == 200) {
console.log(body);
}
});
});
} else {
if (typeof(url) == 'undefined') {
console.error('no url given');
process.exit(1);
}
if (typeof(path) == 'undefined') {
console.error('no path given');
process.exit(1);
}
}
})
.parse(process.argv);
Poster.java is a Java class with one static method of interest, GetData(), requiring two parameters:
It returns the response from the POST.
import java.io.BufferedReader;
import java.io.DataOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import javax.net.ssl.HttpsURLConnection;
public class Poster {
public static void main(String[] args) {
// this is the main module
if (args.length < 2) {
System.out.println("Usage: <url> <path> url is end-point to POST to, path is filespec of JSON file to send");
System.exit(0);
}
String url = args[0];
String path = args[1];
if ((url.length() == 0)||(path.length() == 0))
{
System.exit(0);
}
File f = new File(path);
if (!f.exists() || f.isDirectory()) {
System.exit(0);
}
String jsonRequest = Poster.ReadFile(path);
String result = Poster.GetData(url, jsonRequest);
System.out.println(result);
}
public static String ReadFile(String path)
{
String result = "";
try {
BufferedReader br = new BufferedReader(new FileReader(path));
StringBuilder sb = new StringBuilder();
try {
String line = br.readLine();
while (line != null) {
sb.append(line);
sb.append(System.lineSeparator());
line = br.readLine();
}
}
finally
{
br.close();
}
result = sb.toString();
}
catch (FileNotFoundException e) {
System.out.println(e.getMessage());
e.printStackTrace();
}
catch (IOException e) {
System.out.println(e.getMessage());
e.printStackTrace();
}
return result;
}
public static String GetData(String url, String jsonRequest)
{
String result = "";
try
{
URL obj = new URL(url);
HttpsURLConnection con = (HttpsURLConnection)obj.openConnection();
con.setRequestMethod("POST");
con.setRequestProperty("Content-Type", "application/json");
//con.setRequestProperty("Accept-Encoding", "gzip, deflate");
con.setDoOutput(true);
DataOutputStream wr = new DataOutputStream(con.getOutputStream());
wr.writeBytes(jsonRequest);
wr.flush();
wr.close();
int responseCode = con.getResponseCode();
System.out.println("Sending 'POST' to URL: " + url);
System.out.println("Response code: " + responseCode);
BufferedReader in = new BufferedReader(new InputStreamReader(con.getInputStream()));
String inputLine = "";
StringBuffer response = new StringBuffer();
while((inputLine = in.readLine()) != null) {
response.append(inputLine);
}
in.close();
result = response.toString();
}
catch(MalformedURLException e)
{
System.out.printf("Malformed URL (%s) Exception %s", url, e.getMessage());
}
catch(IOException e)
{
System.out.printf("IO Exception %s", url, e.getMessage());
}
return result;
}
}