Initial commit: enterprise digital platform with portal SSO, DigiServer, IT Assets, NetworkView, Server Monitor

This commit is contained in:
ske087
2026-05-10 21:07:50 +03:00
commit 8d9df56b0b
364 changed files with 73655 additions and 0 deletions
+109
View File
@@ -0,0 +1,109 @@
{% extends 'base.html' %}
{% block title %}Modules — Enterprise Digital Platform{% endblock %}
{% block content %}
<div class="settings-wrapper">
<div class="settings-header">
<h2 class="section-title">Settings</h2>
<div class="settings-tabs">
<a href="{{ url_for('settings.index') }}" class="tab-link">Users &amp; Access</a>
<a href="{{ url_for('settings.api_keys') }}" class="tab-link">API Keys</a>
<a href="{{ url_for('settings.modules') }}" class="tab-link active">Modules</a>
</div>
</div>
<div class="settings-section">
<div class="section-toolbar">
<h3>Installed Modules</h3>
<span class="text-muted" style="font-size:0.875rem;">
Enable or disable services to control which applications run on this instance.
</span>
</div>
<div class="app-grid" style="margin-top:1.25rem;">
{% for ms in module_statuses %}
{% set app = ms.app %}
{% set on = ms.enabled %}
{% set alive = ms.running %}
<div class="app-card {% if not on %}app-card--locked{% endif %}"
style="--accent: {{ app.color }};">
<div class="app-card-header">
<span class="app-icon">{{ app.icon }}</span>
<span class="app-status">
<span class="status-dot {% if alive %}status-dot--active{% else %}status-dot--inactive{% endif %}"></span>
<span class="status-label">{% if alive %}running{% else %}stopped{% endif %}</span>
</span>
</div>
<div class="app-card-body">
<div class="app-name">{{ app.name }}</div>
<div class="app-desc" style="margin-top:0.4rem;">{{ app.description }}</div>
</div>
<div class="app-card-footer" style="display:flex; align-items:center; justify-content:space-between; gap:1rem;">
{# Toggle switch — submits a hidden form on change #}
<label class="module-toggle" title="{% if on %}Disable {{ app.name }}{% else %}Enable {{ app.name }}{% endif %}">
<input
type="checkbox"
class="module-toggle-input"
data-app="{{ app.id }}"
data-action-enable="{{ url_for('settings.toggle_module', app_id=app.id) }}"
{% if on %}checked{% endif %}
/>
<span class="toggle-slider"></span>
<span class="toggle-label">{% if on %}Enabled{% else %}Disabled{% endif %}</span>
</label>
{# Hidden forms — one per action #}
<form id="form-enable-{{ app.id }}" method="POST"
action="{{ url_for('settings.toggle_module', app_id=app.id) }}" style="display:none;">
<input type="hidden" name="action" value="enable" />
</form>
<form id="form-disable-{{ app.id }}" method="POST"
action="{{ url_for('settings.toggle_module', app_id=app.id) }}" style="display:none;">
<input type="hidden" name="action" value="disable" />
</form>
{% if on and alive %}
<a href="{{ app.url }}" class="btn btn-sm btn-secondary" target="_blank">Open ↗</a>
{% endif %}
</div>
</div>
{% endfor %}
</div>
<div class="form-inline-card" style="margin-top:1.5rem; display:flex; align-items:flex-start; gap:0.75rem;">
<span style="font-size:1.25rem; flex-shrink:0;"></span>
<div style="font-size:0.875rem; color:var(--text-secondary); line-height:1.6;">
<strong style="color:var(--text-primary);">How modules work</strong><br/>
Disabling a module sends a stop signal to its process and prevents it from being proxied.
Enabling a module starts its process in the background.
Module state is preserved across page reloads and respected by
<code>./start-dev.sh</code> on next launch.
</div>
</div>
</div>
</div>
<script>
document.querySelectorAll('.module-toggle-input').forEach(function(cb) {
cb.addEventListener('change', function() {
var appId = this.dataset.app;
var action = this.checked ? 'enable' : 'disable';
var confirmed = true;
if (action === 'disable') {
confirmed = confirm(
'Disable and stop this service?\n\n' +
'Users will lose access until it is re-enabled.'
);
}
if (confirmed) {
document.getElementById('form-' + action + '-' + appId).submit();
} else {
// Revert visual state without submitting
this.checked = !this.checked;
}
});
});
</script>
{% endblock %}