diff --git a/codiki-domain/src/main/java/org/codiki/domain/publication/model/Author.java b/codiki-domain/src/main/java/org/codiki/domain/publication/model/Author.java index b4d7c2a..57fbd5f 100644 --- a/codiki-domain/src/main/java/org/codiki/domain/publication/model/Author.java +++ b/codiki-domain/src/main/java/org/codiki/domain/publication/model/Author.java @@ -2,8 +2,6 @@ package org.codiki.domain.publication.model; import java.util.UUID; -import org.codiki.domain.user.model.User; - public record Author( UUID id, String name, diff --git a/codiki-exposition/pom.xml b/codiki-exposition/pom.xml index dd17eec..95b3ca0 100644 --- a/codiki-exposition/pom.xml +++ b/codiki-exposition/pom.xml @@ -25,6 +25,10 @@ org.springframework.boot spring-boot-starter-web + + org.projectlombok + lombok + diff --git a/codiki-exposition/src/main/java/org/codiki/exposition/category/model/CategoryDto.java b/codiki-exposition/src/main/java/org/codiki/exposition/category/model/CategoryDto.java new file mode 100644 index 0000000..d103929 --- /dev/null +++ b/codiki-exposition/src/main/java/org/codiki/exposition/category/model/CategoryDto.java @@ -0,0 +1,23 @@ +package org.codiki.exposition.category.model; + +import java.util.List; +import java.util.UUID; + +import org.codiki.domain.category.model.Category; + +public record CategoryDto( + UUID id, + String name, + List subCategories +) { + public CategoryDto(Category category) { + this( + category.id(), + category.name(), + category.subCategories() + .stream() + .map(CategoryDto::new) + .toList() + ); + } +} diff --git a/codiki-exposition/src/main/java/org/codiki/exposition/publication/PublicationController.java b/codiki-exposition/src/main/java/org/codiki/exposition/publication/PublicationController.java new file mode 100644 index 0000000..5c8072e --- /dev/null +++ b/codiki-exposition/src/main/java/org/codiki/exposition/publication/PublicationController.java @@ -0,0 +1,27 @@ +package org.codiki.exposition.publication; + +import org.codiki.application.publication.PublicationUseCases; +import org.codiki.domain.publication.model.Publication; +import org.codiki.domain.publication.model.PublicationCreationRequest; +import org.codiki.exposition.publication.model.PublicationCreationRequestDto; +import org.springframework.web.bind.annotation.PostMapping; +import org.springframework.web.bind.annotation.RequestBody; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +@RestController +@RequestMapping("/api/publications") +public class PublicationController { + private final PublicationUseCases publicationUseCases; + + public PublicationController(PublicationUseCases publicationUseCases) { + this.publicationUseCases = publicationUseCases; + } + + @PostMapping + public PublicationDto createPublication(@RequestBody PublicationCreationRequestDto requestDto) { + PublicationCreationRequest request = requestDto.toDomain(); + Publication newPublication = publicationUseCases.createPublication(request); + return new PublicationDto(newPublication); + } +} diff --git a/codiki-exposition/src/main/java/org/codiki/exposition/publication/PublicationDto.java b/codiki-exposition/src/main/java/org/codiki/exposition/publication/PublicationDto.java new file mode 100644 index 0000000..c3c5642 --- /dev/null +++ b/codiki-exposition/src/main/java/org/codiki/exposition/publication/PublicationDto.java @@ -0,0 +1,36 @@ +package org.codiki.exposition.publication; + +import java.time.ZonedDateTime; +import java.util.UUID; + +import org.codiki.domain.category.model.Category; +import org.codiki.domain.publication.model.Author; +import org.codiki.domain.publication.model.Publication; +import org.codiki.exposition.category.model.CategoryDto; +import org.codiki.exposition.publication.model.AuthorDto; + +public record PublicationDto( + UUID id, + String key, + String title, + String text, + String description, + String image, + ZonedDateTime creationDate, + AuthorDto author, + CategoryDto category +) { + public PublicationDto(Publication publication) { + this( + publication.id(), + publication.key(), + publication.title(), + publication.text(), + publication.description(), + publication.image(), + publication.creationDate(), + new AuthorDto(publication.author()), + new CategoryDto(publication.category()) + ); + } +} diff --git a/codiki-exposition/src/main/java/org/codiki/exposition/publication/model/AuthorDto.java b/codiki-exposition/src/main/java/org/codiki/exposition/publication/model/AuthorDto.java new file mode 100644 index 0000000..9f83c7a --- /dev/null +++ b/codiki-exposition/src/main/java/org/codiki/exposition/publication/model/AuthorDto.java @@ -0,0 +1,19 @@ +package org.codiki.exposition.publication.model; + +import java.util.UUID; + +import org.codiki.domain.publication.model.Author; + +public record AuthorDto( + UUID id, + String name, + String image +) { + public AuthorDto(Author author) { + this( + author.id(), + author.name(), + author.image() + ); + } +} diff --git a/codiki-exposition/src/main/java/org/codiki/exposition/publication/model/PublicationCreationRequestDto.java b/codiki-exposition/src/main/java/org/codiki/exposition/publication/model/PublicationCreationRequestDto.java new file mode 100644 index 0000000..9a88994 --- /dev/null +++ b/codiki-exposition/src/main/java/org/codiki/exposition/publication/model/PublicationCreationRequestDto.java @@ -0,0 +1,17 @@ +package org.codiki.exposition.publication.model; + +import java.util.UUID; + +import org.codiki.domain.publication.model.PublicationCreationRequest; + +public record PublicationCreationRequestDto( + String title, + String text, + String description, + String image, + UUID categoryId +) { + public PublicationCreationRequest toDomain() { + return new PublicationCreationRequest(title, text, description, image, categoryId); + } +} diff --git a/codiki-infrastructure/src/main/java/org/codiki/infrastructure/category/model/CategoryEntity.java b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/category/model/CategoryEntity.java new file mode 100644 index 0000000..6da54a6 --- /dev/null +++ b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/category/model/CategoryEntity.java @@ -0,0 +1,27 @@ +package org.codiki.infrastructure.category.model; + +import java.util.UUID; + +import org.codiki.domain.category.model.Category; + +import jakarta.persistence.Column; +import jakarta.persistence.Entity; +import jakarta.persistence.Id; +import jakarta.persistence.Table; + +@Entity +@Table(name = "category") +public record CategoryEntity( + @Id + UUID id, + @Column(nullable = false) + String name +// List subCategories +) { + public CategoryEntity(Category category) { + this( + category.id(), + category.name() + ); + } +} diff --git a/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/PublicationJpaAdapter.java b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/PublicationJpaAdapter.java new file mode 100644 index 0000000..c40f597 --- /dev/null +++ b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/PublicationJpaAdapter.java @@ -0,0 +1,22 @@ +package org.codiki.infrastructure.publication; + +import org.codiki.domain.publication.model.Publication; +import org.codiki.domain.publication.port.PublicationPort; +import org.codiki.infrastructure.publication.model.PublicationEntity; +import org.codiki.infrastructure.publication.repository.PublicationRepository; +import org.springframework.stereotype.Component; + +@Component +public class PublicationJpaAdapter implements PublicationPort { + private final PublicationRepository repository; + + public PublicationJpaAdapter(PublicationRepository repository) { + this.repository = repository; + } + + @Override + public void save(final Publication publication) { + PublicationEntity newPublicationEntity = new PublicationEntity(publication); + repository.save(newPublicationEntity); + } +} diff --git a/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/model/AuthorEntity.java b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/model/AuthorEntity.java new file mode 100644 index 0000000..a8bd2cb --- /dev/null +++ b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/model/AuthorEntity.java @@ -0,0 +1,28 @@ +package org.codiki.infrastructure.publication.model; + +import java.util.UUID; + +import org.codiki.domain.publication.model.Author; + +import jakarta.persistence.Column; +import jakarta.persistence.Entity; +import jakarta.persistence.Id; +import jakarta.persistence.Table; + +@Entity +@Table(name = "`user`") +public record AuthorEntity( + @Id + UUID id, + @Column(nullable = false) + String name, + String image +) { + public AuthorEntity(Author author) { + this( + author.id(), + author.name(), + author.image() + ); + } +} diff --git a/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/model/PublicationEntity.java b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/model/PublicationEntity.java new file mode 100644 index 0000000..250350d --- /dev/null +++ b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/model/PublicationEntity.java @@ -0,0 +1,54 @@ +package org.codiki.infrastructure.publication.model; + +import java.time.ZonedDateTime; +import java.util.UUID; + +import org.codiki.domain.publication.model.Publication; +import org.codiki.infrastructure.category.model.CategoryEntity; + +import static jakarta.persistence.FetchType.LAZY; +import jakarta.persistence.Column; +import jakarta.persistence.Entity; +import jakarta.persistence.Id; +import jakarta.persistence.JoinColumn; +import jakarta.persistence.ManyToOne; +import jakarta.persistence.Table; + +@Entity +@Table(name = "publication") +public record PublicationEntity( + @Id + UUID id, + @Column(nullable = false) + String key, + @Column(nullable = false) + String title, + @Column(nullable = false) + String text, + @Column(nullable = false) + String description, + @Column(nullable = false) + String image, + @Column(nullable = false) + ZonedDateTime creationDate, + @ManyToOne(fetch = LAZY) + @JoinColumn(name = "author_id") + AuthorEntity author, + @ManyToOne(fetch = LAZY) + @JoinColumn(name = "category_id") + CategoryEntity categoryId +) { + public PublicationEntity(Publication publication) { + this( + publication.id(), + publication.key(), + publication.title(), + publication.text(), + publication.description(), + publication.image(), + publication.creationDate(), + new AuthorEntity(publication.author()), + new CategoryEntity(publication.category()) + ); + } +} diff --git a/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/repository/PublicationRepository.java b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/repository/PublicationRepository.java new file mode 100644 index 0000000..8b513f0 --- /dev/null +++ b/codiki-infrastructure/src/main/java/org/codiki/infrastructure/publication/repository/PublicationRepository.java @@ -0,0 +1,9 @@ +package org.codiki.infrastructure.publication.repository; + +import java.util.UUID; + +import org.codiki.infrastructure.publication.model.PublicationEntity; +import org.springframework.data.jpa.repository.JpaRepository; + +public interface PublicationRepository extends JpaRepository { +} diff --git a/codiki-infrastructure/src/main/resources/sql/001-initial-script-tables-creation.sql b/codiki-infrastructure/src/main/resources/sql/001-initial-script-tables-creation.sql index fbe60ba..afbfc5b 100644 --- a/codiki-infrastructure/src/main/resources/sql/001-initial-script-tables-creation.sql +++ b/codiki-infrastructure/src/main/resources/sql/001-initial-script-tables-creation.sql @@ -1,5 +1,6 @@ CREATE TABLE IF NOT EXISTS "user" ( id UUID NOT NULL, + name VARCHAR NOT NULL, password VARCHAR NOT NULL, CONSTRAINT user_pk PRIMARY KEY (id) ); @@ -19,4 +20,27 @@ CREATE TABLE IF NOT EXISTS refresh_token ( CONSTRAINT refresh_token_pk PRIMARY KEY (user_id), CONSTRAINT refresh_token_fk_user_id FOREIGN KEY (user_id) REFERENCES "user" (id) ); -CREATE INDEX refresh_token_fk_user_id_idx ON user_role (user_id); \ No newline at end of file +CREATE INDEX refresh_token_fk_user_id_idx ON user_role (user_id); + +CREATE TABLE IF NOT EXISTS category ( + id UUID NOT NULL, + name VARCHAR NOT NULL, + CONSTRAINT category_pk PRIMARY KEY (id) +); + +CREATE TABLE IF NOT EXISTS publication ( + id UUID NOT NULL, + key VARCHAR(10) NOT NULL, + title VARCHAR NOT NULL, + text VARCHAR NOT NULL, + description VARCHAR NOT NULL, + image VARCHAR NOT NULL, + creationDate TIMESTAMP NOT NULL, + author_id UUID NOT NULL, + category_id UUID NOT NULL, + CONSTRAINT publication_pk PRIMARY KEY (id), + CONSTRAINT publication_author_id_fk FOREIGN KEY (author_id) REFERENCES "user" (id), + CONSTRAINT publication_category_id_fk FOREIGN KEY (category_id) REFERENCES category (id) +); +CREATE INDEX publication_author_id_idx ON publication (author_id); +CREATE INDEX publication_category_id_idx ON publication (category_id);