changing profile

This commit is contained in:
Flatlogic Bot 2026-01-25 03:55:35 +00:00
parent b4a62485fb
commit 2fc6e81476
4 changed files with 238 additions and 154 deletions

View File

@ -238,6 +238,8 @@
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/js/bootstrap.bundle.min.js"></script>
<!-- Chatbot Widget JS -->
<script src="{% static 'js/chatbot.js' %}?v={{ deployment_timestamp }}"></script>
{% block extra_js %}{% endblock %}
</body>
</html>

View File

@ -185,6 +185,8 @@
{% block extra_js %}
<script>
document.addEventListener('DOMContentLoaded', function() {
console.log("Profile JS loaded");
const emailInput = document.getElementById('id_email');
const phoneInput = document.getElementById('id_phone_number');
const countryCodeInput = document.getElementById('id_country_code');
@ -196,7 +198,12 @@ document.addEventListener('DOMContentLoaded', function() {
const phoneStatus = document.getElementById('phoneStatus');
const saveBtn = document.getElementById('saveProfileBtn');
const otpModal = new bootstrap.Modal(document.getElementById('otpModal'));
const otpModalElem = document.getElementById('otpModal');
if (!otpModalElem) {
console.error("OTP Modal element not found!");
return;
}
const otpModal = new bootstrap.Modal(otpModalElem);
const otpInput = document.getElementById('otpInput');
const confirmOtpBtn = document.getElementById('confirmOtpBtn');
const otpError = document.getElementById('otpError');
@ -205,13 +212,24 @@ document.addEventListener('DOMContentLoaded', function() {
let currentVerificationMethod = '';
let currentVerificationValue = '';
const initialEmail = emailInput.value;
const initialPhone = phoneInput.value;
const initialCountryCode = countryCodeInput.value;
const initialEmail = emailInput ? emailInput.value : '';
const initialPhone = phoneInput ? phoneInput.value : '';
const initialCountryCode = countryCodeInput ? countryCodeInput.value : '';
const csrfTokenElem = document.querySelector('[name=csrfmiddlewaretoken]');
const csrfToken = csrfTokenElem ? csrfTokenElem.value : '';
function isVerified(val) {
return val === 'True' || val === 'true' || val === '1';
}
function updateSaveButtonState() {
const isEmailVerified = emailVerifiedInput.value === 'True';
const isPhoneVerified = phoneVerifiedInput.value === 'True';
if (!emailVerifiedInput || !phoneVerifiedInput || !saveBtn) return;
const isEmailVerified = isVerified(emailVerifiedInput.value);
const isPhoneVerified = isVerified(phoneVerifiedInput.value);
console.log("Status - Email Verified:", isEmailVerified, "Phone Verified:", isPhoneVerified);
// Enable if at least one is verified
if (isEmailVerified || isPhoneVerified) {
@ -221,162 +239,226 @@ document.addEventListener('DOMContentLoaded', function() {
}
}
emailInput.addEventListener('input', function() {
if (this.value !== initialEmail) {
emailVerifiedInput.value = 'False';
emailStatus.innerHTML = '{% trans "Verify" %}';
verifyEmailBtn.classList.remove('btn-success');
verifyEmailBtn.classList.add('btn-outline-secondary');
} else {
if ("{{ profile.email_verified|yesno:'true,false' }}" === "true") {
emailVerifiedInput.value = 'True';
emailStatus.innerHTML = '<i class="fa-solid fa-check-circle text-success"></i> {% trans "Verified" %}';
}
}
updateSaveButtonState();
});
phoneInput.addEventListener('input', function() {
if (this.value !== initialPhone) {
phoneVerifiedInput.value = 'False';
phoneStatus.innerHTML = '{% trans "Verify" %}';
verifyPhoneBtn.classList.remove('btn-success');
verifyPhoneBtn.classList.add('btn-outline-secondary');
} else {
if ("{{ profile.phone_verified|yesno:'true,false' }}" === "true" && countryCodeInput.value === initialCountryCode) {
phoneVerifiedInput.value = 'True';
phoneStatus.innerHTML = '<i class="fa-solid fa-check-circle text-success"></i> {% trans "Verified" %}';
}
}
updateSaveButtonState();
});
countryCodeInput.addEventListener('change', function() {
if (this.value !== initialCountryCode) {
phoneVerifiedInput.value = 'False';
phoneStatus.innerHTML = '{% trans "Verify" %}';
} else {
if ("{{ profile.phone_verified|yesno:'true,false' }}" === "true" && phoneInput.value === initialPhone) {
phoneVerifiedInput.value = 'True';
phoneStatus.innerHTML = '<i class="fa-solid fa-check-circle text-success"></i> {% trans "Verified" %}';
}
}
updateSaveButtonState();
});
verifyEmailBtn.addEventListener('click', function() {
if (emailVerifiedInput.value === 'True') return;
const email = emailInput.value;
if (!email) return;
verifyEmailBtn.disabled = true;
verifyEmailBtn.innerHTML = '<span class="spinner-border spinner-border-sm"></span>';
fetch("{% url 'send_otp_profile' %}", {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
method: 'email',
value: email
})
})
.then(response => response.json())
.then(data => {
verifyEmailBtn.disabled = false;
verifyEmailBtn.innerHTML = '{% trans "Verify" %}';
if (data.success) {
currentVerificationMethod = 'email';
currentVerificationValue = email;
otpSentMsg.innerText = '{% trans "A code was sent to" %} ' + email;
otpInput.value = '';
otpError.classList.add('d-none');
otpModal.show();
if (emailInput) {
emailInput.addEventListener('input', function() {
if (this.value !== initialEmail) {
emailVerifiedInput.value = 'False';
emailStatus.innerHTML = '{% trans "Verify" %}';
verifyEmailBtn.classList.remove('btn-success');
verifyEmailBtn.classList.add('btn-outline-secondary');
} else {
alert(data.error);
}
});
});
verifyPhoneBtn.addEventListener('click', function() {
if (phoneVerifiedInput.value === 'True') return;
const phone = phoneInput.value;
const countryCode = countryCodeInput.value;
if (!phone) return;
verifyPhoneBtn.disabled = true;
verifyPhoneBtn.innerHTML = '<span class="spinner-border spinner-border-sm"></span>';
fetch("{% url 'send_otp_profile' %}", {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
method: 'phone',
value: phone,
country_code: countryCode
})
})
.then(response => response.json())
.then(data => {
verifyPhoneBtn.disabled = false;
verifyPhoneBtn.innerHTML = '{% trans "Verify" %}';
if (data.success) {
currentVerificationMethod = 'phone';
currentVerificationValue = phone;
otpSentMsg.innerText = '{% trans "A code was sent to WhatsApp number" %} ' + countryCode + phone;
otpInput.value = '';
otpError.classList.add('d-none');
otpModal.show();
} else {
alert(data.error);
}
});
});
confirmOtpBtn.addEventListener('click', function() {
const otp = otpInput.value;
if (otp.length !== 6) return;
confirmOtpBtn.disabled = true;
confirmOtpBtn.innerHTML = '<span class="spinner-border spinner-border-sm"></span>';
fetch("{% url 'verify_otp_profile' %}", {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
method: currentVerificationMethod,
value: currentVerificationValue,
country_code: countryCodeInput.value,
code: otp
})
})
.then(response => response.json())
.then(data => {
confirmOtpBtn.disabled = false;
confirmOtpBtn.innerHTML = '{% trans "Verify" %}';
if (data.success) {
if (currentVerificationMethod === 'email') {
if ("{{ profile.email_verified|yesno:'true,false' }}" === "true") {
emailVerifiedInput.value = 'True';
emailStatus.innerHTML = '<i class="fa-solid fa-check-circle text-success"></i> {% trans "Verified" %}';
} else {
}
}
updateSaveButtonState();
});
}
if (phoneInput) {
phoneInput.addEventListener('input', function() {
if (this.value !== initialPhone) {
phoneVerifiedInput.value = 'False';
phoneStatus.innerHTML = '{% trans "Verify" %}';
verifyPhoneBtn.classList.remove('btn-success');
verifyPhoneBtn.classList.add('btn-outline-secondary');
} else {
if ("{{ profile.phone_verified|yesno:'true,false' }}" === "true" && countryCodeInput.value === initialCountryCode) {
phoneVerifiedInput.value = 'True';
phoneStatus.innerHTML = '<i class="fa-solid fa-check-circle text-success"></i> {% trans "Verified" %}';
}
otpModal.hide();
updateSaveButtonState();
} else {
otpError.innerText = data.error;
otpError.classList.remove('d-none');
}
updateSaveButtonState();
});
});
}
if (countryCodeInput) {
countryCodeInput.addEventListener('change', function() {
if (this.value !== initialCountryCode) {
phoneVerifiedInput.value = 'False';
phoneStatus.innerHTML = '{% trans "Verify" %}';
} else {
if ("{{ profile.phone_verified|yesno:'true,false' }}" === "true" && phoneInput.value === initialPhone) {
phoneVerifiedInput.value = 'True';
phoneStatus.innerHTML = '<i class="fa-solid fa-check-circle text-success"></i> {% trans "Verified" %}';
}
}
updateSaveButtonState();
});
}
if (verifyEmailBtn) {
verifyEmailBtn.addEventListener('click', function() {
console.log("Verify Email clicked");
if (isVerified(emailVerifiedInput.value)) {
console.log("Email already verified");
return;
}
const email = emailInput.value;
if (!email) {
alert('{% trans "Please enter an email address" %}');
return;
}
verifyEmailBtn.disabled = true;
const originalHTML = verifyEmailBtn.innerHTML;
verifyEmailBtn.innerHTML = '<span class="spinner-border spinner-border-sm"></span>';
fetch("{% url 'send_otp_profile' %}", {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'X-CSRFToken': csrfToken
},
body: JSON.stringify({
method: 'email',
value: email
})
})
.then(response => {
if (!response.ok) throw new Error('Network response was not ok');
return response.json();
})
.then(data => {
verifyEmailBtn.disabled = false;
verifyEmailBtn.innerHTML = originalHTML;
if (data.success) {
currentVerificationMethod = 'email';
currentVerificationValue = email;
otpSentMsg.innerText = '{% trans "A code was sent to" %} ' + email;
otpInput.value = '';
otpError.classList.add('d-none');
otpModal.show();
} else {
alert(data.error || '{% trans "Failed to send code" %}');
}
})
.catch(error => {
console.error("Fetch error:", error);
verifyEmailBtn.disabled = false;
verifyEmailBtn.innerHTML = originalHTML;
alert('{% trans "An error occurred. Please try again." %}');
});
});
}
if (verifyPhoneBtn) {
verifyPhoneBtn.addEventListener('click', function() {
console.log("Verify Phone clicked");
if (isVerified(phoneVerifiedInput.value)) {
console.log("Phone already verified");
return;
}
const phone = phoneInput.value;
const countryCode = countryCodeInput.value;
if (!phone) {
alert('{% trans "Please enter a phone number" %}');
return;
}
verifyPhoneBtn.disabled = true;
const originalHTML = verifyPhoneBtn.innerHTML;
verifyPhoneBtn.innerHTML = '<span class="spinner-border spinner-border-sm"></span>';
fetch("{% url 'send_otp_profile' %}", {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'X-CSRFToken': csrfToken
},
body: JSON.stringify({
method: 'phone',
value: phone,
country_code: countryCode
})
})
.then(response => {
if (!response.ok) throw new Error('Network response was not ok');
return response.json();
})
.then(data => {
verifyPhoneBtn.disabled = false;
verifyPhoneBtn.innerHTML = originalHTML;
if (data.success) {
currentVerificationMethod = 'phone';
currentVerificationValue = phone;
otpSentMsg.innerText = '{% trans "A code was sent to WhatsApp number" %} ' + countryCode + phone;
otpInput.value = '';
otpError.classList.add('d-none');
otpModal.show();
} else {
alert(data.error || '{% trans "Failed to send code" %}');
}
})
.catch(error => {
console.error("Fetch error:", error);
verifyPhoneBtn.disabled = false;
verifyPhoneBtn.innerHTML = originalHTML;
alert('{% trans "An error occurred. Please try again." %}');
});
});
}
if (confirmOtpBtn) {
confirmOtpBtn.addEventListener('click', function() {
const otp = otpInput.value;
if (otp.length !== 6) {
otpError.innerText = '{% trans "Please enter a 6-digit code" %}';
otpError.classList.remove('d-none');
return;
}
confirmOtpBtn.disabled = true;
const originalHTML = confirmOtpBtn.innerHTML;
confirmOtpBtn.innerHTML = '<span class="spinner-border spinner-border-sm"></span>';
fetch("{% url 'verify_otp_profile' %}", {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'X-CSRFToken': csrfToken
},
body: JSON.stringify({
method: currentVerificationMethod,
value: currentVerificationValue,
country_code: countryCodeInput.value,
code: otp
})
})
.then(response => {
if (!response.ok) throw new Error('Network response was not ok');
return response.json();
})
.then(data => {
confirmOtpBtn.disabled = false;
confirmOtpBtn.innerHTML = originalHTML;
if (data.success) {
if (currentVerificationMethod === 'email') {
emailVerifiedInput.value = 'True';
emailStatus.innerHTML = '<i class="fa-solid fa-check-circle text-success"></i> {% trans "Verified" %}';
} else {
phoneVerifiedInput.value = 'True';
phoneStatus.innerHTML = '<i class="fa-solid fa-check-circle text-success"></i> {% trans "Verified" %}';
}
otpModal.hide();
updateSaveButtonState();
} else {
otpError.innerText = data.error || '{% trans "Invalid code" %}';
otpError.classList.remove('d-none');
}
})
.catch(error => {
console.error("Fetch error:", error);
confirmOtpBtn.disabled = false;
confirmOtpBtn.innerHTML = originalHTML;
otpError.innerText = '{% trans "An error occurred. Please try again." %}';
otpError.classList.remove('d-none');
});
});
}
// Initial check
updateSaveButtonState();

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.1 KiB