Skip to content

Commit 21b71e4

Browse files
itsDNNSclaude
andcommitted
Change ISP field to dropdown with common providers and Other option
Dropdown lists Vodafone, PYUR, eazy, O2, 1&1, Telekom, NetCologne, M-net, Wilhelm.tel. Selecting "Other" reveals a free text input. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
1 parent 7f3da6b commit 21b71e4

File tree

4 files changed

+68
-11
lines changed

4 files changed

+68
-11
lines changed

CHANGELOG.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,11 @@ All notable changes to this project will be documented in this file.
44

55
Versioning: `YYYY-MM-DD.N` (date + sequential build number per day)
66

7+
## [2026-02-09.8]
8+
9+
### Changed
10+
- **ISP selection**: Dropdown with common German cable ISPs + "Other" option with free text input
11+
712
## [2026-02-09.7]
813

914
### Added

app/i18n.py

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -121,7 +121,11 @@
121121

122122
# ISP
123123
"isp_name": "Internet Provider",
124-
"isp_hint": "e.g. Vodafone, Telekom, O2 (shown in export)",
124+
"isp_hint": "Shown in LLM export report",
125+
"isp_other": "Other",
126+
"isp_other_placeholder": "Enter provider name",
127+
"isp_select": "Select provider",
128+
"isp_options": ["Vodafone", "PYUR", "eazy", "O2", "1&1", "Telekom", "NetCologne", "M-net", "Wilhelm.tel"],
125129

126130
# Export
127131
"export_llm": "Export for LLM",
@@ -239,7 +243,11 @@
239243
"language": "Sprache",
240244

241245
"isp_name": "Internetanbieter",
242-
"isp_hint": "z.B. Vodafone, Telekom, O2 (wird im Export angezeigt)",
246+
"isp_hint": "Wird im LLM-Export angezeigt",
247+
"isp_other": "Andere",
248+
"isp_other_placeholder": "Anbietername eingeben",
249+
"isp_select": "Anbieter waehlen",
250+
"isp_options": ["Vodafone", "PYUR", "eazy", "O2", "1&1", "Telekom", "NetCologne", "M-net", "Wilhelm.tel"],
243251

244252
"export_llm": "Export fuer LLM",
245253
"export_title": "LLM-Analyse Export",

app/templates/settings.html

Lines changed: 26 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -209,11 +209,21 @@ <h2>{{ t.mqtt_broker }} <span style="font-size:0.75em; font-weight:normal; color
209209
<div class="section">
210210
<h2>{{ t.general }}</h2>
211211
<div class="form-grid">
212-
<div class="form-row full">
213-
<label for="isp_name">{{ t.isp_name }}</label>
214-
<input type="text" id="isp_name" name="isp_name" value="{{ config.isp_name }}">
212+
<div class="form-row">
213+
<label for="isp_select">{{ t.isp_name }}</label>
214+
<select id="isp_select" name="isp_select" onchange="onIspChange()">
215+
<option value="">{{ t.isp_select }}</option>
216+
{% for isp in t.isp_options %}
217+
<option value="{{ isp }}" {% if config.isp_name == isp %}selected{% endif %}>{{ isp }}</option>
218+
{% endfor %}
219+
<option value="__other__" {% if config.isp_name and config.isp_name not in t.isp_options %}selected{% endif %}>{{ t.isp_other }}</option>
220+
</select>
215221
<span class="hint">{{ t.isp_hint }}</span>
216222
</div>
223+
<div class="form-row" id="isp-other-row" style="display:{% if config.isp_name and config.isp_name not in t.isp_options %}block{% else %}none{% endif %}">
224+
<label for="isp_other_input">{{ t.isp_other }}</label>
225+
<input type="text" id="isp_other_input" value="{% if config.isp_name and config.isp_name not in t.isp_options %}{{ config.isp_name }}{% endif %}" placeholder="{{ t.isp_other_placeholder }}">
226+
</div>
217227
<div class="form-row">
218228
<label for="poll_interval">{{ t.interval_sec }}</label>
219229
<input type="number" id="poll_interval" name="poll_interval" value="{{ config.poll_interval }}" min="{{ poll_min }}" max="{{ poll_max }}">
@@ -261,6 +271,12 @@ <h2>{{ t.general }}</h2>
261271
}
262272
})();
263273

274+
function onIspChange() {
275+
var sel = document.getElementById('isp_select');
276+
var row = document.getElementById('isp-other-row');
277+
row.style.display = sel.value === '__other__' ? 'block' : 'none';
278+
}
279+
264280
function showToast(msg, ok) {
265281
var el = document.getElementById('toast');
266282
el.textContent = msg;
@@ -275,13 +291,19 @@ <h2>{{ t.general }}</h2>
275291
function getFormData() {
276292
var form = document.getElementById('settings-form');
277293
var data = {};
278-
form.querySelectorAll('input:not(#theme-check), select').forEach(function(inp) {
294+
form.querySelectorAll('input:not(#theme-check):not(#isp_other_input), select:not(#isp_select)').forEach(function(inp) {
279295
if (SECRET_FIELDS.indexOf(inp.name) !== -1) {
280296
data[inp.name] = inp.value || MASK;
281297
} else {
282298
data[inp.name] = inp.value;
283299
}
284300
});
301+
var ispSel = document.getElementById('isp_select');
302+
if (ispSel.value === '__other__') {
303+
data.isp_name = document.getElementById('isp_other_input').value;
304+
} else {
305+
data.isp_name = ispSel.value;
306+
}
285307
data.theme = themeCheck.checked ? 'dark' : 'light';
286308
return data;
287309
}

app/templates/setup.html

Lines changed: 27 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,7 @@
9292
color: var(--muted);
9393
margin-bottom: 4px;
9494
}
95-
.form-row input {
95+
.form-row input, .form-row select {
9696
background: var(--input-bg);
9797
border: 1px solid var(--input-border);
9898
border-radius: 4px;
@@ -101,7 +101,7 @@
101101
font-size: 0.95em;
102102
font-family: inherit;
103103
}
104-
.form-row input:focus { outline: none; border-color: var(--accent); }
104+
.form-row input:focus, .form-row select:focus { outline: none; border-color: var(--accent); }
105105
.form-row .hint { font-size: 0.8em; color: var(--muted); margin-top: 2px; }
106106
.form-grid {
107107
display: grid;
@@ -219,11 +219,21 @@ <h2><span class="step-num">1</span>{{ t.fritz_connection }}</h2>
219219
<div class="section">
220220
<h2><span class="step-num">2</span>{{ t.general }}</h2>
221221
<div class="form-grid">
222-
<div class="form-row full">
223-
<label for="isp_name">{{ t.isp_name }}</label>
224-
<input type="text" id="isp_name" name="isp_name" value="{{ config.isp_name }}" placeholder="e.g. Vodafone, Telekom, O2">
222+
<div class="form-row">
223+
<label for="isp_select">{{ t.isp_name }}</label>
224+
<select id="isp_select" onchange="onIspChange()">
225+
<option value="">{{ t.isp_select }}</option>
226+
{% for isp in t.isp_options %}
227+
<option value="{{ isp }}" {% if config.isp_name == isp %}selected{% endif %}>{{ isp }}</option>
228+
{% endfor %}
229+
<option value="__other__" {% if config.isp_name and config.isp_name not in t.isp_options %}selected{% endif %}>{{ t.isp_other }}</option>
230+
</select>
225231
<span class="hint">{{ t.isp_hint }}</span>
226232
</div>
233+
<div class="form-row" id="isp-other-row" style="display:{% if config.isp_name and config.isp_name not in t.isp_options %}block{% else %}none{% endif %}">
234+
<label for="isp_other_input">{{ t.isp_other }}</label>
235+
<input type="text" id="isp_other_input" value="{% if config.isp_name and config.isp_name not in t.isp_options %}{{ config.isp_name }}{% endif %}" placeholder="{{ t.isp_other_placeholder }}">
236+
</div>
227237
<div class="form-row">
228238
<label for="poll_interval">{{ t.interval_sec }}</label>
229239
<input type="number" id="poll_interval" name="poll_interval" value="{{ config.poll_interval }}" min="{{ poll_min }}" max="{{ poll_max }}">
@@ -288,6 +298,12 @@ <h2>{{ t.mqtt_broker }}</h2>
288298
<script>
289299
var T = {{ t|tojson }};
290300

301+
function onIspChange() {
302+
var sel = document.getElementById('isp_select');
303+
var row = document.getElementById('isp-other-row');
304+
row.style.display = sel.value === '__other__' ? 'block' : 'none';
305+
}
306+
291307
function toggleAdvanced() {
292308
var toggle = document.getElementById('mqtt-toggle');
293309
var section = document.getElementById('mqtt-section');
@@ -309,6 +325,12 @@ <h2>{{ t.mqtt_broker }}</h2>
309325
data[inp.name] = inp.value;
310326
}
311327
});
328+
var ispSel = document.getElementById('isp_select');
329+
if (ispSel.value === '__other__') {
330+
data.isp_name = document.getElementById('isp_other_input').value;
331+
} else {
332+
data.isp_name = ispSel.value;
333+
}
312334
data.language = '{{ lang }}';
313335
return data;
314336
}

0 commit comments

Comments
 (0)