Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,11 @@ public class OlogHttpClient implements LogClient {
private static final String OLOG_CLIENT_INFO_HEADER = "X-Olog-Client-Info";
private static final String CLIENT_INFO =
"CS Studio " + Messages.AppVersion + " on " + System.getProperty("os.name");
/**
* Each endpoint needs this as by default the service's context path is /, but all
* API endpoints are prefixed with <code>Olog</code>.
*/
public static final String OLOG_PREFIX = "/Olog";

private static final Logger LOGGER = Logger.getLogger(OlogHttpClient.class.getName());
private final List<LogEntryChangeHandler> changeHandlers = new ArrayList<>();
Expand Down Expand Up @@ -182,7 +187,7 @@ private LogEntry save(LogEntry log, LogEntry inReplyTo) throws LogbookException
}

HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/logs/multipart?" + QueryParamsHelper.mapToQueryParams(queryParams)))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/logs/multipart?" + QueryParamsHelper.mapToQueryParams(queryParams)))
.header("Content-Type", httpRequestMultipartBody.getContentType())
.header(OLOG_CLIENT_INFO_HEADER, CLIENT_INFO)
.header("Authorization", basicAuthenticationHeader)
Expand Down Expand Up @@ -225,7 +230,7 @@ public LogEntry getLog(Long logId) {
@Override
public LogEntry findLogById(Long logId) {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/logs/" + logId))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/logs/" + logId))
.header("Content-Type", CONTENT_TYPE_JSON)
.GET()
.build();
Expand All @@ -252,7 +257,7 @@ public List<LogEntry> findLogs(Map<String, String> map) {
*/
private SearchResult findLogs(MultivaluedMap<String, String> searchParams) throws RuntimeException {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url +
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX +
"/logs/search?" + QueryParamsHelper.mapToQueryParams(searchParams)))
.header(OLOG_CLIENT_INFO_HEADER, CLIENT_INFO)
.header("Content-Type", CONTENT_TYPE_JSON)
Expand Down Expand Up @@ -311,7 +316,7 @@ public LogEntry update(LogEntry logEntry) {

try {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/logs/" + logEntry.getId() + "?markup=commonmark"))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/logs/" + logEntry.getId() + "?markup=commonmark"))
.header("Content-Type", CONTENT_TYPE_JSON)
.header("Authorization", basicAuthenticationHeader)
.POST(HttpRequest.BodyPublishers.ofString(OlogObjectMappers.logEntrySerializer.writeValueAsString(logEntry)))
Expand Down Expand Up @@ -345,7 +350,7 @@ public SearchResult search(Map<String, String> map) {
public void groupLogEntries(List<Long> logEntryIds) throws LogbookException {
try {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/logs/group"))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/logs/group"))
.header("Content-Type", CONTENT_TYPE_JSON)
.header("Authorization", basicAuthenticationHeader)
.POST(HttpRequest.BodyPublishers.ofString(OlogObjectMappers.logEntrySerializer.writeValueAsString(logEntryIds)))
Expand All @@ -371,7 +376,7 @@ public void groupLogEntries(List<Long> logEntryIds) throws LogbookException {
* @return An {@link AuthenticationStatus} to indicate the outcome of the login attempt.
*/
public AuthenticationStatus authenticate(String userName, String password) {
String stringBuilder = Preferences.olog_url +
String stringBuilder = Preferences.olog_url + OLOG_PREFIX +
"/login";
try {
HttpRequest request = HttpRequest.newBuilder()
Expand Down Expand Up @@ -400,7 +405,7 @@ public AuthenticationStatus authenticate(String userName, String password) {
@Override
public String serviceInfo() {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX))
.header("Content-Type", CONTENT_TYPE_JSON)
.GET()
.build();
Expand Down Expand Up @@ -428,7 +433,7 @@ public Collection<LogEntry> listLogs() {
@Override
public Collection<Logbook> listLogbooks() {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/logbooks"))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/logbooks"))
.header("Content-Type", CONTENT_TYPE_JSON)
.GET()
.build();
Expand All @@ -445,7 +450,7 @@ public Collection<Logbook> listLogbooks() {
@Override
public Collection<Tag> listTags() {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/tags"))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/tags"))
.header("Content-Type", CONTENT_TYPE_JSON)
.GET()
.build();
Expand All @@ -462,7 +467,7 @@ public Collection<Tag> listTags() {
@Override
public Collection<Property> listProperties() {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/properties"))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/properties"))
.header("Content-Type", CONTENT_TYPE_JSON)
.GET()
.build();
Expand All @@ -481,7 +486,7 @@ public Collection<Property> listProperties() {
public InputStream getAttachment(Long logId, String attachmentName) {
try {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/logs/attachments/" + logId + "/" +
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/logs/attachments/" + logId + "/" +
URLEncoder.encode(attachmentName, StandardCharsets.UTF_8).replace("+", "%20"))) // + char does not work in path element!
.GET()
.build();
Expand All @@ -506,7 +511,7 @@ public InputStream getAttachment(Long logId, String attachmentName) {
public SearchResult getArchivedEntries(long id) {

HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url +
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX +
"/logs/archived/" + id))
.header(OLOG_CLIENT_INFO_HEADER, CLIENT_INFO)
.header("Content-Type", CONTENT_TYPE_JSON)
Expand All @@ -527,7 +532,7 @@ public SearchResult getArchivedEntries(long id) {
public Collection<LogTemplate> getTemplates() {

HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url +
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX +
"/templates"))
.header("Content-Type", CONTENT_TYPE_JSON)
.GET()
Expand All @@ -554,7 +559,7 @@ public LogTemplate saveTemplate(LogTemplate template) throws LogbookException {

try {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/templates"))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/templates"))
.header("Content-Type", CONTENT_TYPE_JSON)
.header("Authorization", basicAuthenticationHeader)
.PUT(HttpRequest.BodyPublishers.ofString(OlogObjectMappers.logEntrySerializer.writeValueAsString(template)))
Expand All @@ -575,7 +580,7 @@ public LogTemplate saveTemplate(LogTemplate template) throws LogbookException {
@Override
public Collection<LogEntryLevel> listLevels() {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(Preferences.olog_url + "/levels"))
.uri(URI.create(Preferences.olog_url + OLOG_PREFIX + "/levels"))
.GET()
.build();

Expand Down
13 changes: 12 additions & 1 deletion app/logbook/olog/ui/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,14 @@
</dependency>
<dependency>
<groupId>org.phoebus</groupId>
<artifactId>core-websocket</artifactId>
<artifactId>core-websocket-common</artifactId>
<version>5.0.3-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.phoebus</groupId>
<artifactId>core-websocket-client</artifactId>
<version>5.0.3-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.phoebus</groupId>
<artifactId>core-ui</artifactId>
Expand Down Expand Up @@ -60,6 +65,12 @@
<version>9.0-r1</version>
</dependency>

<dependency>
<groupId>javax.json</groupId>
<artifactId>javax.json-api</artifactId>
<version>1.1.2</version>
</dependency>

<!-- https://mvnrepository.com/artifact/com.atlassian.commonmark/commonmark -->
<dependency>
<groupId>com.atlassian.commonmark</groupId>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,7 @@ public LogEntryCalenderViewController(LogClient logClient, OlogQueryManager olog

@FXML
public void initialize() {
super.initialize();

advancedSearchViewController.setSearchCallback(this::search);
configureComboBox();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@
import javafx.util.Duration;
import javafx.util.StringConverter;
import org.phoebus.applications.logbook.authentication.OlogAuthenticationScope;
import org.phoebus.core.websocket.WebSocketMessageHandler;
import org.phoebus.core.websocket.client.WebSocketMessageHandler;
import org.phoebus.framework.jobs.JobManager;
import org.phoebus.logbook.LogClient;
import org.phoebus.logbook.LogEntry;
Expand All @@ -69,7 +69,6 @@
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.TimeZone;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.logging.Level;
import java.util.logging.Logger;
Expand Down Expand Up @@ -176,6 +175,7 @@ protected void setGoBackAndGoForwardActions(LogEntryTable.GoBackAndGoForwardActi

@FXML
public void initialize() {
super.initialize();

logEntryDisplayController.setLogEntryTableViewController(this);

Expand Down
Original file line number Diff line number Diff line change
@@ -1,26 +1,29 @@
package org.phoebus.logbook.olog.ui;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.module.SimpleModule;
import javafx.application.Platform;
import javafx.beans.property.ObjectProperty;
import javafx.beans.property.SimpleBooleanProperty;
import javafx.beans.property.SimpleObjectProperty;
import javafx.fxml.FXML;
import javafx.scene.layout.GridPane;
import javafx.scene.layout.VBox;
import org.phoebus.core.websocket.WebSocketMessageHandler;
import org.phoebus.core.websocket.springframework.WebSocketClientService;
import org.phoebus.core.websocket.client.WebSocketMessageHandler;
import org.phoebus.core.websocket.common.Constants;
import org.phoebus.core.websocket.common.WebSocketMessage;
import org.phoebus.core.websocket.client.WebSocketClientService;
import org.phoebus.framework.jobs.Job;
import org.phoebus.framework.jobs.JobManager;
import org.phoebus.logbook.LogClient;
import org.phoebus.logbook.LogEntry;
import org.phoebus.logbook.SearchResult;
import org.phoebus.logbook.olog.ui.websocket.MessageType;
import org.phoebus.logbook.olog.ui.websocket.WebSocketMessage;
import org.phoebus.logbook.olog.ui.websocket.LogbookMessageType;
import org.phoebus.logbook.olog.ui.websocket.LogbookWebSocketMessageDeserializer;
import org.phoebus.olog.es.api.Preferences;

import java.net.URI;
import java.util.List;
import java.util.Map;
import java.util.concurrent.CountDownLatch;
Expand Down Expand Up @@ -57,9 +60,8 @@ public abstract class LogbookSearchController implements WebSocketMessageHandler
new SimpleObjectProperty<>(ConnectivityMode.NOT_CONNECTED);

protected WebSocketClientService webSocketClientService;
private final String webSocketConnectUrl;
private final String subscriptionEndpoint;
protected final CountDownLatch connectivityCheckerCountDownLatch = new CountDownLatch(1);
private String webSocketConnectUrl;

@SuppressWarnings("unused")
@FXML
Expand All @@ -69,36 +71,32 @@ public abstract class LogbookSearchController implements WebSocketMessageHandler
@FXML
private GridPane viewSearchPane;

public LogbookSearchController() {
String baseUrl = Preferences.olog_url;
URI uri = URI.create(baseUrl);
String scheme = uri.getScheme();
String host = uri.getHost();
int port = uri.getPort();
String path = uri.getPath();
if (path.endsWith("/")) {
path = path.substring(0, path.length() - 1);
}
String webSocketScheme = scheme.toLowerCase().startsWith("https") ? "wss" : "ws";
this.webSocketConnectUrl = webSocketScheme + "://" + host + (port > -1 ? (":" + port) : "") + path + "/web-socket";
this.subscriptionEndpoint = path + "/web-socket/messages";
@FXML
public void initialize() {
SimpleModule module = new SimpleModule();
module.addDeserializer(WebSocketMessage.class, new LogbookWebSocketMessageDeserializer(WebSocketMessage.class));
objectMapper.registerModule(module);
webSocketConnectUrl = Preferences.olog_url.trim().toLowerCase().startsWith("https://") ?
Preferences.olog_url.trim().replace("https", "wss") :
Preferences.olog_url.trim().replace("http", "ws");
webSocketConnectUrl += "/Olog" + Constants.WEB_SOCKET;
}

/**
* Determines how the client may connect to the remote service. The service info endpoint is called to establish
* availability of the service. If available, then a single web socket connection is attempted to determine
* if the service supports web sockets.
*
* @param consumer {@link Consumer} called when the connectivity mode has been determined.
*/
protected void determineConnectivity(Consumer<ConnectivityMode> consumer){

protected void determineConnectivity(Consumer<ConnectivityMode> consumer) {
// Try to determine the connection mode: is the remote service available at all?
// If so, does it accept web socket connections?
JobManager.schedule("Connection mode probe", monitor -> {
ConnectivityMode connectivityMode = ConnectivityMode.NOT_CONNECTED;
String serviceInfo = client.serviceInfo();
if (serviceInfo != null && !serviceInfo.isEmpty()) { // service online, check web socket availability
if (WebSocketClientService.checkAvailability(this.webSocketConnectUrl)) {
if (WebSocketClientService.checkAvailability(webSocketConnectUrl)) {
connectivityMode = ConnectivityMode.WEB_SOCKETS_SUPPORTED;
} else {
connectivityMode = ConnectivityMode.HTTP_ONLY;
Expand Down Expand Up @@ -184,8 +182,7 @@ public void shutdown() {
Logger.getLogger(LogbookSearchController.class.getName()).log(Level.INFO, "Shutting down web socket");
webSocketClientService.removeWebSocketMessageHandler(this);
webSocketClientService.shutdown();
}
else if(connectivityModeObjectProperty.get().equals(ConnectivityMode.HTTP_ONLY)){
} else if (connectivityModeObjectProperty.get().equals(ConnectivityMode.HTTP_ONLY)) {
cancelPeriodSearch();
}
}
Expand All @@ -204,16 +201,17 @@ protected void connectWebSocket() {
webSocketConnected.set(false);
viewSearchPane.visibleProperty().set(false);
errorPane.visibleProperty().set(true);
}, webSocketConnectUrl, subscriptionEndpoint, null);
}, webSocketConnectUrl);
webSocketClientService.addWebSocketMessageHandler(this);
webSocketClientService.connect();
}

@Override
public void handleWebSocketMessage(String message) {
try {
WebSocketMessage webSocketMessage = objectMapper.readValue(message, WebSocketMessage.class);
if (webSocketMessage.messageType().equals(MessageType.NEW_LOG_ENTRY)) {
WebSocketMessage<?> webSocketMessage = objectMapper.readValue(message, new TypeReference<>() {
});
if (webSocketMessage.messageType().equals(LogbookMessageType.NEW_LOG_ENTRY)) {
// Add a random sleep 0 - 5 seconds to avoid an avalanche of search requests on the service.
long randomSleepTime = Math.round(5000 * Math.random());
try {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,12 @@

package org.phoebus.logbook.olog.ui.websocket;

public enum MessageType {
import org.phoebus.core.websocket.common.MessageType;

/**
* Web socket message types particular to the logbook
*/
public enum LogbookMessageType implements MessageType {
NEW_LOG_ENTRY,
LOG_ENTRY_UPDATED,
SHOW_BANNER
Expand Down
Loading