Skip to content
This repository was archived by the owner on Nov 8, 2022. It is now read-only.

Commit 71c74fa

Browse files
authored
refactor: extract reaction functions (#354)
* refactor: extract collect functions * refactor: rm collect code from ArticleReaction * refactor: extract helper to share upvote && collect logic * refactor: wip * refactor: clean up
1 parent 143d51b commit 71c74fa

File tree

9 files changed

+353
-292
lines changed

9 files changed

+353
-292
lines changed

lib/groupher_server/cms/cms.ex

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,9 @@ defmodule GroupherServer.CMS do
1212
ArticleCURD,
1313
ArticleOperation,
1414
ArticleEmotion,
15-
ArticleReaction,
1615
ArticleComment,
16+
ArticleCollect,
17+
ArticleUpvote,
1718
ArticleCommentAction,
1819
ArticleCommentEmotion,
1920
CommentCURD,
@@ -81,21 +82,20 @@ defmodule GroupherServer.CMS do
8182
defdelegate create_content(community, thread, attrs, user), to: ArticleCURD
8283
defdelegate update_content(content, attrs), to: ArticleCURD
8384

84-
# ArticleReaction
85-
defdelegate upvote_article(thread, article_id, user), to: ArticleReaction
86-
defdelegate undo_upvote_article(thread, article_id, user), to: ArticleReaction
85+
defdelegate upvote_article(thread, article_id, user), to: ArticleUpvote
86+
defdelegate undo_upvote_article(thread, article_id, user), to: ArticleUpvote
8787

88-
defdelegate upvoted_users(thread, article_id, filter), to: ArticleReaction
88+
defdelegate upvoted_users(thread, article_id, filter), to: ArticleUpvote
8989

90-
defdelegate collect_article(thread, article_id, user), to: ArticleReaction
91-
defdelegate collect_article_ifneed(thread, article_id, user), to: ArticleReaction
90+
defdelegate collect_article(thread, article_id, user), to: ArticleCollect
91+
defdelegate collect_article_ifneed(thread, article_id, user), to: ArticleCollect
9292

93-
defdelegate undo_collect_article(thread, article_id, user), to: ArticleReaction
94-
defdelegate undo_collect_article_ifneed(thread, article_id, user), to: ArticleReaction
95-
defdelegate collected_users(thread, article_id, filter), to: ArticleReaction
93+
defdelegate undo_collect_article(thread, article_id, user), to: ArticleCollect
94+
defdelegate undo_collect_article_ifneed(thread, article_id, user), to: ArticleCollect
95+
defdelegate collected_users(thread, article_id, filter), to: ArticleCollect
9696

97-
defdelegate set_collect_folder(collect, folder), to: ArticleReaction
98-
defdelegate undo_set_collect_folder(collect, folder), to: ArticleReaction
97+
defdelegate set_collect_folder(collect, folder), to: ArticleCollect
98+
defdelegate undo_set_collect_folder(collect, folder), to: ArticleCollect
9999

100100
# ArticleOperation
101101
# >> set flag on article, like: pin / unpin article
Lines changed: 143 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,143 @@
1+
defmodule GroupherServer.CMS.Delegate.ArticleCollect do
2+
@moduledoc """
3+
reaction[upvote, collect, watch ...] on article [post, job...]
4+
"""
5+
import GroupherServer.CMS.Helper.Matcher2
6+
import Ecto.Query, warn: false
7+
import Helper.Utils, only: [done: 1]
8+
9+
import GroupherServer.CMS.Delegate.Helper,
10+
only: [
11+
load_reaction_users: 4,
12+
update_article_reactions_count: 4,
13+
update_article_reaction_user_list: 4
14+
]
15+
16+
# import Helper.ErrorCode
17+
alias Helper.{ORM}
18+
alias GroupherServer.{Accounts, CMS, Repo}
19+
20+
alias Accounts.User
21+
alias CMS.ArticleCollect
22+
23+
alias Ecto.Multi
24+
25+
@doc """
26+
get paged collected users
27+
"""
28+
def collected_users(thread, article_id, filter) do
29+
load_reaction_users(ArticleCollect, thread, article_id, filter)
30+
end
31+
32+
@doc """
33+
collect an article
34+
"""
35+
def collect_article(thread, article_id, %User{id: user_id}) do
36+
with {:ok, info} <- match(thread),
37+
{:ok, article} <- ORM.find(info.model, article_id, preload: [author: :user]) do
38+
Multi.new()
39+
|> Multi.run(:inc_author_achieve, fn _, _ ->
40+
Accounts.achieve(article.author.user, :inc, :collect)
41+
end)
42+
|> Multi.run(:inc_article_collects_count, fn _, _ ->
43+
update_article_reactions_count(info, article, :collects_count, :inc)
44+
end)
45+
|> Multi.run(:update_article_reaction_user_list, fn _, _ ->
46+
update_article_reaction_user_list(:collect, article, user_id, :add)
47+
end)
48+
|> Multi.run(:create_collect, fn _, _ ->
49+
thread_upcase = thread |> to_string |> String.upcase()
50+
args = Map.put(%{user_id: user_id, thread: thread_upcase}, info.foreign_key, article.id)
51+
52+
ORM.create(ArticleCollect, args)
53+
end)
54+
|> Repo.transaction()
55+
|> result()
56+
end
57+
end
58+
59+
# 用于在收藏时,用户添加文章到不同的收藏夹中的情况
60+
# 如果是同一篇文章,只创建一次,collect_article 不创建记录,只是后续设置不同的收藏夹即可
61+
# 如果是第一次收藏,那么才创建文章收藏记录
62+
# 避免因为同一篇文章在不同收藏夹内造成的统计和用户成就系统的混乱
63+
def collect_article_ifneed(thread, article_id, %User{id: user_id} = user) do
64+
with findby_args <- collection_findby_args(thread, article_id, user_id) do
65+
already_collected = ORM.find_by(ArticleCollect, findby_args)
66+
67+
case already_collected do
68+
{:ok, article_collect} -> {:ok, article_collect}
69+
{:error, _} -> collect_article(thread, article_id, user)
70+
end
71+
end
72+
end
73+
74+
def undo_collect_article(thread, article_id, %User{id: user_id}) do
75+
with {:ok, info} <- match(thread),
76+
{:ok, article} <- ORM.find(info.model, article_id, preload: [author: :user]) do
77+
Multi.new()
78+
|> Multi.run(:dec_author_achieve, fn _, _ ->
79+
Accounts.achieve(article.author.user, :dec, :collect)
80+
end)
81+
|> Multi.run(:inc_article_collects_count, fn _, _ ->
82+
update_article_reactions_count(info, article, :collects_count, :dec)
83+
end)
84+
|> Multi.run(:update_article_reaction_user_list, fn _, _ ->
85+
update_article_reaction_user_list(:collect, article, user_id, :remove)
86+
end)
87+
|> Multi.run(:undo_collect, fn _, _ ->
88+
args = Map.put(%{user_id: user_id}, info.foreign_key, article.id)
89+
90+
ORM.findby_delete(ArticleCollect, args)
91+
end)
92+
|> Repo.transaction()
93+
|> result()
94+
end
95+
end
96+
97+
def undo_collect_article_ifneed(thread, article_id, %User{id: user_id} = user) do
98+
with findby_args <- collection_findby_args(thread, article_id, user_id),
99+
{:ok, article_collect} = ORM.find_by(ArticleCollect, findby_args) do
100+
case article_collect.collect_folders |> length <= 1 do
101+
true -> undo_collect_article(thread, article_id, user)
102+
false -> {:ok, article_collect}
103+
end
104+
end
105+
end
106+
107+
def set_collect_folder(%ArticleCollect{} = collect, folder) do
108+
collect_folders = (collect.collect_folders ++ [folder]) |> Enum.uniq()
109+
110+
collect
111+
|> Ecto.Changeset.change()
112+
|> Ecto.Changeset.put_embed(:collect_folders, collect_folders)
113+
|> Repo.update()
114+
end
115+
116+
def undo_set_collect_folder(%ArticleCollect{} = collect, folder) do
117+
collect_folders = Enum.reject(collect.collect_folders, &(&1.id == folder.id))
118+
119+
case collect_folders do
120+
# means collect already delete
121+
[] ->
122+
{:ok, :pass}
123+
124+
_ ->
125+
collect
126+
|> Ecto.Changeset.change()
127+
|> Ecto.Changeset.put_embed(:collect_folders, collect_folders)
128+
|> Repo.update()
129+
end
130+
end
131+
132+
defp collection_findby_args(thread, article_id, user_id) do
133+
with {:ok, info} <- match(thread) do
134+
thread_upcase = thread |> to_string |> String.upcase()
135+
%{thread: thread_upcase, user_id: user_id} |> Map.put(info.foreign_key, article_id)
136+
end
137+
end
138+
139+
#############
140+
defp result({:ok, %{create_collect: result}}), do: result |> done()
141+
defp result({:ok, %{undo_collect: result}}), do: result |> done()
142+
defp result({:error, _, result, _steps}), do: {:error, result}
143+
end

lib/groupher_server/cms/delegates/article_comment_action.ex

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleCommentAction do
6363
)
6464
end)
6565
|> Repo.transaction()
66-
|> upsert_comment_result()
66+
|> result()
6767
end
6868
end
6969

@@ -77,7 +77,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleCommentAction do
7777
ORM.findby_delete(ArticlePinedComment, %{article_comment_id: comment.id})
7878
end)
7979
|> Repo.transaction()
80-
|> upsert_comment_result()
80+
|> result()
8181
end
8282
end
8383

@@ -141,7 +141,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleCommentAction do
141141
|> Repo.update()
142142
end)
143143
|> Repo.transaction()
144-
|> upsert_comment_result()
144+
|> result()
145145
end
146146
end
147147

@@ -166,7 +166,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleCommentAction do
166166
update_article_author_upvoted_info(comment, user_id)
167167
end)
168168
|> Repo.transaction()
169-
|> upsert_comment_result()
169+
|> result()
170170
end
171171
end
172172

@@ -194,7 +194,7 @@ defmodule GroupherServer.CMS.Delegate.ArticleCommentAction do
194194
update_article_author_upvoted_info(updated_comment, user_id)
195195
end)
196196
|> Repo.transaction()
197-
|> upsert_comment_result()
197+
|> result()
198198
end
199199
end
200200

@@ -324,24 +324,24 @@ defmodule GroupherServer.CMS.Delegate.ArticleCommentAction do
324324
ORM.update_meta(comment, meta)
325325
end
326326

327-
defp upsert_comment_result({:ok, %{create_article_comment: result}}), do: {:ok, result}
328-
defp upsert_comment_result({:ok, %{add_reply_to: result}}), do: {:ok, result}
329-
defp upsert_comment_result({:ok, %{check_article_author_upvoted: result}}), do: {:ok, result}
330-
defp upsert_comment_result({:ok, %{fold_comment_report_too_many: result}}), do: {:ok, result}
331-
defp upsert_comment_result({:ok, %{update_comment_flag: result}}), do: {:ok, result}
332-
defp upsert_comment_result({:ok, %{delete_article_comment: result}}), do: {:ok, result}
327+
defp result({:ok, %{create_article_comment: result}}), do: {:ok, result}
328+
defp result({:ok, %{add_reply_to: result}}), do: {:ok, result}
329+
defp result({:ok, %{check_article_author_upvoted: result}}), do: {:ok, result}
330+
defp result({:ok, %{fold_comment_report_too_many: result}}), do: {:ok, result}
331+
defp result({:ok, %{update_comment_flag: result}}), do: {:ok, result}
332+
defp result({:ok, %{delete_article_comment: result}}), do: {:ok, result}
333333

334-
defp upsert_comment_result({:error, :create_article_comment, result, _steps}) do
334+
defp result({:error, :create_article_comment, result, _steps}) do
335335
raise_error(:create_comment, result)
336336
end
337337

338-
defp upsert_comment_result({:error, :add_participator, result, _steps}) do
338+
defp result({:error, :add_participator, result, _steps}) do
339339
{:error, result}
340340
end
341341

342-
defp upsert_comment_result({:error, :create_abuse_report, result, _steps}) do
342+
defp result({:error, :create_abuse_report, result, _steps}) do
343343
{:error, result}
344344
end
345345

346-
defp upsert_comment_result({:error, _, result, _steps}), do: {:error, result}
346+
defp result({:error, _, result, _steps}), do: {:error, result}
347347
end

0 commit comments

Comments
 (0)