♻️ Interactive v2 #1
							
								
								
									
										231
									
								
								pkg/server/articles_api.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										231
									
								
								pkg/server/articles_api.go
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,231 @@ | |||||||
|  | package server | ||||||
|  |  | ||||||
|  | import ( | ||||||
|  | 	"strings" | ||||||
|  | 	"time" | ||||||
|  |  | ||||||
|  | 	"code.smartsheep.studio/hydrogen/interactive/pkg/database" | ||||||
|  | 	"code.smartsheep.studio/hydrogen/interactive/pkg/models" | ||||||
|  | 	"code.smartsheep.studio/hydrogen/interactive/pkg/services" | ||||||
|  | 	"github.com/gofiber/fiber/v2" | ||||||
|  | 	"github.com/google/uuid" | ||||||
|  | 	"github.com/samber/lo" | ||||||
|  | ) | ||||||
|  |  | ||||||
|  | func contextArticle() *services.PostTypeContext[models.Article] { | ||||||
|  | 	return &services.PostTypeContext[models.Article]{ | ||||||
|  | 		Tx:        database.C, | ||||||
|  | 		TypeName:  "Article", | ||||||
|  | 		CanReply:  false, | ||||||
|  | 		CanRepost: false, | ||||||
|  | 	} | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func getArticle(c *fiber.Ctx) error { | ||||||
|  | 	id, _ := c.ParamsInt("articleId", 0) | ||||||
|  |  | ||||||
|  | 	mx := contextArticle().FilterPublishedAt(time.Now()) | ||||||
|  |  | ||||||
|  | 	item, err := mx.Get(uint(id)) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.JSON(item) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func listArticle(c *fiber.Ctx) error { | ||||||
|  | 	take := c.QueryInt("take", 0) | ||||||
|  | 	offset := c.QueryInt("offset", 0) | ||||||
|  | 	realmId := c.QueryInt("realmId", 0) | ||||||
|  |  | ||||||
|  | 	mx := contextArticle(). | ||||||
|  | 		FilterPublishedAt(time.Now()). | ||||||
|  | 		FilterRealm(uint(realmId)). | ||||||
|  | 		SortCreatedAt("desc") | ||||||
|  |  | ||||||
|  | 	var author models.Account | ||||||
|  | 	if len(c.Query("authorId")) > 0 { | ||||||
|  | 		if err := database.C.Where(&models.Account{Name: c.Query("authorId")}).First(&author).Error; err != nil { | ||||||
|  | 			return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 		} | ||||||
|  | 		mx = mx.FilterAuthor(author.ID) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if len(c.Query("category")) > 0 { | ||||||
|  | 		mx = mx.FilterWithCategory(c.Query("category")) | ||||||
|  | 	} | ||||||
|  | 	if len(c.Query("tag")) > 0 { | ||||||
|  | 		mx = mx.FilterWithTag(c.Query("tag")) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if !c.QueryBool("reply", true) { | ||||||
|  | 		mx = mx.FilterReply(true) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	count, err := mx.Count() | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusInternalServerError, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	items, err := mx.List(take, offset) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.JSON(fiber.Map{ | ||||||
|  | 		"count": count, | ||||||
|  | 		"data":  items, | ||||||
|  | 	}) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func createArticle(c *fiber.Ctx) error { | ||||||
|  | 	user := c.Locals("principal").(models.Account) | ||||||
|  |  | ||||||
|  | 	var data struct { | ||||||
|  | 		Alias       string              `json:"alias"` | ||||||
|  | 		Title       string              `json:"title" validate:"required"` | ||||||
|  | 		Description string              `json:"description"` | ||||||
|  | 		Content     string              `json:"content" validate:"required"` | ||||||
|  | 		Hashtags    []models.Tag        `json:"hashtags"` | ||||||
|  | 		Categories  []models.Category   `json:"categories"` | ||||||
|  | 		Attachments []models.Attachment `json:"attachments"` | ||||||
|  | 		PublishedAt *time.Time          `json:"published_at"` | ||||||
|  | 		RealmID     *uint               `json:"realm_id"` | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if err := BindAndValidate(c, &data); err != nil { | ||||||
|  | 		return err | ||||||
|  | 	} else if len(data.Alias) == 0 { | ||||||
|  | 		data.Alias = strings.ReplaceAll(uuid.NewString(), "-", "") | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	mx := contextArticle() | ||||||
|  |  | ||||||
|  | 	item := models.Article{ | ||||||
|  | 		PostBase: models.PostBase{ | ||||||
|  | 			Alias:       data.Alias, | ||||||
|  | 			Attachments: data.Attachments, | ||||||
|  | 			PublishedAt: data.PublishedAt, | ||||||
|  | 			AuthorID:    user.ID, | ||||||
|  | 		}, | ||||||
|  | 		Hashtags:    data.Hashtags, | ||||||
|  | 		Categories:  data.Categories, | ||||||
|  | 		Title:       data.Title, | ||||||
|  | 		Description: data.Description, | ||||||
|  | 		Content:     data.Content, | ||||||
|  | 		RealmID:     data.RealmID, | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	var realm *models.Realm | ||||||
|  | 	if data.RealmID != nil { | ||||||
|  | 		if err := database.C.Where(&models.Realm{ | ||||||
|  | 			BaseModel: models.BaseModel{ID: *data.RealmID}, | ||||||
|  | 		}).First(&realm).Error; err != nil { | ||||||
|  | 			return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	item, err := mx.New(item) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.JSON(item) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func editArticle(c *fiber.Ctx) error { | ||||||
|  | 	user := c.Locals("principal").(models.Account) | ||||||
|  | 	id, _ := c.ParamsInt("articleId", 0) | ||||||
|  |  | ||||||
|  | 	var data struct { | ||||||
|  | 		Alias       string              `json:"alias" validate:"required"` | ||||||
|  | 		Title       string              `json:"title" validate:"required"` | ||||||
|  | 		Description string              `json:"description"` | ||||||
|  | 		Content     string              `json:"content" validate:"required"` | ||||||
|  | 		PublishedAt *time.Time          `json:"published_at"` | ||||||
|  | 		Hashtags    []models.Tag        `json:"hashtags"` | ||||||
|  | 		Categories  []models.Category   `json:"categories"` | ||||||
|  | 		Attachments []models.Attachment `json:"attachments"` | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if err := BindAndValidate(c, &data); err != nil { | ||||||
|  | 		return err | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	mx := contextArticle().FilterAuthor(user.ID) | ||||||
|  |  | ||||||
|  | 	item, err := mx.Get(uint(id)) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	item.Alias = data.Alias | ||||||
|  | 	item.Title = data.Title | ||||||
|  | 	item.Description = data.Description | ||||||
|  | 	item.Content = data.Content | ||||||
|  | 	item.PublishedAt = data.PublishedAt | ||||||
|  | 	item.Hashtags = data.Hashtags | ||||||
|  | 	item.Categories = data.Categories | ||||||
|  | 	item.Attachments = data.Attachments | ||||||
|  |  | ||||||
|  | 	item, err = mx.Edit(item) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.JSON(item) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func reactArticle(c *fiber.Ctx) error { | ||||||
|  | 	user := c.Locals("principal").(models.Account) | ||||||
|  | 	id, _ := c.ParamsInt("articleId", 0) | ||||||
|  |  | ||||||
|  | 	var data struct { | ||||||
|  | 		Symbol   string                  `json:"symbol" validate:"required"` | ||||||
|  | 		Attitude models.ReactionAttitude `json:"attitude" validate:"required"` | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if err := BindAndValidate(c, &data); err != nil { | ||||||
|  | 		return err | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	mx := contextArticle() | ||||||
|  |  | ||||||
|  | 	item, err := mx.Get(uint(id)) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	reaction := models.Reaction{ | ||||||
|  | 		Symbol:    data.Symbol, | ||||||
|  | 		Attitude:  data.Attitude, | ||||||
|  | 		AccountID: user.ID, | ||||||
|  | 		ArticleID: &item.ID, | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if positive, reaction, err := mx.React(reaction); err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} else { | ||||||
|  | 		return c.Status(lo.Ternary(positive, fiber.StatusCreated, fiber.StatusNoContent)).JSON(reaction) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func deleteArticle(c *fiber.Ctx) error { | ||||||
|  | 	user := c.Locals("principal").(models.Account) | ||||||
|  | 	id, _ := c.ParamsInt("articleId", 0) | ||||||
|  |  | ||||||
|  | 	mx := contextArticle().FilterAuthor(user.ID) | ||||||
|  |  | ||||||
|  | 	item, err := mx.Get(uint(id)) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if err := mx.Delete(item); err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.SendStatus(fiber.StatusOK) | ||||||
|  | } | ||||||
							
								
								
									
										238
									
								
								pkg/server/comments_api.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										238
									
								
								pkg/server/comments_api.go
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,238 @@ | |||||||
|  | package server | ||||||
|  |  | ||||||
|  | import ( | ||||||
|  | 	"fmt" | ||||||
|  | 	"strings" | ||||||
|  | 	"time" | ||||||
|  |  | ||||||
|  | 	"code.smartsheep.studio/hydrogen/interactive/pkg/database" | ||||||
|  | 	"code.smartsheep.studio/hydrogen/interactive/pkg/models" | ||||||
|  | 	"code.smartsheep.studio/hydrogen/interactive/pkg/services" | ||||||
|  | 	"github.com/gofiber/fiber/v2" | ||||||
|  | 	"github.com/google/uuid" | ||||||
|  | 	"github.com/samber/lo" | ||||||
|  | ) | ||||||
|  |  | ||||||
|  | func contextComment() *services.PostTypeContext[models.Comment] { | ||||||
|  | 	return &services.PostTypeContext[models.Comment]{ | ||||||
|  | 		Tx:        database.C, | ||||||
|  | 		TypeName:  "Comment", | ||||||
|  | 		CanReply:  false, | ||||||
|  | 		CanRepost: true, | ||||||
|  | 	} | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func getComment(c *fiber.Ctx) error { | ||||||
|  | 	id, _ := c.ParamsInt("commentId", 0) | ||||||
|  |  | ||||||
|  | 	mx := contextComment().FilterPublishedAt(time.Now()) | ||||||
|  |  | ||||||
|  | 	item, err := mx.Get(uint(id)) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.JSON(item) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func listComment(c *fiber.Ctx) error { | ||||||
|  | 	take := c.QueryInt("take", 0) | ||||||
|  | 	offset := c.QueryInt("offset", 0) | ||||||
|  | 	realmId := c.QueryInt("realmId", 0) | ||||||
|  |  | ||||||
|  | 	mx := contextComment(). | ||||||
|  | 		FilterPublishedAt(time.Now()). | ||||||
|  | 		FilterRealm(uint(realmId)). | ||||||
|  | 		SortCreatedAt("desc") | ||||||
|  |  | ||||||
|  | 	var author models.Account | ||||||
|  | 	if len(c.Query("authorId")) > 0 { | ||||||
|  | 		if err := database.C.Where(&models.Account{Name: c.Query("authorId")}).First(&author).Error; err != nil { | ||||||
|  | 			return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 		} | ||||||
|  | 		mx = mx.FilterAuthor(author.ID) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if len(c.Query("category")) > 0 { | ||||||
|  | 		mx = mx.FilterWithCategory(c.Query("category")) | ||||||
|  | 	} | ||||||
|  | 	if len(c.Query("tag")) > 0 { | ||||||
|  | 		mx = mx.FilterWithTag(c.Query("tag")) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if !c.QueryBool("reply", true) { | ||||||
|  | 		mx = mx.FilterReply(true) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	count, err := mx.Count() | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusInternalServerError, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	items, err := mx.List(take, offset) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.JSON(fiber.Map{ | ||||||
|  | 		"count": count, | ||||||
|  | 		"data":  items, | ||||||
|  | 	}) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func createComment(c *fiber.Ctx) error { | ||||||
|  | 	user := c.Locals("principal").(models.Account) | ||||||
|  |  | ||||||
|  | 	var data struct { | ||||||
|  | 		Alias       string              `json:"alias"` | ||||||
|  | 		Content     string              `json:"content" validate:"required"` | ||||||
|  | 		Hashtags    []models.Tag        `json:"hashtags"` | ||||||
|  | 		Categories  []models.Category   `json:"categories"` | ||||||
|  | 		Attachments []models.Attachment `json:"attachments"` | ||||||
|  | 		PublishedAt *time.Time          `json:"published_at"` | ||||||
|  | 		ArticleID   *uint               `json:"article_id"` | ||||||
|  | 		MomentID    *uint               `json:"moment_id"` | ||||||
|  | 		ReplyTo     uint                `json:"reply_to"` | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if err := BindAndValidate(c, &data); err != nil { | ||||||
|  | 		return err | ||||||
|  | 	} else if len(data.Alias) == 0 { | ||||||
|  | 		data.Alias = strings.ReplaceAll(uuid.NewString(), "-", "") | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	mx := contextComment() | ||||||
|  |  | ||||||
|  | 	item := models.Comment{ | ||||||
|  | 		PostBase: models.PostBase{ | ||||||
|  | 			Alias:       data.Alias, | ||||||
|  | 			Attachments: data.Attachments, | ||||||
|  | 			PublishedAt: data.PublishedAt, | ||||||
|  | 			AuthorID:    user.ID, | ||||||
|  | 		}, | ||||||
|  | 		Hashtags:   data.Hashtags, | ||||||
|  | 		Categories: data.Categories, | ||||||
|  | 		Content:    data.Content, | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if data.ArticleID == nil && data.MomentID == nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, "comment must belongs to a resource") | ||||||
|  | 	} | ||||||
|  | 	if data.ArticleID != nil { | ||||||
|  | 		var article models.Article | ||||||
|  | 		if err := database.C.Where("id = ?", data.ArticleID).First(&article).Error; err != nil { | ||||||
|  | 			return fiber.NewError(fiber.StatusBadRequest, fmt.Sprintf("belongs to resource was not found: %v", err)) | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	var relatedCount int64 | ||||||
|  | 	if data.ReplyTo > 0 { | ||||||
|  | 		if err := database.C.Where("id = ?", data.ReplyTo). | ||||||
|  | 			Model(&models.Comment{}).Count(&relatedCount).Error; err != nil { | ||||||
|  | 			return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 		} else if relatedCount <= 0 { | ||||||
|  | 			return fiber.NewError(fiber.StatusNotFound, "related post was not found") | ||||||
|  | 		} else { | ||||||
|  | 			item.ReplyID = &data.ReplyTo | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	item, err := mx.New(item) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.JSON(item) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func editComment(c *fiber.Ctx) error { | ||||||
|  | 	user := c.Locals("principal").(models.Account) | ||||||
|  | 	id, _ := c.ParamsInt("commentId", 0) | ||||||
|  |  | ||||||
|  | 	var data struct { | ||||||
|  | 		Alias       string              `json:"alias" validate:"required"` | ||||||
|  | 		Content     string              `json:"content" validate:"required"` | ||||||
|  | 		PublishedAt *time.Time          `json:"published_at"` | ||||||
|  | 		Hashtags    []models.Tag        `json:"hashtags"` | ||||||
|  | 		Categories  []models.Category   `json:"categories"` | ||||||
|  | 		Attachments []models.Attachment `json:"attachments"` | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if err := BindAndValidate(c, &data); err != nil { | ||||||
|  | 		return err | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	mx := contextComment().FilterAuthor(user.ID) | ||||||
|  |  | ||||||
|  | 	item, err := mx.Get(uint(id)) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	item.Alias = data.Alias | ||||||
|  | 	item.Content = data.Content | ||||||
|  | 	item.PublishedAt = data.PublishedAt | ||||||
|  | 	item.Hashtags = data.Hashtags | ||||||
|  | 	item.Categories = data.Categories | ||||||
|  | 	item.Attachments = data.Attachments | ||||||
|  |  | ||||||
|  | 	item, err = mx.Edit(item) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.JSON(item) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func reactComment(c *fiber.Ctx) error { | ||||||
|  | 	user := c.Locals("principal").(models.Account) | ||||||
|  | 	id, _ := c.ParamsInt("commentId", 0) | ||||||
|  |  | ||||||
|  | 	var data struct { | ||||||
|  | 		Symbol   string                  `json:"symbol" validate:"required"` | ||||||
|  | 		Attitude models.ReactionAttitude `json:"attitude" validate:"required"` | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if err := BindAndValidate(c, &data); err != nil { | ||||||
|  | 		return err | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	mx := contextComment() | ||||||
|  |  | ||||||
|  | 	item, err := mx.Get(uint(id)) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	reaction := models.Reaction{ | ||||||
|  | 		Symbol:    data.Symbol, | ||||||
|  | 		Attitude:  data.Attitude, | ||||||
|  | 		AccountID: user.ID, | ||||||
|  | 		CommentID: &item.ID, | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if positive, reaction, err := mx.React(reaction); err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} else { | ||||||
|  | 		return c.Status(lo.Ternary(positive, fiber.StatusCreated, fiber.StatusNoContent)).JSON(reaction) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func deleteComment(c *fiber.Ctx) error { | ||||||
|  | 	user := c.Locals("principal").(models.Account) | ||||||
|  | 	id, _ := c.ParamsInt("commentId", 0) | ||||||
|  |  | ||||||
|  | 	mx := contextComment().FilterAuthor(user.ID) | ||||||
|  |  | ||||||
|  | 	item, err := mx.Get(uint(id)) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusNotFound, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if err := mx.Delete(item); err != nil { | ||||||
|  | 		return fiber.NewError(fiber.StatusBadRequest, err.Error()) | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return c.SendStatus(fiber.StatusOK) | ||||||
|  | } | ||||||
| @@ -12,7 +12,7 @@ import ( | |||||||
| 	"github.com/samber/lo" | 	"github.com/samber/lo" | ||||||
| ) | ) | ||||||
|  |  | ||||||
| func getMomentContext() *services.PostTypeContext[models.Moment] { | func contextMoment() *services.PostTypeContext[models.Moment] { | ||||||
| 	return &services.PostTypeContext[models.Moment]{ | 	return &services.PostTypeContext[models.Moment]{ | ||||||
| 		Tx:        database.C, | 		Tx:        database.C, | ||||||
| 		TypeName:  "Moment", | 		TypeName:  "Moment", | ||||||
| @@ -24,7 +24,7 @@ func getMomentContext() *services.PostTypeContext[models.Moment] { | |||||||
| func getMoment(c *fiber.Ctx) error { | func getMoment(c *fiber.Ctx) error { | ||||||
| 	id, _ := c.ParamsInt("momentId", 0) | 	id, _ := c.ParamsInt("momentId", 0) | ||||||
|  |  | ||||||
| 	mx := getMomentContext().FilterPublishedAt(time.Now()) | 	mx := contextMoment().FilterPublishedAt(time.Now()) | ||||||
|  |  | ||||||
| 	item, err := mx.Get(uint(id)) | 	item, err := mx.Get(uint(id)) | ||||||
| 	if err != nil { | 	if err != nil { | ||||||
| @@ -39,7 +39,7 @@ func listMoment(c *fiber.Ctx) error { | |||||||
| 	offset := c.QueryInt("offset", 0) | 	offset := c.QueryInt("offset", 0) | ||||||
| 	realmId := c.QueryInt("realmId", 0) | 	realmId := c.QueryInt("realmId", 0) | ||||||
|  |  | ||||||
| 	mx := getMomentContext(). | 	mx := contextMoment(). | ||||||
| 		FilterPublishedAt(time.Now()). | 		FilterPublishedAt(time.Now()). | ||||||
| 		FilterRealm(uint(realmId)). | 		FilterRealm(uint(realmId)). | ||||||
| 		SortCreatedAt("desc") | 		SortCreatedAt("desc") | ||||||
| @@ -84,7 +84,6 @@ func createMoment(c *fiber.Ctx) error { | |||||||
|  |  | ||||||
| 	var data struct { | 	var data struct { | ||||||
| 		Alias       string              `json:"alias"` | 		Alias       string              `json:"alias"` | ||||||
| 		Title       string              `json:"title"` |  | ||||||
| 		Content     string              `json:"content" validate:"required"` | 		Content     string              `json:"content" validate:"required"` | ||||||
| 		Hashtags    []models.Tag        `json:"hashtags"` | 		Hashtags    []models.Tag        `json:"hashtags"` | ||||||
| 		Categories  []models.Category   `json:"categories"` | 		Categories  []models.Category   `json:"categories"` | ||||||
| @@ -92,7 +91,6 @@ func createMoment(c *fiber.Ctx) error { | |||||||
| 		PublishedAt *time.Time          `json:"published_at"` | 		PublishedAt *time.Time          `json:"published_at"` | ||||||
| 		RealmID     *uint               `json:"realm_id"` | 		RealmID     *uint               `json:"realm_id"` | ||||||
| 		RepostTo    uint                `json:"repost_to"` | 		RepostTo    uint                `json:"repost_to"` | ||||||
| 		ReplyTo     uint                `json:"reply_to"` |  | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if err := BindAndValidate(c, &data); err != nil { | 	if err := BindAndValidate(c, &data); err != nil { | ||||||
| @@ -101,7 +99,7 @@ func createMoment(c *fiber.Ctx) error { | |||||||
| 		data.Alias = strings.ReplaceAll(uuid.NewString(), "-", "") | 		data.Alias = strings.ReplaceAll(uuid.NewString(), "-", "") | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	mx := getMomentContext() | 	mx := contextMoment() | ||||||
|  |  | ||||||
| 	item := models.Moment{ | 	item := models.Moment{ | ||||||
| 		PostBase: models.PostBase{ | 		PostBase: models.PostBase{ | ||||||
| @@ -162,7 +160,7 @@ func editMoment(c *fiber.Ctx) error { | |||||||
| 		return err | 		return err | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	mx := getMomentContext().FilterAuthor(user.ID) | 	mx := contextMoment().FilterAuthor(user.ID) | ||||||
|  |  | ||||||
| 	item, err := mx.Get(uint(id)) | 	item, err := mx.Get(uint(id)) | ||||||
| 	if err != nil { | 	if err != nil { | ||||||
| @@ -197,7 +195,7 @@ func reactMoment(c *fiber.Ctx) error { | |||||||
| 		return err | 		return err | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	mx := getMomentContext() | 	mx := contextMoment() | ||||||
|  |  | ||||||
| 	item, err := mx.Get(uint(id)) | 	item, err := mx.Get(uint(id)) | ||||||
| 	if err != nil { | 	if err != nil { | ||||||
| @@ -223,7 +221,7 @@ func deleteMoment(c *fiber.Ctx) error { | |||||||
| 	user := c.Locals("principal").(models.Account) | 	user := c.Locals("principal").(models.Account) | ||||||
| 	id, _ := c.ParamsInt("momentId", 0) | 	id, _ := c.ParamsInt("momentId", 0) | ||||||
|  |  | ||||||
| 	mx := getMomentContext().FilterAuthor(user.ID) | 	mx := contextMoment().FilterAuthor(user.ID) | ||||||
|  |  | ||||||
| 	item, err := mx.Get(uint(id)) | 	item, err := mx.Get(uint(id)) | ||||||
| 	if err != nil { | 	if err != nil { | ||||||
|   | |||||||
| @@ -81,6 +81,26 @@ func NewServer() { | |||||||
| 			moments.Delete("/:momentId", authMiddleware, deleteMoment) | 			moments.Delete("/:momentId", authMiddleware, deleteMoment) | ||||||
| 		} | 		} | ||||||
|  |  | ||||||
|  | 		articles := api.Group("/articles").Name("Articles API") | ||||||
|  | 		{ | ||||||
|  | 			articles.Get("/", listArticle) | ||||||
|  | 			articles.Get("/:articleId", getArticle) | ||||||
|  | 			articles.Post("/", authMiddleware, createArticle) | ||||||
|  | 			articles.Post("/:articleId/react", authMiddleware, reactArticle) | ||||||
|  | 			articles.Put("/:articleId", authMiddleware, editArticle) | ||||||
|  | 			articles.Delete("/:articleId", authMiddleware, deleteArticle) | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		comments := api.Group("/comments").Name("Comments API") | ||||||
|  | 		{ | ||||||
|  | 			comments.Get("/", listComment) | ||||||
|  | 			comments.Get("/:commentId", getComment) | ||||||
|  | 			comments.Post("/", authMiddleware, createComment) | ||||||
|  | 			comments.Post("/:commentId/react", authMiddleware, reactComment) | ||||||
|  | 			comments.Put("/:commentId", authMiddleware, editComment) | ||||||
|  | 			comments.Delete("/:commentId", authMiddleware, deleteComment) | ||||||
|  | 		} | ||||||
|  |  | ||||||
| 		api.Get("/categories", listCategories) | 		api.Get("/categories", listCategories) | ||||||
| 		api.Post("/categories", authMiddleware, newCategory) | 		api.Post("/categories", authMiddleware, newCategory) | ||||||
| 		api.Put("/categories/:categoryId", authMiddleware, editCategory) | 		api.Put("/categories/:categoryId", authMiddleware, editCategory) | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user