Filtro en listado de respuestas admin
This commit is contained in:
@@ -8,6 +8,13 @@ export const dynamic = 'force-dynamic'
|
|||||||
const MAX_SUBMISSIONS = 500
|
const MAX_SUBMISSIONS = 500
|
||||||
const PROMPT_MAX_LEN = 60
|
const PROMPT_MAX_LEN = 60
|
||||||
|
|
||||||
|
const SURVEY_OPTIONS = [
|
||||||
|
{ label: 'Todos', id: null },
|
||||||
|
{ label: 'InQuality', id: '30000000-0000-0000-0000-000000000002' },
|
||||||
|
{ label: 'Fundación Solidaridad', id: '30000000-0000-0000-0000-000000000003' },
|
||||||
|
{ label: 'Demo', id: '30000000-0000-0000-0000-000000000001' },
|
||||||
|
] as const
|
||||||
|
|
||||||
interface AllowedQuestion {
|
interface AllowedQuestion {
|
||||||
id: string
|
id: string
|
||||||
code: string
|
code: string
|
||||||
@@ -63,7 +70,12 @@ function renderValue(value: unknown, type: string): string | null {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export default async function AdminResponsesPage() {
|
export default async function AdminResponsesPage({
|
||||||
|
searchParams,
|
||||||
|
}: {
|
||||||
|
searchParams: Promise<{ survey_id?: string }>
|
||||||
|
}) {
|
||||||
|
const { survey_id: surveyId } = await searchParams
|
||||||
const supabase = getSupabaseAdmin()
|
const supabase = getSupabaseAdmin()
|
||||||
|
|
||||||
// 1. Preguntas permitidas — text_long e is_sensitive=true se excluyen ACÁ,
|
// 1. Preguntas permitidas — text_long e is_sensitive=true se excluyen ACÁ,
|
||||||
@@ -91,22 +103,26 @@ export default async function AdminResponsesPage() {
|
|||||||
|
|
||||||
// 2. Submissions con sus respuestas — answers!inner + .in() filtra el ARRAY
|
// 2. Submissions con sus respuestas — answers!inner + .in() filtra el ARRAY
|
||||||
// embebido a solo question_id permitidos (consulta, no post-filtro).
|
// embebido a solo question_id permitidos (consulta, no post-filtro).
|
||||||
|
let responsesQuery = supabase
|
||||||
|
.from('responses')
|
||||||
|
.select(
|
||||||
|
`
|
||||||
|
id,
|
||||||
|
submitted_at,
|
||||||
|
qi_zone,
|
||||||
|
qi_sector,
|
||||||
|
answers!inner ( value, question_id )
|
||||||
|
`
|
||||||
|
)
|
||||||
|
.in('answers.question_id', allowedIds)
|
||||||
|
|
||||||
|
if (surveyId) {
|
||||||
|
responsesQuery = responsesQuery.eq('survey_id', surveyId)
|
||||||
|
}
|
||||||
|
|
||||||
const { data: responsesData, error: responsesError } =
|
const { data: responsesData, error: responsesError } =
|
||||||
allowedIds.length > 0
|
allowedIds.length > 0
|
||||||
? await supabase
|
? await responsesQuery.order('submitted_at', { ascending: false }).limit(MAX_SUBMISSIONS)
|
||||||
.from('responses')
|
|
||||||
.select(
|
|
||||||
`
|
|
||||||
id,
|
|
||||||
submitted_at,
|
|
||||||
qi_zone,
|
|
||||||
qi_sector,
|
|
||||||
answers!inner ( value, question_id )
|
|
||||||
`
|
|
||||||
)
|
|
||||||
.in('answers.question_id', allowedIds)
|
|
||||||
.order('submitted_at', { ascending: false })
|
|
||||||
.limit(MAX_SUBMISSIONS)
|
|
||||||
: { data: [] as ResponseRow[], error: null }
|
: { data: [] as ResponseRow[], error: null }
|
||||||
|
|
||||||
if (responsesError) {
|
if (responsesError) {
|
||||||
@@ -170,6 +186,22 @@ export default async function AdminResponsesPage() {
|
|||||||
{totalSubmissions ?? 0} submissions · {totalAnswers ?? 0} respuestas individuales ·
|
{totalSubmissions ?? 0} submissions · {totalAnswers ?? 0} respuestas individuales ·
|
||||||
actualizado {formatDate(new Date().toISOString())}
|
actualizado {formatDate(new Date().toISOString())}
|
||||||
</p>
|
</p>
|
||||||
|
<nav className="admin-survey-nav" aria-label="Selección de empresa">
|
||||||
|
{SURVEY_OPTIONS.map((opt) => (
|
||||||
|
<a
|
||||||
|
key={opt.label}
|
||||||
|
href={opt.id ? `/admin/responses?survey_id=${opt.id}` : '/admin/responses'}
|
||||||
|
className={
|
||||||
|
opt.id === (surveyId ?? null)
|
||||||
|
? 'admin-survey-link admin-survey-link-active'
|
||||||
|
: 'admin-survey-link'
|
||||||
|
}
|
||||||
|
aria-current={opt.id === (surveyId ?? null) ? 'page' : undefined}
|
||||||
|
>
|
||||||
|
{opt.label}
|
||||||
|
</a>
|
||||||
|
))}
|
||||||
|
</nav>
|
||||||
</div>
|
</div>
|
||||||
<a href="/admin/responses" className="admin-refresh">Actualizar</a>
|
<a href="/admin/responses" className="admin-refresh">Actualizar</a>
|
||||||
</header>
|
</header>
|
||||||
|
|||||||
@@ -758,6 +758,14 @@ body {
|
|||||||
}
|
}
|
||||||
.admin-title { font-size: 1.375rem; font-weight: 700; color: var(--color-text); margin: 0 0 4px; }
|
.admin-title { font-size: 1.375rem; font-weight: 700; color: var(--color-text); margin: 0 0 4px; }
|
||||||
.admin-subtitle { font-size: 0.8125rem; color: var(--color-text-muted); margin: 0; }
|
.admin-subtitle { font-size: 0.8125rem; color: var(--color-text-muted); margin: 0; }
|
||||||
|
.admin-survey-nav { display: flex; gap: 8px; flex-wrap: wrap; margin-top: 10px; }
|
||||||
|
.admin-survey-link {
|
||||||
|
font-size: 0.75rem; font-weight: 600; padding: 4px 12px; border-radius: 999px;
|
||||||
|
border: 1px solid var(--color-border); color: var(--color-text-muted); text-decoration: none;
|
||||||
|
transition: all 0.2s ease;
|
||||||
|
}
|
||||||
|
.admin-survey-link:hover { color: var(--color-text); border-color: var(--color-primary); }
|
||||||
|
.admin-survey-link-active { background: var(--color-primary); color: #fff; border-color: var(--color-primary); }
|
||||||
.admin-refresh {
|
.admin-refresh {
|
||||||
display: inline-block; padding: 8px 16px; border-radius: var(--radius);
|
display: inline-block; padding: 8px 16px; border-radius: var(--radius);
|
||||||
background: var(--color-primary); color: #fff; font-size: 0.8125rem;
|
background: var(--color-primary); color: #fff; font-size: 0.8125rem;
|
||||||
|
|||||||
Reference in New Issue
Block a user