From b8126eeea9d8225b899fbd54e6b5be324220b0df Mon Sep 17 00:00:00 2001 From: miteruzo Date: Mon, 22 Jun 2026 07:18:21 +0900 Subject: [PATCH] #378 --- .../controllers/gekanator_posts_controller.rb | 39 ++++++++++++---- .../gekanator_questions_controller.rb | 46 ++++++++++++++++++- backend/app/models/post.rb | 1 + backend/app/services/similarity/calc.rb | 5 +- backend/lib/tasks/calc_post_similarities.rake | 2 +- backend/lib/tasks/calc_tag_similarities.rake | 2 +- 6 files changed, 81 insertions(+), 14 deletions(-) diff --git a/backend/app/controllers/gekanator_posts_controller.rb b/backend/app/controllers/gekanator_posts_controller.rb index e7be9b8..a176354 100644 --- a/backend/app/controllers/gekanator_posts_controller.rb +++ b/backend/app/controllers/gekanator_posts_controller.rb @@ -7,13 +7,24 @@ class GekanatorPostsController < ApplicationController .order(Arel.sql( 'COALESCE(posts.original_created_before - INTERVAL 1 MINUTE, ' \ 'posts.original_created_from, posts.created_at) DESC, posts.id DESC')) + .to_a - render json: { posts: posts.map { |post| post_json(post) } } + active_tags_by_post_id = + posts.each_with_object({ }) do |post, h| + h[post.id] = post.tags.reject(&:deprecated?) + end + + render json: { + posts: posts.map { |post| + post_json(post, + active_tags_by_post_id:) + } + } end private - def post_json post + def post_json post, active_tags_by_post_id: { id: post.id, url: post.url, @@ -22,16 +33,26 @@ class GekanatorPostsController < ApplicationController thumbnail_base: post.thumbnail_base, original_created_from: post.original_created_from, original_created_before: post.original_created_before, - post_similarity_edges: post.post_similarities.map { |similarity| - { - target_post_id: similarity.target_post_id, - cos: similarity.cos.to_f - } - }, - tags: post.tags.map { |tag| tag_json(tag) } + post_similarity_edges: post_similarity_edges_json( + post, + active_tags_by_post_id:), + tags: active_tags_by_post_id.fetch(post.id, []).map { |tag| tag_json(tag) } } end + def post_similarity_edges_json post, active_tags_by_post_id: + post + .post_similarities + .filter_map do |similarity| + next unless active_tags_by_post_id.key?(similarity.target_post_id) + + { + target_post_id: similarity.target_post_id, + cos: similarity.cos.to_f + } + end + end + def tag_json tag { id: tag.id, diff --git a/backend/app/controllers/gekanator_questions_controller.rb b/backend/app/controllers/gekanator_questions_controller.rb index d4843fd..cc08a21 100644 --- a/backend/app/controllers/gekanator_questions_controller.rb +++ b/backend/app/controllers/gekanator_questions_controller.rb @@ -5,9 +5,16 @@ class GekanatorQuestionsController < ApplicationController .accepted .includes(:gekanator_question_examples) .order(priority_weight: :desc, id: :asc) + .to_a + deprecated_tag_keys = deprecated_tag_keys_for(questions) render json: { - questions: questions.map { |question| question_json(question) } + questions: questions.filter_map { |question| + json = question_json(question) + next if hidden_question?(json[:condition], deprecated_tag_keys) + + json + } } end @@ -100,4 +107,41 @@ class GekanatorQuestionsController < ApplicationController .first &.first end + + def deprecated_tag_keys_for questions + tag_keys = questions.filter_map { |question| + condition = condition_json(question.condition) + next unless condition['type'] == 'tag' + + condition['key'].to_s.presence + }.uniq + return {} if tag_keys.empty? + + categories = [] + names = [] + tag_keys.each do |key| + category, name = parse_tag_key(key) + categories << category + names << name + end + + Tag + .joins(:tag_name) + .where(category: categories.uniq) + .where(tag_names: { name: names.uniq }) + .where.not(deprecated_at: nil) + .pluck('tags.category', 'tag_names.name') + .each_with_object({ }) do |(category, name), h| + h["#{ category }:#{ name }"] = true + end + end + + def hidden_question? condition, deprecated_tag_keys + condition[:type] == 'tag' && deprecated_tag_keys[condition[:key].to_s] + end + + def parse_tag_key key + parts = key.to_s.split(':') + [parts.first.to_s, parts.drop(1).join(':')] + end end diff --git a/backend/app/models/post.rb b/backend/app/models/post.rb index 6a27183..8fdbf9a 100644 --- a/backend/app/models/post.rb +++ b/backend/app/models/post.rb @@ -7,6 +7,7 @@ class Post < ApplicationRecord has_many :active_post_tags, -> { kept }, class_name: 'PostTag', inverse_of: :post has_many :post_tags_with_discarded, -> { with_discarded }, class_name: 'PostTag' has_many :tags, through: :active_post_tags + has_many :active_tags, -> { where(deprecated_at: nil) }, through: :active_post_tags, source: :tag has_many :user_post_views, dependent: :delete_all has_many :post_similarities, dependent: :delete_all diff --git a/backend/app/services/similarity/calc.rb b/backend/app/services/similarity/calc.rb index 40d717d..f320375 100644 --- a/backend/app/services/similarity/calc.rb +++ b/backend/app/services/similarity/calc.rb @@ -1,6 +1,6 @@ module Similarity class Calc - def self.call model, tgt + def self.call model, tgt, scope: nil similarity_model = "#{ model.name }Similarity".constantize # 最大保存件数 @@ -8,7 +8,8 @@ module Similarity similarity_model.delete_all - posts = model.includes(tgt).select(:id).to_a + scope ||= model.all + posts = scope.includes(tgt).select(:id).to_a tag_ids = { } tag_cnts = { } diff --git a/backend/lib/tasks/calc_post_similarities.rake b/backend/lib/tasks/calc_post_similarities.rake index 925770f..5f192f9 100644 --- a/backend/lib/tasks/calc_post_similarities.rake +++ b/backend/lib/tasks/calc_post_similarities.rake @@ -1,6 +1,6 @@ namespace :post_similarity do desc '関聯投稿テーブル作成' task calc: :environment do - Similarity::Calc.call(Post, :tags) + Similarity::Calc.call(Post, :active_tags) end end diff --git a/backend/lib/tasks/calc_tag_similarities.rake b/backend/lib/tasks/calc_tag_similarities.rake index 0fc718a..e029255 100644 --- a/backend/lib/tasks/calc_tag_similarities.rake +++ b/backend/lib/tasks/calc_tag_similarities.rake @@ -1,6 +1,6 @@ namespace :tag_similarity do desc '関聯タグ・テーブル作成' task calc: :environment do - Similarity::Calc.call(Tag, :posts) + Similarity::Calc.call(Tag, :posts, scope: Tag.where(deprecated_at: nil)) end end