nordabiz/templates/admin/social_publisher_settings.html
Maciej Pienczyn 4a033f0d81 feat: Add Social Media Publisher module (MVP)
Admin panel module for publishing posts on NORDA chamber Facebook page.
Includes AI content generation (Gemini), post workflow (draft/approved/
scheduled/published), Facebook Graph API publishing, and engagement tracking.

New: migration 070, SocialPost/SocialMediaConfig models, publisher service,
admin routes with AJAX, 3 templates (list/form/settings).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-18 12:08:29 +01:00

215 lines
7.0 KiB
HTML

{% extends "base.html" %}
{% block title %}Ustawienia Social Publisher - Norda Biznes Partner{% endblock %}
{% block extra_css %}
<style>
.admin-header {
margin-bottom: var(--spacing-xl);
display: flex;
justify-content: space-between;
align-items: center;
}
.admin-header h1 {
font-size: var(--font-size-3xl);
color: var(--text-primary);
}
.form-section {
background: var(--surface);
padding: var(--spacing-xl);
border-radius: var(--radius-lg);
box-shadow: var(--shadow);
max-width: 700px;
margin-bottom: var(--spacing-xl);
}
.form-group {
margin-bottom: var(--spacing-lg);
}
.form-group label {
display: block;
margin-bottom: var(--spacing-xs);
font-weight: 500;
color: var(--text-primary);
}
.form-group input[type="text"],
.form-group textarea {
width: 100%;
padding: var(--spacing-sm) var(--spacing-md);
border: 1px solid var(--border);
border-radius: var(--radius-md);
font-size: var(--font-size-base);
font-family: inherit;
}
.form-group textarea {
min-height: 80px;
resize: vertical;
font-family: 'Monaco', 'Menlo', 'Ubuntu Mono', monospace;
font-size: var(--font-size-sm);
}
.form-hint {
font-size: var(--font-size-sm);
color: var(--text-secondary);
margin-top: var(--spacing-xs);
}
.checkbox-item {
display: flex;
align-items: center;
gap: var(--spacing-xs);
}
.checkbox-item input[type="checkbox"] {
width: 18px;
height: 18px;
}
.btn-group {
display: flex;
gap: var(--spacing-md);
margin-top: var(--spacing-xl);
flex-wrap: wrap;
}
.info-box {
background: var(--surface);
padding: var(--spacing-xl);
border-radius: var(--radius-lg);
box-shadow: var(--shadow);
max-width: 700px;
margin-bottom: var(--spacing-xl);
}
.info-box h2 {
font-size: var(--font-size-xl);
margin-bottom: var(--spacing-md);
color: var(--text-primary);
}
.info-box ol {
padding-left: var(--spacing-lg);
color: var(--text-secondary);
line-height: 1.8;
}
.info-box ol li {
margin-bottom: var(--spacing-xs);
}
.config-status {
background: var(--background);
padding: var(--spacing-md);
border-radius: var(--radius);
margin-bottom: var(--spacing-lg);
font-size: var(--font-size-sm);
}
.config-status strong {
color: var(--primary);
}
.config-status .status-active {
color: var(--success);
font-weight: 600;
}
.config-status .status-inactive {
color: var(--error);
font-weight: 600;
}
.section-title {
font-size: var(--font-size-lg);
font-weight: 600;
color: var(--text-primary);
margin-bottom: var(--spacing-md);
padding-bottom: var(--spacing-xs);
border-bottom: 1px solid var(--border);
}
</style>
{% endblock %}
{% block content %}
<div class="container">
<div class="admin-header">
<h1>Ustawienia Social Publisher</h1>
<a href="{{ url_for('admin.social_publisher_list') }}" class="btn btn-secondary">Powrot do listy</a>
</div>
{% if config %}
<div class="config-status">
<strong>Obecna konfiguracja:</strong>
Strona: <strong>{{ config.page_name or 'Nie ustawiona' }}</strong>
| Status: {% if config.is_active %}<span class="status-active">Aktywna</span>{% else %}<span class="status-inactive">Nieaktywna</span>{% endif %}
| Debug: {% if config.debug_mode %}<span style="color: var(--warning); font-weight: 600;">Wlaczony</span>{% else %}Wylaczony{% endif %}
{% if config.updated_at %}
| Ostatnia aktualizacja: {{ config.updated_at.strftime('%Y-%m-%d %H:%M') }}
{% endif %}
</div>
{% endif %}
<div class="form-section">
<h3 class="section-title">Konfiguracja Facebook</h3>
<form method="POST">
<input type="hidden" name="csrf_token" value="{{ csrf_token() }}">
<div class="form-group">
<label for="page_id">Page ID</label>
<input type="text" id="page_id" name="page_id"
value="{{ config.page_id if config else '' }}"
placeholder="np. 123456789012345">
<p class="form-hint">Numeryczny identyfikator strony na Facebooku</p>
</div>
<div class="form-group">
<label for="page_name">Nazwa strony</label>
<input type="text" id="page_name" name="page_name"
value="{{ config.page_name if config else '' }}"
placeholder="np. Norda Biznes Partner">
</div>
<div class="form-group">
<label for="access_token">Page Access Token</label>
<textarea id="access_token" name="access_token"
placeholder="Wklej Page Access Token...">{{ config.access_token if config else '' }}</textarea>
<p class="form-hint">Token dostepu do strony FB (nie udostepniaj nikomu)</p>
</div>
<div class="form-group">
<label class="checkbox-item">
<input type="checkbox" name="debug_mode"
{% if config and config.debug_mode %}checked{% endif %}>
<span>Tryb debug</span>
</label>
<p class="form-hint">W trybie debug posty sa widoczne tylko dla adminow strony FB (nie sa publiczne)</p>
</div>
<div class="btn-group">
<a href="{{ url_for('admin.social_publisher_list') }}" class="btn btn-secondary">Anuluj</a>
<button type="submit" class="btn btn-primary">Zapisz ustawienia</button>
</div>
</form>
</div>
<div class="info-box">
<h2>Jak uzyskac Page Access Token?</h2>
<ol>
<li>Przejdz do <a href="https://developers.facebook.com/" target="_blank">Facebook Developers</a> i zaloguj sie</li>
<li>Utworz aplikacje (typ: Business) lub wybierz istniejaca</li>
<li>Dodaj produkt "Facebook Login for Business"</li>
<li>Przejdz do <a href="https://developers.facebook.com/tools/explorer/" target="_blank">Graph API Explorer</a></li>
<li>Wybierz swoja aplikacje i wygeneruj User Token z uprawnieniami:
<code>pages_manage_posts</code>, <code>pages_read_engagement</code>, <code>pages_show_list</code></li>
<li>Zamien User Token na Page Token: <code>GET /me/accounts</code> - skopiuj <code>access_token</code> dla wlasciwej strony</li>
<li>Opcjonalnie: przedluz token na dlugotrwaly (60 dni) przez endpoint <code>/oauth/access_token</code></li>
</ol>
</div>
</div>
{% endblock %}