cre-ne-jp/log-archiver

View on GitHub
lib/log_archiver/extract_keyword.rb

Summary

Maintainability
A
1 hr
Test Coverage
# frozen_string_literal: true
 
module LogArchiver
# 発言からキーワードを抜き出し、登録する処理のクラス
class ExtractKeyword
# 既定のキーワード登録コマンドの接頭辞
# @type [Regexp]
DEFAULT_COMMAND_PREFIX = /\A\.(k|a)[  ]+/.freeze
 
# @return [String, Regexp] キーワード登録コマンドの接頭辞
attr_reader :command_prefix
# @return [Boolean] 処理状況を冗長に出力するか
attr_reader :verbose
 
# キーワード抽出、登録処理を初期化する
# @param [String, Regexp] command_prefix キーワード登録コマンドの接頭辞
# @param [Boolean] verbose 処理状況を冗長に出力するか
def initialize(command_prefix: DEFAULT_COMMAND_PREFIX, verbose: false)
# キーワード登録コマンドの接頭辞
# @type [String, Regexp]
@command_prefix = command_prefix
# 処理状況を冗長に出力するか
# @type [Boolean]
@verbose = verbose
end
 
# キーワード抽出、登録処理を実行する
# @param [Privmsg] privmsg メッセージ
# @return [Hash] キーワードおよびPRIVMSGの保存に成功したか
Method `run` has a Cognitive Complexity of 13 (exceeds 5 allowed). Consider refactoring.
def run(privmsg)
display_title = privmsg.message.sub(@command_prefix, '').strip
title = Keyword.normalize(display_title)
 
# 処理の結果
result = { keyword: false, privmsg: false }
 
Keyword.transaction do
keyword = Keyword.find_or_initialize_by(title: title) do |k|
k.display_title = display_title
end
 
if keyword.new_record?
result[:keyword] = save_keyword(keyword)
raise ActiveRecord::Rollback unless result[:keyword]
end
 
unless privmsg.keyword == keyword
result[:privmsg] = associate_privmsg_with_keyword(
privmsg, keyword
)
raise ActiveRecord::Rollback unless result[:privmsg]
end
end
 
result
end
 
private
 
# キーワードを保存する
# @param [Keyword] keyword 保存対象のキーワード
# @return [Boolean] 保存に成功したか
def save_keyword(keyword)
keyword.save!
try_log("#{keyword.title} => #{keyword.display_title}")
 
return true
rescue => e
try_log("! #{keyword.title}: #{e}")
return false
end
 
# PRIVMSGとキーワードを関連づける
# @param [Privmsg] privmsg 対象のPRIVMSG
# @param [Keyword] keyword 対象のキーワード
# @param [Boolean] :quiet 処理状況を出力するなら false
# @return [Boolean] 保存に成功したか
def associate_privmsg_with_keyword(privmsg, keyword)
privmsg.keyword = keyword
privmsg.save!
 
try_log("PRIVMSG #{privmsg.id} <-> #{keyword.title}")
 
return true
rescue => e
try_log("! PRIVMSG #{privmsg.id} <-> #{keyword.title}: #{e}")
return false
end
 
# ログ出力を試みる
# @param [String] message 出力するメッセージ
# @return [void]
#
# verboseがtrueに指定されていた場合のみログを出力する
def try_log(message)
puts(message) if @verbose
end
end
end