Erweiterungen
This commit is contained in:
@@ -23,12 +23,25 @@ public class User {
|
|||||||
|
|
||||||
// Firmen-/Adressdaten
|
// Firmen-/Adressdaten
|
||||||
private String company; // Firma
|
private String company; // Firma
|
||||||
|
private String companyAddition; // Firmenzusatz
|
||||||
private String street; // Straße
|
private String street; // Straße
|
||||||
private String houseNumber; // Hausnr
|
private String houseNumber; // Hausnr
|
||||||
private String addressAddition; // Adresszusatz (optional)
|
private String addressAddition; // Adresszusatz (optional)
|
||||||
private String zip; // Postleitzahl
|
private String zip; // Postleitzahl
|
||||||
private String city; // Stadt
|
private String city; // Stadt
|
||||||
|
|
||||||
|
// Abweichende Rechnungsadresse
|
||||||
|
private boolean diffInvoiceAddress; // Checkbox für abweichende Rechnungsadresse
|
||||||
|
private String invCompany; // Rechnungsadresse: Firma
|
||||||
|
private String invCompanyAddition; // Rechnungsadresse: Firmenzusatz
|
||||||
|
private String invFirstname; // Rechnungsadresse: Vorname
|
||||||
|
private String invLastname; // Rechnungsadresse: Nachname
|
||||||
|
private String invStreet; // Rechnungsadresse: Straße
|
||||||
|
private String invHouseNumber; // Rechnungsadresse: Hausnr
|
||||||
|
private String invAddressAddition; // Rechnungsadresse: Adresszusatz
|
||||||
|
private String invZip; // Rechnungsadresse: Postleitzahl
|
||||||
|
private String invCity; // Rechnungsadresse: Stadt
|
||||||
|
|
||||||
@Indexed(unique = true)
|
@Indexed(unique = true)
|
||||||
private String email;
|
private String email;
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,42 @@
|
|||||||
|
package de.assecutor.votianlt.model;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
import org.bson.types.ObjectId;
|
||||||
|
import org.springframework.data.annotation.Id;
|
||||||
|
import org.springframework.data.mongodb.core.mapping.Document;
|
||||||
|
import org.springframework.data.mongodb.core.index.Indexed;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
@Document(collection = "user_invoice_data")
|
||||||
|
public class UserInvoiceData {
|
||||||
|
|
||||||
|
@Id
|
||||||
|
private ObjectId id;
|
||||||
|
|
||||||
|
@Indexed
|
||||||
|
private ObjectId userId;
|
||||||
|
|
||||||
|
private boolean billingEnabled;
|
||||||
|
private String prefix;
|
||||||
|
private String ustId;
|
||||||
|
private String taxNumber;
|
||||||
|
private String bankName;
|
||||||
|
private String iban;
|
||||||
|
private String taxRate;
|
||||||
|
private String introText;
|
||||||
|
private String paymentTerms;
|
||||||
|
|
||||||
|
private LocalDateTime createdAt;
|
||||||
|
private LocalDateTime updatedAt;
|
||||||
|
|
||||||
|
public UserInvoiceData() {
|
||||||
|
this.createdAt = LocalDateTime.now();
|
||||||
|
this.updatedAt = LocalDateTime.now();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void updateTimestamp() {
|
||||||
|
this.updatedAt = LocalDateTime.now();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -20,6 +20,9 @@ import com.vaadin.flow.router.Layout;
|
|||||||
import com.vaadin.flow.server.auth.AnonymousAllowed;
|
import com.vaadin.flow.server.auth.AnonymousAllowed;
|
||||||
import com.vaadin.flow.server.menu.MenuConfiguration;
|
import com.vaadin.flow.server.menu.MenuConfiguration;
|
||||||
import com.vaadin.flow.server.menu.MenuEntry;
|
import com.vaadin.flow.server.menu.MenuEntry;
|
||||||
|
import de.assecutor.votianlt.model.User;
|
||||||
|
import de.assecutor.votianlt.model.UserInvoiceData;
|
||||||
|
import de.assecutor.votianlt.pages.service.UserInvoiceDataService;
|
||||||
import de.assecutor.votianlt.pages.view.EditProfileView;
|
import de.assecutor.votianlt.pages.view.EditProfileView;
|
||||||
import de.assecutor.votianlt.security.SecurityService;
|
import de.assecutor.votianlt.security.SecurityService;
|
||||||
|
|
||||||
@@ -31,12 +34,14 @@ import static com.vaadin.flow.theme.lumo.LumoUtility.*;
|
|||||||
public final class MainLayout extends AppLayout {
|
public final class MainLayout extends AppLayout {
|
||||||
|
|
||||||
private final SecurityService securityService;
|
private final SecurityService securityService;
|
||||||
|
private final UserInvoiceDataService userInvoiceDataService;
|
||||||
private Div headerRef;
|
private Div headerRef;
|
||||||
private Scroller navRef;
|
private Scroller navRef;
|
||||||
private Component userMenuRef;
|
private Component userMenuRef;
|
||||||
|
|
||||||
public MainLayout(SecurityService securityService) {
|
public MainLayout(SecurityService securityService, UserInvoiceDataService userInvoiceDataService) {
|
||||||
this.securityService = securityService;
|
this.securityService = securityService;
|
||||||
|
this.userInvoiceDataService = userInvoiceDataService;
|
||||||
setPrimarySection(Section.DRAWER);
|
setPrimarySection(Section.DRAWER);
|
||||||
|
|
||||||
// Always build the drawer; keep references and toggle visibility on attach and
|
// Always build the drawer; keep references and toggle visibility on attach and
|
||||||
@@ -102,10 +107,17 @@ public final class MainLayout extends AppLayout {
|
|||||||
SideNavItem customers = new SideNavItem("Kunden", "customers", new Icon(VaadinIcon.USERS));
|
SideNavItem customers = new SideNavItem("Kunden", "customers", new Icon(VaadinIcon.USERS));
|
||||||
SideNavItem appUsers = new SideNavItem("App-Nutzer", "app-user", new Icon(VaadinIcon.USERS));
|
SideNavItem appUsers = new SideNavItem("App-Nutzer", "app-user", new Icon(VaadinIcon.USERS));
|
||||||
SideNavItem devices = new SideNavItem("Endgeräte", "app-devices", new Icon(VaadinIcon.MOBILE));
|
SideNavItem devices = new SideNavItem("Endgeräte", "app-devices", new Icon(VaadinIcon.MOBILE));
|
||||||
SideNavItem invoices = new SideNavItem("Rechnungen", "invoices", new Icon(VaadinIcon.FILE_TEXT));
|
|
||||||
SideNavItem statistics = new SideNavItem("Statistiken", "statistics", new Icon(VaadinIcon.BAR_CHART));
|
SideNavItem statistics = new SideNavItem("Statistiken", "statistics", new Icon(VaadinIcon.BAR_CHART));
|
||||||
|
|
||||||
verwaltungContent.add(jobs, customers, appUsers, devices, invoices, statistics);
|
verwaltungContent.add(jobs, customers, appUsers, devices);
|
||||||
|
|
||||||
|
// Only show invoices menu if billing is enabled for the current user
|
||||||
|
if (isBillingEnabledForCurrentUser()) {
|
||||||
|
SideNavItem invoices = new SideNavItem("Rechnungen", "invoices", new Icon(VaadinIcon.FILE_TEXT));
|
||||||
|
verwaltungContent.add(invoices);
|
||||||
|
}
|
||||||
|
|
||||||
|
verwaltungContent.add(statistics);
|
||||||
verwaltungDetails.add(verwaltungContent);
|
verwaltungDetails.add(verwaltungContent);
|
||||||
|
|
||||||
// Create Details component for "Verwaltung" with collapsible list
|
// Create Details component for "Verwaltung" with collapsible list
|
||||||
@@ -179,4 +191,18 @@ public final class MainLayout extends AppLayout {
|
|||||||
return userMenu;
|
return userMenu;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private boolean isBillingEnabledForCurrentUser() {
|
||||||
|
try {
|
||||||
|
User currentUser = securityService.getCurrentDatabaseUser();
|
||||||
|
if (currentUser != null && currentUser.getId() != null) {
|
||||||
|
UserInvoiceData invoiceData = userInvoiceDataService.findByUserId(currentUser.getId()).orElse(null);
|
||||||
|
return invoiceData != null && invoiceData.isBillingEnabled();
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
// Log error or handle appropriately
|
||||||
|
// Return false as safe default if we can't determine billing status
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,57 @@
|
|||||||
|
package de.assecutor.votianlt.pages.service;
|
||||||
|
|
||||||
|
import de.assecutor.votianlt.model.UserInvoiceData;
|
||||||
|
import de.assecutor.votianlt.repository.UserInvoiceDataRepository;
|
||||||
|
import org.bson.types.ObjectId;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import java.util.Optional;
|
||||||
|
|
||||||
|
@Service
|
||||||
|
public class UserInvoiceDataService {
|
||||||
|
|
||||||
|
private final UserInvoiceDataRepository userInvoiceDataRepository;
|
||||||
|
|
||||||
|
public UserInvoiceDataService(UserInvoiceDataRepository userInvoiceDataRepository) {
|
||||||
|
this.userInvoiceDataRepository = userInvoiceDataRepository;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Optional<UserInvoiceData> findByUserId(ObjectId userId) {
|
||||||
|
return userInvoiceDataRepository.findByUserId(userId);
|
||||||
|
}
|
||||||
|
|
||||||
|
public UserInvoiceData save(UserInvoiceData userInvoiceData) {
|
||||||
|
userInvoiceData.updateTimestamp();
|
||||||
|
return userInvoiceDataRepository.save(userInvoiceData);
|
||||||
|
}
|
||||||
|
|
||||||
|
public UserInvoiceData createOrUpdate(ObjectId userId, boolean billingEnabled, String prefix, String ustId,
|
||||||
|
String taxNumber, String bankName, String iban, String taxRate,
|
||||||
|
String introText, String paymentTerms) {
|
||||||
|
// If billing is disabled, delete any existing record and return null
|
||||||
|
if (!billingEnabled) {
|
||||||
|
deleteByUserId(userId);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Otherwise, create or update the record
|
||||||
|
UserInvoiceData invoiceData = findByUserId(userId).orElse(new UserInvoiceData());
|
||||||
|
|
||||||
|
invoiceData.setUserId(userId);
|
||||||
|
invoiceData.setBillingEnabled(billingEnabled);
|
||||||
|
invoiceData.setPrefix(prefix);
|
||||||
|
invoiceData.setUstId(ustId);
|
||||||
|
invoiceData.setTaxNumber(taxNumber);
|
||||||
|
invoiceData.setBankName(bankName);
|
||||||
|
invoiceData.setIban(iban);
|
||||||
|
invoiceData.setTaxRate(taxRate);
|
||||||
|
invoiceData.setIntroText(introText);
|
||||||
|
invoiceData.setPaymentTerms(paymentTerms);
|
||||||
|
|
||||||
|
return save(invoiceData);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void deleteByUserId(ObjectId userId) {
|
||||||
|
userInvoiceDataRepository.deleteByUserId(userId);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -13,6 +13,7 @@ import com.vaadin.flow.component.icon.VaadinIcon;
|
|||||||
import com.vaadin.flow.component.notification.Notification;
|
import com.vaadin.flow.component.notification.Notification;
|
||||||
import com.vaadin.flow.component.orderedlayout.HorizontalLayout;
|
import com.vaadin.flow.component.orderedlayout.HorizontalLayout;
|
||||||
import com.vaadin.flow.component.orderedlayout.VerticalLayout;
|
import com.vaadin.flow.component.orderedlayout.VerticalLayout;
|
||||||
|
import com.vaadin.flow.component.UI;
|
||||||
import com.vaadin.flow.component.textfield.EmailField;
|
import com.vaadin.flow.component.textfield.EmailField;
|
||||||
import com.vaadin.flow.component.textfield.TextField;
|
import com.vaadin.flow.component.textfield.TextField;
|
||||||
import java.io.ByteArrayOutputStream;
|
import java.io.ByteArrayOutputStream;
|
||||||
@@ -26,7 +27,9 @@ import com.vaadin.flow.data.value.ValueChangeMode;
|
|||||||
import com.vaadin.flow.router.PageTitle;
|
import com.vaadin.flow.router.PageTitle;
|
||||||
import com.vaadin.flow.router.Route;
|
import com.vaadin.flow.router.Route;
|
||||||
import de.assecutor.votianlt.model.User;
|
import de.assecutor.votianlt.model.User;
|
||||||
|
import de.assecutor.votianlt.model.UserInvoiceData;
|
||||||
import de.assecutor.votianlt.pages.service.UserService;
|
import de.assecutor.votianlt.pages.service.UserService;
|
||||||
|
import de.assecutor.votianlt.pages.service.UserInvoiceDataService;
|
||||||
import de.assecutor.votianlt.security.SecurityService;
|
import de.assecutor.votianlt.security.SecurityService;
|
||||||
import jakarta.annotation.security.RolesAllowed;
|
import jakarta.annotation.security.RolesAllowed;
|
||||||
|
|
||||||
@@ -46,8 +49,12 @@ public class EditProfileView extends HorizontalLayout {
|
|||||||
|
|
||||||
private final Binder<User> binder = new Binder<>(User.class);
|
private final Binder<User> binder = new Binder<>(User.class);
|
||||||
private final User currentUser;
|
private final User currentUser;
|
||||||
|
private final UserInvoiceDataService userInvoiceDataService;
|
||||||
|
private UserInvoiceData currentInvoiceData;
|
||||||
|
private Checkbox billingEnabled;
|
||||||
|
|
||||||
public EditProfileView(UserService userService, SecurityService securityService) {
|
public EditProfileView(UserService userService, UserInvoiceDataService userInvoiceDataService, SecurityService securityService) {
|
||||||
|
this.userInvoiceDataService = userInvoiceDataService;
|
||||||
this.currentUser = securityService.getCurrentDatabaseUser();
|
this.currentUser = securityService.getCurrentDatabaseUser();
|
||||||
setSizeFull();
|
setSizeFull();
|
||||||
setPadding(true);
|
setPadding(true);
|
||||||
@@ -155,32 +162,43 @@ public class EditProfileView extends HorizontalLayout {
|
|||||||
form.add(mobileField, 2);
|
form.add(mobileField, 2);
|
||||||
form.add(emailField, 2);
|
form.add(emailField, 2);
|
||||||
// Binder: Pflichtfelder und Bindings
|
// Binder: Pflichtfelder und Bindings
|
||||||
// UI-Pflichtfelder ohne Datenbindung (da nicht im User-Modell vorhanden)
|
// Pflichtfelder markieren
|
||||||
companyField.setRequiredIndicatorVisible(true);
|
companyField.setRequiredIndicatorVisible(true);
|
||||||
streetField.setRequiredIndicatorVisible(true);
|
streetField.setRequiredIndicatorVisible(true);
|
||||||
houseNumberField.setRequiredIndicatorVisible(true);
|
houseNumberField.setRequiredIndicatorVisible(true);
|
||||||
zipField.setRequiredIndicatorVisible(true);
|
zipField.setRequiredIndicatorVisible(true);
|
||||||
cityField.setRequiredIndicatorVisible(true);
|
cityField.setRequiredIndicatorVisible(true);
|
||||||
|
|
||||||
binder.forField(companyField).asRequired("").bind(user -> null, (user, v) -> {
|
// Hauptadresse binden
|
||||||
});
|
binder.forField(companyField).asRequired("Firma ist erforderlich").bind(User::getCompany, User::setCompany);
|
||||||
binder.forField(streetField).asRequired("").bind(user -> null, (user, v) -> {
|
binder.forField(companyAddField).bind(User::getCompanyAddition, User::setCompanyAddition);
|
||||||
});
|
binder.forField(streetField).asRequired("Straße ist erforderlich").bind(User::getStreet, User::setStreet);
|
||||||
binder.forField(houseNumberField).asRequired("").bind(user -> null, (user, v) -> {
|
binder.forField(houseNumberField).asRequired("Hausnummer ist erforderlich").bind(User::getHouseNumber, User::setHouseNumber);
|
||||||
});
|
binder.forField(addressAddField).bind(User::getAddressAddition, User::setAddressAddition);
|
||||||
binder.forField(zipField).asRequired("").bind(user -> null, (user, v) -> {
|
binder.forField(zipField).asRequired("Postleitzahl ist erforderlich").bind(User::getZip, User::setZip);
|
||||||
});
|
binder.forField(cityField).asRequired("Stadt ist erforderlich").bind(User::getCity, User::setCity);
|
||||||
binder.forField(cityField).asRequired("").bind(user -> null, (user, v) -> {
|
|
||||||
});
|
|
||||||
|
|
||||||
binder.forField(firstnameField).asRequired("").bind(User::getFirstname, User::setFirstname);
|
// Personendaten binden
|
||||||
binder.forField(lastnameField).asRequired("").bind(User::getName, User::setName);
|
binder.forField(firstnameField).asRequired("Vorname ist erforderlich").bind(User::getFirstname, User::setFirstname);
|
||||||
binder.forField(phoneField).asRequired("").bind(User::getPhone, User::setPhone);
|
binder.forField(lastnameField).asRequired("Nachname ist erforderlich").bind(User::getName, User::setName);
|
||||||
binder.forField(emailField).asRequired("").withValidator(new EmailValidator("Ungültige E-Mail-Adresse"))
|
binder.forField(phoneField).asRequired("Telefonnummer ist erforderlich").bind(User::getPhone, User::setPhone);
|
||||||
|
binder.forField(emailField).asRequired("E-Mail ist erforderlich").withValidator(new EmailValidator("Ungültige E-Mail-Adresse"))
|
||||||
.bind(User::getEmail, User::setEmail);
|
.bind(User::getEmail, User::setEmail);
|
||||||
// Optionale Felder
|
// Optionale Felder
|
||||||
binder.forField(mobileField).bind(User::getPhone2, User::setPhone2);
|
binder.forField(mobileField).bind(User::getPhone2, User::setPhone2);
|
||||||
binder.forField(faxField).bind(User::getFax, User::setFax);
|
binder.forField(faxField).bind(User::getFax, User::setFax);
|
||||||
|
|
||||||
|
// Abweichende Rechnungsadresse binden
|
||||||
|
binder.forField(diffInvoiceAddress).bind(User::isDiffInvoiceAddress, User::setDiffInvoiceAddress);
|
||||||
|
binder.forField(invCompanyField).bind(User::getInvCompany, User::setInvCompany);
|
||||||
|
binder.forField(invCompanyAddField).bind(User::getInvCompanyAddition, User::setInvCompanyAddition);
|
||||||
|
binder.forField(invFirstnameField).bind(User::getInvFirstname, User::setInvFirstname);
|
||||||
|
binder.forField(invLastnameField).bind(User::getInvLastname, User::setInvLastname);
|
||||||
|
binder.forField(invStreetField).bind(User::getInvStreet, User::setInvStreet);
|
||||||
|
binder.forField(invHouseNumberField).bind(User::getInvHouseNumber, User::setInvHouseNumber);
|
||||||
|
binder.forField(invAddressAddField).bind(User::getInvAddressAddition, User::setInvAddressAddition);
|
||||||
|
binder.forField(invZipField).bind(User::getInvZip, User::setInvZip);
|
||||||
|
binder.forField(invCityField).bind(User::getInvCity, User::setInvCity);
|
||||||
// Pflichtindikator sichtbar machen
|
// Pflichtindikator sichtbar machen
|
||||||
firstnameField.setRequiredIndicatorVisible(true);
|
firstnameField.setRequiredIndicatorVisible(true);
|
||||||
lastnameField.setRequiredIndicatorVisible(true);
|
lastnameField.setRequiredIndicatorVisible(true);
|
||||||
@@ -232,7 +250,7 @@ public class EditProfileView extends HorizontalLayout {
|
|||||||
partsTitle.getStyle().set("margin", "0 0 var(--lumo-space-s) 0");
|
partsTitle.getStyle().set("margin", "0 0 var(--lumo-space-s) 0");
|
||||||
|
|
||||||
// Felder für Rechnungsstellung (für Live-Update)
|
// Felder für Rechnungsstellung (für Live-Update)
|
||||||
Checkbox billingEnabled = new Checkbox("Rechnungslegung über votianLT");
|
billingEnabled = new Checkbox("Rechnungslegung über votianLT");
|
||||||
billingEnabled.setValue(false);
|
billingEnabled.setValue(false);
|
||||||
billingEnabled.addValueChangeListener(e -> toggleBilling(e.getValue()));
|
billingEnabled.addValueChangeListener(e -> toggleBilling(e.getValue()));
|
||||||
|
|
||||||
@@ -302,6 +320,9 @@ public class EditProfileView extends HorizontalLayout {
|
|||||||
billingTab.add(billingLeft, billingRight);
|
billingTab.add(billingLeft, billingRight);
|
||||||
tabSheet.add("Rechnungsstellung", billingTab);
|
tabSheet.add("Rechnungsstellung", billingTab);
|
||||||
|
|
||||||
|
// Bestehende Rechnungsdaten laden (nach Erstellung aller Felder)
|
||||||
|
loadInvoiceData();
|
||||||
|
|
||||||
// Zweiter Tab: Einstellungen (Beispiel mit Schaltern)
|
// Zweiter Tab: Einstellungen (Beispiel mit Schaltern)
|
||||||
VerticalLayout switches = new VerticalLayout();
|
VerticalLayout switches = new VerticalLayout();
|
||||||
switches.setPadding(false);
|
switches.setPadding(false);
|
||||||
@@ -342,9 +363,19 @@ public class EditProfileView extends HorizontalLayout {
|
|||||||
saveProfile.addClickListener(e -> {
|
saveProfile.addClickListener(e -> {
|
||||||
if (binder.validate().isOk()) {
|
if (binder.validate().isOk()) {
|
||||||
try {
|
try {
|
||||||
|
// Check if billing status changed
|
||||||
|
boolean oldBillingStatus = currentInvoiceData != null && currentInvoiceData.isBillingEnabled();
|
||||||
|
boolean newBillingStatus = billingEnabled.getValue();
|
||||||
|
|
||||||
binder.writeBean(currentUser);
|
binder.writeBean(currentUser);
|
||||||
userService.save(currentUser);
|
userService.save(currentUser);
|
||||||
|
saveInvoiceData();
|
||||||
Notification.show("Profil gespeichert", 3000, Notification.Position.BOTTOM_END);
|
Notification.show("Profil gespeichert", 3000, Notification.Position.BOTTOM_END);
|
||||||
|
|
||||||
|
// Always reload if billing status changed to update the sidebar
|
||||||
|
if (oldBillingStatus != newBillingStatus) {
|
||||||
|
UI.getCurrent().getPage().reload();
|
||||||
|
}
|
||||||
} catch (Exception ex) {
|
} catch (Exception ex) {
|
||||||
Notification.show("Fehler beim Speichern: " + ex.getMessage(), 4000, Notification.Position.MIDDLE);
|
Notification.show("Fehler beim Speichern: " + ex.getMessage(), 4000, Notification.Position.MIDDLE);
|
||||||
}
|
}
|
||||||
@@ -445,4 +476,45 @@ public class EditProfileView extends HorizontalLayout {
|
|||||||
return f != null && f.getValue() != null ? f.getValue() : "";
|
return f != null && f.getValue() != null ? f.getValue() : "";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void loadInvoiceData() {
|
||||||
|
currentInvoiceData = userInvoiceDataService.findByUserId(currentUser.getId()).orElse(null);
|
||||||
|
|
||||||
|
if (currentInvoiceData != null) {
|
||||||
|
billingEnabled.setValue(currentInvoiceData.isBillingEnabled());
|
||||||
|
prefixField.setValue(safe(currentInvoiceData.getPrefix()));
|
||||||
|
ustIdField.setValue(safe(currentInvoiceData.getUstId()));
|
||||||
|
taxNumberField.setValue(safe(currentInvoiceData.getTaxNumber()));
|
||||||
|
bankNameField.setValue(safe(currentInvoiceData.getBankName()));
|
||||||
|
ibanField.setValue(safe(currentInvoiceData.getIban()));
|
||||||
|
taxRateField.setValue(safe(currentInvoiceData.getTaxRate()));
|
||||||
|
introTextArea.setValue(safe(currentInvoiceData.getIntroText()));
|
||||||
|
termsTextArea.setValue(safe(currentInvoiceData.getPaymentTerms()));
|
||||||
|
|
||||||
|
// Update field enabled state and PDF preview based on loaded state
|
||||||
|
setBillingFieldsEnabled(currentInvoiceData.isBillingEnabled());
|
||||||
|
if (currentInvoiceData.isBillingEnabled()) {
|
||||||
|
refreshPdf();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void saveInvoiceData() {
|
||||||
|
currentInvoiceData = userInvoiceDataService.createOrUpdate(
|
||||||
|
currentUser.getId(),
|
||||||
|
billingEnabled.getValue(),
|
||||||
|
prefixField.getValue(),
|
||||||
|
ustIdField.getValue(),
|
||||||
|
taxNumberField.getValue(),
|
||||||
|
bankNameField.getValue(),
|
||||||
|
ibanField.getValue(),
|
||||||
|
taxRateField.getValue(),
|
||||||
|
introTextArea.getValue(),
|
||||||
|
termsTextArea.getValue()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
private String safe(String value) {
|
||||||
|
return value != null ? value : "";
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,16 @@
|
|||||||
|
package de.assecutor.votianlt.repository;
|
||||||
|
|
||||||
|
import de.assecutor.votianlt.model.UserInvoiceData;
|
||||||
|
import org.bson.types.ObjectId;
|
||||||
|
import org.springframework.data.mongodb.repository.MongoRepository;
|
||||||
|
import org.springframework.stereotype.Repository;
|
||||||
|
|
||||||
|
import java.util.Optional;
|
||||||
|
|
||||||
|
@Repository
|
||||||
|
public interface UserInvoiceDataRepository extends MongoRepository<UserInvoiceData, ObjectId> {
|
||||||
|
|
||||||
|
Optional<UserInvoiceData> findByUserId(ObjectId userId);
|
||||||
|
|
||||||
|
void deleteByUserId(ObjectId userId);
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user