Ir al contenido

TalentBricksAI incluye un sistema completo de perfiles de instructores que permite asociar cursos a personas específicas y mostrar sus perfiles públicos.

El modelo Instructor en schema.prisma:

model Instructor {
id String @id @default(uuid())
name String
slug String @unique // URL-friendly: "juan-perez"
title String? // "Senior Data Engineer"
bio String? @db.Text // Biografía larga
avatarUrl String? // URL de foto de perfil
linkedinUrl String?
githubUrl String?
twitterUrl String?
isPublished Boolean @default(true) // false = oculto del sitio público
courses Course[] // cursos vinculados
createdAt DateTime @default(now())
updatedAt DateTime @updatedAt
}

Relación con Course: un curso puede tener cero o un instructor (instructorId opcional en Course).

Las operaciones están declaradas en main.wasp e implementadas en app/src/admin/operations.ts.

QueryDescripciónRequiere Admin
getAllInstructorsLista todos los instructores con conteo de cursos y estudiantesNo (público)
getAdminInstructorDetailDetalle completo con cursos vinculados
ActionDescripciónRequiere Admin
createInstructorCrea un nuevo perfil
updateInstructorActualiza datos del perfil
deleteInstructorElimina el perfil (desvincula cursos primero)

Ruta: /admin/instructors — visible en el sidebar del admin.

  1. Clic en “Nuevo Instructor”
  2. Completar campos requeridos (nombre, slug)
  3. El slug se genera automáticamente desde el nombre — puede editarse manualmente
  4. Añadir título profesional, biografía y foto de perfil (URL externa)
  5. Añadir links sociales (LinkedIn, GitHub, Twitter)
  6. Activar/desactivar “Publicado”
  7. Guardar

Reglas del slug:

  • Solo minúsculas, números y guiones
  • Único en todo el sistema
  • Generado automáticamente: “Juan Pérez” → juan-perez
  • Se puede editar antes de guardar

Desde la lista → ícono de edición (lápiz). Abre el mismo formulario con datos pre-poblados.

El slug no se puede editar una vez el instructor está publicado (rompería URLs públicas). Para cambiarlo, desactivar primero.

  1. Desde la lista → ícono de ojo para abrir la página de detalle del instructor
  2. En la sección “Cursos” → “Vincular Curso”
  3. Seleccionar un curso del dropdown (solo muestra cursos no vinculados)
  4. Confirmar

También puedes crear un nuevo curso directamente desde aquí con “Nuevo Curso” — pasa el instructorId como parámetro.

Desde la página de detalle del instructor → ícono de desvinculación (cadena rota) junto al curso.

Desvincular no borra el curso — solo elimina la relación. El campo instructorId en el curso queda en null.

Solo disponible desde la lista de instructores (ícono papelera). No es posible si tiene cursos vinculados — desvincular primero.

Cuando un curso tiene instructor asignado, la página del curso muestra:

  • Foto de perfil del instructor
  • Nombre y título profesional
  • Enlace al perfil completo del instructor

Si no hay instructor asignado, se muestra el campo instructorName del curso (texto plano, default: “TalentBricksAI”).

import { useQuery, getAllInstructors } from "wasp/client/operations";
function InstructorBadge({ instructorId }: { instructorId: string | null }) {
const { data: instructors } = useQuery(getAllInstructors);
if (!instructorId || !instructors) return null;
const instructor = instructors.find(i => i.id === instructorId);
if (!instructor) return null;
return (
<div className="flex items-center gap-2">
{instructor.avatarUrl && (
<img src={instructor.avatarUrl} alt={instructor.name} className="w-8 h-8 rounded-full" />
)}
<div>
<p className="text-sm font-medium">{instructor.name}</p>
{instructor.title && <p className="text-xs text-muted-foreground">{instructor.title}</p>}
</div>
</div>
);
}

La query getAllInstructors retorna campos calculados:

{
id: string;
name: string;
slug: string;
title: string | null;
avatarUrl: string | null;
isPublished: boolean;
_count: {
courses: number; // número de cursos vinculados
}
totalStudents: number; // suma de enrollments de todos sus cursos
}
ArchivoDescripción
app/schema.prismaModelo Instructor (línea ~166)
app/src/admin/dashboards/instructors/AdminInstructorsPage.tsxLista y CRUD
app/src/admin/dashboards/instructors/AdminInstructorDetailPage.tsxDetalle + vinculación de cursos
app/src/admin/operations.tsImplementación de queries y actions
app/main.waspDeclaraciones de operaciones + rutas admin
  • Las fotos de perfil usan URLs externas — hostear en un CDN propio (ej. AWS S3) en producción
  • Los slugs son públicos en URLs — elegir slugs permanentes antes de publicar
  • Los instructores con isPublished: false no aparecen en el sitio público pero sí en el admin