mirror of
https://github.com/discourse/discourse.git
synced 2025-02-25 18:55:32 -06:00
PERF: faster Screened IP Address roll up
This commit is contained in:
parent
fd54c92a52
commit
051d1a3c36
@ -136,44 +136,41 @@ class ScreenedIpAddress < ActiveRecord::Base
|
|||||||
end
|
end
|
||||||
|
|
||||||
def self.roll_up(current_user = Discourse.system_user)
|
def self.roll_up(current_user = Discourse.system_user)
|
||||||
# 1 - retrieve all subnets that needs roll up
|
|
||||||
subnets = [star_subnets, star_star_subnets].flatten
|
subnets = [star_subnets, star_star_subnets].flatten
|
||||||
|
|
||||||
# 2 - log the call
|
|
||||||
StaffActionLogger.new(current_user).log_roll_up(subnets) unless subnets.blank?
|
StaffActionLogger.new(current_user).log_roll_up(subnets) unless subnets.blank?
|
||||||
|
|
||||||
subnets.each do |subnet|
|
subnets.each do |subnet|
|
||||||
# 3 - create subnet if not already exists
|
ScreenedIpAddress.create(ip_address: subnet) unless ScreenedIpAddress.where("? <<= ip_address", subnet).exists?
|
||||||
ScreenedIpAddress.new(ip_address: subnet).save unless ScreenedIpAddress.where(ip_address: subnet).exists?
|
|
||||||
|
|
||||||
# 4 - update stats
|
|
||||||
sql = <<-SQL
|
sql = <<-SQL
|
||||||
UPDATE screened_ip_addresses
|
UPDATE screened_ip_addresses
|
||||||
SET match_count = sum_match_count,
|
SET match_count = sum_match_count
|
||||||
created_at = min_created_at,
|
, created_at = min_created_at
|
||||||
last_match_at = max_last_match_at
|
, last_match_at = max_last_match_at
|
||||||
FROM (
|
FROM (
|
||||||
SELECT SUM(match_count) AS sum_match_count,
|
SELECT SUM(match_count) AS sum_match_count
|
||||||
MIN(created_at) AS min_created_at,
|
, MIN(created_at) AS min_created_at
|
||||||
MAX(last_match_at) AS max_last_match_at
|
, MAX(last_match_at) AS max_last_match_at
|
||||||
FROM screened_ip_addresses
|
FROM screened_ip_addresses
|
||||||
WHERE action_type = #{ScreenedIpAddress.actions[:block]}
|
WHERE action_type = #{ScreenedIpAddress.actions[:block]}
|
||||||
AND family(ip_address) = 4
|
AND family(ip_address) = 4
|
||||||
AND ip_address << :ip_address
|
AND ip_address << :ip_address
|
||||||
) s
|
) s
|
||||||
WHERE ip_address = :ip_address
|
WHERE ip_address = :ip_address
|
||||||
|
AND sum_match_count IS NOT NULL
|
||||||
|
AND min_created_at IS NOT NULL
|
||||||
|
AND max_last_match_at IS NOT NULL
|
||||||
SQL
|
SQL
|
||||||
|
|
||||||
ScreenedIpAddress.exec_sql(sql, ip_address: subnet)
|
ScreenedIpAddress.exec_sql(sql, ip_address: subnet)
|
||||||
|
|
||||||
# 5 - remove old matches
|
|
||||||
ScreenedIpAddress.where(action_type: ScreenedIpAddress.actions[:block])
|
ScreenedIpAddress.where(action_type: ScreenedIpAddress.actions[:block])
|
||||||
.where("family(ip_address) = 4")
|
.where("family(ip_address) = 4")
|
||||||
.where("ip_address << ?", subnet)
|
.where("ip_address << ?", subnet)
|
||||||
.delete_all
|
.delete_all
|
||||||
end
|
end
|
||||||
|
|
||||||
# return the subnets
|
|
||||||
subnets
|
subnets
|
||||||
end
|
end
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user