Skip to content

Commit b8bc0a1

Browse files
vladcheckTimur Gauzhaev
andauthored
Gauzhaevt/version1: Интеграция Dto, разделение слоев API и UI (#2)
Co-authored-by: Timur Gauzhaev <gaujaev.to@vbtec.ru>
1 parent 049902a commit b8bc0a1

30 files changed

Lines changed: 963 additions & 168 deletions

‎pom.xml‎

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -26,14 +26,12 @@
2626
<dependency>
2727
<groupId>com.fasterxml.jackson.core</groupId>
2828
<artifactId>jackson-databind</artifactId>
29-
<version>2.18.11</version>
29+
<version>2.18.8</version>
3030
</dependency>
31-
32-
<!-- 2. Модуль Jackson для поддержки дат (LocalDateTime) -->
3331
<dependency>
3432
<groupId>com.fasterxml.jackson.datatype</groupId>
3533
<artifactId>jackson-datatype-jsr310</artifactId>
36-
<version>2.17.0</version>
34+
<version>2.18.8</version>
3735
</dependency>
3836
<dependency>
3937
<groupId>org.testfx</groupId>

‎src/main/java/com/DesktopApplicationClientJava/Api/ApiClient.java‎

Lines changed: 108 additions & 136 deletions
Large diffs are not rendered by default.
Lines changed: 88 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,90 @@
11
package com.DesktopApplicationClientJava.Api;
22

3-
public class ApiConfig {}
3+
import java.io.IOException;
4+
import java.io.InputStream;
5+
import java.util.Properties;
6+
7+
public final class ApiConfig {
8+
9+
private static final Properties PROPS = new Properties();
10+
11+
static {
12+
try (InputStream in = ApiConfig.class.getResourceAsStream("/api.properties")) {
13+
if (in == null) {
14+
throw new IllegalStateException("api.properties not found on classpath");
15+
}
16+
PROPS.load(in);
17+
} catch (IOException e) {
18+
throw new ExceptionInInitializerError(e);
19+
}
20+
}
21+
22+
private ApiConfig() {}
23+
24+
public static String baseUrl() {
25+
return required("api.baseUrl");
26+
}
27+
28+
public static long connectTimeoutMs() {
29+
return Long.parseLong(required("api.connectTimeoutMs"));
30+
}
31+
32+
public static long readTimeoutMs() {
33+
return Long.parseLong(required("api.readTimeoutMs"));
34+
}
35+
36+
public static String pathLogin() {
37+
return required("api.path.login");
38+
}
39+
40+
public static String pathRefresh() {
41+
return required("api.path.refresh");
42+
}
43+
44+
public static String pathLogout() {
45+
return required("api.path.logout");
46+
}
47+
48+
public static String pathMe() {
49+
return required("api.path.me");
50+
}
51+
52+
public static String pathResource() {
53+
return required("api.path.resource");
54+
}
55+
56+
public static String pathAdmin() {
57+
return required("api.path.admin");
58+
}
59+
60+
public static String pathExportUsers() {
61+
return required("api.path.export.users");
62+
}
63+
64+
public static String pathExportResources() {
65+
return required("api.path.export.resources");
66+
}
67+
68+
/** /api/v1/admin/resource/{uuid}/files/export */
69+
public static String pathExportResourceFiles(String resourceId) {
70+
return pathAdmin() + "/resource/" + resourceId + "/files/export";
71+
}
72+
73+
/** /api/v1/resource/{uuid}/file */
74+
public static String pathResourceFiles(String resourceId) {
75+
return pathResource() + "/" + resourceId + "/file";
76+
}
77+
78+
/** /api/v1/resource/{uuid}/file/{fileId} */
79+
public static String pathResourceFile(String resourceId, String fileId) {
80+
return pathResource() + "/" + resourceId + "/file/" + fileId;
81+
}
82+
83+
private static String required(String key) {
84+
String value = PROPS.getProperty(key);
85+
if (value == null || value.isBlank()) {
86+
throw new IllegalStateException("Missing config property: " + key);
87+
}
88+
return value;
89+
}
90+
}
Lines changed: 33 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
package com.DesktopApplicationClientJava;
22

3+
import com.DesktopApplicationClientJava.Api.ApiClient;
4+
import com.DesktopApplicationClientJava.navigation.Navigator;
5+
import com.DesktopApplicationClientJava.services.ServiceRegistry;
36
import com.DesktopApplicationClientJava.session.Session;
47
import com.DesktopApplicationClientJava.utils.ControllerWiring;
58
import java.io.IOException;
@@ -10,29 +13,50 @@
1013
import javafx.stage.Stage;
1114

1215
public class Program extends Application {
16+
private static final String INITIAL_PAGE_PATH = "/fxml/Search.fxml";
17+
private static final double WINDOW_WIDTH = 800.0;
18+
private static final double WINDOW_HEIGHT = 600.0;
19+
1320
private final Session session = new Session();
14-
private static final double windowWidthPx = 400.0;
15-
private static final double windowHeightPx = 400.0;
21+
private final ApiClient apiClient = new ApiClient(session);
22+
private final ServiceRegistry services = new ServiceRegistry(apiClient, session);
23+
24+
public static void main(String[] args) {
25+
launch(args);
26+
}
1627

1728
@Override
1829
public void start(Stage stage) throws IOException {
19-
FXMLLoader loader = new FXMLLoader(getClass().getResource("/fxml/LoginForm.fxml"));
30+
Navigator navigator = new Navigator(stage, session, services);
31+
32+
FXMLLoader loader = new FXMLLoader(getClass().getResource(INITIAL_PAGE_PATH));
33+
loader.setControllerFactory(
34+
clazz -> {
35+
try {
36+
Object controller = clazz.getDeclaredConstructor().newInstance();
37+
ControllerWiring.wire(controller, navigator, session, services);
38+
return controller;
39+
} catch (Exception e) {
40+
throw new RuntimeException("Cannot create controller: " + clazz, e);
41+
}
42+
});
43+
2044
Parent root = loader.load();
2145
Scene scene = new Scene(root);
2246
loadStyleSheet(scene, "/styles.css");
2347

24-
ControllerWiring.wire(loader.getController(), stage, session);
25-
2648
stage.setScene(scene);
2749
stage.setTitle("JavaFX Application");
28-
stage.setWidth(windowWidthPx);
29-
stage.setHeight(windowHeightPx);
50+
stage.setWidth(WINDOW_WIDTH);
51+
stage.setHeight(WINDOW_HEIGHT);
3052
stage.centerOnScreen();
31-
3253
stage.show();
3354
}
3455

3556
private void loadStyleSheet(Scene scene, String path) {
36-
scene.getStylesheets().add(getClass().getResource(path).toExternalForm());
57+
var url = getClass().getResource(path);
58+
if (url != null) {
59+
scene.getStylesheets().add(url.toExternalForm());
60+
}
3761
}
3862
}

‎src/main/java/com/DesktopApplicationClientJava/controllers/LoginFormController.java‎

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
package com.DesktopApplicationClientJava.controllers;
22

33
import com.DesktopApplicationClientJava.controllers.utils.Controller;
4+
import com.DesktopApplicationClientJava.entities.Role;
45
import com.DesktopApplicationClientJava.entities.User;
56
import com.DesktopApplicationClientJava.utils.FieldError;
67
import com.DesktopApplicationClientJava.validation.EmailValidator;
@@ -9,6 +10,7 @@
910
import com.DesktopApplicationClientJava.validation.PasswordValidator;
1011
import com.DesktopApplicationClientJava.validation.ThirdNameValidator;
1112
import com.DesktopApplicationClientJava.validation.utils.Validator;
13+
import java.util.UUID;
1214
import javafx.event.ActionEvent;
1315
import javafx.fxml.FXML;
1416
import javafx.scene.control.Button;
@@ -103,6 +105,6 @@ private boolean isFieldValid(TextField field, Validator validator, FieldError er
103105
}
104106

105107
private User authenticate(String firstName, String lastName, String email) {
106-
return new User(firstName, lastName, email);
108+
return new User(UUID.randomUUID(), email, Role.USER, firstName, lastName, true);
107109
}
108110
}

‎src/main/java/com/DesktopApplicationClientJava/controllers/utils/Controller.java‎

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,18 +2,29 @@
22

33
import com.DesktopApplicationClientJava.navigation.Navigator;
44
import com.DesktopApplicationClientJava.navigation.NavigatorAware;
5+
import com.DesktopApplicationClientJava.services.ServiceRegistry;
6+
import com.DesktopApplicationClientJava.services.ServicesAware;
57
import com.DesktopApplicationClientJava.session.Session;
68
import com.DesktopApplicationClientJava.session.SessionAware;
79

8-
public abstract class Controller implements SessionAware, NavigatorAware {
10+
public abstract class Controller implements SessionAware, NavigatorAware, ServicesAware {
11+
912
protected Session session;
1013
protected Navigator navigator;
14+
protected ServiceRegistry services;
1115

16+
@Override
1217
public void setSession(Session session) {
1318
this.session = session;
1419
}
1520

21+
@Override
1622
public void setNavigator(Navigator navigator) {
1723
this.navigator = navigator;
1824
}
25+
26+
@Override
27+
public void setServices(ServiceRegistry services) {
28+
this.services = services;
29+
}
1930
}
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
package com.DesktopApplicationClientJava.entities;
2+
3+
import java.util.UUID;
4+
import lombok.AllArgsConstructor;
5+
import lombok.Getter;
6+
import lombok.NoArgsConstructor;
7+
import lombok.Setter;
8+
9+
@Getter
10+
@Setter
11+
@NoArgsConstructor
12+
@AllArgsConstructor
13+
public class FileInfo {
14+
private UUID uuid;
15+
private String name;
16+
private String contentType;
17+
private Long size;
18+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
package com.DesktopApplicationClientJava.entities;
2+
3+
import java.time.LocalDateTime;
4+
import java.util.UUID;
5+
import lombok.AllArgsConstructor;
6+
import lombok.Getter;
7+
import lombok.NoArgsConstructor;
8+
import lombok.Setter;
9+
10+
@Getter
11+
@Setter
12+
@NoArgsConstructor
13+
@AllArgsConstructor
14+
public class Resource {
15+
private UUID uuid;
16+
private String title;
17+
private String description;
18+
private LocalDateTime createdAt;
19+
private LocalDateTime updatedAt;
20+
}
Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,20 @@
11
package com.DesktopApplicationClientJava.entities;
22

3+
import java.util.UUID;
34
import lombok.AllArgsConstructor;
45
import lombok.Getter;
6+
import lombok.NoArgsConstructor;
57
import lombok.Setter;
68

7-
/** User */
8-
@AllArgsConstructor
99
@Getter
1010
@Setter
11+
@NoArgsConstructor
12+
@AllArgsConstructor
1113
public class User {
14+
private UUID uuid;
15+
private String email;
16+
private Role role;
1217
private String firstName;
1318
private String lastName;
14-
private String email;
19+
private Boolean enabled;
1520
}

‎src/main/java/com/DesktopApplicationClientJava/navigation/Navigator.java‎

Lines changed: 23 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,25 @@
11
package com.DesktopApplicationClientJava.navigation;
22

3+
import com.DesktopApplicationClientJava.services.ServiceRegistry;
34
import com.DesktopApplicationClientJava.session.Session;
45
import com.DesktopApplicationClientJava.session.SessionAware;
6+
import com.DesktopApplicationClientJava.utils.ControllerWiring;
57
import java.io.IOException;
68
import javafx.fxml.FXMLLoader;
79
import javafx.scene.Parent;
810
import javafx.stage.Stage;
9-
import lombok.AllArgsConstructor;
1011

1112
/** Navigator */
12-
@AllArgsConstructor
1313
public class Navigator {
1414
private final Stage stage;
1515
private final Session session;
16+
private final ServiceRegistry services;
17+
18+
public Navigator(Stage stage, Session session, ServiceRegistry services) {
19+
this.stage = stage;
20+
this.session = session;
21+
this.services = services;
22+
}
1623

1724
public void goTo(String fxmlFile) {
1825
var url = Navigator.class.getResource(fxmlFile);
@@ -21,15 +28,28 @@ public void goTo(String fxmlFile) {
2128
}
2229

2330
FXMLLoader loader = new FXMLLoader(url);
31+
loader.setControllerFactory(
32+
clazz -> {
33+
try {
34+
Object controller = clazz.getDeclaredConstructor().newInstance();
35+
ControllerWiring.wire(controller, this, session, services);
36+
return controller;
37+
} catch (Exception e) {
38+
throw new RuntimeException("Cannot create controller: " + clazz, e);
39+
}
40+
});
41+
2442
try {
2543
Parent root = loader.load();
26-
var controller = loader.getController();
44+
45+
Object controller = loader.getController();
2746
if (controller instanceof SessionAware sa) {
2847
sa.setSession(session);
2948
}
3049
if (controller instanceof NavigatorAware na) {
3150
na.setNavigator(this);
3251
}
52+
3353
stage.getScene().setRoot(root);
3454
} catch (IOException e) {
3555
throw new RuntimeException("Failed to load FXML: " + fxmlFile, e);

0 commit comments

Comments
 (0)