Skip to content
This repository was archived by the owner on Nov 8, 2022. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 1 addition & 2 deletions lib/groupher_server/accounts/delegates/collect_folder.ex
Original file line number Diff line number Diff line change
Expand Up @@ -208,8 +208,7 @@ defmodule GroupherServer.Accounts.Delegate.CollectFolder do
folder
|> Ecto.Changeset.change(%{total_count: total_count, last_updated: last_updated})
|> Ecto.Changeset.put_embed(:collects, collects)
|> Ecto.Changeset.put_embed(:meta, meta)
|> Repo.update()
|> ORM.update_meta(meta)
end

# check if the article is already in this folder
Expand Down
1 change: 1 addition & 0 deletions lib/groupher_server/cms/article_comment.ex
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ defmodule GroupherServer.CMS.ArticleComment do

# 是否置顶
field(:is_pinned, :boolean, default: false)
field(:viewer_has_upvoted, :boolean, default: false, virtual: true)

belongs_to(:author, Accounts.User, foreign_key: :author_id)
belongs_to(:post, Post, foreign_key: :post_id)
Expand Down
48 changes: 37 additions & 11 deletions lib/groupher_server/cms/delegates/article_comment.ex
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleComment do
CURD and operations for article comments
"""
import Ecto.Query, warn: false
import Helper.Utils, only: [done: 1]
import Helper.Utils, only: [done: 1, strip_struct: 1]
import Helper.ErrorCode

import GroupherServer.CMS.Utils.Matcher2
Expand Down Expand Up @@ -281,13 +281,6 @@ defmodule GroupherServer.CMS.Delegate.ArticleComment do
end)
|> Repo.transaction()
|> upsert_comment_result

# is not work this way, why?
# updated_emotions =
# Map.merge(comment.emotions, %{
# downvote_count: comment.emotions.downvote_count + Enum.random([1, 2, 3]),
# tada_count: comment.emotions.tada_count + Enum.random([1, 2, 3])
# })
end
end

Expand Down Expand Up @@ -363,12 +356,15 @@ defmodule GroupherServer.CMS.Delegate.ArticleComment do
def upvote_article_comment(comment_id, %User{id: user_id}) do
with {:ok, comment} <- ORM.find(ArticleComment, comment_id),
false <- comment.is_deleted do
# IO.inspect(comment, label: "the comment")
# TODO: is user upvoted before?
Multi.new()
|> Multi.run(:create_comment_upvote, fn _, _ ->
ORM.create(ArticleCommentUpvote, %{article_comment_id: comment.id, user_id: user_id})
end)
|> Multi.run(:inc_upvotes_count, fn _, _ ->
|> Multi.run(:add_upvoted_user, fn _, _ ->
update_upvoted_user_list(comment, user_id, :add)
end)
|> Multi.run(:inc_upvotes_count, fn _, %{add_upvoted_user: comment} ->
count_query = from(c in ArticleCommentUpvote, where: c.article_comment_id == ^comment.id)
upvotes_count = Repo.aggregate(count_query, :count)
ORM.update(comment, %{upvotes_count: upvotes_count})
Expand All @@ -392,7 +388,10 @@ defmodule GroupherServer.CMS.Delegate.ArticleComment do
user_id: user_id
})
end)
|> Multi.run(:desc_upvotes_count, fn _, _ ->
|> Multi.run(:remove_upvoted_user, fn _, _ ->
update_upvoted_user_list(comment, user_id, :remove)
end)
|> Multi.run(:desc_upvotes_count, fn _, %{remove_upvoted_user: comment} ->
count_query = from(c in ArticleCommentUpvote, where: c.article_comment_id == ^comment_id)
upvotes_count = Repo.aggregate(count_query, :count)

Expand All @@ -419,6 +418,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleComment do
|> ORM.paginater(~m(page size)a)
|> set_viewer_emotion_ifneed(user)
|> add_pined_comments_ifneed(thread, article_id, filters)
|> mark_viewer_has_upvoted(user)
|> done()
end
end
Expand All @@ -435,6 +435,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleComment do
|> QueryBuilder.filter_pack(filters)
|> ORM.paginater(~m(page size)a)
|> set_viewer_emotion_ifneed(user)
|> mark_viewer_has_upvoted(user)
|> done()
end

Expand Down Expand Up @@ -607,6 +608,18 @@ defmodule GroupherServer.CMS.Delegate.ArticleComment do
%{paged_comments | entries: new_entries}
end

defp mark_viewer_has_upvoted(paged_comments, nil), do: paged_comments

defp mark_viewer_has_upvoted(%{entries: entries} = paged_comments, %User{} = user) do
entries =
Enum.map(
entries,
&Map.merge(&1, %{viewer_has_upvoted: Enum.member?(&1.meta.upvoted_user_ids, user.id)})
)

Map.merge(paged_comments, %{entries: entries})
end

defp get_article(%ArticleComment{post_id: post_id} = comment) when not is_nil(post_id) do
with {:ok, article} <- ORM.find(Post, comment.post_id, preload: [author: :user]) do
{:post, article}
Expand Down Expand Up @@ -674,6 +687,19 @@ defmodule GroupherServer.CMS.Delegate.ArticleComment do
end
end

defp update_upvoted_user_list(comment, user_id, opt) do
cur_user_ids = get_in(comment, [:meta, :upvoted_user_ids])

user_ids =
case opt do
:add -> [user_id] ++ cur_user_ids
:remove -> cur_user_ids -- [user_id]
end

meta = comment.meta |> Map.merge(%{upvoted_user_ids: user_ids}) |> strip_struct
ORM.update_meta(comment, meta)
end

defp upsert_comment_result({:ok, %{create_article_comment: result}}), do: {:ok, result}
defp upsert_comment_result({:ok, %{add_reply_to: result}}), do: {:ok, result}
defp upsert_comment_result({:ok, %{check_article_author_upvoted: result}}), do: {:ok, result}
Expand Down
18 changes: 3 additions & 15 deletions lib/groupher_server/cms/delegates/article_curd.ex
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleCURD do
import GroupherServer.CMS.Utils.Matcher2
import GroupherServer.CMS.Utils.Matcher, only: [match_action: 2]

import Helper.Utils, only: [done: 1, pick_by: 2, integerfy: 1]
import Helper.Utils, only: [done: 1, pick_by: 2, integerfy: 1, strip_struct: 1]
import Helper.ErrorCode

alias Helper.{Later, ORM}
Expand Down Expand Up @@ -443,16 +443,11 @@ defmodule GroupherServer.CMS.Delegate.ArticleCURD do

defp exec_update_tags(_content, _), do: {:ok, :pass}

# TODO: move to utils
defp strip_struct(struct) do
struct |> Map.from_struct() |> Map.delete(:id)
end

defp update_viewed_user_list(%{meta: nil} = article, user_id) do
new_ids = Enum.uniq([user_id] ++ @default_article_meta.viewed_user_ids)
meta = @default_article_meta |> Map.merge(%{viewed_user_ids: new_ids})

do_update_viewed_user_list(article, meta)
ORM.update_meta(article, meta)
end

defp update_viewed_user_list(%{meta: meta} = article, user_id) do
Expand All @@ -462,20 +457,13 @@ defmodule GroupherServer.CMS.Delegate.ArticleCURD do
true ->
new_ids = Enum.uniq([user_id] ++ meta.viewed_user_ids)
meta = meta |> Map.merge(%{viewed_user_ids: new_ids}) |> strip_struct
do_update_viewed_user_list(article, meta)
ORM.update_meta(article, meta)

false ->
{:ok, :pass}
end
end

defp do_update_viewed_user_list(article, meta) do
article
|> Ecto.Changeset.change()
|> Ecto.Changeset.put_embed(:meta, meta)
|> Repo.update()
end

defp read_result({:ok, %{inc_views: result}}), do: result |> done()

defp read_result({:error, _, result, _steps}) do
Expand Down
26 changes: 7 additions & 19 deletions lib/groupher_server/cms/delegates/article_operation.ex
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleOperation do

import Helper.ErrorCode
import ShortMaps
import Helper.Utils, only: [strip_struct: 1]
import GroupherServer.CMS.Utils.Matcher2

alias Helper.Types, as: T
Expand Down Expand Up @@ -163,20 +164,15 @@ defmodule GroupherServer.CMS.Delegate.ArticleOperation do
@doc "update isEdited meta label if needed"
# TODO: diff history
def update_edit_status(%{meta: %Embeds.ArticleMeta{is_edited: false} = meta} = content) do
new_meta =
meta
|> Map.from_struct()
|> Map.delete(:id)
|> Map.merge(%{is_edited: true})

do_update_meta(content, new_meta)
meta = meta |> strip_struct |> Map.merge(%{is_edited: true})
ORM.update_meta(content, meta)
end

# for test or exsiting articles
def update_edit_status(%{meta: nil} = content) do
new_meta = Embeds.ArticleMeta.default_meta() |> Map.merge(%{is_edited: true})
meta = Embeds.ArticleMeta.default_meta() |> Map.merge(%{is_edited: true})

do_update_meta(content, new_meta)
ORM.update_meta(content, meta)
end

def update_edit_status(content, _), do: {:ok, content}
Expand All @@ -186,25 +182,17 @@ defmodule GroupherServer.CMS.Delegate.ArticleOperation do
def lock_article_comment(
%{meta: %Embeds.ArticleMeta{is_comment_locked: false} = meta} = content
) do
new_meta =
meta =
meta
|> Map.from_struct()
|> Map.delete(:id)
|> Map.merge(%{is_comment_locked: true})

do_update_meta(content, new_meta)
ORM.update_meta(content, meta)
end

def lock_article_comment(content), do: {:ok, content}

# TODO: put it into ORM helper
defp do_update_meta(%{meta: _} = content, meta_params) do
content
|> Ecto.Changeset.change()
|> Ecto.Changeset.put_embed(:meta, meta_params)
|> Repo.update()
end

# check if the thread has aready enough pined articles
defp check_pinned_article_count(community_id, thread) do
thread_upcase = thread |> to_string |> String.upcase()
Expand Down
24 changes: 5 additions & 19 deletions lib/groupher_server/cms/delegates/article_reaction.ex
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,9 @@ defmodule GroupherServer.CMS.Delegate.ArticleReaction do
@moduledoc """
reaction[upvote, collect, watch ...] on article [post, job...]
"""
import Helper.Utils, only: [done: 1]

import GroupherServer.CMS.Utils.Matcher2
import Ecto.Query, warn: false
import Helper.Utils, only: [done: 1, strip_struct: 1]
# import Helper.ErrorCode
import ShortMaps

Expand Down Expand Up @@ -232,9 +231,8 @@ defmodule GroupherServer.CMS.Delegate.ArticleReaction do
:remove -> cur_user_ids -- [user_id]
end

updated_meta = @default_article_meta |> Map.merge(%{"#{action}ed_user_ids": updated_user_ids})

do_update_article_meta(article, updated_meta)
meta = @default_article_meta |> Map.merge(%{"#{action}ed_user_ids": updated_user_ids})
ORM.update_meta(article, meta)
end

defp update_article_reaction_user_list(action, article, user_id, opt) do
Expand All @@ -246,20 +244,8 @@ defmodule GroupherServer.CMS.Delegate.ArticleReaction do
:remove -> cur_user_ids -- [user_id]
end

meta =
article.meta
|> Map.merge(%{"#{action}ed_user_ids": updated_user_ids})
|> Map.from_struct()
|> Map.delete(:id)

do_update_article_meta(article, meta)
end

defp do_update_article_meta(article, meta) do
article
|> Ecto.Changeset.change()
|> Ecto.Changeset.put_embed(:meta, meta)
|> Repo.update()
meta = article.meta |> Map.merge(%{"#{action}ed_user_ids": updated_user_ids}) |> strip_struct
ORM.update_meta(article, meta)
end

defp reaction_result({:ok, %{create_upvote: result}}), do: result |> done()
Expand Down
7 changes: 6 additions & 1 deletion lib/groupher_server/cms/embeds/article_comment_meta.ex
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ defmodule GroupherServer.CMS.Embeds.ArticleCommentMeta do
general article comment meta info
"""
use Ecto.Schema
use Accessible

import Ecto.Changeset

@optional_fields ~w(is_article_author_upvoted is_solution report_count is_reply_to_others)a
Expand All @@ -11,7 +13,8 @@ defmodule GroupherServer.CMS.Embeds.ArticleCommentMeta do
is_article_author_upvoted: false,
is_solution: false,
is_reply_to_others: false,
report_count: 0
report_count: 0,
upvoted_user_ids: []
}

@doc "for test usage"
Expand All @@ -24,6 +27,8 @@ defmodule GroupherServer.CMS.Embeds.ArticleCommentMeta do
# 用于回复模式,指代这条回复是回复“回复列表其他人的” (方便前端展示)
field(:is_reply_to_others, :boolean, default: false)
field(:report_count, :integer, default: 0)

field(:upvoted_user_ids, {:array, :integer}, default: [])
end

def changeset(struct, params) do
Expand Down
13 changes: 6 additions & 7 deletions lib/groupher_server/cms/utils/loader.ex
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ defmodule GroupherServer.CMS.Utils.Loader do

alias CMS.{
Author,
ArticleCommentUpvote,
CommunityEditor,
CommunitySubscriber,
CommunityThread,
Expand Down Expand Up @@ -165,12 +164,12 @@ defmodule GroupherServer.CMS.Utils.Loader do
|> QueryBuilder.members_pack(args)
end

def query({"articles_comments_upvotes", ArticleCommentUpvote}, %{
viewer_did: _,
cur_user: cur_user
}) do
ArticleCommentUpvote |> where([f], f.user_id == ^cur_user.id)
end
# def query({"articles_comments_upvotes", ArticleCommentUpvote}, %{
# viewer_did: _,
# cur_user: cur_user
# }) do
# ArticleCommentUpvote |> where([f], f.user_id == ^cur_user.id)
# end

# default loader
def query(queryable, _args) do
Expand Down
19 changes: 2 additions & 17 deletions lib/groupher_server_web/schema/cms/cms_types.ex
Original file line number Diff line number Diff line change
Expand Up @@ -339,15 +339,7 @@ defmodule GroupherServerWeb.Schema.CMS.Types do
field(:meta, :article_comment_meta)
field(:replies_count, :integer)
field(:reply_to, :article_comment_reply)

field :viewer_has_upvoted, :boolean do
arg(:viewer_did, :viewer_did_type, default_value: :viewer_did)

middleware(M.Authorize, :login)
middleware(M.PutCurrentUser)
resolve(dataloader(CMS, :upvotes))
middleware(M.ViewerDidConvert)
end
field(:viewer_has_upvoted, :boolean)

timestamp_fields()
end
Expand All @@ -365,15 +357,8 @@ defmodule GroupherServerWeb.Schema.CMS.Types do
field(:reply_to, :article_comment_reply)
field(:replies, list_of(:article_comment_reply))
field(:replies_count, :integer)
# field(:viewer_has_upvoted, :boolean, resolve: dataloader(CMS, :))
field :viewer_has_upvoted, :boolean do
arg(:viewer_did, :viewer_did_type, default_value: :viewer_did)

middleware(M.Authorize, :login)
middleware(M.PutCurrentUser)
resolve(dataloader(CMS, :upvotes))
middleware(M.ViewerDidConvert)
end
field(:viewer_has_upvoted, :boolean)

timestamp_fields()
end
Expand Down
10 changes: 10 additions & 0 deletions lib/helper/orm.ex
Original file line number Diff line number Diff line change
Expand Up @@ -262,6 +262,16 @@ defmodule Helper.ORM do
queryable |> count() |> add()
end

@doc """
update meta info for article / comment
"""
def update_meta(queryable, meta) do
queryable
|> Ecto.Changeset.change()
|> Ecto.Changeset.put_embed(:meta, meta)
|> Repo.update()
end

@doc "extract common articles info"
@spec extract_articles(T.paged_data(), [Atom.t()]) :: T.paged_article_common()
def extract_articles(%{entries: entries} = paged_articles, supported_threads) do
Expand Down
Loading