Skip to content

Commit 3a83d81

Browse files
authored
Merge pull request #7 from ithsjava25/model
Add model layer with NtfyConnection
2 parents 21c51e8 + 06d034f commit 3a83d81

File tree

15 files changed

+296
-15
lines changed

15 files changed

+296
-15
lines changed

.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,4 @@
11
target/
22
/.idea/
3+
.env
4+
package-lock.json

pom.xml

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,22 @@
4545
<artifactId>javafx-fxml</artifactId>
4646
<version>${javafx.version}</version>
4747
</dependency>
48+
<dependency>
49+
<groupId>tools.jackson.core</groupId>
50+
<artifactId>jackson-databind</artifactId>
51+
<version>3.0.1</version>
52+
</dependency>
53+
<dependency>
54+
<groupId>io.github.cdimascio</groupId>
55+
<artifactId>dotenv-java</artifactId>
56+
<version>3.2.0</version>
57+
</dependency>
58+
<dependency>
59+
<groupId>org.wiremock</groupId>
60+
<artifactId>wiremock</artifactId>
61+
<version>4.0.0-beta.15</version>
62+
<scope>test</scope>
63+
</dependency>
4864
</dependencies>
4965
<build>
5066
<plugins>
Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,16 @@
11
package com.example;
2-
2+
import javafx.event.ActionEvent;
33
import javafx.fxml.FXML;
44
import javafx.scene.control.Label;
5+
import javafx.scene.control.ListView;
56

67
/**
78
* Controller layer: mediates between the view (FXML) and the model.
89
*/
910
public class HelloController {
1011

11-
private final HelloModel model = new HelloModel();
12+
private final HelloModel model = new HelloModel(new NtfyConnectionImpl());
13+
public ListView<NtfyMessageDto> messageView;
1214

1315
@FXML
1416
private Label messageLabel;
@@ -18,5 +20,11 @@ private void initialize() {
1820
if (messageLabel != null) {
1921
messageLabel.setText(model.getGreeting());
2022
}
23+
messageView.setItems(model.getMessages());
24+
25+
}
26+
27+
public void sendMessage(ActionEvent actionEvent) {
28+
model.sendMessage();
2129
}
2230
}

src/main/java/com/example/HelloFX.java

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
package com.example;
2-
32
import javafx.application.Application;
43
import javafx.fxml.FXMLLoader;
54
import javafx.scene.Parent;
@@ -13,7 +12,7 @@ public void start(Stage stage) throws Exception {
1312
FXMLLoader fxmlLoader = new FXMLLoader(HelloFX.class.getResource("hello-view.fxml"));
1413
Parent root = fxmlLoader.load();
1514
Scene scene = new Scene(root, 640, 480);
16-
stage.setTitle("Hello MVC");
15+
stage.setTitle("Chatt Client");
1716
stage.setScene(scene);
1817
stage.show();
1918
}
Lines changed: 44 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,56 @@
11
package com.example;
2+
import javafx.application.Platform;
3+
import javafx.beans.property.SimpleStringProperty;
4+
import javafx.beans.property.StringProperty;
5+
import javafx.collections.FXCollections;
6+
import javafx.collections.ObservableList;
7+
28

39
/**
410
* Model layer: encapsulates application data and business logic.
511
*/
612
public class HelloModel {
13+
14+
private final NtfyConnection connection;
15+
16+
private final ObservableList<NtfyMessageDto> messages = FXCollections.observableArrayList();
17+
private final StringProperty messageToSend = new SimpleStringProperty();
18+
19+
public HelloModel(NtfyConnection connection) {
20+
this.connection = connection;
21+
receiveMessage();
22+
}
23+
24+
25+
public ObservableList<NtfyMessageDto> getMessages() {
26+
return messages;
27+
}
28+
29+
public String getMessageToSend() {
30+
return messageToSend.get();
31+
}
32+
33+
public StringProperty messageToSendProperty() {
34+
return messageToSend;
35+
}
36+
37+
public void setMessageToSend(String message) {
38+
messageToSend.set(message);
39+
}
40+
741
/**
842
* Returns a greeting based on the current Java and JavaFX versions.
943
*/
1044
public String getGreeting() {
11-
String javaVersion = System.getProperty("java.version");
12-
String javafxVersion = System.getProperty("javafx.version");
13-
return "Hello, JavaFX " + javafxVersion + ", running on Java " + javaVersion + ".";
45+
return "Chat Client by Adam";
46+
}
47+
48+
public void sendMessage() {
49+
connection.send(messageToSend.get());
50+
51+
}
52+
53+
public void receiveMessage() {
54+
connection.receive(m->Platform.runLater(()->messages.add(m)));
1455
}
1556
}
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
package com.example;
2+
3+
public class ManyParameters {
4+
5+
public ManyParameters(String computerName, int timeout, String method, int size, byte[] data){
6+
7+
}
8+
9+
static void main(){
10+
ManyParametersBuilder builder = new ManyParametersBuilder();
11+
builder
12+
.setComputerName("localhost") // Fluent API
13+
.setTimeout(10)
14+
.setSize(0)
15+
.createManyParameters();
16+
}
17+
}
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
package com.example;
2+
3+
public class ManyParametersBuilder {
4+
private String computerName;
5+
private int timeout = 0;
6+
private String method;
7+
private int size = 0;
8+
private byte[] data = null;
9+
10+
public ManyParametersBuilder setComputerName(String computerName) {
11+
this.computerName = computerName;
12+
return this;
13+
}
14+
15+
public ManyParametersBuilder setTimeout(int timeout) {
16+
this.timeout = timeout;
17+
return this;
18+
}
19+
20+
public ManyParametersBuilder setMethod(String method) {
21+
this.method = method;
22+
return this;
23+
}
24+
25+
public ManyParametersBuilder setSize(int size) {
26+
this.size = size;
27+
return this;
28+
}
29+
30+
public ManyParametersBuilder setData(byte[] data) {
31+
this.data = data;
32+
return this;
33+
}
34+
35+
public ManyParameters createManyParameters() {
36+
return new ManyParameters(computerName, timeout, method, size, data);
37+
}
38+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
package com.example;
2+
3+
import java.util.function.Consumer;
4+
5+
public interface NtfyConnection {
6+
public boolean send(String message);
7+
8+
public void receive(Consumer<NtfyMessageDto> messageHandler);
9+
}
Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
package com.example;
2+
import io.github.cdimascio.dotenv.Dotenv;
3+
import tools.jackson.databind.ObjectMapper;
4+
import java.io.IOException;
5+
import java.net.URI;
6+
import java.net.http.HttpClient;
7+
import java.net.http.HttpRequest;
8+
import java.net.http.HttpResponse;
9+
import java.util.Objects;
10+
import java.util.function.Consumer;
11+
12+
public class NtfyConnectionImpl implements NtfyConnection {
13+
14+
private final HttpClient http = HttpClient.newHttpClient();
15+
private final String hostName;
16+
private final ObjectMapper mapper = new ObjectMapper();
17+
18+
NtfyConnectionImpl(){
19+
Dotenv dotenv = Dotenv.load();
20+
hostName = Objects.requireNonNull(dotenv.get("HOST_NAME"));
21+
}
22+
23+
public NtfyConnectionImpl(String hostName){
24+
this.hostName = hostName;
25+
}
26+
27+
@Override
28+
public boolean send(String message) {
29+
HttpRequest httpRequest = HttpRequest.newBuilder()
30+
.POST(HttpRequest.BodyPublishers.ofString(message))
31+
.uri(URI.create(hostName + "/mytopic"))
32+
.build();
33+
try {
34+
// TODO: handle long blocking send requests to not freeze the JavaFX thread
35+
// 1. Use thread send message?
36+
// 2. Use async?
37+
var response = http.send(httpRequest, HttpResponse.BodyHandlers.ofString());
38+
return true;
39+
} catch (IOException e) {
40+
System.out.println("Error sending message");
41+
} catch (InterruptedException e) {
42+
System.out.println("Interrupted sending message");
43+
}
44+
return false;
45+
}
46+
47+
@Override
48+
public void receive(Consumer<NtfyMessageDto> messageHandler) {
49+
HttpRequest httpRequest = HttpRequest.newBuilder()
50+
.GET()
51+
.uri(URI.create(hostName + "/mytopic/json?since=wBuD2KGEaAe0"))
52+
.build();
53+
54+
http.sendAsync(httpRequest, HttpResponse.BodyHandlers.ofLines())
55+
.thenAccept(response -> response.body()
56+
.map(s->
57+
mapper.readValue(s, NtfyMessageDto.class))
58+
.filter(message -> message.event().equals("message"))
59+
.peek(System.out::println)
60+
.forEach(messageHandler));
61+
}
62+
}
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
package com.example;
2+
3+
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
4+
5+
@JsonIgnoreProperties(ignoreUnknown = true)
6+
public record NtfyMessageDto(String id, long time, String event, String topic, String message) {}

0 commit comments

Comments
 (0)