jiangdunchun / WampFramework

A lightweight framework allows remote calls of methods and subscription of events in local c# assembly

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Welcome to WampFramework


Author: Dunchun Jiang Version: 1.0 Date: 26/11/2018

Here is a website introducing the theory of Wamp. But, actually, I modify some technical details in order to meet the demand of invoking API in local c# assembly base on websocket. In summary, this framework could do these:

  • Open the API of c# assembly to websocket connection in a simple and quick way, even though you don't have a clear conscious about how to organize the router
  • Export all c# API to js file, as a result, the front_end could invoke these API just by referencing these files
  • The asynchronous invoking is also supported. In other words, even though one method invoked by remote command in your assembly needs a long time to process, the later remote command will not be blocked

Open API From Local C# Assembly(for C# developer)

@ to do

Protocol Definition

This framework supports two types of packet in websocket: String Mode and Byte[] Mode. Both these two modes have the same items in packet. This chart explains the structure of packet delivered between master and slaves(*represents this item is not essential).

Items: Packet Head ID Class Name Method(Event) Name Arg_0* ...*
Type in C#: byte UInt16 string string - -

So, what these items mean:

Packet Head: several numbers are defined to present different command of this packet. This chart explains which command type each number represents:

Number Command
0 Remote call
8 Feedback of successful remote call
9 Feedback of failed remote call
10 Remote subscribe
11 Subscribed event invoked
18 Feedback of successful remote subscribe
19 Feedback of failed remote subscribe
20 Remote unsubscribe
28 Feedback of successful remote unsubscribe
29 Feedback of failed remote unsubscribe
30 Remote register
38 Feedback of successful remote register
39 Feedback of failed remote register
101 An error happened

ID: No matter calling a method or subscribing a event, the Wamp slaves need to generate a unique ID, and send it to Wamp master. After that, the master will send it back to slave in the feedback message. This ID make sure that all message could be send back to the slave where it came from.

Class Name: The name of a class in c# assembly.

Method(Event) Name: The name of a method(event) belong to the class mentioned above in c# assembly.

Arg_n: Wamp message will have this item in 3 occasions. Firstly, the slave should send the arguments when remotely call a method, if this method needs. Secondly, the master would send a argument back in the feedback message of a remote call, if this method has return value. Finally, the master would send arguments back when a subscribed event invoked, if this event delivers parameters out.

String Mode

Well, it's very simple to orgnaise a packet in string mode, converting all items to string, then splitting them by '|' is enough. You might wonder why we still need byte[] mode if string mode is so simple and both the master and slaves could decode the packet very easy. The reason is the packet in byte[] mode is smaller than string mode in most occasion.

Byte[] Mode

Like the string mode, all items in byte[] need to be converted to byte array. Then the master and salves need to decode packet and get all items according to every item's length in the packet(byte array). This chart shows every items' length.(* represents this item is not essential, *** represents this item will be explained latter)

Items: Packet Head ID Class Name and Method(Event) Name Arg_0* ...*
Type in C#: byte UInt16 string - -
Length in array: 1 2 1+n *** ***

You might notice that the Class Name and Method(Event) Name looks a little strange(different with the structure in packet). Actually, in byte[] mode, we use this item to merge the Class Name and Method(Event) Name which stores the Class Name and Method(Event) Name together, and splits them using a '|'. Because these two items are both string type. Another consideration is we need another byte to illustrates this compound string's length when it was converted to byte array. As a result, this new item will occupy 1+n bytes in the packet, the front 1 byte stores a byte representing the byte array's length(n) converted from this compound string, the next n bytes store the byte array converted from this compound string. Also for this reason, the length of the byte array converted from this compound string must less than 255.

Another point need to be noticed is the length of Arg_n. I explain it in more details because it's a bit of complicated. Different types(in C#) of arguments have different length when they were converted to byte array, so, we need to label which type this argument is in packet. Several numbers(Byte) are defined to present different argument types.

Argument Type in C# Lable
null 0
string 1
byte 2
bool 3
ushort 4
short 5
int 6
float 7
double 8
json 9
string[] 11
byte[] 12
bool[] 13
ushort[] 14
short[] 15
int[] 16
float[] 17
double[] 18
json[] 19

Well, after we lable different type of arguments, storing them in packet will be easyer. Let's begin with the most typical argument's type: int. If an argument in c# is int, it will occupy 1+4 bytes in the packet, the front 1 stores the lable(6) of int, the next 4 bytes store the byte array converted from this argument. These type are similar to the int.

Argument Type in C# Length in Packet Content in Packet
byte 1+1 2+arg.ConvertToByteArray()
bool 1+1 3+arg.ConvertToByteArray()
ushort 1+2 4+arg.ConvertToByteArray()
short 1+2 5+arg.ConvertToByteArray()
int 1+4 6+arg.ConvertToByteArray()
float 1+4 7+arg.ConvertToByteArray()
double 1+8 8+arg.ConvertToByteArray()

string need to be payed more attention because arguments of string type have a changed length when they were converted to byte array. So, we insert a int(four bytes) to indicate this arguments' length in byte[] mode. As a result, if an argument in c# is string, it will occupy 1+4+n bytes in the packet, the front 1 stores the lable(1) of string, the next 4 bytes is a int value store the length of byte array converted from this argument, the last n store the real byte array converted from this argument. The arguments of json are as same as string.

Argument Type in C# Length in Packet Content in Packet
string 1+4+n 1+arg.ConvertToByteArray().length.ConvertToByteArray()+arg.ConvertToByteArray()
json 1+4+n 9+arg.ConvertToByteArray().length.ConvertToByteArray()+arg.ConvertToByteArray()

But we still have problem when we store arrays in packet. We need @ to do

About

A lightweight framework allows remote calls of methods and subscription of events in local c# assembly

License:MIT License


Languages

Language:C# 84.3%Language:JavaScript 15.7%