[DEV] add capability to get the data with the python timestamps

This commit is contained in:
Edouard DUPIN 2023-02-17 19:04:04 +01:00
parent f30c8d30db
commit 10d6edad5a
10 changed files with 132 additions and 26 deletions

View File

@ -22,7 +22,7 @@
<dependency>
<groupId>kangaroo-and-rabbit</groupId>
<artifactId>archidata</artifactId>
<version>0.3.1</version>
<version>0.3.3</version>
</dependency>
</dependencies>

View File

@ -80,6 +80,7 @@ public class WebLauncher {
rc.registerClasses(StateHistoryResource.class);
rc.registerClasses(LogResource.class);
rc.registerClasses(HealthCheck.class);
rc.registerClasses(Front.class);

View File

@ -13,7 +13,7 @@ import jakarta.ws.rs.core.Response.ResponseBuilder;
import org.kar.archidata.api.FrontGeneric;
import org.kar.karanage.util.ConfigVariable;
@Path("/karanage")
@Path("/front")
public class Front extends FrontGeneric {
public Front() {
this.baseFrontFolder = ConfigVariable.getFrontFolder();

View File

@ -52,7 +52,8 @@ public class LogResource {
@PathParam("system") String system,
@QueryParam("since") String since,
@QueryParam("sinceId") Integer sinceId,
@QueryParam("limit") Integer limit) throws Exception {
@QueryParam("limit") Integer limit,
@QueryParam("mode") String mode) throws Exception {
// Keep Group ID:
if (groupName == null || groupName.length() == 0) {
throw new InputException("group", "Missing URL parameter /state/{group}/...");
@ -136,7 +137,17 @@ public class LogResource {
} else {
out.append(",");
}
out.append("{ \"id\": " + data.id + ", \"time\": \"" + data.create_date.toInstant().toString() + "\", \"data\":" + data.data + "}");
out.append("{ \"id\": " + data.id + ", \"time\": ");
if ("raw".equals(mode)) {
double seconds = data.create_date.toInstant().toEpochMilli() * 0.001;
out.append(seconds);
} else {
out.append("\"");
out.append(data.create_date.toInstant().toString());
out.append("\"");
}
out.append(", \"data\":" + data.data + "}");
}
out.append("]");
return out.toString();

View File

@ -33,7 +33,8 @@ public class StateHistoryResource {
@PathParam("topic") String topic,
@QueryParam("since") String since,
@QueryParam("sinceId") Integer sinceId,
@QueryParam("limit") Integer limit) throws Exception {
@QueryParam("limit") Integer limit,
@QueryParam("mode") String mode) throws Exception {
// Keep Group ID:
if (groupName == null || groupName.length() == 0) {
throw new InputException("group", "Missing URL parameter /state/{group}/...");
@ -117,7 +118,16 @@ public class StateHistoryResource {
} else {
out.append(",");
}
out.append("{ \"id\": " + data.id + ", \"time\": \"" + data.modify_date.toInstant().toString() + "\", \"data\":" + data.data + "}");
out.append("{ \"id\": " + data.id + ", \"time\": ");
if ("raw".equals(mode)) {
double seconds = data.modify_date.toInstant().toEpochMilli() * 0.001;
out.append(seconds);
} else {
out.append("\"");
out.append(data.modify_date.toInstant().toString());
out.append("\"");
}
out.append(", \"data\":" + data.data + "}");
}
out.append("]");
return out.toString();

View File

@ -33,7 +33,8 @@ public class StateResource {
public static String getWithTopic(
@PathParam("group") String groupName,
@PathParam("topic") String topic,
@QueryParam("since") String since) throws Exception {
@QueryParam("since") String since,
@QueryParam("mode") String mode) throws Exception {
if (groupName == null || groupName.length() == 0) {
throw new InputException("group", "Missing URL parameter /state/{group}/...");
}
@ -74,7 +75,28 @@ public class StateResource {
throw new FailException(Response.Status.NOT_FOUND, "Topic does not exist: '" + topic + "'");
}
}
return "{ \"time\": \"" + data.modify_date.toInstant().toString() + "\", \"data\":" + data.data + "}";
StringBuilder out = new StringBuilder("{ \"time\": ");
if ("raw".equals(mode)) {
double seconds = data.modify_date.toInstant().toEpochMilli() * 0.001;
out.append(seconds);
return "{ \"time\": " + seconds + ", \"data\":" + data.data + "}";
} else {
out.append("\"");
out.append(data.modify_date.toInstant().toString());
out.append("\"");
}
out.append(", \"state\":");
if (data.state == null) {
out.append("null");
} else {
out.append("\"");
out.append(data.state);
out.append("\"");
}
out.append(", \"data\":");
out.append(data.data);
out.append("}");
return out.toString();
}
@GET
@ -83,7 +105,8 @@ public class StateResource {
@PermitAll
public String get(
@PathParam("group") String groupName,
@QueryParam("since") String since) throws Exception {
@QueryParam("since") String since,
@QueryParam("mode") String mode) throws Exception {
if (groupName == null || groupName.length() == 0) {
throw new InputException("group", "Missing URL parameter /state/{group}/...");
}
@ -125,7 +148,24 @@ public class StateResource {
} else {
out.append(",");
}
out.append("{ \"time\": \"" + data.modify_date.toInstant().toString() + "\", \"topic\": \"" + data.topic + "\", \"data\":" + data.data + "}");
out.append("{ \"time\": ");
if ("raw".equals(mode)) {
double seconds = data.modify_date.toInstant().toEpochMilli() * 0.001;
out.append(seconds);
} else {
out.append("\"");
out.append(data.modify_date.toInstant().toString());
out.append("\"");
}
out.append(", \"state\":");
if (data.state == null) {
out.append("null");
} else {
out.append("\"");
out.append(data.state);
out.append("\"");
}
out.append(", \"topic\": \"" + data.topic + "\", \"data\":" + data.data + "}");
}
out.append("]");
return out.toString();
@ -148,7 +188,7 @@ public class StateResource {
public Response post(
@PathParam("group") String groupName,
@PathParam("topic") String topic,
@QueryParam("state") String state,
@QueryParam("state") String state,
String dataToInsert) throws Exception {
StateInstant previous = null;

View File

@ -5,6 +5,7 @@ import json
from pathlib import Path
import subprocess
import time
from datetime import timezone
from typing import Dict, List
from karanage import (
@ -21,6 +22,8 @@ if __name__ == '__main__':
parser.add_argument("-C", "--connection", type=str, help="json configuration file")
parser.add_argument("-t", "--topic", type=str, help="Topic of the message")
parser.add_argument("-s", "--since", type=str, help="Iso date since the value time must be")
parser.add_argument("-w", "--watch", help="Display new states", action='store_true')
# This element are read from the connection file:
parser.add_argument("-u", "--url", type=str, help="Base URL of the web service")
@ -39,6 +42,14 @@ if __name__ == '__main__':
# create the rest interface of karanage
stateInterface = KaranageState(connection)
data = stateInterface.gets(topic=args.topic, since=args.since)
print(f"Ret = {json.dumps(data, indent=4)}")
# transform since in a datetime:
while True:
data = stateInterface.gets(topic=args.topic, since=args.since)
for elem in data:
print(f"{elem.topic} @ {elem.time.astimezone()} => {elem.state}");
print(json.dumps(elem.data, indent=4))
args.since = elem.time
if not args.watch:
break
else:
time.sleep(1)

View File

@ -1 +1 @@
0.5.0-dev
0.6.0-dev

View File

@ -9,8 +9,9 @@
##
import enum
import json
from typing import Dict, Optional
from typing import Dict, Optional, Union, List, NamedTuple
from datetime import datetime, timezone
import requests
from .connection import KaranageConnectionInterface
@ -22,6 +23,21 @@ class StateSystem(enum.Enum):
FAIL = "FAIL"
DOWN = "DOWN"
class StateData(NamedTuple):
topic: str
time: datetime
state: str
data: Dict
def convert_to_state_data(json_data: Dict, topic:Optional[str] = None) -> StateData:
time = datetime.fromtimestamp(json_data["time"], timezone.utc)
if topic is not None:
topic = topic
else:
topic = json_data["topic"]
return StateData(topic, time, json_data["state"], json_data["data"])
## Generic karanage sending system.
class KaranageState:
@ -53,40 +69,57 @@ class KaranageState:
f"Fail send message: '{ret.url}'", ret.status, ret.data
)
def gets(self, topic: Optional[str] = None, since: Optional[str] = None) -> Dict:
def gets(self, topic: Optional[str] = None, since: Union[None, str, datetime] = None) -> List[StateData]:
"""Get all the topic fom the server.
:param since: ISO1866 time value.
:return: A dictionary with the requested data.
"""
param = {}
param = {
"mode":"raw" # request raw mode to have the timestant in a float in second
}
if since is not None:
param["since"] = since
if since is str:
param["since"] = since
else:
param["since"] = since.replace(tzinfo=timezone.utc).isoformat()
ret = self.connection.get("state", topic, params=param)
if 200 <= ret.status <= 299:
return json.loads(ret.data)
out: List[StateData] = []
for elem in json.loads(ret.data):
out.append(convert_to_state_data(elem, topic))
return out
raise KaranageException(f"Fail get data: '{ret.url}'", ret.status, ret.data)
def get_history(
self,
topic: Optional[str] = None,
since: Optional[str] = None,
since: Union[None, str, datetime] = None,
since_id: Optional[int] = None,
limit: Optional[int] = None,
) -> Dict:
) -> List[StateData]:
"""Get all the topic fom the server.
:param since: ISO1866 time value.
:param since_id: remote BDD index of the field.
:param limit: the number of value we want to get
:return: A dictionary with the requested data.
"""
param = {}
param = {
"mode":"raw" # request raw mode to have the timestant in a float in second
}
if since is not None:
param["since"] = since
if since is str:
param["since"] = since
else:
param["since"] = since.replace(tzinfo=timezone.utc).isoformat()
if since_id is not None:
param["sinceId"] = since_id
if limit is not None:
param["limit"] = limit
ret = self.connection.get("state_history", topic, params=param)
if 200 <= ret.status <= 299:
return json.loads(ret.data)
out: List[StateData] = []
for elem in json.loads(ret.data):
out.append(convert_to_state_data(elem, topic))
return out
raise KaranageException(f"Fail get data: '{ret.url}'", ret.status, ret.data)

View File

@ -1 +1 @@
0.5.0-dev
0.6.0-dev