diff --git a/miniapp/index.html b/miniapp/index.html
index 6e53995b..1023062b 100644
--- a/miniapp/index.html
+++ b/miniapp/index.html
@@ -2041,174 +2041,6 @@
border-radius: var(--radius-sm);
}
- .info-item--autopay {
- flex-direction: column;
- align-items: stretch;
- gap: 12px;
- }
-
- .info-item--autopay:hover {
- padding-left: 0;
- padding-right: 0;
- margin: 0;
- background: none;
- }
-
- .info-item--autopay .info-item-header {
- width: 100%;
- display: flex;
- align-items: center;
- justify-content: space-between;
- gap: 12px;
- }
-
- .autopay-controls {
- display: flex;
- flex-direction: column;
- gap: 12px;
- width: 100%;
- }
-
- .autopay-controls.hidden {
- display: none;
- }
-
- .autopay-toggle {
- display: flex;
- gap: 8px;
- }
-
- .autopay-toggle-btn {
- flex: 1;
- padding: 10px 12px;
- border-radius: var(--radius);
- border: 1px solid var(--border-color);
- background: var(--bg-secondary);
- color: var(--text-primary);
- font-size: 13px;
- font-weight: 600;
- cursor: pointer;
- transition: all 0.25s ease;
- }
-
- .autopay-toggle-btn:hover:not(:disabled) {
- border-color: var(--primary);
- color: var(--primary);
- box-shadow: 0 2px 6px rgba(var(--primary-rgb), 0.1);
- }
-
- .autopay-toggle-btn:disabled {
- opacity: 0.6;
- cursor: not-allowed;
- }
-
- .autopay-toggle-btn.active {
- background: rgba(var(--primary-rgb), 0.12);
- border-color: rgba(var(--primary-rgb), 0.6);
- color: var(--primary);
- }
-
- .autopay-slider {
- display: flex;
- flex-direction: column;
- gap: 8px;
- padding: 0 4px;
- }
-
- .autopay-slider.hidden {
- display: none;
- }
-
- .autopay-slider-caption {
- font-size: 12px;
- font-weight: 600;
- color: var(--text-secondary);
- }
-
- .autopay-slider-input {
- width: 100%;
- appearance: none;
- height: 6px;
- border-radius: 999px;
- background: var(--border-color);
- outline: none;
- transition: background 0.3s ease;
- }
-
- .autopay-slider-input::-webkit-slider-thumb {
- appearance: none;
- width: 18px;
- height: 18px;
- border-radius: 50%;
- background: var(--primary);
- border: 2px solid var(--bg-primary);
- cursor: pointer;
- box-shadow: 0 2px 6px rgba(var(--primary-rgb), 0.3);
- transition: transform 0.2s ease, background 0.3s ease;
- }
-
- .autopay-slider-input::-moz-range-thumb {
- width: 18px;
- height: 18px;
- border-radius: 50%;
- background: var(--primary);
- border: 2px solid var(--bg-primary);
- cursor: pointer;
- box-shadow: 0 2px 6px rgba(var(--primary-rgb), 0.3);
- transition: transform 0.2s ease, background 0.3s ease;
- }
-
- .autopay-slider-input:disabled::-webkit-slider-thumb,
- .autopay-slider-input:disabled::-moz-range-thumb {
- background: var(--border-color);
- box-shadow: none;
- cursor: not-allowed;
- }
-
- .autopay-slider-input::-webkit-slider-thumb:hover,
- .autopay-slider-input::-moz-range-thumb:hover {
- transform: scale(1.05);
- }
-
- .autopay-slider-marks {
- display: flex;
- justify-content: space-between;
- align-items: flex-start;
- font-size: 11px;
- font-weight: 600;
- color: var(--text-secondary);
- }
-
- .autopay-slider-mark {
- flex: 1;
- text-align: center;
- position: relative;
- padding-top: 6px;
- user-select: none;
- }
-
- .autopay-slider-mark::before {
- content: '';
- position: absolute;
- top: 0;
- left: 50%;
- width: 6px;
- height: 6px;
- border-radius: 50%;
- background: var(--border-color);
- transform: translateX(-50%);
- transition: background 0.3s ease, transform 0.3s ease;
- }
-
- .autopay-slider-mark.active {
- color: var(--text-primary);
- }
-
- .autopay-slider-mark.active::before {
- background: var(--primary);
- transform: translateX(-50%) scale(1.2);
- }
-
.info-label {
font-size: 14px;
color: var(--text-secondary);
@@ -4712,42 +4544,9 @@
Device Limit
-
-
-
-
-
-
-
-
-
-
+
+ Auto-Pay
+ -
@@ -5335,7 +5134,6 @@
setupSubscriptionSettingsEvents();
setupSubscriptionPurchaseEvents();
setupSubscriptionRenewalEvents();
- setupAutopayControlsEvents();
const themeToggle = document.getElementById('themeToggle');
const THEME_STORAGE_KEY = 'remnawave-miniapp-theme';
@@ -5787,18 +5585,6 @@
'trial.activation.error.already_active': 'You already have an active subscription.',
'autopay.enabled': 'Enabled',
'autopay.disabled': 'Disabled',
- 'autopay.toggle.enable': 'Enable auto-pay',
- 'autopay.toggle.disable': 'Disable auto-pay',
- 'autopay.update_in_progress': 'Updating…',
- 'autopay.slider.caption': 'Charge {count} days before renewal',
- 'autopay.slider.caption.one': 'Charge {count} day before renewal',
- 'autopay.slider.hint': 'Choose when to charge automatically.',
- 'autopay.days.label': '{count} days',
- 'autopay.days.label.one': '{count} day',
- 'autopay.error.generic': 'Failed to update auto-pay settings. Please try again later.',
- 'autopay.success.enabled': 'Auto-pay enabled.',
- 'autopay.success.disabled': 'Auto-pay disabled.',
- 'autopay.success.updated': 'Auto-pay schedule updated.',
'platform.ios': 'iOS',
'platform.android': 'Android',
'platform.pc': 'PC',
@@ -6176,18 +5962,6 @@
'trial.activation.error.already_active': 'У вас уже есть активная подписка.',
'autopay.enabled': 'Включен',
'autopay.disabled': 'Выключен',
- 'autopay.toggle.enable': 'Включить автоплатеж',
- 'autopay.toggle.disable': 'Отключить автоплатеж',
- 'autopay.update_in_progress': 'Обновляем…',
- 'autopay.slider.caption': 'Списывать за {count} дн. до окончания',
- 'autopay.slider.caption.one': 'Списывать за {count} день до окончания',
- 'autopay.slider.hint': 'Выберите, за сколько дней до окончания списывать оплату автоматически.',
- 'autopay.days.label': '{count} дн.',
- 'autopay.days.label.one': '{count} день',
- 'autopay.error.generic': 'Не удалось обновить автоплатеж. Попробуйте позже.',
- 'autopay.success.enabled': 'Автоплатеж включен.',
- 'autopay.success.disabled': 'Автоплатеж отключен.',
- 'autopay.success.updated': 'Настройки автоплатежа обновлены.',
'platform.ios': 'iOS',
'platform.android': 'Android',
'platform.pc': 'ПК',
@@ -6343,15 +6117,6 @@
const activePaymentMonitors = new Map();
let paymentStatusPollTimer = null;
let isPaymentStatusPolling = false;
- const autopayState = {
- enabled: false,
- daysBefore: null,
- options: [],
- previewDays: null,
- updating: false,
- pendingAction: null,
- available: false,
- };
let subscriptionSettingsData = null;
let subscriptionSettingsPromise = null;
let subscriptionSettingsError = null;
@@ -7489,7 +7254,6 @@
detectPlatform();
setActivePlatformButton();
- syncAutopayStateFromUserData(userData);
refreshAfterLanguageChange();
animateCardsOnce();
@@ -7682,8 +7446,6 @@
: autopayLabel;
}
- renderAutopayControls();
-
renderSubscriptionMissingCard();
renderSubscriptionPurchaseCard();
renderSubscriptionRenewalCard();
@@ -7701,553 +7463,6 @@
updateActionButtons();
}
- function resolveAutopayString(key, fallback) {
- const value = t(key);
- if (value && value !== key) {
- return value;
- }
- return fallback;
- }
-
- function normalizeAutopaySourceValues(source) {
- if (Array.isArray(source)) {
- return source;
- }
- if (source === undefined || source === null) {
- return [];
- }
- if (typeof source === 'number') {
- return [source];
- }
- if (typeof source === 'string') {
- return source
- .split(/[,;\s]+/)
- .map(entry => entry.trim())
- .filter(Boolean);
- }
- if (typeof source === 'object') {
- const collected = [];
- if (Array.isArray(source.options)) {
- collected.push(...source.options);
- }
- if (Array.isArray(source.values)) {
- collected.push(...source.values);
- }
- if (Array.isArray(source.days)) {
- collected.push(...source.days);
- }
- if (Array.isArray(source.list)) {
- collected.push(...source.list);
- }
- ['min', 'max', 'default', 'value', 'days_before', 'daysBefore'].forEach(key => {
- if (source[key] !== undefined && source[key] !== null) {
- collected.push(source[key]);
- }
- });
- return collected;
- }
- return [];
- }
-
- function resolveAutopayOptions(data = userData) {
- const sources = [
- data?.autopay_days_options,
- data?.autopayDaysOptions,
- data?.autopay_warning_days,
- data?.autopayWarningDays,
- data?.autopay?.days_before_options,
- data?.autopay?.daysBeforeOptions,
- data?.autopay?.options,
- data?.autopay?.values,
- appsConfig?.autopay_days_options,
- appsConfig?.autopayDaysOptions,
- appsConfig?.autopay_warning_days,
- appsConfig?.autopayWarningDays,
- ];
- const values = new Set();
- sources.forEach(source => {
- normalizeAutopaySourceValues(source).forEach(entry => {
- const number = coercePositiveInt(entry, null);
- if (number !== null && number > 0) {
- values.add(number);
- }
- });
- });
- if (values.size === 0) {
- return [1, 3];
- }
- return Array.from(values).sort((a, b) => a - b);
- }
-
- function extractAutopayDaysValue(data = userData) {
- const candidates = [
- data?.autopay_days_before,
- data?.autopayDaysBefore,
- data?.autopay?.days_before,
- data?.autopay?.daysBefore,
- data?.user?.autopay_days_before,
- data?.user?.autopayDaysBefore,
- ];
- for (const candidate of candidates) {
- const value = coercePositiveInt(candidate, null);
- if (value !== null) {
- return value;
- }
- }
- return null;
- }
-
- function syncAutopayStateFromUserData(data = userData) {
- if (!data) {
- autopayState.available = false;
- autopayState.enabled = false;
- autopayState.options = [];
- autopayState.daysBefore = null;
- autopayState.previewDays = null;
- return;
- }
-
- const subscriptionMissing = Boolean(data.subscription_missing ?? data.subscriptionMissing);
- const hasSubscription = Boolean(data.subscription_id ?? data.subscriptionId);
- const available = hasSubscription && !subscriptionMissing && hasPaidSubscription();
- autopayState.available = available;
-
- const enabled = Boolean(data.autopay_enabled ?? data.autopayEnabled);
- autopayState.enabled = enabled;
-
- const options = resolveAutopayOptions(data);
- const daysValue = extractAutopayDaysValue(data);
-
- const normalizedOptions = Array.isArray(options) ? options.slice() : [];
- if (daysValue !== null && !normalizedOptions.includes(daysValue)) {
- normalizedOptions.push(daysValue);
- }
- normalizedOptions.sort((a, b) => a - b);
- autopayState.options = normalizedOptions;
-
- if (daysValue !== null) {
- autopayState.daysBefore = daysValue;
- } else if (!autopayState.daysBefore || !normalizedOptions.includes(autopayState.daysBefore)) {
- autopayState.daysBefore = normalizedOptions.length
- ? normalizedOptions[normalizedOptions.length - 1]
- : null;
- }
-
- if (!available) {
- autopayState.previewDays = null;
- }
- }
-
- function getAutopayActiveDays() {
- if (autopayState.previewDays !== null && autopayState.previewDays !== undefined) {
- return autopayState.previewDays;
- }
- if (autopayState.daysBefore !== null && autopayState.daysBefore !== undefined) {
- return autopayState.daysBefore;
- }
- if (autopayState.options.length) {
- return autopayState.options[autopayState.options.length - 1];
- }
- return null;
- }
-
- function formatAutopayDaysLabel(days) {
- const value = coercePositiveInt(days, null);
- if (value === null) {
- return '';
- }
- const key = value === 1 ? 'autopay.days.label.one' : 'autopay.days.label';
- const template = t(key);
- if (template && template !== key) {
- return template.replace('{count}', String(value));
- }
- return value === 1 ? `${value} day` : `${value} days`;
- }
-
- function formatAutopayCaption(days) {
- const value = coercePositiveInt(days, null);
- if (value === null) {
- return resolveAutopayString('autopay.slider.hint', 'Choose when to charge automatically.');
- }
- const key = value === 1 ? 'autopay.slider.caption.one' : 'autopay.slider.caption';
- const template = t(key);
- if (template && template !== key) {
- return template.replace('{count}', String(value));
- }
- return value === 1
- ? `Charge ${value} day before renewal`
- : `Charge ${value} days before renewal`;
- }
-
- function updateAutopaySliderTrack(slider, activeIndex) {
- if (!slider) {
- return;
- }
- const hasMultiple = autopayState.options.length > 1;
- if (!autopayState.enabled || !hasMultiple) {
- slider.style.background = `linear-gradient(90deg, var(--border-color) 0%, var(--border-color) 100%)`;
- return;
- }
- const maxIndex = autopayState.options.length - 1;
- const safeIndex = Math.max(0, Math.min(maxIndex, activeIndex || 0));
- const percentage = (safeIndex / maxIndex) * 100;
- slider.style.background = `linear-gradient(90deg, rgba(var(--primary-rgb), 0.7) 0%, rgba(var(--primary-rgb), 0.7) ${percentage}%, var(--border-color) ${percentage}%, var(--border-color) 100%)`;
- }
-
- function renderAutopayControls() {
- const controls = document.getElementById('autopayControls');
- if (!controls) {
- return;
- }
-
- const shouldShowControls = autopayState.available;
- controls.classList.toggle('hidden', !shouldShowControls);
- if (!shouldShowControls) {
- return;
- }
-
- const enableBtn = document.getElementById('autopayEnableBtn');
- const disableBtn = document.getElementById('autopayDisableBtn');
- const sliderWrapper = document.getElementById('autopaySliderWrapper');
- const slider = document.getElementById('autopaySlider');
- const marksContainer = document.getElementById('autopaySliderMarks');
- const caption = document.getElementById('autopaySliderLabel');
-
- const activeDays = getAutopayActiveDays();
- const options = autopayState.options;
- const hasSlider = autopayState.enabled && options.length > 0;
-
- if (enableBtn) {
- const key = autopayState.updating && autopayState.pendingAction === 'enable'
- ? 'autopay.update_in_progress'
- : 'autopay.toggle.enable';
- const fallback = autopayState.updating && autopayState.pendingAction === 'enable'
- ? 'Updating…'
- : 'Enable auto-pay';
- enableBtn.textContent = resolveAutopayString(key, fallback);
- enableBtn.disabled = autopayState.updating || autopayState.enabled;
- enableBtn.classList.toggle('active', autopayState.enabled);
- enableBtn.setAttribute('aria-pressed', autopayState.enabled ? 'true' : 'false');
- }
-
- if (disableBtn) {
- const key = autopayState.updating && autopayState.pendingAction === 'disable'
- ? 'autopay.update_in_progress'
- : 'autopay.toggle.disable';
- const fallback = autopayState.updating && autopayState.pendingAction === 'disable'
- ? 'Updating…'
- : 'Disable auto-pay';
- disableBtn.textContent = resolveAutopayString(key, fallback);
- disableBtn.disabled = autopayState.updating || !autopayState.enabled;
- disableBtn.classList.toggle('active', !autopayState.enabled);
- disableBtn.setAttribute('aria-pressed', autopayState.enabled ? 'false' : 'true');
- }
-
- if (sliderWrapper) {
- sliderWrapper.classList.toggle('hidden', !hasSlider);
- }
-
- if (caption) {
- caption.textContent = hasSlider && activeDays !== null
- ? formatAutopayCaption(activeDays)
- : resolveAutopayString('autopay.slider.hint', 'Choose when to charge automatically.');
- }
-
- if (slider) {
- const maxIndex = Math.max(options.length - 1, 0);
- slider.setAttribute('aria-valuemin', '0');
- slider.setAttribute('aria-valuemax', String(maxIndex));
- slider.disabled = autopayState.updating || !autopayState.enabled || options.length <= 1;
-
- if (options.length > 0) {
- let activeIndex = options.findIndex(value => value === activeDays);
- if (activeIndex < 0) {
- activeIndex = options.length - 1;
- }
- slider.max = String(Math.max(options.length - 1, 0));
- slider.value = String(Math.max(activeIndex, 0));
- slider.setAttribute('aria-valuenow', activeDays !== null ? String(activeDays) : '0');
- slider.setAttribute('aria-label', formatAutopayCaption(activeDays));
- updateAutopaySliderTrack(slider, activeIndex);
- } else {
- slider.max = '0';
- slider.value = '0';
- slider.setAttribute('aria-valuenow', '0');
- slider.setAttribute('aria-label', resolveAutopayString('autopay.slider.hint', 'Choose when to charge automatically.'));
- slider.style.background = `linear-gradient(90deg, var(--border-color) 0%, var(--border-color) 100%)`;
- }
- }
-
- if (marksContainer) {
- marksContainer.innerHTML = '';
- if (hasSlider && options.length) {
- const activeValue = activeDays;
- options.forEach((value, index) => {
- const mark = document.createElement('div');
- mark.className = 'autopay-slider-mark';
- if (value === activeValue) {
- mark.classList.add('active');
- }
- mark.textContent = formatAutopayDaysLabel(value);
- if (!slider?.disabled) {
- mark.style.cursor = 'pointer';
- mark.addEventListener('click', () => {
- if (autopayState.updating || !autopayState.enabled) {
- return;
- }
- const sliderElement = document.getElementById('autopaySlider');
- if (!sliderElement) {
- return;
- }
- sliderElement.value = String(index);
- sliderElement.dispatchEvent(new Event('input'));
- sliderElement.dispatchEvent(new Event('change'));
- });
- }
- marksContainer.appendChild(mark);
- });
- }
- }
- }
-
- function handleAutopayToggle(enabled) {
- if (autopayState.updating || !autopayState.available) {
- return;
- }
- if (autopayState.enabled === enabled) {
- return;
- }
-
- const previousEnabled = autopayState.enabled;
- const previousDays = autopayState.daysBefore;
- const targetDays = autopayState.daysBefore
- ?? (autopayState.options.length ? autopayState.options[autopayState.options.length - 1] : null);
-
- autopayState.enabled = enabled;
- autopayState.previewDays = null;
- renderAutopayControls();
-
- submitAutopayUpdate({
- enabled,
- daysBefore: targetDays,
- action: enabled ? 'enable' : 'disable',
- }).catch(error => {
- console.warn('Failed to toggle autopay:', error);
- autopayState.enabled = previousEnabled;
- autopayState.daysBefore = previousDays;
- renderAutopayControls();
- });
- }
-
- function handleAutopaySliderInput(event) {
- if (!autopayState.options.length) {
- return;
- }
- const index = Math.round(Number(event.target.value) || 0);
- const safeIndex = Math.max(0, Math.min(autopayState.options.length - 1, index));
- autopayState.previewDays = autopayState.options[safeIndex];
- renderAutopayControls();
- }
-
- function handleAutopaySliderChange(event) {
- if (!autopayState.options.length) {
- return;
- }
- const index = Math.round(Number(event.target.value) || 0);
- const safeIndex = Math.max(0, Math.min(autopayState.options.length - 1, index));
- const selected = autopayState.options[safeIndex];
- autopayState.previewDays = null;
-
- if (selected === autopayState.daysBefore) {
- renderAutopayControls();
- return;
- }
-
- const previousDays = autopayState.daysBefore;
- autopayState.daysBefore = selected;
- renderAutopayControls();
-
- if (!autopayState.enabled) {
- return;
- }
-
- submitAutopayUpdate({
- enabled: true,
- daysBefore: selected,
- action: 'days',
- }).catch(error => {
- console.warn('Failed to update autopay days:', error);
- autopayState.daysBefore = previousDays;
- renderAutopayControls();
- });
- }
-
- async function submitAutopayUpdate(options) {
- const { enabled, daysBefore, action } = options || {};
- const initData = tg.initData || '';
- if (!initData) {
- const error = createError('Authorization Error', t('subscription_settings.error.unauthorized'));
- showPopup(error.message, resolveAutopayString('info.autopay', 'Auto-pay'));
- throw error;
- }
-
- const subscriptionId = userData?.subscription_id ?? userData?.subscriptionId ?? null;
- if (!subscriptionId) {
- const fallback = resolveAutopayString('autopay.error.generic', 'Failed to update auto-pay settings. Please try again later.');
- const error = createError('Autopay Error', fallback);
- showPopup(error.message, resolveAutopayString('info.autopay', 'Auto-pay'));
- throw error;
- }
-
- const payload = {
- initData,
- subscription_id: subscriptionId,
- subscriptionId,
- enabled,
- autopay_enabled: enabled,
- autopayEnabled: enabled,
- };
-
- const daysValue = coercePositiveInt(daysBefore, null);
- if (daysValue !== null) {
- payload.days_before = daysValue;
- payload.daysBefore = daysValue;
- payload.autopay_days_before = daysValue;
- payload.autopayDaysBefore = daysValue;
- }
-
- autopayState.updating = true;
- autopayState.pendingAction = action || (enabled ? 'enable' : 'disable');
- renderAutopayControls();
-
- try {
- const response = await fetch('/miniapp/subscription/autopay', {
- method: 'POST',
- headers: { 'Content-Type': 'application/json' },
- body: JSON.stringify(payload),
- });
- const body = await parseJsonSafe(response);
- if (!response.ok || (body && body.success === false)) {
- const message = extractAutopayError(body, response.status);
- throw createError('Autopay update error', message, response.status);
- }
-
- if (!userData) {
- userData = {};
- }
- userData.autopay_enabled = enabled;
- userData.autopayEnabled = enabled;
- if (daysValue !== null) {
- userData.autopay_days_before = daysValue;
- userData.autopayDaysBefore = daysValue;
- }
-
- autopayState.enabled = enabled;
- if (daysValue !== null) {
- autopayState.daysBefore = daysValue;
- }
- autopayState.previewDays = null;
-
- const successKey = action === 'days'
- ? 'autopay.success.updated'
- : enabled
- ? 'autopay.success.enabled'
- : 'autopay.success.disabled';
- const successFallback = action === 'days'
- ? 'Auto-pay schedule updated.'
- : enabled
- ? 'Auto-pay enabled.'
- : 'Auto-pay disabled.';
- showPopup(resolveAutopayString(successKey, successFallback), resolveAutopayString('info.autopay', 'Auto-pay'));
-
- renderUserData();
-
- try {
- await refreshSubscriptionData({ silent: true });
- } catch (refreshError) {
- console.warn('Failed to refresh subscription after autopay update:', refreshError);
- }
-
- return true;
- } catch (error) {
- const message = resolveAutopayErrorMessage(error);
- showPopup(message, resolveAutopayString('info.autopay', 'Auto-pay'));
- throw error;
- } finally {
- autopayState.updating = false;
- autopayState.pendingAction = null;
- renderAutopayControls();
- }
- }
-
- function extractAutopayError(payload, status) {
- if (status === 401) {
- return t('subscription_settings.error.unauthorized');
- }
- if (!payload || typeof payload !== 'object') {
- return resolveAutopayString('autopay.error.generic', 'Failed to update auto-pay settings. Please try again later.');
- }
- if (typeof payload.detail === 'string') {
- return payload.detail;
- }
- if (payload.detail && typeof payload.detail === 'object') {
- if (typeof payload.detail.message === 'string') {
- return payload.detail.message;
- }
- if (typeof payload.detail.error === 'string') {
- return payload.detail.error;
- }
- }
- if (typeof payload.message === 'string') {
- return payload.message;
- }
- if (typeof payload.error === 'string') {
- return payload.error;
- }
- return resolveAutopayString('autopay.error.generic', 'Failed to update auto-pay settings. Please try again later.');
- }
-
- function resolveAutopayErrorMessage(error) {
- if (!error) {
- return resolveAutopayString('autopay.error.generic', 'Failed to update auto-pay settings. Please try again later.');
- }
- if (typeof error === 'string') {
- return error;
- }
- if (typeof error.message === 'string' && error.message.trim()) {
- return error.message;
- }
- if (error.detail) {
- if (typeof error.detail === 'string' && error.detail.trim()) {
- return error.detail;
- }
- if (typeof error.detail.message === 'string' && error.detail.message.trim()) {
- return error.detail.message;
- }
- }
- if (error.status === 401) {
- const unauthorized = t('subscription_settings.error.unauthorized');
- if (unauthorized && unauthorized !== 'subscription_settings.error.unauthorized') {
- return unauthorized;
- }
- }
- return resolveAutopayString('autopay.error.generic', 'Failed to update auto-pay settings. Please try again later.');
- }
-
- function setupAutopayControlsEvents() {
- document.getElementById('autopayEnableBtn')?.addEventListener('click', () => {
- handleAutopayToggle(true);
- });
- document.getElementById('autopayDisableBtn')?.addEventListener('click', () => {
- handleAutopayToggle(false);
- });
- const slider = document.getElementById('autopaySlider');
- if (slider) {
- slider.addEventListener('input', handleAutopaySliderInput);
- slider.addEventListener('change', handleAutopaySliderChange);
- }
- }
-
function renderSubscriptionMissingCard() {
const card = document.getElementById('subscriptionMissingCard');
if (!card) {