0
0
Fork 0
mirror of https://github.com/discourse/discourse.git synced 2026-08-08 17:53:55 +08:00
discourse/app/serializers/concerns/user_auth_tokens_mixin.rb
Sam 746000edc8
FIX: Enforce can_see_ip checks across admin IP features (#40019)
Same-IP user lookups now identify the target by user_id and
ip_type rather than accepting a raw IP in params, so the IP is
resolved server-side and never round-trips through clients that
lack permission to see it.

Additionally:

- Hide the `suspicious_logins` report (list, bulk, show, CSV
  export and the security dashboard tile) from non-admin staff
  lacking `can_see_ip?`.
- Hide the IP column and CSV export button on the screened
  emails page from staff lacking `can_see_ip?`.
- Omit `ip_address` from `ScreenedUrlSerializer` for staff
  lacking `can_see_ip?`.
- Require `can_see_ip?` (in addition to `can_see_emails?`) to
  export the `screened_email` entity.
- Record the username (not the IP) in the staff-log context
  for "delete other accounts with same IP" when the acting
  user lacks `can_see_ip?`.
2026-05-19 11:37:20 +08:00

58 lines
1.2 KiB
Ruby
Vendored

# frozen_string_literal: true
module UserAuthTokensMixin
extend ActiveSupport::Concern
included { attributes :id, :client_ip, :location, :browser, :device, :os, :icon, :created_at }
def include_client_ip?
can_see_ip_details?
end
def client_ip
object.client_ip.to_s
end
def location
ipinfo = DiscourseIpInfo.get(client_ip, locale: I18n.locale)
ipinfo[:location].presence || I18n.t("staff_action_logs.unknown")
end
def browser
val = BrowserDetection.browser(object.user_agent)
I18n.t("user_auth_tokens.browser.#{val}")
end
def device
val = BrowserDetection.device(object.user_agent)
I18n.t("user_auth_tokens.device.#{val}")
end
def os
val = BrowserDetection.os(object.user_agent)
I18n.t("user_auth_tokens.os.#{val}")
end
def icon
case BrowserDetection.os(object.user_agent)
when :android
"fab-android"
when :chromeos
"fab-chrome"
when :macos, :ios
"fab-apple"
when :linux
"fab-linux"
when :windows
"fab-windows"
else
"question"
end
end
private
def can_see_ip_details?
scope&.can_see_ip? || (scope&.user.present? && scope.user.id == object.user_id)
end
end