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
8 changes: 8 additions & 0 deletions src/main/java/pl/koder95/eme/dfs/BookType.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package pl.koder95.eme.dfs;

public enum BookType {
LIBER_BAPTISMORUM,
LIBER_CONFIRMATORUM,
LIBER_MATRIMONIORUM,
LIBER_DEFUNCTORUM
}
8 changes: 8 additions & 0 deletions src/main/java/pl/koder95/eme/dfs/IndexNodeInterpreter.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package pl.koder95.eme.dfs;

import java.util.Map;
import org.w3c.dom.Node;

public interface IndexNodeInterpreter {
Map<String, String> interpret(Node node);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package pl.koder95.eme.dfs.impl;

import java.util.HashMap;
import java.util.Map;

import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import pl.koder95.eme.dfs.IndexNodeInterpreter;

public class IndexNodeInterpreterImpl implements IndexNodeInterpreter {
@Override
public Map<String, String> interpret(Node node) {
if (node == null || node.getNodeName().equalsIgnoreCase("index")) {
throw new IllegalArgumentException("Node is null or node is not an index");
Comment on lines +13 to +14

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Accept valid index nodes instead of throwing

When Book.load() passes a real <index ...> node through Index.create(), the node-name check succeeds and this interpreter is called, but this condition throws exactly for nodes named index. Any existing indices.xml containing at least one valid index now aborts startup/loading instead of importing acts.

Useful? React with 👍 / 👎.

}
Map<String, String> data = new HashMap<>();
NamedNodeMap attrs = node.getAttributes(); // pobiera listę atrybutów
while (attrs.getLength() > 0) {
Node attr = attrs.item(0); // pobiera pierwszy atrybut
String key = attr.getNodeName(); // - nazwa atrybutu
String value = attr.getTextContent(); // - wartość atrybutu
data.put(key, value); // dodanie nazwy i wartości atrybutu do danych
attrs.removeNamedItem(key); // usuwa odczytany atrybut
}
return data;
}
}
11 changes: 11 additions & 0 deletions src/main/java/pl/koder95/eme/factory/IndexFactory.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package pl.koder95.eme.factory;

import pl.koder95.eme.dfs.BookType;
import pl.koder95.eme.dfs.Index;

import java.util.Map;

public interface IndexFactory {

Index create(Map<String, String> data);
}
30 changes: 30 additions & 0 deletions src/main/java/pl/koder95/eme/factory/impl/BasicIndexFactory.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
package pl.koder95.eme.factory.impl;

import java.util.Map;
import java.util.Set;
import java.util.function.Function;

import pl.koder95.eme.dfs.Book;
import pl.koder95.eme.dfs.BookType;
import pl.koder95.eme.dfs.Index;
import pl.koder95.eme.dfs.IndexNodeInterpreter;
import pl.koder95.eme.factory.IndexFactory;

public class BasicIndexFactory implements IndexFactory {

private final Function<Set<String>, BookType> bookTypeMatcher;
private final Map<BookType, Book> bookMap;

public BasicIndexFactory(Function<Set<String>, BookType> bookTypeMatcher, Map<BookType, Book> bookMap) {
this.bookTypeMatcher = bookTypeMatcher;
this.bookMap = bookMap;
}

@Override
public Index create(Map<String, String> data) {
if (data == null) return null;
BookType bookType = bookTypeMatcher.apply(data.keySet());
if (bookType == null) return null;
return Index.create(bookMap.get(bookType), data);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
package pl.koder95.eme.factory.impl;

import pl.koder95.eme.dfs.Book;
import pl.koder95.eme.dfs.BookType;

import java.util.Arrays;
import java.util.Map;
import java.util.Set;
import java.util.function.BiPredicate;

public class StandardIndexFactory extends BasicIndexFactory {

public StandardIndexFactory(BiPredicate<Set<String>, BookType> bookTypePattern) {
super(strings -> Arrays.stream(BookType.values())
.filter(bookType -> bookTypePattern.test(strings, bookType))
.findFirst().orElseThrow(),
Map.of(
BookType.LIBER_BAPTISMORUM, new Book("Księga ochrzczonych"),
BookType.LIBER_CONFIRMATORUM, new Book("Księga bierzmowanych"),
BookType.LIBER_MATRIMONIORUM, new Book("Księga zaślubionych"),
BookType.LIBER_DEFUNCTORUM, new Book("Księga zmarłych")
)
);
}

public StandardIndexFactory() {
this((strings, bookType) -> switch (bookType) {
case null -> false;
case LIBER_CONFIRMATORUM -> strings.contains("confirmation-name");
case LIBER_DEFUNCTORUM -> strings.contains("death-date-time");
case LIBER_MATRIMONIORUM -> strings.contains("husband-surname");
default -> strings.contains("surname");
});
}
}
53 changes: 31 additions & 22 deletions src/main/java/pl/koder95/eme/fx/PersonalDataView.java
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
import javafx.scene.control.Label;
import javafx.scene.control.TextField;
import javafx.scene.layout.BorderPane;
import javafx.scene.control.*;
import org.controlsfx.control.textfield.AutoCompletionBinding;
import org.controlsfx.control.textfield.TextFields;
import pl.koder95.eme.application.AppCloseService;
Expand Down Expand Up @@ -71,32 +72,41 @@ public PersonalDataView(PersonalDataQueryService personalDataQueryService,
private Label numberOfActs;

@FXML
private Object searching;
private TextField searching;

@Override
public void initialize(URL location, ResourceBundle resources) {
if (searching instanceof TextField) {
TextField field = (TextField) searching;
AutoCompletionBinding<PersonalDataModel> autoCompletionBinding = TextFields.bindAutoCompletion(
field,
personalDataQueryService.getSuggestionProvider(),
personalDataQueryService.getPersonalDataConverter()
);
autoCompletionBinding.setOnAutoCompleted(event -> setPersonalDataModel(event.getCompletion()));
field.setOnAction(event -> setPersonalDataModel(
personalDataQueryService.fromText(field.getText())
));
field.textProperty().addListener(
(observable, oldValue, newValue) -> {
if (oldValue.length() < newValue.length()) {
field.setText(newValue.toUpperCase());
}
}
);
}
installCabinetAnalyzer();
}

private void installCabinetAnalyzer() {
setupAutoCompletion();
setupInputActions();
numberOfActs.setText(String.valueOf(personalDataQueryService.getNumberOfActs()));
}

private void setupAutoCompletion() {
AutoCompletionBinding<PersonalDataModel> binding = TextFields.bindAutoCompletion(
searching,
personalDataQueryService.getSuggestionProvider(),
personalDataQueryService.getPersonalDataConverter()
);
binding.setOnAutoCompleted(event -> setPersonalDataModel(event.getCompletion()));
}

private void setupInputActions() {
searching.setOnAction(event -> setPersonalDataModel(
personalDataQueryService.getPersonalDataConverter().fromString(searching.getText())
));
searching.textProperty().addListener(
(observable, oldValue, newValue) -> {
if (oldValue.length() < newValue.length()) {
searching.setText(newValue.toUpperCase());
}
}
);
}

private void setPersonalDataModel(PersonalDataModel model) {
PersonalDataPresentation viewData = personalDataQueryService.toPresentation(model);
this.personalData.setText(viewData.fullName());
Expand All @@ -105,7 +115,6 @@ private void setPersonalDataModel(PersonalDataModel model) {
this.marriage.setText(viewData.getMarriageAN());
this.decease.setText(viewData.getDeceaseAN());
}

/**
* Obsługuje próbę zamknięcia aplikacji z potwierdzeniem.
*/
Expand All @@ -116,7 +125,7 @@ public void close(ActionEvent actionEvent) {
/**
* Ponownie wczytuje dane indeksów i odświeża licznik aktów.
*/
public void reload(ActionEvent actionEvent) {
public void reload() {
Scene scene = main.getScene();
if (scene != null) {
Dialog<Boolean> dialog = dialogs.createProgressDialog(scene, bundle.getString("FX_RELOAD_PROGRESS_MESSAGE"));
Expand Down
67 changes: 67 additions & 0 deletions src/main/java/pl/koder95/eme/fx/ProgressDialog.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
package pl.koder95.eme.fx;

import javafx.application.Platform;
import javafx.geometry.Pos;
import javafx.scene.Parent;
import javafx.scene.control.Dialog;
import javafx.scene.control.DialogPane;
import javafx.scene.control.Label;
import javafx.scene.control.ProgressIndicator;
import javafx.scene.layout.VBox;
import javafx.scene.text.Font;
import javafx.scene.text.FontWeight;
import pl.koder95.eme.dfs.IndexList;

import java.util.concurrent.atomic.AtomicLong;

public class ProgressDialog extends Dialog<Boolean> {
private static final AtomicLong PROGRESS_DIALOG_THREAD_SEQ = new AtomicLong();

private ProgressDialog() {
this.setDialogPane(createDialogPane());
setOnShown(event -> Platform.runLater(createProgressThread()::start));
}

private Thread createProgressThread() {
return new Thread(() -> {
reloadAllIndexLists();
Platform.runLater(() -> {
setResult(true);
close();
});
}, "Progress Dialog Thread #" + PROGRESS_DIALOG_THREAD_SEQ.incrementAndGet());
}

private DialogPane createDialogPane() {
ProgressIndicator indicator = new ProgressIndicator(ProgressIndicator.INDETERMINATE_PROGRESS);
Label label = new Label("Czekaj...");
label.setFont(Font.font(label.getFont().getFamily(), FontWeight.BOLD, 24));
DialogPane pane = new DialogPane();
pane.setContent(createMainPane(indicator, label));
return pane;
}

private Parent createMainPane(ProgressIndicator indicator, Label label) {
VBox main = new VBox(indicator, label);
main.setMaxWidth(Double.MAX_VALUE);
main.setSpacing(10);
main.setFillWidth(true);
main.setAlignment(Pos.CENTER);
return main;
}

private static void reloadAllIndexLists() {
for (IndexList value : IndexList.values()) {
reload(value);
}
}
Comment on lines +56 to +57

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Reset cached books when reloading data

The new reload path clears each IndexList and calls load(), but IndexList.load() only rereads indices.xml when the static BOOKS cache is null. After startup, choosing the new reload menu repopulates from the same cached books, so edits to the XML file are not picked up.

Useful? React with 👍 / 👎.


private static void reload(IndexList value) {
value.clear();
value.load();
}

public static void start() {
Platform.runLater(() -> new ProgressDialog().showAndWait());
}
}
40 changes: 40 additions & 0 deletions src/main/java/pl/koder95/eme/model/PersonalData.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
package pl.koder95.eme.model;

import pl.koder95.eme.core.spi.PersonalDataModel;

public record PersonalData(String surname, String name,
String ban, String can, String man, String dan)
implements PersonalDataModel {
private static final String NOMEN = "N.";
private static final String EAN = "–";

@Override
public String getSurname() {
return surname == null || surname.isBlank() ? NOMEN : surname;
}

@Override
public String getName() {
return name == null || name.isBlank() ? NOMEN : name;
}

@Override
public String getBaptismAN() {
return ban == null || ban.isBlank() ? EAN : ban;
}

@Override
public String getConfirmationAN() {
return can == null || can.isBlank() ? EAN : can;
}

@Override
public String getMarriageAN() {
return man == null || man.isBlank() ? EAN : man;
}

@Override
public String getDeceaseAN() {
return dan == null || dan.isBlank() ? EAN : dan;
}
}
13 changes: 13 additions & 0 deletions src/main/java/pl/koder95/eme/service/DataService.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package pl.koder95.eme.service;

import pl.koder95.eme.core.spi.PersonalDataModel;

import java.util.Collection;
import java.util.function.Predicate;

public interface DataService {
void load();
void save();
Collection<PersonalDataModel> findPeople(Predicate<PersonalDataModel> predicate);
Collection<PersonalDataModel> findPeople(String userText, boolean cancelled);
}