Custom backend services can be written for Busby in C# using our NuGet package (ask Squared Paper for access to this).
using SqCommon.Logging;
using SqCommon.ESB;
using SqCommon.Subscribers;
using SqCommon.Subscribers.ResourceGroupService;
using SqCommon.JsonLib;
using System.Collections.Generic;
namespace SqCommonTest.TestSubscriber
{
class SomeMessageResult
{
public int test { get; set; }
public int test2 { get; set; }
}
public class ExampleSubscriber
{
public ExampleSubscriber()
{
}
public async void Init()
{
//Sets up the connection into Busby
//If this program is being run inside of Busby, the host, username, password and providerId will be passed in as command line arguments in that order
LoginDetails.Set("busby-core", "squared", "Squared1", "yourProviderId-1");
//Sets up logging file name
Log.SetFileName(LoginDetails.Get().GetProviderId());
Log.StartLogging();
//This is a generic subscriber which can subscribe to any service
//We can make specific subscribers for core services which contain definitions for each call. An example of this is the ResourceGroupSubscriber, see below
//This method will always return the same subscriber to a service, no matter where it's called from or how many times it is called
//There are two ways of connecting to a service, GetConnected, which returns when it connects to the service
//In the below example "testService" is the name of the service we wish to connect to
GenericSubscriber subscriber = await GenericSubscriber.GetConnectedAsync("serviceName");
subscriber.Connect();
//The other way will return the subscriber, but it won't necessarily be connected.
GenericSubscriber subscriber2 = GenericSubscriber.Get("serviceName");
//Callbacks can be added when the subscriber connects and disconnected
subscriber.AddConnectedProcessor((bool initial) =>
{
Log.LogInfo("Connected");
});
subscriber.AddDisconnectedProcessor((bool initial) =>
{
Log.LogInfo("Disconnected");
});
//Send/SendAsync is used to send a control message to a service
//It takes a message name and a params object
//Returns EsbResult exactly the same as calling a service from a workflow using busby.services
EsbResult result = await subscriber.SendAsync("messageName", new JsonObject());
if (!result.IsError())
{
var someMessageResult = result.GetResult();
}
//Result can also be typed
EsbResult<SomeMessageResult> result2 = await subscriber.SendAsync<SomeMessageResult>("messageName", new JsonObject());
if (!result2.IsError())
{
var someMessageResult = result2.GetResult();
var test = someMessageResult.test;
var test2 = someMessageResult.test2;
}
//This is an example of a specific subscriber which contains all available calls to the service
//Connecting to the service works in the same way as the GenericSubscriber, where GetConnectedAsync or Get can be used
ResourceGroupSubscriber resourceGroupSubscriber = await ResourceGroupSubscriber.GetConnectedAsync("testResourceService");
var getResourceTypesResult = await resourceGroupSubscriber.GetResourceTypesAsync();
if (!getResourceTypesResult.IsError())
{
List<string> resourceTypes = getResourceTypesResult.GetResult().resourceTypes;
}
//Callbacks can be added to receive status messages from the connected service
subscriber.AddStatusFunction((EsbMessage incoming) =>
{
string messageName = incoming.GetMessageName();
JsonObject parameters = incoming.GetParams();
Log.LogInfo($"Incoming status message {messageName}");
});
}
}
}
using SqCommon.Logging;
using SqCommon.ESB;
using SqCommon.JsonLib;
using System.Timers;
namespace SqCommonTest.TestProvider
{
public class ExampleProvider : ControlProcessor
{
private string providerId;
public ExampleProvider()
{
}
public void Init()
{
//Provider ID is found in Busby Admin (http://busby-core:5005) against the host and service configured in Busby Config Editor (http://busby-core:3002)
providerId = "yourProviderId-1";
//Sets up the connection into Busby
//If this program is being run inside of Busby, the host, username, password and providerId will be passed in as command line arguments in that order
LoginDetails.Set("busby-core", "squared", "Squared1", providerId);
//Sets up logging file name. This logs to /var/log/squaredpaper (Mac/Linux), or C:/var/log/squaredpaper (Windows) by default
Log.SetFileName(LoginDetails.Get().GetProviderId());
Log.StartLogging();
//A provider can either be set up to receive messages using an arrow function
Provider provider = new Provider((EsbMessage incoming) =>
{
string messageName = incoming.GetMessageName();
JsonObject parameters = incoming.GetParams();
EsbMessage result = EsbMessage.MakeControlReplyNak(providerId, incoming, "message name not supported");
switch (messageName)
{
case "helloWorld":
{
JsonObject jo = new JsonObject();
jo.AddString("hello", "world!");
result = EsbMessage.MakeControlReply(providerId, incoming, jo);
break;
}
}
return result;
});
//Or the class can implement ControlProcessor which will use the Process function to receive messages
Provider provider2 = new Provider(this);
//Call Connect() to connect into Busby.
bool connected = provider.Connect();
//Configuration from the config editor (http://busby-core:3002) for this service can be obtained using this call
JsonObject config = provider.GetConfig().GetConfigData();
//The service must call tryActive every 3 seconds to tell Busby that the service is alive
Timer timer = new Timer(3000);
timer.Elapsed += new ElapsedEventHandler((object sender, System.Timers.ElapsedEventArgs e) => {
bool active = provider.TryActive();
});
timer.Start();
}
public EsbMessage Process(EsbMessage incoming)
{
string messageName = incoming.GetMessageName();
JsonObject parameters = incoming.GetParams();
EsbMessage result = EsbMessage.MakeControlReplyNak(providerId, incoming, "message name not supported");
switch (messageName)
{
case "helloWorld":
{
JsonObject jo = new JsonObject();
jo.AddString("hello", "world!");
result = EsbMessage.MakeControlReply(providerId, incoming, jo);
break;
}
}
return result;
}
}
}