Files
aplp.backend.lms/AGENTS.md
2026-09-15 23:08:38 +07:00

3.3 KiB

AGENTS.md

Spring Boot 4.1.0 / Java 17 REST backend for an LMS (PostgreSQL). Root package aplp.backend.lms.

Commands

  • Build: ./mvnw -DskipTests package
  • Run: ./mvnw spring-boot:run
  • All tests: ./mvnw test
  • Single test: ./mvnw test -Dtest=LmsApplicationTests
  • Requires JDK 17. No linter, formatter, or checkstyle is configured — don't invent one.

Build gotcha: GitLab Maven registry

aplp.backend:core:1.0-SNAPSHOT is not built here; it resolves from the GitLab package registry (repository id gitlab-maven in pom.xml). A fresh checkout needs a token for server id gitlab-maven in ~/.m2/settings.xml (or the artifact cached in ~/.m2/repository). Credentials are not in the repo.

aplp.backend.core shared types

Not defined in this repo; import them instead of recreating:

  • BaseEntity@MappedSuperclass for every entity: id, createdAt/By, updatedAt/By, deletedAt/By; timestamps set via @PrePersist/@PreUpdate.
  • ApiResponse<T>ok(data), ok(message, data), error(code, message).
  • PagedResponse<T>of(content, page, size, totalElements).
  • ErrorCode, DomainException, ResourceNotFoundException, TokenHasher.sha256Hex.

Architecture

Vertical slices per feature under aplp.backend.lms.<feature> (currently course, lesson, section); common/ holds cross-cutting api, config, security. Layers per feature:

  • api/controller@RestController, returns ResponseEntity<ApiResponse<...>>
  • application/services, application/dtos (Java records), application/mappers (MapStruct)
  • domain/entities, domain/enums, domain/repositories (plain interfaces)
  • infrastructure/persistence*RepositoryImpl implements the domain repo and delegates to a Spring Data *JpaRepository

Conventions:

  • Entities extend BaseEntity, use Lombok @Getter/@Setter/@NoArgsConstructor, @Table snake_case.
  • Controllers stay thin; services throw ResourceNotFoundException; GlobalExceptionHandler maps exceptions to ApiResponse.
  • Mappers are interfaces annotated @Mapper(componentModel = "spring"); Lombok/MapStruct annotation processing is already wired in pom.xml.
  • Add derived queries to *JpaRepository and expose them through the domain repo interface.

Database

  • PostgreSQL, Hibernate default schema lms; datasource hardcoded in src/main/resources/application.yaml.
  • spring.flyway.enabled: false + spring.jpa.hibernate.ddl-auto: update: Hibernate maintains the schema at runtime. Scripts in db/migration (V{n}__desc.sql) are history only and are NOT applied on startup. A schema change needs both the entity field and a migration; don't assume Flyway runs.
  • jsonb columns use @JdbcTypeCode(SqlTypes.JSON) on a String field.

Security

  • SecurityConfig disables CSRF and permitAlls every request — endpoints are currently unauthenticated despite OpenAPI declaring a bearerAuth JWT scheme (Swagger UI at /swagger-ui).
  • JpaAuditingConfig reads the current user from SecurityContextHolder and expects Authentication.getPrincipal() to be a Long userId.

Testing

Only LmsApplicationTests (@SpringBootTest contextLoads) exists. There is no src/test/resources or test profile, so tests use the real application.yaml datasource and require access to the remote DB — ./mvnw test fails without it.