Files
dockerfluxodecaixapro/modules/seo/views/admin/index.twig
T
2026-09-01 10:46:29 -03:00

795 lines
52 KiB
Twig
Executable File

{% extends "layouts/dashboard.twig" %}
{% block title %}{{ page_title }} - {{ platformName }}{% endblock %}
{% block head %}
<style>
.serp-preview {
max-width: 600px;
padding: 15px;
border: 1px solid #dfe1e5;
border-radius: 8px;
background: #fff;
font-family: arial, sans-serif;
}
.serp-url {
color: #202124;
font-size: 14px;
margin-bottom: 4px;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.serp-title {
color: #1a0dab;
font-size: 20px;
line-height: 1.3;
margin-bottom: 3px;
cursor: pointer;
}
.serp-title:hover {
text-decoration: underline;
}
.serp-description {
color: #4d5156;
font-size: 14px;
line-height: 1.58;
word-wrap: break-word;
}
.health-badge {
font-size: 0.8rem;
padding: 0.3rem 0.6rem;
}
.btn-outline-purple {
color: #6f42c1;
border-color: #6f42c1;
}
.btn-outline-purple:hover {
background-color: #6f42c1;
color: #fff;
}
</style>
{% endblock %}
{% block content %}
<div class="container-fluid px-4">
<h1 class="mt-4">{{ page_title }}</h1>
<ol class="breadcrumb mb-4">
<li class="breadcrumb-item"><a href="{{ url('admin/dashboard') }}">{{ __('layout.dashboard') }}</a></li>
<li class="breadcrumb-item active">{{ page_title }}</li>
</ol>
{% include '@seo/admin/nav.twig' ignore missing %}
{% if flash_messages.success %}
<div class="alert alert-success alert-dismissible fade show" role="alert">
{{ flash_messages.success }}
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
</div>
{% endif %}
<div class="row">
<div class="col-xl-8">
<div class="card mb-4">
<div class="card-header d-flex justify-content-between align-items-center">
<div>
<i class="bi bi-search me-1"></i>
{{ __('seo.configuration') }}
</div>
<div class="d-flex gap-2">
<button type="button" id="btn-ai-generate" class="btn btn-outline-purple btn-sm">
<i class="bi bi-cpu me-1"></i> {{ __('seo.ai_generate') }}
</button>
<button type="button" class="btn btn-primary btn-sm" onclick="document.getElementById('seoSettingsForm').submit();">
<i class="bi bi-save me-1"></i> {{ __('seo.save_settings') }}
</button>
</div>
</div>
<div class="card-body">
<form id="seoSettingsForm" action="{{ url('/admin/seo/save') }}" method="POST" enctype="multipart/form-data">
<input type="hidden" name="csrf_token" value="{{ session('csrf_token') }}">
<input type="hidden" name="_token" value="{{ session('_token') }}">
<ul class="nav nav-tabs mb-3" id="seoTabs" role="tablist">
<li class="nav-item" role="presentation">
<button class="nav-link active" id="general-tab" data-bs-toggle="tab" data-bs-target="#general" type="button" role="tab">{{ __('seo.general') }}</button>
</li>
<li class="nav-item" role="presentation">
<button class="nav-link" id="social-tab" data-bs-toggle="tab" data-bs-target="#social" type="button" role="tab">{{ __('seo.social_media') }}</button>
</li>
<li class="nav-item" role="presentation">
<button class="nav-link" id="structured-tab" data-bs-toggle="tab" data-bs-target="#structured" type="button" role="tab">{{ __('seo.structured_data') }}</button>
</li>
<li class="nav-item" role="presentation">
<button class="nav-link" id="google-tab" data-bs-toggle="tab" data-bs-target="#google" type="button" role="tab">{{ __('seo.google_tools') }}</button>
</li>
<li class="nav-item" role="presentation">
<button class="nav-link" id="sitemap-tab" data-bs-toggle="tab" data-bs-target="#sitemap" type="button" role="tab">{{ __('seo.sitemap') }}</button>
</li>
<li class="nav-item" role="presentation">
<button class="nav-link" id="redirects-tab" data-bs-toggle="tab" data-bs-target="#redirects" type="button" role="tab">{{ __('seo.redirects') }}</button>
</li>
<li class="nav-item" role="presentation">
<button class="nav-link" id="robots-tab" data-bs-toggle="tab" data-bs-target="#robots" type="button" role="tab">{{ __('seo.robots_txt') }}</button>
</li>
</ul>
<div class="tab-content" id="seoTabsContent">
<!-- General Tab -->
<div class="tab-pane fade show active" id="general" role="tabpanel">
<div class="mb-3">
<label for="meta_title" class="form-label fw-bold">{{ __('seo.meta_title') }}</label>
<div class="input-group">
<input type="text" class="form-control" id="meta_title" name="meta_title" value="{{ settings.meta_title }}" onkeyup="updatePreview()">
<span class="input-group-text" id="title-counter">0</span>
</div>
<div class="form-text">{{ __('seo.meta_title_help') }}</div>
</div>
<div class="mb-3">
<label for="meta_description" class="form-label fw-bold">{{ __('seo.meta_description') }}</label>
<div class="input-group">
<textarea class="form-control" id="meta_description" name="meta_description" rows="3" onkeyup="updatePreview()">{{ settings.meta_description }}</textarea>
<span class="input-group-text" id="desc-counter">0</span>
</div>
</div>
<div class="mb-3">
<label for="meta_keywords" class="form-label fw-bold">{{ __('seo.meta_keywords') }}</label>
<input type="text" class="form-control" id="meta_keywords" name="meta_keywords" value="{{ settings.meta_keywords }}">
<div class="form-text">{{ __('seo.meta_keywords_help') }}</div>
</div>
<div class="mt-4">
<h6 class="fw-bold mb-3">{{ __('seo.serp_preview') }}</h6>
<div class="serp-preview shadow-sm">
<div class="serp-url">{{ url('/') }}</div>
<div class="serp-title" id="preview-title">Título do Site</div>
<div class="serp-description" id="preview-description">Descrição meta aparecerá aqui para visualização nos resultados de busca do Google.</div>
</div>
</div>
</div>
<!-- Social Media Tab -->
<div class="tab-pane fade" id="social" role="tabpanel">
<h5 class="mt-3">{{ __('seo.og_section') }}</h5>
<div class="mb-3">
<label for="og_title" class="form-label">{{ __('seo.og_title') }}</label>
<input type="text" class="form-control" id="og_title" name="og_title" value="{{ settings.og_title }}">
</div>
<div class="mb-3">
<label for="og_description" class="form-label">{{ __('seo.og_description') }}</label>
<textarea class="form-control" id="og_description" name="og_description" rows="2">{{ settings.og_description }}</textarea>
</div>
<div class="mb-3">
<label class="form-label d-block">{{ __('seo.og_image') }}</label>
{% if settings.og_image %}
<div class="mb-2">
<img src="/storage/uploads/seo/{{ settings.og_image }}" class="img-thumbnail" style="max-height: 150px;">
<div class="small text-muted">{{ __('seo.og_image_current') }}</div>
</div>
{% endif %}
<input type="file" class="form-control" name="og_image_file" accept="image/*">
<div class="form-text">{{ __('seo.og_image_help') }}</div>
</div>
<hr>
<h5 class="mt-3">{{ __('seo.twitter_section') }}</h5>
<div class="mb-3">
<label for="twitter_card" class="form-label">{{ __('seo.twitter_card_type') }}</label>
<select class="form-select" id="twitter_card" name="twitter_card">
<option value="summary" {{ settings.twitter_card == 'summary' ? 'selected' : '' }}>{{ __('seo.summary') }}</option>
<option value="summary_large_image" {{ settings.twitter_card == 'summary_large_image' ? 'selected' : '' }}>{{ __('seo.summary_large_image') }}</option>
</select>
</div>
</div>
<!-- Structured Data Tab -->
<div class="tab-pane fade" id="structured" role="tabpanel">
<h5 class="mt-3">{{ __('seo.structured_data') }} (JSON-LD)</h5>
<div class="mb-3">
<label for="json_ld_type" class="form-label">{{ __('seo.json_ld_type') }}</label>
<select class="form-select" id="json_ld_type" name="json_ld_type" onchange="toggleJsonLdFields()">
<option value="none" {{ settings.json_ld_type == 'none' ? 'selected' : '' }}>{{ __('seo.json_ld_none') }}</option>
<option value="Organization" {{ settings.json_ld_type == 'Organization' ? 'selected' : '' }}>{{ __('seo.json_ld_organization') }}</option>
<option value="LocalBusiness" {{ settings.json_ld_type == 'LocalBusiness' ? 'selected' : '' }}>{{ __('seo.json_ld_local_business') }}</option>
</select>
</div>
<div id="json-ld-fields" style="{{ settings.json_ld_type == 'none' or not settings.json_ld_type ? 'display: none;' : '' }}">
<div class="row">
<div class="col-md-6 mb-3">
<label for="json_ld_name" class="form-label">{{ __('seo.json_ld_name') }}</label>
<input type="text" class="form-control" id="json_ld_name" name="json_ld_name" value="{{ settings.json_ld_name }}">
</div>
<div class="col-md-6 mb-3">
<label for="json_ld_url" class="form-label">{{ __('seo.json_ld_url') }}</label>
<input type="url" class="form-control" id="json_ld_url" name="json_ld_url" value="{{ settings.json_ld_url ?: url('/') }}">
</div>
</div>
<div class="mb-3">
<label for="json_ld_description" class="form-label">{{ __('seo.json_ld_description') }}</label>
<textarea class="form-control" id="json_ld_description" name="json_ld_description" rows="2">{{ settings.json_ld_description }}</textarea>
</div>
<div class="row">
<div class="col-md-6 mb-3">
<label for="json_ld_phone" class="form-label">{{ __('seo.json_ld_phone') }}</label>
<input type="text" class="form-control" id="json_ld_phone" name="json_ld_phone" value="{{ settings.json_ld_phone }}">
</div>
<div class="col-md-6 mb-3">
<label for="json_ld_email" class="form-label">{{ __('seo.json_ld_email') }}</label>
<input type="email" class="form-control" id="json_ld_email" name="json_ld_email" value="{{ settings.json_ld_email }}">
</div>
</div>
<div class="mb-3">
<label for="json_ld_address" class="form-label">{{ __('seo.json_ld_address') }}</label>
<input type="text" class="form-control" id="json_ld_address" name="json_ld_address" value="{{ settings.json_ld_address }}">
</div>
<div class="row">
<div class="col-md-4 mb-3">
<label for="json_ld_city" class="form-label">{{ __('seo.json_ld_city') }}</label>
<input type="text" class="form-control" id="json_ld_city" name="json_ld_city" value="{{ settings.json_ld_city }}">
</div>
<div class="col-md-4 mb-3">
<label for="json_ld_state" class="form-label">{{ __('seo.json_ld_state') }}</label>
<input type="text" class="form-control" id="json_ld_state" name="json_ld_state" value="{{ settings.json_ld_state }}">
</div>
<div class="col-md-4 mb-3">
<label for="json_ld_zip" class="form-label">{{ __('seo.json_ld_zip') }}</label>
<input type="text" class="form-control" id="json_ld_zip" name="json_ld_zip" value="{{ settings.json_ld_zip }}">
</div>
</div>
<div class="mb-3">
<label for="json_ld_social_links" class="form-label">{{ __('seo.json_ld_social_links') }}</label>
<textarea class="form-control" id="json_ld_social_links" name="json_ld_social_links" rows="3" placeholder="https://facebook.com/yourpage&#10;https://twitter.com/yourprofile">{{ settings.json_ld_social_links }}</textarea>
</div>
</div>
</div>
<!-- Google Tools Tab -->
<div class="tab-pane fade" id="google" role="tabpanel">
<div class="mb-3 mt-3">
<label for="google_analytics_id" class="form-label">{{ __('seo.google_analytics_id') }}</label>
<input type="text" class="form-control" id="google_analytics_id" name="google_analytics_id" value="{{ settings.google_analytics_id }}" placeholder="G-XXXXXXXXXX">
</div>
<div class="mb-3">
<label for="google_site_verification" class="form-label">{{ __('seo.google_site_verification') }}</label>
<input type="text" class="form-control" id="google_site_verification" name="google_site_verification" value="{{ settings.google_site_verification }}">
</div>
</div>
<!-- Sitemap Tab -->
<div class="tab-pane fade" id="sitemap" role="tabpanel">
<div class="alert alert-light border border-info mt-3">
<i class="bi bi-info-circle text-info me-2"></i>
Configure a visibilidade, frequência de atualização e prioridade para cada tipo de conteúdo do seu site.
</div>
<div class="table-responsive">
<table class="table table-hover align-middle">
<thead class="table-light">
<tr>
<th style="width: 40px;"></th>
<th>Tipo de Conteúdo</th>
<th style="width: 200px;">Frequência</th>
<th style="width: 150px;">Prioridade (0.1 - 1.0)</th>
</tr>
</thead>
<tbody>
{# Static Pages #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_static" value="1" {{ settings.sitemap_include_static|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Páginas Estáticas</div>
<div class="small text-muted">Home, Sobre, Contato, etc.</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_static">
{% set freqs = ['always', 'hourly', 'daily', 'weekly', 'monthly', 'yearly', 'never'] %}
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_static|default('weekly') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_static" value="{{ settings.sitemap_prio_static|default('1.0') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# Blog Posts #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_blog" value="1" {{ settings.sitemap_include_blog|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Blog</div>
<div class="small text-muted">Artigos e postagens individuais</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_blog">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_blog|default('daily') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_blog" value="{{ settings.sitemap_prio_blog|default('0.8') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# News #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_news" value="1" {{ settings.sitemap_include_news|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Notícias</div>
<div class="small text-muted">Últimas notícias e comunicados</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_news">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_news|default('daily') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_news" value="{{ settings.sitemap_prio_news|default('0.7') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# Commercial Guide #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_guide" value="1" {{ settings.sitemap_include_guide|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Guia Comercial</div>
<div class="small text-muted">Empresas e perfis comerciais</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_guide">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_guide|default('monthly') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_guide" value="{{ settings.sitemap_prio_guide|default('0.7') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# Events Guide #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_events" value="1" {{ settings.sitemap_include_events|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Guia de Eventos</div>
<div class="small text-muted">Eventos públicos e datas festivas</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_events">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_events|default('daily') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_events" value="{{ settings.sitemap_prio_events|default('0.7') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# FAQ #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_faq" value="1" {{ settings.sitemap_include_faq|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">FAQ</div>
<div class="small text-muted">Perguntas frequentes</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_faq">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_faq|default('monthly') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_faq" value="{{ settings.sitemap_prio_faq|default('0.5') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# Expositor #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_expositor" value="1" {{ settings.sitemap_include_expositor|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Expositor (Vitrine)</div>
<div class="small text-muted">Produtos, serviços e categorias da vitrine</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_expositor">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_expositor|default('daily') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_expositor" value="{{ settings.sitemap_prio_expositor|default('0.8') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# Photo Albums #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_albums" value="1" {{ settings.sitemap_include_albums|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Álbuns de Fotos</div>
<div class="small text-muted">Galerias e álbuns de fotos públicos</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_albums">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_albums|default('monthly') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_albums" value="{{ settings.sitemap_prio_albums|default('0.6') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# Custom Pages #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_pages" value="1" {{ settings.sitemap_include_pages|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Páginas Personalizadas</div>
<div class="small text-muted">Páginas criadas via PageBuilder</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_pages">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_pages|default('monthly') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_pages" value="{{ settings.sitemap_prio_pages|default('0.7') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
{# Photo Essays #}
<tr>
<td>
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" name="sitemap_include_photoessays" value="1" {{ settings.sitemap_include_photoessays|default('1') == '1' ? 'checked' : '' }}>
</div>
</td>
<td>
<div class="fw-bold">Ensaios Fotográficos</div>
<div class="small text-muted">Ensaios e galerias do PhotoEssay</div>
</td>
<td>
<select class="form-select form-select-sm" name="sitemap_freq_photoessays">
{% for freq in freqs %}
<option value="{{ freq }}" {{ settings.sitemap_freq_photoessays|default('monthly') == freq ? 'selected' : '' }}>{{ __('seo.' ~ freq) }}</option>
{% endfor %}
</select>
</td>
<td>
<input type="number" class="form-control form-control-sm" name="sitemap_prio_photoessays" value="{{ settings.sitemap_prio_photoessays|default('0.6') }}" step="0.1" min="0.1" max="1.0">
</td>
</tr>
</tbody>
</table>
</div>
</div>
<!-- Redirects Tab (Handled separately) -->
<div class="tab-pane fade" id="redirects" role="tabpanel">
<div class="alert alert-warning mt-3">
<i class="bi bi-exclamation-triangle"></i> Redirecionamentos são aplicados globalmente. Tenha cuidado ao configurar caminhos que já existem.
</div>
<div class="mb-3 d-flex justify-content-end">
<button type="button" class="btn btn-success btn-sm" data-bs-toggle="modal" data-bs-target="#addRedirectModal">
<i class="bi bi-plus-lg"></i> {{ __('seo.add_redirect') }}
</button>
</div>
<div class="table-responsive">
<table class="table table-hover table-sm">
<thead>
<tr>
<th>{{ __('seo.redirect_from') }}</th>
<th>{{ __('seo.redirect_to') }}</th>
<th>{{ __('seo.redirect_code') }}</th>
<th>Ações</th>
</tr>
</thead>
<tbody>
{% for redirect in redirects %}
<tr>
<td><code>{{ redirect.redirects_from }}</code></td>
<td><code>{{ redirect.redirects_to }}</code></td>
<td><span class="badge bg-secondary">{{ redirect.redirects_code }}</span></td>
<td>
<a href="{{ url('admin/seo/redirect/delete/' ~ redirect.redirects_id) }}" class="text-danger" onclick="return confirm('Tem certeza?')">
<i class="bi bi-trash"></i>
</a>
</td>
</tr>
{% else %}
<tr>
<td colspan="4" class="text-center text-muted">{{ __('seo.no_redirects') }}</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
</div>
<!-- Robots.txt Tab -->
<div class="tab-pane fade" id="robots" role="tabpanel">
<div class="alert alert-info mt-3">
<i class="bi bi-info-circle"></i> {{ __('seo.robots_txt_help') }} <code>/robots.txt</code>.
</div>
<div class="mb-3">
<label for="robots_txt" class="form-label">{{ __('seo.robots_txt_content') }}</label>
<textarea class="form-control font-monospace" id="robots_txt" name="robots_txt" rows="10">{{ settings.robots_txt }}</textarea>
</div>
<div class="form-check mb-3">
<input class="form-check-input" type="checkbox" value="1" id="update_robots_file" name="update_robots_file">
<label class="form-check-label" for="update_robots_file">
{{ __('seo.update_robots_file') }}
</label>
</div>
</div>
</div>
{# Botão removido daqui pois o superior no card-header é o que está funcionando #}
</form>
</div>
</div>
</div>
<div class="col-xl-4">
<!-- SEO Health Card -->
<div class="card mb-4">
<div class="card-header bg-primary text-white">
<i class="bi bi-heart-pulse me-1"></i>
{{ __('seo.seo_health') }}
</div>
<div class="card-body">
<div class="d-flex justify-content-between align-items-center mb-3">
<span>{{ __('seo.health_title_length') }}</span>
<span id="health-title-badge" class="badge health-badge bg-secondary">...</span>
</div>
<div class="d-flex justify-content-between align-items-center mb-3">
<span>{{ __('seo.health_desc_length') }}</span>
<span id="health-desc-badge" class="badge health-badge bg-secondary">...</span>
</div>
<div class="d-flex justify-content-between align-items-center mb-0">
<span>{{ __('seo.health_keywords_presence') }}</span>
<span id="health-keywords-badge" class="badge health-badge bg-secondary">...</span>
</div>
</div>
</div>
<div class="card mb-4">
<div class="card-header bg-light">
<i class="bi bi-link-45deg me-1"></i>
Links Gerados
</div>
<div class="card-body">
<div class="mb-3">
<label class="small fw-bold text-muted d-block mb-1">Sitemap XML</label>
<div class="input-group">
<input type="text" class="form-control form-control-sm" value="{{ url('sitemap.xml') }}" readonly>
<a href="{{ url('sitemap.xml') }}" target="_blank" class="btn btn-outline-secondary btn-sm"><i class="bi bi-box-arrow-up-right"></i></a>
</div>
</div>
<div class="mb-0">
<label class="small fw-bold text-muted d-block mb-1">Robots.txt</label>
<div class="input-group">
<input type="text" class="form-control form-control-sm" value="{{ url('robots.txt') }}" readonly>
<a href="{{ url('robots.txt') }}" target="_blank" class="btn btn-outline-secondary btn-sm"><i class="bi bi-box-arrow-up-right"></i></a>
</div>
</div>
</div>
</div>
<div class="card mb-4">
<div class="card-header bg-light">
<i class="bi bi-info-circle me-1"></i>
Dicas de SEO
</div>
<div class="card-body small">
<ul class="ps-3 mb-0">
<li class="mb-2"><strong>Título:</strong> Mantenha entre 50-60 caracteres.</li>
<li class="mb-2"><strong>Descrição:</strong> Idealmente entre 150-160 caracteres.</li>
<li class="mb-2"><strong>Schema.org:</strong> Ajuda o Google a entender quem você é.</li>
<li><strong>Redirecionamentos:</strong> Evite erros 404 ao mudar URLs.</li>
</ul>
</div>
</div>
</div>
</div>
</div>
<!-- Add Redirect Modal -->
<div class="modal fade" id="addRedirectModal" tabindex="-1" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<form action="{{ url('admin/seo/redirect/add') }}" method="POST">
{{ csrf_field()|raw }}
<div class="modal-header">
<h5 class="modal-title">{{ __('seo.add_redirect') }}</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<div class="mb-3">
<label for="redirects_from" class="form-label">{{ __('seo.redirect_from') }}</label>
<input type="text" class="form-control" id="redirects_from" name="redirects_from" placeholder="/pagina-antiga" required>
</div>
<div class="mb-3">
<label for="redirects_to" class="form-label">{{ __('seo.redirect_to') }}</label>
<input type="text" class="form-control" id="redirects_to" name="redirects_to" placeholder="/nova-pagina" required>
</div>
<div class="mb-3">
<label for="redirects_code" class="form-label">{{ __('seo.redirect_code') }}</label>
<select class="form-select" id="redirects_code" name="redirects_code">
<option value="301">{{ __('seo.redirect_permanent') }}</option>
<option value="302">{{ __('seo.redirect_temporary') }}</option>
</select>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Fechar</button>
<button type="submit" class="btn btn-primary">Salvar</button>
</div>
</form>
</div>
</div>
</div>
{% endblock %}
{% block scripts %}
<script>
function updatePreview() {
const titleInput = document.getElementById('meta_title');
const descInput = document.getElementById('meta_description');
const keywordsInput = document.getElementById('meta_keywords');
const title = titleInput.value || 'Título do Site';
const desc = descInput.value || 'Descrição meta aparecerá aqui para visualização nos resultados de busca do Google.';
document.getElementById('preview-title').innerText = title;
document.getElementById('preview-description').innerText = desc;
// Counters
const titleLen = titleInput.value.length;
const descLen = descInput.value.length;
document.getElementById('title-counter').innerText = titleLen;
document.getElementById('desc-counter').innerText = descLen;
// Health Check
const titleBadge = document.getElementById('health-title-badge');
if (titleLen === 0) {
titleBadge.innerText = '{{ __('seo.health_error') }}';
titleBadge.className = 'badge health-badge bg-danger';
} else if (titleLen < 30 || titleLen > 65) {
titleBadge.innerText = '{{ __('seo.health_warning') }}';
titleBadge.className = 'badge health-badge bg-warning text-dark';
} else {
titleBadge.innerText = '{{ __('seo.health_good') }}';
titleBadge.className = 'badge health-badge bg-success';
}
const descBadge = document.getElementById('health-desc-badge');
if (descLen === 0) {
descBadge.innerText = '{{ __('seo.health_error') }}';
descBadge.className = 'badge health-badge bg-danger';
} else if (descLen < 120 || descLen > 165) {
descBadge.innerText = '{{ __('seo.health_warning') }}';
descBadge.className = 'badge health-badge bg-warning text-dark';
} else {
descBadge.innerText = '{{ __('seo.health_good') }}';
descBadge.className = 'badge health-badge bg-success';
}
const kwBadge = document.getElementById('health-keywords-badge');
if (keywordsInput.value.trim() === '') {
kwBadge.innerText = '{{ __('seo.health_warning') }}';
kwBadge.className = 'badge health-badge bg-warning text-dark';
} else {
kwBadge.innerText = '{{ __('seo.health_good') }}';
kwBadge.className = 'badge health-badge bg-success';
}
}
function toggleJsonLdFields() {
const type = document.getElementById('json_ld_type').value;
const fields = document.getElementById('json-ld-fields');
fields.style.display = type === 'none' ? 'none' : 'block';
}
// Check hash for active tab
document.addEventListener('DOMContentLoaded', function() {
if (window.location.hash) {
const tabId = window.location.hash.substring(1) + '-tab';
const tab = document.getElementById(tabId);
if (tab) {
const bsTab = new bootstrap.Tab(tab);
bsTab.show();
}
}
updatePreview();
});
// AI Generate Logic
document.getElementById('btn-ai-generate').addEventListener('click', function() {
const btn = this;
const originalHtml = btn.innerHTML;
btn.disabled = true;
btn.innerHTML = '<span class="spinner-border spinner-border-sm me-1"></span> {{ __('seo.ai_generating') }}';
fetch('{{ url('/admin/seo/ai-generate') }}')
.then(response => response.json())
.then(data => {
if (data.success) {
document.getElementById('meta_title').value = data.title;
document.getElementById('meta_description').value = data.description;
document.getElementById('meta_keywords').value = data.keywords;
// Robots.txt
if (data.robots_txt) {
document.getElementById('robots_txt').value = data.robots_txt;
console.log('Robots.txt preenchido via IA');
}
updatePreview();
// Alerta informativo
const alertMsg = '{{ __('seo.ai_success') }}' + '\n\nAs tags Meta e o arquivo Robots.txt foram preenchidos com sugestões otimizadas.';
alert(alertMsg);
} else {
alert('{{ __('seo.ai_error') }}');
}
})
.catch(error => {
console.error('AI Error:', error);
alert('{{ __('seo.ai_error') }}');
})
.finally(() => {
btn.disabled = false;
btn.innerHTML = originalHtml;
});
});
</script>
{% endblock %}