mirror of
https://github.com/internetee/registry.git
synced 2025-05-28 16:39:55 +02:00
Merge remote-tracking branch 'origin/master' into 113524121-legal_doc_min_size
# Conflicts: # public/assets/.sprockets-manifest-48c2dd3ff16b86b70040480e74a50543.json # public/assets/registrant-manifest.js # public/assets/registrar-manifest.css # public/assets/registrar-manifest.js # public/assets/registrar/application.js
This commit is contained in:
commit
0a5428f2ee
259 changed files with 2592 additions and 426072 deletions
|
@ -16,7 +16,7 @@ class Ability
|
|||
@user.roles.each { |role| send(role) } if @user.roles
|
||||
when 'ApiUser'
|
||||
@user.roles.each { |role| send(role) } if @user.roles
|
||||
when 'RegistrantUser'
|
||||
when 'RegistrantUser'
|
||||
static_registrant
|
||||
end
|
||||
|
||||
|
@ -117,9 +117,11 @@ class Ability
|
|||
end
|
||||
|
||||
def static_registrant
|
||||
customer_service
|
||||
can :manage, :registrant_domains
|
||||
can :manage, :registrant_whois
|
||||
can :manage, Depp::Domain
|
||||
can :manage, Domain
|
||||
end
|
||||
|
||||
def user
|
||||
|
|
|
@ -1,8 +1,9 @@
|
|||
class BlockedDomain < ActiveRecord::Base
|
||||
include Versions
|
||||
before_save :generate_data
|
||||
before_destroy :remove_data
|
||||
validates :name, domain_name: true, uniqueness: true
|
||||
before_save :generate_data
|
||||
after_destroy :remove_data
|
||||
|
||||
validates :name, domain_name: true, uniqueness: true
|
||||
|
||||
|
||||
class << self
|
||||
|
@ -22,19 +23,14 @@ validates :name, domain_name: true, uniqueness: true
|
|||
def generate_data
|
||||
return if Domain.where(name: name).any?
|
||||
|
||||
@json = generate_json
|
||||
@body = generate_body
|
||||
update_whois_server
|
||||
wr = Whois::Record.find_or_initialize_by(name: name)
|
||||
wr.json = @json = generate_json # we need @json to bind to class
|
||||
wr.body = generate_body
|
||||
wr.save
|
||||
end
|
||||
|
||||
alias_method :update_whois_record, :generate_data
|
||||
|
||||
def update_whois_server
|
||||
wr = Whois::Record.find_or_initialize_by(name: name)
|
||||
wr.body = @body
|
||||
wr.json = @json
|
||||
wr.save
|
||||
end
|
||||
|
||||
def generate_body
|
||||
template = Rails.root.join("app/views/for_models/whois_other.erb".freeze)
|
||||
|
@ -49,8 +45,6 @@ validates :name, domain_name: true, uniqueness: true
|
|||
end
|
||||
|
||||
def remove_data
|
||||
return if Domain.where(name: name).any?
|
||||
|
||||
Whois::Record.where(name: name).delete_all
|
||||
UpdateWhoisRecordJob.enqueue name, 'blocked'
|
||||
end
|
||||
end
|
||||
|
|
74
app/models/business_registry_cache.rb
Normal file
74
app/models/business_registry_cache.rb
Normal file
|
@ -0,0 +1,74 @@
|
|||
|
||||
=begin
|
||||
The portal for registrants has to offer an overview of the domains the user is related to directly or through an organisation.
|
||||
Personal relation is defined by matching the personal identification code associated with a domain and the one acquired on
|
||||
authentication using electronic ID. Association through a business organisation requires a query to business registry.
|
||||
|
||||
* when user logs in the personal identification code is sent to business registry (using XML service)
|
||||
* business registry returns the list of business registry codes the user is a board member of
|
||||
* the list is cached for two days (configurable)
|
||||
* during that time no new queries are made to business registry for that personal identification code
|
||||
and the cached organisation code listing is used
|
||||
* user sees the listing of domains that are associated with him/her directly or through registered organisation
|
||||
* UI of the portal displays the list of organisation codes and names used to fetch additional domains for the user
|
||||
(currently by clicking on a username in top right corner of the screen).
|
||||
Also time and date of the query to the business registry is displayed with the list of organisations.
|
||||
* if the query to the business registry fails for any reason the list of
|
||||
domains associated directly with the user is still displayed with an error message indicating a problem
|
||||
with receiving current list business entities. Outdated list of organisations cannot be used.
|
||||
=end
|
||||
|
||||
class BusinessRegistryCache < ActiveRecord::Base
|
||||
|
||||
# 1. load domains by business
|
||||
# 2. load domains by person
|
||||
def associated_domains
|
||||
domains = []
|
||||
|
||||
contact_ids = Contact.where(ident_type: 'org', ident: associated_businesses, ident_country_code: 'EE').pluck(:id)
|
||||
contact_ids += Contact.where(ident_type: 'priv', ident: ident, ident_country_code: ident_country_code).pluck(:id)
|
||||
|
||||
unless contact_ids.blank?
|
||||
domains = DomainContact.distinct.where(contact_id: contact_ids).pluck(:domain_id)
|
||||
end
|
||||
|
||||
Domain.includes(:registrar, :registrant).where(id: domains)
|
||||
end
|
||||
|
||||
class << self
|
||||
def fetch_associated_domains(ident_code, ident_cc)
|
||||
fetch_by_ident_and_cc(ident_code, ident_cc).associated_domains
|
||||
end
|
||||
|
||||
def fetch_by_ident_and_cc(ident_code, ident_cc)
|
||||
cache = BusinessRegistryCache.where(ident: ident_code, ident_country_code: ident_cc).first_or_initialize
|
||||
msg_start = "[Ariregister] #{ident_cc}-#{ident_code}:"
|
||||
|
||||
# fetch new data if cache is expired
|
||||
if cache.retrieved_on && cache.retrieved_on > (Time.zone.now - Setting.days_to_keep_business_registry_cache.days)
|
||||
Rails.logger.info("#{msg_start} Info loaded from cache")
|
||||
return cache
|
||||
end
|
||||
|
||||
cache.attributes = business_registry.associated_businesses(ident_code, ident_cc)
|
||||
Rails.logger.info("#{msg_start} Info loaded from server")
|
||||
|
||||
cache.save
|
||||
cache
|
||||
end
|
||||
|
||||
def business_registry
|
||||
Soap::Arireg.new
|
||||
end
|
||||
|
||||
def purge
|
||||
STDOUT << "#{Time.zone.now.utc} - Starting Purge of old BusinessRegistry data from cache\n" unless Rails.env.test?
|
||||
purged = 0
|
||||
BusinessRegistryCache.where('retrieved_on < ?',
|
||||
Time.zone.now < Setting.days_to_keep_business_registry_cache.days).each do |br|
|
||||
br.destroy and purged += 1
|
||||
end
|
||||
STDOUT << "#{Time.zone.now.utc} - Finished purging #{purged} old BusinessRegistry cache items\n" unless Rails.env.test?
|
||||
end
|
||||
end
|
||||
end
|
|
@ -499,7 +499,8 @@ class Contact < ActiveRecord::Base
|
|||
end
|
||||
|
||||
def update_related_whois_records
|
||||
related_domain_descriptions.each{ |x, y| WhoisRecord.find_by(name: x).try(:save) }
|
||||
names = related_domain_descriptions.keys
|
||||
UpdateWhoisRecordJob.enqueue(names, :domain) if names.present?
|
||||
end
|
||||
|
||||
end
|
||||
|
|
|
@ -2,14 +2,23 @@ class Directo < ActiveRecord::Base
|
|||
belongs_to :item, polymorphic: true
|
||||
|
||||
def self.send_receipts
|
||||
new_trans = Invoice.where(invoice_type: "DEB", in_directo: false).where.not(cancelled_at: nil)
|
||||
new_trans = Invoice.where(invoice_type: "DEB", in_directo: false).where(cancelled_at: nil)
|
||||
total = new_trans.count
|
||||
counter = 0
|
||||
Rails.logger.info("[DIRECTO] Will try to send #{total} invoices")
|
||||
|
||||
new_trans.find_in_batches(batch_size: 10).each do |group|
|
||||
mappers = {} # need them as no direct connection between invoice
|
||||
builder = Nokogiri::XML::Builder.new(encoding: "UTF-8") do |xml|
|
||||
xml.invoices {
|
||||
group.each do |invoice|
|
||||
next if invoice.account_activity.nil? || invoice.account_activity.bank_transaction.nil?
|
||||
# next if invoice.account_activity.bank_transaction.sum.nil? || invoice.account_activity.bank_transaction.sum != invoice.sum_cache
|
||||
|
||||
if invoice.account_activity.nil? || invoice.account_activity.bank_transaction.nil? ||
|
||||
invoice.account_activity.bank_transaction.sum.nil? || invoice.account_activity.bank_transaction.sum != invoice.sum_cache
|
||||
Rails.logger.info("[DIRECTO] Invoice #{invoice.number} has been skipped")
|
||||
next
|
||||
end
|
||||
counter += 1
|
||||
|
||||
num = invoice.number
|
||||
mappers[num] = invoice
|
||||
|
@ -36,6 +45,8 @@ class Directo < ActiveRecord::Base
|
|||
response = RestClient::Request.execute(url: ENV['directo_invoice_url'], method: :post, payload: {put: "1", what: "invoice", xmldata: data}, verify_ssl: false).to_s
|
||||
dump_result_to_db(mappers, response)
|
||||
end
|
||||
|
||||
STDOUT << "#{Time.zone.now.utc} - Directo receipts sending finished. #{counter} of #{total} are sent\n"
|
||||
end
|
||||
|
||||
def self.dump_result_to_db mappers, xml
|
||||
|
|
|
@ -43,7 +43,7 @@ class Domain < ActiveRecord::Base
|
|||
has_many :dnskeys, dependent: :destroy
|
||||
|
||||
has_many :keyrelays
|
||||
has_one :whois_record, dependent: :destroy
|
||||
has_one :whois_record # destroyment will be done in after_commit
|
||||
|
||||
accepts_nested_attributes_for :dnskeys, allow_destroy: true
|
||||
|
||||
|
@ -87,14 +87,11 @@ class Domain < ActiveRecord::Base
|
|||
true
|
||||
end
|
||||
|
||||
after_save :update_whois_record
|
||||
after_commit :update_whois_record
|
||||
|
||||
after_create :update_reserved_domains
|
||||
def update_reserved_domains
|
||||
return unless in_reserved_list?
|
||||
rd = ReservedDomain.by_domain(name).first
|
||||
rd.password = SecureRandom.hex
|
||||
rd.save
|
||||
ReservedDomain.new_password_for(name) if in_reserved_list?
|
||||
end
|
||||
|
||||
validates :name_dirty, domain_name: true, uniqueness: true
|
||||
|
@ -203,6 +200,31 @@ class Domain < ActiveRecord::Base
|
|||
statuses.include? DomainStatus::SERVER_TECH_CHANGE_PROHIBITED
|
||||
end
|
||||
|
||||
def self.clean_expired_pendings
|
||||
ActiveSupport::Deprecation.instance.deprecation_warning(DomainCron, __method__)
|
||||
DomainCron.send(__method__)
|
||||
end
|
||||
|
||||
def self.start_expire_period
|
||||
ActiveSupport::Deprecation.instance.deprecation_warning(DomainCron, __method__)
|
||||
DomainCron.send(__method__)
|
||||
end
|
||||
|
||||
def self.start_redemption_grace_period
|
||||
ActiveSupport::Deprecation.instance.deprecation_warning(DomainCron, __method__)
|
||||
DomainCron.send(__method__)
|
||||
end
|
||||
|
||||
def self.start_delete_period
|
||||
ActiveSupport::Deprecation.instance.deprecation_warning(DomainCron, __method__)
|
||||
DomainCron.send(__method__)
|
||||
end
|
||||
|
||||
def self.destroy_delete_candidates
|
||||
ActiveSupport::Deprecation.instance.deprecation_warning(DomainCron, __method__)
|
||||
DomainCron.send(__method__)
|
||||
end
|
||||
|
||||
class << self
|
||||
def convert_period_to_time(period, unit)
|
||||
return (period.to_i / 365).years if unit == 'd'
|
||||
|
@ -220,122 +242,6 @@ class Domain < ActiveRecord::Base
|
|||
{ admin_contacts: :registrar }
|
||||
)
|
||||
end
|
||||
|
||||
# rubocop: disable Metrics/AbcSize
|
||||
# rubocop: disable Metrics/CyclomaticComplexity
|
||||
# rubocop: disable Metrics/PerceivedComplexity
|
||||
def clean_expired_pendings
|
||||
STDOUT << "#{Time.zone.now.utc} - Clean expired domain pendings\n" unless Rails.env.test?
|
||||
|
||||
expire_at = Setting.expire_pending_confirmation.hours.ago
|
||||
count = 0
|
||||
expired_pending_domains = Domain.where('registrant_verification_asked_at <= ?', expire_at)
|
||||
expired_pending_domains.each do |domain|
|
||||
unless domain.pending_update? || domain.pending_delete? || domain.pending_delete_confirmation?
|
||||
msg = "#{Time.zone.now.utc} - ISSUE: DOMAIN #{domain.id}: #{domain.name} IS IN EXPIRED PENDING LIST, " \
|
||||
"but no pendingDelete/pendingUpdate state present!\n"
|
||||
STDOUT << msg unless Rails.env.test?
|
||||
next
|
||||
end
|
||||
count += 1
|
||||
if domain.pending_update?
|
||||
domain.send_mail :pending_update_expired_notification_for_new_registrant
|
||||
end
|
||||
if domain.pending_delete? || domain.pending_delete_confirmation?
|
||||
DomainMailer.pending_delete_expired_notification(domain.id, true).deliver
|
||||
end
|
||||
domain.clean_pendings_lowlevel
|
||||
unless Rails.env.test?
|
||||
STDOUT << "#{Time.zone.now.utc} Domain.clean_expired_pendings: ##{domain.id} (#{domain.name})\n"
|
||||
end
|
||||
end
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully cancelled #{count} domain pendings\n" unless Rails.env.test?
|
||||
count
|
||||
end
|
||||
# rubocop: enable Metrics/PerceivedComplexity
|
||||
# rubocop: enable Metrics/AbcSize
|
||||
# rubocop: enable Metrics/CyclomaticComplexity
|
||||
|
||||
# rubocop: disable Metrics/LineLength
|
||||
def start_expire_period
|
||||
STDOUT << "#{Time.zone.now.utc} - Expiring domains\n" unless Rails.env.test?
|
||||
|
||||
domains = Domain.where('valid_to <= ?', Time.zone.now)
|
||||
domains.each do |domain|
|
||||
next unless domain.expirable?
|
||||
domain.set_graceful_expired
|
||||
DomainMailer.expiration_reminder(domain.id).deliver_in(Setting.expiration_reminder_mail.to_i.days)
|
||||
STDOUT << "#{Time.zone.now.utc} Domain.start_expire_period: ##{domain.id} (#{domain.name}) #{domain.changes}\n" unless Rails.env.test?
|
||||
domain.save(validate: false)
|
||||
end
|
||||
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully expired #{domains.count} domains\n" unless Rails.env.test?
|
||||
end
|
||||
|
||||
def start_redemption_grace_period
|
||||
STDOUT << "#{Time.zone.now.utc} - Setting server_hold to domains\n" unless Rails.env.test?
|
||||
|
||||
d = Domain.where('outzone_at <= ?', Time.zone.now)
|
||||
d.each do |domain|
|
||||
next unless domain.server_holdable?
|
||||
domain.statuses << DomainStatus::SERVER_HOLD
|
||||
STDOUT << "#{Time.zone.now.utc} Domain.start_redemption_grace_period: ##{domain.id} (#{domain.name}) #{domain.changes}\n" unless Rails.env.test?
|
||||
domain.save(validate: false)
|
||||
end
|
||||
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully set server_hold to #{d.count} domains\n" unless Rails.env.test?
|
||||
end
|
||||
|
||||
def start_delete_period
|
||||
STDOUT << "#{Time.zone.now.utc} - Setting delete_candidate to domains\n" unless Rails.env.test?
|
||||
|
||||
d = Domain.where('delete_at <= ?', Time.zone.now)
|
||||
d.each do |domain|
|
||||
next unless domain.delete_candidateable?
|
||||
domain.statuses << DomainStatus::DELETE_CANDIDATE
|
||||
STDOUT << "#{Time.zone.now.utc} Domain.start_delete_period: ##{domain.id} (#{domain.name}) #{domain.changes}\n" unless Rails.env.test?
|
||||
domain.save(validate: false)
|
||||
end
|
||||
|
||||
return if Rails.env.test?
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully set delete_candidate to #{d.count} domains\n"
|
||||
end
|
||||
|
||||
# rubocop:disable Rails/FindEach
|
||||
# rubocop:disable Metrics/AbcSize
|
||||
def destroy_delete_candidates
|
||||
STDOUT << "#{Time.zone.now.utc} - Destroying domains\n" unless Rails.env.test?
|
||||
|
||||
c = 0
|
||||
Domain.where("statuses @> '{deleteCandidate}'::varchar[]").each do |x|
|
||||
WhoisRecord.where(domain_id: x.id).destroy_all
|
||||
destroy_with_message x
|
||||
STDOUT << "#{Time.zone.now.utc} Domain.destroy_delete_candidates: by deleteCandidate ##{x.id} (#{x.name})\n" unless Rails.env.test?
|
||||
|
||||
c += 1
|
||||
end
|
||||
|
||||
Domain.where('force_delete_at <= ?', Time.zone.now).each do |x|
|
||||
WhoisRecord.where(domain_id: x.id).destroy_all
|
||||
destroy_with_message x
|
||||
STDOUT << "#{Time.zone.now.utc} Domain.destroy_delete_candidates: by force delete time ##{x.id} (#{x.name})\n" unless Rails.env.test?
|
||||
c += 1
|
||||
end
|
||||
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully destroyed #{c} domains\n" unless Rails.env.test?
|
||||
end
|
||||
# rubocop: enable Metrics/AbcSize
|
||||
# rubocop:enable Rails/FindEach
|
||||
# rubocop: enable Metrics/LineLength
|
||||
def destroy_with_message(domain)
|
||||
domain.destroy
|
||||
bye_bye = domain.versions.last
|
||||
domain.registrar.messages.create!(
|
||||
body: "#{I18n.t(:domain_deleted)}: #{domain.name}",
|
||||
attached_obj_id: bye_bye.id,
|
||||
attached_obj_type: bye_bye.class.to_s # DomainVersion
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
def name=(value)
|
||||
|
@ -370,7 +276,7 @@ class Domain < ActiveRecord::Base
|
|||
end
|
||||
|
||||
def in_reserved_list?
|
||||
ReservedDomain.pw_for(name).present?
|
||||
@in_reserved_list ||= ReservedDomain.by_domain(name).any?
|
||||
end
|
||||
|
||||
def pending_transfer
|
||||
|
@ -592,7 +498,7 @@ class Domain < ActiveRecord::Base
|
|||
|
||||
def name_in_wire_format
|
||||
res = ''
|
||||
parts = name.split('.')
|
||||
parts = name_puny.split('.')
|
||||
parts.each do |x|
|
||||
res += format('%02X', x.length) # length of label in hex
|
||||
res += x.each_byte.map { |b| format('%02X', b) }.join # label
|
||||
|
@ -728,8 +634,12 @@ class Domain < ActiveRecord::Base
|
|||
case s
|
||||
when DomainStatus::PENDING_DELETE
|
||||
self.delete_at = nil
|
||||
# Handle any other special remove cases?
|
||||
# when DomainStatus::FORCE_DELETE unset_force_delete
|
||||
when DomainStatus::SERVER_MANUAL_INZONE # removal causes server hold to set
|
||||
self.outzone_at = Time.zone.now if self.force_delete_at.present?
|
||||
when DomainStatus::DomainStatus::EXPIRED # removal causes server hold to set
|
||||
self.outzone_at = self.valid_to + 15.day
|
||||
when DomainStatus::DomainStatus::SERVER_HOLD # removal causes server hold to set
|
||||
self.outzone_at = nil
|
||||
end
|
||||
end
|
||||
end
|
||||
|
@ -826,7 +736,7 @@ class Domain < ActiveRecord::Base
|
|||
end
|
||||
|
||||
def update_whois_record
|
||||
whois_record.blank? ? create_whois_record : whois_record.save
|
||||
UpdateWhoisRecordJob.enqueue name, 'domain'
|
||||
end
|
||||
|
||||
def status_notes_array=(notes)
|
||||
|
@ -841,5 +751,19 @@ class Domain < ActiveRecord::Base
|
|||
DomainMailer.send(action, DomainMailModel.new(self).send(action)).deliver
|
||||
end
|
||||
|
||||
|
||||
def self.to_csv
|
||||
CSV.generate do |csv|
|
||||
csv << column_names
|
||||
all.each do |domain|
|
||||
csv << domain.attributes.values_at(*column_names)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def self.pdf(html)
|
||||
kit = PDFKit.new(html)
|
||||
kit.to_pdf
|
||||
end
|
||||
end
|
||||
# rubocop: enable Metrics/ClassLength
|
||||
|
|
123
app/models/domain_cron.rb
Normal file
123
app/models/domain_cron.rb
Normal file
|
@ -0,0 +1,123 @@
|
|||
class DomainCron
|
||||
|
||||
def self.clean_expired_pendings
|
||||
STDOUT << "#{Time.zone.now.utc} - Clean expired domain pendings\n" unless Rails.env.test?
|
||||
|
||||
expire_at = Setting.expire_pending_confirmation.hours.ago
|
||||
count = 0
|
||||
expired_pending_domains = Domain.where('registrant_verification_asked_at <= ?', expire_at)
|
||||
expired_pending_domains.each do |domain|
|
||||
unless domain.pending_update? || domain.pending_delete? || domain.pending_delete_confirmation?
|
||||
msg = "#{Time.zone.now.utc} - ISSUE: DOMAIN #{domain.id}: #{domain.name} IS IN EXPIRED PENDING LIST, " \
|
||||
"but no pendingDelete/pendingUpdate state present!\n"
|
||||
STDOUT << msg unless Rails.env.test?
|
||||
next
|
||||
end
|
||||
count += 1
|
||||
if domain.pending_update?
|
||||
DomainMailer.pending_update_expired_notification_for_new_registrant(domain.id).deliver
|
||||
end
|
||||
if domain.pending_delete? || domain.pending_delete_confirmation?
|
||||
DomainMailer.pending_delete_expired_notification(domain.id, true).deliver
|
||||
end
|
||||
domain.clean_pendings_lowlevel
|
||||
unless Rails.env.test?
|
||||
STDOUT << "#{Time.zone.now.utc} DomainCron.clean_expired_pendings: ##{domain.id} (#{domain.name})\n"
|
||||
end
|
||||
UpdateWhoisRecordJob.enqueue domain.name, 'domain'
|
||||
end
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully cancelled #{count} domain pendings\n" unless Rails.env.test?
|
||||
count
|
||||
end
|
||||
|
||||
def self.start_expire_period
|
||||
STDOUT << "#{Time.zone.now.utc} - Expiring domains\n" unless Rails.env.test?
|
||||
|
||||
domains = Domain.where('valid_to <= ?', Time.zone.now)
|
||||
marked = 0
|
||||
real = 0
|
||||
domains.each do |domain|
|
||||
next unless domain.expirable?
|
||||
real += 1
|
||||
domain.set_graceful_expired
|
||||
STDOUT << "#{Time.zone.now.utc} DomainCron.start_expire_period: ##{domain.id} (#{domain.name}) #{domain.changes}\n" unless Rails.env.test?
|
||||
domain.save(validate: false) and marked += 1
|
||||
end
|
||||
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully expired #{marked} of #{real} domains\n" unless Rails.env.test?
|
||||
end
|
||||
|
||||
def self.start_redemption_grace_period
|
||||
STDOUT << "#{Time.zone.now.utc} - Setting server_hold to domains\n" unless Rails.env.test?
|
||||
|
||||
d = Domain.where('outzone_at <= ?', Time.zone.now)
|
||||
marked = 0
|
||||
real = 0
|
||||
d.each do |domain|
|
||||
next unless domain.server_holdable?
|
||||
real += 1
|
||||
domain.statuses << DomainStatus::SERVER_HOLD
|
||||
STDOUT << "#{Time.zone.now.utc} DomainCron.start_redemption_grace_period: ##{domain.id} (#{domain.name}) #{domain.changes}\n" unless Rails.env.test?
|
||||
domain.save(validate: false) and marked += 1
|
||||
end
|
||||
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully set server_hold to #{marked} of #{real} domains\n" unless Rails.env.test?
|
||||
marked
|
||||
end
|
||||
|
||||
def self.start_delete_period
|
||||
begin
|
||||
STDOUT << "#{Time.zone.now.utc} - Setting delete_candidate to domains\n" unless Rails.env.test?
|
||||
|
||||
d = Domain.where('delete_at <= ?', Time.zone.now)
|
||||
marked = 0
|
||||
real = 0
|
||||
d.each do |domain|
|
||||
next unless domain.delete_candidateable?
|
||||
real += 1
|
||||
domain.statuses << DomainStatus::DELETE_CANDIDATE
|
||||
STDOUT << "#{Time.zone.now.utc} DomainCron.start_delete_period: ##{domain.id} (#{domain.name}) #{domain.changes}\n" unless Rails.env.test?
|
||||
domain.save(validate: false) and marked += 1
|
||||
end
|
||||
ensure # the operator should see what was accomplished
|
||||
STDOUT << "#{Time.zone.now.utc} - Finished setting delete_candidate - #{marked} out of #{real} successfully set\n" unless Rails.env.test?
|
||||
end
|
||||
marked
|
||||
end
|
||||
|
||||
def self.destroy_delete_candidates
|
||||
STDOUT << "#{Time.zone.now.utc} - Destroying domains\n" unless Rails.env.test?
|
||||
|
||||
c = 0
|
||||
Domain.where("statuses @> '{deleteCandidate}'::varchar[]").each do |x|
|
||||
WhoisRecord.where(domain_id: x.id).destroy_all
|
||||
destroy_with_message x
|
||||
STDOUT << "#{Time.zone.now.utc} Domain.destroy_delete_candidates: by deleteCandidate ##{x.id} (#{x.name})\n" unless Rails.env.test?
|
||||
|
||||
c += 1
|
||||
end
|
||||
|
||||
Domain.where('force_delete_at <= ?', Time.zone.now).each do |x|
|
||||
WhoisRecord.where(domain_id: x.id).destroy_all
|
||||
destroy_with_message x
|
||||
STDOUT << "#{Time.zone.now.utc} DomainCron.destroy_delete_candidates: by force delete time ##{x.id} (#{x.name})\n" unless Rails.env.test?
|
||||
c += 1
|
||||
end
|
||||
|
||||
STDOUT << "#{Time.zone.now.utc} - Successfully destroyed #{c} domains\n" unless Rails.env.test?
|
||||
end
|
||||
|
||||
# rubocop: enable Metrics/AbcSize
|
||||
# rubocop:enable Rails/FindEach
|
||||
# rubocop: enable Metrics/LineLength
|
||||
def self.destroy_with_message(domain)
|
||||
domain.destroy
|
||||
bye_bye = domain.versions.last
|
||||
domain.registrar.messages.create!(
|
||||
body: "#{I18n.t(:domain_deleted)}: #{domain.name}",
|
||||
attached_obj_id: bye_bye.id,
|
||||
attached_obj_type: bye_bye.class.to_s # DomainVersion
|
||||
)
|
||||
end
|
||||
|
||||
end
|
|
@ -175,6 +175,8 @@ class Epp::Contact < Contact
|
|||
else
|
||||
throw :epp_error, {code: '2306', msg: I18n.t(:ident_update_error)}
|
||||
end
|
||||
else
|
||||
throw :epp_error, {code: '2306', msg: I18n.t(:ident_update_error)}
|
||||
end
|
||||
end
|
||||
|
||||
|
|
|
@ -489,6 +489,15 @@ class Epp::Domain < Domain
|
|||
|
||||
# at[:statuses] += at_add[:domain_statuses_attributes]
|
||||
|
||||
if registrant_id && registrant.code == frame.css('registrant')
|
||||
|
||||
throw :epp_error, {
|
||||
code: '2305',
|
||||
msg: I18n.t(:contact_already_associated_with_the_domain)
|
||||
}
|
||||
|
||||
end
|
||||
|
||||
if errors.empty? && verify &&
|
||||
Setting.request_confrimation_on_registrant_change_enabled &&
|
||||
frame.css('registrant').present? &&
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
class RegistrantUser < User
|
||||
ACCEPTED_ISSUER = 'AS Sertifitseerimiskeskus'
|
||||
attr_accessor :idc_data
|
||||
|
||||
def ability
|
||||
|
@ -6,6 +7,19 @@ class RegistrantUser < User
|
|||
end
|
||||
delegate :can?, :cannot?, to: :ability
|
||||
|
||||
def ident
|
||||
registrant_ident.to_s.split("-").last
|
||||
end
|
||||
|
||||
def domains
|
||||
ident_cc, ident = registrant_ident.to_s.split '-'
|
||||
Domain.includes(:registrar, :registrant).where(contacts: {
|
||||
ident_type: 'priv',
|
||||
ident: ident, #identity_code,
|
||||
ident_country_code: ident_cc #country_code
|
||||
})
|
||||
end
|
||||
|
||||
def to_s
|
||||
username
|
||||
end
|
||||
|
@ -13,11 +27,9 @@ class RegistrantUser < User
|
|||
class << self
|
||||
def find_or_create_by_idc_data(idc_data, issuer_organization)
|
||||
return false if idc_data.blank?
|
||||
return false if issuer_organization != 'AS Sertifitseerimiskeskus'
|
||||
return false if issuer_organization != ACCEPTED_ISSUER
|
||||
|
||||
idc_data.force_encoding('UTF-8')
|
||||
logger.error(idc_data)
|
||||
logger.error(idc_data.encoding)
|
||||
identity_code = idc_data.scan(/serialNumber=(\d+)/).flatten.first
|
||||
country = idc_data.scan(/^\/C=(.{2})/).flatten.first
|
||||
first_name = idc_data.scan(%r{/GN=(.+)/serialNumber}).flatten.first
|
||||
|
|
|
@ -2,7 +2,8 @@ class ReservedDomain < ActiveRecord::Base
|
|||
include Versions # version/reserved_domain_version.rb
|
||||
before_save :fill_empty_passwords
|
||||
before_save :generate_data
|
||||
before_destroy :remove_data
|
||||
after_destroy :remove_data
|
||||
|
||||
validates :name, domain_name: true, uniqueness: true
|
||||
|
||||
|
||||
|
@ -21,38 +22,40 @@ class ReservedDomain < ActiveRecord::Base
|
|||
def any_of_domains names
|
||||
where(name: names)
|
||||
end
|
||||
end
|
||||
|
||||
def new_password_for name
|
||||
record = by_domain(name).first
|
||||
return unless record
|
||||
|
||||
def fill_empty_passwords
|
||||
|
||||
if self.password.empty?
|
||||
|
||||
self.password = SecureRandom.hex
|
||||
|
||||
record.regenerate_password
|
||||
record.save
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
|
||||
def name= val
|
||||
super SimpleIDN.to_unicode(val)
|
||||
end
|
||||
|
||||
def fill_empty_passwords
|
||||
regenerate_password if self.password.blank?
|
||||
end
|
||||
|
||||
def regenerate_password
|
||||
self.password = SecureRandom.hex
|
||||
end
|
||||
|
||||
def generate_data
|
||||
return if Domain.where(name: name).any?
|
||||
|
||||
@json = generate_json
|
||||
@body = generate_body
|
||||
update_whois_server
|
||||
end
|
||||
|
||||
alias_method :update_whois_record, :generate_data
|
||||
|
||||
def update_whois_server
|
||||
wr = Whois::Record.find_or_initialize_by(name: name)
|
||||
wr.body = @body
|
||||
wr.json = @json
|
||||
wr.json = @json = generate_json # we need @json to bind to class
|
||||
wr.body = generate_body
|
||||
wr.save
|
||||
end
|
||||
alias_method :update_whois_record, :generate_data
|
||||
|
||||
|
||||
def generate_body
|
||||
template = Rails.root.join("app/views/for_models/whois_other.erb".freeze)
|
||||
|
@ -67,9 +70,7 @@ class ReservedDomain < ActiveRecord::Base
|
|||
end
|
||||
|
||||
def remove_data
|
||||
return if Domain.where(name: name).any?
|
||||
|
||||
Whois::Record.where(name: name).delete_all
|
||||
UpdateWhoisRecordJob.enqueue name, 'reserved'
|
||||
end
|
||||
|
||||
end
|
||||
|
|
219
app/models/soap/arireg.rb
Normal file
219
app/models/soap/arireg.rb
Normal file
|
@ -0,0 +1,219 @@
|
|||
# coding: utf-8
|
||||
require 'savon'
|
||||
=begin
|
||||
|
||||
Estonian Business registry provides information about registered companies via xml (SOAP over HTTPS).
|
||||
|
||||
Note:
|
||||
The SSL endpoint certificate is self signed.
|
||||
|
||||
Documentation:
|
||||
http://www.rik.ee/et/e-ariregister/xml-teenus
|
||||
Specifications are in Eng and Est
|
||||
User contract required
|
||||
|
||||
Testing:
|
||||
https://demo-ariregxml.rik.ee:447/testariport/?wsdl
|
||||
http://demo-ariregxml.rik.ee:81
|
||||
https://demo-ariregxml.rik.ee:447
|
||||
|
||||
Live service:
|
||||
https://ariregxml.rik.ee/ariport/?wsdl
|
||||
https://ariregxml.rik.ee/
|
||||
|
||||
Implements Soap::Arireg # associated_businesses
|
||||
8. arireg.paringesindus_v4
|
||||
Rights of representation of all persons related to the company (newer)
|
||||
http://www2.rik.ee/schemas/xtee/arireg/live/paringesindus_v4.xsd
|
||||
expects personal id code, to fetch list of registered business id codes
|
||||
returning {ident: person, ident_country_code: ... associated_businesses: [...id_codes...]}
|
||||
|
||||
=end
|
||||
|
||||
# do some SSL set up?
|
||||
# ssl_version
|
||||
# ssl_verify_mode
|
||||
# ssl_cert_key_file
|
||||
# ssl_cert_key
|
||||
# ssl_cert_key_password
|
||||
# ssl_cert_file
|
||||
# ssl_cert
|
||||
# ssl_ca_cert_file
|
||||
# ssl_ca_cert
|
||||
|
||||
module Soap
|
||||
|
||||
class Arireg
|
||||
|
||||
class NotAvailableError < StandardError
|
||||
attr_accessor :json
|
||||
def initialize(params)
|
||||
params[:message] = "#{I18n.t(:business_registry_service_not_available)}" unless params.key? :message
|
||||
@json = params
|
||||
|
||||
super(params)
|
||||
end
|
||||
end
|
||||
|
||||
class << self
|
||||
attr_accessor :wsdl, :host, :username, :password
|
||||
end
|
||||
|
||||
def initialize
|
||||
if self.class.username.nil?
|
||||
if Rails.application.secrets.key?(:arireg)
|
||||
arireg = Rails.application.secrets[:arireg].with_indifferent_access
|
||||
self.class.username = arireg[:username]
|
||||
self.class.password = arireg[:password]
|
||||
if self.class.wsdl.nil? # no override of config/environments/* ?
|
||||
self.class.wsdl = arireg[:wsdl]
|
||||
self.class.host = arireg[:host]
|
||||
end
|
||||
else
|
||||
self.class.username = ENV['arireg_username']
|
||||
self.class.password = ENV['arireg_password']
|
||||
end
|
||||
end
|
||||
if self.class.wsdl.nil?
|
||||
self.class.wsdl = ENV['arireg_wsdl']
|
||||
self.class.host = ENV['arireg_host']
|
||||
end
|
||||
|
||||
# note Savon has error if https w/non-standard port,
|
||||
# use non-standard force to pre-set endpoint
|
||||
@client = Savon.client(wsdl: self.class.wsdl,
|
||||
host: self.class.host,
|
||||
endpoint: "#{self.class.host}/cgi-bin/consumer_proxy")
|
||||
@session = nil
|
||||
end
|
||||
|
||||
# retrieve business id codes for business that a person has a legal role
|
||||
def associated_businesses(ident, ident_cc = 'EST')
|
||||
begin
|
||||
msg = {
|
||||
'fyysilise_isiku_kood' => ident,
|
||||
'fyysilise_isiku_koodi_riik' => country_code_3(ident_cc)
|
||||
}
|
||||
Rails.logger.info "[Ariregister] Request sent with data: #{msg.inspect}"
|
||||
|
||||
response = @client.call :paringesindus_v4, message: body(msg)
|
||||
content = extract response, :paringesindus_v4_response
|
||||
Rails.logger.info "[Ariregister] Got response with data: #{content.inspect}"
|
||||
|
||||
if content.present? && content[:ettevotjad].key?(:item)
|
||||
business_ident = items(content, :ettevotjad).map{|item| item[:ariregistri_kood]}
|
||||
else
|
||||
business_ident = []
|
||||
end
|
||||
|
||||
{
|
||||
ident: ident,
|
||||
ident_country_code: ident_cc,
|
||||
# ident_type: 'priv',
|
||||
retrieved_on: Time.now,
|
||||
associated_businesses: business_ident
|
||||
}
|
||||
rescue Savon::SOAPFault => fault
|
||||
Rails.logger.error "[Ariregister] #{fault} Äriregister arireg #{self.class.username} at #{self.class.host }"
|
||||
raise NotAvailableError.new(exception: fault)
|
||||
rescue HTTPI::SSLError => ssl_error
|
||||
Rails.logger.error "[Ariregister] #{ssl_error} at #{self.class.host}"
|
||||
raise NotAvailableError.new(exception: ssl_error)
|
||||
rescue SocketError => sock
|
||||
Rails.logger.error "[Ariregister] #{sock}"
|
||||
raise NotAvailableError.new(exception: sock)
|
||||
end
|
||||
end
|
||||
|
||||
def debug
|
||||
@client.globals.log_level :debug
|
||||
@client.globals.log true
|
||||
@client.globals.pretty_print_xml true
|
||||
@debug = true
|
||||
@client
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
# add required elements to request
|
||||
def body(args)
|
||||
if @session.nil?
|
||||
args['ariregister_kasutajanimi'] = self.class.username
|
||||
args['ariregister_parool'] = self.class.password
|
||||
else
|
||||
args['ariregister_sessioon'] = @session
|
||||
end
|
||||
{keha: args}
|
||||
end
|
||||
|
||||
# TLA --- three letter acronym required not two letter acronym, transform
|
||||
def country_code_3(code)
|
||||
if code.length == 2
|
||||
code = CC2X3[code]
|
||||
raise NotAvailableError.new(message: 'Unrecognized Country') if code.nil?
|
||||
end
|
||||
code
|
||||
end
|
||||
|
||||
def extract(response, element)
|
||||
# response envelope body has again header/body under element; header is user and password returned
|
||||
response.hash[:envelope][:body][element][:keha]
|
||||
end
|
||||
|
||||
def items(content, parent)
|
||||
items = content[parent][:item]
|
||||
items.is_a?(Array) ? items : [items]
|
||||
end
|
||||
|
||||
CC2X3 = {"AF"=>"AFG", "AX"=>"ALA", "AL"=>"ALB", "DZ"=>"DZA", "AS"=>"ASM",
|
||||
"AD"=>"AND", "AO"=>"AGO", "AI"=>"AIA", "AQ"=>"ATA", "AG"=>"ATG",
|
||||
"AR"=>"ARG", "AM"=>"ARM", "AW"=>"ABW", "AU"=>"AUS", "AT"=>"AUT",
|
||||
"AZ"=>"AZE", "BS"=>"BHS", "BH"=>"BHR", "BD"=>"BGD", "BB"=>"BRB",
|
||||
"BY"=>"BLR", "BE"=>"BEL", "BZ"=>"BLZ", "BJ"=>"BEN", "BM"=>"BMU",
|
||||
"BT"=>"BTN", "BO"=>"BOL", "BQ"=>"BES", "BA"=>"BIH", "BW"=>"BWA",
|
||||
"BV"=>"BVT", "BR"=>"BRA", "IO"=>"IOT", "BN"=>"BRN", "BG"=>"BGR",
|
||||
"BF"=>"BFA", "BI"=>"BDI", "CV"=>"CPV", "KH"=>"KHM", "CM"=>"CMR",
|
||||
"CA"=>"CAN", "KY"=>"CYM", "CF"=>"CAF", "TD"=>"TCD", "CL"=>"CHL",
|
||||
"CN"=>"CHN", "CX"=>"CXR", "CC"=>"CCK", "CO"=>"COL", "KM"=>"COM",
|
||||
"CD"=>"COD", "CG"=>"COG", "CK"=>"COK", "CR"=>"CRI", "CI"=>"CIV",
|
||||
"HR"=>"HRV", "CU"=>"CUB", "CW"=>"CUW", "CY"=>"CYP", "CZ"=>"CZE",
|
||||
"DK"=>"DNK", "DJ"=>"DJI", "DM"=>"DMA", "DO"=>"DOM", "EC"=>"ECU",
|
||||
"EG"=>"EGY", "SV"=>"SLV", "GQ"=>"GNQ", "ER"=>"ERI", "EE"=>"EST",
|
||||
"ET"=>"ETH", "FK"=>"FLK", "FO"=>"FRO", "FJ"=>"FJI", "FI"=>"FIN",
|
||||
"FR"=>"FRA", "GF"=>"GUF", "PF"=>"PYF", "TF"=>"ATF", "GA"=>"GAB",
|
||||
"GM"=>"GMB", "GE"=>"GEO", "DE"=>"DEU", "GH"=>"GHA", "GI"=>"GIB",
|
||||
"GR"=>"GRC", "GL"=>"GRL", "GD"=>"GRD", "GP"=>"GLP", "GU"=>"GUM",
|
||||
"GT"=>"GTM", "GG"=>"GGY", "GN"=>"GIN", "GW"=>"GNB", "GY"=>"GUY",
|
||||
"HT"=>"HTI", "HM"=>"HMD", "VA"=>"VAT", "HN"=>"HND", "HK"=>"HKG",
|
||||
"HU"=>"HUN", "IS"=>"ISL", "IN"=>"IND", "ID"=>"IDN", "IR"=>"IRN",
|
||||
"IQ"=>"IRQ", "IE"=>"IRL", "IM"=>"IMN", "IL"=>"ISR", "IT"=>"ITA",
|
||||
"JM"=>"JAM", "JP"=>"JPN", "JE"=>"JEY", "JO"=>"JOR", "KZ"=>"KAZ",
|
||||
"KE"=>"KEN", "KI"=>"KIR", "KP"=>"PRK", "KR"=>"KOR", "KW"=>"KWT",
|
||||
"KG"=>"KGZ", "LA"=>"LAO", "LV"=>"LVA", "LB"=>"LBN", "LS"=>"LSO",
|
||||
"LR"=>"LBR", "LY"=>"LBY", "LI"=>"LIE", "LT"=>"LTU", "LU"=>"LUX",
|
||||
"MO"=>"MAC", "MK"=>"MKD", "MG"=>"MDG", "MW"=>"MWI", "MY"=>"MYS",
|
||||
"MV"=>"MDV", "ML"=>"MLI", "MT"=>"MLT", "MH"=>"MHL", "MQ"=>"MTQ",
|
||||
"MR"=>"MRT", "MU"=>"MUS", "YT"=>"MYT", "MX"=>"MEX", "FM"=>"FSM",
|
||||
"MD"=>"MDA", "MC"=>"MCO", "MN"=>"MNG", "ME"=>"MNE", "MS"=>"MSR",
|
||||
"MA"=>"MAR", "MZ"=>"MOZ", "MM"=>"MMR", "NA"=>"NAM", "NR"=>"NRU",
|
||||
"NP"=>"NPL", "NL"=>"NLD", "NC"=>"NCL", "NZ"=>"NZL", "NI"=>"NIC",
|
||||
"NE"=>"NER", "NG"=>"NGA", "NU"=>"NIU", "NF"=>"NFK", "MP"=>"MNP",
|
||||
"NO"=>"NOR", "OM"=>"OMN", "PK"=>"PAK", "PW"=>"PLW", "PS"=>"PSE",
|
||||
"PA"=>"PAN", "PG"=>"PNG", "PY"=>"PRY", "PE"=>"PER", "PH"=>"PHL",
|
||||
"PN"=>"PCN", "PL"=>"POL", "PT"=>"PRT", "PR"=>"PRI", "QA"=>"QAT",
|
||||
"RE"=>"REU", "RO"=>"ROU", "RU"=>"RUS", "RW"=>"RWA", "BL"=>"BLM",
|
||||
"SH"=>"SHN", "KN"=>"KNA", "LC"=>"LCA", "MF"=>"MAF", "PM"=>"SPM",
|
||||
"VC"=>"VCT", "WS"=>"WSM", "SM"=>"SMR", "ST"=>"STP", "SA"=>"SAU",
|
||||
"SN"=>"SEN", "RS"=>"SRB", "SC"=>"SYC", "SL"=>"SLE", "SG"=>"SGP",
|
||||
"SX"=>"SXM", "SK"=>"SVK", "SI"=>"SVN", "SB"=>"SLB", "SO"=>"SOM",
|
||||
"ZA"=>"ZAF", "GS"=>"SGS", "SS"=>"SSD", "ES"=>"ESP", "LK"=>"LKA",
|
||||
"SD"=>"SDN", "SR"=>"SUR", "SJ"=>"SJM", "SZ"=>"SWZ", "SE"=>"SWE",
|
||||
"CH"=>"CHE", "SY"=>"SYR", "TW"=>"TWN", "TJ"=>"TJK", "TZ"=>"TZA",
|
||||
"TH"=>"THA", "TL"=>"TLS", "TG"=>"TGO", "TK"=>"TKL", "TO"=>"TON",
|
||||
"TT"=>"TTO", "TN"=>"TUN", "TR"=>"TUR", "TM"=>"TKM", "TC"=>"TCA",
|
||||
"TV"=>"TUV", "UG"=>"UGA", "UA"=>"UKR", "AE"=>"ARE", "GB"=>"GBR",
|
||||
"UM"=>"UMI", "US"=>"USA", "UY"=>"URY", "UZ"=>"UZB", "VU"=>"VUT",
|
||||
"VE"=>"VEN", "VN"=>"VNM", "VG"=>"VGB", "VI"=>"VIR", "WF"=>"WLF",
|
||||
"EH"=>"ESH", "YE"=>"YEM", "ZM"=>"ZMB", "ZW"=>"ZWE"}
|
||||
end
|
||||
end
|
Loading…
Add table
Add a link
Reference in a new issue