Skip to main content
Skip table of contents

SDK (.net)

Downloading the SDK

POWERSHELL
Install-Package Pharmx.DataSync.SDK.Dotnet -Version 0.1.32

Or via nuget: https://www.nuget.org/packages/Pharmx.DataSync.SDK.Dotnet/

Instantiating the client

First instantiate the data sync client, providing the access keys, site id, and optional service id.

C#
var client = new DataSyncClient(
    siteID: "112",
    serviceID: null,
    inboundKey: new DataSyncClientKey()
    {
        SharedAccessKeyName = "112",
        SharedAccessKey = "***************************="
    },
    outboundKey: new DataSyncClientKey()
    {
        SharedAccessKeyName = "112",
        SharedAccessKey = "***************************="
    },
    environment: Environment.Test
);

Sending Messages

Constructing a message

New up a DataSyncMessage object, set the message type, message direction, and complete the necessary fields. All data sync messages in effect share a single object schema.

C#
var message = new DataSyncMessage() {
    MessageType = Enums.MessageType.RetailTransaction,
    MessageDirection = Enums.MessageDirection.Inbound,
    RetailTransaction = new Transactions.RetailTransaction()
    {
        LineItems = new List<LineItem> { 
            new LineItem()
            {
                Sale = new Sale()
                {
                    Quantity = 5,
                    UnitListPrice = 2.00M
                }
            }
        },
        Total = new Transactions.Total()
        {
            Amount = 10.00M
        }
    }
};

Validating a message

When sending a message, depending on the context pharmx will run several hundred validation rules, this may result in your message not being sent to the destination, but instead sent back to you, in the form of an error. To avoid this round-trip scenario, as well as to provide a cleaner response to the user, and/or error recovery processes, we recommend validating the object before it is sent.

The data sync client has a method that validates a message, and returns an isvalid response, as well as an array of validation errors. Use these control the message flow.

C#
var validationresult = client.ValidateDataSyncMessage(message);

if (validationresult.IsValid == true)
{
    // Proceed
}
else
{
    // Reverse/Exit
    Console.WriteLine(validationresult.ToString());
}

Sending a message

The DataSync client has two methods to send messages, one of them is to send a single message, the other is to send a batch of messages. Both of them can be used in high-flow/low latency scenarios, however the batch method does use less network bandwidth (as headers are shared). Batching generally will put between 50 and 300 messages together as a single network request. The consumer will recieve the same stream regardless of whether a batch or a single message is sent.

Send Single message

C#
await client.SendMessageAsync(message);

Send a batch of messages

C#
var batchOfMessages = new List<DataSyncMessage>();
batchOfMessages.Add(message);
batchOfMessages.Add(message);
batchOfMessages.Add(message);

await client.SendBatchAsync(batchOfMessages);

Receiving Messages

Intro two choices

There are two methods of recieving messages, each with their own use case.

Receive Message Batch

The easiest way to receive a batch of messages is in batch, although we only recommend this in limited circumstances where latency and reliability is not a priority.

C#
var messageBatch = await client.ReceiveMessageAsync(limitCount: 1000, limitTime: 60);

The above command will connect to the pharmx network and download a 1000 messages, if 1000 messages do not exist on the endpoint, the request will wait a total of 60 seconds before returning a partial batch (which could be 0 messages.)

In this method you are forced to choose between an optimal batch size and wait time, this however can still be useful if your work flow is to download a 1,000 messages or 1 second, and then save the 1,000 messages to the database, databases like sql server, prefer batched writes for maximum throughput, example below.

Please keep in mind with the below code, you can recieve much more than a thousand messages per second. (It is ‘a thousand messages or 1 second, whichever comes first’.)

Example. recieving a thousand messages (or 1 second) and persisting for later processing

C#
while (true)
{
    var messageBatch = await client.ReceiveMessageAsync(limitCount: 1000, limitTime: 1);
    database.AddRange(messageBatch);
    try
    {
        await database.SaveChangesAsync();
    }
    catch (Exception e)
    {
        // These messages will be lost forever if this is unhandled
        // So try to put them somwhere, where they can be retried.
    }
}

We do not recommend trying to processing business logic in this fashion, when the 1000 messages is pulled off the queue, they are immediately marked as completed on the pharmx network and removed. We therefor recommend that you pull them off the queue and straight into a persistent format, where you subsequently re-order, and process.

Receive Message Stream

This is the preferred method of recieving messages where you want to handle inbound messages with high concurrency, low latency, and high-reliability.

First you will want to register two method handlers, and then call StartProcessingAsync.

C#
client.ProcessDataSyncMessageAsync += Client_ProcessDataSyncMessageAsync1;
client.ProcessDataSyncErrorAsync += Client_ProcessDataSyncErrorAsync;
await client.StartProcessingAsync();

The client will then start feeding events in real-time to the ProcessDataSyncMessage method, if any unhandled exceptions occur (in your code, not on the network), then the second method (ProcessDataSyncError) will be triggered.

Below is an example, of how you might handle a message:

C#
private static async Task Client_ProcessDataSyncMessageAsync1(DataSyncMessageReceivedEvent dataSyncMessageEvent)
{
    var message = dataSyncMessageEvent.DataSyncMessage;

    try
    {
        await DoSomeKindOfWorkHereAsync(message);
        await dataSyncMessageEvent.Session.CompleteMessageAsync(dataSyncMessageEvent.Session.Message);
    }
    catch (Exception e)
    {
        // Save message to an error recovery workflow.
    }
}

// Here an error has occcurred within your client.
// This could be due to a version mismatch between the SDK and the PharmX Portal
private static Task Client_ProcessDataSyncErrorAsync(Azure.Messaging.ServiceBus.ProcessErrorEventArgs arg)
{
    
    // So we have two choices:
        // either throw an exception, which cause the pharmx network to try and send this message to another reciever or wait a small interval of time and send back to this same reciever.
        // Or save the message to an internal error handling workflow
    throw new NotImplementedException();
}

JavaScript errors detected

Please note, these errors can depend on your browser setup.

If this problem persists, please contact our support.