Perceptive Content Integration API - Capture new Document
This article demonstrates how a custom application can capture a document and upload a page through a few code examples. Always open a session before calling the Integration API and close it afterwards (https://kb.wisc.edu/ecms/102520). This example comes from an asynchronous .Net WebAPI written in C#.
Capture New Document
Below is the code for creating a document and adding a page split up into several methods. Once the document is created, consider adding it to a workflow queue.
/// <summary>
/// Creates an empty document then uploads a file or "page" associated with the document
///
/// https://docs.hyland.com/Developer/IS/en_US/7.4/operations.html#call_Document_V3_POST-document
/// </summary>
/// <param name="Doc">Object containing the new document's metadata</param>
public static async Task<Document> CreateDocument(DocumentPost Doc)
{
//Convert incoming JSON data to string
string postData = JsonConvert.SerializeObject(Doc);
//Create the new document getting its detail url from the response location header
var NewDocURL = await PostRequestReturnLocationHeader(BaseURL + $"document", postData);
//Creating the document returns the URL location but
//does not return any metadata so we need to go get it
var newDocData = await GetRequest(NewDocURL);
var newDocObject = JsonConvert.DeserializeObject<Document>(newDocData); //parse the JSON to object
//grab a file to be used as a new page
byte[] arr = System.IO.File.ReadAllBytes("C:/Users/nwelker/Documents/Projects/Perceptive-Content-API/Content/unnamed.tiff");
//add the page to the new document using the new id we retrieved
await AddPageToDocument(newDocObject.info.id, arr);
//get the doc data again now that we have added a page
newDocData = await GetRequest(NewDocURL);
var json = JsonConvert.DeserializeObject<Document>(newDocData);
return json;
}
/// <summary>
/// Helper for making a POST request to the Integration Server API
/// that returns the value of the resulting Location response header
/// </summary>
/// <param name="url">URL for this request</param>
/// <param name="postData">Data payload for this request, defaults to empty string</param>
/// <returns></returns>
private static async Task<string> PostRequestReturnLocationHeader(string url, string postData = null) //post data defaults to null
{
try
{
//http client data persists so first we clear headers
client.DefaultRequestHeaders.Clear();
//API will default to returning XML if we do not
//specify the Accept header
client.DefaultRequestHeaders.Accept.Add(
new MediaTypeWithQualityHeaderValue("application/json"));
//Retrieve the access token from memory and
//add it to the request as a custom header
client.DefaultRequestHeaders.Add("X-IntegrationServer-Session-Hash", Token);
//This line adds the post data and sets the content-type
//header to application/json
var data = new StringContent(postData, Encoding.UTF8, "application/json");
//Send the POST request
HttpResponseMessage response = await client.PostAsync(url, data);
//throws exception if not a success
response.EnsureSuccessStatusCode();
//Get the location header value
var location = response.Headers.GetValues("Location").FirstOrDefault();
return location;
}
catch (Exception e) //if anything goes wrong end the session
{
await CloseSession();
throw;
}
}
/// <summary>
/// Add a file or "page" to the given document. Returns the newly updated
/// document object
///
/// </summary>
/// <param name="docID">ID of target document</param>
/// <param name="arr">Byte array for the file to be uploaded</param>
public static async Task<string> AddPageToDocument(string docID, byte[] arr)
{
//upload a file or "page" to the given document, including the file and file name
var retval = await UploadPage(BaseURL + $"document/{docID}/page", arr, "unnamed.tiff");
return retval;
}
/// <summary>
/// Uploads a file or "page" associated with the given document. Document id
/// comes in as a part of the URL
/// </summary>
/// <param name="url">URL for the request, should include doc id</param>
/// <param name="file">Byte array derived from given file</param>
/// <param name="filename">Name of the given file</param>
/// <returns></returns>
public static async Task<string> UploadPage(string url, byte[] file, string filename)
{
try
{
string responseFromServer = "";
//http client data persists so first we clear headers
client.DefaultRequestHeaders.Clear();
//Integration API will default to returning XML if we do not
//specify the Accept header
client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
//Always add token for auth
client.DefaultRequestHeaders.Add("X-IntegrationServer-Session-Hash", Token);
//Add special headers for file name and size
client.DefaultRequestHeaders.Add("X-IntegrationServer-Resource-Name", filename);
//File size should be the number of bytes to be uploaded
client.DefaultRequestHeaders.Add("X-IntegrationServer-File-Size", file.Length.ToString());
//add the byte array to the request
using (var content = new ByteArrayContent(file))
{
//set the proper content type
content.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream");
//make the POST request
var response = await client.PostAsync(url, content);
//Read the server response text
responseFromServer = await response.Content.ReadAsStringAsync();
}
return responseFromServer;
}
catch (Exception ex)
{
//Always close session on fail
await CloseSession();
throw;
}
}
/// <summary>
/// Helper for making a POST request to Integration Server API
/// </summary>
/// <param name="url">URL for this request</param>
/// <param name="postData">Data payload for this request, defaults to empty string</param>
private static async Task<string> PostRequest(string url, string postData = "") //post data defaults to null
{
try
{
//http client data persists so first we clear headers
client.DefaultRequestHeaders.Clear();
//API will default to returning XML if we do not
//specify the Accept header
client.DefaultRequestHeaders.Accept.Add(
new MediaTypeWithQualityHeaderValue("application/json"));
//Retrieve the access token from memory and
//add it to the request as a custom header
client.DefaultRequestHeaders.Add("X-IntegrationServer-Session-Hash", Token);
//This line adds the post data and sets the content-type
//header to application/json
var data = new StringContent(postData, Encoding.UTF8, "application/json");
//Send the POST2 request
HttpResponseMessage response = await client.PostAsync(url, data);
//throws exception if not a success
response.EnsureSuccessStatusCode();
//Read the response text and return it
string responseBody = await response.Content.ReadAsStringAsync();
return responseBody;
}
catch (Exception e) //if anything goes wrong end the session
{
await CloseSession();
throw;
}
}