push
This commit is contained in:
292
templates/form.html
Normal file
292
templates/form.html
Normal file
@@ -0,0 +1,292 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Hosts Converter</title>
|
||||
<style>
|
||||
:root {
|
||||
--bg-color: #1a1a1a;
|
||||
--card-bg: #2d2d2d;
|
||||
--text-color: #e0e0e0;
|
||||
--accent: #007bff;
|
||||
--accent-light: #4da6ff;
|
||||
--border-color: #404040;
|
||||
--link-color: #4da6ff;
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-color: #f5f5f5;
|
||||
--card-bg: #ffffff;
|
||||
--text-color: #333333;
|
||||
--border-color: #dddddd;
|
||||
--link-color: #0066cc;
|
||||
--accent: #0066cc;
|
||||
--accent-light: #007bff;
|
||||
}
|
||||
|
||||
* {
|
||||
transition: background-color 0.3s, color 0.3s;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Segoe UI', system-ui, sans-serif;
|
||||
background-color: var(--bg-color);
|
||||
color: var(--text-color);
|
||||
max-width: 800px;
|
||||
margin: 20px auto;
|
||||
padding: 20px;
|
||||
line-height: 1.6;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
min-height: 100vh;
|
||||
}
|
||||
|
||||
.theme-toggle {
|
||||
position: fixed;
|
||||
top: 20px;
|
||||
right: 20px;
|
||||
background: var(--card-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 20px;
|
||||
padding: 8px 15px;
|
||||
cursor: pointer;
|
||||
color: var(--text-color);
|
||||
}
|
||||
|
||||
h1 {
|
||||
color: var(--accent);
|
||||
margin-bottom: 30px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
form {
|
||||
background: var(--card-bg);
|
||||
padding: 25px;
|
||||
border-radius: 12px;
|
||||
box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
.form-group {
|
||||
margin: 15px 0;
|
||||
padding: 0 15px;
|
||||
}
|
||||
|
||||
input[type="text"] {
|
||||
width: calc(100% - 30px);
|
||||
padding: 10px 15px;
|
||||
margin: 8px 0;
|
||||
background: var(--bg-color);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 6px;
|
||||
color: var(--text-color);
|
||||
}
|
||||
|
||||
button {
|
||||
background: linear-gradient(135deg, var(--accent), var(--accent-light));
|
||||
color: white;
|
||||
padding: 12px 25px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
cursor: pointer;
|
||||
font-weight: 600;
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 0.5px;
|
||||
margin: 0 15px;
|
||||
}
|
||||
|
||||
button:hover {
|
||||
opacity: 0.9;
|
||||
}
|
||||
|
||||
.result-box {
|
||||
background: var(--card-bg);
|
||||
padding: 20px;
|
||||
border-radius: 12px;
|
||||
margin: 25px 15px;
|
||||
border: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.recent-links {
|
||||
margin: 35px 15px 0;
|
||||
padding: 25px 15px 0;
|
||||
border-top: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.link-item {
|
||||
background: var(--card-bg);
|
||||
padding: 15px;
|
||||
margin: 12px 0;
|
||||
border-radius: 8px;
|
||||
border: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.link-item:hover {
|
||||
transform: translateX(5px);
|
||||
transition: transform 0.2s;
|
||||
}
|
||||
|
||||
.timestamp {
|
||||
color: #888;
|
||||
font-size: 0.85em;
|
||||
}
|
||||
|
||||
a {
|
||||
color: var(--link-color);
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
a:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
footer {
|
||||
text-align: center;
|
||||
margin-top: 40px;
|
||||
padding: 20px;
|
||||
border-top: 1px solid var(--border-color);
|
||||
color: #888;
|
||||
}
|
||||
|
||||
footer a {
|
||||
color: var(--link-color);
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
footer a:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
@media (max-width: 768px) {
|
||||
body {
|
||||
padding: 15px;
|
||||
margin: 10px;
|
||||
}
|
||||
|
||||
form {
|
||||
padding: 15px 0;
|
||||
}
|
||||
|
||||
.form-group {
|
||||
padding: 0 10px;
|
||||
}
|
||||
|
||||
input[type="text"] {
|
||||
width: calc(100% - 20px);
|
||||
padding: 10px;
|
||||
}
|
||||
|
||||
button {
|
||||
width: calc(100% - 20px);
|
||||
padding: 15px;
|
||||
margin: 0 10px;
|
||||
}
|
||||
|
||||
.result-box {
|
||||
margin: 25px 10px;
|
||||
padding: 15px;
|
||||
}
|
||||
|
||||
.recent-links {
|
||||
margin: 35px 10px 0;
|
||||
padding: 25px 10px 0;
|
||||
}
|
||||
}
|
||||
|
||||
.copy-btn {
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.copy-btn::after {
|
||||
content: "Copied!";
|
||||
position: absolute;
|
||||
background: var(--card-bg);
|
||||
color: var(--text-color);
|
||||
padding: 5px 10px;
|
||||
border-radius: 4px;
|
||||
right: -80px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
opacity: 0;
|
||||
transition: opacity 0.3s;
|
||||
}
|
||||
|
||||
.copy-btn.copied::after {
|
||||
opacity: 1;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body data-theme="dark">
|
||||
<button class="theme-toggle" onclick="toggleTheme()">🌓 Toggle Theme</button>
|
||||
|
||||
<h1>Hosts File Converter</h1>
|
||||
|
||||
<form method="GET" action="/">
|
||||
<div class="form-group">
|
||||
<label>URL to hosts file:</label>
|
||||
<input type="text" name="url" required
|
||||
placeholder="ex. https://paulgb.github.io/BarbBlock/blacklists/hosts-file.txt">
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<label>Target IP:</label>
|
||||
<input type="text" name="ip" pattern="\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}"
|
||||
value="195.187.6.34" required>
|
||||
</div>
|
||||
|
||||
<button type="submit">Generate convert link</button>
|
||||
</form>
|
||||
|
||||
{% if generated_link %}
|
||||
<div class="result-box">
|
||||
<h3>Link to MikroTik/Adguard:</h3>
|
||||
<input type="text" value="{{ generated_link }}" readonly>
|
||||
<button class="copy-btn" onclick="copyToClipboard(this)">Copy link</button>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<div class="recent-links">
|
||||
<h3>Last converts:</h3>
|
||||
{% if recent_links %}
|
||||
{% for link_data in recent_links %}
|
||||
<div class="link-item">
|
||||
<div class="timestamp">{{ link_data[0]|datetimeformat }}</div>
|
||||
<a href="/convert?url={{ link_data[1]|urlencode }}&ip={{ link_data[2] }}" target="_blank">
|
||||
{{ link_data[1] }} → {{ link_data[2] }}
|
||||
</a>
|
||||
</div>
|
||||
{% endfor %}
|
||||
{% else %}
|
||||
<p>Empty..</p>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<footer>
|
||||
© 2025 <a href="https://www.linuxiarz.pl" target="_blank">linuxiarz.pl</a> - All rights reserved <br>
|
||||
Your IP address: <strong>{{ client_ip }}</strong> | Your User Agent: <strong>{{ user_agent }}</strong>
|
||||
</footer>
|
||||
|
||||
<script>
|
||||
function toggleTheme() {
|
||||
const body = document.body;
|
||||
body.setAttribute('data-theme',
|
||||
body.getAttribute('data-theme') === 'dark' ? 'light' : 'dark');
|
||||
localStorage.setItem('theme', body.getAttribute('data-theme'));
|
||||
}
|
||||
|
||||
function copyToClipboard(btn) {
|
||||
const copyText = document.querySelector("input[readonly]");
|
||||
copyText.select();
|
||||
document.execCommand("copy");
|
||||
|
||||
btn.classList.add('copied');
|
||||
setTimeout(() => btn.classList.remove('copied'), 2000);
|
||||
}
|
||||
|
||||
// Load saved theme
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.body.setAttribute('data-theme', savedTheme);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
Reference in New Issue
Block a user