-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathtest.java
More file actions
280 lines (237 loc) · 12.8 KB
/
Copy pathtest.java
File metadata and controls
280 lines (237 loc) · 12.8 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
import java.util.*;
import java.lang.reflect.*;
import java.nio.charset.StandardCharsets;
import java.nio.file.*;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.net.*;
import java.io.*;
//Command Codes:
//a: method invocation requests
//b: outputs or errors that needs to be returned to invocator
//c: left by this program at the last point of the file upto where it has read all requests
//Json Requests/Outputs Format:
//{"index":"1", "command code":"a", "method":"GreetingFunction-strhello"}
//
//EXPLANATION:- index is the index, command codes are discussed above, methods are like 'method_name' and then separate their parameters
//through a dash or a hyphen '-' and on the next side write the parameter value's class and then the value like
//'str' or 'string' for and then without space or any delimeter add the value. Same goes with 'int' for integer values such as
//'int8080' meaning '8080' is an integer class and then it could be handled accordingly here. These codes are safe with custom
//functions to differentiate b/w class IDs and their values efficiently and the the overall system can be changed according
//to your needs. Refer to this document for more info: //add the link to the document
class Program{
//store all method names here in order to not check it again and again if needed multiple times.
private static final Set<String> METHOD_NAMES = new HashSet<>();
//run a static code block in the starting of the program to cache all the methods in the script and save them in the
//above variable.
static{
// Populate method names once during initialization
for (java.lang.reflect.Method method: Program.class.getDeclaredMethods()){
METHOD_NAMES.add(method.getName());
}
}
//Json file REF that we're gonna check the method requests in
public static String methodInvocReq_Path_String = "command_Invoc_Requests.json";
//return value along with their datatype
public static String returnValue = "--$null";
//create a log file in the same directory in order to store logs or function outputs and errors.
public static void CreateLogFile(String name){
//try to create a .txt file with the name passed as an argument
try{
String logFilePathStr = "C:/Users/DESKTOP-A/Desktop/test-environment/" + name + ".txt";
Path logFilePath = Paths.get(logFilePathStr);
Files.writeString(logFilePath, "" + System.lineSeparator(),
StandardOpenOption.CREATE, StandardOpenOption.APPEND);
}
catch (IOException e){
System.out.println("Error in creating file: " + e.getMessage());
}
}
//write in log file function's overload
public static void WriteInLogs(String line){
WriteInLogs("LFTUCPCLogs", line, "PRO");
}
//write in log txt file with the time and the date and the log code of a line.
//call this directly to create a log file (if not already there) and then write in it as normal
public static void WriteInLogs(String name, String line, String logCode) {
try {
String baseDir = "C:/Users/DESKTOP-A/Desktop/test-environment/";
Path dirPath = Paths.get(baseDir);
if (!Files.exists(dirPath)) {
Files.createDirectories(dirPath);
}
Path logFilePath = dirPath.resolve(name + ".txt");
LocalDateTime now = LocalDateTime.now();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("HH:mm:ss - dd/MM/yyyy");
String dateAndTimeFormatted = now.format(formatter);
String finalLine = logCode + " ~ " + dateAndTimeFormatted + " =>\t" + line;
Files.writeString(logFilePath, finalLine + System.lineSeparator(),
StandardOpenOption.CREATE, StandardOpenOption.APPEND);
} catch (IOException e) {
System.out.println("Error writing to log file: " + e.getMessage());
}
}
//parse the data and convert it to its right type with the help of its data class part sent with the value (ex: int8080 for 'int' '8080')
public static Object ParseDataType(String RawParameter){
//parse data into the data class and save it in java
if(RawParameter.startsWith("string")){
return RawParameter.substring("string".length());
}
else if(RawParameter.startsWith("int")){
return Integer.parseInt(RawParameter.substring("int".length()));
}
else if(RawParameter.startsWith("float")){
return Float.parseFloat(RawParameter.substring("float".length()));
}
else if(RawParameter.startsWith("bool")){
if (RawParameter.substring("bool".length()).toLowerCase() == "true"){
return true;
}else{
return false;
}
}
return null;
}
//custom function for finding out if our string starts with any of the available prefixes that are provided through the parameters
private static boolean StartsWithAny(String string, String... prefixes){
for (String prefix : prefixes){
if(string.startsWith(prefix)){
return true;
}
}
return false;
}
//return just the class of a value according to its passed datatype code
public static Class<?> ParseDataClass(String RawParameter){
//Map to transform inputs given to a signature of Java Language and then use it
if(StartsWithAny(RawParameter, "string", "str")){
return String.class;
}
else if(RawParameter.startsWith("int")){
return int.class;
}
else if(RawParameter.startsWith("float")){
return float.class;
}
else if(StartsWithAny(RawParameter, "bool", "boolean")){//custom function to check if a string has any one of the given prefixes
return boolean.class;
}
return null;
}
//this method checks if the input is in the right format ("method_Name-(datatype.value),(datatype.value),...")
public static void RunMethod(String arg){
//check if the method sent through argument has a parameters
if(arg.contains("-")){
//if the argument has parameters according to the structure, then extract it
String[] splice_of_arg = arg.trim().split("-");
//extract the method name from if arg conatins parameters
String methodName = splice_of_arg[0];
// extract the string that has all the parameters like stringarg,int80,float80.0
String methodParameterSplice = splice_of_arg[1];
//initialize a list to contain all parameters separtely
List<Object> parsedParams = new ArrayList<>();
//store theclass of the parameters separetely in same order
List<Class<?>> paramTypes = new ArrayList<>(); // Added to track parameter types
//check if there are any parameters. (if yes) then are there are multiple of them.
boolean containsParams = (methodParameterSplice.length() > 0)? true : false;
boolean multipleParams = (containsParams)? ((methodParameterSplice.contains(","))? true: false) : false;
//check if method asked for exists
if(METHOD_NAMES.contains(methodName)){
//check if arg passed contains any parameter(s) for this method
if(containsParams){
//check if multiple parameters are passed and launch the method accordingly
if(multipleParams){
//split the parameters through (,) delimeter and save them separately
String[] methodParameters = methodParameterSplice.split(",");
for (String param: methodParameters){
//add parsed data to the parameters list
parsedParams.add(ParseDataType(param));
//add class of the parsed parameters to the class list
paramTypes.add(ParseDataClass(param));
}
//print all passed parameters for debugging
System.out.println("Method Params: " + parsedParams);
}
//take the one and only parameter and save it to launch themethod accordingly
else{
parsedParams.add(ParseDataType(methodParameterSplice));
//print all passed parameters for debugging
System.out.println("Method Param: " + parsedParams);
}
//the saved parameters whether multiple or single doesn't make a difference
try {
Method method = Program.class.getDeclaredMethod(methodName, paramTypes.toArray(new Class[0]));
method.invoke(null, parsedParams.toArray());
} catch (Exception e) {
System.out.println("Error invoking " + methodName + ": " + e.getMessage());
WriteInLogs("LFTUCPCLogs", "Error invoking " + methodName + ": " + e.getMessage(), "ERR");
}
}else{
System.out.println("No parameter.");
//now launching the method with no parameters
try {
Method method = Program.class.getDeclaredMethod(methodName); // No paramTypes needed
method.invoke(null); // No parameters passed
} catch (Exception e) {
System.out.println("Error invoking " + methodName + ": " + e.getMessage());
WriteInLogs("LFTUCPCLogs", "Error invoking " + methodName + ": " + e.getMessage(), "ERR");
}
}
}
}else{
System.out.println("Java running: No Method");
}
}
//**entry point**//
//ENTRY POINT of the program (this code block runs as the start point of the script because it has the 'main' method signature as the name).
public static void main(String[] args) {
if (args.length != 0) {
int port;
try {
port = Integer.parseInt(args[0]);
WriteInLogs("port: " + port);
} catch (Exception ex) {
port = 54321; // fallback port
WriteInLogs("Can't parse port: " + ex);
}
try (ServerSocket serverSocket = new ServerSocket(port)) {
WriteInLogs("Server started on port " + port);
while (true) {
Socket clientSocket = serverSocket.accept(); // Accept client connection
WriteInLogs("Client connected: " + clientSocket.getRemoteSocketAddress());
// Setup input and output streams for the client
BufferedReader reader = new BufferedReader(new InputStreamReader(clientSocket.getInputStream(), StandardCharsets.UTF_8));
PrintWriter output = new PrintWriter(new OutputStreamWriter(clientSocket.getOutputStream(), StandardCharsets.UTF_8), true);
String message;
// Read bytes in a loop
while ((message = reader.readLine()) != null) {
WriteInLogs("Received from client: " + message);
RunMethod(message);
output.println(returnValue);
if ("exit".equalsIgnoreCase(message)) {
WriteInLogs("Client requested exit.");
break;
}
}
clientSocket.close();
WriteInLogs("Client disconnected.");
System.exit(0);
}
} catch (IOException e) {
WriteInLogs("Server exception: " + e.getMessage());
}
} else {
WriteInLogs("No port argument provided.");
}
}
//method created to call for checking if the system is working as expected or not
public static void StartLFTUCServer(String IPAddress, int port){
StartLFTUCServer(IPAddress, port, 94.26f, true);
}
public static void StartLFTUCServer(String IPAddress, int port, float swim, boolean lmao){
String message = "\nStarting Server At: " + IPAddress + ":" + port + "/" + swim + "\\" + lmao;
returnValue = message;
System.out.println(message);
WriteInLogs(message);
}
}