2024-06-24 23:34:10 +00:00
|
|
|
package storage
|
|
|
|
|
|
|
|
import (
|
2024-06-26 01:45:04 +00:00
|
|
|
"context"
|
|
|
|
"fmt"
|
|
|
|
|
2024-06-24 23:34:10 +00:00
|
|
|
"git.obamna.ru/erius/ozon-task/graph/model"
|
|
|
|
)
|
|
|
|
|
|
|
|
type InMemory struct {
|
|
|
|
postId uint
|
|
|
|
commentId uint
|
|
|
|
posts []*model.Post
|
|
|
|
comments []*model.Comment
|
|
|
|
}
|
|
|
|
|
|
|
|
func InitInMemory() *InMemory {
|
|
|
|
return &InMemory{
|
|
|
|
postId: 0,
|
|
|
|
commentId: 0,
|
|
|
|
posts: make([]*model.Post, 0),
|
|
|
|
comments: make([]*model.Comment, 0),
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) AddPost(input *model.PostInput) (*model.AddResult, error) {
|
|
|
|
post := model.PostFromInput(input)
|
2024-06-26 01:45:04 +00:00
|
|
|
s.insertPost(post)
|
2024-06-24 23:34:10 +00:00
|
|
|
return &model.AddResult{ItemID: &post.ID}, nil
|
|
|
|
}
|
|
|
|
|
2024-06-26 01:45:04 +00:00
|
|
|
func (s *InMemory) AddReplyToComment(input *model.CommentInput) (*model.AddResult, error) {
|
|
|
|
if !s.commentExists(*input.ParentCommentID) {
|
|
|
|
return nil, &IDNotFoundError{objName: "comment", id: *input.ParentCommentID}
|
|
|
|
}
|
|
|
|
comment, parent := model.CommentFromInput(input), s.comments[*input.ParentCommentID]
|
|
|
|
s.insertComment(comment)
|
|
|
|
parent.Replies = append(parent.Replies, comment)
|
|
|
|
return &model.AddResult{ItemID: &comment.ID}, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) AddCommentToPost(input *model.CommentInput) (*model.AddResult, error) {
|
|
|
|
if !s.postExists(*input.ParentPostID) {
|
|
|
|
return nil, &IDNotFoundError{objName: "post", id: *input.ParentPostID}
|
|
|
|
}
|
|
|
|
parent := s.posts[*input.ParentPostID]
|
|
|
|
if !parent.AllowComments {
|
|
|
|
return nil, fmt.Errorf("author disabled comments for this post")
|
|
|
|
}
|
2024-06-24 23:34:10 +00:00
|
|
|
comment := model.CommentFromInput(input)
|
2024-06-26 01:45:04 +00:00
|
|
|
s.insertComment(comment)
|
|
|
|
parent.Comments = append(parent.Comments, comment)
|
|
|
|
return &model.AddResult{ItemID: &comment.ID}, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) GetPost(id uint, ctx context.Context) (*model.Post, error) {
|
|
|
|
if !s.postExists(id) {
|
|
|
|
return nil, &IDNotFoundError{objName: "post", id: id}
|
|
|
|
}
|
|
|
|
return s.posts[id], nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) GetComment(id uint, ctx context.Context) (*model.Comment, error) {
|
|
|
|
if !s.commentExists(id) {
|
|
|
|
return nil, &IDNotFoundError{objName: "comment", id: id}
|
|
|
|
}
|
|
|
|
return s.comments[id], nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) GetPosts(first uint, after uint, ctx context.Context) (*model.PostsConnection, error) {
|
|
|
|
if !s.postExists(after) {
|
|
|
|
return nil, &IDNotFoundError{objName: "post", id: after}
|
|
|
|
}
|
|
|
|
nextPage, until := true, after+first
|
|
|
|
if !s.postExists(until) {
|
|
|
|
nextPage = false
|
|
|
|
until = uint(len(s.posts))
|
|
|
|
}
|
|
|
|
info, edges := &model.PageInfo{
|
|
|
|
StartCursor: after,
|
|
|
|
EndCursor: until - 1,
|
|
|
|
HasNextPage: nextPage,
|
|
|
|
}, make([]*model.PostsEdge, until-after)
|
|
|
|
for i, p := range s.posts[after:until] {
|
|
|
|
edges[i] = &model.PostsEdge{
|
|
|
|
Cursor: p.ID,
|
|
|
|
Node: p,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return &model.PostsConnection{
|
|
|
|
Edges: edges,
|
|
|
|
PageInfo: info,
|
|
|
|
}, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) GetComments(post *model.Post, first uint, after uint, ctx context.Context) (*model.CommentsConnection, error) {
|
|
|
|
if !s.commentExists(after) {
|
|
|
|
return nil, &IDNotFoundError{objName: "comment", id: after}
|
|
|
|
}
|
|
|
|
nextPage, until := true, after+first
|
|
|
|
if !s.commentExists(until) {
|
|
|
|
nextPage = false
|
|
|
|
until = uint(len(s.comments))
|
|
|
|
}
|
|
|
|
info, edges := &model.PageInfo{
|
|
|
|
StartCursor: after,
|
|
|
|
EndCursor: until - 1,
|
|
|
|
HasNextPage: nextPage,
|
|
|
|
}, make([]*model.CommentsEdge, until-after)
|
|
|
|
for i, c := range post.Comments[after:until] {
|
|
|
|
edges[i] = &model.CommentsEdge{
|
|
|
|
Cursor: c.ID,
|
|
|
|
Node: c,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return &model.CommentsConnection{
|
|
|
|
Edges: edges,
|
|
|
|
PageInfo: info,
|
|
|
|
}, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) GetReplies(comment *model.Comment, first uint, after uint, ctx context.Context) (*model.CommentsConnection, error) {
|
|
|
|
if !s.commentExists(after) {
|
|
|
|
return nil, &IDNotFoundError{objName: "comment", id: after}
|
|
|
|
}
|
|
|
|
nextPage, until := true, after+first
|
|
|
|
if !s.commentExists(until) {
|
|
|
|
nextPage = false
|
|
|
|
until = uint(len(s.comments))
|
|
|
|
}
|
|
|
|
info, edges := &model.PageInfo{
|
|
|
|
StartCursor: after,
|
|
|
|
EndCursor: until - 1,
|
|
|
|
HasNextPage: nextPage,
|
|
|
|
}, make([]*model.CommentsEdge, until-after)
|
|
|
|
for i, c := range comment.Replies[after:until] {
|
|
|
|
edges[i] = &model.CommentsEdge{
|
|
|
|
Cursor: c.ID,
|
|
|
|
Node: c,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return &model.CommentsConnection{
|
|
|
|
Edges: edges,
|
|
|
|
PageInfo: info,
|
|
|
|
}, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) postExists(id uint) bool {
|
|
|
|
return id < uint(len(s.posts))
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) commentExists(id uint) bool {
|
|
|
|
return id < uint(len(s.comments))
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *InMemory) insertComment(comment *model.Comment) {
|
2024-06-24 23:34:10 +00:00
|
|
|
comment.ID = s.commentId
|
|
|
|
s.comments = append(s.comments, comment)
|
|
|
|
s.commentId++
|
|
|
|
}
|
|
|
|
|
2024-06-26 01:45:04 +00:00
|
|
|
func (s *InMemory) insertPost(post *model.Post) {
|
|
|
|
post.ID = s.postId
|
|
|
|
s.posts = append(s.posts, post)
|
|
|
|
s.postId++
|
2024-06-24 23:34:10 +00:00
|
|
|
}
|