1 module handlers.response;
2 
3 import std.json : JSONValue, JSONException;
4 import std.conv : to;
5 import utils.debugging : debugPrint;
6 import std.string : cmp;
7 import std.stdio : writeln;
8 import connection.connection;
9 
10 /* The type of the command the message handler wants us to run */
11 private enum CommandType
12 {
13 	SEND_CLIENTS, SEND_SERVERS, SEND_HANDLER
14 }
15 
16 public final class HandlerResponse
17 {
18 	/* The message-handler's response */
19 	private JSONValue messageResponse;
20 
21 	/* The command to be executed */
22 	private CommandType commandType;
23 
24 	this(JSONValue messageResponse)
25 	{
26 		/* Set the message-handler's response message */
27 		this.messageResponse = messageResponse;
28 
29 		/* Attempt parsing the message and error checking it */
30 		parse(messageResponse);
31 	}
32 
33 	private void parse(JSONValue handlerResponse)
34 	{
35 		/**
36 		 * Handles the response sent back to the server from the
37 		 * message handler.
38 		 */
39 
40 		 /* Get the status */
41 		 ulong statusCode;
42 
43 		 /* Error? */
44 		 bool error;
45 		
46 				/* TODO: Bounds checking, type checking */
47 				try
48 				{
49 					/* Get the header block */
50 					JSONValue headerBlock = handlerResponse["header"];
51 		
52 					/* Get the status */
53 					statusCode = to!(ulong)(headerBlock["status"].str());
54 					debugPrint("Status code: " ~ to!(string)(statusCode));
55 		
56 					/* If the status is 0, then it is all fine */
57 					if(statusCode == 0)
58 					{
59 						debugPrint("Status is fine, the handler ran correctly");
60 						
61 						/* The command block */
62 						JSONValue commandBlock = headerBlock["command"];
63 						
64 						/**
65 						 * Get the command that the message handler wants the
66 						 * server to run.
67 						 */
68 						string serverCommand = commandBlock["type"].str;
69 						debugPrint("Handler->Server command: \"" ~ serverCommand ~ "\"");
70 						
71 						/* Check the command to be run */
72 						if(cmp(serverCommand, "sendClients") == 0)
73 						{
74 							/* Set the command type to SEND_CLIENTS */
75 							commandType = CommandType.SEND_CLIENTS;
76 
77 							/* TODO: Error check and do accesses JSON that would be done in `.execute` */
78 						}
79 						else if(cmp(serverCommand, "sendServers") == 0)
80 						{
81 							/* Set the command type to SEND_SERVERS */
82 							commandType = CommandType.SEND_SERVERS;
83 
84 							/* TODO: Error check and do accesses JSON that would be done in `.execute` */
85 						}
86 						else if(cmp(serverCommand, "sendHandler") == 0)
87 						{
88 							/* Set the command type to SEND_HAANDLER */
89 							commandType = CommandType.SEND_HANDLER;
90 
91 							/* TODO: Error check and do accesses JSON that would be done in `.execute` */
92 						}
93 						else
94 						{
95 							/* TODO: Error handling */
96 							debugPrint("The message handler is using an invalid command");
97 						}
98 					}
99 					else
100 					{
101 						/* If the message handler returned a response in error */
102 						debugPrint("Message handler returned an error code: " ~ to!(string)(statusCode));
103 						error = true;
104 					}
105 				}
106 				catch(JSONException exception)
107 				{
108 					debugPrint("<<< There was an error handling the response message >>>\n\n" ~ exception.toString());
109 					error = true;
110 				}
111 		
112 		if(error)
113 		{
114 			throw new ResponseError(messageResponse, statusCode);
115 		}
116 			
117 		
118 	}
119 
120 	public void execute(BesterConnection originalRequester)
121 	{
122 		/* TODO: Implement me */
123 
124 		/* If the command is SEND_CLIENTS */
125 		if(commandType == CommandType.SEND_CLIENTS)
126 		{
127 			/* Get the list of clients to send to */
128 			string[] clients;
129 			JSONValue[] clientList = messageResponse["header"]["command"]["data"].array();
130 			for(ulong i = 0; i < clientList.length; i++)
131 			{
132 				clients ~= clientList[i].str();
133 			}
134 
135 			writeln("Users wanting to send to ", clients);
136 
137 			/* Find the users that are wanting to be sent to */
138 			BesterConnection[] connectionList = originalRequester.server.getClients(clients);
139 			writeln(connectionList);
140 
141 			/* TODO: Implement me */
142 			
143 			writeln("sdafdfasd", originalRequester.server.clients[0].toString());
144 		}
145 		else if (commandType == CommandType.SEND_SERVERS)
146 		{
147 			/* Get the list of servers to send to */
148 			string[] servers;
149 			JSONValue[] serverList = messageResponse["header"]["command"]["data"].array();
150 			for(ulong i = 0; i < serverList.length; i++)
151 			{
152 				servers ~= serverList[i].str();
153 			}
154 													
155 			/* TODO: Implement me */
156 			writeln("Servers wanting to send to ", servers);
157 		}
158 		else if (commandType == CommandType.SEND_HANDLER)
159 		{
160 			/* Name of the handler to send the message to */
161 			string handler = messageResponse["header"]["command"]["data"]["handler"].str();
162 			debugPrint("Handler to forward to: " ~ handler);
163 
164 			/* TODO: Add me */
165 		}
166 	}
167 
168 	override public string toString()
169 	{
170 		return messageResponse.toPrettyString();
171 	}
172 }
173 
174 public final class ResponseError : Exception
175 {
176 	this(JSONValue messageResponse, ulong statusCode)
177 	{
178 		/* TODO: Set message afterwards again */
179 		super("");
180 	}
181 }