big improvements yay!
This commit is contained in:
@@ -4,7 +4,7 @@
|
|||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<groupId>de.champonthis</groupId>
|
<groupId>de.champonthis</groupId>
|
||||||
<artifactId>abi</artifactId>
|
<artifactId>abi</artifactId>
|
||||||
<version>0.2.8</version>
|
<version>0.3.0</version>
|
||||||
<name>abi</name>
|
<name>abi</name>
|
||||||
|
|
||||||
<parent>
|
<parent>
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package de.champonthis.abi.buisinesslogic;
|
package de.champonthis.abi.buisinesslogic;
|
||||||
|
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
import org.apache.commons.lang3.StringUtils;
|
import org.apache.commons.lang3.StringUtils;
|
||||||
@@ -37,6 +38,14 @@ public class ContactDataManager {
|
|||||||
contactDataRepository.save(contactData);
|
contactDataRepository.save(contactData);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public List<ContactData> findPendingContactData(Long reportedBy) {
|
||||||
|
return contactDataRepository.findByReportedBy(reportedBy).stream()
|
||||||
|
.filter(cd -> !cd.getContact().equals(reportedBy))
|
||||||
|
.filter(cd -> findByContactAndReportedBy(cd.getContact(), cd.getContact()) == null)
|
||||||
|
.sorted((cd1, cd2) -> cd1.getContact().compareTo(cd2.getContact()))
|
||||||
|
.toList();
|
||||||
|
}
|
||||||
|
|
||||||
public void sendInviteMail(Contact contact, ContactData contactData, Contact reportedBy) {
|
public void sendInviteMail(Contact contact, ContactData contactData, Contact reportedBy) {
|
||||||
if (StringUtils.isNoneEmpty(contactData.getEmail()) && StringUtils.isNoneEmpty(contactData.getInviteToken())) {
|
if (StringUtils.isNoneEmpty(contactData.getEmail()) && StringUtils.isNoneEmpty(contactData.getInviteToken())) {
|
||||||
Map<String, Object> variables = new HashMap<>();
|
Map<String, Object> variables = new HashMap<>();
|
||||||
|
|||||||
@@ -1,10 +1,16 @@
|
|||||||
package de.champonthis.abi.controller;
|
package de.champonthis.abi.controller;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
import org.apache.commons.lang3.StringUtils;
|
import org.apache.commons.lang3.StringUtils;
|
||||||
|
import org.springframework.http.HttpHeaders;
|
||||||
import org.springframework.http.HttpStatus;
|
import org.springframework.http.HttpStatus;
|
||||||
import org.springframework.http.ResponseEntity;
|
import org.springframework.http.ResponseEntity;
|
||||||
|
import org.springframework.web.bind.annotation.GetMapping;
|
||||||
import org.springframework.web.bind.annotation.PostMapping;
|
import org.springframework.web.bind.annotation.PostMapping;
|
||||||
import org.springframework.web.bind.annotation.RequestBody;
|
import org.springframework.web.bind.annotation.RequestBody;
|
||||||
|
import org.springframework.web.bind.annotation.RequestHeader;
|
||||||
import org.springframework.web.bind.annotation.RequestMapping;
|
import org.springframework.web.bind.annotation.RequestMapping;
|
||||||
import org.springframework.web.bind.annotation.RestController;
|
import org.springframework.web.bind.annotation.RestController;
|
||||||
import org.springframework.web.server.ResponseStatusException;
|
import org.springframework.web.server.ResponseStatusException;
|
||||||
@@ -12,6 +18,7 @@ import org.springframework.web.server.ResponseStatusException;
|
|||||||
import de.champonthis.abi.buisinesslogic.ContactDataManager;
|
import de.champonthis.abi.buisinesslogic.ContactDataManager;
|
||||||
import de.champonthis.abi.buisinesslogic.ContactManager;
|
import de.champonthis.abi.buisinesslogic.ContactManager;
|
||||||
import de.champonthis.abi.controller.request.ContactDataRequest;
|
import de.champonthis.abi.controller.request.ContactDataRequest;
|
||||||
|
import de.champonthis.abi.controller.response.ContactDataResponse;
|
||||||
import de.champonthis.abi.entity.Contact;
|
import de.champonthis.abi.entity.Contact;
|
||||||
import de.champonthis.abi.entity.ContactData;
|
import de.champonthis.abi.entity.ContactData;
|
||||||
import jakarta.validation.Valid;
|
import jakarta.validation.Valid;
|
||||||
@@ -58,13 +65,14 @@ public class ContactDataController {
|
|||||||
contactData.setEmail(request.getEmail().toLowerCase());
|
contactData.setEmail(request.getEmail().toLowerCase());
|
||||||
contactData.setPhone(request.getPhone());
|
contactData.setPhone(request.getPhone());
|
||||||
|
|
||||||
if (!contact.getId().equals(reportedBy.getId())
|
if (!contact.getId().equals(reportedBy.getId()) && StringUtils.isEmpty(contact.getToken())) {
|
||||||
&& (contactData.getInviteToken() == null || StringUtils.isEmpty(contactData.getInviteToken()))) {
|
if (contactData.getInviteToken() == null || StringUtils.isEmpty(contactData.getInviteToken())) {
|
||||||
String inviteToken = ContactManager.generateToken();
|
String inviteToken = ContactManager.generateToken();
|
||||||
while (contactDataManager.findByinviteToken(inviteToken) != null) {
|
while (contactDataManager.findByinviteToken(inviteToken) != null) {
|
||||||
inviteToken = ContactManager.generateToken();
|
inviteToken = ContactManager.generateToken();
|
||||||
|
}
|
||||||
|
contactData.setInviteToken(inviteToken);
|
||||||
}
|
}
|
||||||
contactData.setInviteToken(inviteToken);
|
|
||||||
|
|
||||||
if (contactDataManager.findByContactAndEmail(contact.getId(), contactData.getEmail()) == null) {
|
if (contactDataManager.findByContactAndEmail(contact.getId(), contactData.getEmail()) == null) {
|
||||||
contactDataManager.sendInviteMail(contact, contactData, reportedBy);
|
contactDataManager.sendInviteMail(contact, contactData, reportedBy);
|
||||||
@@ -80,4 +88,29 @@ public class ContactDataController {
|
|||||||
|
|
||||||
return ResponseEntity.status(status.value()).body(contactData);
|
return ResponseEntity.status(status.value()).body(contactData);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@GetMapping("/pending")
|
||||||
|
public List<ContactDataResponse> getPending(
|
||||||
|
@RequestHeader(name = HttpHeaders.AUTHORIZATION, required = false) String authToken) {
|
||||||
|
if (StringUtils.isEmpty(authToken)) {
|
||||||
|
throw new ResponseStatusException(HttpStatus.UNAUTHORIZED);
|
||||||
|
}
|
||||||
|
|
||||||
|
Contact contact = contactManager.findByToken(authToken);
|
||||||
|
if (contact == null) {
|
||||||
|
throw new ResponseStatusException(HttpStatus.UNAUTHORIZED);
|
||||||
|
}
|
||||||
|
|
||||||
|
return contactDataManager.findPendingContactData(contact.getId()).stream()
|
||||||
|
.map(cd -> {
|
||||||
|
Contact contactEntity = contactManager.findById(cd.getContact());
|
||||||
|
String contactName = contactEntity != null ? contactEntity.getName() : "Unbekannt";
|
||||||
|
return new ContactDataResponse(
|
||||||
|
contactName,
|
||||||
|
cd.getEmail(),
|
||||||
|
cd.getPhone());
|
||||||
|
})
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,12 @@
|
|||||||
|
package de.champonthis.abi.controller.response;
|
||||||
|
|
||||||
|
import lombok.AllArgsConstructor;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
@AllArgsConstructor
|
||||||
|
public class ContactDataResponse {
|
||||||
|
private String contactName;
|
||||||
|
private String email;
|
||||||
|
private String phone;
|
||||||
|
}
|
||||||
@@ -1,5 +1,6 @@
|
|||||||
package de.champonthis.abi.repository;
|
package de.champonthis.abi.repository;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
|
|
||||||
import org.springframework.data.jpa.repository.JpaRepository;
|
import org.springframework.data.jpa.repository.JpaRepository;
|
||||||
@@ -15,4 +16,6 @@ public interface ContactDataRepository extends JpaRepository<ContactData, Long>
|
|||||||
Optional<ContactData> findByContactAndEmail(Long contact, String email);
|
Optional<ContactData> findByContactAndEmail(Long contact, String email);
|
||||||
|
|
||||||
Optional<ContactData> findByinviteToken(String inviteToken);
|
Optional<ContactData> findByinviteToken(String inviteToken);
|
||||||
|
|
||||||
|
List<ContactData> findByReportedBy(Long reportedBy);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -201,27 +201,54 @@
|
|||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
<div class="alert py-2" :class="'alert-' + stepMsgType" x-text="stepMsg" x-show="stepMsg"></div>
|
<div class="alert py-2" :class="'alert-' + stepMsgType" x-text="stepMsg" x-show="stepMsg"></div>
|
||||||
<div id="knownContactDataDiv" x-show="showKnownContactData" x-transition>
|
<ul class="list-group mb-3" id="enteredContacts" x-show="enteredContacts && enteredContacts.length > 0">
|
||||||
<p x-text="foundKnownContactName"></p>
|
<template x-for="(c, index) in enteredContacts || []" :key="c.name + '_' + index">
|
||||||
<form @submit.prevent="submitKnownContactData" class="mb-3">
|
<li class="list-group-item">
|
||||||
<div class="mb-3">
|
<!-- Normal view -->
|
||||||
<label class="form-label">E-Mail:</label>
|
<div x-show="editingContactIndex !== index"
|
||||||
<input type="email" x-model="knownContactEmail" placeholder="name@example.com"
|
:class="editingContactIndex === index ? 'd-none' : 'd-flex justify-content-between align-items-center'">
|
||||||
required autocomplete="off" class="form-control" autofocus />
|
<div>
|
||||||
</div>
|
<strong x-text="c.name"></strong><br>
|
||||||
<div class="mb-3">
|
<small class="text-muted">
|
||||||
<label class="form-label">Handynummer (optional):</label>
|
<span x-text="c.email"></span>
|
||||||
<input type="text" x-model="knownContactPhone" placeholder="+49123456789"
|
<span x-show="c.phone" x-text="', ' + c.phone"></span>
|
||||||
autocomplete="off" class="form-control" />
|
</small>
|
||||||
</div>
|
</div>
|
||||||
<button type="submit" class="btn btn-outline-success flex-fill"
|
<button class="btn btn-sm btn-outline-primary" @click="startEdit(index)" :disabled="working">
|
||||||
:class="{'disabled': working}" autofocus>Speichern</button>
|
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" viewBox="0 0 16 16">
|
||||||
</form>
|
<path d="M12.146.146a.5.5 0 0 1 .708 0l3 3a.5.5 0 0 1 0 .708L4.707 14.707a.5.5 0 0 1-.168.11l-5 2a.5.5 0 0 1-.65-.65l2-5a.5.5 0 0 1 .11-.168L12.146.146zM11.207 2.5 13.5 4.793 14.793 3.5 12.5 1.207 11.207 2.5zm1.586 3L10.5 3.207 4 9.707V10h.5a.5.5 0 0 1 .5.5v.5h.5a.5.5 0 0 1 .5.5v.5h.293L12.793 5.5z"/>
|
||||||
</div>
|
</svg>
|
||||||
<ul class="list-group mb-3" id="enteredContacts">
|
</button>
|
||||||
<template x-for="c in enteredContacts" :key="c.name">
|
</div>
|
||||||
<li class="list-group-item"
|
|
||||||
x-text="`${c.name} (${c.email}${c.phone ? ', ' + c.phone : ''})`"></li>
|
<!-- Edit view - fully inline -->
|
||||||
|
<div x-show="editingContactIndex === index"
|
||||||
|
:class="editingContactIndex === index ? 'row g-2 align-items-start' : 'd-none'">
|
||||||
|
<div class="col-12">
|
||||||
|
<strong x-text="c.name"></strong>
|
||||||
|
</div>
|
||||||
|
<div class="col-12 col-md">
|
||||||
|
<input type="email" class="form-control form-control-sm" x-model="editingContactData.email" placeholder="E-Mail" required>
|
||||||
|
</div>
|
||||||
|
<div class="col-12 col-md">
|
||||||
|
<input type="text" class="form-control form-control-sm" x-model="editingContactData.phone" placeholder="Telefon (optional)">
|
||||||
|
</div>
|
||||||
|
<div class="col-12 col-md-auto">
|
||||||
|
<div class="d-flex gap-1">
|
||||||
|
<button class="btn btn-sm btn-outline-danger" @click="cancelEdit()" :disabled="working">
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" width="14" height="14" fill="currentColor" viewBox="0 0 16 16">
|
||||||
|
<path d="M2.146 2.854a.5.5 0 1 1 .708-.708L8 7.293l5.146-5.147a.5.5 0 0 1 .708.708L8.707 8l5.147 5.146a.5.5 0 0 1-.708.708L8 8.707l-5.146 5.147a.5.5 0 0 1-.708-.708L7.293 8 2.146 2.854Z"/>
|
||||||
|
</svg>
|
||||||
|
</button>
|
||||||
|
<button class="btn btn-sm btn-success" @click="saveContactData(index)" :disabled="working">
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" width="18" height="18" fill="currentColor" viewBox="0 0 16 16">
|
||||||
|
<path d="M10.97 4.97a.235.235 0 0 0-.02.022L7.477 9.417 5.384 7.323a.75.75 0 0 0-1.06 1.06L6.97 11.03a.75.75 0 0 0 1.079-.02l3.992-4.99a.75.75 0 0 0-1.071-1.05z"/>
|
||||||
|
</svg>
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</li>
|
||||||
</template>
|
</template>
|
||||||
</ul>
|
</ul>
|
||||||
<div class="d-flex gap-2 mt-3 justify-content-center">
|
<div class="d-flex gap-2 mt-3 justify-content-center">
|
||||||
@@ -250,16 +277,22 @@
|
|||||||
</svg> Schritt 4: Bist du beim 20-Jahrestreffen am 13.11.2027 in Gevelsberg dabei?
|
</svg> Schritt 4: Bist du beim 20-Jahrestreffen am 13.11.2027 in Gevelsberg dabei?
|
||||||
</h2>
|
</h2>
|
||||||
<div class="alert py-2" :class="'alert-' + stepMsgType" x-text="stepMsg" x-show="stepMsg"></div>
|
<div class="alert py-2" :class="'alert-' + stepMsgType" x-text="stepMsg" x-show="stepMsg"></div>
|
||||||
<p x-show="!stepMsg">
|
<p x-show="!stepMsg && !committed">
|
||||||
Hast du Lust, am Samstag, den 13.11.2027, beim Nachtreffen in Gevelsberg dabei zu sein?
|
Hast du Lust, am Samstag, den 13.11.2027, beim Nachtreffen in Gevelsberg dabei zu sein?
|
||||||
Genauere Infos und Details gibt's dann später hier und per Mail.
|
Genauere Infos und Details gibt's dann später hier und per Mail.
|
||||||
</p>
|
</p>
|
||||||
|
<p x-show="!stepMsg && committed === 'YES'">
|
||||||
|
Du hast bereits <strong>zugesagt</strong>. Genauere Infos und Details gibt's dann später hier und per Mail. Falls du deine Meinung ändern möchtest, kannst du hier nochmal wählen.
|
||||||
|
</p>
|
||||||
|
<p x-show="!stepMsg && committed === 'NO'">
|
||||||
|
Du hast bereits <strong>abgesagt</strong>. Falls du deine Meinung ändern möchtest, kannst du hier nochmal wählen.
|
||||||
|
</p>
|
||||||
<div class="d-flex gap-2 mb-3">
|
<div class="d-flex gap-2 mb-3">
|
||||||
<button x-show="!stepMsg" id="commitYes" class="btn flex-fill"
|
<button x-show="!stepMsg" id="commitYes" class="btn flex-fill"
|
||||||
:class="{'btn-success': committed != 'NO', 'btn-outline-dark' : committed == 'NO', 'disabled': working}"
|
:class="{'btn-success': committed != 'NO', 'btn-outline-secondary' : committed == 'NO', 'disabled': working}"
|
||||||
@click="submitCommit('YES')" autofocus>Ja, ich bin dabei!</button>
|
@click="submitCommit('YES')" autofocus>Ja, ich bin dabei!</button>
|
||||||
<button x-show="!stepMsg" id="commitNo" class="btn flex-fill"
|
<button x-show="!stepMsg" id="commitNo" class="btn flex-fill"
|
||||||
:class="{'btn-danger' : committed != 'YES','btn-outline-dark' : committed == 'YES', 'disabled': working}"
|
:class="{'btn-danger' : committed != 'YES','btn-outline-secondary' : committed == 'YES', 'disabled': working}"
|
||||||
@click="submitCommit('NO')">Nein,
|
@click="submitCommit('NO')">Nein,
|
||||||
ich
|
ich
|
||||||
kann leider nicht</button>
|
kann leider nicht</button>
|
||||||
@@ -416,11 +449,9 @@
|
|||||||
email: '[[${email}]]',
|
email: '[[${email}]]',
|
||||||
phone: '[[${phone}]]',
|
phone: '[[${phone}]]',
|
||||||
knownContactName: '',
|
knownContactName: '',
|
||||||
knownContactEmail: '',
|
|
||||||
knownContactPhone: '',
|
|
||||||
showKnownContactData: false,
|
|
||||||
enteredContacts: [],
|
enteredContacts: [],
|
||||||
foundKnownContactName: null,
|
editingContactIndex: -1,
|
||||||
|
editingContactData: { email: '', phone: '' },
|
||||||
committed: '[[${committed}]]',
|
committed: '[[${committed}]]',
|
||||||
|
|
||||||
init() {
|
init() {
|
||||||
@@ -443,6 +474,36 @@
|
|||||||
this.stepMsg = '';
|
this.stepMsg = '';
|
||||||
this.stepMsgType = '';
|
this.stepMsgType = '';
|
||||||
this.step = step;
|
this.step = step;
|
||||||
|
|
||||||
|
if (!this.enteredContacts) {
|
||||||
|
this.enteredContacts = [];
|
||||||
|
}
|
||||||
|
|
||||||
|
if (step === 3 && this.userToken) {
|
||||||
|
this.loadPendingContacts();
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
async loadPendingContacts() {
|
||||||
|
try {
|
||||||
|
const resp = await axios.get('/api/v1/contact/data/pending', {
|
||||||
|
headers: { 'Authorization': this.userToken },
|
||||||
|
validateStatus: () => true
|
||||||
|
});
|
||||||
|
|
||||||
|
if (resp.status === 200) {
|
||||||
|
this.enteredContacts = (this.enteredContacts || []).filter((c) => c.isNew);
|
||||||
|
resp.data.forEach(contact => {
|
||||||
|
this.enteredContacts.push({
|
||||||
|
name: contact.contactName,
|
||||||
|
email: contact.email,
|
||||||
|
phone: contact.phone || ''
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Fehler beim Laden der Kontakte:', error);
|
||||||
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
async findSelf() {
|
async findSelf() {
|
||||||
@@ -535,36 +596,48 @@
|
|||||||
async findKnownContact() {
|
async findKnownContact() {
|
||||||
this.stepMsg = '';
|
this.stepMsg = '';
|
||||||
this.stepMsgType = '';
|
this.stepMsgType = '';
|
||||||
this.showKnownContactData = false;
|
|
||||||
this.knownContactEmail = '';
|
|
||||||
this.knownContactPhone = '';
|
|
||||||
this.foundKnownContactName = null;
|
|
||||||
this.working = true;
|
this.working = true;
|
||||||
try {
|
try {
|
||||||
const resp = await axios.get('/api/v1/contact', {
|
const resp = await axios.get('/api/v1/contact', {
|
||||||
params: { name: this.knownContactName.trim() },
|
params: { name: this.knownContactName.trim() },
|
||||||
|
headers: this.userToken ? { 'Authorization': this.userToken } : {},
|
||||||
validateStatus: () => true
|
validateStatus: () => true
|
||||||
});
|
});
|
||||||
if (resp.status === 200) {
|
if (resp.status === 200) {
|
||||||
this.foundKnownContactName = resp.data.name.trim();
|
const contactName = resp.data.name.trim();
|
||||||
if (this.foundKnownContactName == this.yourName) {
|
if (contactName == this.yourName || contactName == this.userName) {
|
||||||
this.stepMsg = 'Das bist du selbst - deine Daten hast du ja schon eingetragen!';
|
this.stepMsg = 'Witzig, das bist du selbst - deine Daten hast du ja schon eingetragen!';
|
||||||
this.stepMsgType = 'warning';
|
this.stepMsgType = 'warning';
|
||||||
this.showKnownContactData = false;
|
this.knownContactName = '';
|
||||||
this.knownContactName = ''
|
|
||||||
} else {
|
} else {
|
||||||
this.knownContactName = this.foundKnownContactName;
|
const existingIndex = this.enteredContacts.findIndex(c => c.name === contactName);
|
||||||
this.stepMsg = 'Super, trag bitte die Kontaktdaten ein!';
|
if (existingIndex !== -1) {
|
||||||
this.stepMsgType = 'success';
|
this.startEdit(existingIndex);
|
||||||
this.showKnownContactData = true;
|
this.stepMsg = 'Kontakt bereits vorhanden - du kannst die Daten hier bearbeiten.';
|
||||||
|
this.stepMsgType = 'info';
|
||||||
|
this.knownContactName = '';
|
||||||
|
} else {
|
||||||
|
this.enteredContacts.unshift({
|
||||||
|
name: contactName,
|
||||||
|
email: '',
|
||||||
|
phone: '',
|
||||||
|
isNew: true // Mark as new for cancel behavior
|
||||||
|
});
|
||||||
|
this.startEdit(0);
|
||||||
|
this.stepMsg = 'Super, trag bitte die Kontaktdaten ein!';
|
||||||
|
this.stepMsgType = 'success';
|
||||||
|
this.knownContactName = '';
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} else if (resp.status === 404) {
|
} else if (resp.status === 404) {
|
||||||
this.stepMsg = 'Diesen Namen gibt es leider nicht in unserer Liste.';
|
this.stepMsg = 'Diesen Namen gibt es leider nicht in unserer Liste.';
|
||||||
this.stepMsgType = 'warning';
|
this.stepMsgType = 'warning';
|
||||||
} else if (resp.status === 208) {
|
} else if (resp.status === 208) {
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
this.stepMsg = 'Für diese Person haben wir schon Kontaktdaten. Danke trotzdem fürs Mitmachen!';
|
this.stepMsg = 'Für diese Person haben wir schon Kontaktdaten. Danke trotzdem fürs Mitmachen!';
|
||||||
this.stepMsgType = 'info';
|
this.stepMsgType = 'info';
|
||||||
this.showKnownContactData = false;
|
|
||||||
} else {
|
} else {
|
||||||
this.stepMsg = 'Da ist was schiefgelaufen. Versuch es bitte nochmal!';
|
this.stepMsg = 'Da ist was schiefgelaufen. Versuch es bitte nochmal!';
|
||||||
this.stepMsgType = 'danger';
|
this.stepMsgType = 'danger';
|
||||||
@@ -576,34 +649,68 @@
|
|||||||
this.working = false;
|
this.working = false;
|
||||||
},
|
},
|
||||||
|
|
||||||
async submitKnownContactData() {
|
startEdit(index) {
|
||||||
this.stepMsg = '';
|
this.editingContactIndex = index;
|
||||||
this.stepMsgType = '';
|
this.editingContactData = {
|
||||||
|
email: this.enteredContacts[index].email,
|
||||||
|
phone: this.enteredContacts[index].phone || ''
|
||||||
|
};
|
||||||
|
|
||||||
|
// Focus the email input of the specific contact being edited
|
||||||
|
setTimeout(() => {
|
||||||
|
// Find all email inputs and select the one that's currently visible (not d-none)
|
||||||
|
const emailInputs = document.querySelectorAll('.list-group-item input[type="email"]');
|
||||||
|
for (let input of emailInputs) {
|
||||||
|
const parentDiv = input.closest('div[x-show]');
|
||||||
|
if (parentDiv && !parentDiv.classList.contains('d-none')) {
|
||||||
|
input.focus();
|
||||||
|
input.select();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}, 100);
|
||||||
|
},
|
||||||
|
|
||||||
|
cancelEdit() {
|
||||||
|
// If this is a new contact that hasn't been saved, remove it from the list
|
||||||
|
if (this.editingContactIndex >= 0 && this.enteredContacts[this.editingContactIndex].isNew) {
|
||||||
|
this.enteredContacts.splice(this.editingContactIndex, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
this.editingContactIndex = -1;
|
||||||
|
this.editingContactData = { email: '', phone: '' };
|
||||||
|
},
|
||||||
|
|
||||||
|
async saveContactData(index) {
|
||||||
this.working = true;
|
this.working = true;
|
||||||
try {
|
try {
|
||||||
|
const contact = this.enteredContacts[index];
|
||||||
const resp = await axios.post('/api/v1/contact/data', {
|
const resp = await axios.post('/api/v1/contact/data', {
|
||||||
name: this.foundKnownContactName,
|
name: contact.name,
|
||||||
reportedBy: this.userName,
|
reportedBy: this.userName,
|
||||||
email: this.knownContactEmail.trim(),
|
email: this.editingContactData.email.trim(),
|
||||||
phone: this.knownContactPhone.trim()
|
phone: this.editingContactData.phone.trim()
|
||||||
}, { validateStatus: () => true });
|
}, {
|
||||||
|
headers: this.userToken ? { 'Authorization': this.userToken } : {},
|
||||||
|
validateStatus: () => true
|
||||||
|
});
|
||||||
|
|
||||||
if (resp.status === 200 || resp.status === 201) {
|
if (resp.status === 200 || resp.status === 201) {
|
||||||
this.enteredContacts = this.enteredContacts.filter((c) => c.name !== this.foundKnownContactName);
|
// Update the contact in our local list
|
||||||
this.enteredContacts.push({
|
this.enteredContacts[index].email = this.editingContactData.email.trim();
|
||||||
name: this.foundKnownContactName,
|
this.enteredContacts[index].phone = this.editingContactData.phone.trim();
|
||||||
email: this.knownContactEmail.trim(),
|
// Remove the isNew flag since it's now saved
|
||||||
phone: this.knownContactPhone.trim()
|
delete this.enteredContacts[index].isNew;
|
||||||
});
|
|
||||||
this.stepMsg = 'Danke, die Kontaktdaten sind gespeichert! Du kannst noch mehr eintragen oder einfach weitermachen.';
|
this.stepMsg = 'Kontakt erfolgreich gespeichert!';
|
||||||
this.stepMsgType = 'success';
|
this.stepMsgType = 'success';
|
||||||
this.showKnownContactData = false;
|
this.editingContactIndex = -1;
|
||||||
this.knownContactName = '';
|
this.editingContactData = { email: '', phone: '' };
|
||||||
this.foundKnownContactName = null;
|
|
||||||
} else if (resp.status === 400) {
|
} else if (resp.status === 400) {
|
||||||
this.stepMsg = 'Bitte prüfe die Angaben nochmal – da stimmt was nicht.';
|
this.stepMsg = 'Bitte prüfe die Angaben nochmal – da stimmt was nicht.';
|
||||||
this.stepMsgType = 'warning';
|
this.stepMsgType = 'warning';
|
||||||
} else {
|
} else {
|
||||||
this.stepMsg = 'Da ist was schiefgelaufen. Versuch es bitte nochmal!';
|
this.stepMsg = 'Fehler beim Speichern des Kontakts.';
|
||||||
this.stepMsgType = 'danger';
|
this.stepMsgType = 'danger';
|
||||||
}
|
}
|
||||||
} catch {
|
} catch {
|
||||||
|
|||||||
Reference in New Issue
Block a user