mirror of
https://github.com/snowykami/neo-blog.git
synced 2025-09-25 18:46:23 +00:00
feat: 更新评论输入框的占位符,支持自定义占位符文本
All checks were successful
Push to Helm Chart Repository / build (push) Successful in 27s
All checks were successful
Push to Helm Chart Repository / build (push) Successful in 27s
This commit is contained in:
@ -1,179 +1,179 @@
|
||||
package service
|
||||
|
||||
import (
|
||||
"context"
|
||||
"strconv"
|
||||
"context"
|
||||
"strconv"
|
||||
|
||||
"github.com/snowykami/neo-blog/pkg/constant"
|
||||
"github.com/snowykami/neo-blog/pkg/constant"
|
||||
|
||||
"github.com/snowykami/neo-blog/internal/ctxutils"
|
||||
"github.com/snowykami/neo-blog/internal/dto"
|
||||
"github.com/snowykami/neo-blog/internal/model"
|
||||
"github.com/snowykami/neo-blog/internal/repo"
|
||||
"github.com/snowykami/neo-blog/pkg/errs"
|
||||
"github.com/snowykami/neo-blog/internal/ctxutils"
|
||||
"github.com/snowykami/neo-blog/internal/dto"
|
||||
"github.com/snowykami/neo-blog/internal/model"
|
||||
"github.com/snowykami/neo-blog/internal/repo"
|
||||
"github.com/snowykami/neo-blog/pkg/errs"
|
||||
)
|
||||
|
||||
type CommentService struct{}
|
||||
|
||||
func NewCommentService() *CommentService {
|
||||
return &CommentService{}
|
||||
return &CommentService{}
|
||||
}
|
||||
|
||||
func (cs *CommentService) CreateComment(ctx context.Context, req *dto.CreateCommentReq) (uint, error) {
|
||||
currentUser, ok := ctxutils.GetCurrentUser(ctx)
|
||||
if !ok {
|
||||
return 0, errs.ErrUnauthorized
|
||||
}
|
||||
currentUser, ok := ctxutils.GetCurrentUser(ctx)
|
||||
if !ok {
|
||||
return 0, errs.ErrUnauthorized
|
||||
}
|
||||
|
||||
if ok, err := cs.checkTargetExists(req.TargetID, req.TargetType); !ok {
|
||||
if err != nil {
|
||||
return 0, errs.New(errs.ErrBadRequest.Code, "target not found", err)
|
||||
}
|
||||
return 0, errs.ErrBadRequest
|
||||
}
|
||||
if ok, err := cs.checkTargetExists(req.TargetID, req.TargetType); !ok {
|
||||
if err != nil {
|
||||
return 0, errs.New(errs.ErrBadRequest.Code, "target not found", err)
|
||||
}
|
||||
return 0, errs.ErrBadRequest
|
||||
}
|
||||
|
||||
comment := &model.Comment{
|
||||
Content: req.Content,
|
||||
ReplyID: req.ReplyID,
|
||||
TargetID: req.TargetID,
|
||||
TargetType: req.TargetType,
|
||||
UserID: currentUser.ID,
|
||||
IsPrivate: req.IsPrivate,
|
||||
RemoteAddr: req.RemoteAddr,
|
||||
UserAgent: req.UserAgent,
|
||||
}
|
||||
comment := &model.Comment{
|
||||
Content: req.Content,
|
||||
ReplyID: req.ReplyID,
|
||||
TargetID: req.TargetID,
|
||||
TargetType: req.TargetType,
|
||||
UserID: currentUser.ID,
|
||||
IsPrivate: req.IsPrivate,
|
||||
RemoteAddr: req.RemoteAddr,
|
||||
UserAgent: req.UserAgent,
|
||||
}
|
||||
|
||||
commentID, err := repo.Comment.CreateComment(comment)
|
||||
commentID, err := repo.Comment.CreateComment(comment)
|
||||
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
return commentID, nil
|
||||
return commentID, nil
|
||||
}
|
||||
|
||||
func (cs *CommentService) UpdateComment(ctx context.Context, req *dto.UpdateCommentReq) error {
|
||||
currentUser, ok := ctxutils.GetCurrentUser(ctx)
|
||||
if !ok {
|
||||
return errs.ErrUnauthorized
|
||||
}
|
||||
currentUser, ok := ctxutils.GetCurrentUser(ctx)
|
||||
if !ok {
|
||||
return errs.ErrUnauthorized
|
||||
}
|
||||
|
||||
comment, err := repo.Comment.GetComment(strconv.Itoa(int(req.CommentID)))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
comment, err := repo.Comment.GetComment(strconv.Itoa(int(req.CommentID)))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if currentUser.ID != comment.UserID {
|
||||
return errs.ErrForbidden
|
||||
}
|
||||
if currentUser.ID != comment.UserID {
|
||||
return errs.ErrForbidden
|
||||
}
|
||||
|
||||
comment.Content = req.Content
|
||||
comment.IsPrivate = req.IsPrivate
|
||||
comment.Content = req.Content
|
||||
comment.IsPrivate = req.IsPrivate
|
||||
|
||||
err = repo.Comment.UpdateComment(comment)
|
||||
err = repo.Comment.UpdateComment(comment)
|
||||
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
return nil
|
||||
}
|
||||
|
||||
func (cs *CommentService) DeleteComment(ctx context.Context, commentID string) error {
|
||||
currentUser, ok := ctxutils.GetCurrentUser(ctx)
|
||||
if !ok {
|
||||
return errs.ErrUnauthorized
|
||||
}
|
||||
if commentID == "" {
|
||||
return errs.ErrBadRequest
|
||||
}
|
||||
currentUser, ok := ctxutils.GetCurrentUser(ctx)
|
||||
if !ok {
|
||||
return errs.ErrUnauthorized
|
||||
}
|
||||
if commentID == "" {
|
||||
return errs.ErrBadRequest
|
||||
}
|
||||
|
||||
comment, err := repo.Comment.GetComment(commentID)
|
||||
if err != nil {
|
||||
return errs.New(errs.ErrNotFound.Code, "comment not found", err)
|
||||
}
|
||||
comment, err := repo.Comment.GetComment(commentID)
|
||||
if err != nil {
|
||||
return errs.New(errs.ErrNotFound.Code, "comment not found", err)
|
||||
}
|
||||
|
||||
if comment.UserID != currentUser.ID {
|
||||
return errs.ErrForbidden
|
||||
}
|
||||
if comment.UserID != currentUser.ID {
|
||||
return errs.ErrForbidden
|
||||
}
|
||||
|
||||
if err := repo.Comment.DeleteComment(commentID); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := repo.Comment.DeleteComment(commentID); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
return nil
|
||||
}
|
||||
|
||||
func (cs *CommentService) GetComment(ctx context.Context, commentID string) (*dto.CommentDto, error) {
|
||||
comment, err := repo.Comment.GetComment(commentID)
|
||||
comment, err := repo.Comment.GetComment(commentID)
|
||||
|
||||
if err != nil {
|
||||
return nil, errs.New(errs.ErrNotFound.Code, "comment not found", err)
|
||||
}
|
||||
if err != nil {
|
||||
return nil, errs.New(errs.ErrNotFound.Code, "comment not found", err)
|
||||
}
|
||||
|
||||
commentDto := dto.CommentDto{
|
||||
ID: comment.ID,
|
||||
TargetID: comment.TargetID,
|
||||
TargetType: comment.TargetType,
|
||||
Content: comment.Content,
|
||||
ReplyID: comment.ReplyID,
|
||||
Depth: comment.Depth,
|
||||
CreatedAt: comment.CreatedAt.String(),
|
||||
UpdatedAt: comment.UpdatedAt.String(),
|
||||
User: comment.User.ToDto(),
|
||||
}
|
||||
commentDto := dto.CommentDto{
|
||||
ID: comment.ID,
|
||||
TargetID: comment.TargetID,
|
||||
TargetType: comment.TargetType,
|
||||
Content: comment.Content,
|
||||
ReplyID: comment.ReplyID,
|
||||
Depth: comment.Depth,
|
||||
CreatedAt: comment.CreatedAt.String(),
|
||||
UpdatedAt: comment.UpdatedAt.String(),
|
||||
User: comment.User.ToDto(),
|
||||
}
|
||||
|
||||
return &commentDto, err
|
||||
return &commentDto, err
|
||||
}
|
||||
|
||||
func (cs *CommentService) GetCommentList(ctx context.Context, req *dto.GetCommentListReq) ([]dto.CommentDto, error) {
|
||||
currentUserID := uint(0)
|
||||
if currentUser, ok := ctxutils.GetCurrentUser(ctx); ok {
|
||||
currentUserID = currentUser.ID
|
||||
}
|
||||
currentUserID := uint(0)
|
||||
if currentUser, ok := ctxutils.GetCurrentUser(ctx); ok {
|
||||
currentUserID = currentUser.ID
|
||||
}
|
||||
|
||||
comments, err := repo.Comment.ListComments(currentUserID, req.TargetID, req.CommentID, req.TargetType, req.Page, req.Size, req.OrderBy, req.Desc, req.Depth)
|
||||
if err != nil {
|
||||
return nil, errs.New(errs.ErrInternalServer.Code, "failed to list comments", err)
|
||||
}
|
||||
comments, err := repo.Comment.ListComments(currentUserID, req.TargetID, req.CommentID, req.TargetType, req.Page, req.Size, req.OrderBy, req.Desc, req.Depth)
|
||||
if err != nil {
|
||||
return nil, errs.New(errs.ErrInternalServer.Code, "failed to list comments", err)
|
||||
}
|
||||
|
||||
commentDtos := make([]dto.CommentDto, 0)
|
||||
commentDtos := make([]dto.CommentDto, 0)
|
||||
|
||||
for _, comment := range comments {
|
||||
//replyCount, _ := repo.Comment.CountReplyComments(currentUserID, comment.ID)
|
||||
isLiked := false
|
||||
if currentUserID != 0 {
|
||||
isLiked, _ = repo.Like.IsLiked(currentUserID, comment.ID, constant.TargetTypeComment)
|
||||
}
|
||||
for _, comment := range comments {
|
||||
//replyCount, _ := repo.Comment.CountReplyComments(currentUserID, comment.ID)
|
||||
isLiked := false
|
||||
if currentUserID != 0 {
|
||||
isLiked, _ = repo.Like.IsLiked(currentUserID, comment.ID, constant.TargetTypeComment)
|
||||
}
|
||||
|
||||
commentDto := dto.CommentDto{
|
||||
ID: comment.ID,
|
||||
Content: comment.Content,
|
||||
TargetID: comment.TargetID,
|
||||
TargetType: comment.TargetType,
|
||||
ReplyID: comment.ReplyID,
|
||||
CreatedAt: comment.CreatedAt.String(),
|
||||
UpdatedAt: comment.UpdatedAt.String(),
|
||||
Depth: comment.Depth,
|
||||
User: comment.User.ToDto(),
|
||||
ReplyCount: comment.CommentCount,
|
||||
LikeCount: comment.LikeCount,
|
||||
IsLiked: isLiked,
|
||||
IsPrivate: comment.IsPrivate,
|
||||
}
|
||||
commentDtos = append(commentDtos, commentDto)
|
||||
}
|
||||
return commentDtos, nil
|
||||
commentDto := dto.CommentDto{
|
||||
ID: comment.ID,
|
||||
Content: comment.Content,
|
||||
TargetID: comment.TargetID,
|
||||
TargetType: comment.TargetType,
|
||||
ReplyID: comment.ReplyID,
|
||||
CreatedAt: comment.CreatedAt.String(),
|
||||
UpdatedAt: comment.UpdatedAt.String(),
|
||||
Depth: comment.Depth,
|
||||
User: comment.User.ToDto(),
|
||||
ReplyCount: comment.CommentCount,
|
||||
LikeCount: comment.LikeCount,
|
||||
IsLiked: isLiked,
|
||||
IsPrivate: comment.IsPrivate,
|
||||
}
|
||||
commentDtos = append(commentDtos, commentDto)
|
||||
}
|
||||
return commentDtos, nil
|
||||
}
|
||||
|
||||
func (cs *CommentService) checkTargetExists(targetID uint, targetType string) (bool, error) {
|
||||
switch targetType {
|
||||
case constant.TargetTypePost:
|
||||
if _, err := repo.Post.GetPostByID(strconv.Itoa(int(targetID))); err != nil {
|
||||
return false, errs.New(errs.ErrNotFound.Code, "post not found", err)
|
||||
}
|
||||
default:
|
||||
return false, errs.New(errs.ErrBadRequest.Code, "invalid target type", nil)
|
||||
}
|
||||
return true, nil
|
||||
switch targetType {
|
||||
case constant.TargetTypePost:
|
||||
if _, err := repo.Post.GetPostByID(strconv.Itoa(int(targetID))); err != nil {
|
||||
return false, errs.New(errs.ErrNotFound.Code, "post not found", err)
|
||||
}
|
||||
default:
|
||||
return false, errs.New(errs.ErrBadRequest.Code, "invalid target type", nil)
|
||||
}
|
||||
return true, nil
|
||||
}
|
||||
|
@ -16,12 +16,14 @@ export function CommentInput(
|
||||
onCommentSubmitted,
|
||||
initContent = "",
|
||||
initIsPrivate = false,
|
||||
placeholder = "",
|
||||
isUpdate = false
|
||||
}: {
|
||||
user: User | null,
|
||||
onCommentSubmitted: ({ commentContent, isPrivate }: { commentContent: string, isPrivate: boolean }) => void,
|
||||
initContent?: string,
|
||||
initIsPrivate?: boolean,
|
||||
placeholder?: string,
|
||||
isUpdate?: boolean,
|
||||
}
|
||||
) {
|
||||
@ -65,7 +67,7 @@ export function CommentInput(
|
||||
</div>
|
||||
<div className="flex-1 pl-2 fade-in-up">
|
||||
<Textarea
|
||||
placeholder={user ? (isPrivate ? t("private_placeholder") : t("placeholder")) : t("login_required", { loginButton: "登录" })}
|
||||
placeholder={placeholder || (user ? (isPrivate ? t("private_placeholder") : t("placeholder")) : t("login_required", { loginButton: "登录" }))}
|
||||
className="w-full p-2 border border-gray-300 rounded-md fade-in-up"
|
||||
value={commentContent}
|
||||
onChange={(e) => setCommentContent(e.target.value)}
|
||||
|
@ -268,6 +268,7 @@ export function CommentItem(
|
||||
user={user}
|
||||
onCommentSubmitted={onReply}
|
||||
initIsPrivate={isPrivate}
|
||||
placeholder={`${t("reply")} ${comment.user.nickname} :`}
|
||||
/>}
|
||||
{activeInput && activeInput.type === 'edit' && activeInput.id === comment.id && <CommentInput
|
||||
user={user}
|
||||
|
Reference in New Issue
Block a user