diff --git a/.codeclimate.yml b/.codeclimate.yml
index d079d891f..33801cc17 100644
--- a/.codeclimate.yml
+++ b/.codeclimate.yml
@@ -7,14 +7,19 @@ prepare:
plugins:
brakeman:
enabled: true
+ checks:
+ mass_assign_permit!:
+ enabled: false
bundler-audit:
enabled: true
duplication:
enabled: true
config:
languages:
- - ruby
- - javascript
+ ruby:
+ mass_threshold: 100
+ javascript:
+ mass_threshold: 100
eslint:
enabled: true
channel: eslint-5
@@ -26,6 +31,9 @@ plugins:
rubocop:
enabled: true
channel: rubocop-0-74
+ checks:
+ Rubocop/Style/ClassAndModuleChildren:
+ enabled: false
checks:
method-lines:
config:
diff --git a/.github/workflows/ruby.yml b/.github/workflows/ruby.yml
index eea0ccc03..8880e83d4 100644
--- a/.github/workflows/ruby.yml
+++ b/.github/workflows/ruby.yml
@@ -17,7 +17,7 @@ jobs:
fail-fast: false
matrix:
os: [ubuntu-18.04]
- ruby: [2.6, 2.7 ]
+ ruby: [ 2.7 ]
runs-on: ${{ matrix.os }}
continue-on-error: ${{ endsWith(matrix.ruby, 'head') || matrix.ruby == 'debug' }}
steps:
@@ -100,11 +100,6 @@ jobs:
- name: Give test coverage reporter executable permissions
run: chmod +x cc-test-reporter
- - uses: actions/download-artifact@v1
- with:
- name: coverage-2.6
- path: coverage
-
- uses: actions/download-artifact@v1
with:
name: coverage-2.7
diff --git a/.ruby-version b/.ruby-version
index 57cf282eb..37c2961c2 100644
--- a/.ruby-version
+++ b/.ruby-version
@@ -1 +1 @@
-2.6.5
+2.7.2
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 50e8560d6..b5c2e19cb 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,81 @@
+12.03.2021
+* Removed old classnames from notifications [#1878](https://github.com/internetee/registry/pull/1878)
+
+11.03.2021
+* Account activity in registrar and REPP now return balance with each record [#1819](https://github.com/internetee/registry/issues/1819)
+* Fixed CookieOverflow error with large authentication service keys [#1879](https://github.com/internetee/registry/pull/1879)
+
+10.03.2021
+* Registrant API returns full contact details for admin contacts [#1876](https://github.com/internetee/registry/pull/1876)
+
+09.03.2021
+* AWS message id saving over API [#1877](https://github.com/internetee/registry/pull/1877)
+* Enabled Zeitwerk autoloader [#1872](https://github.com/internetee/registry/issues/1872)
+
+04.03.2021
+* Removed old registrant portal from the project [#1826](https://github.com/internetee/registry/issues/1826)
+
+03.03.2021
+* Email notification is sent in case of pendingupdate expiry [#897](https://github.com/internetee/registry/issues/897)
+
+26.02.2021
+* Domain delete is not affected by updateProhibited [#1844](https://github.com/internetee/registry/issues/1844)
+* Registrant API fix for handling eidas personal identificators [#1864](https://github.com/internetee/registry/pull/1864)
+
+23.02.2021
+* UpdateProhibited status affects bulk actions in REPP [#1818](https://github.com/internetee/registry/issues/1818)
+* Registrant api domain request now excludes tech only domains by default [#1836](https://github.com/internetee/registry/pull/1836)
+
+22.02.2021
+* serverDeleteProhibited prohibts delete action [#1849](https://github.com/internetee/registry/issues/1849)
+
+19.02.2021
+* Update prohibited staatus is kept after renew [#1843](https://github.com/internetee/registry/issues/1843)
+* Fixed clientHold and serverManualInzone status conflict issue [#1845](https://github.com/internetee/registry/issues/1845)
+* Replacing registrant object with another that has the same ident data set does not require registrant verification [#1852](https://github.com/internetee/registry/issues/1852)
+
+11.02.2021
+* Poll messages on locking and unlocking a domain [#1828](https://github.com/internetee/registry/issues/1828)
+* Registrar's prefix is now checked and added to contact id for info and check requests [#1832](https://github.com/internetee/registry/issues/1832)
+
+10.02.2021
+* Admin contact bulk change option for registrars [#1764](https://github.com/internetee/registry/issues/1764)
+* Option to remove email addresses from AWS SES Supression list [#1839](https://github.com/internetee/registry/issues/1839)
+* Added separate key for bounce API [#1842](https://github.com/internetee/registry/pull/1842)
+
+09.02.2021
+* Added new endpoint for WHOIS contact requests [#1794](https://github.com/internetee/registry/pull/1794)
+
+05.02.2021
+* Fixed IPv4 empty string issue in case of IPv6 only entries for IP whitelist [#1833](https://github.com/internetee/registry/issues/1833)
+
+02.02.2021
+* Fixed updateProhibited status not affecting bulk tech contact change operation [#1820](https://github.com/internetee/registry/pull/1820)
+
+01.02.2021
+* Improved tests for admin interface [#1805](https://github.com/internetee/registry/pull/1805)
+
+28.01.2021
+* Fixed transfer with shared admin and tech contacts [#1808](https://github.com/internetee/registry/issues/1808)
+* Improved error handling with double admin/tech contacts [#1758](https://github.com/internetee/registry/issues/1758)
+* Added CSV export option to admin [#1775](https://github.com/internetee/registry/issues/1775)
+* Improved DNSSEC key validation for illegal characters [#1790](https://github.com/internetee/registry/issues/1790)
+* Fix for whois record creation issue on releasing domain to auction [#1139](https://github.com/internetee/registry/issues/1139)
+* Fix for handling malformed request frames [#1825](https://github.com/internetee/registry/issues/1825)
+* Improved registrar account activity tests [#1824](https://github.com/internetee/registry/pull/1824)
+
+27.01.2021
+* Figaro update to 1.2.0 [#1823](https://github.com/internetee/registry/pull/1823)
+
+26.01.2021
+* Ruby update to 2.7 [#1791](https://github.com/internetee/registry/issues/1791)
+
+21.01.2021
+* Registrant API: optimised contact linking [#1807](https://github.com/internetee/registry/pull/1807)
+
+20.01.2021
+* Fixed legaldoc assignment issue on registrant confirmation [#1806](https://github.com/internetee/registry/pull/1806)
+
14.01.2021
* Fixed IDN and punycode support for REPP domain transfer_info request [#1801](https://github.com/internetee/registry/issues/1801)
diff --git a/Dockerfile b/Dockerfile
index 5d241eeef..97b0452e1 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -1,4 +1,4 @@
-FROM internetee/ruby:2.6-buster
+FROM internetee/ruby:2.7-buster
RUN mkdir -p /opt/webapps/app/tmp/pids
WORKDIR /opt/webapps/app
diff --git a/Gemfile b/Gemfile
index 9bbcba254..82a0b4666 100644
--- a/Gemfile
+++ b/Gemfile
@@ -9,7 +9,7 @@ gem 'rest-client'
gem 'uglifier'
# load env
-gem 'figaro', '1.1.1'
+gem 'figaro', '~> 1.2'
# model related
gem 'activerecord-import'
@@ -92,3 +92,5 @@ group :test do
gem 'webdrivers'
gem 'webmock'
end
+
+gem 'aws-sdk-sesv2', '~> 1.16'
diff --git a/Gemfile.lock b/Gemfile.lock
index 2a0bb55b1..08daf4226 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -148,6 +148,18 @@ GEM
attr_required (1.0.1)
autoprefixer-rails (10.0.0.2)
execjs
+ aws-eventstream (1.1.0)
+ aws-partitions (1.424.0)
+ aws-sdk-core (3.112.0)
+ aws-eventstream (~> 1, >= 1.0.2)
+ aws-partitions (~> 1, >= 1.239.0)
+ aws-sigv4 (~> 1.1)
+ jmespath (~> 1.0)
+ aws-sdk-sesv2 (1.16.0)
+ aws-sdk-core (~> 3, >= 3.112.0)
+ aws-sigv4 (~> 1.1)
+ aws-sigv4 (1.2.2)
+ aws-eventstream (~> 1, >= 1.0.2)
bcrypt (3.1.16)
bindata (2.4.8)
bootsnap (1.4.8)
@@ -202,8 +214,8 @@ GEM
erubis (2.7.0)
execjs (2.7.0)
ffi (1.13.1)
- figaro (1.1.1)
- thor (~> 0.14)
+ figaro (1.2.0)
+ thor (>= 0.14.0, < 2)
globalid (0.4.2)
activesupport (>= 4.2.0)
gyoku (1.3.1)
@@ -226,6 +238,7 @@ GEM
i18n_data (0.10.0)
isikukood (0.1.2)
iso8601 (0.12.1)
+ jmespath (1.4.0)
jquery-rails (4.4.0)
rails-dom-testing (>= 1, < 3)
railties (>= 4.2.0)
@@ -484,6 +497,7 @@ DEPENDENCIES
active_interaction (~> 3.8)
activerecord-import
airbrake
+ aws-sdk-sesv2 (~> 1.16)
bootsnap (>= 1.1.0)
bootstrap-sass (~> 3.4)
cancancan
@@ -502,7 +516,7 @@ DEPENDENCIES
e_invoice!
epp!
epp-xml (= 1.1.0)!
- figaro (= 1.1.1)
+ figaro (~> 1.2)
haml (~> 5.0)
isikukood
iso8601 (= 0.12.1)
diff --git a/app/assets/javascripts/admin/application.coffee b/app/assets/javascripts/admin/application.coffee
index 4c7e6acb2..a149d89cf 100644
--- a/app/assets/javascripts/admin/application.coffee
+++ b/app/assets/javascripts/admin/application.coffee
@@ -8,6 +8,8 @@ $(window).load ->
$('[data-toggle="popover"]').popover()
+ $('[data-toggle="tooltip"]').tooltip()
+
# doublescroll
$('[data-doublescroll]').doubleScroll({
onlyIfScroll: false,
diff --git a/app/controllers/admin/contact_versions_controller.rb b/app/controllers/admin/contact_versions_controller.rb
index 834353cf4..9638b341f 100644
--- a/app/controllers/admin/contact_versions_controller.rb
+++ b/app/controllers/admin/contact_versions_controller.rb
@@ -2,12 +2,12 @@ module Admin
class ContactVersionsController < BaseController
include ObjectVersionsHelper
- load_and_authorize_resource
+ load_and_authorize_resource class: Version::ContactVersion
def index
params[:q] ||= {}
- @q = ContactVersion.search(params[:q])
+ @q = Version::ContactVersion.search(params[:q])
@versions = @q.result.page(params[:page])
search_params = params[:q].deep_dup
@@ -23,7 +23,7 @@ module Admin
end
end
- versions = ContactVersion.includes(:item).where(whereS).order(created_at: :desc, id: :desc)
+ versions = Version::ContactVersion.includes(:item).where(whereS).order(created_at: :desc, id: :desc)
@q = versions.search(params[:q])
@versions = @q.result.page(params[:page])
@versions = @versions.per(params[:results_per_page]) if params[:results_per_page].to_i.positive?
@@ -32,8 +32,8 @@ module Admin
def show
per_page = 7
- @version = ContactVersion.find(params[:id])
- @versions = ContactVersion.where(item_id: @version.item_id).order(created_at: :desc, id: :desc)
+ @version = Version::ContactVersion.find(params[:id])
+ @versions = Version::ContactVersion.where(item_id: @version.item_id).order(created_at: :desc, id: :desc)
@versions_map = @versions.all.map(&:id)
# what we do is calc amount of results until needed version
@@ -49,7 +49,7 @@ module Admin
end
def search
- render json: ContactVersion.search_by_query(params[:q])
+ render json: Version::ContactVersion.search_by_query(params[:q])
end
def create_where_string(key, value)
diff --git a/app/controllers/admin/domain_versions_controller.rb b/app/controllers/admin/domain_versions_controller.rb
index b6245f6ea..2d054f73d 100644
--- a/app/controllers/admin/domain_versions_controller.rb
+++ b/app/controllers/admin/domain_versions_controller.rb
@@ -2,12 +2,12 @@ module Admin
class DomainVersionsController < BaseController
include ObjectVersionsHelper
- load_and_authorize_resource
+ load_and_authorize_resource class: Version::DomainVersion
def index
params[:q] ||= {}
- @q = DomainVersion.includes(:item).search(params[:q])
+ @q = Version::DomainVersion.includes(:item).search(params[:q])
@versions = @q.result.page(params[:page])
search_params = params[:q].deep_dup
@@ -40,7 +40,7 @@ module Admin
whereS += " AND object->>'registrar_id' IN (#{registrars.map { |r| "'#{r.id.to_s}'" }.join ','})" if registrars.present?
whereS += " AND 1=0" if registrars == []
- versions = DomainVersion.includes(:item).where(whereS).order(created_at: :desc, id: :desc)
+ versions = Version::DomainVersion.includes(:item).where(whereS).order(created_at: :desc, id: :desc)
@q = versions.search(params[:q])
@versions = @q.result.page(params[:page])
@versions = @versions.per(params[:results_per_page]) if params[:results_per_page].to_i.positive?
@@ -50,8 +50,8 @@ module Admin
def show
per_page = 7
- @version = DomainVersion.find(params[:id])
- @versions = DomainVersion.where(item_id: @version.item_id).order(created_at: :desc, id: :desc)
+ @version = Version::DomainVersion.find(params[:id])
+ @versions = Version::DomainVersion.where(item_id: @version.item_id).order(created_at: :desc, id: :desc)
@versions_map = @versions.all.map(&:id)
# what we do is calc amount of results until needed version
@@ -67,7 +67,7 @@ module Admin
end
def search
- render json: DomainVersion.search_by_query(params[:q])
+ render json: Version::DomainVersion.search_by_query(params[:q])
end
def create_where_string(key, value)
diff --git a/app/controllers/admin/domains_controller.rb b/app/controllers/admin/domains_controller.rb
index 4a8e5961e..3e2d78671 100644
--- a/app/controllers/admin/domains_controller.rb
+++ b/app/controllers/admin/domains_controller.rb
@@ -27,8 +27,17 @@ module Admin
params[:q][:name_matches] = n_cache # we don't want to show wildcards in search form
end
end
-
@domains = @domains.per(params[:results_per_page]) if params[:results_per_page].to_i.positive?
+
+ respond_to do |format|
+ format.html do
+ @domains
+ end
+ format.csv do
+ raw_csv = @domains.to_csv
+ send_data raw_csv, filename: 'domains.csv', type: "#{Mime[:csv]}; charset=utf-8"
+ end
+ end
end
def show
diff --git a/app/controllers/api/v1/base_controller.rb b/app/controllers/api/v1/base_controller.rb
index b62b3e063..6ee986a48 100644
--- a/app/controllers/api/v1/base_controller.rb
+++ b/app/controllers/api/v1/base_controller.rb
@@ -11,7 +11,7 @@ module Api
end
def authenticate_shared_key
- api_key = "Basic #{ENV['api_shared_key']}"
+ api_key = "Basic #{ENV['rwhois_internal_api_shared_key']}"
head(:unauthorized) unless api_key == request.authorization
end
diff --git a/app/controllers/api/v1/bounces_controller.rb b/app/controllers/api/v1/bounces_controller.rb
index fd10a3398..de2814250 100644
--- a/app/controllers/api/v1/bounces_controller.rb
+++ b/app/controllers/api/v1/bounces_controller.rb
@@ -1,7 +1,7 @@
module Api
module V1
class BouncesController < BaseController
- before_action :authenticate_shared_key
+ before_action :validate_shared_key_integrity
# POST api/v1/bounces/
def create
@@ -20,6 +20,13 @@ module Api
params.require(:data)
end
+
+ private
+
+ def validate_shared_key_integrity
+ api_key = "Basic #{ENV['rwhois_bounces_api_shared_key']}"
+ head(:unauthorized) unless api_key == request.authorization
+ end
end
end
end
diff --git a/app/controllers/api/v1/contact_requests_controller.rb b/app/controllers/api/v1/contact_requests_controller.rb
new file mode 100644
index 000000000..1ef73e9ef
--- /dev/null
+++ b/app/controllers/api/v1/contact_requests_controller.rb
@@ -0,0 +1,38 @@
+module Api
+ module V1
+ class ContactRequestsController < BaseController
+ before_action :authenticate_shared_key
+
+ # POST api/v1/contact_requests/
+ def create
+ return head(:bad_request) if contact_request_params[:email].blank?
+
+ contact_request = ContactRequest.save_record(contact_request_params)
+ render json: contact_request, status: :created
+ rescue StandardError
+ head(:bad_request)
+ end
+
+ def update
+ return head(:bad_request) if params[:id].blank?
+
+ process_id(params[:id])
+ end
+
+ def process_id(id)
+ record = ContactRequest.find_by(id: id)
+ return :not_found unless record
+
+ record.update_record(contact_request_params)
+ render json: record, status: :ok
+ rescue StandardError
+ head :bad_request
+ end
+
+ def contact_request_params
+ params.require(:contact_request).permit(:email, :whois_record_id, :name, :status, :ip,
+ :message_id)
+ end
+ end
+ end
+end
diff --git a/app/controllers/api/v1/registrant/auth_controller.rb b/app/controllers/api/v1/registrant/auth_controller.rb
index 03dfa45f3..728ef696d 100644
--- a/app/controllers/api/v1/registrant/auth_controller.rb
+++ b/app/controllers/api/v1/registrant/auth_controller.rb
@@ -19,6 +19,9 @@ module Api
token = create_token(user)
if token
+ msg = "Bearer for #{eid_params[:first_name]} #{eid_params[:last_name]} " \
+ "(#{eid_params[:ident]}) - '#{token[:access_token]}'"
+ ToStdout.msg(msg) unless Rails.env.production?
render json: token
else
render json: { errors: [{ base: ['Cannot create generate session token'] }] }
@@ -37,7 +40,7 @@ module Api
obj.require(key)
end
- params.permit(required_params)
+ params.permit(required_params + [:country_code])
end
def create_token(user)
diff --git a/app/controllers/api/v1/registrant/contacts_controller.rb b/app/controllers/api/v1/registrant/contacts_controller.rb
index e11458ff8..ec59ed83f 100644
--- a/app/controllers/api/v1/registrant/contacts_controller.rb
+++ b/app/controllers/api/v1/registrant/contacts_controller.rb
@@ -24,7 +24,7 @@ module Api
end
def show
- contact = current_user_contacts.find_by(uuid: params[:uuid])
+ contact = representable_contact(params[:uuid])
links = params[:links] == 'true'
if contact
@@ -91,6 +91,22 @@ module Api
private
+ def representable_contact(uuid)
+ country = current_registrant_user.country.alpha2
+ contact = Contact.find_by(uuid: uuid, ident: current_registrant_user.ident,
+ ident_type: 'priv', ident_country_code: country)
+ return contact if contact
+
+ Contact.find_by(uuid: uuid, ident_type: 'org', ident: company_codes,
+ ident_country_code: country)
+ rescue CompanyRegister::NotAvailableError
+ nil
+ end
+
+ def company_codes
+ current_registrant_user.companies.collect(&:registration_number)
+ end
+
def current_user_contacts
current_registrant_user.contacts(representable: false)
rescue CompanyRegister::NotAvailableError
diff --git a/app/controllers/api/v1/registrant/domains_controller.rb b/app/controllers/api/v1/registrant/domains_controller.rb
index 73b534598..94d2c865a 100644
--- a/app/controllers/api/v1/registrant/domains_controller.rb
+++ b/app/controllers/api/v1/registrant/domains_controller.rb
@@ -4,6 +4,8 @@ module Api
module V1
module Registrant
class DomainsController < ::Api::V1::Registrant::BaseController
+ before_action :set_tech_flag, only: [:show]
+
def index
limit = params[:limit] || 200
offset = params[:offset] || 0
@@ -25,7 +27,8 @@ module Api
serializer.to_json
end
- render json: { count: domains.count, domains: serialized_domains }
+ render json: { total: current_user_domains_total_count, count: domains.count,
+ domains: serialized_domains }
end
def show
@@ -41,10 +44,22 @@ module Api
private
- def current_user_domains
- current_registrant_user.domains
+ def set_tech_flag
+ # current_user_domains scope depends on tech flag
+ # However, if it's not present, tech contact can not see specific domain entry at all.
+ params.merge!(tech: 'true')
+ end
+
+ def current_user_domains_total_count
+ current_registrant_user.domains.count
rescue CompanyRegister::NotAvailableError
- current_registrant_user.direct_domains
+ current_registrant_user.direct_domains.count
+ end
+
+ def current_user_domains
+ current_registrant_user.domains(admin: params[:tech] != 'true')
+ rescue CompanyRegister::NotAvailableError
+ current_registrant_user.direct_domains(admin: params[:tech] != 'true')
end
end
end
diff --git a/app/controllers/epp/contacts_controller.rb b/app/controllers/epp/contacts_controller.rb
index 85305213b..65354ff48 100644
--- a/app/controllers/epp/contacts_controller.rb
+++ b/app/controllers/epp/contacts_controller.rb
@@ -14,7 +14,7 @@ module Epp
authorize! :check, Epp::Contact
ids = params[:parsed_frame].css('id').map(&:text)
- @results = Epp::Contact.check_availability(ids)
+ @results = Epp::Contact.check_availability(ids, reg: current_user.registrar.code)
render_epp_response '/epp/contacts/check'
end
@@ -93,7 +93,11 @@ module Epp
def find_contact
code = params[:parsed_frame].css('id').text.strip.upcase
- @contact = Epp::Contact.find_by!(code: code)
+ reg_code = current_user.registrar.code.upcase
+ arr = [code, "#{reg_code}:#{code}", "CID:#{code}", "CID:#{reg_code}:#{code}"]
+
+ contact = arr.find { |c| Epp::Contact.find_by(code: c).present? }
+ @contact = Epp::Contact.find_by!(code: contact || code)
end
#
diff --git a/app/controllers/epp/polls_controller.rb b/app/controllers/epp/polls_controller.rb
index 060931796..a93fa300d 100644
--- a/app/controllers/epp/polls_controller.rb
+++ b/app/controllers/epp/polls_controller.rb
@@ -12,9 +12,11 @@ module Epp
@notification = current_user.unread_notifications.order('created_at DESC').take
render_epp_response 'epp/poll/poll_no_messages' and return unless @notification
+
if @notification.attached_obj_type && @notification.attached_obj_id
begin
- @object = Object.const_get(@notification.attached_obj_type).find(@notification.attached_obj_id)
+ @object = object_by_type(@notification.attached_obj_type)
+ .find(@notification.attached_obj_id)
rescue => problem
# the data model might be inconsistent; or ...
# this could happen if the registrar does not dequeue messages, and then the domain was deleted
@@ -31,6 +33,12 @@ module Epp
render_epp_response 'epp/poll/poll_req'
end
+ def object_by_type(object_type)
+ Object.const_get(object_type)
+ rescue NameError
+ Object.const_get("Version::#{object_type}")
+ end
+
def ack_poll
@notification = current_user.unread_notifications.find_by(id: params[:parsed_frame].css('poll').first['msgID'])
diff --git a/app/controllers/registrant/contacts_controller.rb b/app/controllers/registrant/contacts_controller.rb
deleted file mode 100644
index 49070ebde..000000000
--- a/app/controllers/registrant/contacts_controller.rb
+++ /dev/null
@@ -1,115 +0,0 @@
-class Registrant::ContactsController < RegistrantController
- helper_method :domain
- helper_method :fax_enabled?
- helper_method :domain_filter_params
- skip_authorization_check only: %i[edit update]
- before_action :set_contact, only: [:show]
-
- def show
- @requester_contact = Contact.find_by(ident: current_registrant_user.ident)
- authorize! :read, @contact
- end
-
- def edit
- @contact = current_user_contacts.find(params[:id])
- end
-
- def update
- @contact = current_user_contacts.find(params[:id])
- @contact.attributes = contact_params
- response = update_contact_via_api(@contact.uuid)
- updated = response.is_a?(Net::HTTPSuccess)
-
- if updated
- redirect_to registrant_domain_contact_url(domain, @contact), notice: t('.updated')
- else
- parsed_response = JSON.parse(response.body, symbolize_names: true)
- @errors = parsed_response[:errors]
- render :edit
- end
- end
-
- private
-
- def set_contact
- id = params[:id]
- contact = domain.contacts.find_by(id: id) || current_user_contacts.find_by(id: id)
- contact ||= Contact.find_by(id: id, ident: domain.registrant.ident)
- @contact = contact
- end
-
- def domain
- current_user_domains.find(params[:domain_id])
- end
-
- def contact_params
- permitted = %i[
- name
- email
- phone
- ]
-
- permitted << :fax if fax_enabled?
- permitted += %i[street zip city state country_code] if Contact.address_processing?
- params.require(:contact).permit(*permitted)
- end
-
- def access_token
- uri = URI.parse("#{ENV['registrant_api_base_url']}/api/v1/registrant/auth/eid")
- request = Net::HTTP::Post.new(uri)
- request.form_data = access_token_request_params
-
- response = Net::HTTP.start(uri.hostname, uri.port, use_ssl: (uri.scheme == 'https')) do |http|
- http.request(request)
- end
-
- json_doc = JSON.parse(response.body, symbolize_names: true)
- json_doc[:access_token]
- end
-
- def access_token_request_params
- { ident: current_registrant_user.ident,
- first_name: current_registrant_user.first_name,
- last_name: current_registrant_user.last_name }
- end
-
- def fax_enabled?
- ENV['fax_enabled'] == 'true'
- end
-
- def contact_update_api_params
- params = contact_params
- params = normalize_address_attributes_for_api(params) if Contact.address_processing?
- params
- end
-
- def normalize_address_attributes_for_api(params)
- normalized = params
- address_parts = {}
-
- Contact.address_attribute_names.each do |attr|
- attr = attr.to_sym
- address_parts[attr] = params[attr]
- normalized.delete(attr)
- end
-
- normalized[:address] = address_parts
- normalized
- end
-
- def update_contact_via_api(uuid)
- uri = URI.parse("#{ENV['registrant_api_base_url']}/api/v1/registrant/contacts/#{uuid}")
- request = Net::HTTP::Patch.new(uri)
- request['Authorization'] = "Bearer #{access_token}"
- request['Content-type'] = 'application/json'
- request.body = contact_update_api_params.to_json
-
- Net::HTTP.start(uri.hostname, uri.port, use_ssl: (uri.scheme == 'https')) do |http|
- http.request(request)
- end
- end
-
- def domain_filter_params
- params.permit(:domain_filter)
- end
-end
diff --git a/app/controllers/registrant/domain_delete_confirms_controller.rb b/app/controllers/registrant/domain_delete_confirms_controller.rb
deleted file mode 100644
index 337ca2403..000000000
--- a/app/controllers/registrant/domain_delete_confirms_controller.rb
+++ /dev/null
@@ -1,44 +0,0 @@
-class Registrant::DomainDeleteConfirmsController < RegistrantController
- skip_before_action :authenticate_registrant_user!, only: [:show, :update]
- skip_authorization_check only: [:show, :update]
-
- def show
- return if params[:confirmed] || params[:rejected]
-
- @domain = Domain.find(params[:id])
- @domain = nil unless @domain.registrant_delete_confirmable?(params[:token])
- end
-
- def update
- @domain = Domain.find(params[:id])
- unless @domain.registrant_delete_confirmable?(params[:token])
- flash[:alert] = t(:registrant_domain_verification_failed)
- return render 'show'
- end
-
- @registrant_verification = RegistrantVerification.new(domain_id: @domain.id,
- verification_token: params[:token])
-
- initiator = current_registrant_user ? current_registrant_user.username :
- t(:user_not_authenticated)
-
- confirmed = params[:confirmed] ? true : false
- action = if confirmed
- @registrant_verification.domain_registrant_delete_confirm!("email link #{initiator}")
- else
- @registrant_verification.domain_registrant_delete_reject!("email link #{initiator}")
- end
-
- fail_msg = t("registrant_domain_delete_#{confirmed ? 'confirmed' : 'rejected'}_failed".to_sym)
- success_msg = t("registrant_domain_verification_#{confirmed ? 'confirmed' : 'rejected'}".to_sym)
-
- flash[:alert] = action ? success_msg : fail_msg
- (render 'show' && return) unless action
-
- if confirmed
- redirect_to registrant_domain_delete_confirm_path(@domain.id, confirmed: true)
- else
- redirect_to registrant_domain_delete_confirm_path(@domain.id, rejected: true)
- end
- end
-end
diff --git a/app/controllers/registrant/domain_update_confirms_controller.rb b/app/controllers/registrant/domain_update_confirms_controller.rb
deleted file mode 100644
index 0e4f2a582..000000000
--- a/app/controllers/registrant/domain_update_confirms_controller.rb
+++ /dev/null
@@ -1,44 +0,0 @@
-class Registrant::DomainUpdateConfirmsController < RegistrantController
- skip_before_action :authenticate_registrant_user!, only: %i[show update]
- skip_authorization_check only: %i[show update]
-
- def show
- return if params[:confirmed] || params[:rejected]
- @domain = Domain.find(params[:id])
- @domain = nil unless @domain.registrant_update_confirmable?(params[:token])
- end
-
- def update
- @domain = Domain.find(params[:id])
- unless @domain.registrant_update_confirmable?(params[:token])
- flash[:alert] = t(:registrant_domain_verification_failed)
- return render 'show'
- end
-
- @registrant_verification = RegistrantVerification.new(domain_id: @domain.id,
- verification_token: params[:token])
-
- initiator = current_registrant_user ? current_registrant_user.username :
- t(:user_not_authenticated)
-
- if params[:rejected]
- if @registrant_verification.domain_registrant_change_reject!("email link, #{initiator}")
- flash[:notice] = t(:registrant_domain_verification_rejected)
- redirect_to registrant_domain_update_confirm_path(@domain.id, rejected: true)
- else
- flash[:alert] = t(:registrant_domain_verification_rejected_failed)
- return render 'show'
- end
- elsif params[:confirmed]
- if @registrant_verification.domain_registrant_change_confirm!("email link, #{initiator}")
- Dispute.close_by_domain(@domain.name) if @domain.disputed?
-
- flash[:notice] = t(:registrant_domain_verification_confirmed)
- redirect_to registrant_domain_update_confirm_path(@domain.id, confirmed: true)
- else
- flash[:alert] = t(:registrant_domain_verification_confirmed_failed)
- return render 'show'
- end
- end
- end
-end
diff --git a/app/controllers/registrant/domains_controller.rb b/app/controllers/registrant/domains_controller.rb
deleted file mode 100644
index 216f87e54..000000000
--- a/app/controllers/registrant/domains_controller.rb
+++ /dev/null
@@ -1,79 +0,0 @@
-class Registrant::DomainsController < RegistrantController
- def index
- authorize! :view, :registrant_domains
-
- params[:q] ||= {}
- normalize_search_parameters do
- @q = current_user_domains.search(search_params)
- end
-
- domains = @q.result
-
- respond_to do |format|
- format.html do
- @domains = domains.page(params[:page])
- domains_per_page = params[:results_per_page].to_i
- @domains = @domains.per(domains_per_page) if domains_per_page.positive?
- end
- format.csv do
- raw_csv = @q.result.to_csv
- send_data raw_csv, filename: 'domains.csv', type: "#{Mime[:csv]}; charset=utf-8"
- end
- format.pdf do
- view = ActionView::Base.new(ActionController::Base.view_paths, domains: domains)
- raw_html = view.render(file: 'registrant/domains/list_pdf', layout: false)
- raw_pdf = domains.pdf(raw_html)
-
- send_data raw_pdf, filename: 'domains.pdf'
- end
- end
- end
-
- def show
- @domain = current_user_domains.find(params[:id])
- authorize! :read, @domain
- end
-
- def confirmation
- authorize! :view, :registrant_domains
- domain = current_user_domains.find(params[:id])
-
- if (domain.statuses.include?(DomainStatus::PENDING_UPDATE) ||
- domain.statuses.include?(DomainStatus::PENDING_DELETE_CONFIRMATION)) &&
- domain.pending_json.present?
-
- @domain = domain
- @confirmation_url = confirmation_url(domain)
- else
- flash[:warning] = I18n.t('available_verification_url_not_found')
- redirect_to registrant_domain_path(domain)
- end
- end
-
- private
-
- def normalize_search_parameters
- ca_cache = params[:q][:valid_to_lteq]
- begin
- end_time = params[:q][:valid_to_lteq].try(:to_date)
- params[:q][:valid_to_lteq] = end_time.try(:end_of_day)
- rescue
- logger.warn('Invalid date')
- end
- yield
- params[:q][:valid_to_lteq] = ca_cache
- end
-
- def confirmation_url(domain)
- if domain.statuses.include?(DomainStatus::PENDING_UPDATE)
- registrant_domain_update_confirm_url(token: domain.registrant_verification_token)
- elsif domain.statuses.include?(DomainStatus::PENDING_DELETE_CONFIRMATION)
- registrant_domain_delete_confirm_url(token: domain.registrant_verification_token)
- end
- end
-
- def search_params
- params.require(:q).permit(:name_matches, :registrant_ident_eq, :valid_to_gteq, :valid_to_lteq,
- :results_per_page)
- end
-end
diff --git a/app/controllers/registrant/registrars_controller.rb b/app/controllers/registrant/registrars_controller.rb
deleted file mode 100644
index 7bb101bb9..000000000
--- a/app/controllers/registrant/registrars_controller.rb
+++ /dev/null
@@ -1,6 +0,0 @@
-class Registrant::RegistrarsController < RegistrantController
- def show
- @registrar = Registrar.find(params[:id])
- authorize! :read, @registrar
- end
-end
\ No newline at end of file
diff --git a/app/controllers/registrant/sessions_controller.rb b/app/controllers/registrant/sessions_controller.rb
deleted file mode 100644
index 73b6d52da..000000000
--- a/app/controllers/registrant/sessions_controller.rb
+++ /dev/null
@@ -1,17 +0,0 @@
-class Registrant::SessionsController < Devise::SessionsController
- layout 'registrant/application'
-
- private
-
- def after_sign_in_path_for(_resource_or_scope)
- registrant_root_path
- end
-
- def after_sign_out_path_for(_resource_or_scope)
- new_registrant_user_session_path
- end
-
- def user_for_paper_trail
- current_registrant_user.present? ? current_registrant_user.id_role_username : 'anonymous'
- end
-end
diff --git a/app/controllers/registrar/admin_contacts_controller.rb b/app/controllers/registrar/admin_contacts_controller.rb
new file mode 100644
index 000000000..a1400b6dc
--- /dev/null
+++ b/app/controllers/registrar/admin_contacts_controller.rb
@@ -0,0 +1,18 @@
+class Registrar
+ class AdminContactsController < BulkChangeController
+ BASE_URL = URI.parse("#{ENV['repp_url']}domains/admin_contacts").freeze
+ ACTIVE_TAB = :admin_contact
+
+ def update
+ authorize! :manage, :repp
+ uri = BASE_URL
+ request = form_request(uri)
+ response = do_request(request, uri)
+ start_notice = t('.replaced')
+
+ process_response(response: response,
+ start_notice: start_notice,
+ active_tab: ACTIVE_TAB)
+ end
+ end
+end
diff --git a/app/controllers/registrar/base_controller.rb b/app/controllers/registrar/base_controller.rb
index 54bed977b..2aad861b8 100644
--- a/app/controllers/registrar/base_controller.rb
+++ b/app/controllers/registrar/base_controller.rb
@@ -17,7 +17,7 @@ class Registrar
private
def check_ip_restriction
- ip_restriction = Authorization::RestrictedIP.new(request.ip)
+ ip_restriction = Authorization::RestrictedIp.new(request.ip)
allowed = ip_restriction.can_access_registrar_area?(current_registrar_user.registrar)
return if allowed
diff --git a/app/controllers/registrar/bulk_change_controller.rb b/app/controllers/registrar/bulk_change_controller.rb
index 801ab0516..74bbf89e8 100644
--- a/app/controllers/registrar/bulk_change_controller.rb
+++ b/app/controllers/registrar/bulk_change_controller.rb
@@ -26,6 +26,84 @@ class Registrar
private
+ def form_request(uri)
+ request = Net::HTTP::Patch.new(uri)
+ request.set_form_data(current_contact_id: params[:current_contact_id],
+ new_contact_id: params[:new_contact_id])
+ request.basic_auth(current_registrar_user.username,
+ current_registrar_user.plain_text_password)
+ request
+ end
+
+ def process_response(response:, start_notice: '', active_tab:)
+ parsed_response = JSON.parse(response.body, symbolize_names: true)
+
+ if response.code == '200'
+ notices = success_notices(parsed_response, start_notice)
+
+ flash[:notice] = notices.join(', ')
+ redirect_to registrar_domains_url
+ else
+ @error = response.code == '404' ? 'Contact(s) not found' : parsed_response[:message]
+ render file: 'registrar/bulk_change/new', locals: { active_tab: active_tab }
+ end
+ end
+
+ def success_notices(parsed_response, start_notice)
+ notices = [start_notice]
+
+ notices << "#{t('.affected_domains')}: " \
+ "#{parsed_response[:data][:affected_domains].join(', ')}"
+
+ if parsed_response[:data][:skipped_domains]
+ notices << "#{t('.skipped_domains')}: " \
+ "#{parsed_response[:data][:skipped_domains].join(', ')}"
+ end
+ notices
+ end
+
+ def do_request(request, uri)
+ response = if Rails.env.test?
+ do_test_request(request, uri)
+ elsif Rails.env.development?
+ do_dev_request(request, uri)
+ else
+ do_live_request(request, uri)
+ end
+ response
+ end
+
+ def do_live_request(request, uri)
+ client_cert = File.read(ENV['cert_path'])
+ client_key = File.read(ENV['key_path'])
+ Net::HTTP.start(uri.hostname, uri.port,
+ use_ssl: (uri.scheme == 'https'),
+ cert: OpenSSL::X509::Certificate.new(client_cert),
+ key: OpenSSL::PKey::RSA.new(client_key)) do |http|
+ http.request(request)
+ end
+ end
+
+ def do_dev_request(request, uri)
+ client_cert = File.read(ENV['cert_path'])
+ client_key = File.read(ENV['key_path'])
+ Net::HTTP.start(uri.hostname, uri.port,
+ use_ssl: (uri.scheme == 'https'),
+ verify_mode: OpenSSL::SSL::VERIFY_NONE,
+ cert: OpenSSL::X509::Certificate.new(client_cert),
+ key: OpenSSL::PKey::RSA.new(client_key)) do |http|
+ http.request(request)
+ end
+ end
+
+ def do_test_request(request, uri)
+ Net::HTTP.start(uri.hostname, uri.port,
+ use_ssl: (uri.scheme == 'https'),
+ verify_mode: OpenSSL::SSL::VERIFY_NONE) do |http|
+ http.request(request)
+ end
+ end
+
def ready_to_renew?
domain_ids_for_bulk_renew.present? && params[:renew].present?
end
diff --git a/app/controllers/registrar/domain_transfers_controller.rb b/app/controllers/registrar/domain_transfers_controller.rb
index 584a50d33..e055c38d8 100644
--- a/app/controllers/registrar/domain_transfers_controller.rb
+++ b/app/controllers/registrar/domain_transfers_controller.rb
@@ -25,32 +25,7 @@ class Registrar
current_registrar_user.plain_text_password)
- if Rails.env.test?
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- verify_mode: OpenSSL::SSL::VERIFY_NONE) do |http|
- http.request(request)
- end
- elsif Rails.env.development?
- client_cert = File.read(ENV['cert_path'])
- client_key = File.read(ENV['key_path'])
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- verify_mode: OpenSSL::SSL::VERIFY_NONE,
- cert: OpenSSL::X509::Certificate.new(client_cert),
- key: OpenSSL::PKey::RSA.new(client_key)) do |http|
- http.request(request)
- end
- else
- client_cert = File.read(ENV['cert_path'])
- client_key = File.read(ENV['key_path'])
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- cert: OpenSSL::X509::Certificate.new(client_cert),
- key: OpenSSL::PKey::RSA.new(client_key)) do |http|
- http.request(request)
- end
- end
+ response = do_request(request, uri)
parsed_response = JSON.parse(response.body, symbolize_names: true)
diff --git a/app/controllers/registrar/domains_controller.rb b/app/controllers/registrar/domains_controller.rb
index 1a46da463..2e268af0b 100644
--- a/app/controllers/registrar/domains_controller.rb
+++ b/app/controllers/registrar/domains_controller.rb
@@ -49,7 +49,7 @@ class Registrar
domain_presenters << ::DomainPresenter.new(domain: domain, view: view_context)
end
- raw_csv = Registrar::DomainListCSVPresenter.new(domains: domain_presenters,
+ raw_csv = Registrar::DomainListCsvPresenter.new(domains: domain_presenters,
view: view_context).to_s
filename = "Domains_#{l(Time.zone.now, format: :filename)}.csv"
send_data raw_csv, filename: filename, type: "#{Mime[:csv]}; charset=utf-8"
diff --git a/app/controllers/registrar/nameservers_controller.rb b/app/controllers/registrar/nameservers_controller.rb
index 52c43bb1d..3eb23cd48 100644
--- a/app/controllers/registrar/nameservers_controller.rb
+++ b/app/controllers/registrar/nameservers_controller.rb
@@ -18,32 +18,7 @@ class Registrar
request.basic_auth(current_registrar_user.username,
current_registrar_user.plain_text_password)
- if Rails.env.test?
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- verify_mode: OpenSSL::SSL::VERIFY_NONE) do |http|
- http.request(request)
- end
- elsif Rails.env.development?
- client_cert = File.read(ENV['cert_path'])
- client_key = File.read(ENV['key_path'])
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- verify_mode: OpenSSL::SSL::VERIFY_NONE,
- cert: OpenSSL::X509::Certificate.new(client_cert),
- key: OpenSSL::PKey::RSA.new(client_key)) do |http|
- http.request(request)
- end
- else
- client_cert = File.read(ENV['cert_path'])
- client_key = File.read(ENV['key_path'])
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- cert: OpenSSL::X509::Certificate.new(client_cert),
- key: OpenSSL::PKey::RSA.new(client_key)) do |http|
- http.request(request)
- end
- end
+ response = do_request(request, uri)
parsed_response = JSON.parse(response.body, symbolize_names: true)
diff --git a/app/controllers/registrar/sessions_controller.rb b/app/controllers/registrar/sessions_controller.rb
index e413c4feb..ec7cda148 100644
--- a/app/controllers/registrar/sessions_controller.rb
+++ b/app/controllers/registrar/sessions_controller.rb
@@ -72,7 +72,7 @@ class Registrar
end
def check_ip_restriction
- ip_restriction = Authorization::RestrictedIP.new(request.ip)
+ ip_restriction = Authorization::RestrictedIp.new(request.ip)
allowed = ip_restriction.can_access_registrar_area_sign_in_page?
return if allowed
diff --git a/app/controllers/registrar/tech_contacts_controller.rb b/app/controllers/registrar/tech_contacts_controller.rb
index 001651250..cc9238730 100644
--- a/app/controllers/registrar/tech_contacts_controller.rb
+++ b/app/controllers/registrar/tech_contacts_controller.rb
@@ -1,62 +1,19 @@
class Registrar
class TechContactsController < BulkChangeController
+ BASE_URL = URI.parse("#{ENV['repp_url']}domains/contacts").freeze
+ ACTIVE_TAB = :technical_contact
+
def update
authorize! :manage, :repp
- uri = URI.parse("#{ENV['repp_url']}domains/contacts")
+ uri = BASE_URL
+ request = form_request(uri)
+ response = do_request(request, uri)
+ start_notice = t('.replaced')
- request = Net::HTTP::Patch.new(uri)
- request.set_form_data(current_contact_id: params[:current_contact_id],
- new_contact_id: params[:new_contact_id])
- request.basic_auth(current_registrar_user.username,
- current_registrar_user.plain_text_password)
-
- if Rails.env.test?
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- verify_mode: OpenSSL::SSL::VERIFY_NONE) do |http|
- http.request(request)
- end
- elsif Rails.env.development?
- client_cert = File.read(ENV['cert_path'])
- client_key = File.read(ENV['key_path'])
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- verify_mode: OpenSSL::SSL::VERIFY_NONE,
- cert: OpenSSL::X509::Certificate.new(client_cert),
- key: OpenSSL::PKey::RSA.new(client_key)) do |http|
- http.request(request)
- end
- else
- client_cert = File.read(ENV['cert_path'])
- client_key = File.read(ENV['key_path'])
- response = Net::HTTP.start(uri.hostname, uri.port,
- use_ssl: (uri.scheme == 'https'),
- cert: OpenSSL::X509::Certificate.new(client_cert),
- key: OpenSSL::PKey::RSA.new(client_key)) do |http|
- http.request(request)
- end
- end
-
- parsed_response = JSON.parse(response.body, symbolize_names: true)
-
- if response.code == '200'
- notices = [t('.replaced')]
-
- notices << "#{t('.affected_domains')}: " \
- "#{parsed_response[:data][:affected_domains].join(', ')}"
-
- if parsed_response[:data][:skipped_domains]
- notices << "#{t('.skipped_domains')}: " \
- "#{parsed_response[:data][:skipped_domains].join(', ')}"
- end
-
- flash[:notice] = notices.join(', ')
- redirect_to registrar_domains_url
- else
- @error = response.code == '404' ? 'Contact(s) not found' : parsed_response[:message]
- render file: 'registrar/bulk_change/new', locals: { active_tab: :technical_contact }
- end
+ process_response(response: response,
+ start_notice: start_notice,
+ active_tab: ACTIVE_TAB)
end
end
end
diff --git a/app/controllers/repp/v1/accounts_controller.rb b/app/controllers/repp/v1/accounts_controller.rb
index 89c14808f..1e0fde466 100644
--- a/app/controllers/repp/v1/accounts_controller.rb
+++ b/app/controllers/repp/v1/accounts_controller.rb
@@ -4,8 +4,28 @@ module Repp
def balance
resp = { balance: current_user.registrar.cash_account.balance,
currency: current_user.registrar.cash_account.currency }
+ resp[:transactions] = activities if params[:detailed] == 'true'
render_success(data: resp)
end
+
+ def activities
+ arr = []
+ registrar_activities.each do |a|
+ arr << { created_at: a.created_at, description: a.description,
+ type: a.activity_type == 'add_credit' ? 'credit' : 'debit',
+ sum: a.sum, balance: a.new_balance }
+ end
+
+ arr
+ end
+
+ def registrar_activities
+ activities = current_user.registrar.cash_account.activities.order(created_at: :desc)
+ activities = activities.where('created_at >= ?', params[:from]) if params[:from]
+ activities = activities.where('created_at <= ?', params[:until]) if params[:until]
+
+ activities
+ end
end
end
end
diff --git a/app/controllers/repp/v1/domains/admin_contacts_controller.rb b/app/controllers/repp/v1/domains/admin_contacts_controller.rb
new file mode 100644
index 000000000..2e9a285eb
--- /dev/null
+++ b/app/controllers/repp/v1/domains/admin_contacts_controller.rb
@@ -0,0 +1,21 @@
+module Repp
+ module V1
+ module Domains
+ class AdminContactsController < BaseContactsController
+ def update
+ super
+
+ unless @new_contact.identical_to?(@current_contact)
+ @epp_errors << { code: 2304, msg: 'Admin contacts must be identical' }
+ end
+
+ return handle_errors if @epp_errors.any?
+
+ affected, skipped = AdminDomainContact.replace(@current_contact, @new_contact)
+ @response = { affected_domains: affected, skipped_domains: skipped }
+ render_success(data: @response)
+ end
+ end
+ end
+ end
+end
diff --git a/app/controllers/repp/v1/domains/base_contacts_controller.rb b/app/controllers/repp/v1/domains/base_contacts_controller.rb
new file mode 100644
index 000000000..b601c5313
--- /dev/null
+++ b/app/controllers/repp/v1/domains/base_contacts_controller.rb
@@ -0,0 +1,31 @@
+module Repp
+ module V1
+ module Domains
+ class BaseContactsController < BaseController
+ before_action :set_current_contact, only: [:update]
+ before_action :set_new_contact, only: [:update]
+
+ def set_current_contact
+ @current_contact = current_user.registrar.contacts
+ .find_by!(code: contact_params[:current_contact_id])
+ end
+
+ def set_new_contact
+ @new_contact = current_user.registrar.contacts.find_by!(code: params[:new_contact_id])
+ end
+
+ def update
+ @epp_errors ||= []
+ @epp_errors << { code: 2304, msg: 'New contact must be valid' } if @new_contact.invalid?
+ end
+
+ private
+
+ def contact_params
+ params.require(%i[current_contact_id new_contact_id])
+ params.permit(:current_contact_id, :new_contact_id)
+ end
+ end
+ end
+ end
+end
diff --git a/app/controllers/repp/v1/domains/contacts_controller.rb b/app/controllers/repp/v1/domains/contacts_controller.rb
index 75404e0c6..131615570 100644
--- a/app/controllers/repp/v1/domains/contacts_controller.rb
+++ b/app/controllers/repp/v1/domains/contacts_controller.rb
@@ -1,23 +1,9 @@
module Repp
module V1
module Domains
- class ContactsController < BaseController
- before_action :set_current_contact, only: [:update]
- before_action :set_new_contact, only: [:update]
-
- def set_current_contact
- @current_contact = current_user.registrar.contacts.find_by!(
- code: contact_params[:current_contact_id]
- )
- end
-
- def set_new_contact
- @new_contact = current_user.registrar.contacts.find_by!(code: params[:new_contact_id])
- end
-
+ class ContactsController < BaseContactsController
def update
- @epp_errors ||= []
- @epp_errors << { code: 2304, msg: 'New contact must be valid' } if @new_contact.invalid?
+ super
if @new_contact == @current_contact
@epp_errors << { code: 2304, msg: 'New contact must be different from current' }
@@ -29,13 +15,6 @@ module Repp
@response = { affected_domains: affected, skipped_domains: skipped }
render_success(data: @response)
end
-
- private
-
- def contact_params
- params.require(%i[current_contact_id new_contact_id])
- params.permit(:current_contact_id, :new_contact_id)
- end
end
end
end
diff --git a/app/controllers/sso/tara_controller.rb b/app/controllers/sso/tara_controller.rb
index 37c8ab608..eb046730b 100644
--- a/app/controllers/sso/tara_controller.rb
+++ b/app/controllers/sso/tara_controller.rb
@@ -14,7 +14,7 @@ module Sso
# rubocop:disable Style/AndOr
def callback(user, registrar: true)
- session[:omniauth_hash] = user_hash
+ session[:omniauth_hash] = user_hash.delete_if { |key, _| key == 'credentials' }
(show_error(registrar: registrar) and return) unless user
flash[:notice] = t(:signed_in_successfully)
diff --git a/app/interactions/domains/expired_pendings/process_clean.rb b/app/interactions/domains/expired_pendings/process_clean.rb
index c6277c3c5..63a8f1ba5 100644
--- a/app/interactions/domains/expired_pendings/process_clean.rb
+++ b/app/interactions/domains/expired_pendings/process_clean.rb
@@ -17,7 +17,9 @@ module Domains
def notify_pending_update
RegistrantChangeMailer.expired(domain: domain,
registrar: domain.registrar,
- registrant: domain.registrant).deliver_later
+ registrant: domain.registrant,
+ send_to: [domain.new_registrant_email,
+ domain.registrant.email]).deliver_later
end
def notify_pending_delete
diff --git a/app/jobs/registrant_change_expired_email_job.rb b/app/jobs/registrant_change_expired_email_job.rb
deleted file mode 100644
index 3c1bc35e2..000000000
--- a/app/jobs/registrant_change_expired_email_job.rb
+++ /dev/null
@@ -1,20 +0,0 @@
-class RegistrantChangeExpiredEmailJob < Que::Job
- def run(domain_id)
- domain = Domain.find(domain_id)
- log(domain)
- RegistrantChangeMailer.expired(domain: domain,
- registrar: domain.registrar,
- registrant: domain.registrant).deliver_now
- end
-
- private
-
- def log(domain)
- message = "Send RegistrantChangeMailer#expired email for domain #{domain.name} (##{domain.id}) to #{domain.new_registrant_email}"
- logger.info(message)
- end
-
- def logger
- Rails.logger
- end
-end
diff --git a/app/lib/to_stdout.rb b/app/lib/to_stdout.rb
new file mode 100644
index 000000000..eeab82c15
--- /dev/null
+++ b/app/lib/to_stdout.rb
@@ -0,0 +1,6 @@
+class ToStdout
+ def self.msg(message)
+ time = Time.zone.now.utc
+ STDOUT << "#{time} - #{message}\n" unless Rails.env.test?
+ end
+end
diff --git a/app/mailers/application_mailer.rb b/app/mailers/application_mailer.rb
index af5d59d63..2fdb84366 100644
--- a/app/mailers/application_mailer.rb
+++ b/app/mailers/application_mailer.rb
@@ -6,10 +6,6 @@ class ApplicationMailer < ActionMailer::Base
token = domain.registrant_verification_token
base_url = ENV['registrant_portal_verifications_base_url']
- url = registrant_domain_delete_confirm_url(domain, token: token) if method == 'delete'
- url ||= registrant_domain_update_confirm_url(domain, token: token)
- return url if base_url.blank?
-
"#{base_url}/confirmation/#{domain.name_puny}/#{method}/#{token}"
end
end
diff --git a/app/mailers/interceptors/punycode_interceptor.rb b/app/mailers/interceptors/punycode_interceptor.rb
index 0680a7371..3bd38ebee 100644
--- a/app/mailers/interceptors/punycode_interceptor.rb
+++ b/app/mailers/interceptors/punycode_interceptor.rb
@@ -1,4 +1,4 @@
-class PunycodeInterceptor
+class Interceptors::PunycodeInterceptor
class << self
def delivering_email(message)
message.from = encode_addresses_as_punycode(message.from)
@@ -21,4 +21,4 @@ class PunycodeInterceptor
SimpleIDN.to_ascii(domain_part)
end
end
-end
\ No newline at end of file
+end
diff --git a/app/mailers/registrant_change_mailer.rb b/app/mailers/registrant_change_mailer.rb
index 8f43f4ab5..101e6c3e1 100644
--- a/app/mailers/registrant_change_mailer.rb
+++ b/app/mailers/registrant_change_mailer.rb
@@ -38,13 +38,13 @@ class RegistrantChangeMailer < ApplicationMailer
mail(to: domain.new_registrant_email, subject: subject)
end
- def expired(domain:, registrar:, registrant:)
+ def expired(domain:, registrar:, registrant:, send_to:)
@domain = DomainPresenter.new(domain: domain, view: view_context)
@registrar = RegistrarPresenter.new(registrar: registrar, view: view_context)
@registrant = RegistrantPresenter.new(registrant: registrant, view: view_context)
subject = default_i18n_subject(domain_name: domain.name)
- mail(to: domain.new_registrant_email, subject: subject)
+ mail(to: send_to, subject: subject)
end
private
diff --git a/app/models/ability.rb b/app/models/ability.rb
index 0bee01f9c..66a8793bc 100644
--- a/app/models/ability.rb
+++ b/app/models/ability.rb
@@ -89,8 +89,8 @@ class Ability
can :manage, BlockedDomain
can :manage, ReservedDomain
can :manage, DNS::Zone
- can :manage, DomainVersion
- can :manage, ContactVersion
+ can :manage, Version::DomainVersion
+ can :manage, Version::ContactVersion
can :manage, Billing::Price
can :manage, User
can :manage, ApiUser
diff --git a/app/models/account_activity.rb b/app/models/account_activity.rb
index d8e6be4d4..9df64209a 100644
--- a/app/models/account_activity.rb
+++ b/app/models/account_activity.rb
@@ -13,6 +13,9 @@ class AccountActivity < ApplicationRecord
def update_balance
account.balance += sum
account.save
+
+ self.new_balance = account.balance
+ save
end
class << self
diff --git a/app/models/action.rb b/app/models/action.rb
index 273dee821..ac5ee7f72 100644
--- a/app/models/action.rb
+++ b/app/models/action.rb
@@ -1,5 +1,5 @@
class Action < ApplicationRecord
- has_paper_trail versions: { class_name: 'ActionVersion' }
+ has_paper_trail versions: { class_name: 'Version::ActionVersion' }
belongs_to :user
belongs_to :contact
diff --git a/app/models/actions/contact_delete.rb b/app/models/actions/contact_delete.rb
index 59032d566..60d3252c4 100644
--- a/app/models/actions/contact_delete.rb
+++ b/app/models/actions/contact_delete.rb
@@ -19,6 +19,11 @@ module Actions
return
end
+ if contact.delete_prohibited?
+ contact.errors.add(:statuses, :delete_prohibited)
+ return
+ end
+
commit
end
diff --git a/app/models/admin_domain_contact.rb b/app/models/admin_domain_contact.rb
index 14907403d..7ccf3efcb 100644
--- a/app/models/admin_domain_contact.rb
+++ b/app/models/admin_domain_contact.rb
@@ -1,2 +1,26 @@
class AdminDomainContact < DomainContact
+ # rubocop:disable Metrics/AbcSize
+ # rubocop:disable Metrics/MethodLength
+ def self.replace(current_contact, new_contact)
+ affected_domains = []
+ skipped_domains = []
+ admin_contacts = where(contact: current_contact)
+
+ admin_contacts.each do |admin_contact|
+ if admin_contact.domain.bulk_update_prohibited?
+ skipped_domains << admin_contact.domain.name
+ next
+ end
+ begin
+ admin_contact.contact = new_contact
+ admin_contact.save!
+ affected_domains << admin_contact.domain.name
+ rescue ActiveRecord::RecordNotUnique
+ skipped_domains << admin_contact.domain.name
+ end
+ end
+ [affected_domains.sort, skipped_domains.sort]
+ end
+ # rubocop:enable Metrics/AbcSize
+ # rubocop:enable Metrics/MethodLength
end
diff --git a/app/models/authorization/restricted_ip.rb b/app/models/authorization/restricted_ip.rb
index b3c7b7cdb..41bb15f98 100644
--- a/app/models/authorization/restricted_ip.rb
+++ b/app/models/authorization/restricted_ip.rb
@@ -1,5 +1,5 @@
module Authorization
- class RestrictedIP
+ class RestrictedIp
def initialize(ip)
@ip = ip
end
diff --git a/app/models/billing/price.rb b/app/models/billing/price.rb
index dac458b00..3b0c253d4 100644
--- a/app/models/billing/price.rb
+++ b/app/models/billing/price.rb
@@ -1,6 +1,6 @@
module Billing
class Price < ApplicationRecord
- include Concerns::Billing::Price::Expirable
+ include Billing::Price::Expirable
include Versions
belongs_to :zone, class_name: 'DNS::Zone', required: true
diff --git a/app/models/bounced_mail_address.rb b/app/models/bounced_mail_address.rb
index 73c6a0941..db4413829 100644
--- a/app/models/bounced_mail_address.rb
+++ b/app/models/bounced_mail_address.rb
@@ -1,5 +1,6 @@
class BouncedMailAddress < ApplicationRecord
validates :email, :message_id, :bounce_type, :bounce_subtype, :action, :status, presence: true
+ after_destroy :destroy_aws_suppression
def bounce_reason
"#{action} (#{status} #{diagnostic})"
@@ -25,4 +26,20 @@ class BouncedMailAddress < ApplicationRecord
diagnostic: bounced_record['diagnosticCode'],
}
end
+
+ def destroy_aws_suppression
+ return unless BouncedMailAddress.ses_configured?
+
+ res = Aws::SESV2::Client.new.delete_suppressed_destination(email_address: email)
+ res.successful?
+ rescue Aws::SESV2::Errors::ServiceError => e
+ logger.warn("Suppression not removed. #{e}")
+ end
+
+ def self.ses_configured?
+ ses ||= Aws::SESV2::Client.new
+ ses.config.credentials.access_key_id.present?
+ rescue Aws::Errors::MissingRegionError
+ false
+ end
end
diff --git a/app/models/concerns/billing/price/expirable.rb b/app/models/concerns/billing/price/expirable.rb
index c0e05832a..2387bf320 100644
--- a/app/models/concerns/billing/price/expirable.rb
+++ b/app/models/concerns/billing/price/expirable.rb
@@ -1,4 +1,4 @@
-module Concerns::Billing::Price::Expirable
+module Billing::Price::Expirable
extend ActiveSupport::Concern
class_methods do
diff --git a/app/models/concerns/contact/archivable.rb b/app/models/concerns/contact/archivable.rb
index 4526e04c5..ca2d19b1b 100644
--- a/app/models/concerns/contact/archivable.rb
+++ b/app/models/concerns/contact/archivable.rb
@@ -1,68 +1,64 @@
-module Concerns
- module Contact
- module Archivable
- extend ActiveSupport::Concern
+module Contact::Archivable
+ extend ActiveSupport::Concern
- class_methods do
- def archivable
- unlinked.find_each.select(&:archivable?)
- end
- end
-
- def archivable?(post: false)
- inactive = inactive?
-
- log("Found archivable contact id(#{id}), code (#{code})") if inactive && !post
-
- inactive
- end
-
- def archive(verified: false, notify: true, extra_log: false)
- unless verified
- raise 'Contact cannot be archived' unless archivable?(post: true)
- end
-
- notify_registrar_about_archivation if notify
- write_to_registrar_log if extra_log
- destroy!
- end
-
- private
-
- def notify_registrar_about_archivation
- registrar.notifications.create!(
- text: I18n.t('contact_has_been_archived',
- contact_code: code, orphan_months: Setting.orphans_contacts_in_months)
- )
- end
-
- def inactive?
- if DomainVersion.contact_unlinked_more_than?(contact_id: id, period: inactivity_period)
- return true
- end
-
- DomainVersion.was_contact_linked?(id) ? false : created_at <= inactivity_period.ago
- end
-
- def inactivity_period
- Setting.orphans_contacts_in_months.months
- end
-
- def log(msg)
- @log ||= Logger.new(STDOUT)
- @log.info(msg)
- end
-
- def write_to_registrar_log
- registrar_name = registrar.accounting_customer_code
- archive_path = ENV['contact_archivation_log_file_dir']
- registrar_log_path = "#{archive_path}/#{registrar_name}.txt"
- FileUtils.mkdir_p(archive_path) unless Dir.exist?(archive_path)
-
- f = File.new(registrar_log_path, 'a+')
- f.write("#{code}\n")
- f.close
- end
+ class_methods do
+ def archivable
+ unlinked.find_each.select(&:archivable?)
end
end
+
+ def archivable?(post: false)
+ inactive = inactive?
+
+ log("Found archivable contact id(#{id}), code (#{code})") if inactive && !post
+
+ inactive
+ end
+
+ def archive(verified: false, notify: true, extra_log: false)
+ unless verified
+ raise 'Contact cannot be archived' unless archivable?(post: true)
+ end
+
+ notify_registrar_about_archivation if notify
+ write_to_registrar_log if extra_log
+ destroy!
+ end
+
+ private
+
+ def notify_registrar_about_archivation
+ registrar.notifications.create!(
+ text: I18n.t('contact_has_been_archived',
+ contact_code: code, orphan_months: Setting.orphans_contacts_in_months)
+ )
+ end
+
+ def inactive?
+ if Version::DomainVersion.contact_unlinked_more_than?(contact_id: id, period: inactivity_period)
+ return true
+ end
+
+ Version::DomainVersion.was_contact_linked?(id) ? false : created_at <= inactivity_period.ago
+ end
+
+ def inactivity_period
+ Setting.orphans_contacts_in_months.months
+ end
+
+ def log(msg)
+ @log ||= Logger.new(STDOUT)
+ @log.info(msg)
+ end
+
+ def write_to_registrar_log
+ registrar_name = registrar.accounting_customer_code
+ archive_path = ENV['contact_archivation_log_file_dir']
+ registrar_log_path = "#{archive_path}/#{registrar_name}.txt"
+ FileUtils.mkdir_p(archive_path) unless Dir.exist?(archive_path)
+
+ f = File.new(registrar_log_path, 'a+')
+ f.write("#{code}\n")
+ f.close
+ end
end
diff --git a/app/models/concerns/contact/disclosable.rb b/app/models/concerns/contact/disclosable.rb
index 6c3b81849..a61b240b1 100644
--- a/app/models/concerns/contact/disclosable.rb
+++ b/app/models/concerns/contact/disclosable.rb
@@ -1,26 +1,22 @@
-module Concerns
- module Contact
- module Disclosable
- extend ActiveSupport::Concern
+module Contact::Disclosable
+ extend ActiveSupport::Concern
- class_methods do
- attr_accessor :disclosable_attributes
- end
+ class_methods do
+ attr_accessor :disclosable_attributes
+ end
- included do
- self.disclosable_attributes = %w[name email]
- validate :validate_disclosed_attributes
- end
+ included do
+ self.disclosable_attributes = %w[name email]
+ validate :validate_disclosed_attributes
+ end
- private
+ private
- def validate_disclosed_attributes
- return if disclosed_attributes.empty?
+ def validate_disclosed_attributes
+ return if disclosed_attributes.empty?
- has_undisclosable_attributes = (disclosed_attributes - self.class.disclosable_attributes)
- .any?
- errors.add(:disclosed_attributes, :invalid) if has_undisclosable_attributes
- end
- end
+ has_undisclosable_attributes = (disclosed_attributes - self.class.disclosable_attributes)
+ .any?
+ errors.add(:disclosed_attributes, :invalid) if has_undisclosable_attributes
end
end
diff --git a/app/models/concerns/contact/identical.rb b/app/models/concerns/contact/identical.rb
index f529e09ac..d9bcf1046 100644
--- a/app/models/concerns/contact/identical.rb
+++ b/app/models/concerns/contact/identical.rb
@@ -1,4 +1,4 @@
-module Concerns::Contact::Identical
+module Contact::Identical
extend ActiveSupport::Concern
IDENTIFIABLE_ATTRIBUTES = %w[
@@ -11,6 +11,13 @@ module Concerns::Contact::Identical
ident_country_code
org_name
]
+
+ IDENTICAL_ATTRIBUTES = %w[
+ ident
+ ident_type
+ ident_country_code
+ ].freeze
+
private_constant :IDENTIFIABLE_ATTRIBUTES
def identical(registrar)
@@ -20,6 +27,12 @@ module Concerns::Contact::Identical
.where.not(id: id).take
end
+ def identical_to?(contact)
+ IDENTICAL_ATTRIBUTES.all? do |attribute|
+ attributes[attribute] == contact.attributes[attribute]
+ end
+ end
+
private
def identifiable_hash
diff --git a/app/models/concerns/domain/activatable.rb b/app/models/concerns/domain/activatable.rb
index 58ff822d9..ae1bd6f7b 100644
--- a/app/models/concerns/domain/activatable.rb
+++ b/app/models/concerns/domain/activatable.rb
@@ -1,4 +1,4 @@
-module Concerns::Domain::Activatable
+module Domain::Activatable
extend ActiveSupport::Concern
def active?
diff --git a/app/models/concerns/domain/bulk_updatable.rb b/app/models/concerns/domain/bulk_updatable.rb
new file mode 100644
index 000000000..6a462e1af
--- /dev/null
+++ b/app/models/concerns/domain/bulk_updatable.rb
@@ -0,0 +1,13 @@
+module Domain::BulkUpdatable
+ extend ActiveSupport::Concern
+
+ def bulk_update_prohibited?
+ discarded? || statuses_blocks_update?
+ end
+
+ def statuses_blocks_update?
+ prohibited_array = [DomainStatus::SERVER_UPDATE_PROHIBITED,
+ DomainStatus::CLIENT_UPDATE_PROHIBITED]
+ prohibited_array.any? { |block_status| statuses.include?(block_status) }
+ end
+end
diff --git a/app/models/concerns/domain/deletable.rb b/app/models/concerns/domain/deletable.rb
index 81518c739..50c418feb 100644
--- a/app/models/concerns/domain/deletable.rb
+++ b/app/models/concerns/domain/deletable.rb
@@ -1,6 +1,12 @@
-module Concerns::Domain::Deletable
+module Domain::Deletable
extend ActiveSupport::Concern
+ DELETE_STATUSES = [
+ DomainStatus::PENDING_DELETE_CONFIRMATION,
+ DomainStatus::PENDING_DELETE,
+ DomainStatus::FORCE_DELETE,
+ ].freeze
+
private
def delete_later
diff --git a/app/models/concerns/domain/discardable.rb b/app/models/concerns/domain/discardable.rb
index 25547af0f..abb105d80 100644
--- a/app/models/concerns/domain/discardable.rb
+++ b/app/models/concerns/domain/discardable.rb
@@ -1,4 +1,4 @@
-module Concerns::Domain::Discardable
+module Domain::Discardable
extend ActiveSupport::Concern
def keep
diff --git a/app/models/concerns/domain/disputable.rb b/app/models/concerns/domain/disputable.rb
index a05d7cea6..a70d8b7cf 100644
--- a/app/models/concerns/domain/disputable.rb
+++ b/app/models/concerns/domain/disputable.rb
@@ -1,44 +1,40 @@
# frozen_string_literal: true
-module Concerns
- module Domain
- module Disputable
- extend ActiveSupport::Concern
+module Domain::Disputable
+ extend ActiveSupport::Concern
- included do
- validate :validate_disputed
- end
+ included do
+ validate :validate_disputed
+ end
- def mark_as_disputed
- statuses.push(DomainStatus::DISPUTED) unless statuses.include?(DomainStatus::DISPUTED)
- save
- end
+ def mark_as_disputed
+ statuses.push(DomainStatus::DISPUTED) unless statuses.include?(DomainStatus::DISPUTED)
+ save
+ end
- def unmark_as_disputed
- statuses.delete_if { |status| status == DomainStatus::DISPUTED }
- save
- end
+ def unmark_as_disputed
+ statuses.delete_if { |status| status == DomainStatus::DISPUTED }
+ save
+ end
- def in_disputed_list?
- @in_disputed_list ||= Dispute.active.find_by(domain_name: name).present?
- end
+ def in_disputed_list?
+ @in_disputed_list ||= Dispute.active.find_by(domain_name: name).present?
+ end
- def disputed?
- Dispute.active.where(domain_name: name).any?
- end
+ def disputed?
+ Dispute.active.where(domain_name: name).any?
+ end
- def validate_disputed
- return if persisted? || !in_disputed_list?
+ def validate_disputed
+ return if persisted? || !in_disputed_list?
- if reserved_pw.blank?
- errors.add(:base, :required_parameter_missing_disputed)
- return false
- end
-
- return if Dispute.valid_auth?(name, reserved_pw)
-
- errors.add(:base, :invalid_auth_information_reserved)
- end
+ if reserved_pw.blank?
+ errors.add(:base, :required_parameter_missing_disputed)
+ return false
end
+
+ return if Dispute.valid_auth?(name, reserved_pw)
+
+ errors.add(:base, :invalid_auth_information_reserved)
end
end
diff --git a/app/models/concerns/domain/expirable.rb b/app/models/concerns/domain/expirable.rb
index f4e8b61f8..1710f9dcd 100644
--- a/app/models/concerns/domain/expirable.rb
+++ b/app/models/concerns/domain/expirable.rb
@@ -1,4 +1,4 @@
-module Concerns::Domain::Expirable
+module Domain::Expirable
extend ActiveSupport::Concern
included do
diff --git a/app/models/concerns/domain/force_delete.rb b/app/models/concerns/domain/force_delete.rb
index 87e9a957b..ca13eb5d1 100644
--- a/app/models/concerns/domain/force_delete.rb
+++ b/app/models/concerns/domain/force_delete.rb
@@ -1,4 +1,4 @@
-module Concerns::Domain::ForceDelete # rubocop:disable Metrics/ModuleLength
+module Domain::ForceDelete # rubocop:disable Metrics/ModuleLength
extend ActiveSupport::Concern
included do
@@ -11,6 +11,11 @@ module Concerns::Domain::ForceDelete # rubocop:disable Metrics/ModuleLength
lambda {
where("(force_delete_data->>'contact_notification_sent_date') is null")
}
+
+ HOLD_STATUSES = [
+ DomainStatus::SERVER_HOLD,
+ DomainStatus::CLIENT_HOLD,
+ ].freeze
end
class_methods do
@@ -19,6 +24,10 @@ module Concerns::Domain::ForceDelete # rubocop:disable Metrics/ModuleLength
end
end
+ def hold_status?
+ HOLD_STATUSES.any? { |status| statuses.include? status }
+ end
+
def notification_template(explicit: nil)
reason = explicit&.downcase
return reason if %w[invalid_email invalid_phone].include?(reason)
diff --git a/app/models/concerns/domain/registry_lockable.rb b/app/models/concerns/domain/registry_lockable.rb
index 4a759296d..2e80b7dda 100644
--- a/app/models/concerns/domain/registry_lockable.rb
+++ b/app/models/concerns/domain/registry_lockable.rb
@@ -1,51 +1,59 @@
-module Concerns
- module Domain
- module RegistryLockable
- extend ActiveSupport::Concern
+module Domain::RegistryLockable
+ extend ActiveSupport::Concern
- def apply_registry_lock
- return unless registry_lockable?
- return if locked_by_registrant?
+ def apply_registry_lock
+ return unless registry_lockable?
+ return if locked_by_registrant?
- transaction do
- statuses << DomainStatus::SERVER_UPDATE_PROHIBITED
- statuses << DomainStatus::SERVER_DELETE_PROHIBITED
- statuses << DomainStatus::SERVER_TRANSFER_PROHIBITED
- self.locked_by_registrant_at = Time.zone.now
+ transaction do
+ statuses << DomainStatus::SERVER_UPDATE_PROHIBITED
+ statuses << DomainStatus::SERVER_DELETE_PROHIBITED
+ statuses << DomainStatus::SERVER_TRANSFER_PROHIBITED
+ self.locked_by_registrant_at = Time.zone.now
+ alert_registrar_lock_changes!(lock: true)
- save!
- end
- end
-
- def registry_lockable?
- (statuses & [DomainStatus::PENDING_DELETE_CONFIRMATION,
- DomainStatus::PENDING_CREATE, DomainStatus::PENDING_UPDATE,
- DomainStatus::PENDING_DELETE, DomainStatus::PENDING_RENEW,
- DomainStatus::PENDING_TRANSFER, DomainStatus::FORCE_DELETE]).empty?
- end
-
- def locked_by_registrant?
- return false unless locked_by_registrant_at
-
- lock_statuses = [DomainStatus::SERVER_UPDATE_PROHIBITED,
- DomainStatus::SERVER_DELETE_PROHIBITED,
- DomainStatus::SERVER_TRANSFER_PROHIBITED]
-
- (statuses & lock_statuses).count == 3
- end
-
- def remove_registry_lock
- return unless locked_by_registrant?
-
- transaction do
- statuses.delete(DomainStatus::SERVER_UPDATE_PROHIBITED)
- statuses.delete(DomainStatus::SERVER_DELETE_PROHIBITED)
- statuses.delete(DomainStatus::SERVER_TRANSFER_PROHIBITED)
- self.locked_by_registrant_at = nil
-
- save!
- end
- end
+ save!
end
end
+
+ def registry_lockable?
+ (statuses & [DomainStatus::PENDING_DELETE_CONFIRMATION,
+ DomainStatus::PENDING_CREATE, DomainStatus::PENDING_UPDATE,
+ DomainStatus::PENDING_DELETE, DomainStatus::PENDING_RENEW,
+ DomainStatus::PENDING_TRANSFER, DomainStatus::FORCE_DELETE]).empty?
+ end
+
+ def locked_by_registrant?
+ return false unless locked_by_registrant_at
+
+ lock_statuses = [DomainStatus::SERVER_UPDATE_PROHIBITED,
+ DomainStatus::SERVER_DELETE_PROHIBITED,
+ DomainStatus::SERVER_TRANSFER_PROHIBITED]
+
+ (statuses & lock_statuses).count == 3
+ end
+
+ def remove_registry_lock
+ return unless locked_by_registrant?
+
+ transaction do
+ statuses.delete(DomainStatus::SERVER_UPDATE_PROHIBITED)
+ statuses.delete(DomainStatus::SERVER_DELETE_PROHIBITED)
+ statuses.delete(DomainStatus::SERVER_TRANSFER_PROHIBITED)
+ self.locked_by_registrant_at = nil
+ alert_registrar_lock_changes!(lock: false)
+
+ save!
+ end
+ end
+
+ def alert_registrar_lock_changes!(lock: true)
+ translation = lock ? 'locked' : 'unlocked'
+ registrar.notifications.create!(
+ text: I18n.t("notifications.texts.registrar_#{translation}",
+ domain_name: name),
+ attached_obj_id: name,
+ attached_obj_type: self.class.name
+ )
+ end
end
diff --git a/app/models/concerns/domain/releasable.rb b/app/models/concerns/domain/releasable.rb
index 4aa5faa58..81410329b 100644
--- a/app/models/concerns/domain/releasable.rb
+++ b/app/models/concerns/domain/releasable.rb
@@ -1,55 +1,53 @@
-module Concerns
- module Domain
- module Releasable
- extend ActiveSupport::Concern
+module Domain::Releasable
+ extend ActiveSupport::Concern
- class_methods do
- def release_domains
- releasable_domains.each do |domain|
- domain.release
- yield domain if block_given?
- end
- end
-
- private
-
- def releasable_domains
- if release_to_auction
- where('(delete_date <= ? OR force_delete_date <= ?)' \
- ' AND ? != ALL(coalesce(statuses, array[]::varchar[]))',
- Time.zone.today,
- Time.zone.today,
- DomainStatus::SERVER_DELETE_PROHIBITED)
- else
- where('(delete_date <= ? OR force_delete_date <= ?)' \
- ' AND ? != ALL(coalesce(statuses, array[]::varchar[])) AND' \
- ' ? != ALL(COALESCE(statuses, array[]::varchar[]))',
- Time.zone.today,
- Time.zone.today,
- DomainStatus::SERVER_DELETE_PROHIBITED,
- DomainStatus::DELETE_CANDIDATE)
- end
- end
+ class_methods do
+ def release_domains
+ releasable_domains.each do |domain|
+ domain.release
+ yield domain if block_given?
end
+ end
- included do
- class_attribute :release_to_auction
- self.release_to_auction = ENV['release_domains_to_auction'] == 'true'
- end
+ private
- def release
- if release_to_auction
- transaction do
- domain_name.sell_at_auction if domain_name.auctionable?
- destroy!
- registrar.notifications.create!(text: "#{I18n.t(:domain_deleted)}: #{name}",
- attached_obj_id: id,
- attached_obj_type: self.class)
- end
- else
- discard
- end
+ def releasable_domains
+ if release_to_auction
+ where('(delete_date <= ? OR force_delete_date <= ?)' \
+ ' AND ? != ALL(coalesce(statuses, array[]::varchar[]))',
+ Time.zone.today,
+ Time.zone.today,
+ DomainStatus::SERVER_DELETE_PROHIBITED)
+ else
+ where('(delete_date <= ? OR force_delete_date <= ?)' \
+ ' AND ? != ALL(coalesce(statuses, array[]::varchar[])) AND' \
+ ' ? != ALL(COALESCE(statuses, array[]::varchar[]))',
+ Time.zone.today,
+ Time.zone.today,
+ DomainStatus::SERVER_DELETE_PROHIBITED,
+ DomainStatus::DELETE_CANDIDATE)
end
end
end
+
+ included do
+ class_attribute :release_to_auction
+ self.release_to_auction = ENV['release_domains_to_auction'] == 'true'
+ end
+
+ def release
+ if release_to_auction
+ ToStdout.msg 'Destroying domain'
+ destroy!
+ ToStdout.msg "Checking if domain_name is auctionable: #{domain_name.auctionable?}"
+ domain_name.sell_at_auction if domain_name.auctionable?
+
+ ToStdout.msg 'Sending registrar notification'
+ registrar.notifications.create!(text: "#{I18n.t(:domain_deleted)}: #{name}",
+ attached_obj_id: id,
+ attached_obj_type: self.class)
+ else
+ discard
+ end
+ end
end
diff --git a/app/models/concerns/domain/transferable.rb b/app/models/concerns/domain/transferable.rb
index 9de2fff83..d280f6d67 100644
--- a/app/models/concerns/domain/transferable.rb
+++ b/app/models/concerns/domain/transferable.rb
@@ -1,4 +1,4 @@
-module Concerns::Domain::Transferable
+module Domain::Transferable
extend ActiveSupport::Concern
included do
@@ -31,7 +31,9 @@ module Concerns::Domain::Transferable
DomainStatus::PENDING_TRANSFER,
DomainStatus::FORCE_DELETE,
DomainStatus::SERVER_TRANSFER_PROHIBITED,
- DomainStatus::CLIENT_TRANSFER_PROHIBITED
+ DomainStatus::CLIENT_TRANSFER_PROHIBITED,
+ DomainStatus::SERVER_UPDATE_PROHIBITED,
+ DomainStatus::CLIENT_UPDATE_PROHIBITED,
]).empty?
end
@@ -59,7 +61,7 @@ module Concerns::Domain::Transferable
copied_ids = []
domain_contacts.each do |dc|
contact = Contact.find(dc.contact_id)
- next if copied_ids.include?(contact.id) || contact.registrar == new_registrar
+ next if copied_ids.include?(uniq_contact_hash(dc)) || contact.registrar == new_registrar
if registrant_id_was == contact.id # registrant was copied previously, do not copy it again
oc = OpenStruct.new(id: registrant_id)
@@ -72,7 +74,11 @@ module Concerns::Domain::Transferable
else
dc.update(contact_id: oc.id)
end
- copied_ids << contact.id
+ copied_ids << uniq_contact_hash(dc)
end
end
+
+ def uniq_contact_hash(contact)
+ Digest::SHA1.hexdigest(contact.contact_id.to_s + contact.type)
+ end
end
diff --git a/app/models/concerns/email_verifable.rb b/app/models/concerns/email_verifable.rb
index d0bb6aecb..457555b44 100644
--- a/app/models/concerns/email_verifable.rb
+++ b/app/models/concerns/email_verifable.rb
@@ -1,95 +1,93 @@
-module Concerns
- module EmailVerifable
- extend ActiveSupport::Concern
+module EmailVerifable
+ extend ActiveSupport::Concern
- def email_verification
- @email_verification ||= EmailAddressVerification.find_or_create_by(email: unicode_email,
- domain: domain(email))
- end
+ def email_verification
+ @email_verification ||= EmailAddressVerification.find_or_create_by(email: unicode_email,
+ domain: domain(email))
+ end
- def billing_email_verification
- return unless attribute_names.include?('billing_email')
+ def billing_email_verification
+ return unless attribute_names.include?('billing_email')
- @billing_email_verification ||= EmailAddressVerification
- .find_or_create_by(email: unicode_billing_email,
- domain: domain(billing_email))
- end
+ @billing_email_verification ||= EmailAddressVerification
+ .find_or_create_by(email: unicode_billing_email,
+ domain: domain(billing_email))
+ end
- def email_verification_failed?
- email_verification&.failed?
- end
-
- class_methods do
- def domain(email)
- Mail::Address.new(email).domain&.downcase || 'not_found'
- rescue Mail::Field::IncompleteParseError
- 'not_found'
- end
-
- def local(email)
- Mail::Address.new(email).local&.downcase || email
- rescue Mail::Field::IncompleteParseError
- email
- end
-
- def punycode_to_unicode(email)
- return email if domain(email) == 'not_found'
-
- local = local(email)
- domain = SimpleIDN.to_unicode(domain(email))
- "#{local}@#{domain}"&.downcase
- end
-
- def unicode_to_punycode(email)
- return email if domain(email) == 'not_found'
-
- local = local(email)
- domain = SimpleIDN.to_ascii(domain(email))
- "#{local}@#{domain}"&.downcase
- end
- end
-
- def unicode_billing_email
- self.class.punycode_to_unicode(billing_email)
- end
-
- def unicode_email
- self.class.punycode_to_unicode(email)
- end
+ def email_verification_failed?
+ email_verification&.failed?
+ end
+ class_methods do
def domain(email)
- SimpleIDN.to_unicode(self.class.domain(email))
+ Mail::Address.new(email).domain&.downcase || 'not_found'
+ rescue Mail::Field::IncompleteParseError
+ 'not_found'
+ end
+
+ def local(email)
+ Mail::Address.new(email).local&.downcase || email
+ rescue Mail::Field::IncompleteParseError
+ email
end
def punycode_to_unicode(email)
- self.class.punycode_to_unicode(email)
+ return email if domain(email) == 'not_found'
+
+ local = local(email)
+ domain = SimpleIDN.to_unicode(domain(email))
+ "#{local}@#{domain}"&.downcase
end
- def correct_email_format
- return if email.blank?
+ def unicode_to_punycode(email)
+ return email if domain(email) == 'not_found'
- result = email_verification.verify
- process_result(result: result, field: :email)
+ local = local(email)
+ domain = SimpleIDN.to_ascii(domain(email))
+ "#{local}@#{domain}"&.downcase
end
-
- def correct_billing_email_format
- return if email.blank?
-
- result = billing_email_verification.verify
- process_result(result: result, field: :billing_email)
- end
-
- # rubocop:disable Metrics/LineLength
- def process_result(result:, field:)
- case result[:errors].keys.first
- when :smtp
- errors.add(field, I18n.t('activerecord.errors.models.contact.attributes.email.email_smtp_check_error'))
- when :mx
- errors.add(field, I18n.t('activerecord.errors.models.contact.attributes.email.email_mx_check_error'))
- when :regex
- errors.add(field, I18n.t('activerecord.errors.models.contact.attributes.email.email_regex_check_error'))
- end
- end
- # rubocop:enable Metrics/LineLength
end
+
+ def unicode_billing_email
+ self.class.punycode_to_unicode(billing_email)
+ end
+
+ def unicode_email
+ self.class.punycode_to_unicode(email)
+ end
+
+ def domain(email)
+ SimpleIDN.to_unicode(self.class.domain(email))
+ end
+
+ def punycode_to_unicode(email)
+ self.class.punycode_to_unicode(email)
+ end
+
+ def correct_email_format
+ return if email.blank?
+
+ result = email_verification.verify
+ process_result(result: result, field: :email)
+ end
+
+ def correct_billing_email_format
+ return if email.blank?
+
+ result = billing_email_verification.verify
+ process_result(result: result, field: :billing_email)
+ end
+
+ # rubocop:disable Metrics/LineLength
+ def process_result(result:, field:)
+ case result[:errors].keys.first
+ when :smtp
+ errors.add(field, I18n.t('activerecord.errors.models.contact.attributes.email.email_smtp_check_error'))
+ when :mx
+ errors.add(field, I18n.t('activerecord.errors.models.contact.attributes.email.email_mx_check_error'))
+ when :regex
+ errors.add(field, I18n.t('activerecord.errors.models.contact.attributes.email.email_regex_check_error'))
+ end
+ end
+ # rubocop:enable Metrics/LineLength
end
diff --git a/app/models/concerns/invoice/book_keeping.rb b/app/models/concerns/invoice/book_keeping.rb
index 82e6506c9..03998cc50 100644
--- a/app/models/concerns/invoice/book_keeping.rb
+++ b/app/models/concerns/invoice/book_keeping.rb
@@ -1,34 +1,30 @@
-module Concerns
- module Invoice
- module BookKeeping
- extend ActiveSupport::Concern
+module Invoice::BookKeeping
+ extend ActiveSupport::Concern
- def as_directo_json
- invoice = ActiveSupport::JSON.decode(ActiveSupport::JSON.encode(self))
- invoice['customer'] = compose_directo_customer
- invoice['issue_date'] = issue_date.strftime('%Y-%m-%d')
- invoice['transaction_date'] = account_activity
- .bank_transaction&.paid_at&.strftime('%Y-%m-%d')
- invoice['language'] = buyer.language == 'en' ? 'ENG' : ''
- invoice['invoice_lines'] = compose_directo_product
+ def as_directo_json
+ invoice = ActiveSupport::JSON.decode(ActiveSupport::JSON.encode(self))
+ invoice['customer'] = compose_directo_customer
+ invoice['issue_date'] = issue_date.strftime('%Y-%m-%d')
+ invoice['transaction_date'] = account_activity
+ .bank_transaction&.paid_at&.strftime('%Y-%m-%d')
+ invoice['language'] = buyer.language == 'en' ? 'ENG' : ''
+ invoice['invoice_lines'] = compose_directo_product
- invoice
- end
+ invoice
+ end
- def compose_directo_product
- [{ 'product_id': Setting.directo_receipt_product_name, 'description': order,
- 'quantity': 1, 'price': ActionController::Base.helpers.number_with_precision(
- subtotal, precision: 2, separator: '.'
- ) }].as_json
- end
+ def compose_directo_product
+ [{ 'product_id': Setting.directo_receipt_product_name, 'description': order,
+ 'quantity': 1, 'price': ActionController::Base.helpers.number_with_precision(
+ subtotal, precision: 2, separator: '.'
+ ) }].as_json
+ end
- def compose_directo_customer
- {
- 'code': buyer.accounting_customer_code,
- 'destination': buyer_country_code,
- 'vat_reg_no': buyer_vat_no,
- }.as_json
- end
- end
+ def compose_directo_customer
+ {
+ 'code': buyer.accounting_customer_code,
+ 'destination': buyer_country_code,
+ 'vat_reg_no': buyer_vat_no,
+ }.as_json
end
end
diff --git a/app/models/concerns/invoice/cancellable.rb b/app/models/concerns/invoice/cancellable.rb
index 2eb0f8e2e..0374c9d2a 100644
--- a/app/models/concerns/invoice/cancellable.rb
+++ b/app/models/concerns/invoice/cancellable.rb
@@ -1,28 +1,24 @@
-module Concerns
- module Invoice
- module Cancellable
- extend ActiveSupport::Concern
+module Invoice::Cancellable
+ extend ActiveSupport::Concern
- included do
- scope :non_cancelled, -> { where(cancelled_at: nil) }
- end
+ included do
+ scope :non_cancelled, -> { where(cancelled_at: nil) }
+ end
- def cancellable?
- unpaid? && not_cancelled?
- end
+ def cancellable?
+ unpaid? && not_cancelled?
+ end
- def cancel
- raise 'Invoice cannot be cancelled' unless cancellable?
- update!(cancelled_at: Time.zone.now)
- end
+ def cancel
+ raise 'Invoice cannot be cancelled' unless cancellable?
+ update!(cancelled_at: Time.zone.now)
+ end
- def cancelled?
- cancelled_at
- end
+ def cancelled?
+ cancelled_at
+ end
- def not_cancelled?
- !cancelled?
- end
- end
+ def not_cancelled?
+ !cancelled?
end
end
diff --git a/app/models/concerns/invoice/payable.rb b/app/models/concerns/invoice/payable.rb
index 1a1c3e269..ad91b886e 100644
--- a/app/models/concerns/invoice/payable.rb
+++ b/app/models/concerns/invoice/payable.rb
@@ -1,28 +1,24 @@
-module Concerns
- module Invoice
- module Payable
- extend ActiveSupport::Concern
+module Invoice::Payable
+ extend ActiveSupport::Concern
- included do
- scope :unpaid, -> { where('id NOT IN (SELECT invoice_id FROM account_activities WHERE' \
- ' invoice_id IS NOT NULL)') }
- end
+ included do
+ scope :unpaid, -> { where('id NOT IN (SELECT invoice_id FROM account_activities WHERE' \
+ ' invoice_id IS NOT NULL)') }
+ end
- def payable?
- unpaid? && not_cancelled?
- end
+ def payable?
+ unpaid? && not_cancelled?
+ end
- def paid?
- account_activity
- end
+ def paid?
+ account_activity
+ end
- def receipt_date
- account_activity.created_at.to_date
- end
+ def receipt_date
+ account_activity.created_at.to_date
+ end
- def unpaid?
- !paid?
- end
- end
+ def unpaid?
+ !paid?
end
end
diff --git a/app/models/concerns/registrar/book_keeping.rb b/app/models/concerns/registrar/book_keeping.rb
index 60b9c2b1a..d8a7c2e72 100644
--- a/app/models/concerns/registrar/book_keeping.rb
+++ b/app/models/concerns/registrar/book_keeping.rb
@@ -1,128 +1,124 @@
-module Concerns
- module Registrar
- module BookKeeping
- extend ActiveSupport::Concern
+module Registrar::BookKeeping
+ extend ActiveSupport::Concern
- DOMAIN_TO_PRODUCT = { 'ee': '01EE', 'com.ee': '02COM', 'pri.ee': '03PRI',
- 'fie.ee': '04FIE', 'med.ee': '05MED' }.freeze
+ DOMAIN_TO_PRODUCT = { 'ee': '01EE', 'com.ee': '02COM', 'pri.ee': '03PRI',
+ 'fie.ee': '04FIE', 'med.ee': '05MED' }.freeze
- def monthly_summary(month:)
- activities = monthly_activites(month)
- return unless activities.any?
+ def monthly_summary(month:)
+ activities = monthly_activites(month)
+ return unless activities.any?
- invoice = {
- 'number': 1,
- 'customer': compose_directo_customer,
- 'language': language == 'en' ? 'ENG' : '', 'currency': activities.first.currency,
- 'date': month.end_of_month.strftime('%Y-%m-%d')
- }.as_json
+ invoice = {
+ 'number': 1,
+ 'customer': compose_directo_customer,
+ 'language': language == 'en' ? 'ENG' : '', 'currency': activities.first.currency,
+ 'date': month.end_of_month.strftime('%Y-%m-%d')
+ }.as_json
- invoice['invoice_lines'] = prepare_invoice_lines(month: month, activities: activities)
+ invoice['invoice_lines'] = prepare_invoice_lines(month: month, activities: activities)
- invoice
- end
+ invoice
+ end
- def prepare_invoice_lines(month:, activities:)
- lines = []
+ def prepare_invoice_lines(month:, activities:)
+ lines = []
- lines << { 'description': title_for_summary(month) }
- activities.each do |activity|
- fetch_invoice_lines(activity, lines)
- end
- lines << prepayment_for_all(lines)
+ lines << { 'description': title_for_summary(month) }
+ activities.each do |activity|
+ fetch_invoice_lines(activity, lines)
+ end
+ lines << prepayment_for_all(lines)
- lines.as_json
- end
+ lines.as_json
+ end
- def title_for_summary(date)
- I18n.with_locale(language == 'en' ? 'en' : 'et') do
- I18n.t('registrar.monthly_summary_title', date: I18n.l(date, format: '%B %Y'))
- end
- end
-
- def fetch_invoice_lines(activity, lines)
- price = load_price(activity)
- if price.duration.include? 'year'
- price.duration.to_i.times do |duration|
- lines << new_monthly_invoice_line(activity: activity, duration: duration + 1).as_json
- end
- else
- lines << new_monthly_invoice_line(activity: activity).as_json
- end
- end
-
- def monthly_activites(month)
- AccountActivity.where(account_id: account_ids)
- .where(created_at: month.beginning_of_month..month.end_of_month)
- .where(activity_type: [AccountActivity::CREATE, AccountActivity::RENEW])
- end
-
- def new_monthly_invoice_line(activity:, duration: nil)
- price = load_price(activity)
- line = {
- 'product_id': DOMAIN_TO_PRODUCT[price.zone_name.to_sym],
- 'quantity': 1,
- 'unit': language == 'en' ? 'pc' : 'tk',
- }
-
- finalize_invoice_line(line, price: price, duration: duration, activity: activity)
- end
-
- def finalize_invoice_line(line, price:, activity:, duration:)
- yearly = price.duration.include?('year')
-
- line['price'] = yearly ? (price.price.amount / price.duration.to_i) : price.price.amount
- line['description'] = description_in_language(price: price, yearly: yearly)
-
- if duration.present?
- add_product_timeframe(line: line, activity: activity, duration: duration) if duration > 1
- end
-
- line
- end
-
- def add_product_timeframe(line:, activity:, duration:)
- create_time = activity.created_at
- line['start_date'] = (create_time + (duration - 1).year).end_of_month.strftime('%Y-%m-%d')
- line['end_date'] = (create_time + (duration - 1).year + 1).end_of_month.strftime('%Y-%m-%d')
- end
-
- def description_in_language(price:, yearly:)
- timeframe_string = yearly ? 'yearly' : 'monthly'
- locale_string = "registrar.invoice_#{timeframe_string}_product_description"
-
- I18n.with_locale(language == 'en' ? 'en' : 'et') do
- I18n.t(locale_string, tld: ".#{price.zone_name}", length: price.duration.to_i)
- end
- end
-
- def prepayment_for_all(lines)
- total = 0
- en = language == 'en'
- lines.each { |l| total += l['quantity'].to_f * l['price'].to_f }
- {
- 'product_id': Setting.directo_receipt_product_name,
- 'description': en ? 'Domains prepayment' : 'Domeenide ettemaks',
- 'quantity': -1,
- 'price': total,
- 'unit': en ? 'pc' : 'tk',
- }
- end
-
- def compose_directo_customer
- {
- 'code': accounting_customer_code,
- 'destination': address_country_code,
- 'vat_reg_no': vat_no,
- }.as_json
- end
-
- def load_price(account_activity)
- @pricelists ||= {}
- return @pricelists[account_activity.price_id] if @pricelists.key? account_activity.price_id
-
- @pricelists[account_activity.price_id] = account_activity.price
- end
+ def title_for_summary(date)
+ I18n.with_locale(language == 'en' ? 'en' : 'et') do
+ I18n.t('registrar.monthly_summary_title', date: I18n.l(date, format: '%B %Y'))
end
end
+
+ def fetch_invoice_lines(activity, lines)
+ price = load_price(activity)
+ if price.duration.include? 'year'
+ price.duration.to_i.times do |duration|
+ lines << new_monthly_invoice_line(activity: activity, duration: duration + 1).as_json
+ end
+ else
+ lines << new_monthly_invoice_line(activity: activity).as_json
+ end
+ end
+
+ def monthly_activites(month)
+ AccountActivity.where(account_id: account_ids)
+ .where(created_at: month.beginning_of_month..month.end_of_month)
+ .where(activity_type: [AccountActivity::CREATE, AccountActivity::RENEW])
+ end
+
+ def new_monthly_invoice_line(activity:, duration: nil)
+ price = load_price(activity)
+ line = {
+ 'product_id': DOMAIN_TO_PRODUCT[price.zone_name.to_sym],
+ 'quantity': 1,
+ 'unit': language == 'en' ? 'pc' : 'tk',
+ }
+
+ finalize_invoice_line(line, price: price, duration: duration, activity: activity)
+ end
+
+ def finalize_invoice_line(line, price:, activity:, duration:)
+ yearly = price.duration.include?('year')
+
+ line['price'] = yearly ? (price.price.amount / price.duration.to_i) : price.price.amount
+ line['description'] = description_in_language(price: price, yearly: yearly)
+
+ if duration.present?
+ add_product_timeframe(line: line, activity: activity, duration: duration) if duration > 1
+ end
+
+ line
+ end
+
+ def add_product_timeframe(line:, activity:, duration:)
+ create_time = activity.created_at
+ line['start_date'] = (create_time + (duration - 1).year).end_of_month.strftime('%Y-%m-%d')
+ line['end_date'] = (create_time + (duration - 1).year + 1).end_of_month.strftime('%Y-%m-%d')
+ end
+
+ def description_in_language(price:, yearly:)
+ timeframe_string = yearly ? 'yearly' : 'monthly'
+ locale_string = "registrar.invoice_#{timeframe_string}_product_description"
+
+ I18n.with_locale(language == 'en' ? 'en' : 'et') do
+ I18n.t(locale_string, tld: ".#{price.zone_name}", length: price.duration.to_i)
+ end
+ end
+
+ def prepayment_for_all(lines)
+ total = 0
+ en = language == 'en'
+ lines.each { |l| total += l['quantity'].to_f * l['price'].to_f }
+ {
+ 'product_id': Setting.directo_receipt_product_name,
+ 'description': en ? 'Domains prepayment' : 'Domeenide ettemaks',
+ 'quantity': -1,
+ 'price': total,
+ 'unit': en ? 'pc' : 'tk',
+ }
+ end
+
+ def compose_directo_customer
+ {
+ 'code': accounting_customer_code,
+ 'destination': address_country_code,
+ 'vat_reg_no': vat_no,
+ }.as_json
+ end
+
+ def load_price(account_activity)
+ @pricelists ||= {}
+ return @pricelists[account_activity.price_id] if @pricelists.key? account_activity.price_id
+
+ @pricelists[account_activity.price_id] = account_activity.price
+ end
end
diff --git a/app/models/concerns/registrar/legal_doc.rb b/app/models/concerns/registrar/legal_doc.rb
index 2f21f6637..294c9487d 100644
--- a/app/models/concerns/registrar/legal_doc.rb
+++ b/app/models/concerns/registrar/legal_doc.rb
@@ -1,16 +1,12 @@
-module Concerns
- module Registrar
- module LegalDoc
- extend ActiveSupport::Concern
+module Registrar::LegalDoc
+ extend ActiveSupport::Concern
- def legaldoc_mandatory?
- !legaldoc_not_mandatory?
- end
+ def legaldoc_mandatory?
+ !legaldoc_not_mandatory?
+ end
- def legaldoc_not_mandatory?
- setting = Setting.legal_document_is_mandatory
- legaldoc_optout || !setting
- end
- end
+ def legaldoc_not_mandatory?
+ setting = Setting.legal_document_is_mandatory
+ legaldoc_optout || !setting
end
end
diff --git a/app/models/concerns/versions.rb b/app/models/concerns/versions.rb
index 033ebe52a..a1c872b56 100644
--- a/app/models/concerns/versions.rb
+++ b/app/models/concerns/versions.rb
@@ -7,10 +7,10 @@ module Versions
attr_accessor :version_loader
if WITH_CHILDREN.include?(model_name.name)
- has_paper_trail versions: { class_name: "#{model_name}Version" },
+ has_paper_trail versions: { class_name: "Version::#{model_name}Version" },
meta: { children: :children_log }
else
- has_paper_trail versions: { class_name: "#{model_name}Version" }
+ has_paper_trail versions: { class_name: "Version::#{model_name}Version" }
end
# add creator and updator
diff --git a/app/models/concerns/zone/whois_queryable.rb b/app/models/concerns/zone/whois_queryable.rb
index c79700582..e4a6c1314 100644
--- a/app/models/concerns/zone/whois_queryable.rb
+++ b/app/models/concerns/zone/whois_queryable.rb
@@ -1,74 +1,70 @@
-module Concerns
- module Zone
- module WhoisQueryable
- extend ActiveSupport::Concern
+module Zone::WhoisQueryable
+ extend ActiveSupport::Concern
- included do
- after_save :update_whois_record, if: :subzone?
- after_destroy :update_whois_record
- end
+ included do
+ after_save :update_whois_record, if: :subzone?
+ after_destroy :update_whois_record
+ end
- def subzone?
- origin.include? '.'
- end
+ def subzone?
+ origin.include? '.'
+ end
- def update_whois_record
- UpdateWhoisRecordJob.enqueue origin, 'zone'
- end
+ def update_whois_record
+ UpdateWhoisRecordJob.enqueue origin, 'zone'
+ end
- def generate_data
- wr = Whois::Record.find_or_initialize_by(name: origin)
- wr.json = generate_json
- wr.save
- end
+ def generate_data
+ wr = Whois::Record.find_or_initialize_by(name: origin)
+ wr.json = generate_json
+ wr.save
+ end
- def generate_json
- data = {}.with_indifferent_access
- [domain_vars, registrar_vars, registrant_vars].each do |h|
- data.merge!(h)
- end
-
- data
- end
-
- # Take note - since this concern only used to zone whois queries, dnssec keys are set to
- # empty array
- def domain_vars
- { disclaimer: Setting.registry_whois_disclaimer, name: origin,
- registered: created_at.try(:to_s, :iso8601), status: ['ok (paid and in zone)'],
- changed: updated_at.try(:to_s, :iso8601), email: Setting.registry_email,
- admin_contacts: [contact_vars], tech_contacts: [contact_vars],
- nameservers: nameserver_vars, dnssec_keys: [], dnssec_changed: nil }
- end
-
- def registrar_vars
- { registrar: Setting.registry_juridical_name, registrar_website: Setting.registry_url,
- registrar_phone: Setting.registry_phone }
- end
-
- def registrant_vars
- { registrant: Setting.registry_juridical_name, registrant_reg_no: Setting.registry_reg_no,
- registrant_ident_country_code: Setting.registry_country_code, registrant_kind: 'org',
- registrant_disclosed_attributes: %w[name email] }
- end
-
- def contact_vars
- { name: Setting.registry_invoice_contact, email: Setting.registry_email,
- disclosed_attributes: %w[name email] }
- end
-
- def nameserver_vars
- vars = []
- return vars unless ns_records
-
- parsed_ns = ns_records.gsub("\r", '').gsub("\n", '')
- parsed_ns.split("#{origin}. IN NS ").each do |ns|
- ns.delete_suffix! '.'
- vars << ns if ns.match? Nameserver::HOSTNAME_REGEXP
- end
-
- vars
- end
+ def generate_json
+ data = {}.with_indifferent_access
+ [domain_vars, registrar_vars, registrant_vars].each do |h|
+ data.merge!(h)
end
+
+ data
+ end
+
+ # Take note - since this concern only used to zone whois queries, dnssec keys are set to
+ # empty array
+ def domain_vars
+ { disclaimer: Setting.registry_whois_disclaimer, name: origin,
+ registered: created_at.try(:to_s, :iso8601), status: ['ok (paid and in zone)'],
+ changed: updated_at.try(:to_s, :iso8601), email: Setting.registry_email,
+ admin_contacts: [contact_vars], tech_contacts: [contact_vars],
+ nameservers: nameserver_vars, dnssec_keys: [], dnssec_changed: nil }
+ end
+
+ def registrar_vars
+ { registrar: Setting.registry_juridical_name, registrar_website: Setting.registry_url,
+ registrar_phone: Setting.registry_phone }
+ end
+
+ def registrant_vars
+ { registrant: Setting.registry_juridical_name, registrant_reg_no: Setting.registry_reg_no,
+ registrant_ident_country_code: Setting.registry_country_code, registrant_kind: 'org',
+ registrant_disclosed_attributes: %w[name email] }
+ end
+
+ def contact_vars
+ { name: Setting.registry_invoice_contact, email: Setting.registry_email,
+ disclosed_attributes: %w[name email] }
+ end
+
+ def nameserver_vars
+ vars = []
+ return vars unless ns_records
+
+ parsed_ns = ns_records.gsub("\r", '').gsub("\n", '')
+ parsed_ns.split("#{origin}. IN NS ").each do |ns|
+ ns.delete_suffix! '.'
+ vars << ns if ns.match? Nameserver::HOSTNAME_REGEXP
+ end
+
+ vars
end
end
diff --git a/app/models/contact.rb b/app/models/contact.rb
index e30312b4a..61d49c10c 100644
--- a/app/models/contact.rb
+++ b/app/models/contact.rb
@@ -4,11 +4,11 @@ class Contact < ApplicationRecord
include Versions # version/contact_version.rb
include EppErrors
include UserEvents
- include Concerns::Contact::Transferable
- include Concerns::Contact::Identical
- include Concerns::Contact::Disclosable
- include Concerns::Contact::Archivable
- include Concerns::EmailVerifable
+ include Contact::Transferable
+ include Contact::Identical
+ include Contact::Disclosable
+ include Contact::Archivable
+ include EmailVerifable
belongs_to :original, class_name: self.name
belongs_to :registrar, required: true
@@ -360,9 +360,11 @@ class Contact < ApplicationRecord
@desc
end
+ # Limits returned objects to 11
def related_domains
- a = related_domain_descriptions
- a.keys.map { |d| { name: d, id: a[d][:id], roles: a[d][:roles] } }
+ ids = DomainContact.select(:domain_id).where(contact_id: id).limit(11).map(&:domain_id).uniq
+ res = Domain.where(id: ids).or(Domain.where(registrant_id: id)).select(:name, :uuid).limit(11)
+ res.pluck(:name, :uuid).map { |name, id| { name: name, id: id } }
end
def status_notes_array=(notes)
diff --git a/app/models/concerns/contact/transferable.rb b/app/models/contact/transferable.rb
similarity index 91%
rename from app/models/concerns/contact/transferable.rb
rename to app/models/contact/transferable.rb
index 987933a8d..b10a3acfc 100644
--- a/app/models/concerns/contact/transferable.rb
+++ b/app/models/contact/transferable.rb
@@ -1,4 +1,4 @@
-module Concerns::Contact::Transferable
+module Contact::Transferable
extend ActiveSupport::Concern
included do
@@ -9,7 +9,7 @@ module Concerns::Contact::Transferable
def transfer(new_registrar)
return identical(new_registrar) if identical(new_registrar)
- new_contact = self.dup
+ new_contact = dup
new_contact.registrar = new_registrar
new_contact.original = self
new_contact.code = nil
diff --git a/app/models/contact_request.rb b/app/models/contact_request.rb
new file mode 100644
index 000000000..f4c6db716
--- /dev/null
+++ b/app/models/contact_request.rb
@@ -0,0 +1,41 @@
+class ContactRequest < ApplicationRecord
+ establish_connection :"whois_#{Rails.env}"
+ self.table_name = 'contact_requests'
+
+ STATUS_NEW = 'new'.freeze
+ STATUS_CONFIRMED = 'confirmed'.freeze
+ STATUS_SENT = 'sent'.freeze
+ STATUSES = [STATUS_NEW, STATUS_CONFIRMED, STATUS_SENT].freeze
+
+ validates :whois_record_id, presence: true
+ validates :email, presence: true
+ validates :name, presence: true
+ validates :status, inclusion: { in: STATUSES }
+
+ attr_readonly :secret,
+ :valid_to
+
+ def self.save_record(params)
+ contact_request = new(params)
+ contact_request.secret = create_random_secret
+ contact_request.valid_to = set_valid_to_24_hours_from_now
+ contact_request.status = STATUS_NEW
+ contact_request.save!
+ contact_request
+ end
+
+ def update_record(params)
+ self.status = params['status'] if params['status']
+ self.ip_address = params['ip'] if params['ip']
+ self.message_id = params['ip'] if params['message_id']
+ save!
+ end
+
+ def self.create_random_secret
+ SecureRandom.hex(64)
+ end
+
+ def self.set_valid_to_24_hours_from_now
+ (Time.zone.now + 24.hours)
+ end
+end
diff --git a/app/models/dns/domain_name.rb b/app/models/dns/domain_name.rb
index c1af4d5e7..1e9cd6587 100644
--- a/app/models/dns/domain_name.rb
+++ b/app/models/dns/domain_name.rb
@@ -36,6 +36,7 @@ module DNS
auction = Auction.new
auction.domain = name
auction.start
+ ToStdout.msg "Created the auction: #{auction.inspect}"
update_whois_from_auction(auction)
end
@@ -100,7 +101,8 @@ module DNS
whois_record = Whois::Record.find_or_create_by!(name: name) do |record|
record.json = {}
end
-
+ ToStdout.msg "Starting to update WHOIS record #{whois_record.inspect}\n\n"\
+ "from auction #{auction.inspect}"
whois_record.update_from_auction(auction)
end
end
diff --git a/app/models/dns/zone.rb b/app/models/dns/zone.rb
index 31749d952..6e18b84bb 100644
--- a/app/models/dns/zone.rb
+++ b/app/models/dns/zone.rb
@@ -5,7 +5,7 @@ module DNS
validates :origin, :ttl, :refresh, :retry, :expire, :minimum_ttl, :email, :master_nameserver, presence: true
validates :ttl, :refresh, :retry, :expire, :minimum_ttl, numericality: { only_integer: true }
validates :origin, uniqueness: true
- include Concerns::Zone::WhoisQueryable
+ include ::Zone::WhoisQueryable
before_destroy do
throw(:abort) if used?
diff --git a/app/models/domain.rb b/app/models/domain.rb
index 88fa94fbc..657688016 100644
--- a/app/models/domain.rb
+++ b/app/models/domain.rb
@@ -1,15 +1,16 @@
class Domain < ApplicationRecord
include UserEvents
include Versions # version/domain_version.rb
- include Concerns::Domain::Expirable
- include Concerns::Domain::Activatable
- include Concerns::Domain::ForceDelete
- include Concerns::Domain::Discardable
- include Concerns::Domain::Deletable
- include Concerns::Domain::Transferable
- include Concerns::Domain::RegistryLockable
- include Concerns::Domain::Releasable
- include Concerns::Domain::Disputable
+ include Domain::Expirable
+ include Domain::Activatable
+ include Domain::ForceDelete
+ include Domain::Discardable
+ include Domain::Deletable
+ include Domain::Transferable
+ include Domain::RegistryLockable
+ include Domain::Releasable
+ include Domain::Disputable
+ include Domain::BulkUpdatable
attr_accessor :roles
@@ -78,7 +79,7 @@ class Domain < ApplicationRecord
true
end
- after_commit :update_whois_record, unless: -> { domain_name.at_auction? }
+ after_commit :update_whois_record
after_create :update_reserved_domains
def update_reserved_domains
@@ -106,13 +107,13 @@ class Domain < ApplicationRecord
validate :status_is_consistant
def status_is_consistant
- has_error = (statuses.include?(DomainStatus::SERVER_HOLD) && statuses.include?(DomainStatus::SERVER_MANUAL_INZONE))
- unless has_error
- if (statuses & [DomainStatus::PENDING_DELETE_CONFIRMATION, DomainStatus::PENDING_DELETE, DomainStatus::FORCE_DELETE]).any?
- has_error = statuses.include? DomainStatus::SERVER_DELETE_PROHIBITED
- end
+ has_error = (hold_status? && statuses.include?(DomainStatus::SERVER_MANUAL_INZONE))
+ unless has_error
+ if (statuses & DELETE_STATUSES).any?
+ has_error = statuses.include? DomainStatus::SERVER_DELETE_PROHIBITED
end
- errors.add(:domains, I18n.t(:object_status_prohibits_operation)) if has_error
+ end
+ errors.add(:domains, I18n.t(:object_status_prohibits_operation)) if has_error
end
attr_accessor :is_admin
@@ -197,6 +198,23 @@ class Domain < ApplicationRecord
Setting.nameserver_required
end
+ def registrant_user_admin_registrant_domains(registrant_user)
+ companies = Contact.registrant_user_company_contacts(registrant_user)
+ from(
+ "(#{registrant_user_administered_domains(registrant_user).to_sql} UNION " \
+ "#{registrant_user_company_registrant(companies).to_sql} UNION " \
+ "#{registrant_user_domains_company(companies, except_tech: true).to_sql}) AS domains"
+ )
+ end
+
+ def registrant_user_direct_admin_registrant_domains(registrant_user)
+ from(
+ "(#{registrant_user_direct_domains_by_registrant(registrant_user).to_sql} UNION " \
+ "#{registrant_user_direct_domains_by_contact(registrant_user,
+ except_tech: true).to_sql}) AS domains"
+ )
+ end
+
def registrant_user_domains(registrant_user)
from(
"(#{registrant_user_domains_by_registrant(registrant_user).to_sql} UNION " \
@@ -246,16 +264,20 @@ class Domain < ApplicationRecord
where(registrant: registrant_user.direct_contacts)
end
- def registrant_user_direct_domains_by_contact(registrant_user)
- joins(:domain_contacts).where(domain_contacts: { contact_id: registrant_user.direct_contacts })
+ def registrant_user_direct_domains_by_contact(registrant_user, except_tech: false)
+ request = { contact_id: registrant_user.direct_contacts }
+ request[:type] = [AdminDomainContact.name] if except_tech
+ joins(:domain_contacts).where(domain_contacts: request)
end
def registrant_user_company_registrant(companies)
where(registrant: companies)
end
- def registrant_user_domains_company(companies)
- joins(:domain_contacts).where(domain_contacts: { contact: companies })
+ def registrant_user_domains_company(companies, except_tech: false)
+ request = { contact: companies }
+ request[:type] = [AdminDomainContact.name] if except_tech
+ joins(:domain_contacts).where(domain_contacts: request)
end
end
diff --git a/app/models/domain_status.rb b/app/models/domain_status.rb
index bf0ae2a51..30161c076 100644
--- a/app/models/domain_status.rb
+++ b/app/models/domain_status.rb
@@ -109,14 +109,12 @@ class DomainStatus < ApplicationRecord
DELETE_PROHIBIT_STATES = [
DomainStatus::CLIENT_DELETE_PROHIBITED,
DomainStatus::SERVER_DELETE_PROHIBITED,
- DomainStatus::CLIENT_UPDATE_PROHIBITED,
- DomainStatus::SERVER_UPDATE_PROHIBITED,
DomainStatus::PENDING_CREATE,
DomainStatus::PENDING_RENEW,
DomainStatus::PENDING_TRANSFER,
DomainStatus::PENDING_UPDATE,
DomainStatus::PENDING_DELETE
- ]
+ ].freeze
def epp_code_map
{
diff --git a/app/models/epp/contact.rb b/app/models/epp/contact.rb
index 50ebac065..4cd876d5f 100644
--- a/app/models/epp/contact.rb
+++ b/app/models/epp/contact.rb
@@ -42,17 +42,12 @@ class Epp::Contact < Contact
)
end
- def check_availability(codes)
+ def check_availability(codes, reg:)
codes = [codes] if codes.is_a?(String)
-
res = []
- codes.each do |x|
- contact = find_by_epp_code(x)
- if contact
- res << { code: contact.code, avail: 0, reason: 'in use' }
- else
- res << { code: x, avail: 1 }
- end
+ codes.map { |c| c.include?(':') ? c : "#{reg}:#{c}" }.map { |c| c.strip.upcase }.each do |x|
+ c = find_by_epp_code(x)
+ res << (c ? { code: c.code, avail: 0, reason: 'in use' } : { code: x, avail: 1 })
end
res
@@ -87,8 +82,11 @@ class Epp::Contact < Contact
'2302' => [ # Object exists
[:code, :epp_id_taken]
],
+ '2304' => [ # Status prohibits operation
+ [:statuses, :delete_prohibited],
+ ],
'2305' => [ # Association exists
- [:domains, :exist]
+ [:domains, :exist],
]
}
end
diff --git a/app/models/epp/domain.rb b/app/models/epp/domain.rb
index 6a51b4cfe..f3da8d533 100644
--- a/app/models/epp/domain.rb
+++ b/app/models/epp/domain.rb
@@ -162,6 +162,9 @@ class Epp::Domain < Domain
at[:admin_domain_contacts_attributes] = admin_domain_contacts_attrs(frame, action)
at[:tech_domain_contacts_attributes] = tech_domain_contacts_attrs(frame, action)
+ check_for_same_contacts(at[:admin_domain_contacts_attributes], 'admin')
+ check_for_same_contacts(at[:tech_domain_contacts_attributes], 'tech')
+
pw = frame.css('authInfo > pw').text
at[:transfer_code] = pw if pw.present?
@@ -176,6 +179,11 @@ class Epp::Domain < Domain
at
end
+ def check_for_same_contacts(contacts, contact_type)
+ return unless contacts.uniq.count != contacts.count
+
+ add_epp_error('2306', contact_type, nil, %i[domain_contacts invalid])
+ end
# Adding legal doc to domain and
# if something goes wrong - raise Rollback error
@@ -312,6 +320,7 @@ class Epp::Domain < Domain
keys = []
return keys if frame.blank?
inf_data = DnsSecKeys.new(frame)
+ add_epp_error('2005', nil, nil, %i[dnskeys invalid]) if not_base64?(inf_data)
if action == 'rem' &&
frame.css('rem > all').first.try(:text) == 'true'
@@ -333,6 +342,16 @@ class Epp::Domain < Domain
errors.any? ? [] : keys
end
+ def not_base64?(inf_data)
+ inf_data.key_data.any? do |key|
+ value = key[:public_key]
+
+ !value.is_a?(String) || Base64.strict_encode64(Base64.strict_decode64(value)) != value
+ end
+ rescue ArgumentError
+ true
+ end
+
class DnsSecKeys
def initialize(frame)
@key_data = []
@@ -381,7 +400,7 @@ class Epp::Domain < Domain
def key_data_from(frame)
xm_copy frame, KEY_INTERFACE
- end
+ end
def ds_data_from(frame)
frame.css('dsData').each do |ds_data|
@@ -446,7 +465,7 @@ class Epp::Domain < Domain
def update(frame, current_user, verify = true)
return super if frame.blank?
- if discarded?
+ if discarded? || statuses_blocks_update?
add_epp_error('2304', nil, nil, 'Object status prohibits operation')
return
end
@@ -476,7 +495,7 @@ class Epp::Domain < Domain
registrant_verification_needed = false
# registrant block may not be present, so we need this to rule out false positives
if frame.css('registrant').text.present?
- registrant_verification_needed = (registrant.code != frame.css('registrant').text)
+ registrant_verification_needed = verification_needed?(code: frame.css('registrant').text)
end
if registrant_verification_needed && disputed?
@@ -520,6 +539,7 @@ class Epp::Domain < Domain
def attach_legal_document(legal_document_data)
return unless legal_document_data
+ return unless legal_document_data[:body]
return if legal_document_data[:body].starts_with?(ENV['legal_documents_dir'])
legal_documents.create(
@@ -592,7 +612,6 @@ class Epp::Domain < Domain
statuses.delete(DomainStatus::SERVER_HOLD)
statuses.delete(DomainStatus::EXPIRED)
- statuses.delete(DomainStatus::SERVER_UPDATE_PROHIBITED)
cancel_pending_delete
save
@@ -778,4 +797,13 @@ class Epp::Domain < Domain
result
end
end
+
+ private
+
+ def verification_needed?(code:)
+ new_registrant = Registrant.find_by(code: code)
+ return false if new_registrant.try(:identical_to?, registrant)
+
+ registrant.code != code
+ end
end
diff --git a/app/models/invoice.rb b/app/models/invoice.rb
index fb625f7b9..73ed88567 100644
--- a/app/models/invoice.rb
+++ b/app/models/invoice.rb
@@ -1,8 +1,8 @@
class Invoice < ApplicationRecord
include Versions
- include Concerns::Invoice::Cancellable
- include Concerns::Invoice::Payable
- include Concerns::Invoice::BookKeeping
+ include Invoice::Cancellable
+ include Invoice::Payable
+ include Invoice::BookKeeping
belongs_to :buyer, class_name: 'Registrar'
has_one :account_activity
@@ -34,7 +34,7 @@ class Invoice < ApplicationRecord
before_create :calculate_total, unless: :total?
before_create :apply_default_buyer_vat_no, unless: :buyer_vat_no?
- attribute :vat_rate, ::Type::VATRate.new
+ attribute :vat_rate, ::Type::VatRate.new
def set_invoice_number
last_no = Invoice.order(number: :desc).limit(1).pluck(:number).first
diff --git a/app/models/legal_document.rb b/app/models/legal_document.rb
index e4aab5869..377a9fdde 100644
--- a/app/models/legal_document.rb
+++ b/app/models/legal_document.rb
@@ -82,7 +82,7 @@ class LegalDocument < ApplicationRecord
end
end
- contact_ids = DomainVersion.where(item_id: orig_legal.documentable_id).distinct.
+ contact_ids = Version::DomainVersion.where(item_id: orig_legal.documentable_id).distinct.
pluck("object->>'registrant_id'", "object_changes->>'registrant_id'",
"children->>'tech_contacts'", "children->>'admin_contacts'").flatten.uniq
contact_ids = contact_ids.map{|id|
diff --git a/app/models/notification.rb b/app/models/notification.rb
index e83b2c9da..07e824367 100644
--- a/app/models/notification.rb
+++ b/app/models/notification.rb
@@ -25,6 +25,10 @@ class Notification < ApplicationRecord
''
end
+ def registry_lock?
+ text.include?('has been locked') || text.include?('has been unlocked')
+ end
+
private
def set_defaults
diff --git a/app/models/registrant_user.rb b/app/models/registrant_user.rb
index aa41ccff8..f7e85c5af 100644
--- a/app/models/registrant_user.rb
+++ b/app/models/registrant_user.rb
@@ -9,7 +9,7 @@ class RegistrantUser < User
delegate :can?, :cannot?, to: :ability
def ident
- registrant_ident.to_s.split('-').last
+ registrant_ident.to_s[3..]
end
def country
@@ -18,6 +18,8 @@ class RegistrantUser < User
end
def companies(company_register = CompanyRegister::Client.new)
+ return [] if ident.include?('-')
+
company_register.representation_rights(citizen_personal_code: ident,
citizen_country_code: country.alpha3)
end
@@ -30,11 +32,15 @@ class RegistrantUser < User
Contact.registrant_user_direct_contacts(self)
end
- def domains
+ def domains(admin: false)
+ return Domain.registrant_user_admin_registrant_domains(self) if admin
+
Domain.registrant_user_domains(self)
end
- def direct_domains
+ def direct_domains(admin: false)
+ return Domain.registrant_user_direct_admin_registrant_domains(self) if admin
+
Domain.registrant_user_direct_domains(self)
end
@@ -72,7 +78,7 @@ class RegistrantUser < User
return false unless user_data[:last_name]
user_data[:country_code] ||= 'EE'
- %i[ident country_code].each { |f| user_data[f].upcase! if user_data[f].is_a?(String) }
+ user_data[:country_code].upcase! if user_data[:country_code].is_a?(String)
find_or_create_by_user_data(user_data)
end
diff --git a/app/models/registrar.rb b/app/models/registrar.rb
index 168dfdca7..335fb9115 100644
--- a/app/models/registrar.rb
+++ b/app/models/registrar.rb
@@ -1,8 +1,8 @@
class Registrar < ApplicationRecord
include Versions # version/registrar_version.rb
- include Concerns::Registrar::BookKeeping
- include Concerns::EmailVerifable
- include Concerns::Registrar::LegalDoc
+ include Registrar::BookKeeping
+ include EmailVerifable
+ include Registrar::LegalDoc
has_many :domains, dependent: :restrict_with_error
has_many :contacts, dependent: :restrict_with_error
@@ -30,7 +30,7 @@ class Registrar < ApplicationRecord
validates :vat_rate, numericality: { greater_than_or_equal_to: 0, less_than: 100 },
allow_nil: true
- attribute :vat_rate, ::Type::VATRate.new
+ attribute :vat_rate, ::Type::VatRate.new
after_initialize :set_defaults
validate :correct_email_format, if: proc { |c| c.will_save_change_to_email? }
@@ -153,7 +153,7 @@ class Registrar < ApplicationRecord
puny = origin.domain.name_puny
next unless domains.include?(idn) || domains.include?(puny) || domains.empty?
- if origin.domain.nameservers.where(hostname: new_attributes[:hostname]).any?
+ if domain_not_updatable?(hostname: new_attributes[:hostname], domain: origin.domain)
failed_list << idn
next
end
@@ -202,6 +202,10 @@ class Registrar < ApplicationRecord
private
+ def domain_not_updatable?(hostname:, domain:)
+ domain.nameservers.where(hostname: hostname).any? || domain.bulk_update_prohibited?
+ end
+
def set_defaults
self.language = Setting.default_language unless language
end
diff --git a/app/models/tech_domain_contact.rb b/app/models/tech_domain_contact.rb
index 92799061c..20f21b6ed 100644
--- a/app/models/tech_domain_contact.rb
+++ b/app/models/tech_domain_contact.rb
@@ -6,7 +6,7 @@ class TechDomainContact < DomainContact
tech_contacts = where(contact: current_contact)
tech_contacts.each do |tech_contact|
- if tech_contact.domain.discarded?
+ if tech_contact.domain.bulk_update_prohibited?
skipped_domains << tech_contact.domain.name
next
end
@@ -18,7 +18,6 @@ class TechDomainContact < DomainContact
skipped_domains << tech_contact.domain.name
end
end
-
[affected_domains.sort, skipped_domains.sort]
end
end
diff --git a/app/models/type/vat_rate.rb b/app/models/type/vat_rate.rb
index 6a31e389b..142ae0559 100644
--- a/app/models/type/vat_rate.rb
+++ b/app/models/type/vat_rate.rb
@@ -1,5 +1,5 @@
module Type
- class VATRate < ActiveRecord::Type::Decimal
+ class VatRate < ActiveRecord::Type::Decimal
def deserialize(value)
super * 100 if value
end
diff --git a/app/models/version.rb b/app/models/version.rb
new file mode 100644
index 000000000..68770a5a1
--- /dev/null
+++ b/app/models/version.rb
@@ -0,0 +1 @@
+class Version; end
diff --git a/app/models/version/account_activity_version.rb b/app/models/version/account_activity_version.rb
index b742f7a63..17d8bc8a7 100644
--- a/app/models/version/account_activity_version.rb
+++ b/app/models/version/account_activity_version.rb
@@ -1,4 +1,4 @@
-class AccountActivityVersion < PaperTrail::Version
+class Version::AccountActivityVersion < PaperTrail::Version
self.table_name = :log_account_activities
self.sequence_name = :log_account_activities_id_seq
end
diff --git a/app/models/version/account_version.rb b/app/models/version/account_version.rb
index b68edd4a5..aca10d41f 100644
--- a/app/models/version/account_version.rb
+++ b/app/models/version/account_version.rb
@@ -1,4 +1,4 @@
-class AccountVersion < PaperTrail::Version
+class Version::AccountVersion < PaperTrail::Version
self.table_name = :log_accounts
self.sequence_name = :log_accounts_id_seq
end
diff --git a/app/models/version/action_version.rb b/app/models/version/action_version.rb
index bd23d7697..5ca6220b1 100644
--- a/app/models/version/action_version.rb
+++ b/app/models/version/action_version.rb
@@ -1,4 +1,4 @@
-class ActionVersion < PaperTrail::Version
+class Version::ActionVersion < PaperTrail::Version
self.table_name = :log_actions
self.sequence_name = :log_actions_id_seq
end
diff --git a/app/models/version/bank_statement_version.rb b/app/models/version/bank_statement_version.rb
index ae66f4efe..5a61da3af 100644
--- a/app/models/version/bank_statement_version.rb
+++ b/app/models/version/bank_statement_version.rb
@@ -1,4 +1,4 @@
-class BankStatementVersion < PaperTrail::Version
+class Version::BankStatementVersion < PaperTrail::Version
self.table_name = :log_bank_statements
self.sequence_name = :log_bank_statements_id_seq
end
diff --git a/app/models/version/bank_transaction_version.rb b/app/models/version/bank_transaction_version.rb
index 93e13be74..63c65e2b8 100644
--- a/app/models/version/bank_transaction_version.rb
+++ b/app/models/version/bank_transaction_version.rb
@@ -1,4 +1,4 @@
-class BankTransactionVersion < PaperTrail::Version
+class Version::BankTransactionVersion < PaperTrail::Version
self.table_name = :log_bank_transactions
self.sequence_name = :log_bank_transactions_id_seq
end
diff --git a/app/models/version/billing/price_version.rb b/app/models/version/billing/price_version.rb
index 7502c18e2..611405142 100644
--- a/app/models/version/billing/price_version.rb
+++ b/app/models/version/billing/price_version.rb
@@ -1,7 +1,4 @@
-module Billing
- class PriceVersion < PaperTrail::Version
- self.table_name = :log_prices
- self.sequence_name = :log_prices_id_seq
- end
+class Version::Billing::PriceVersion < PaperTrail::Version
+ self.table_name = :log_prices
+ self.sequence_name = :log_prices_id_seq
end
-
diff --git a/app/models/version/blocked_domain_version.rb b/app/models/version/blocked_domain_version.rb
index 82e6b30da..b511445c0 100644
--- a/app/models/version/blocked_domain_version.rb
+++ b/app/models/version/blocked_domain_version.rb
@@ -1,4 +1,4 @@
-class BlockedDomainVersion < PaperTrail::Version
+class Version::BlockedDomainVersion < PaperTrail::Version
self.table_name = :log_blocked_domains
self.sequence_name = :log_blocked_domains_id_seq
end
diff --git a/app/models/version/certificate_version.rb b/app/models/version/certificate_version.rb
index bcc89e62a..1edd03204 100644
--- a/app/models/version/certificate_version.rb
+++ b/app/models/version/certificate_version.rb
@@ -1,4 +1,4 @@
-class CertificateVersion < PaperTrail::Version
+class Version::CertificateVersion < PaperTrail::Version
self.table_name = :log_certificates
self.sequence_name = :log_certificates_id_seq
end
diff --git a/app/models/version/contact_version.rb b/app/models/version/contact_version.rb
index 781813302..6c5c70a99 100644
--- a/app/models/version/contact_version.rb
+++ b/app/models/version/contact_version.rb
@@ -1,7 +1,7 @@
-class ContactVersion < PaperTrail::Version
+class Version::ContactVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_contacts
self.sequence_name = :log_contacts_id_seq
-
+
# scope :deleted, -> { where(event: 'destroy') }
end
diff --git a/app/models/version/dnskey_version.rb b/app/models/version/dnskey_version.rb
index c50528e42..ea468194e 100644
--- a/app/models/version/dnskey_version.rb
+++ b/app/models/version/dnskey_version.rb
@@ -1,4 +1,4 @@
-class DnskeyVersion < PaperTrail::Version
+class Version::DnskeyVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_dnskeys
self.sequence_name = :log_dnskeys_id_seq
diff --git a/app/models/version/domain_contact_version.rb b/app/models/version/domain_contact_version.rb
index 234ff8d9e..d0e1954be 100644
--- a/app/models/version/domain_contact_version.rb
+++ b/app/models/version/domain_contact_version.rb
@@ -1,4 +1,4 @@
-class DomainContactVersion < PaperTrail::Version
+class Version::DomainContactVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_domain_contacts
self.sequence_name = :log_domain_contacts_id_seq
diff --git a/app/models/version/domain_version.rb b/app/models/version/domain_version.rb
index 27753960a..b2962d1ee 100644
--- a/app/models/version/domain_version.rb
+++ b/app/models/version/domain_version.rb
@@ -1,4 +1,4 @@
-class DomainVersion < PaperTrail::Version
+class Version::DomainVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_domains
diff --git a/app/models/version/invoice_item_version.rb b/app/models/version/invoice_item_version.rb
index ffdef5d3e..59a9db6ea 100644
--- a/app/models/version/invoice_item_version.rb
+++ b/app/models/version/invoice_item_version.rb
@@ -1,4 +1,4 @@
-class InvoiceItemVersion < PaperTrail::Version
+class Version::InvoiceItemVersion < PaperTrail::Version
self.table_name = :log_invoice_items
self.sequence_name = :log_invoice_items_id_seq
end
diff --git a/app/models/version/invoice_version.rb b/app/models/version/invoice_version.rb
index 0b98c873f..037ce7237 100644
--- a/app/models/version/invoice_version.rb
+++ b/app/models/version/invoice_version.rb
@@ -1,4 +1,4 @@
-class InvoiceVersion < PaperTrail::Version
+class Version::InvoiceVersion < PaperTrail::Version
self.table_name = :log_invoices
self.sequence_name = :log_invoices_id_seq
end
diff --git a/app/models/version/nameserver_version.rb b/app/models/version/nameserver_version.rb
index 01a02c93a..e4d3a8a0f 100644
--- a/app/models/version/nameserver_version.rb
+++ b/app/models/version/nameserver_version.rb
@@ -1,4 +1,4 @@
-class NameserverVersion < PaperTrail::Version
+class Version::NameserverVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_nameservers
self.sequence_name = :log_nameservers_id_seq
diff --git a/app/models/version/notification_version.rb b/app/models/version/notification_version.rb
index 0b66aabe5..a7eb31ee5 100644
--- a/app/models/version/notification_version.rb
+++ b/app/models/version/notification_version.rb
@@ -1,4 +1,4 @@
-class NotificationVersion < PaperTrail::Version
+class Version::NotificationVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_notifications
self.sequence_name = :log_notifications_id_seq
diff --git a/app/models/version/payment_order_version.rb b/app/models/version/payment_order_version.rb
index e556f1021..8d0a6d083 100644
--- a/app/models/version/payment_order_version.rb
+++ b/app/models/version/payment_order_version.rb
@@ -1,4 +1,4 @@
-class PaymentOrderVersion < PaperTrail::Version
+class Version::PaymentOrderVersion < PaperTrail::Version
self.table_name = :log_payment_orders
self.sequence_name = :log_payment_orders_id_seq
end
diff --git a/app/models/version/registrant_verification_version.rb b/app/models/version/registrant_verification_version.rb
index b7dbb8852..4f1d38601 100644
--- a/app/models/version/registrant_verification_version.rb
+++ b/app/models/version/registrant_verification_version.rb
@@ -1,4 +1,4 @@
-class RegistrantVerificationVersion < PaperTrail::Version
+class Version::RegistrantVerificationVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_registrant_verifications
self.sequence_name = :log_registrant_verifications_id_seq
diff --git a/app/models/version/registrar_version.rb b/app/models/version/registrar_version.rb
index 1e9c9584f..2a55ed212 100644
--- a/app/models/version/registrar_version.rb
+++ b/app/models/version/registrar_version.rb
@@ -1,4 +1,4 @@
-class RegistrarVersion < PaperTrail::Version
+class Version::RegistrarVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_registrars
self.sequence_name = :log_registrars_id_seq
diff --git a/app/models/version/reserved_domain_version.rb b/app/models/version/reserved_domain_version.rb
index 1f3289b79..db68441ab 100644
--- a/app/models/version/reserved_domain_version.rb
+++ b/app/models/version/reserved_domain_version.rb
@@ -1,4 +1,4 @@
-class ReservedDomainVersion < PaperTrail::Version
+class Version::ReservedDomainVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_reserved_domains
self.sequence_name = :log_reserved_domains_id_seq
diff --git a/app/models/version/setting_entry_version.rb b/app/models/version/setting_entry_version.rb
index de1e4d1ca..97840771a 100644
--- a/app/models/version/setting_entry_version.rb
+++ b/app/models/version/setting_entry_version.rb
@@ -1,4 +1,4 @@
-class SettingEntryVersion < PaperTrail::Version
+class Version::SettingEntryVersion < PaperTrail::Version
self.table_name = :log_setting_entries
self.sequence_name = :log_setting_entries
end
diff --git a/app/models/version/setting_version.rb b/app/models/version/setting_version.rb
index d532f8ef4..f93e576a3 100644
--- a/app/models/version/setting_version.rb
+++ b/app/models/version/setting_version.rb
@@ -1,4 +1,4 @@
-class SettingVersion < PaperTrail::Version
+class Version::SettingVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_settings
self.sequence_name = :log_settings_id_seq
diff --git a/app/models/version/user_version.rb b/app/models/version/user_version.rb
index 13453713b..6737ece7b 100644
--- a/app/models/version/user_version.rb
+++ b/app/models/version/user_version.rb
@@ -1,4 +1,4 @@
-class UserVersion < PaperTrail::Version
+class Version::UserVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_users
self.sequence_name = :log_users_id_seq
diff --git a/app/models/version/white_ip_version.rb b/app/models/version/white_ip_version.rb
index 0f2ee8a53..44d851628 100644
--- a/app/models/version/white_ip_version.rb
+++ b/app/models/version/white_ip_version.rb
@@ -1,4 +1,4 @@
-class WhiteIpVersion < PaperTrail::Version
+class Version::WhiteIpVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_white_ips
self.sequence_name = :log_white_ips_id_seq
diff --git a/app/models/white_ip.rb b/app/models/white_ip.rb
index 417633b12..38cee7b6b 100644
--- a/app/models/white_ip.rb
+++ b/app/models/white_ip.rb
@@ -4,8 +4,13 @@ class WhiteIp < ApplicationRecord
validate :valid_ipv4?
validate :valid_ipv6?
-
validate :validate_ipv4_and_ipv6
+ before_save :normalize_blank_values
+
+ def normalize_blank_values
+ %i[ipv4 ipv6].each { |c| self[c].present? || self[c] = nil }
+ end
+
def validate_ipv4_and_ipv6
return if ipv4.present? || ipv6.present?
errors.add(:base, I18n.t(:ipv4_or_ipv6_must_be_present))
@@ -50,10 +55,10 @@ class WhiteIp < ApplicationRecord
def ids_including(ip)
ipv4 = ipv6 = []
if check_ip4(ip).present?
- ipv4 = select { |white_ip| IPAddr.new(white_ip.ipv4, Socket::AF_INET) === check_ip4(ip) }
+ ipv4 = select { |white_ip| check_ip4(white_ip.ipv4) === check_ip4(ip) }
end
if check_ip6(ip).present?
- ipv6 = select { |white_ip| IPAddr.new(white_ip.ipv6, Socket::AF_INET6) === check_ip6(ip) }
+ ipv6 = select { |white_ip| check_ip6(white_ip.ipv6) === check_ip6(ip) }
end
(ipv4 + ipv6).pluck(:id).flatten.uniq
end
diff --git a/app/models/whois/record.rb b/app/models/whois/record.rb
index 1d827e22a..dc9cc2ba0 100644
--- a/app/models/whois/record.rb
+++ b/app/models/whois/record.rb
@@ -2,23 +2,34 @@ module Whois
class Record < Whois::Server
self.table_name = 'whois_records'
+ def self.without_auctions
+ ids = Whois::Record.all.select { |record| Auction.where(domain: record.name).blank? }
+ .pluck(:id)
+ Whois::Record.where(id: ids)
+ end
+
def self.disclaimer
Setting.registry_whois_disclaimer
end
+ # rubocop:disable Metrics/AbcSize
def update_from_auction(auction)
if auction.started?
update!(json: { name: auction.domain,
status: ['AtAuction'],
disclaimer: self.class.disclaimer })
+ ToStdout.msg "Updated from auction WHOIS record #{inspect}"
elsif auction.no_bids?
+ ToStdout.msg "Destroying WHOIS record #{inspect}"
destroy!
elsif auction.awaiting_payment? || auction.payment_received?
update!(json: { name: auction.domain,
status: ['PendingRegistration'],
disclaimer: self.class.disclaimer,
registration_deadline: auction.whois_deadline })
+ ToStdout.msg "Updated from auction WHOIS record #{inspect}"
end
end
+ # rubocop:enable Metrics/AbcSize
end
end
diff --git a/app/models/whois_record.rb b/app/models/whois_record.rb
index 3563b9630..9a6229fcb 100644
--- a/app/models/whois_record.rb
+++ b/app/models/whois_record.rb
@@ -97,6 +97,8 @@ class WhoisRecord < ApplicationRecord
end
def destroy_whois_record
+ return if Auction.find_by(domain: name).present?
+
Whois::Record.where(name: name).delete_all
end
diff --git a/app/presenters/registrar/domain_list_csv_presenter.rb b/app/presenters/registrar/domain_list_csv_presenter.rb
index 46b11f80b..5f32bd022 100644
--- a/app/presenters/registrar/domain_list_csv_presenter.rb
+++ b/app/presenters/registrar/domain_list_csv_presenter.rb
@@ -1,4 +1,4 @@
-class Registrar::DomainListCSVPresenter
+class Registrar::DomainListCsvPresenter
def initialize(domains:, view:)
@domains = domains
@view = view
diff --git a/app/views/admin/domain_versions/archive.haml b/app/views/admin/domain_versions/archive.haml
index f813f5eb3..46a79190b 100644
--- a/app/views/admin/domain_versions/archive.haml
+++ b/app/views/admin/domain_versions/archive.haml
@@ -66,7 +66,7 @@
= domain.registrant.name
- else
- contact = Contact.all_versions_for([domain.registrant_id], version.created_at).first
- - if contact.nil? && ver = ContactVersion.where(item_id: domain.registrant_id).last
+ - if contact.nil? && ver = Version::ContactVersion.where(item_id: domain.registrant_id).last
- contact = Contact.new(ver.object.to_h.merge(ver.object_changes.to_h.each_with_object({}) {|(k,v), o| o[k] = v.last }))
= contact.try(:name)
= " ".html_safe
diff --git a/app/views/admin/domains/_search_form.html.erb b/app/views/admin/domains/_search_form.html.erb
index bc317ea0b..1b1f50491 100644
--- a/app/views/admin/domains/_search_form.html.erb
+++ b/app/views/admin/domains/_search_form.html.erb
@@ -6,7 +6,7 @@
<%= f.search_field :name_matches, value: params[:q][:name_matches], class: 'form-control', placeholder: t(:name) %>
-
+
<%= f.label :registrant_ident, for: nil %>
<%= f.search_field :registrant_ident_eq, class: 'form-control', placeholder: t(:registrant_ident) %>
@@ -18,7 +18,7 @@
<%= f.search_field :contacts_ident_eq, class: 'form-control', placeholder: t(:contact_ident) %>
-
+
<%= f.label :nameserver_hostname, for: nil %>
<%= f.search_field :nameservers_hostname_eq, class: 'form-control', placeholder: t(:nameserver_hostname) %>
@@ -26,7 +26,7 @@
-
+
<%= f.label :registrar_name, for: nil %>
<%= f.select :registrar_id_eq, Registrar.all.map { |x| [x, x.id] }, { include_blank: true }, class: 'form-control selectize' %>
@@ -38,7 +38,7 @@
<%= f.search_field :valid_to_gteq, value: params[:q][:valid_to_gteq], class: 'form-control js-datepicker', placeholder: t(:valid_to_from) %>
-
+
<%= f.label :valid_to_until, for: nil %>
<%= f.search_field :valid_to_lteq, value: params[:q][:valid_to_lteq], class: 'form-control js-datepicker', placeholder: t(:valid_to_until) %>
@@ -46,7 +46,7 @@
-
+
<%= label_tag :status, nil, for: nil %>
<%= select_tag :statuses_contains, options_for_select(DomainStatus::STATUSES, params[:statuses_contains]), { multiple: true, class: 'form-control js-combobox' } %>
@@ -58,13 +58,17 @@
<%= text_field_tag :results_per_page, params[:results_per_page], class: 'form-control', placeholder: t(:results_per_page) %>
-
+
+ <%= link_to t('.download_csv_btn'), admin_domains_path(format: :csv, params: params.permit!),
+ "data-toggle" => "tooltip", "data-placement" => "bottom", "title" => t('.download_csv_btn'),
+ class: 'btn btn-default' %>
<%= link_to t('.reset_btn'), admin_domains_path, class: 'btn btn-default' %>
+
<% end %>
diff --git a/app/views/admin/domains/partials/_version.haml b/app/views/admin/domains/partials/_version.haml
index da0a0ece1..4533c9293 100644
--- a/app/views/admin/domains/partials/_version.haml
+++ b/app/views/admin/domains/partials/_version.haml
@@ -23,7 +23,7 @@
- admin_contacts = domain.admin_contacts
- registrant = domain.registrant
- unless registrant
- - ver = ContactVersion.where(item_id: domain.registrant_id).where(event: :destroy).last
+ - ver = Version::ContactVersion.where(item_id: domain.registrant_id).where(event: :destroy).last
- registrant = ver.reify
- registrant.version_loader = ver
- registrant = [registrant]
diff --git a/app/views/admin/repp_logs/show.haml b/app/views/admin/repp_logs/show.haml
index bbaae977f..9bb9ea52e 100644
--- a/app/views/admin/repp_logs/show.haml
+++ b/app/views/admin/repp_logs/show.haml
@@ -1,6 +1,6 @@
- content_for :actions do
= link_to(t(:back), :back, class: 'btn btn-primary')
-= render 'shared/title', name: t(:repp_log)
+= render 'shared/title', name: t('.title')
.row
.col-md-12
diff --git a/app/views/epp/poll/poll_req.xml.builder b/app/views/epp/poll/poll_req.xml.builder
index 664327dae..a58b082c5 100644
--- a/app/views/epp/poll/poll_req.xml.builder
+++ b/app/views/epp/poll/poll_req.xml.builder
@@ -15,12 +15,22 @@ xml.epp_head do
end if @object
end
- if @notification.action&.contact
- render(partial: 'epp/poll/action',
- locals: {
- builder: xml,
- action: @notification.action
- })
+ if @notification.action&.contact || @notification.registry_lock?
+ if @notification.registry_lock?
+ state = @notification.text.include?('unlocked') ? 'unlock' : 'lock'
+ xml.extension do
+ xml.tag!('changePoll:changeData',
+ 'xmlns:changePoll': 'https://epp.tld.ee/schema/changePoll-1.0.xsd') do
+ xml.tag!('changePoll:operation', state)
+ end
+ end
+ else
+ render(partial: 'epp/poll/action',
+ locals: {
+ builder: xml,
+ action: @notification.action,
+ })
+ end
end
render('epp/shared/trID', builder: xml)
diff --git a/app/views/registrant/contacts/_api_errors.html.erb b/app/views/registrant/contacts/_api_errors.html.erb
deleted file mode 100644
index 35617fa99..000000000
--- a/app/views/registrant/contacts/_api_errors.html.erb
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
- <% errors.each_value do |errors| %>
- <%= errors.join(' ') %>
- <% end %>
-
-
\ No newline at end of file
diff --git a/app/views/registrant/contacts/_form.html.erb b/app/views/registrant/contacts/_form.html.erb
deleted file mode 100644
index f203f39e8..000000000
--- a/app/views/registrant/contacts/_form.html.erb
+++ /dev/null
@@ -1,64 +0,0 @@
-<%= form_for [:registrant, domain, @contact], html: { class: 'form-horizontal' } do |f| %>
- <% if @errors.present? %>
- <%= render 'api_errors', errors: @errors %>
- <% end %>
-
-
-
-
-
-
-
- <% if Contact.address_processing? %>
-
-
<%= t '.address' %>
-
- <%= render 'registrant/contacts/form/address', f: f %>
-
-
- <% end %>
-
- <% if fax_enabled? %>
-
- <% end %>
-
-
-
-
-
- <%= button_tag t('.submit_btn'), class: 'btn btn-success' %>
-
-
-<% end %>
\ No newline at end of file
diff --git a/app/views/registrant/contacts/edit.html.erb b/app/views/registrant/contacts/edit.html.erb
deleted file mode 100644
index 0a453ded1..000000000
--- a/app/views/registrant/contacts/edit.html.erb
+++ /dev/null
@@ -1,12 +0,0 @@
-
- <%= link_to t('registrant.domains.index.header'), registrant_domains_path %>
- <%= link_to domain, registrant_domain_path(domain) %>
- <%= t 'registrant.contacts.contact_index' %>
- <%= link_to @contact, registrant_domain_contact_path(domain, @contact) %>
-
-
-
-
-<%= render 'form' %>
\ No newline at end of file
diff --git a/app/views/registrant/contacts/form/_address.html.erb b/app/views/registrant/contacts/form/_address.html.erb
deleted file mode 100644
index a43784d3f..000000000
--- a/app/views/registrant/contacts/form/_address.html.erb
+++ /dev/null
@@ -1,51 +0,0 @@
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/app/views/registrant/contacts/show.html.erb b/app/views/registrant/contacts/show.html.erb
deleted file mode 100644
index 1f0a87b5f..000000000
--- a/app/views/registrant/contacts/show.html.erb
+++ /dev/null
@@ -1,42 +0,0 @@
-
- <%= link_to t('registrant.domains.index.header'), registrant_domains_path %>
- <%= link_to domain, registrant_domain_path(domain) %>
- <%= t 'registrant.contacts.contact_index' %>
-
-
-
-
-
-
- <%= render 'registrant/contacts/show/general' %>
-
-
-
- <%= render 'registrant/contacts/show/address' %>
-
-
-
-
-
- <%= render 'registrant/contacts/show/statuses', contact: @contact %>
-
-
-
-
-
- <%= render 'registrant/contacts/show/domains', contact: @contact %>
-
-
\ No newline at end of file
diff --git a/app/views/registrant/contacts/show/_address.html.erb b/app/views/registrant/contacts/show/_address.html.erb
deleted file mode 100644
index c9bc80150..000000000
--- a/app/views/registrant/contacts/show/_address.html.erb
+++ /dev/null
@@ -1,31 +0,0 @@
-
-
-
- <%= t '.header' %>
-
-
-
-
-
- <% if @contact.org_name.present? %>
- <%= Contact.human_attribute_name :org_name %>
- <%= @contact.org_name %>
- <% end %>
-
- <%= Contact.human_attribute_name :street %>
- <%= @contact.street %>
-
- <%= Contact.human_attribute_name :city %>
- <%= @contact.city %>
-
- <%= Contact.human_attribute_name :zip %>
- <%= @contact.zip %>
-
- <%= Contact.human_attribute_name :state %>
- <%= @contact.state %>
-
- <%= Contact.human_attribute_name :country %>
- <%= @contact.country %>
-
-
-
\ No newline at end of file
diff --git a/app/views/registrant/contacts/show/_domain.html.erb b/app/views/registrant/contacts/show/_domain.html.erb
deleted file mode 100644
index 83b7f49d5..000000000
--- a/app/views/registrant/contacts/show/_domain.html.erb
+++ /dev/null
@@ -1,6 +0,0 @@
-
- <%= link_to domain.name, registrant_domain_path(domain) %>
- <%= link_to domain.registrar, registrant_registrar_path(domain.registrar) %>
- <%= l domain.valid_to %>
- <%= domain.roles.join(", ") %>
-
\ No newline at end of file
diff --git a/app/views/registrant/contacts/show/_domains.html.erb b/app/views/registrant/contacts/show/_domains.html.erb
deleted file mode 100644
index d783b55b2..000000000
--- a/app/views/registrant/contacts/show/_domains.html.erb
+++ /dev/null
@@ -1,54 +0,0 @@
-<% domains = contact.all_domains(page: params[:domain_page], per: 20,
- params: domain_filter_params.to_h, requester: @requester_contact) %>
-
-
-
-
-
- <%= t '.header' %>
-
-
-
- <%= form_tag request.path, method: :get, class: 'form-inline' do %>
- <%= select_tag :domain_filter,
- options_for_select(%w(Registrant AdminDomainContact TechDomainContact),
- selected: params[:domain_filter]),
- include_blank: t('.all'),
- class: 'form-control' %>
-
-
-
- <% end %>
-
-
-
-
-
-
-
-
-
- <%= custom_sort_link Domain.human_attribute_name(:name), :name %>
-
-
- <%= custom_sort_link Registrar.model_name.human, :registrar_name %>
-
-
- <%= custom_sort_link Domain.human_attribute_name(:valid_to), :valid_to %>
-
-
- <%= custom_sort_link Domain.human_attribute_name(:roles), :roles %>
-
-
-
-
-
- <%= render partial: 'registrant/contacts/show/domain', collection: domains %>
-
-
-
-
-
-
diff --git a/app/views/registrant/contacts/show/_general.html.erb b/app/views/registrant/contacts/show/_general.html.erb
deleted file mode 100644
index b61d2f50e..000000000
--- a/app/views/registrant/contacts/show/_general.html.erb
+++ /dev/null
@@ -1,48 +0,0 @@
-
-
-
- <%= t '.header' %>
-
-
-
-
-
- <%= Contact.human_attribute_name :code %>
- <%= @contact.code %>
-
- <%= Contact.human_attribute_name :name %>
- <%= @contact.name %>
-
- <%= Contact.human_attribute_name :auth_info %>
-
- <%= tag :input, type: 'text', value: @contact.auth_info, readonly: true,
- class: 'form-control input-sm' %>
-
-
- <%= Contact.human_attribute_name :ident %>
- <%= ident_for(@contact) %>
-
- <%= Contact.human_attribute_name :email %>
- <%= @contact.email %>
-
- <%= Contact.human_attribute_name :phone %>
- <%= @contact.phone %>
-
- <% if @contact.fax %>
- <%= Contact.human_attribute_name :fax %>
- <%= @contact.fax %>
- <% end %>
-
- <%= Contact.human_attribute_name :created_at %>
- <%= l @contact.created_at %>
-
- <%= Contact.human_attribute_name :updated_at %>
- <%= l @contact.updated_at %>
-
- <%= Registrar.model_name.human %>
-
- <%= link_to @contact.registrar, registrant_registrar_path(@contact.registrar) %>
-
-
-
-
\ No newline at end of file
diff --git a/app/views/registrant/contacts/show/_search.html.erb b/app/views/registrant/contacts/show/_search.html.erb
deleted file mode 100644
index f44fa322f..000000000
--- a/app/views/registrant/contacts/show/_search.html.erb
+++ /dev/null
@@ -1,6 +0,0 @@
-<%= search_form_for [:registrant, @q] do |f| %>
- <%= f.search_field :name_cont %>
- <%= f.submit do %>
-
- <% end %>
-<% end %>
\ No newline at end of file
diff --git a/app/views/registrant/contacts/show/_statuses.html.erb b/app/views/registrant/contacts/show/_statuses.html.erb
deleted file mode 100644
index 07db6bc87..000000000
--- a/app/views/registrant/contacts/show/_statuses.html.erb
+++ /dev/null
@@ -1,25 +0,0 @@
-
-
- <%= t '.header' %>
-
-
-
-
-
-
- <%= t '.status' %>
- <%= t '.notes' %>
-
-
-
-
- <% contact.statuses.each do |status| %>
-
- <%= status %>
- <%= contact.status_notes[status] %>
-
- <% end %>
-
-
-
-
\ No newline at end of file
diff --git a/app/views/registrant/domain_delete_confirms/show.haml b/app/views/registrant/domain_delete_confirms/show.haml
deleted file mode 100644
index fffc03219..000000000
--- a/app/views/registrant/domain_delete_confirms/show.haml
+++ /dev/null
@@ -1,44 +0,0 @@
-- if params[:confirmed].present?
- .row
- .col-md-12
- %h1= t(:domain_delete_confirmed_title)
- .row
- .col-md-12
- %p= t(:domain_delete_confirmed_body)
-- elsif params[:rejected].present?
- .row
- .col-md-12
- %h1= t(:domain_delete_rejected_title)
- .row
- .col-md-12
- %p= t(:domain_delete_rejected_body)
-- else
- - if @domain.present?
- .row
- .col-md-12
- %h1= t(:domain_delete_title)
- .row
- .col-md-12
- %p= t(:domain_delete_body)
-
- %hr
- .row
- .col-md-12.text-center.confirmation
- .column-keys
- %p= t(:domain_name) + ':'
- %p= t('.registrant') + ':'
- .column-values
- %p= @domain.name
- %p= "#{@domain.registrant.name} (#{@domain.registrant.ident})"
-
- .row
- .col-md-12.text-center
- .confirmation
- = form_for registrant_domain_delete_confirm_path(@domain.id), method: :patch do |f|
- = hidden_field_tag :token, params[:token]
- = f.button t(:confirm_domain_delete), name: 'confirmed', class: 'btn btn-primary'
- = f.button t(:reject_domain_delete), name: 'rejected', class: 'btn btn-warning'
- %hr
- - else
- %h1= t(:not_valid_domain_verification_title).html_safe
- %p= t(:not_valid_domain_verification_body).html_safe
diff --git a/app/views/registrant/domain_update_confirms/show.haml b/app/views/registrant/domain_update_confirms/show.haml
deleted file mode 100644
index 5f7a978ce..000000000
--- a/app/views/registrant/domain_update_confirms/show.haml
+++ /dev/null
@@ -1,46 +0,0 @@
-- if params[:confirmed].present?
- .row
- .col-md-12
- %h1= t(:domain_registrant_change_confirmed_title)
- .row
- .col-md-12
- %p= t(:domain_registrant_change_confirmed_body)
-- elsif params[:rejected].present?
- .row
- .col-md-12
- %h1= t(:domain_registrant_change_rejected_title)
- .row
- .col-md-12
- %p= t(:domain_registrant_change_rejected_body)
-- else
- - if @domain.present?
- .row
- .col-md-12
- %h1= t(:domain_registrant_change_title)
- .row
- .col-md-12
- %p= t(:domain_registrant_change_body)
-
- %hr
- .row
- .col-md-12.text-center.confirmation
- .column-keys
- %p= t(:domain_name) + ':'
- %p= t(:current_registrant) + ':'
- %p= t(:new_pending_registrant) + ':'
- .column-values
- %p= @domain.name
- %p= "#{@domain.registrant.name} (#{@domain.registrant.ident})"
- %p= "#{@domain.pending_registrant.try(:name)} (#{@domain.pending_registrant.try(:ident)})"
-
- .row
- .col-md-12.text-center
- .confirmation
- = form_for registrant_domain_update_confirm_path(@domain.id), method: :patch do |f|
- = hidden_field_tag :token, params[:token]
- = f.button t(:confirm_domain_registrant_update), name: 'confirmed', class: 'btn btn-primary'
- = f.button t(:reject_domain_registrant_update), name: 'rejected', class: 'btn btn-warning'
- %hr
- - else
- %h1= t(:not_valid_domain_verification_title).html_safe
- %p= t(:not_valid_domain_verification_body).html_safe
diff --git a/app/views/registrant/domains/_domain.html.erb b/app/views/registrant/domains/_domain.html.erb
deleted file mode 100644
index 8cc8a490b..000000000
--- a/app/views/registrant/domains/_domain.html.erb
+++ /dev/null
@@ -1,9 +0,0 @@
-
- <%= link_to domain, registrant_domain_path(domain) %>
-
- <%= link_to domain.registrant.name,
- registrant_domain_contact_path(domain, domain.registrant) %>
-
- <%= l domain.expire_time %>
- <%= link_to domain.registrar, registrant_registrar_path(domain.registrar) %>
-
diff --git a/app/views/registrant/domains/confirmation.haml b/app/views/registrant/domains/confirmation.haml
deleted file mode 100644
index b1bc0cb2f..000000000
--- a/app/views/registrant/domains/confirmation.haml
+++ /dev/null
@@ -1,13 +0,0 @@
-- content_for :actions do
- = render 'shared/title', name: @domain.name
-
-.row
- .col-md-12
- .panel.panel-default
- .panel-heading
- %h3.panel-title= t('.header')
- .panel-body
- .input-group.input-group-lg
- %span#sizing-addon1.input-group-addon.glyphicon.glyphicon-link
- %input.form-control{"aria-describedby" => "sizing-addon1", type: "text", value: @confirmation_url}
-
diff --git a/app/views/registrant/domains/index.html.erb b/app/views/registrant/domains/index.html.erb
deleted file mode 100644
index 1254bfbc8..000000000
--- a/app/views/registrant/domains/index.html.erb
+++ /dev/null
@@ -1,102 +0,0 @@
-
-
-
-
- <%= search_form_for [:registrant, @q], html: { class: 'search-form', autocomplete: 'off' } do |f| %>
-
-
-
- <%= f.label :name, for: nil %>
- <%= f.search_field :name_matches, value: params[:q][:name_matches], class: 'form-control', placeholder: t(:name) %>
-
-
-
-
- <%= f.label t(:registrant_ident), for: nil %>
- <%= f.search_field :registrant_ident_eq, class: 'form-control', placeholder: t(:registrant_ident) %>
-
-
-
-
-
- <%= label_tag t(:results_per_page) %>
- <%= text_field_tag :results_per_page, params[:results_per_page], class: 'form-control', placeholder: t(:results_per_page) %>
-
-
-
-
-
-
- <%= f.label t(:valid_to_from), for: nil %>
- <%= f.search_field :valid_to_gteq, value: params[:q][:valid_to_gteq], class: 'form-control js-datepicker', placeholder: t(:valid_to_from) %>
-
-
-
-
- <%= f.label t(:valid_to_until), for: nil %>
- <%= f.search_field :valid_to_lteq, value: params[:q][:valid_to_lteq], class: 'form-control js-datepicker', placeholder: t(:valid_to_until) %>
-
-
-
-
-
-
-
-
-
-
-
- <%= button_tag t('.download_pdf_btn'),
- formaction: registrant_domains_path(format: :pdf),
- name: nil,
- class: 'btn btn-default' %>
- <%= button_tag t('.download_csv_btn'),
- formaction: registrant_domains_path(format: :csv),
- name: nil,
- class: 'btn btn-default' %>
- <%= link_to t('.reset_btn'), registrant_domains_path,
- class: 'btn btn-default' %>
-
-
- <% end %>
-
-
-
-
-
-
-
-
-
-
- <%= sort_link(@q, 'name') %>
-
-
- <%= sort_link(@q, 'registrant_name', t('.registrant')) %>
-
-
- <%= sort_link(@q, 'valid_to', t(:valid_to)) %>
-
-
- <%= sort_link(@q, 'registrar_name', t(:registrar_name)) %>
-
-
-
-
-
- <%= render @domains %>
-
-
-
-
-
- <%= paginate @domains %>
-
-
-
-
-
diff --git a/app/views/registrant/domains/list_pdf.html.erb b/app/views/registrant/domains/list_pdf.html.erb
deleted file mode 100644
index 4ce4f5ed0..000000000
--- a/app/views/registrant/domains/list_pdf.html.erb
+++ /dev/null
@@ -1,32 +0,0 @@
-
-
-
-
-
-
-
-
-
- <%= Domain.human_attribute_name :name %>
- <%= Registrant.model_name.human %>
- <%= Domain.human_attribute_name :valid_to %>
- <%= Registrar.model_name.human %>
-
-
-
-
- <% @domains.each do |domain| %>
-
- <%= domain.name %>
- <%= domain.registrant %>
- <%= l(domain.valid_to, format: :short) %>
- <%= domain.registrar %>
-
- <% end %>
-
-
-
-
-
-
-
diff --git a/app/views/registrant/domains/partials/_dnskeys.haml b/app/views/registrant/domains/partials/_dnskeys.haml
deleted file mode 100644
index ddd95e952..000000000
--- a/app/views/registrant/domains/partials/_dnskeys.haml
+++ /dev/null
@@ -1,18 +0,0 @@
-.panel.panel-default
- .panel-heading.clearfix
- = t(:dnskeys)
- .table-responsive
- %table.table.table-hover.table-bordered.table-condensed
- %thead
- %tr
- %th{class: 'col-xs-1'}= t(:flag)
- %th{class: 'col-xs-1'}= t(:protocol)
- %th{class: 'col-xs-1'}= t(:algorithm)
- %th{class: 'col-xs-9'}= t(:public_key)
- %tbody
- - @domain.dnskeys.each do |x|
- %tr
- %td= x.flags
- %td= x.protocol
- %td= x.alg
- %td= x.public_key
diff --git a/app/views/registrant/domains/partials/_domain_contact.html.erb b/app/views/registrant/domains/partials/_domain_contact.html.erb
deleted file mode 100644
index e4eaf7115..000000000
--- a/app/views/registrant/domains/partials/_domain_contact.html.erb
+++ /dev/null
@@ -1,7 +0,0 @@
-<% contact = domain_contact.contact %>
-
-
- <%= link_to contact, registrant_domain_contact_path(domain, contact) %>
- <%= contact.code %>
- <%= contact.email %>
-
\ No newline at end of file
diff --git a/app/views/registrant/domains/partials/_domain_contacts.html.erb b/app/views/registrant/domains/partials/_domain_contacts.html.erb
deleted file mode 100644
index 3876e2546..000000000
--- a/app/views/registrant/domains/partials/_domain_contacts.html.erb
+++ /dev/null
@@ -1,24 +0,0 @@
-
-
- <%= t ".header_#{domain_contacts.model_name.plural.underscore}" %>
-
-
-
-
-
-
- <%= Contact.human_attribute_name :name %>
- <%= Contact.human_attribute_name :code %>
- <%= Contact.human_attribute_name :email %>
-
-
-
-
- <%= render partial: 'registrant/domains/partials/domain_contact',
- collection: domain_contacts,
- locals: { domain: domain } %>
-
-
-
-
\ No newline at end of file
diff --git a/app/views/registrant/domains/partials/_general.html.erb b/app/views/registrant/domains/partials/_general.html.erb
deleted file mode 100644
index 38995be01..000000000
--- a/app/views/registrant/domains/partials/_general.html.erb
+++ /dev/null
@@ -1,38 +0,0 @@
-
-
-
- <%= t(:general) %>
-
-
-
-
-
- <%= t(:name) %>
- <%= @domain.name %>
-
- <%= Domain.human_attribute_name :registered_at %>
- <%= l(@domain.registered_at) %>
-
- <%= Registrar.model_name.human %>
- <%= link_to(@domain.registrar, registrant_registrar_path(@domain.registrar)) %>
-
- <%= Domain.human_attribute_name :transfer_code %>
-
- <%= tag :input, type: 'text', value: @domain.transfer_code, readonly: true,
- class: 'form-control input-sm' %>
-
-
- <%= t(:valid_to) %>
- <%= l(@domain.valid_to) %>
-
- <%= Domain.human_attribute_name :outzone_at %>
- <%= l(@domain.outzone_at) %>
-
- <%= Domain.human_attribute_name :delete_date %>
- <%= l @domain.delete_date %>
-
- <%= Domain.human_attribute_name :force_delete_date %>
- <%= l @domain.force_delete_date %>
-
-
-
diff --git a/app/views/registrant/domains/partials/_legal_documents.haml b/app/views/registrant/domains/partials/_legal_documents.haml
deleted file mode 100644
index 7d740977b..000000000
--- a/app/views/registrant/domains/partials/_legal_documents.haml
+++ /dev/null
@@ -1,14 +0,0 @@
-.panel.panel-default
- .panel-heading.clearfix
- = t(:legal_documents)
- .table-responsive
- %table.table.table-hover.table-bordered.table-condensed
- %thead
- %tr
- %th{class: 'col-xs-8'}= t(:created_at)
- %th{class: 'col-xs-4'}= t(:type)
- %tbody
- - legal_documents.each do |x|
- %tr
- %td= link_to(x.created_at, [:registrar, x])
- %td= x.document_type
diff --git a/app/views/registrant/domains/partials/_nameservers.haml b/app/views/registrant/domains/partials/_nameservers.haml
deleted file mode 100644
index 0bc22732d..000000000
--- a/app/views/registrant/domains/partials/_nameservers.haml
+++ /dev/null
@@ -1,16 +0,0 @@
-.panel.panel-default
- .panel-heading.clearfix
- = t(:nameservers)
- .table-responsive
- %table.table.table-hover.table-bordered.table-condensed
- %thead
- %tr
- %th{class: 'col-xs-4'}= t(:hostname)
- %th{class: 'col-xs-4'}= t(:ipv4)
- %th{class: 'col-xs-4'}= t(:ipv6)
- %tbody
- - @domain.nameservers.each do |x|
- %tr
- %td= x
- %td= x.ipv4
- %td= x.ipv6
diff --git a/app/views/registrant/domains/partials/_registrant.html.erb b/app/views/registrant/domains/partials/_registrant.html.erb
deleted file mode 100644
index f02a2eb4e..000000000
--- a/app/views/registrant/domains/partials/_registrant.html.erb
+++ /dev/null
@@ -1,26 +0,0 @@
-
-
- <%= t '.header' %>
-
-
-
-
- <%= Registrant.human_attribute_name :name %>
-
- <%= link_to registrant.name, registrant_domain_contact_path(domain, registrant) %>
-
-
- <%= Registrant.human_attribute_name :code %>
- <%= registrant.code %>
-
- <%= Registrant.human_attribute_name :ident %>
- <%= registrant.ident %>
-
- <%= Registrant.human_attribute_name :email %>
- <%= registrant.email %>
-
- <%= Registrant.human_attribute_name :phone %>
- <%= registrant.phone %>
-
-
-
\ No newline at end of file
diff --git a/app/views/registrant/domains/partials/_statuses.haml b/app/views/registrant/domains/partials/_statuses.haml
deleted file mode 100644
index 10fc795eb..000000000
--- a/app/views/registrant/domains/partials/_statuses.haml
+++ /dev/null
@@ -1,18 +0,0 @@
-#domain_statuses.panel.panel-default
- .panel-heading.clearfix
- = t(:statuses)
- .table-responsive
- %table.table.table-hover.table-bordered.table-condensed
- %thead
- %tr
- %th{class: 'col-xs-6'}= t(:status)
- %th{class: 'col-xs-6'}= t(:notes)
- %tbody
- - @domain.statuses.each do |status|
- %tr
- %td
- - if [DomainStatus::PENDING_UPDATE, DomainStatus::PENDING_DELETE_CONFIRMATION].include?(status) && @domain.pending_json.present?
- = link_to(status, confirmation_registrant_domain_path(@domain))
- - else
- = status
- %td= @domain.status_notes[status]
diff --git a/app/views/registrant/domains/show.html.erb b/app/views/registrant/domains/show.html.erb
deleted file mode 100644
index 81ca04b51..000000000
--- a/app/views/registrant/domains/show.html.erb
+++ /dev/null
@@ -1,52 +0,0 @@
-
- <%= link_to t('registrant.domains.index.header'), registrant_domains_path %>
-
-
-
-
-
-
- <%= render 'registrant/domains/partials/general' %>
-
-
-
- <%= render partial: 'registrant/domains/partials/registrant',
- locals: { registrant: @domain.registrant, domain: @domain } %>
-
-
-
-
-
- <%= render 'registrant/domains/partials/domain_contacts',
- domain: @domain,
- domain_contacts: @domain.tech_domain_contacts %>
-
-
-
-
-
- <%= render 'registrant/domains/partials/domain_contacts',
- domain: @domain,
- domain_contacts: @domain.admin_domain_contacts %>
-
-
-
-
-
- <%= render 'registrant/domains/partials/statuses' %>
-
-
-
-
-
- <%= render 'registrant/domains/partials/nameservers' %>
-
-
-
-
-
- <%= render 'registrant/domains/partials/dnskeys' %>
-
-
diff --git a/app/views/registrant/registrars/show.haml b/app/views/registrant/registrars/show.haml
deleted file mode 100644
index f5e0f40f4..000000000
--- a/app/views/registrant/registrars/show.haml
+++ /dev/null
@@ -1,44 +0,0 @@
-= render 'shared/title', name: @registrar.name
-
-- if @registrar.errors.any?
- - @registrar.errors.each do |attr, err|
- = err
- %br
-- if @registrar.errors.any?
- %hr
-.row
- .col-md-6
- .panel.panel-default
- .panel-heading
- %h3.panel-title= t(:general)
- .panel-body
- %dl.dl-horizontal
- %dt= Registrar.human_attribute_name :name
- %dd= @registrar.name
-
- %dt= Registrar.human_attribute_name :reg_no
- %dd= @registrar.reg_no
-
- %dt= Registrar.human_attribute_name :vat_no
- %dd= @registrar.vat_no
-
- %dt= Registrar.human_attribute_name :code
- %dd= @registrar.code
-
- .col-md-6
- .panel.panel-default
- .panel-heading
- %h3.panel-title= t(:contact)
- .panel-body
- %dl.dl-horizontal
- %dt= Registrar.human_attribute_name :country
- %dd= @registrar.country
-
- %dt= Registrar.human_attribute_name :address
- %dd= @registrar.address
-
- %dt= Registrar.human_attribute_name :phone
- %dd= @registrar.phone
-
- %dt= Registrar.human_attribute_name :email
- %dd= @registrar.email
diff --git a/app/views/registrant/sessions/new.html.erb b/app/views/registrant/sessions/new.html.erb
deleted file mode 100644
index 9f7af3254..000000000
--- a/app/views/registrant/sessions/new.html.erb
+++ /dev/null
@@ -1,13 +0,0 @@
-
-
-
- <%= t '.header' %>
-
-
-
- <%= t '.hint' %>
-
-
- <%= link_to t(:sign_in), "/auth/rant_tara", method: :post, class: 'btn btn-lg btn-primary btn-block' %>
-
-
diff --git a/app/views/registrant/whois/index.haml b/app/views/registrant/whois/index.haml
deleted file mode 100644
index 5b1e64efa..000000000
--- a/app/views/registrant/whois/index.haml
+++ /dev/null
@@ -1,17 +0,0 @@
-= render 'shared/title', name: t(:whois)
-
-.row
- .col-md-12{style: 'margin-bottom: -15px;'}
- = form_tag registrant_whois_path, class: 'form-horizontal', method: :get do
- .col-md-11
- .form-group
- = text_field_tag :domain_name, params[:domain_name], class: 'form-control', placeholder: t(:domain_name), autocomplete: 'off', autofocus: true
- .col-md-1.text-right.text-center-xs
- .form-group
- %button.btn.btn-default
-
- %span.glyphicon.glyphicon-search
-
-%hr
-- if @domain
- %pre= @domain.body
diff --git a/app/views/registrar/account_activities/index.html.erb b/app/views/registrar/account_activities/index.html.erb
index c5eaf2063..aefcdd47f 100644
--- a/app/views/registrar/account_activities/index.html.erb
+++ b/app/views/registrar/account_activities/index.html.erb
@@ -14,7 +14,7 @@
-
+
<%= sort_link(@q, 'description') %>
@@ -26,6 +26,9 @@
<%= sort_link(@q, 'sum') %>
+
+ <%= sort_link(@q, 'new_balance', 'New balance') %>
+
@@ -45,6 +48,9 @@
<%= s %>
+
+ <%= x.new_balance.present? ? "#{currency(x.new_balance)} EUR" : 'N/A' %>
+
<% end %>
diff --git a/app/views/registrar/bulk_change/_admin_contact_form.html.erb b/app/views/registrar/bulk_change/_admin_contact_form.html.erb
new file mode 100644
index 000000000..77734e872
--- /dev/null
+++ b/app/views/registrar/bulk_change/_admin_contact_form.html.erb
@@ -0,0 +1,65 @@
+<%= form_tag registrar_admin_contacts_path, method: :patch, class: 'form-horizontal' do %>
+ <% if @error %>
+
+ <%= @error %>
+
+ <% end %>
+
+
+
+
+
+
+
+
+<% end %>
+
+
+ <% available_contacts.each do |data| %>
+ <%= data.first %>
+ <% end %>
+
diff --git a/app/views/registrar/bulk_change/_tech_contact_form.html.erb b/app/views/registrar/bulk_change/_tech_contact_form.html.erb
index 2848e3634..789db92ba 100644
--- a/app/views/registrar/bulk_change/_tech_contact_form.html.erb
+++ b/app/views/registrar/bulk_change/_tech_contact_form.html.erb
@@ -10,7 +10,7 @@
<%= label_tag :current_contact_id, t('.current_contact_id') %>
-
+
<%= text_field_tag :current_contact_id, params[:current_contact_id],
list: :contacts,
required: true,
@@ -24,7 +24,7 @@
<%= label_tag :new_contact_id, t('.new_contact_id') %>
-
+
+
+ <%= render 'admin_contact_form', available_contacts: available_contacts %>
+
+
<%= render 'nameserver_form' %>
diff --git a/config/application.rb b/config/application.rb
index a5fb17c9d..0ab5aa8bb 100644
--- a/config/application.rb
+++ b/config/application.rb
@@ -17,7 +17,7 @@ end
module DomainNameRegistry
class Application < Rails::Application
config.load_defaults 6.0
- config.autoloader = :classic # Do not use zeitwerk for now
+ config.autoloader = :zeitwerk # Do not use zeitwerk for now
# Settings in config/environments/* take precedence over those specified here.
# Application configuration should go into files in config/initializers
@@ -35,9 +35,11 @@ module DomainNameRegistry
# config.autoload_paths += Dir[Rails.root.join('app', 'api', '*')]
# Autoload all model subdirs
- config.autoload_paths += Dir[Rails.root.join('app', 'models', '**/')]
- config.autoload_paths += Dir[Rails.root.join('app', 'interactions', '**/')]
+ # config.autoload_paths += Dir[Rails.root.join('app', 'models', '**/')]
+ # config.autoload_paths += Dir[Rails.root.join('app', 'lib', '**/')]
+ # config.autoload_paths += Dir[Rails.root.join('app', 'interactions', '**/')]
config.eager_load_paths << config.root.join('lib', 'validators')
+ config.eager_load_paths << config.root.join('app', 'lib')
config.watchable_dirs['lib'] = %i[rb]
config.active_record.schema_format = :sql
@@ -70,8 +72,7 @@ module DomainNameRegistry
}
config.action_mailer.default_options = { from: ENV['action_mailer_default_from'] }
- require "#{Rails.root}/app/mailers/interceptors/punycode_interceptor"
- ActionMailer::Base.register_interceptor(PunycodeInterceptor)
+ config.action_mailer.interceptors = ["Interceptors::PunycodeInterceptor"]
config.action_view.default_form_builder = 'DefaultFormBuilder'
config.secret_key_base = Figaro.env.secret_key_base
diff --git a/config/application.yml.sample b/config/application.yml.sample
index 5885c47a2..88fc28a0d 100644
--- a/config/application.yml.sample
+++ b/config/application.yml.sample
@@ -87,8 +87,11 @@ sk_digi_doc_service_name: 'Testimine'
registrant_api_base_url:
registrant_api_auth_allowed_ips: '127.0.0.1, 0.0.0.0' #ips, separated with commas
-# Bounces API
-api_shared_key: testkey
+# Shared key for REST-WHOIS Bounces API incl. CERT
+rwhois_bounces_api_shared_key: testkey
+
+# Link to REST-WHOIS API
+rwhois_internal_api_shared_key: testkey
# Base URL (inc. https://) of REST registrant portal
# Leave blank to use internal registrant portal
@@ -167,7 +170,7 @@ tara_issuer: 'https://tara-test.ria.ee'
tara_identifier: 'identifier'
tara_secret: 'secret'
tara_redirect_uri: 'redirect_url'
-tara_keys: "{\"kty\":\"RSA\",\"kid\":\"de6cc4\",\"n\":\"jWwAjT_03ypme9ZWeSe7c-jY26NO50Wo5I1LBnPW2JLc0dPMj8v7y4ehiRpClYNTaSWcLd4DJmlKXDXXudEUWwXa7TtjBFJfzlZ-1u0tDvJ-H9zv9MzO7UhUFytztUEMTrtStdhGbzkzdEZZCgFYeo2i33eXxzIR1nGvI05d9Y-e_LHnNE2ZKTa89BC7ZiCXq5nfAaCgQna_knh4kFAX-KgiPRAtsiDHcAWKcBY3qUVcb-5XAX8p668MlGLukzsh5tFkQCbJVyNtmlbIHdbGvVHPb8C0H3oLYciv1Fjy_tS1lO7OT_cb3GVp6Ql-CG0uED_8pkpVtfsGRviub4_ElQ\",\"e\":\"AQAB\"}"
+tara_keys: "{\"kty\":\"RSA\",\"kid\":\"public:xWbbVoYq9EwMqphp\",\"n\":\"2vlgaxaUJYUWjkNM_b-ruADW3gyGnkPvxDyEXWeLyP668vn5aTrSdZ42psr6Vpu6V1MEjMr27bnE7swqndfmspqJHKlp47fO9orWWNGmrHFtClxU36wqFiIg9V39hbHdoXqZVdLywwjx6KLgsuYff95KvwfDqUK9IxxADm91ckD9m9aoQaPTrn8KsB9uhkyEchejNHRg7EGZDvWHF-aiQHCMnieSowiapPd7kTYGemPMheVyY_Zwvyya8DkvjnVa8HlrmbzjMjGdSRq5dVL0lCxb4-OlZ-QZuORUBqZ5xEAhWg2Jl6oG0slj3z8l_fd7l2oj7THNoepYWTnzUDxsN1hvRLzFnJh8MNUklYHWf8CFrwmPdqGDs0jeLP2v7X8LJeQ-Ly3GHsUBai1aVORZXCHq1Tzt2XyQhvPVt_3WoaVKJBi4hjz0CLKlSE0eUv9TWL58CU76tU98dxOwSb6hhqEu3xn6mLApyyEZzeUdYdJutDFQuTYz2pb1yqMFqlp2LHa49p7Q5TvBp4pKOxwjrqnlKTsasL8BU2vA9xHuEEYttVzAPWjH_5-BfoJ8GKQTLaXc6LOmWIZcMDVM8QEOkLXQdUtlaPVz-2wl9Q_FwhoBzXSZujEYQVcSZznxIdNyV4nvn2mo56isITX18PTcdyZ4V-wWlS5PuUNVVRQHWE0\",\"e\":\"AQAB\"}"
tara_rant_identifier: 'identifier'
tara_rant_secret: 'secret'
diff --git a/config/initializers/aws_ses.rb b/config/initializers/aws_ses.rb
new file mode 100644
index 000000000..baa148e65
--- /dev/null
+++ b/config/initializers/aws_ses.rb
@@ -0,0 +1,4 @@
+Aws.config.update(
+ region: ENV['aws_default_region'],
+ credentials: Aws::Credentials.new(ENV['aws_access_key_id'], ENV['aws_secret_access_key'])
+)
diff --git a/config/initializers/filter_parameter_logging.rb b/config/initializers/filter_parameter_logging.rb
index f2acc88e6..4f4e68288 100644
--- a/config/initializers/filter_parameter_logging.rb
+++ b/config/initializers/filter_parameter_logging.rb
@@ -1,9 +1,9 @@
Rails.application.configure do
config.filter_parameters += [:password, /^frame$/, /^nokogiri_frame$/, /^parsed_frame$/]
config.filter_parameters << lambda do |key, value|
- if key == 'raw_frame'
- value.to_s.gsub!(/pw>.+<\//, 'pw>[FILTERED]')
- value.to_s.gsub!(/
]+)>([^<])+<\/eis:legalDocument>/,
+ if key == 'raw_frame' && value.respond_to?(:gsub!)
+ value.gsub!(/pw>.+<\//, 'pw>[FILTERED]')
+ value.gsub!(/]+)>([^<])+<\/eis:legalDocument>/,
"[FILTERED] ")
end
end
diff --git a/config/locales/admin/domains.en.yml b/config/locales/admin/domains.en.yml
index c6e96bb15..ce59294dd 100644
--- a/config/locales/admin/domains.en.yml
+++ b/config/locales/admin/domains.en.yml
@@ -11,6 +11,7 @@ en:
search_form:
reset_btn: Reset
+ download_csv_btn: CSV
form:
pending_delete: &pending_delete
diff --git a/config/locales/admin/repp_logs.en.yml b/config/locales/admin/repp_logs.en.yml
index 559ae234a..0a58fe7ba 100644
--- a/config/locales/admin/repp_logs.en.yml
+++ b/config/locales/admin/repp_logs.en.yml
@@ -4,3 +4,6 @@ en:
index:
title: REPP log
reset_btn: Reset
+ show:
+ title: REPP log
+
diff --git a/config/locales/contacts.en.yml b/config/locales/contacts.en.yml
index 906bde193..4b4d099d7 100644
--- a/config/locales/contacts.en.yml
+++ b/config/locales/contacts.en.yml
@@ -25,8 +25,10 @@ en:
email_regex_check_error: Invalid format
domains:
exist: 'Object association prohibits operation'
+ delete_prohibited: Contact delete prohibited by status
statuses:
not_uniq: 'not uniq'
+ delete_prohibited: Contact delete prohibited by status
country_code:
invalid: Country code is not valid, should be in ISO_3166-1 alpha 2 format (%{value})
disclosed_attributes:
diff --git a/config/locales/notifications.en.yml b/config/locales/notifications.en.yml
index 1dff4a97c..d67fb5a5b 100644
--- a/config/locales/notifications.en.yml
+++ b/config/locales/notifications.en.yml
@@ -6,3 +6,5 @@ en:
It was associated with registrant %{old_registrant_code}
and contacts %{old_contacts_codes}.
contact_update: Contact %{contact} has been updated by registrant
+ registrar_locked: Domain %{domain_name} has been locked by registrant
+ registrar_unlocked: Domain %{domain_name} has been unlocked by registrant
diff --git a/config/locales/registrar/admin_contacts.en.yml b/config/locales/registrar/admin_contacts.en.yml
new file mode 100644
index 000000000..9265a6d10
--- /dev/null
+++ b/config/locales/registrar/admin_contacts.en.yml
@@ -0,0 +1,6 @@
+en:
+ registrar:
+ admin_contacts:
+ update:
+ replaced: Admin contacts have been successfully replaced.
+ replaced: Technical contacts have been successfully replaced.
diff --git a/config/locales/registrar/admin_contacts.yml b/config/locales/registrar/admin_contacts.yml
new file mode 100644
index 000000000..d258b4275
--- /dev/null
+++ b/config/locales/registrar/admin_contacts.yml
@@ -0,0 +1,11 @@
+en:
+ registrar:
+ admin_contacts:
+ update:
+ replaced: Admin contacts have been successfully replaced.
+ affected_domains: Affected domains
+ skipped_domains: Skipped domains
+ process_request:
+ affected_domains: Affected domains
+ skipped_domains: Skipped domains
+ replaced: Admin contacts have been successfully replaced.
diff --git a/config/locales/registrar/bulk_change.en.yml b/config/locales/registrar/bulk_change.en.yml
index 75becfada..d9f6ebbd2 100644
--- a/config/locales/registrar/bulk_change.en.yml
+++ b/config/locales/registrar/bulk_change.en.yml
@@ -4,6 +4,7 @@ en:
new:
header: Bulk change
technical_contact: Technical contact
+ admin_contact: Admin contact
nameserver: Nameserver
bulk_transfer: Bulk transfer
bulk_renew: Bulk renew
@@ -17,6 +18,19 @@ en:
Replace technical contact specified in "current contact ID" with the one in "new
contact ID" on any domain registered under this registrar
+ admin_contact_form:
+ current_contact_id: Current admin contact ID
+ new_contact_id: New admin contact ID
+ submit_btn: Replace admin contacts
+ help_btn: Toggle help
+ help: >-
+ Replace admin contact specified in "current contact ID" with the one in "new
+ contact ID" on any domain registered under this registrar. Contact idents must
+ be the same
+ comment: >-
+ Bulk admin change is only allowed in case of old and new contact are sharing identical
+ ident data ie for updating contact information.
+
nameserver_form:
ip_hint: One IP per line
replace_btn: Replace nameserver
@@ -38,3 +52,5 @@ en:
domain_ids: Domains for bulk renewal
current_balance: Current balance
period: Period
+ affected_domains: Affected domains
+ skipped_domains: Skipped domains
diff --git a/config/locales/registrar/tech_contacts.en.yml b/config/locales/registrar/tech_contacts.en.yml
index bf57f0cc7..b6e5d041b 100644
--- a/config/locales/registrar/tech_contacts.en.yml
+++ b/config/locales/registrar/tech_contacts.en.yml
@@ -5,3 +5,7 @@ en:
replaced: Technical contacts have been successfully replaced.
affected_domains: Affected domains
skipped_domains: Skipped domains
+ process_request:
+ affected_domains: Affected domains
+ skipped_domains: Skipped domains
+ replaced: Technical contacts have been successfully replaced.
diff --git a/config/routes.rb b/config/routes.rb
index 3042eced4..949fcb345 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -64,6 +64,7 @@ Rails.application.routes.draw do
get ':id/transfer_info', to: 'domains#transfer_info', constraints: { id: /.*/ }
post 'transfer', to: 'domains#transfer'
patch 'contacts', to: 'domains/contacts#update'
+ patch 'admin_contacts', to: 'domains/admin_contacts#update'
post 'renew/bulk', to: 'domains/renews#bulk_renew'
end
end
@@ -91,6 +92,7 @@ Rails.application.routes.draw do
end
resources :auctions, only: %i[index show update], param: :uuid
+ resources :contact_requests, only: %i[create update], param: :id
resources :bounces, only: %i[create]
end
@@ -136,6 +138,7 @@ Rails.application.routes.draw do
resource :bulk_change, controller: :bulk_change, only: :new
post '/bulk_renew/new', to: 'bulk_change#bulk_renew', as: :bulk_renew
resource :tech_contacts, only: :update
+ resource :admin_contacts, only: :update
resource :nameservers, only: :update
resources :contacts, constraints: {:id => /[^\/]+(?=#{ ActionController::Renderers::RENDERERS.map{|e| "\\.#{e}\\z"}.join("|") })|[^\/]+/} do
member do
@@ -188,35 +191,8 @@ Rails.application.routes.draw do
end
end
- scope :registrant do
- devise_scope :registrant_user do
- get 'sign_in', to: 'registrant/sessions#new', as: :new_registrant_user_session
- post 'sessions', to: 'registrant/sessions#create', as: :registrant_user_session
- delete 'sign_out', to: 'registrant/sessions#destroy', as: :destroy_registrant_user_session
-
- # TARA
- match '/open_id/callback', via: %i[get post], to: 'sso/tara#registrant_callback'
- match '/open_id/cancel', via: %i[get post delete], to: 'sso/tara#cancel'
- end
- end
-
namespace :registrant do
- root 'domains#index'
-
- # POST /registrant/sign_in is not used
devise_for :users, path: '', class_name: 'RegistrantUser'
-
- resources :registrars, only: :show
- # resources :companies, only: :index
- resources :domains, only: %i[index show] do
- resources :contacts, only: %i[show edit update]
- member do
- get 'confirmation'
- end
- end
-
- resources :domain_update_confirms, only: %i[show update]
- resources :domain_delete_confirms, only: %i[show update]
end
# ADMIN ROUTES
@@ -271,12 +247,24 @@ Rails.application.routes.draw do
end
end
+ resources :version_domain_versions do
+ collection do
+ get 'search' => 'domain_versions#search', via: [:get, :post], as: :search
+ end
+ end
+
resources :contact_versions do
collection do
get 'search'
end
end
+ resources :version_contact_versions do
+ collection do
+ get 'search' => 'contact_versions#search', via: [:get, :post], as: :search
+ end
+ end
+
resources :settings, only: %i[index create]
resources :blocked_domains do
diff --git a/db/migrate/20210215101019_add_new_balance_to_account_activity.rb b/db/migrate/20210215101019_add_new_balance_to_account_activity.rb
new file mode 100644
index 000000000..64c829833
--- /dev/null
+++ b/db/migrate/20210215101019_add_new_balance_to_account_activity.rb
@@ -0,0 +1,5 @@
+class AddNewBalanceToAccountActivity < ActiveRecord::Migration[6.0]
+ def change
+ add_column :account_activities, :new_balance, :decimal, precision: 10, scale: 2, null: true
+ end
+end
diff --git a/db/structure.sql b/db/structure.sql
index acf134a55..de2243597 100644
--- a/db/structure.sql
+++ b/db/structure.sql
@@ -226,7 +226,8 @@ CREATE TABLE public.account_activities (
creator_str character varying,
updator_str character varying,
activity_type character varying,
- price_id integer
+ price_id integer,
+ new_balance numeric(10,2)
);
@@ -4959,6 +4960,7 @@ INSERT INTO "schema_migrations" (version) VALUES
('20200908131554'),
('20200910085157'),
('20200910102028'),
-('20200916125326');
+('20200916125326'),
+('20210215101019');
diff --git a/doc/repp/v1/admin_contacts.md b/doc/repp/v1/admin_contacts.md
new file mode 100644
index 000000000..3b78829d0
--- /dev/null
+++ b/doc/repp/v1/admin_contacts.md
@@ -0,0 +1,30 @@
+# Admin domain contacts
+
+## PATCH https://repp.internet.ee/v1/domains/admin_contacts
+Replaces admin domain contacts of the current registrar.
+
+### Example request
+```
+PATCH /repp/v1/domains/admin_contacts HTTP/1.1
+Accept: application/json
+Content-Type: application/json
+Authorization: Basic dGVzdDp0ZXN0dGVzdA==
+
+{
+ "current_contact_id": "ATSAA:749AA80F",
+ "new_contact_id": "ATSAA:E36957D7"
+}
+```
+### Example response
+```
+{
+ "code": 1000,
+ "message": "Command completed successfully",
+ "data": {
+ "affected_domains": [
+ "private.ee",
+ ],
+ "skipped_domains": []
+ }
+}
+```
diff --git a/doc/repp/v1/domain_contacts.md b/doc/repp/v1/domain_contacts.md
index 2e542bf81..8c3c9b9de 100644
--- a/doc/repp/v1/domain_contacts.md
+++ b/doc/repp/v1/domain_contacts.md
@@ -1,7 +1,7 @@
-# Domain contacts
+# Tech domain contacts
## PATCH https://repp.internet.ee/v1/domains/contacts
-Replaces all domain contacts of the current registrar.
+Replaces technical domain contacts of the current registrar.
### Example request
```
diff --git a/lib/gem_monkey_patches/i18n.rb b/lib/gem_monkey_patches/i18n.rb
index 2f7fceff7..7d0613247 100644
--- a/lib/gem_monkey_patches/i18n.rb
+++ b/lib/gem_monkey_patches/i18n.rb
@@ -5,6 +5,7 @@ module I18n
alias_method :original_localize, :localize
def localize(object, options = {})
+ options.merge!({ default: '-' })
object.present? ? original_localize(object, options) : ''
end
end
diff --git a/lib/serializers/registrant_api/domain.rb b/lib/serializers/registrant_api/domain.rb
index 64913a7fb..b087a3a88 100644
--- a/lib/serializers/registrant_api/domain.rb
+++ b/lib/serializers/registrant_api/domain.rb
@@ -25,6 +25,12 @@ module Serializers
registrant: {
name: domain.registrant.name,
id: domain.registrant.uuid,
+ ident: domain.registrant.ident,
+ ident_type: domain.registrant.ident_type,
+ ident_country_code: domain.registrant.ident_country_code,
+ phone: domain.registrant.phone,
+ email: domain.registrant.email,
+ org: domain.registrant.org?,
},
tech_contacts: contacts(:tech),
admin_contacts: contacts(:admin),
@@ -60,7 +66,7 @@ module Serializers
registrar: { name: domain.registrar.name, website: domain.registrar.website },
registrant: { name: domain.registrant.name, id: domain.registrant.uuid,
phone: domain.registrant.phone, email: domain.registrant.email,
- ident: domain.registrant.ident }
+ ident: domain.registrant.ident, org: domain.registrant.org? }
}
end
diff --git a/lib/tasks/documents.rake b/lib/tasks/documents.rake
index 5ae8fb4df..39c32a3bd 100644
--- a/lib/tasks/documents.rake
+++ b/lib/tasks/documents.rake
@@ -16,8 +16,8 @@ namespace :documents do
next if x.documentable_id.blank?
document_type = case x.documentable_type
- when 'Domain' then DomainVersion
- when 'Contact'then ContactVersion
+ when 'Domain' then Version::DomainVersion
+ when 'Contact'then Version::ContactVersion
end
dc = document_type.where(item_id: x.documentable_id)
diff --git a/test/application_system_test_case.rb b/test/application_system_test_case.rb
index b31489691..726767390 100644
--- a/test/application_system_test_case.rb
+++ b/test/application_system_test_case.rb
@@ -35,7 +35,6 @@ class JavaScriptApplicationSystemTestCase < ApplicationSystemTestCase
def setup
DatabaseCleaner.start
-
super
Capybara.current_driver = :chrome
diff --git a/test/fixtures/contact_requests.yml b/test/fixtures/contact_requests.yml
new file mode 100644
index 000000000..030a4d726
--- /dev/null
+++ b/test/fixtures/contact_requests.yml
@@ -0,0 +1,8 @@
+new:
+ whois_record_id: 1
+ email: aaa@bbb.com
+ name: Testname
+ status: new
+ secret: somesecret
+ valid_to: 2010-07-05
+
diff --git a/test/integration/admin_area/account_activities_test.rb b/test/integration/admin_area/account_activities_test.rb
new file mode 100644
index 000000000..306935269
--- /dev/null
+++ b/test/integration/admin_area/account_activities_test.rb
@@ -0,0 +1,39 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminAreaAccountActivitiesIntegrationTest < ApplicationSystemTestCase
+ # /admin/account_activities
+ setup do
+ sign_in users(:admin)
+ @original_default_language = Setting.default_language
+ end
+
+ def test_show_account_activities_page
+ account_activities(:one).update(sum: "123.00")
+ visit admin_account_activities_path
+ assert_text 'Account activities'
+ end
+
+ def test_default_url_params
+ account_activities(:one).update(sum: "123.00")
+ visit admin_root_path
+ click_link_or_button 'Settings', match: :first
+ find(:xpath, "//ul/li/a[text()='Account activities']").click
+
+ assert has_current_path?(admin_account_activities_path(created_after: 'today'))
+ end
+
+ def test_download_account_activity
+ now = Time.zone.parse('2010-07-05 08:00')
+ travel_to now
+ account_activities(:one).update(sum: "123.00")
+
+ get admin_account_activities_path(format: :csv)
+
+ assert_response :ok
+ assert_equal "text/csv", response.headers['Content-Type']
+ assert_equal %(attachment; filename="account_activities_#{Time.zone.now.to_formatted_s(:number)}.csv"; filename*=UTF-8''account_activities_#{Time.zone.now.to_formatted_s(:number)}.csv),
+ response.headers['Content-Disposition']
+ assert_not_empty response.body
+ end
+end
diff --git a/test/integration/admin_area/admin_users_test.rb b/test/integration/admin_area/admin_users_test.rb
new file mode 100644
index 000000000..89b9edef9
--- /dev/null
+++ b/test/integration/admin_area/admin_users_test.rb
@@ -0,0 +1,101 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminAreaAdminUsersIntegrationTest < JavaScriptApplicationSystemTestCase
+ include Devise::Test::IntegrationHelpers
+ include ActionView::Helpers::NumberHelper
+
+ setup do
+ WebMock.allow_net_connect!
+ @original_default_language = Setting.default_language
+ sign_in users(:admin)
+ end
+
+ def test_create_new_admin_user
+ createNewAdminUser(true)
+ end
+
+ def test_create_with_invalid_data_new_admin_user
+ createNewAdminUser(false)
+ end
+
+ def test_edit_successfully_exist_record
+ createNewAdminUser(true)
+
+ visit admin_admin_users_path
+ click_on 'test_user_name'
+
+ assert_text 'General'
+ click_on 'Edit'
+
+ fill_in 'Password', with: 'test_password'
+ fill_in 'Password confirmation', with: 'test_password'
+
+ click_on 'Save'
+ assert_text 'Record updated'
+ end
+
+ def test_edit_exist_record_with_invalid_data
+ createNewAdminUser(true)
+
+ visit admin_admin_users_path
+ click_on 'test_user_name'
+
+ assert_text 'General'
+ click_on 'Edit'
+
+ fill_in 'Password', with: 'test_password'
+ fill_in 'Password confirmation', with: 'test_password2'
+
+ click_on 'Save'
+ assert_text 'Failed to update record'
+ end
+
+ def test_delete_exist_record
+ createNewAdminUser(true)
+
+ visit admin_admin_users_path
+ click_on 'test_user_name'
+ assert_text 'General'
+ click_on 'Delete'
+
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Record deleted'
+ end
+
+ private
+
+ def createNewAdminUser(valid)
+ visit admin_admin_users_path
+ click_on 'New admin user'
+
+ fill_in 'Username', with: 'test_user_name'
+ # If valid=true creating valid user, if else, then with invalid data
+ if valid
+ fill_in 'Password', with: 'test_password'
+ fill_in 'Password confirmation', with: 'test_password'
+ else
+ fill_in 'Password', with: 'test_password'
+ fill_in 'Password confirmation', with: 'test_password2'
+ end
+ fill_in 'Identity code', with: '38903110313'
+ fill_in 'Email', with: 'oleg@tester.ee'
+
+ select 'Estonia', from: 'admin_user_country_code', match: :first
+
+ select_element = find(:xpath, "/html/body/div[2]/form/div[2]/div/div[7]/div[2]/div/div[1]")
+ select_element.click
+
+ option_element = find(:xpath, "/html/body/div[2]/form/div[2]/div/div[7]/div[2]/div/div[2]/div/div[1]")
+ option_element.click
+
+ click_on 'Save'
+
+ if valid
+ assert_text 'Record created'
+ else
+ assert_text 'Failed to create record'
+ end
+ end
+end
diff --git a/test/integration/admin_area/blocked_domains_test.rb b/test/integration/admin_area/blocked_domains_test.rb
new file mode 100644
index 000000000..7df9d30e7
--- /dev/null
+++ b/test/integration/admin_area/blocked_domains_test.rb
@@ -0,0 +1,68 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+
+# /admin/blocked_domains
+class AdminAreaBlockedDomainsIntegrationTest < JavaScriptApplicationSystemTestCase
+ setup do
+ WebMock.allow_net_connect!
+ sign_in users(:admin)
+ @domain = domains(:shop)
+ @blocked_domain = blocked_domains(:one)
+ end
+
+ def test_page_successfully_loaded
+ visit_admin_blocked_domains_path
+ end
+
+ def test_add_into_blocked_list
+ visit_admin_blocked_domains_path
+ add_domain_into_blocked_list(true)
+ end
+
+ def test_add_into_blocked_list_same_domain
+ visit_admin_blocked_domains_path
+ add_domain_into_blocked_list(true)
+ add_domain_into_blocked_list(false)
+ end
+
+ def test_delete_domain_from_blocked_list
+ visit_admin_blocked_domains_path
+ add_domain_into_blocked_list(true)
+
+ click_link_or_button 'Delete', match: :first
+
+ # Accept to delete in modal window
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Domain deleted!'
+ end
+
+ def test_find_blocked_domain_from_blocked_list
+ visit_admin_blocked_domains_path
+ add_domain_into_blocked_list(true)
+
+ fill_in 'Name', with: @domain.name
+ find(:xpath, "//span[@class='glyphicon glyphicon-search']").click
+
+ assert_text @domain.name
+ end
+
+ private
+
+ def visit_admin_blocked_domains_path
+ visit admin_blocked_domains_path
+ assert_text 'Blocked domains'
+ end
+
+ def add_domain_into_blocked_list(value)
+ click_on 'New blocked domain'
+ assert_text 'Add domain to blocked list'
+
+ fill_in 'Name', with: @domain.name
+ click_on 'Save'
+
+ return assert_text 'Domain added!' if value
+ return assert_text 'Failed to add domain!'
+ end
+end
diff --git a/test/integration/admin_area/certificates_test.rb b/test/integration/admin_area/certificates_test.rb
new file mode 100644
index 000000000..d2eec0bc4
--- /dev/null
+++ b/test/integration/admin_area/certificates_test.rb
@@ -0,0 +1,71 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminAreaCertificatesIntegrationTest < JavaScriptApplicationSystemTestCase
+
+ setup do
+ WebMock.allow_net_connect!
+ sign_in users(:admin)
+
+ @apiuser = users(:api_bestnames)
+ @certificate = certificates(:api)
+ @certificate.update!(csr: "-----BEGIN CERTIFICATE REQUEST-----\nMIICszCCAZsCAQAwbjELMAkGA1UEBhMCRUUxFDASBgNVBAMMC2ZyZXNoYm94LmVl\nMRAwDgYDVQQHDAdUYWxsaW5uMREwDwYDVQQKDAhGcmVzaGJveDERMA8GA1UECAwI\nSGFyanVtYWExETAPBgNVBAsMCEZyZXNoYm94MIIBIjANBgkqhkiG9w0BAQEFAAOC\nAQ8AMIIBCgKCAQEA1VVESynZoZhIbe8s9zHkELZ/ZDCGiM2Q8IIGb1IOieT5U2mx\nIsVXz85USYsSQY9+4YdEXnupq9fShArT8pstS/VN6BnxdfAiYXc3UWWAuaYAdNGJ\nDr5Jf6uMt1wVnCgoDL7eJq9tWMwARC/viT81o92fgqHFHW0wEolfCmnpik9o0ACD\nFiWZ9IBIevmFqXtq25v9CY2cT9+eZW127WtJmOY/PKJhzh0QaEYHqXTHWOLZWpnp\nHH4elyJ2CrFulOZbHPkPNB9Nf4XQjzk1ffoH6e5IVys2VV5xwcTkF0jY5XTROVxX\nlR2FWqic8Q2pIhSks48+J6o1GtXGnTxv94lSDwIDAQABoAAwDQYJKoZIhvcNAQEL\nBQADggEBAEFcYmQvcAC8773eRTWBJJNoA4kRgoXDMYiiEHih5iJPVSxfidRwYDTF\nsP+ttNTUg3JocFHY75kuM9T2USh+gu/trRF0o4WWa+AbK3JbbdjdT1xOMn7XtfUU\nZ/f1XCS9YdHQFCA6nk4Z+TLWwYsgk7n490AQOiB213fa1UIe83qIfw/3GRqRUZ7U\nwIWEGsHED5WT69GyxjyKHcqGoV7uFnqFN0sQVKVTy/NFRVQvtBUspCbsOirdDRie\nAB2KbGHL+t1QrRF10szwCJDyk5aYlVhxvdI8zn010nrxHkiyQpDFFldDMLJl10BW\n2w9PGO061z+tntdRcKQGuEpnIr9U5Vs=\n-----END CERTIFICATE REQUEST-----\n")
+ end
+
+ def test_show_certificate_info
+ show_certificate_info
+ end
+
+ def test_destroy_certificate
+ show_certificate_info
+ find(:xpath, "//a[text()='Delete']").click
+
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Record deleted'
+ end
+
+ def test_download_csr
+ get download_csr_admin_api_user_certificate_path(api_user_id: @apiuser.id, id: @certificate.id)
+
+ assert_response :ok
+ assert_equal 'application/octet-stream', response.headers['Content-Type']
+ assert_equal "attachment; filename=\"test_bestnames.csr.pem\"; filename*=UTF-8''test_bestnames.csr.pem", response.headers['Content-Disposition']
+ assert_not_empty response.body
+ end
+
+ def test_download_crt
+ get download_crt_admin_api_user_certificate_path(api_user_id: @apiuser.id, id: @certificate.id)
+
+ assert_response :ok
+ assert_equal 'application/octet-stream', response.headers['Content-Type']
+ assert_equal "attachment; filename=\"test_bestnames.crt.pem\"; filename*=UTF-8''test_bestnames.crt.pem", response.headers['Content-Disposition']
+ assert_not_empty response.body
+ end
+
+ def test_failed_to_revoke_certificate
+ show_certificate_info
+
+ find(:xpath, "//a[text()='Revoke this certificate']").click
+ assert_text 'Failed to update record'
+ end
+
+ def test_new_api_user
+ visit new_admin_registrar_api_user_path(registrar_id: registrars(:bestnames).id)
+
+ fill_in 'Username', with: 'testapiuser'
+ fill_in 'Password', with: 'secretpassword'
+ fill_in 'Identity code', with: '60305062718'
+
+ click_on 'Create API user'
+
+ assert_text 'API user has been successfully created'
+ end
+
+ private
+
+ def show_certificate_info
+ visit admin_api_user_certificate_path(api_user_id: @apiuser.id, id: @certificate.id)
+ assert_text 'Certificates'
+ end
+end
diff --git a/test/integration/admin_area/epp_logs_test.rb b/test/integration/admin_area/epp_logs_test.rb
new file mode 100644
index 000000000..5ad514cb8
--- /dev/null
+++ b/test/integration/admin_area/epp_logs_test.rb
@@ -0,0 +1,52 @@
+# admin_epp_logs_path
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminEppLogsIntegrationTest < ApplicationSystemTestCase
+ setup do
+ sign_in users(:admin)
+ end
+
+ def test_visit_epp_logs_page
+ visit admin_epp_logs_path
+ assert_text 'EPP log'
+ end
+
+ def test_show_epp_log_page
+ visit admin_epp_logs_path
+ send_epp_request_hello
+ visit admin_epp_logs_path
+
+ find(:xpath, "//tbody/tr/td/a", match: :first).click
+ assert_text 'Details'
+ end
+
+ def test_dates_sort
+ Capybara.exact = true
+ visit admin_epp_logs_path
+ send_epp_request_hello
+ visit admin_epp_logs_path
+
+ find(:xpath, "//a[contains(text(), 'Created at')]", match: :first).click
+ find(:xpath, "//a[contains(text(), 'Created at')]", match: :first).click
+
+ epp_log_date = find(:xpath, "//table/tbody/tr/td[6]", match: :first).text(:all)
+ date_now = Date.today.to_s(:db)
+
+ assert_match /#{date_now}/, epp_log_date
+ end
+
+ private
+
+ def send_epp_request_hello
+ request_xml = <<-XML
+
+
+
+
+ XML
+
+ get epp_hello_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=non-existent' }
+ end
+end
diff --git a/test/integration/admin_area/invoices_test.rb b/test/integration/admin_area/invoices_test.rb
index 887f57212..2aa17201d 100644
--- a/test/integration/admin_area/invoices_test.rb
+++ b/test/integration/admin_area/invoices_test.rb
@@ -6,6 +6,27 @@ class AdminAreaInvoicesIntegrationTest < ApplicationIntegrationTest
sign_in users(:admin)
end
+ def test_create_new_invoice
+ visit new_admin_invoice_path
+
+ assert_text 'Create new invoice'
+ select 'Best Names', from: 'deposit_registrar_id', match: :first
+ fill_in 'Amount', with: '1000'
+ click_on 'Save'
+
+ assert_equal page.status_code, 200
+ end
+
+ def test_visit_list_of_invoices_pages
+ visit admin_invoices_path
+ assert_text 'Invoices'
+ end
+
+ def test_visit_invoice_page
+ visit admin_invoices_path(id: @invoice.id)
+ assert_text "Invoice no. #{@invoice.number}"
+ end
+
def test_downloads_invoice
assert_equal 1, @invoice.number
diff --git a/test/integration/admin_area/pending_delete_test.rb b/test/integration/admin_area/pending_delete_test.rb
new file mode 100644
index 000000000..737d12480
--- /dev/null
+++ b/test/integration/admin_area/pending_delete_test.rb
@@ -0,0 +1,60 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminAreaPendingDeleteIntegrationTest < JavaScriptApplicationSystemTestCase
+ setup do
+ WebMock.allow_net_connect!
+ sign_in users(:admin)
+
+ @domain = domains(:shop)
+ @token = '123456'
+
+ @domain.update!(statuses: [DomainStatus::PENDING_DELETE_CONFIRMATION],
+ registrant_verification_asked_at: Time.zone.now - 1.day,
+ registrant_verification_token: @token)
+ end
+
+ def test_accept_pending_delete
+ visit edit_admin_domain_path(id: @domain.id)
+
+ click_on 'Accept'
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Pending was successfully applied.'
+ end
+
+ def test_accept_pending_delete_no_success
+ @domain.update!(statuses: [DomainStatus::PENDING_DELETE_CONFIRMATION],
+ registrant_verification_asked_at: Time.zone.now - 1.day,
+ registrant_verification_token: nil)
+
+ visit edit_admin_domain_path(id: @domain.id)
+
+ click_on 'Accept'
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Not success'
+ end
+
+ def test_reject_panding_delete
+ visit edit_admin_domain_path(id: @domain.id)
+
+ click_on 'Reject'
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Pending was successfully removed.'
+ end
+
+ def test_accept_pending_delete_no_success
+ @domain.update!(statuses: [DomainStatus::PENDING_DELETE_CONFIRMATION],
+ registrant_verification_asked_at: Time.zone.now - 1.day,
+ registrant_verification_token: nil)
+
+ visit edit_admin_domain_path(id: @domain.id)
+
+ click_on 'Reject'
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Not success'
+ end
+end
diff --git a/test/integration/admin_area/pending_update_test.rb b/test/integration/admin_area/pending_update_test.rb
new file mode 100644
index 000000000..5d08e104b
--- /dev/null
+++ b/test/integration/admin_area/pending_update_test.rb
@@ -0,0 +1,96 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminAreaPendingUpdateIntegrationTest < JavaScriptApplicationSystemTestCase
+
+ setup do
+ WebMock.allow_net_connect!
+ sign_in users(:admin)
+
+ @domain = domains(:hospital)
+
+ @new_registrant = contacts(:jack)
+ @user = users(:api_bestnames)
+ @token = '123456'
+
+ @domain.update!(statuses: [DomainStatus::PENDING_UPDATE],
+ registrant_verification_asked_at: Time.zone.now - 1.day,
+ registrant_verification_token: @token)
+ end
+
+ def test_accept_pending_update
+ pending_json = { new_registrant_id: @new_registrant.id,
+ new_registrant_name: @new_registrant.name,
+ new_registrant_email: @new_registrant.email,
+ current_user_id: @user.id }
+
+ @domain.update(pending_json: pending_json)
+ @domain.reload
+
+ visit edit_admin_domain_path(id: @domain.id)
+
+ click_on 'Accept'
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Pending was successfully applied.'
+ end
+
+ def test_accept_pending_update_no_success
+ @domain.update!(statuses: [DomainStatus::PENDING_UPDATE],
+ registrant_verification_asked_at: Time.zone.now - 1.day,
+ registrant_verification_token: nil)
+
+ pending_json = { new_registrant_id: @new_registrant.id,
+ new_registrant_name: @new_registrant.name,
+ new_registrant_email: @new_registrant.email,
+ current_user_id: @user.id,
+ }
+
+ @domain.update(pending_json: pending_json)
+ @domain.reload
+
+ visit edit_admin_domain_path(id: @domain.id)
+
+ click_on 'Accept'
+ page.driver.browser.switch_to.alert.accept
+ assert_text 'Not success'
+ end
+
+ def test_reject_panding_update
+ pending_json = { new_registrant_id: @new_registrant.id,
+ new_registrant_name: @new_registrant.name,
+ new_registrant_email: @new_registrant.email,
+ current_user_id: @user.id,
+ }
+
+ @domain.update(pending_json: pending_json)
+ @domain.reload
+
+ visit edit_admin_domain_path(id: @domain.id)
+
+ click_on 'Reject'
+ page.driver.browser.switch_to.alert.accept
+ assert_text 'Pending was successfully removed.'
+ end
+
+ def test_accept_pending_update_no_success
+ @domain.update!(statuses: [DomainStatus::PENDING_UPDATE],
+ registrant_verification_asked_at: Time.zone.now - 1.day,
+ registrant_verification_token: nil)
+
+ pending_json = { new_registrant_id: @new_registrant.id,
+ new_registrant_name: @new_registrant.name,
+ new_registrant_email: @new_registrant.email,
+ current_user_id: @user.id,
+ }
+
+ @domain.update(pending_json: pending_json)
+ @domain.reload
+
+ visit edit_admin_domain_path(id: @domain.id)
+
+ click_on 'Reject'
+ page.driver.browser.switch_to.alert.accept
+ assert_text 'Not success'
+ end
+end
diff --git a/test/integration/admin_area/registrars_test.rb b/test/integration/admin_area/registrars_test.rb
index d73496899..552650791 100644
--- a/test/integration/admin_area/registrars_test.rb
+++ b/test/integration/admin_area/registrars_test.rb
@@ -17,4 +17,4 @@ class AdminAreaRegistrarsIntegrationTest < ActionDispatch::IntegrationTest
assert_equal new_iban, @registrar.iban
end
-end
\ No newline at end of file
+end
diff --git a/test/integration/admin_area/repp_logs_test.rb b/test/integration/admin_area/repp_logs_test.rb
new file mode 100644
index 000000000..6630a6d57
--- /dev/null
+++ b/test/integration/admin_area/repp_logs_test.rb
@@ -0,0 +1,23 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminAreaReppLogsIntegrationTest < ApplicationSystemTestCase
+ setup do
+ sign_in users(:admin)
+ end
+
+ def test_repp_logs_page
+ visit admin_repp_logs_path
+ assert_text 'REPP log'
+ end
+
+ def test_show_repp_log_page
+ visit admin_repp_logs_path
+ get repp_v1_contacts_path
+ visit admin_repp_logs_path
+
+ find(:xpath, "//tbody/tr/td/a", match: :first).click
+
+ assert_text 'REPP log'
+ end
+end
diff --git a/test/integration/admin_area/reserved_domains_test.rb b/test/integration/admin_area/reserved_domains_test.rb
new file mode 100644
index 000000000..c09c3723b
--- /dev/null
+++ b/test/integration/admin_area/reserved_domains_test.rb
@@ -0,0 +1,39 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminAreaReservedDomainsIntegrationTest < JavaScriptApplicationSystemTestCase
+
+ setup do
+ WebMock.allow_net_connect!
+ @original_default_language = Setting.default_language
+ sign_in users(:admin)
+
+ @reserved_domain = reserved_domains(:one)
+ end
+
+ def test_remove_reserved_domain
+ visit admin_reserved_domains_path
+ click_link_or_button 'Delete', match: :first
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Domain deleted!'
+ end
+
+ def test_add_invalid_domain
+ visit admin_reserved_domains_path
+ click_on 'New reserved domain'
+ fill_in "Name", with: "@##@$"
+ click_on 'Save'
+
+ assert_text 'Failed to add domain!'
+ end
+
+ def test_update_reserved_domain
+ visit admin_reserved_domains_path
+ click_link_or_button 'Edit Pw', match: :first
+ fill_in 'Password', with: '12345678'
+ click_on 'Save'
+
+ assert_text 'Domain updated!'
+ end
+end
diff --git a/test/integration/admin_area/white_ips_test.rb b/test/integration/admin_area/white_ips_test.rb
new file mode 100644
index 000000000..499c86f57
--- /dev/null
+++ b/test/integration/admin_area/white_ips_test.rb
@@ -0,0 +1,94 @@
+require 'test_helper'
+require 'application_system_test_case'
+
+class AdminAreaWhiteIpsIntegrationTest < JavaScriptApplicationSystemTestCase
+
+ setup do
+ WebMock.allow_net_connect!
+ sign_in users(:admin)
+
+ @registrar = registrars(:bestnames)
+ @white_ip = white_ips(:one)
+ end
+
+ def test_visit_new_whitelisted_ip_page
+ visit_new_whitelisted_ip_page
+ end
+
+ def test_create_new_whitelisted_ip
+ visit_new_whitelisted_ip_page
+ fill_in 'IPv4', with: "127.0.0.1"
+ fill_in 'IPv6', with: "::ffff:192.0.2.1"
+
+ find(:css, "#white_ip_interfaces_api").set(true)
+ find(:css, "#white_ip_interfaces_registrar").set(true)
+
+ click_on 'Save'
+
+ assert_text 'Record created'
+ end
+
+ def test_failed_to_create_new_whitelisted_ip
+ visit_new_whitelisted_ip_page
+ fill_in 'IPv4', with: "asdadadad.asd"
+
+ click_on 'Save'
+
+ assert_text 'Failed to create record'
+ end
+
+ def test_visit_edit_whitelisted_ip_page
+ visit_edit_whitelisted_ip_page
+ end
+
+ def test_update_whitelisted_ip
+ visit_info_whitelisted_ip_page
+ click_on 'Edit'
+
+ fill_in 'IPv4', with: "127.0.0.2"
+ find(:css, "#white_ip_interfaces_api").set(false)
+ click_on 'Save'
+
+ assert_text 'Record updated'
+ end
+
+ def test_failed_to_update_whitelisted_ip
+ visit_info_whitelisted_ip_page
+ click_on 'Edit'
+ fill_in 'IPv4', with: "asdadad#"
+
+ click_on 'Save'
+
+ assert_text 'Failed to update record'
+ end
+
+ def test_visit_info_whitelisted_ip_page
+ visit_info_whitelisted_ip_page
+ end
+
+ def test_delete_whitelisted_ip
+ visit_info_whitelisted_ip_page
+ click_on 'Delete'
+
+ page.driver.browser.switch_to.alert.accept
+
+ assert_text 'Record deleted'
+ end
+
+ private
+
+ def visit_new_whitelisted_ip_page
+ visit new_admin_registrar_white_ip_path(registrar_id: @registrar.id)
+ assert_text 'New whitelisted IP'
+ end
+
+ def visit_edit_whitelisted_ip_page
+ visit edit_admin_registrar_white_ip_path(registrar_id: @registrar.id, id: @white_ip.id)
+ assert_text 'Edit white IP'
+ end
+
+ def visit_info_whitelisted_ip_page
+ visit admin_registrar_white_ip_path(registrar_id: @registrar.id, id: @white_ip.id)
+ assert_text 'White IP'
+ end
+end
diff --git a/test/integration/api/domain_admin_contacts_test.rb b/test/integration/api/domain_admin_contacts_test.rb
new file mode 100644
index 000000000..cd5b92865
--- /dev/null
+++ b/test/integration/api/domain_admin_contacts_test.rb
@@ -0,0 +1,153 @@
+require 'test_helper'
+
+class APIDomainAdminContactsTest < ApplicationIntegrationTest
+ setup do
+ @admin_current = domains(:shop).admin_contacts.find_by(code: 'jane-001')
+ domain = domains(:airport)
+ domain.admin_contacts << @admin_current
+ @admin_new = contacts(:william)
+
+ @admin_new.update(ident: @admin_current.ident,
+ ident_type: @admin_current.ident_type,
+ ident_country_code: @admin_current.ident_country_code)
+ end
+
+ def test_replace_all_admin_contacts_when_ident_data_doesnt_match
+ @admin_new.update(ident: '777' ,
+ ident_type: 'priv',
+ ident_country_code: 'LV')
+
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: @admin_new.code },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_response :bad_request
+ assert_equal ({ code: 2304, message: 'Admin contacts must be identical', data: {} }),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
+ def test_replace_all_admin_contacts_of_the_current_registrar
+ assert @admin_new.identical_to?(@admin_current)
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: @admin_new.code },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_nil domains(:shop).admin_contacts.find_by(code: @admin_current.code)
+ assert domains(:shop).admin_contacts.find_by(code: @admin_new.code)
+ assert domains(:airport).admin_contacts.find_by(code: @admin_new.code)
+ end
+
+ def test_skip_discarded_domains
+ domains(:airport).update!(statuses: [DomainStatus::DELETE_CANDIDATE])
+
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: @admin_new.code },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert domains(:airport).admin_contacts.find_by(code: @admin_current.code)
+ end
+
+ def test_return_affected_domains_in_alphabetical_order
+ domain = domains(:airport)
+ domain.admin_contacts = [@admin_current]
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: @admin_new.code },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_response :ok
+ assert_equal ({ code: 1000, message: 'Command completed successfully', data: { affected_domains: %w[airport.test shop.test],
+ skipped_domains: [] }}),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
+ def test_return_skipped_domains_in_alphabetical_order
+ domains(:shop).update!(statuses: [DomainStatus::DELETE_CANDIDATE])
+ domains(:airport).update!(statuses: [DomainStatus::DELETE_CANDIDATE])
+
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: @admin_new.code },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_response :ok
+ assert_equal %w[airport.test shop.test], JSON.parse(response.body,
+ symbolize_names: true)[:data][:skipped_domains]
+ end
+
+ def test_keep_other_admin_contacts_intact
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: @admin_new.code },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert domains(:airport).admin_contacts.find_by(code: 'john-001')
+ end
+
+ def test_keep_tech_contacts_intact
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: @admin_new.code },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert domains(:airport).tech_contacts.find_by(code: 'william-001')
+ end
+
+ def test_restrict_contacts_to_the_current_registrar
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: 'william-002' },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_response :not_found
+ assert_equal ({ code: 2303, message: 'Object does not exist' }),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
+ def test_non_existent_current_contact
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: 'non-existent',
+ new_contact_id: @admin_new.code},
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+ assert_response :not_found
+ assert_equal ({ code: 2303, message: 'Object does not exist' }),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
+ def test_non_existent_new_contact
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: 'non-existent' },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+ assert_response :not_found
+ assert_equal ({code: 2303, message: 'Object does not exist'}),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
+ def test_disallow_invalid_new_contact
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: 'invalid' },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+ assert_response :bad_request
+ assert_equal ({ code: 2304, message: 'New contact must be valid', data: {} }),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
+ def test_admin_bulk_changed_when_domain_update_prohibited
+ domains(:shop).update!(statuses: [DomainStatus::SERVER_UPDATE_PROHIBITED])
+ domains(:airport).admin_contacts = [@admin_current]
+
+ shop_admin_contact = Contact.find_by(code: 'jane-001')
+ assert domains(:shop).admin_contacts.include?(shop_admin_contact)
+
+ patch '/repp/v1/domains/admin_contacts', params: { current_contact_id: @admin_current.code,
+ new_contact_id: @admin_new.code },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_response :ok
+ assert_equal ({ code: 1000,
+ message: 'Command completed successfully',
+ data: { affected_domains: ["airport.test"],
+ skipped_domains: ["shop.test"] }}),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
+ private
+
+ def http_auth_key
+ ActionController::HttpAuthentication::Basic.encode_credentials('test_bestnames', 'testtest')
+ end
+end
diff --git a/test/integration/api/domain_contacts_test.rb b/test/integration/api/domain_contacts_test.rb
index 6704739d1..efd7032b4 100644
--- a/test/integration/api/domain_contacts_test.rb
+++ b/test/integration/api/domain_contacts_test.rb
@@ -107,6 +107,24 @@ class APIDomainContactsTest < ApplicationIntegrationTest
JSON.parse(response.body, symbolize_names: true)
end
+ def test_tech_bulk_changed_when_domain_update_prohibited
+ domains(:shop).update!(statuses: [DomainStatus::SERVER_UPDATE_PROHIBITED])
+
+ shop_tech_contact = Contact.find_by(code: 'william-001')
+ assert domains(:shop).tech_contacts.include?(shop_tech_contact)
+
+ patch '/repp/v1/domains/contacts', params: { current_contact_id: 'william-001',
+ new_contact_id: 'john-001' },
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_response :ok
+ assert_equal ({ code: 1000,
+ message: 'Command completed successfully',
+ data: { affected_domains: ["airport.test"],
+ skipped_domains: ["shop.test"] }}),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
private
def http_auth_key
diff --git a/test/integration/api/domain_transfers_test.rb b/test/integration/api/domain_transfers_test.rb
index 3e9c10100..3ed5b0fc6 100644
--- a/test/integration/api/domain_transfers_test.rb
+++ b/test/integration/api/domain_transfers_test.rb
@@ -63,6 +63,23 @@ class APIDomainTransfersTest < ApplicationIntegrationTest
assert_equal 1, @new_registrar.contacts.where(name: 'William').size
end
+ def test_bulk_transfer_if_domain_has_update_prohibited_status
+ domains(:shop).update!(statuses: [DomainStatus::SERVER_UPDATE_PROHIBITED])
+
+ post '/repp/v1/domains/transfer', params: request_params, as: :json,
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_response :ok
+ assert_equal ({ code: 1000,
+ message: 'Command completed successfully',
+ data: { success: [],
+ failed: [{ type: "domain_transfer",
+ domain_name: "shop.test",
+ errors: [{:code=>"2304", :msg=>"Object status prohibits operation"}] }],
+ }}),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
private
def request_params
diff --git a/test/integration/api/nameservers/put_test.rb b/test/integration/api/nameservers/put_test.rb
index 77b01a9b1..a55014709 100644
--- a/test/integration/api/nameservers/put_test.rb
+++ b/test/integration/api/nameservers/put_test.rb
@@ -104,6 +104,25 @@ class APINameserversPutTest < ApplicationIntegrationTest
JSON.parse(response.body, symbolize_names: true)
end
+ def test_bulk_namesaervers_if_domain_update_prohibited
+ domains(:shop).update!(statuses: [DomainStatus::SERVER_UPDATE_PROHIBITED])
+
+ params = { data: { type: 'nameserver', id: domains(:shop).nameservers.hostnames[0],
+ attributes: { hostname: 'ns55.bestnames.test' } } }
+ put '/repp/v1/registrar/nameservers', params: params, as: :json,
+ headers: { 'HTTP_AUTHORIZATION' => http_auth_key }
+
+ assert_response :ok
+ assert_equal ({ code: 1000,
+ message: 'Command completed successfully',
+ data: { type: "nameserver",
+ id: "ns55.bestnames.test",
+ attributes: {hostname: "ns55.bestnames.test"},
+ affected_domains: ["airport.test"],
+ skipped_domains: ["shop.test"]}}),
+ JSON.parse(response.body, symbolize_names: true)
+ end
+
def test_unauthenticated
put '/repp/v1/registrar/nameservers'
assert_response 401
diff --git a/test/integration/api/registrant/registrant_api_contacts_test.rb b/test/integration/api/registrant/registrant_api_contacts_test.rb
index 191222764..f3998a2e9 100644
--- a/test/integration/api/registrant/registrant_api_contacts_test.rb
+++ b/test/integration/api/registrant/registrant_api_contacts_test.rb
@@ -57,6 +57,15 @@ class RegistrantApiContactsTest < ApplicationIntegrationTest
assert_equal({ errors: [base: ['Not authorized']] }, json_body)
end
+ def test_gets_contact_domain_links_when_requested
+ get "/api/v1/registrant/contacts/#{@contact.uuid}?links=true", headers: @auth_headers
+
+ expected_links = @contact.domains.uniq.map { |d| { name: d.name, id: d.uuid }}
+ assert_response :ok
+ response_json = JSON.parse(response.body, symbolize_names: true)
+
+ assert_empty expected_links - response_json[:links]
+ end
private
def auth_token
diff --git a/test/integration/api/registrant/registrant_api_domains_test.rb b/test/integration/api/registrant/registrant_api_domains_test.rb
index 61d635e5f..a8801f1b4 100644
--- a/test/integration/api/registrant/registrant_api_domains_test.rb
+++ b/test/integration/api/registrant/registrant_api_domains_test.rb
@@ -5,9 +5,10 @@ class RegistrantApiDomainsTest < ApplicationIntegrationTest
def setup
super
- @domain = domains(:hospital)
+ @domain = domains(:airport)
@registrant = @domain.registrant
@user = users(:registrant)
+ domains(:metro).tech_domain_contacts.update(contact_id: @registrant.id)
@auth_headers = { 'HTTP_AUTHORIZATION' => auth_token }
end
@@ -19,7 +20,14 @@ class RegistrantApiDomainsTest < ApplicationIntegrationTest
assert_equal('hospital.test', domain[:name])
assert_equal('5edda1a5-3548-41ee-8b65-6d60daf85a37', domain[:id])
- assert_equal({name: 'John', id: 'eb2f2766-b44c-4e14-9f16-32ab1a7cb957'}, domain[:registrant])
+ assert_equal({:name=>"John",
+ :id=>"eb2f2766-b44c-4e14-9f16-32ab1a7cb957",
+ :ident=>"1234", :ident_type=>"priv",
+ :ident_country_code=>"US",
+ :phone=>"+555.555",
+ :email=>"john@inbox.test",
+ :org=>false},
+ domain[:registrant])
assert_equal([{name: 'John',
id: 'eb2f2766-b44c-4e14-9f16-32ab1a7cb957',
email: 'john@inbox.test'}],
@@ -57,6 +65,46 @@ class RegistrantApiDomainsTest < ApplicationIntegrationTest
assert(array_of_domain_registrars.include?({name: 'Good Names', website: nil}))
end
+ def test_return_domain_list_with_registrants_and_admins
+ domains(:hospital).admin_domain_contacts.update(contact_id: contacts(:william).id)
+ domains(:hospital).update(registrant: contacts(:william).becomes(Registrant))
+
+ get '/api/v1/registrant/domains', headers: @auth_headers, params: { 'offset' => 0 }
+ assert_equal(200, response.status)
+
+ response_json = JSON.parse(response.body, symbolize_names: true)
+ response_json[:domains].each do |x|
+ if x[:registrant][:org] == false
+ x[:tech_contacts].each do |s|
+ assert_not s[:name].include?(@registrant.name)
+ end
+ end
+ end
+ end
+
+ def test_return_domain_list_with_registrants_and_admins_tech
+ get '/api/v1/registrant/domains', headers: @auth_headers, params: { 'offset' => 0, 'tech' => true }
+ assert_equal(200, response.status)
+
+ response_json = JSON.parse(response.body, symbolize_names: true)
+ response_json[:domains].each do |x|
+ if x[:name] == 'metro.test'
+ x[:tech_contacts].each do |s|
+ assert s[:name].include?(@registrant.name)
+ end
+ end
+ end
+ end
+
+ def test_domains_total_if_an_incomplete_list_is_returned
+ get '/api/v1/registrant/domains', headers: @auth_headers, params: { 'offset' => 0 }
+ assert_equal(200, response.status)
+
+ response_json = JSON.parse(response.body, symbolize_names: true)
+ assert_equal response_json[:domains].length, response_json[:count]
+ assert_equal response_json[:total], 5
+ end
+
def test_root_accepts_limit_and_offset_parameters
get '/api/v1/registrant/domains', params: { 'limit' => 2, 'offset' => 0 },
headers: @auth_headers
diff --git a/test/integration/api/registrant/registrant_api_registry_locks_test.rb b/test/integration/api/registrant/registrant_api_registry_locks_test.rb
index fb6d13aca..0de47dbc9 100644
--- a/test/integration/api/registrant/registrant_api_registry_locks_test.rb
+++ b/test/integration/api/registrant/registrant_api_registry_locks_test.rb
@@ -130,7 +130,15 @@ class RegistrantApiRegistryLocksTest < ApplicationIntegrationTest
response_json = JSON.parse(response.body, symbolize_names: true)
assert_equal({ name: 'Best Names', website: 'https://bestnames.test' }, response_json[:registrar])
- assert_equal({name: 'John', id: 'eb2f2766-b44c-4e14-9f16-32ab1a7cb957'}, response_json[:registrant])
+ assert_equal({:name=>"John",
+ :id=>"eb2f2766-b44c-4e14-9f16-32ab1a7cb957",
+ :ident=>"1234",
+ :ident_type=>"priv",
+ :ident_country_code=>"US",
+ :phone=>"+555.555",
+ :email=>"john@inbox.test",
+ :org=>false},
+ response_json[:registrant])
assert_equal([{name: 'Jane',
id: '9db3de62-2414-4487-bee2-d5c155567768',
email: 'jane@mail.test'
diff --git a/test/integration/api/v1/bounces/create_test.rb b/test/integration/api/v1/bounces/create_test.rb
index 899b6c5c7..0d3dc65d7 100644
--- a/test/integration/api/v1/bounces/create_test.rb
+++ b/test/integration/api/v1/bounces/create_test.rb
@@ -2,7 +2,7 @@ require 'test_helper'
class BouncesApiV1CreateTest < ActionDispatch::IntegrationTest
def setup
- @api_key = "Basic #{ENV['api_shared_key']}"
+ @api_key = "Basic #{ENV['rwhois_bounces_api_shared_key']}"
@headers = { "Authorization": "#{@api_key}" }
@json_body = { "data": valid_bounce_request }.as_json
end
diff --git a/test/integration/api/v1/contact_requests_test.rb b/test/integration/api/v1/contact_requests_test.rb
new file mode 100644
index 000000000..c9e2ac9bd
--- /dev/null
+++ b/test/integration/api/v1/contact_requests_test.rb
@@ -0,0 +1,68 @@
+require 'test_helper'
+
+class ApiV1ContactRequestTest < ActionDispatch::IntegrationTest
+ def setup
+ @api_key = "Basic #{ENV['rwhois_internal_api_shared_key']}"
+ @headers = { "Authorization": "#{@api_key}" }
+ @json_create = { "contact_request": valid_contact_request_create }.as_json
+ @json_update = { "contact_request": valid_contact_request_update }.as_json
+ @contact_request = contact_requests(:new)
+ end
+
+ def test_authorizes_api_request
+ post api_v1_contact_requests_path, params: @json_create, headers: @headers
+ assert_response :created
+
+ invalid_headers = { "Authorization": "Basic invalid_api_key" }
+ post api_v1_contact_requests_path, params: @json_create, headers: invalid_headers
+ assert_response :unauthorized
+ end
+
+ def test_saves_new_contact_request
+ request_body = @json_create.dup
+ random_mail = "#{rand(10000..99999)}@registry.test"
+ request_body['contact_request']['email'] = random_mail
+
+ post api_v1_contact_requests_path, params: request_body, headers: @headers
+ assert_response :created
+
+ contact_request = ContactRequest.last
+ assert_equal contact_request.email, random_mail
+ assert ContactRequest::STATUS_NEW, contact_request.status
+ end
+
+ def test_updates_existing_contact_request
+ request_body = @json_update.dup
+
+ put api_v1_contact_request_path(@contact_request.id), params: request_body, headers: @headers
+ assert_response :ok
+
+ @contact_request.reload
+ assert ContactRequest::STATUS_CONFIRMED, @contact_request.status
+ end
+
+ def test_not_updates_if_status_error
+ request_body = @json_update.dup
+ request_body['contact_request']['status'] = 'some_error_status'
+
+ put api_v1_contact_request_path(@contact_request.id), params: request_body, headers: @headers
+ assert_response 400
+
+ @contact_request.reload
+ assert ContactRequest::STATUS_NEW, @contact_request.status
+ end
+
+ def valid_contact_request_create
+ {
+ "email": "aaa@bbb.com",
+ "whois_record_id": "1",
+ "name": "test"
+ }.as_json
+ end
+
+ def valid_contact_request_update
+ {
+ "status": "#{ContactRequest::STATUS_CONFIRMED}",
+ }.as_json
+ end
+end
diff --git a/test/integration/api/v1/registrant/contacts/list_test.rb b/test/integration/api/v1/registrant/contacts/list_test.rb
index 2389019f1..33e8b67eb 100644
--- a/test/integration/api/v1/registrant/contacts/list_test.rb
+++ b/test/integration/api/v1/registrant/contacts/list_test.rb
@@ -1,5 +1,6 @@
require 'test_helper'
require 'auth_token/auth_token_creator'
+require 'json'
CompanyRegisterClientStub = Struct.new(:any_method) do
def representation_rights(citizen_personal_code:, citizen_country_code:)
@@ -55,6 +56,42 @@ class RegistrantApiV1ContactListTest < ActionDispatch::IntegrationTest
assert_equal '1234', response_json.first[:ident][:code]
end
+ def test_out_of_range_limit
+ get api_v1_registrant_contacts_path + "?limit=300", as: :json, headers: { 'HTTP_AUTHORIZATION' => auth_token }
+ response_json = JSON.parse(response.body, symbolize_names: true)
+
+ text_response = JSON.pretty_generate(response_json[:errors][0][:limit][0])
+
+ assert_equal text_response, '"parameter is out of range"'
+ end
+
+ def test_negative_offset
+ get api_v1_registrant_contacts_path + "?offset=-300", as: :json, headers: { 'HTTP_AUTHORIZATION' => auth_token }
+ response_json = JSON.parse(response.body, symbolize_names: true)
+
+ text_response = JSON.pretty_generate(response_json[:errors][0][:offset][0])
+
+ assert_equal text_response, '"parameter is out of range"'
+ end
+
+ def test_show_valid_contact
+ get api_v1_registrant_contacts_path + "/eb2f2766-b44c-4e14-9f16-32ab1a7cb957", as: :json, headers: { 'HTTP_AUTHORIZATION' => auth_token }
+ response_json = JSON.parse(response.body, symbolize_names: true)
+
+ text_response = response_json[:name]
+
+ assert_equal @contact[:name], text_response
+ end
+
+ def test_show_invalid_contact
+ get api_v1_registrant_contacts_path + "/435", as: :json, headers: { 'HTTP_AUTHORIZATION' => auth_token }
+ response_json = JSON.parse(response.body, symbolize_names: true)
+
+ text_response = response_json[:errors][0][:base][0]
+
+ assert_equal text_response, 'Contact not found'
+ end
+
private
def delete_direct_contact
diff --git a/test/integration/api/v1/registrant/contacts/update_test.rb b/test/integration/api/v1/registrant/contacts/update_test.rb
index 4ddf8b0ff..c1eaa005c 100644
--- a/test/integration/api/v1/registrant/contacts/update_test.rb
+++ b/test/integration/api/v1/registrant/contacts/update_test.rb
@@ -4,11 +4,12 @@ require 'auth_token/auth_token_creator'
class RegistrantApiV1ContactUpdateTest < ActionDispatch::IntegrationTest
setup do
@contact = contacts(:john)
+ @contact_org = contacts(:acme_ltd)
@original_address_processing = Setting.address_processing
@original_fax_enabled_setting = ENV['fax_enabled']
-
@user = users(:registrant)
+
end
teardown do
@@ -90,6 +91,32 @@ class RegistrantApiV1ContactUpdateTest < ActionDispatch::IntegrationTest
@contact.address
end
+ def test_update_address_when_enabled_without_address_params
+ Setting.address_processing = true
+
+ patch api_v1_registrant_contact_path(@contact.uuid), params: { address: { } },
+ as: :json,
+ headers: { 'HTTP_AUTHORIZATION' => auth_token }
+
+ assert_response :bad_request
+ @contact.reload
+ assert_equal Contact::Address.new(nil, nil, nil, nil, nil),
+ @contact.address
+ end
+
+ def test_update_address_when_enabled_without_address_params
+ Setting.address_processing = true
+
+ patch api_v1_registrant_contact_path(@contact.uuid), params: { },
+ as: :json,
+ headers: { 'HTTP_AUTHORIZATION' => auth_token }
+
+ assert_response :bad_request
+ @contact.reload
+ assert_equal Contact::Address.new(nil, nil, nil, nil, nil),
+ @contact.address
+ end
+
def test_address_is_optional_when_enabled
Setting.address_processing = true
@contact.update!(street: 'any', zip: 'any', city: 'any', state: 'any', country_code: 'US')
@@ -211,6 +238,21 @@ class RegistrantApiV1ContactUpdateTest < ActionDispatch::IntegrationTest
symbolize_names: true)
end
+ def test_org_disclosed_attributes
+ patch api_v1_registrant_contact_path(@contact_org.uuid), params: { disclosed_attributes: ["some_attr"] },
+ as: :json,
+ headers: { 'HTTP_AUTHORIZATION' => auth_token }
+
+ assert_response :bad_request
+
+ err_msg = "Legal person's data is visible by default and cannot be concealed. Please remove this parameter."
+
+ response_json = JSON.parse(response.body, symbolize_names: true)
+ response_msg = response_json[:errors][0][:disclosed_attributes][0]
+
+ assert_equal err_msg, response_msg
+ end
+
def test_unmanaged_contact_cannot_be_updated
assert_equal 'US-1234', @user.registrant_ident
@contact.update!(ident: '12345')
diff --git a/test/integration/epp/contact/check/base_test.rb b/test/integration/epp/contact/check/base_test.rb
index 528d69d86..8f7e3df16 100644
--- a/test/integration/epp/contact/check/base_test.rb
+++ b/test/integration/epp/contact/check/base_test.rb
@@ -26,7 +26,7 @@ class EppContactCheckBaseTest < EppTestCase
response_xml = Nokogiri::XML(response.body)
assert_epp_response :completed_successfully
- assert_equal 'john-001', response_xml.at_xpath('//contact:id', contact: xml_schema).text
+ assert_equal "#{@contact.registrar.code}:JOHN-001".upcase, response_xml.at_xpath('//contact:id', contact: xml_schema).text
end
def test_contact_is_available
@@ -52,7 +52,8 @@ class EppContactCheckBaseTest < EppTestCase
end
def test_contact_is_unavailable
- assert_equal 'john-001', @contact.code
+ @contact.update_columns(code: "#{@contact.registrar.code}:JOHN-001".upcase)
+ assert @contact.code, "#{@contact.registrar.code}:JOHN-001".upcase
request_xml = <<-XML
@@ -98,9 +99,61 @@ class EppContactCheckBaseTest < EppTestCase
assert_equal 3, response_xml.xpath('//contact:cd', contact: xml_schema).size
end
+ def test_check_contact_with_prefix
+ @contact.update_columns(code: "#{@contact.registrar.code}:JOHN-001".upcase)
+ assert @contact.code, "#{@contact.registrar.code}:JOHN-001".upcase
+
+ request_xml = <<-XML
+
+
+
+
+
+ BESTNAMES:JOHN-001
+
+
+
+
+ XML
+
+ post epp_check_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+
+ response_xml = Nokogiri::XML(response.body)
+ assert_epp_response :completed_successfully
+ assert_equal "#{@contact.registrar.code}:JOHN-001".upcase, response_xml.at_xpath('//contact:id', contact: xml_schema).text
+ assert_equal 'in use', response_xml.at_xpath('//contact:reason', contact: xml_schema).text
+ end
+
+ def test_check_contact_without_prefix
+ @contact.update_columns(code: "#{@contact.registrar.code}:JOHN-001".upcase)
+ assert @contact.code, "#{@contact.registrar.code}:JOHN-001".upcase
+
+ request_xml = <<-XML
+
+
+
+
+
+ JOHN-001
+
+
+
+
+ XML
+
+ post epp_check_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+
+ response_xml = Nokogiri::XML(response.body)
+ assert_epp_response :completed_successfully
+ assert_equal "#{@contact.registrar.code}:JOHN-001".upcase, response_xml.at_xpath('//contact:id', contact: xml_schema).text
+ assert_equal 'in use', response_xml.at_xpath('//contact:reason', contact: xml_schema).text
+ end
+
private
def xml_schema
'https://epp.tld.ee/schema/contact-ee-1.1.xsd'
end
-end
\ No newline at end of file
+end
diff --git a/test/integration/epp/contact/delete/base_test.rb b/test/integration/epp/contact/delete/base_test.rb
index 26ba63897..e86bea9dd 100644
--- a/test/integration/epp/contact/delete/base_test.rb
+++ b/test/integration/epp/contact/delete/base_test.rb
@@ -27,6 +27,60 @@ class EppContactDeleteBaseTest < EppTestCase
assert_epp_response :completed_successfully
end
+ def test_delete_contact_with_server_delete_prohibited
+ contact = deletable_contact
+ contact.update(statuses: Contact::SERVER_DELETE_PROHIBITED)
+ assert contact.statuses.include? Contact::SERVER_DELETE_PROHIBITED
+
+ contact.update_columns(code: contact.code.upcase)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{contact.code.upcase}
+
+
+
+
+ XML
+
+ post epp_delete_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+
+ assert Contact.exists?(id: contact.id)
+ assert_epp_response :object_status_prohibits_operation
+ end
+
+ def test_delete_contact_with_client_delete_prohibited
+ contact = deletable_contact
+ contact.update(statuses: Contact::CLIENT_DELETE_PROHIBITED)
+ assert contact.statuses.include? Contact::CLIENT_DELETE_PROHIBITED
+
+ contact.update_columns(code: contact.code.upcase)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{contact.code.upcase}
+
+
+
+
+ XML
+
+ post epp_delete_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+
+ assert Contact.exists?(id: contact.id)
+ assert_epp_response :object_status_prohibits_operation
+ end
+
def test_undeletable_cannot_be_deleted
contact = contacts(:john)
assert_not contact.deletable?
@@ -61,4 +115,4 @@ class EppContactDeleteBaseTest < EppTestCase
DomainContact.delete_all
contacts(:john)
end
-end
\ No newline at end of file
+end
diff --git a/test/integration/epp/contact/info/base_test.rb b/test/integration/epp/contact/info/base_test.rb
index 4e4a9190e..3edb6d461 100644
--- a/test/integration/epp/contact/info/base_test.rb
+++ b/test/integration/epp/contact/info/base_test.rb
@@ -44,6 +44,58 @@ class EppContactInfoBaseTest < EppTestCase
contact: xml_schema).text
end
+ def test_get_info_about_contact_with_prefix
+ @contact.update_columns(code: 'TEST:JOHN-001')
+ assert @contact.code, 'TEST:JOHN-001'
+
+ request_xml = <<-XML
+
+
+
+
+
+ TEST:JOHN-001
+
+
+
+
+ XML
+
+ post epp_info_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+
+ response_xml = Nokogiri::XML(response.body)
+ assert_epp_response :completed_successfully
+ assert_equal 'TEST:JOHN-001', response_xml.at_xpath('//contact:id', contact: xml_schema).text
+ assert_equal '+555.555', response_xml.at_xpath('//contact:voice', contact: xml_schema).text
+ end
+
+ def test_get_info_about_contact_without_prefix
+ @contact.update_columns(code: "#{@contact.registrar.code}:JOHN-001".upcase)
+ assert @contact.code, "#{@contact.registrar.code}:JOHN-001".upcase
+
+ request_xml = <<-XML
+
+
+
+
+
+ JOHN-001
+
+
+
+
+ XML
+
+ post epp_info_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+
+ response_xml = Nokogiri::XML(response.body)
+ assert_epp_response :completed_successfully
+ assert_equal "#{@contact.registrar.code}:JOHN-001".upcase, response_xml.at_xpath('//contact:id', contact: xml_schema).text
+ assert_equal '+555.555', response_xml.at_xpath('//contact:voice', contact: xml_schema).text
+ end
+
def test_hides_password_and_name_when_current_registrar_is_not_sponsoring
non_sponsoring_registrar = registrars(:goodnames)
@contact.update!(registrar: non_sponsoring_registrar)
diff --git a/test/integration/epp/domain/create/base_test.rb b/test/integration/epp/domain/create/base_test.rb
index 9d817524d..35ef38179 100644
--- a/test/integration/epp/domain/create/base_test.rb
+++ b/test/integration/epp/domain/create/base_test.rb
@@ -2,6 +2,51 @@ require 'test_helper'
class EppDomainCreateBaseTest < EppTestCase
+ def test_illegal_chars_in_dns_key
+ name = "new.#{dns_zones(:one).origin}"
+ contact = contacts(:john)
+ registrant = contact.becomes(Registrant)
+
+ pub_key = "AwEAAddt2AkLf\n
+ \n
+ YGKgiEZB5SmIF8E\n
+ vrjxNMH6HtxW\rEA4RJ9Ao6LCWheg8"
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{name}
+ #{registrant.code}
+
+
+
+
+
+ 257
+ 3
+ 8
+ #{pub_key}
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+ assert_no_difference 'Domain.count' do
+ post epp_create_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+
+ assert_epp_response :parameter_value_syntax_error
+ end
+
+
def test_not_registers_domain_without_legaldoc
now = Time.zone.parse('2010-07-05')
travel_to now
@@ -31,6 +76,230 @@ class EppDomainCreateBaseTest < EppTestCase
assert_epp_response :required_parameter_missing
end
+ def test_create_domain_with_unique_contact
+ now = Time.zone.parse('2010-07-05')
+ travel_to now
+ name = "new.#{dns_zones(:one).origin}"
+ contact = contacts(:john)
+ registrant = contact.becomes(Registrant)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{name}
+ #{registrant.code}
+ #{contacts(:jane).code}
+ #{contacts(:william).code}
+
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+
+ assert_difference 'Domain.count' do
+ post epp_create_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+ assert_epp_response :completed_successfully
+ end
+
+
+ def test_create_domain_with_array_of_not_unique_admins_and_techs
+ now = Time.zone.parse('2010-07-05')
+ travel_to now
+ name = "new.#{dns_zones(:one).origin}"
+ contact = contacts(:john)
+ registrant = contact.becomes(Registrant)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{name}
+ #{registrant.code}
+ #{contact.code}
+ #{contact.code}
+ #{contact.code}
+ #{contact.code}
+
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+
+ assert_no_difference 'Domain.count' do
+ post epp_create_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+
+ assert_epp_response :parameter_value_policy_error
+ end
+
+ def test_create_domain_with_array_of_not_unique_admins
+ now = Time.zone.parse('2010-07-05')
+ travel_to now
+ name = "new.#{dns_zones(:one).origin}"
+ contact = contacts(:john)
+ registrant = contact.becomes(Registrant)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{name}
+ #{registrant.code}
+ #{contact.code}
+ #{contact.code}
+ #{contact.code}
+
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+
+ assert_no_difference 'Domain.count' do
+ post epp_create_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+
+ assert_epp_response :parameter_value_policy_error
+ end
+
+ def test_create_domain_with_array_of_not_unique_techs
+ now = Time.zone.parse('2010-07-05')
+ travel_to now
+ name = "new.#{dns_zones(:one).origin}"
+ contact = contacts(:john)
+ registrant = contact.becomes(Registrant)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{name}
+ #{registrant.code}
+ #{contact.code}
+ #{contact.code}
+ #{contact.code}
+
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+
+ assert_no_difference 'Domain.count' do
+ post epp_create_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+
+ assert_epp_response :parameter_value_policy_error
+ end
+
+ def test_create_domain_with_array_of_not_unique_admin_but_tech_another_one
+ now = Time.zone.parse('2010-07-05')
+ travel_to now
+ name = "new.#{dns_zones(:one).origin}"
+ contact = contacts(:john)
+ registrant = contact.becomes(Registrant)
+ contact_two = contacts(:william)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{name}
+ #{registrant.code}
+ #{contact.code}
+ #{contact.code}
+ #{contact_two.code}
+
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+
+ assert_no_difference 'Domain.count' do
+ post epp_create_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+
+ assert_epp_response :parameter_value_policy_error
+ end
+
+ def test_create_domain_with_array_of_not_unique_techs_but_admin_another_one
+ now = Time.zone.parse('2010-07-05')
+ travel_to now
+ name = "new.#{dns_zones(:one).origin}"
+ contact = contacts(:john)
+ registrant = contact.becomes(Registrant)
+ contact_two = contacts(:william)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{name}
+ #{registrant.code}
+ #{contact_two.code}
+ #{contact.code}
+ #{contact.code}
+
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+
+ assert_no_difference 'Domain.count' do
+ post epp_create_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+
+ assert_epp_response :parameter_value_policy_error
+ end
+
def test_registers_new_domain_with_required_attributes
now = Time.zone.parse('2010-07-05')
travel_to now
diff --git a/test/integration/epp/domain/delete/base_test.rb b/test/integration/epp/domain/delete/base_test.rb
index 56a3cc31e..d32a89f63 100644
--- a/test/integration/epp/domain/delete/base_test.rb
+++ b/test/integration/epp/domain/delete/base_test.rb
@@ -133,6 +133,40 @@ class EppDomainDeleteBaseTest < EppTestCase
assert_epp_response :completed_successfully
end
+ def test_deletes_on_update_prohibited
+ assert_equal 'shop.test', @domain.name
+ @domain.update(statuses: [DomainStatus::SERVER_UPDATE_PROHIBITED])
+ Setting.request_confirmation_on_domain_deletion_enabled = false
+
+ request_xml = <<-XML
+
+
+
+
+
+ shop.test
+
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+
+ perform_enqueued_jobs do
+ post epp_delete_path, params: { frame: request_xml }, headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+ @domain.reload
+
+ assert_not @domain.registrant_verification_asked?
+ assert_not @domain.pending_delete_confirmation?
+ assert_no_emails
+ assert_epp_response :completed_successfully
+ end
+
def test_skips_registrant_confirmation_when_required_but_already_verified_by_registrar
assert_equal 'shop.test', @domain.name
Setting.request_confirmation_on_domain_deletion_enabled = true
diff --git a/test/integration/epp/domain/transfer/request_test.rb b/test/integration/epp/domain/transfer/request_test.rb
index 1c3614421..273a9f490 100644
--- a/test/integration/epp/domain/transfer/request_test.rb
+++ b/test/integration/epp/domain/transfer/request_test.rb
@@ -3,6 +3,7 @@ require 'test_helper'
class EppDomainTransferRequestTest < EppTestCase
def setup
@domain = domains(:shop)
+ @contact = contacts(:jane)
@new_registrar = registrars(:goodnames)
@original_transfer_wait_time = Setting.transfer_wait_time
Setting.transfer_wait_time = 0
@@ -12,6 +13,95 @@ class EppDomainTransferRequestTest < EppTestCase
Setting.transfer_wait_time = @original_transfer_wait_time
end
+ def test_transfer_domain_with_contacts_if_registrant_and_tech_are_shared
+ @domain.tech_domain_contacts[0].update!(contact_id: @domain.registrant.id)
+
+ @domain.tech_domain_contacts[1].delete
+ @domain.reload
+
+ post epp_transfer_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_goodnames' }
+
+ assert_epp_response :completed_successfully
+
+ @domain.reload
+
+ tech = Contact.find_by(id: @domain.tech_domain_contacts[0].contact_id)
+
+ assert_equal @domain.contacts.where(original_id: @domain.registrant.original_id).count, 1
+ assert_equal tech.registrar_id, @domain.registrar.id
+ end
+
+ def test_transfer_domain_with_contacts_if_registrant_and_admin_are_shared
+ @domain.admin_domain_contacts[0].update!(contact_id: @domain.registrant.id)
+ @domain.tech_domain_contacts[0].update!(contact_id: @contact.id)
+
+ @domain.tech_domain_contacts[1].delete
+ @domain.reload
+
+ post epp_transfer_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_goodnames' }
+
+ assert_epp_response :completed_successfully
+
+ @domain.reload
+
+ admin = Contact.find_by(id: @domain.admin_domain_contacts[0].contact_id)
+
+ assert_equal @domain.contacts.where(original_id: @domain.registrant.original_id).count, 1
+ assert_equal admin.registrar_id, @domain.registrar.id
+ end
+
+ def test_transfer_domain_with_contacts_if_admin_and_tech_are_shared
+ @domain.admin_domain_contacts[0].update!(contact_id: @contact.id)
+ @domain.tech_domain_contacts[0].update!(contact_id: @contact.id)
+
+ @domain.tech_domain_contacts[1].delete
+ @domain.reload
+
+ post epp_transfer_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_goodnames' }
+
+ assert_epp_response :completed_successfully
+
+ @domain.reload
+
+ admin = Contact.find_by(id: @domain.admin_domain_contacts[0].contact_id)
+ tech = Contact.find_by(id: @domain.tech_domain_contacts[0].contact_id)
+
+ result_hash = @domain.contacts.pluck(:original_id).group_by(&:itself).transform_values(&:count)
+ assert result_hash[admin.original_id], 2
+
+ assert_equal admin.registrar_id, @domain.registrar.id
+ assert_equal tech.registrar_id, @domain.registrar.id
+ end
+
+ def test_transfer_domain_with_contacts_if_admin_and_tech_and_registrant_are_shared
+ @domain.tech_domain_contacts[0].update!(contact_id: @domain.registrant.id)
+ @domain.admin_domain_contacts[0].update!(contact_id: @domain.registrant.id)
+
+ @domain.tech_domain_contacts[1].delete
+ @domain.reload
+
+ post epp_transfer_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_goodnames' }
+
+ assert_epp_response :completed_successfully
+
+ @domain.reload
+
+ admin = Contact.find_by(id: @domain.admin_domain_contacts[0].contact_id)
+ tech = Contact.find_by(id: @domain.tech_domain_contacts[0].contact_id)
+
+ assert_equal @domain.contacts.where(original_id: @domain.registrant.original_id).count, 2
+
+ result_hash = @domain.contacts.pluck(:original_id).group_by(&:itself).transform_values(&:count)
+ assert result_hash[@domain.registrant.original_id], 2
+
+ assert_equal admin.registrar_id, @domain.registrar.id
+ assert_equal tech.registrar_id, @domain.registrar.id
+ end
+
def test_transfers_domain_at_once
post epp_transfer_path, params: { frame: request_xml },
headers: { 'HTTP_COOKIE' => 'session=api_goodnames' }
diff --git a/test/integration/epp/domain/update/base_test.rb b/test/integration/epp/domain/update/base_test.rb
index 7ddcb35ad..83ba65478 100644
--- a/test/integration/epp/domain/update/base_test.rb
+++ b/test/integration/epp/domain/update/base_test.rb
@@ -63,6 +63,27 @@ class EppDomainUpdateBaseTest < EppTestCase
assert_epp_response :object_status_prohibits_operation
end
+ def test_prohibited_domain_cannot_be_updated
+ @domain.update!(statuses: [DomainStatus::SERVER_UPDATE_PROHIBITED])
+
+ request_xml = <<-XML
+
+
+
+
+
+ shop.test
+
+
+
+
+ XML
+
+ post epp_update_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ assert_epp_response :object_status_prohibits_operation
+ end
+
def test_does_not_return_server_delete_prohibited_status_when_pending_update_status_is_set
@domain.update!(statuses: [DomainStatus::SERVER_DELETE_PROHIBITED,
DomainStatus::PENDING_UPDATE])
@@ -124,6 +145,46 @@ class EppDomainUpdateBaseTest < EppTestCase
assert_verification_and_notification_emails
end
+ def test_domain_should_doesnt_have_pending_update_when_updated_registrant_with_same_idents_data
+ assert_not @domain.statuses.include? "pendingUpdate"
+
+ old_registrant = @domain.registrant
+ new_registrant = contacts(:william).becomes(Registrant)
+
+ new_registrant.update(ident: old_registrant.ident)
+ new_registrant.update(ident_country_code: old_registrant.ident_country_code)
+ new_registrant.update(ident_type: old_registrant.ident_type)
+
+ request_xml = <<-XML
+
+
+
+
+
+ #{@domain.name}
+
+ #{new_registrant.code}
+
+
+
+
+
+ #{'test' * 2000}
+
+
+
+
+ XML
+
+ post epp_update_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ @domain.reload
+ assert_epp_response :completed_successfully
+
+ assert_equal @domain.registrant, new_registrant
+ assert_not @domain.statuses.include? "pendingUpdate"
+ end
+
def test_requires_verification_from_current_registrant_when_not_yet_verified_by_registrar
Setting.request_confirmation_on_registrant_change_enabled = true
new_registrant = contacts(:william)
diff --git a/test/integration/epp/poll_test.rb b/test/integration/epp/poll_test.rb
index 6d3ec467e..a18fdbe4e 100644
--- a/test/integration/epp/poll_test.rb
+++ b/test/integration/epp/poll_test.rb
@@ -26,6 +26,31 @@ class EppPollTest < EppTestCase
assert_equal 'Your domain has been updated', xml_doc.at_css('msgQ msg').text
end
+ def test_does_not_drop_error_if_old_version
+ version = Version::DomainVersion.last
+ @notification.update(attached_obj_type: 'DomainVersion', attached_obj_id: version.id)
+
+ request_xml = <<-XML
+
+
+
+
+
+
+ XML
+ assert_nothing_raised do
+ post epp_poll_path, params: { frame: request_xml },
+ headers: { 'HTTP_COOKIE' => 'session=api_bestnames' }
+ end
+
+ xml_doc = Nokogiri::XML(response.body)
+ assert_epp_response :completed_successfully_ack_to_dequeue
+ assert_equal 2.to_s, xml_doc.at_css('msgQ')[:count]
+ assert_equal @notification.id.to_s, xml_doc.at_css('msgQ')[:id]
+ assert_equal Time.zone.parse('2010-07-05').utc.xmlschema, xml_doc.at_css('msgQ qDate').text
+ assert_equal 'Your domain has been updated', xml_doc.at_css('msgQ msg').text
+ end
+
def test_return_action_data_when_present
@notification.update!(action: actions(:contact_update))
diff --git a/test/integration/registrant_area/contacts_test.rb b/test/integration/registrant_area/contacts_test.rb
deleted file mode 100644
index c906cd026..000000000
--- a/test/integration/registrant_area/contacts_test.rb
+++ /dev/null
@@ -1,19 +0,0 @@
-require 'test_helper'
-
-class RegistrantAreaContactsIntegrationTest < ApplicationIntegrationTest
- setup do
- @domain = domains(:shop)
- @registrant = users(:registrant)
- sign_in @registrant
- end
-
- def test_can_view_other_domain_contacts
- secondary_contact = contacts(:jane)
-
- visit registrant_domain_path(@domain)
- assert_text secondary_contact.name
- click_link secondary_contact.name
- assert_text @domain.name
- assert_text secondary_contact.email
- end
-end
diff --git a/test/integration/registrant_area/domain_delete_confirmations.rb b/test/integration/registrant_area/domain_delete_confirmations.rb
deleted file mode 100644
index 29bca7ed9..000000000
--- a/test/integration/registrant_area/domain_delete_confirmations.rb
+++ /dev/null
@@ -1,30 +0,0 @@
-require 'test_helper'
-
-class RegistrantAreaDomainDeleteConfirmationIntegrationTest < ActionDispatch::IntegrationTest
- include ActionMailer::TestHelper
-
- setup do
- @domain = domains(:shop)
- ActionMailer::Base.deliveries.clear
- end
-
- def test_notifies_registrant_by_email_when_accepted
- @domain.update!(registrant_verification_asked_at: Time.zone.now,
- registrant_verification_token: 'test',
- statuses: [DomainStatus::PENDING_DELETE_CONFIRMATION])
-
- patch registrant_domain_delete_confirm_path(@domain, token: 'test', confirmed: true)
-
- assert_emails 1
- end
-
- def test_notifies_registrant_by_email_when_rejected
- @domain.update!(registrant_verification_asked_at: Time.zone.now,
- registrant_verification_token: 'test',
- statuses: [DomainStatus::PENDING_DELETE_CONFIRMATION])
-
- patch registrant_domain_delete_confirm_path(@domain, token: 'test', rejected: true)
-
- assert_emails 1
- end
-end
\ No newline at end of file
diff --git a/test/integration/registrant_area/domains_test.rb b/test/integration/registrant_area/domains_test.rb
deleted file mode 100644
index d2ca1c775..000000000
--- a/test/integration/registrant_area/domains_test.rb
+++ /dev/null
@@ -1,25 +0,0 @@
-require 'test_helper'
-
-class RegistrantAreaDomainsIntegrationTest < ApplicationIntegrationTest
- setup do
- sign_in users(:registrant)
- end
-
- def test_downloads_list_as_csv
- get registrant_domains_path(format: :csv)
-
- assert_response :ok
- assert_equal "#{Mime[:csv]}; charset=utf-8", response.headers['Content-Type']
- assert_equal "attachment; filename=\"domains.csv\"; filename*=UTF-8''domains.csv", response.headers['Content-Disposition']
- assert_not_empty response.body
- end
-
- def test_downloads_list_as_pdf
- get registrant_domains_path(format: :pdf)
-
- assert_response :ok
- assert_equal Mime[:pdf], response.headers['Content-Type']
- assert_equal "attachment; filename=\"domains.pdf\"; filename*=UTF-8''domains.pdf", response.headers['Content-Disposition']
- assert_not_empty response.body
- end
-end
diff --git a/test/integration/repp/v1/accounts/balance_test.rb b/test/integration/repp/v1/accounts/balance_test.rb
index 785e0aee8..4b711bd05 100644
--- a/test/integration/repp/v1/accounts/balance_test.rb
+++ b/test/integration/repp/v1/accounts/balance_test.rb
@@ -2,6 +2,7 @@ require 'test_helper'
class ReppV1BalanceTest < ActionDispatch::IntegrationTest
def setup
+ travel_to Time.zone.parse('2010-07-05')
@registrar = users(:api_bestnames)
token = Base64.encode64("#{@registrar.username}:#{@registrar.plain_text_password}")
token = "Basic #{token}"
@@ -19,4 +20,32 @@ class ReppV1BalanceTest < ActionDispatch::IntegrationTest
assert_equal @registrar.registrar.cash_account.balance.to_s, json[:data][:balance]
assert_equal @registrar.registrar.cash_account.currency, json[:data][:currency]
end
+
+ def test_can_query_balance_with_details
+ # Create new billable action to get activity
+ post "/repp/v1/domains/renew/bulk", headers: @auth_headers, params: { domains: ['shop.test'], renew_period: '1y' }
+
+ started_from = "2010-07-05"
+ end_to = DateTime.current.to_date.to_s(:db)
+
+ get "/repp/v1/accounts/balance?detailed=true", headers: @auth_headers
+ json = JSON.parse(response.body, symbolize_names: true)
+
+ assert_response :ok
+ assert_equal 1000, json[:code]
+ assert_equal 'Command completed successfully', json[:message]
+ assert_equal @registrar.registrar.cash_account.balance.to_s, json[:data][:balance]
+ assert_equal @registrar.registrar.cash_account.currency, json[:data][:currency]
+ entry = json[:data][:transactions].last
+ assert_equal @registrar.registrar.cash_account.account_activities.last.created_at, entry[:created_at]
+ assert_equal @registrar.registrar.cash_account.account_activities.last.description, entry[:description]
+ assert_equal 'debit', entry[:type]
+ assert_equal @registrar.registrar.cash_account.account_activities.last.sum.to_s, entry[:sum]
+ assert_equal @registrar.registrar.cash_account.account_activities.last.new_balance.to_s, entry[:balance]
+
+ json[:data][:transactions].map do |trans|
+ assert trans[:created_at].to_date.to_s(:db) >= started_from
+ assert trans[:created_at].to_date.to_s(:db) >= end_to
+ end
+ end
end
diff --git a/test/integration/repp/v1/domains/bulk_renew_test.rb b/test/integration/repp/v1/domains/bulk_renew_test.rb
index 4cec91914..46e2fbf7d 100644
--- a/test/integration/repp/v1/domains/bulk_renew_test.rb
+++ b/test/integration/repp/v1/domains/bulk_renew_test.rb
@@ -37,6 +37,29 @@ class ReppV1DomainsBulkRenewTest < ActionDispatch::IntegrationTest
end
end
+ def test_keeps_update_prohibited_status
+ domain = domains(:shop)
+ domain.update(statuses: [DomainStatus::CLIENT_UPDATE_PROHIBITED, DomainStatus::SERVER_UPDATE_PROHIBITED])
+ payload = {
+ "domains": [
+ 'shop.test'
+ ],
+ "renew_period": "1y"
+ }
+
+ assert_changes -> { Domain.find_by(name: 'shop.test').valid_to } do
+ post "/repp/v1/domains/renew/bulk", headers: @auth_headers, params: payload
+ json = JSON.parse(response.body, symbolize_names: true)
+
+ assert_response :ok
+ assert_equal 1000, json[:code]
+ assert_equal 'Command completed successfully', json[:message]
+ assert json[:data][:updated_domains].include? 'shop.test'
+ end
+ domain.reload
+ assert_equal domain.statuses, [DomainStatus::CLIENT_UPDATE_PROHIBITED, DomainStatus::SERVER_UPDATE_PROHIBITED]
+ end
+
def test_throws_error_when_domain_not_renewable
payload = {
"domains": [
diff --git a/test/integration/repp/v1/registrar/nameservers_test.rb b/test/integration/repp/v1/registrar/nameservers_test.rb
index f01769dfb..e2c6f890b 100644
--- a/test/integration/repp/v1/registrar/nameservers_test.rb
+++ b/test/integration/repp/v1/registrar/nameservers_test.rb
@@ -34,6 +34,33 @@ class ReppV1RegistrarNameserversTest < ActionDispatch::IntegrationTest
assert json[:data][:affected_domains].include? 'shop.test'
end
+ def test_fails_to_update_if_prohibited
+ domain = domains(:shop)
+ domain.update(statuses: [DomainStatus::CLIENT_UPDATE_PROHIBITED])
+ nameserver = nameservers(:shop_ns1)
+ payload = {
+ "data": {
+ "id": nameserver.hostname,
+ "type": "nameserver",
+ "attributes": {
+ "hostname": "#{nameserver.hostname}.test",
+ "ipv4": ["1.1.1.1"]
+ }
+ }
+ }
+
+ put '/repp/v1/registrar/nameservers', headers: @auth_headers, params: payload
+ json = JSON.parse(response.body, symbolize_names: true)
+
+ assert_response :ok
+ assert_equal 1000, json[:code]
+ assert_equal 'Command completed successfully', json[:message]
+ assert_equal({ hostname: "#{nameserver.hostname}.test", ipv4: ["1.1.1.1"] }, json[:data][:attributes])
+ assert_equal({ hostname: "#{nameserver.hostname}.test", ipv4: ["1.1.1.1"] }, json[:data][:attributes])
+ assert json[:data][:affected_domains].include? 'airport.test'
+ assert json[:data][:skipped_domains].include? 'shop.test'
+ end
+
def test_nameserver_with_hostname_must_exist
payload = {
"data": {
diff --git a/test/integration/repp/v1/retained_domains_test.rb b/test/integration/repp/v1/retained_domains_test.rb
index 1c9f49f58..824c826ef 100644
--- a/test/integration/repp/v1/retained_domains_test.rb
+++ b/test/integration/repp/v1/retained_domains_test.rb
@@ -21,7 +21,7 @@ class ReppV1RetainedDomainsTest < ActionDispatch::IntegrationTest
status: 'reserved',
punycode_name: 'reserved.test' }]
- assert_equal response_json[:domains], expected_objects
+ assert_empty response_json[:domains] - expected_objects
end
def test_get_index_with_type_parameter
@@ -77,7 +77,7 @@ class ReppV1RetainedDomainsTest < ActionDispatch::IntegrationTest
status: 'disputed',
punycode_name: 'reserved.test' }]
- assert_equal response_json[:domains], expected_objects
+ assert_empty response_json[:domains] - expected_objects
end
def test_etags_cache
diff --git a/test/jobs/domain_update_confirm_job_test.rb b/test/jobs/domain_update_confirm_job_test.rb
index ded0d3d8a..d2d3a3252 100644
--- a/test/jobs/domain_update_confirm_job_test.rb
+++ b/test/jobs/domain_update_confirm_job_test.rb
@@ -1,5 +1,4 @@
require "test_helper"
-
class DomainUpdateConfirmJobTest < ActiveSupport::TestCase
def setup
super
@@ -19,6 +18,22 @@ class DomainUpdateConfirmJobTest < ActiveSupport::TestCase
super
end
+ def test_registrant_locked_domain
+ refute @domain.locked_by_registrant?
+ @domain.apply_registry_lock
+ assert @domain.locked_by_registrant?
+ assert_equal(@domain.registrar.notifications.last.text, "Domain #{@domain.name} has been locked by registrant")
+ end
+
+ def test_registrant_unlocked_domain
+ refute @domain.locked_by_registrant?
+ @domain.apply_registry_lock
+ assert @domain.locked_by_registrant?
+ @domain.remove_registry_lock
+ refute @domain.locked_by_registrant?
+ assert_equal(@domain.registrar.notifications.last.text, "Domain #{@domain.name} has been unlocked by registrant")
+ end
+
def test_rejected_registrant_verification_notifies_registrar
DomainUpdateConfirmJob.perform_now(@domain.id, RegistrantVerification::REJECTED)
diff --git a/test/lib/serializers/registrant_api/domain_test.rb b/test/lib/serializers/registrant_api/domain_test.rb
index f2623741f..2e68e4293 100644
--- a/test/lib/serializers/registrant_api/domain_test.rb
+++ b/test/lib/serializers/registrant_api/domain_test.rb
@@ -30,8 +30,15 @@ class SerializersRegistrantApiDomainTest < ActiveSupport::TestCase
assert_equal({name: 'Best Names', website: 'https://bestnames.test' }, @json[:registrar])
end
- def test_returns_registrant_name_and_uuid
- assert_equal({name: 'John', id: 'eb2f2766-b44c-4e14-9f16-32ab1a7cb957'},
+ def test_returns_registrant_name_uuid_and_org
+ assert_equal({:name=>"John",
+ :id=>"eb2f2766-b44c-4e14-9f16-32ab1a7cb957",
+ :ident=>"1234",
+ :ident_type=>"priv",
+ :ident_country_code=>"US",
+ :phone=>"+555.555",
+ :email=>"john@inbox.test",
+ :org=>false},
@json[:registrant])
end
diff --git a/test/mailers/registrant_change_mailer_test.rb b/test/mailers/registrant_change_mailer_test.rb
index 5d14972e3..5ddfc76db 100644
--- a/test/mailers/registrant_change_mailer_test.rb
+++ b/test/mailers/registrant_change_mailer_test.rb
@@ -72,11 +72,14 @@ class RegistrantChangeMailerTest < ActionMailer::TestCase
email = RegistrantChangeMailer.expired(domain: @domain,
registrar: @domain.registrar,
- registrant: @domain.registrant).deliver_now
+ registrant: @domain.registrant,
+ send_to: [@domain.new_registrant_email,
+ @domain.registrant.email],
+ ).deliver_now
assert_emails 1
- assert_equal ['william@inbox.test'], email.to
+ assert_equal ['william@inbox.test', @domain.registrant.email], email.to
assert_equal 'Domeeni shop.test registreerija vahetuse taotlus on tühistatud' \
' / shop.test registrant change cancelled', email.subject
end
-end
\ No newline at end of file
+end
diff --git a/test/models/concerns/versions_test.rb b/test/models/concerns/versions_test.rb
index 2a54b4476..bc823d51c 100644
--- a/test/models/concerns/versions_test.rb
+++ b/test/models/concerns/versions_test.rb
@@ -7,7 +7,7 @@ class VersionsTest < ActiveSupport::TestCase
@nameserver.update(hostname: 'ns99.bestnames.test')
@ignored_column_title = Nameserver.ignored_columns.first
- version = NameserverVersion.last
+ version = Version::NameserverVersion.last
hash = version.object
hash[@ignored_column_title] = 123456
version.update(object: hash)
diff --git a/test/models/contact/archivable_test.rb b/test/models/contact/archivable_test.rb
index 340ca54e0..cd07d3894 100644
--- a/test/models/contact/archivable_test.rb
+++ b/test/models/contact/archivable_test.rb
@@ -6,8 +6,8 @@ class ArchivableContactTest < ActiveSupport::TestCase
end
def test_contact_is_archivable_when_it_was_linked_and_inactivity_period_has_passed
- DomainVersion.stub(:was_contact_linked?, true) do
- DomainVersion.stub(:contact_unlinked_more_than?, true) do
+ Version::DomainVersion.stub(:was_contact_linked?, true) do
+ Version::DomainVersion.stub(:contact_unlinked_more_than?, true) do
assert @contact.archivable?
end
end
@@ -18,7 +18,7 @@ class ArchivableContactTest < ActiveSupport::TestCase
@contact.created_at = Time.zone.parse('2010-07-05 00:00:00')
travel_to Time.zone.parse('2010-07-05 00:00:01')
- DomainVersion.stub(:was_contact_linked?, false) do
+ Version::DomainVersion.stub(:was_contact_linked?, false) do
assert @contact.archivable?
end
end
@@ -28,14 +28,14 @@ class ArchivableContactTest < ActiveSupport::TestCase
@contact.created_at = Time.zone.parse('2010-07-05')
travel_to Time.zone.parse('2010-07-05')
- DomainVersion.stub(:contact_unlinked_more_than?, false) do
+ Version::DomainVersion.stub(:contact_unlinked_more_than?, false) do
assert_not @contact.archivable?
end
end
def test_contact_is_not_archivable_when_it_was_ever_linked_but_linked_within_inactivity_period
- DomainVersion.stub(:was_contact_linked?, true) do
- DomainVersion.stub(:contact_unlinked_more_than?, false) do
+ Version::DomainVersion.stub(:was_contact_linked?, true) do
+ Version::DomainVersion.stub(:contact_unlinked_more_than?, false) do
assert_not @contact.archivable?
end
end
@@ -73,7 +73,7 @@ class ArchivableContactTest < ActiveSupport::TestCase
def archivable_contact
contact = contacts(:john)
Setting.orphans_contacts_in_months = 0
- DomainVersion.delete_all
+ Version::DomainVersion.delete_all
other_contact = contacts(:william)
assert_not_equal other_contact, contact
diff --git a/test/models/domain/force_delete_test.rb b/test/models/domain/force_delete_test.rb
index 2bb1b5b8f..19338f495 100644
--- a/test/models/domain/force_delete_test.rb
+++ b/test/models/domain/force_delete_test.rb
@@ -234,6 +234,19 @@ class ForceDeleteTest < ActionMailer::TestCase
assert_includes(@domain.statuses, asserted_status)
end
+ def test_client_hold_prohibits_manual_inzone
+ @domain.update(valid_to: Time.zone.parse('2012-08-05'))
+ @domain.update(template_name: 'legal_person')
+ travel_to Time.zone.parse('2010-07-05')
+ @domain.schedule_force_delete(type: :soft)
+ travel_to Time.zone.parse('2010-08-21')
+ Domains::ClientHold::SetClientHold.run!
+ @domain.reload
+
+ @domain.statuses << DomainStatus::SERVER_MANUAL_INZONE
+ assert_not @domain.valid?
+ end
+
def test_force_delete_soft_year_ahead_not_sets_client_hold_before_threshold
asserted_status = DomainStatus::CLIENT_HOLD
diff --git a/test/models/domain/releasable/auctionable_test.rb b/test/models/domain/releasable/auctionable_test.rb
index de3ac0ff6..d24f46913 100644
--- a/test/models/domain/releasable/auctionable_test.rb
+++ b/test/models/domain/releasable/auctionable_test.rb
@@ -25,6 +25,7 @@ class DomainReleasableAuctionableTest < ActiveSupport::TestCase
def test_skips_auction_when_domains_is_blocked
assert_equal 'shop.test', @domain.name
blocked_domains(:one).update!(name: 'shop.test')
+ @domain.save!(validate: false)
@domain.release
@@ -34,6 +35,7 @@ class DomainReleasableAuctionableTest < ActiveSupport::TestCase
def test_skips_auction_when_domains_is_reserved
assert_equal 'shop.test', @domain.name
reserved_domains(:one).update!(name: 'shop.test')
+ @domain.save!(validate: false)
@domain.release
@@ -58,6 +60,24 @@ class DomainReleasableAuctionableTest < ActiveSupport::TestCase
end
end
+ def test_updates_whois_server
+ @domain.update!(delete_date: '2010-07-04')
+ travel_to Time.zone.parse('2010-07-05')
+ old_whois = @domain.whois_record
+
+ Domain.release_domains
+
+ assert_raises ActiveRecord::RecordNotFound do
+ old_whois.reload
+ end
+
+ whois_record = Whois::Record.find_by(name: @domain.name)
+ json = { "name"=>@domain.name,
+ "status"=>["AtAuction"],
+ "disclaimer"=> Setting.registry_whois_disclaimer }
+ assert_equal whois_record.json, json
+ end
+
def test_notifies_registrar
@domain.update!(delete_date: '2010-07-04')
travel_to Time.zone.parse('2010-07-05')
diff --git a/test/models/domain_test.rb b/test/models/domain_test.rb
index ae12f4a1e..15ab8b0c2 100644
--- a/test/models/domain_test.rb
+++ b/test/models/domain_test.rb
@@ -69,6 +69,12 @@ class DomainTest < ActiveSupport::TestCase
domain.name = 'xn--mnchen-3ya.test'
assert domain.valid?
+
+ domain.name = '####'
+ assert domain.invalid?
+
+ domain.name = 'https://example.test'
+ assert domain.invalid?
end
def test_invalid_when_name_is_already_taken
diff --git a/test/models/registrant_verification_test.rb b/test/models/registrant_verification_test.rb
index ef4038784..a8707fd85 100644
--- a/test/models/registrant_verification_test.rb
+++ b/test/models/registrant_verification_test.rb
@@ -15,7 +15,7 @@ class RegistrantVerificationTest < ActiveSupport::TestCase
registrant_verification = registrant_verifications(:one)
random_action = "random#{rand(100)}"
- assert_difference -> { RegistrantVerificationVersion.count } do
+ assert_difference -> { Version::RegistrantVerificationVersion.count } do
registrant_verification.update_attributes!(action: random_action)
end
end
@@ -23,11 +23,11 @@ class RegistrantVerificationTest < ActiveSupport::TestCase
def test_reject_changes
@registrant_verification = RegistrantVerification.new(domain_id: @domain.id,
verification_token: @token)
- start_versions_count = RegistrantVerificationVersion.count
+ start_versions_count = Version::RegistrantVerificationVersion.count
assert_nothing_raised do
@registrant_verification.domain_registrant_change_reject!("email link, #{@initiator}")
end
- assert_equal RegistrantVerificationVersion.count, start_versions_count + 1
+ assert_equal Version::RegistrantVerificationVersion.count, start_versions_count + 1
end
end
diff --git a/test/models/version/domain_version_test.rb b/test/models/version/domain_version_test.rb
index 719fcf3ba..be8b020c4 100644
--- a/test/models/version/domain_version_test.rb
+++ b/test/models/version/domain_version_test.rb
@@ -11,7 +11,7 @@ class DomainVersionTest < ActiveSupport::TestCase
tech_contacts: [],
registrant: [@contact.id] })
- assert DomainVersion.was_contact_linked?(@contact.id)
+ assert Version::DomainVersion.was_contact_linked?(@contact.id)
end
def test_was_contact_linked_returns_true_when_contact_was_used_as_admin_contact
@@ -19,7 +19,7 @@ class DomainVersionTest < ActiveSupport::TestCase
tech_contacts: [],
registrant: [] })
- assert DomainVersion.was_contact_linked?(@contact.id)
+ assert Version::DomainVersion.was_contact_linked?(@contact.id)
end
def test_was_contact_linked_returns_true_when_contact_was_used_as_tech_contact
@@ -27,7 +27,7 @@ class DomainVersionTest < ActiveSupport::TestCase
tech_contacts: [@contact.id],
registrant: [] })
- assert DomainVersion.was_contact_linked?(@contact.id)
+ assert Version::DomainVersion.was_contact_linked?(@contact.id)
end
def test_was_contact_linked_returns_false_when_contact_was_not_used
@@ -35,7 +35,7 @@ class DomainVersionTest < ActiveSupport::TestCase
tech_contacts: [],
registrant: [] })
- assert_not DomainVersion.was_contact_linked?(@contact.id)
+ assert_not Version::DomainVersion.was_contact_linked?(@contact.id)
end
def test_contact_unlinked_more_than_returns_true_when_contact_was_linked_as_registrant_more_than_given_period
@@ -45,7 +45,7 @@ class DomainVersionTest < ActiveSupport::TestCase
registrant: [@contact.id] })
travel_to Time.zone.parse('2010-07-05 00:00:01')
- assert DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
+ assert Version::DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
end
def test_contact_unlinked_more_than_given_period_as_admin_contact
@@ -55,7 +55,7 @@ class DomainVersionTest < ActiveSupport::TestCase
registrant: [] })
travel_to Time.zone.parse('2010-07-05 00:00:01')
- assert DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
+ assert Version::DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
end
def test_contact_unlinked_more_than_given_period_as_tech_contact
@@ -65,7 +65,7 @@ class DomainVersionTest < ActiveSupport::TestCase
registrant: [] })
travel_to Time.zone.parse('2010-07-05 00:00:01')
- assert DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
+ assert Version::DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
end
def test_contact_linked_within_given_period_as_registrant
@@ -75,7 +75,7 @@ class DomainVersionTest < ActiveSupport::TestCase
registrant: [@contact.id] })
travel_to Time.zone.parse('2010-07-05')
- assert_not DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
+ assert_not Version::DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
end
def test_contact_linked_within_given_period_as_admin_contact
@@ -85,7 +85,7 @@ class DomainVersionTest < ActiveSupport::TestCase
registrant: [] })
travel_to Time.zone.parse('2010-07-05')
- assert_not DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
+ assert_not Version::DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
end
def test_contact_linked_within_given_period_as_tech_contact
@@ -95,11 +95,11 @@ class DomainVersionTest < ActiveSupport::TestCase
registrant: [] })
travel_to Time.zone.parse('2010-07-05')
- assert_not DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
+ assert_not Version::DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
end
def test_contact_was_never_linked
- DomainVersion.delete_all
- assert_not DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
+ Version::DomainVersion.delete_all
+ assert_not Version::DomainVersion.contact_unlinked_more_than?(contact_id: @contact.id, period: 1.day)
end
end
diff --git a/test/models/white_ip_test.rb b/test/models/white_ip_test.rb
index 607887730..ba5abe42f 100644
--- a/test/models/white_ip_test.rb
+++ b/test/models/white_ip_test.rb
@@ -38,6 +38,20 @@ class WhiteIpTest < ActiveSupport::TestCase
assert white_ip.valid?
end
+ def test_validates_include_empty_ipv4
+ white_ip = WhiteIp.new
+
+ white_ip.ipv4 = nil
+ white_ip.ipv6 = '001:0db8:85a3:0000:0000:8a2e:0370:7334'
+ white_ip.registrar = registrars(:bestnames)
+
+ assert_nothing_raised { white_ip.save }
+ assert white_ip.valid?
+
+ assert WhiteIp.include_ip?(white_ip.ipv6)
+ assert_not WhiteIp.include_ip?('192.168.1.1')
+ end
+
private
def valid_white_ip
diff --git a/test/system/admin_area/bank_statement_test.rb b/test/system/admin_area/bank_statement_test.rb
index 6de21b1c3..8630049dc 100644
--- a/test/system/admin_area/bank_statement_test.rb
+++ b/test/system/admin_area/bank_statement_test.rb
@@ -4,6 +4,35 @@ class AdminAreaBankStatementTest < ApplicationSystemTestCase
setup do
sign_in users(:admin)
travel_to Time.zone.parse('2010-07-05 00:30:00')
+
+ @invoice = invoices(:one)
+ end
+
+ def test_update_bank_statement
+ visit admin_bank_statement_path(id: @invoice.id)
+
+ click_link_or_button 'Add'
+
+ fill_in 'Description', with: 'Invoice with id 123'
+ fill_in 'Reference number', with: '1232'
+ fill_in 'Sum', with: '500'
+ fill_in 'Paid at', with: Time.zone.today.to_s
+
+ click_link_or_button 'Save'
+ assert_text 'Bank transaction'
+
+ click_link_or_button 'Edit'
+ fill_in 'Description', with: 'Invoice with id 123'
+ click_link_or_button 'Save'
+
+ assert_text 'Record updated'
+ end
+
+ def test_bind_bank
+ visit admin_bank_statement_path(id: @invoice.id)
+ click_link_or_button 'Bind invoices'
+
+ assert_text 'No invoices were binded'
end
def test_can_create_statement_manually
diff --git a/test/system/admin_area/contacts_test.rb b/test/system/admin_area/contacts_test.rb
index d98882dff..19b15c8a5 100644
--- a/test/system/admin_area/contacts_test.rb
+++ b/test/system/admin_area/contacts_test.rb
@@ -8,6 +8,17 @@ class AdminContactsTest < ApplicationSystemTestCase
sign_in users(:admin)
end
+ def test_update_contact
+ visit admin_contact_path(id: @contact.id)
+ assert_text "#{@contact.name}"
+
+ click_on 'Edit statuses'
+ assert_text "Edit: #{@contact.name}"
+
+ click_on 'Save'
+ assert_text 'Contact updated'
+ end
+
def test_display_list
visit admin_contacts_path
diff --git a/test/system/admin_area/domains/csv_test.rb b/test/system/admin_area/domains/csv_test.rb
new file mode 100644
index 000000000..7d4b44124
--- /dev/null
+++ b/test/system/admin_area/domains/csv_test.rb
@@ -0,0 +1,18 @@
+require 'application_system_test_case'
+
+class AdminAreaCsvTest < ApplicationSystemTestCase
+ setup do
+ sign_in users(:admin)
+ end
+
+ def test_downloads_domain_list_as_csv
+ search_params = {"valid_to_lteq"=>nil}
+ expected_csv = Domain.includes(:registrar, :registrant).search(search_params).result.to_csv
+
+ travel_to Time.zone.parse('2010-07-05 10:30')
+ visit admin_domains_url
+ click_link('CSV')
+ assert_equal "attachment; filename=\"domains.csv\"; filename*=UTF-8''domains.csv", response_headers['Content-Disposition']
+ assert_equal expected_csv, page.body
+ end
+end
diff --git a/test/system/admin_area/domains/legal_doc_test.rb b/test/system/admin_area/domains/legal_doc_test.rb
index 00cc7cc3a..48eedcf4f 100644
--- a/test/system/admin_area/domains/legal_doc_test.rb
+++ b/test/system/admin_area/domains/legal_doc_test.rb
@@ -15,7 +15,7 @@ class AdminAreaDomainsLegalDocTest < ApplicationSystemTestCase
def test_absent_doc_downloading_without_errors
visit admin_domain_url(@domain)
assert_nothing_raised do
- click_on "#{@document.created_at}"
+ click_on "#{@document.created_at}", match: :first
end
end
end
diff --git a/test/system/admin_area/invoices_test.rb b/test/system/admin_area/invoices_test.rb
index 814f95d4a..40a50e1c7 100644
--- a/test/system/admin_area/invoices_test.rb
+++ b/test/system/admin_area/invoices_test.rb
@@ -40,4 +40,4 @@ class AdminAreaInvoicesTest < ApplicationSystemTestCase
assert_current_path admin_invoice_path(@invoice)
assert_text 'Invoice has been sent'
end
-end
\ No newline at end of file
+end
diff --git a/test/system/admin_area/prices_test.rb b/test/system/admin_area/prices_test.rb
index dbb91966a..f5a299c38 100644
--- a/test/system/admin_area/prices_test.rb
+++ b/test/system/admin_area/prices_test.rb
@@ -20,6 +20,7 @@ class AdminAreaPricesTest < ApplicationSystemTestCase
fill_in 'Valid from', with: effective_date
click_on 'Create price'
+
assert_text 'Price has been created'
assert_text I18n.localize(effective_date)
end
diff --git a/test/system/admin_area/protected_area_test.rb b/test/system/admin_area/protected_area_test.rb
index f3375776a..fa413291b 100644
--- a/test/system/admin_area/protected_area_test.rb
+++ b/test/system/admin_area/protected_area_test.rb
@@ -19,4 +19,4 @@ class AdminAreaProtectedAreaTest < ApplicationSystemTestCase
assert_text 'You are already signed in'
assert_current_path admin_domains_path
end
-end
\ No newline at end of file
+end
diff --git a/test/system/registrant_area/contacts/details_test.rb b/test/system/registrant_area/contacts/details_test.rb
deleted file mode 100644
index bf96046a6..000000000
--- a/test/system/registrant_area/contacts/details_test.rb
+++ /dev/null
@@ -1,33 +0,0 @@
-require 'application_system_test_case'
-
-class RegistrantAreaContactDetailsTest < ApplicationSystemTestCase
- setup do
- sign_in users(:registrant)
- @domain = domains(:shop)
- @contact = contacts(:john)
- end
-
- def test_general_data
- visit registrant_domain_contact_url(@domain, @contact)
- assert_text 'Code john-001'
- assert_text 'Name John'
-
- assert_text 'Auth info'
- assert_css('[value="cacb5b"]')
-
- assert_text 'Ident 1234'
- assert_text 'Email john@inbox.test'
- assert_text 'Phone +555.555'
-
- assert_text "Created at #{l Time.zone.parse('2010-07-05')}"
- assert_text "Updated at #{l Time.zone.parse('2010-07-06')}"
- end
-
- def test_registrant_user_cannot_access_contact_when_given_domain_belongs_to_another_user
- suppress(ActiveRecord::RecordNotFound) do
- visit registrant_domain_contact_url(domains(:metro), @contact)
- assert_response :not_found
- assert_no_text 'Name John'
- end
- end
-end
diff --git a/test/system/registrant_area/contacts/update_test.rb b/test/system/registrant_area/contacts/update_test.rb
deleted file mode 100644
index 07115579b..000000000
--- a/test/system/registrant_area/contacts/update_test.rb
+++ /dev/null
@@ -1,172 +0,0 @@
-require 'application_system_test_case'
-
-class RegistrantAreaContactUpdateTest < ApplicationIntegrationTest
- setup do
- @domain = domains(:shop)
- @contact = contacts(:john)
- sign_in users(:registrant)
-
- @original_address_processing = Setting.address_processing
- @original_fax_enabled_setting = ENV['fax_enabled']
- @original_registrant_api_base_url_setting = ENV['registrant_api_base_url']
-
- ENV['registrant_api_base_url'] = 'https://api.test'
- end
-
- teardown do
- Setting.address_processing = @original_address_processing
- ENV['fax_enabled'] = @original_fax_enabled_setting
- ENV['registrant_api_base_url'] = @original_registrant_api_base_url_setting
- end
-
- def test_form_is_pre_populated_with_contact_data
- visit edit_registrant_domain_contact_url(@domain, @contact)
-
- assert_field 'Name', with: 'John'
- assert_field 'Email', with: 'john@inbox.test'
- assert_field 'Phone', with: '+555.555'
- end
-
- def test_update_contact
- stub_auth_request
-
- request_body = { name: 'new name', email: 'new@inbox.test', phone: '+666.6' }.to_json
- headers = { 'Content-Type' => Mime[:json],
- 'Authorization' => 'Bearer test-access-token' }
- url = "https://api.test/api/v1/registrant/contacts/#{@contact.uuid}"
- update_request_stub = stub_request(:patch, url).with(body: request_body, headers: headers)
- .to_return(body: '{}', status: 200)
-
- visit registrant_domain_contact_url(@domain, @contact)
- click_link_or_button 'Edit'
-
- fill_in 'Name', with: 'new name'
- fill_in 'Email', with: 'new@inbox.test'
- fill_in 'Phone', with: '+666.6'
-
- click_link_or_button 'Update contact'
-
- assert_requested update_request_stub
- assert_current_path registrant_domain_contact_path(@domain, @contact)
- assert_text 'Contact has been successfully updated'
- end
-
- def test_form_is_pre_populated_with_fax_when_enabled
- ENV['fax_enabled'] = 'true'
- @contact.update!(fax: '+111.1')
-
- visit edit_registrant_domain_contact_url(@domain, @contact)
- assert_field 'Fax', with: '+111.1'
- end
-
- def test_update_fax_when_enabled
- ENV['fax_enabled'] = 'true'
- stub_auth_request
-
- request_body = { email: 'john@inbox.test', name: 'John', phone: '+555.555', fax: '+222.2' }
- headers = { 'Authorization' => 'Bearer test-access-token' }
- url = "https://api.test/api/v1/registrant/contacts/#{@contact.uuid}"
- update_request_stub = stub_request(:patch, url).with(body: request_body, headers: headers)
- .to_return(body: '{}', status: 200)
-
- visit edit_registrant_domain_contact_url(@domain, @contact)
-
- fill_in 'Fax', with: '+222.2'
- click_link_or_button 'Update contact'
-
- assert_requested update_request_stub
- assert_current_path registrant_domain_contact_path(@domain, @contact)
- assert_text 'Contact has been successfully updated'
- end
-
- def test_hide_fax_field_when_disabled
- visit edit_registrant_domain_contact_url(@domain, @contact)
- assert_no_field 'Fax'
- end
-
- def test_form_is_pre_populated_with_address_when_enabled
- Setting.address_processing = true
- @contact.update!(street: 'Main Street',
- zip: '12345',
- city: 'New York',
- state: 'New York State',
- country_code: 'US')
-
- visit edit_registrant_domain_contact_url(@domain, @contact)
-
- assert_field 'Street', with: 'Main Street'
- assert_field 'Zip', with: '12345'
- assert_field 'City', with: 'New York'
- assert_field 'State', with: 'New York State'
- assert_select 'Country', selected: 'United States'
- end
-
- def test_update_address_when_enabled
- Setting.address_processing = true
- stub_auth_request
-
- request_body = { name: 'John',
- email: 'john@inbox.test',
- phone: '+555.555',
- address: {
- city: 'new city',
- street: 'new street',
- zip: '93742',
- country_code: 'AT',
- state: 'new state',
- } }.to_json
- headers = { 'Content-type' => Mime[:json],
- 'Authorization' => 'Bearer test-access-token' }
- url = "https://api.test/api/v1/registrant/contacts/#{@contact.uuid}"
- update_request_stub = stub_request(:patch, url).with(body: request_body, headers: headers)
- .to_return(body: '{}', status: 200)
-
- visit edit_registrant_domain_contact_url(@domain, @contact)
-
- fill_in 'Street', with: 'new street'
- fill_in 'City', with: 'new city'
- fill_in 'State', with: 'new state'
- fill_in 'Zip', with: '93742'
- select 'Austria', from: 'Country'
- click_link_or_button 'Update contact'
-
- assert_requested update_request_stub
- assert_current_path registrant_domain_contact_path(@domain, @contact)
- assert_text 'Contact has been successfully updated'
- end
-
- def test_hide_address_field_when_disabled
- visit edit_registrant_domain_contact_url(@domain, @contact)
- assert_no_field 'Address'
- assert_no_field 'Street'
- end
-
- def test_fail_gracefully
- stub_auth_request
-
- response_body = { errors: { name: ['Name is invalid'] } }.to_json
- headers = { 'Authorization' => 'Bearer test-access-token' }
- stub_request(:patch, "https://api.test/api/v1/registrant/contacts/#{@contact.uuid}")
- .with(headers: headers)
- .to_return(body: response_body, status: 400)
-
- visit edit_registrant_domain_contact_url(@domain, @contact)
- fill_in 'Name', with: 'invalid name'
- click_link_or_button 'Update contact'
-
- assert_current_path registrant_domain_contact_path(@domain, @contact)
- assert_text 'Name is invalid'
- assert_field 'Name', with: 'invalid name'
- assert_no_text 'Contact has been successfully updated'
- end
-
- private
-
- def stub_auth_request
- body = { ident: '1234', first_name: 'Registrant', last_name: 'User' }
- stub_request(:post, 'https://api.test/api/v1/registrant/auth/eid').with(body: body)
- .to_return(body: { access_token: 'test-access-token' }.to_json,
- headers: { 'Content-type' => Mime[:json] },
- status: 200)
- end
-end
diff --git a/test/system/registrant_area/domains/details_test.rb b/test/system/registrant_area/domains/details_test.rb
deleted file mode 100644
index 2f61d46be..000000000
--- a/test/system/registrant_area/domains/details_test.rb
+++ /dev/null
@@ -1,76 +0,0 @@
-require 'application_system_test_case'
-
-class RegistrantAreaDomainDetailsTest < ApplicationSystemTestCase
- setup do
- sign_in users(:registrant)
- @domain = domains(:shop)
- end
-
- def test_general_data
- @domain.update_columns(force_delete_date: '2010-07-08', statuses: [DomainStatus::FORCE_DELETE])
-
- visit registrant_domain_url(@domain)
-
- assert_text 'Name shop.test'
- assert_text "Registered at #{l @domain.registered_at}"
- assert_link 'Best Names', href: registrant_registrar_path(@domain.registrar)
-
- assert_text 'Transfer code'
- assert_css('[value="65078d5"]')
-
- assert_text "Valid to #{l Time.zone.parse('2010-07-05')}"
- assert_text "Outzone at #{l Time.zone.parse('2010-07-06')}"
- assert_text "Delete date #{l Date.parse('2010-07-07')}"
- assert_text "Force delete date #{l Date.parse('2010-07-08')}"
- end
-
- def test_registrant
- visit registrant_domain_url(@domain)
- assert_link 'John', href: registrant_domain_contact_path(@domain, @domain.registrant)
- assert_text 'Code john-001'
- assert_text 'Ident 1234'
- assert_text 'Email john@inbox.test'
- assert_text 'Phone +555.555'
- end
-
- def test_admin_contacts
- visit registrant_domain_url(@domain)
-
- within('.admin-domain-contacts') do
- assert_link 'Jane', href: registrant_domain_contact_path(@domain, contacts(:jane))
- assert_text 'jane-001'
- assert_text 'jane@mail.test'
- assert_css '.admin-domain-contact', count: 1
- end
- end
-
- def test_tech_contacts
- visit registrant_domain_url(@domain)
-
- within('.tech-domain-contacts') do
- assert_link 'William', href: registrant_domain_contact_path(@domain, contacts(:william))
- assert_text 'william-001'
- assert_text 'william@inbox.test'
- assert_css '.tech-domain-contact', count: 2
- end
- end
-
- def test_registrant_user_cannot_access_domains_of_other_users
- suppress(ActiveRecord::RecordNotFound) do
- visit registrant_domain_url(domains(:metro))
- assert_response :not_found
- assert_no_text 'metro.test'
- end
- end
-
- def test_confirmation_url
- @domain.update!(registrant_verification_token: 'a01',
- pending_json: { new_registrant_email: 'any' },
- statuses: [DomainStatus::PENDING_UPDATE])
-
- visit registrant_domain_url(@domain)
- click_on 'pendingUpdate'
-
- assert_field nil, with: registrant_domain_update_confirm_url(@domain, token: 'a01')
- end
-end
diff --git a/test/system/registrant_area/domains/domain_delete_confirms_test.rb b/test/system/registrant_area/domains/domain_delete_confirms_test.rb
deleted file mode 100644
index 765cd0149..000000000
--- a/test/system/registrant_area/domains/domain_delete_confirms_test.rb
+++ /dev/null
@@ -1,46 +0,0 @@
-require 'application_system_test_case'
-
-class DomainDeleteConfirmsTest < ApplicationSystemTestCase
- include ActionMailer::TestHelper
- setup do
- @user = users(:registrant)
- sign_in @user
-
- @domain = domains(:shop)
- @domain.registrant_verification_asked!('\n ', @user.id)
- @domain.pending_delete!
- end
-
- def test_enqueues_approve_job_after_verification
- visit registrant_domain_delete_confirm_url(@domain.id, token: @domain.registrant_verification_token)
-
- perform_enqueued_jobs do
- click_on 'Confirm domain delete'
- end
- assert_text 'Domain registrant change has successfully received.'
-
- @domain.reload
- assert_includes @domain.statuses, 'serverHold'
- end
-
- def test_enqueues_reject_job_after_verification
- visit registrant_domain_delete_confirm_url(@domain.id, token: @domain.registrant_verification_token)
-
- perform_enqueued_jobs do
- click_on 'Reject domain delete'
- end
- assert_text 'Domain registrant change has been rejected successfully.'
-
- @domain.reload
- assert_equal ['ok'], @domain.statuses
- end
-
- def test_saves_whodunnit_info_after_verifivation
- visit registrant_domain_delete_confirm_url(@domain.id, token: @domain.registrant_verification_token)
- token = @domain.registrant_verification_token
- click_on 'Confirm domain delete'
- assert_text 'Domain registrant change has successfully received.'
-
- refute RegistrantVerification.find_by(verification_token:token).updator_str.empty?
- end
-end
diff --git a/test/system/registrant_area/domains/list_test.rb b/test/system/registrant_area/domains/list_test.rb
deleted file mode 100644
index 3cbf477da..000000000
--- a/test/system/registrant_area/domains/list_test.rb
+++ /dev/null
@@ -1,71 +0,0 @@
-require 'application_system_test_case'
-
-CompanyRegisterClientStub = Struct.new(:any_method) do
- def representation_rights(citizen_personal_code:, citizen_country_code:)
- raise CompanyRegister::NotAvailableError
- end
-end
-
-class RegistrantAreaDomainListTest < ApplicationSystemTestCase
- setup do
- @user = users(:registrant)
- sign_in @user
-
- @domain = domains(:shop)
- end
-
- def test_show_domain_list
- visit registrant_domains_url
- assert_link 'shop.test', href: registrant_domain_path(@domain)
- assert_link 'John', href: registrant_domain_contact_path(@domain, @domain.registrant)
- assert_link 'Best Names', href: registrant_registrar_path(@domain.registrar)
- assert_text l(Time.zone.parse('2010-07-05'))
- assert_css '.domains .domain', count: 4
- end
-
- def test_do_not_show_domains_of_other_registrant_users
- visit registrant_domains_url
- assert_no_text 'metro.test'
- end
-
- def test_only_shows_direct_relation_and_or_company_domains
- # case https://github.com/internetee/registry/issues/1690
- tech_contact = contacts(:registrar_ltd)
-
- # All domains share the same tech contact object
- Domain.all.each do |domain|
- DomainContact.create(domain: domain, contact: tech_contact, type: TechDomainContact)
- end
-
- visit registrant_domains_url
- assert_no_text 'Company register is unavailable.'
- assert_no_text 'metro.test'
- end
-
- def test_notification_when_company_register_is_unavailable
- CompanyRegister::Client.stub(:new, CompanyRegisterClientStub.new) do
- visit registrant_domains_url
- end
-
- assert_text 'Company register is unavailable. Domains and contacts associated via' \
- ' organizations are not shown.'
- end
-
- def test_show_direct_domains_when_company_register_is_unavailable
- assert_equal 'US-1234', @user.registrant_ident
-
- contact = contacts(:john)
- assert_equal '1234', contact.ident
- assert_equal Contact::PRIV, contact.ident_type
- assert_equal 'US', contact.ident_country_code
-
- assert_equal contact.becomes(Registrant), @domain.registrant
- assert_equal 'shop.test', @domain.name
-
- CompanyRegister::Client.stub(:new, CompanyRegisterClientStub.new) do
- visit registrant_domains_url
- end
-
- assert_text 'shop.test'
- end
-end
diff --git a/test/system/registrant_area/domains_test.rb b/test/system/registrant_area/domains_test.rb
deleted file mode 100644
index fa151c89e..000000000
--- a/test/system/registrant_area/domains_test.rb
+++ /dev/null
@@ -1,22 +0,0 @@
-require 'application_system_test_case'
-
-class RegistrantDomainsTest < ApplicationSystemTestCase
- setup do
- sign_in users(:registrant)
- end
-
- def test_shows_domains_where_current_user_is_registrant
- visit registrant_domains_url
- assert_text 'shop.test'
- end
-
- def test_shows_domains_where_current_user_is_contact_person
- visit registrant_domains_url
- assert_text 'airport.test'
- end
-
- def test_shows_domains_where_current_user_has_associated_organizations
- visit registrant_domains_url
- assert_text 'library.test'
- end
-end
diff --git a/test/system/registrant_area/layout_test.rb b/test/system/registrant_area/layout_test.rb
deleted file mode 100644
index 9df8028e3..000000000
--- a/test/system/registrant_area/layout_test.rb
+++ /dev/null
@@ -1,15 +0,0 @@
-require 'application_system_test_case'
-
-class RegistrantLayoutTest < ApplicationSystemTestCase
- def setup
- super
- sign_in(users(:registrant))
- end
-
- def test_has_link_to_rest_whois_and_internet_ee
- visit registrant_domains_url
-
- assert(has_link?('Internet.ee', href: 'https://internet.ee'))
- assert(has_link?('WHOIS', href: 'https://whois.internet.ee'))
- end
-end
diff --git a/test/system/registrant_area/tara/tara_users_test.rb b/test/system/registrant_area/tara/tara_users_test.rb
deleted file mode 100644
index 5020616d4..000000000
--- a/test/system/registrant_area/tara/tara_users_test.rb
+++ /dev/null
@@ -1,51 +0,0 @@
-require 'application_system_test_case'
-
-class RegistrantAreaTaraUsersTest < ApplicationSystemTestCase
- def setup
- super
-
- OmniAuth.config.test_mode = true
- @registrant = users(:registrant)
-
- @existing_user_hash = {
- 'provider' => 'rant_tara',
- 'uid' => "US1234",
- 'info': { 'first_name': 'Registrant', 'last_name': 'User' }
- }
-
- @new_user_hash = {
- 'provider' => 'rant_tara',
- 'uid' => 'EE51007050604',
- 'info': { 'first_name': 'New Registrant', 'last_name': 'User'}
- }
- end
-
- def teardown
- super
-
- OmniAuth.config.test_mode = false
- OmniAuth.config.mock_auth['rant_tara'] = nil
- end
-
- def test_existing_user_gets_signed_in
- OmniAuth.config.mock_auth[:rant_tara] = OmniAuth::AuthHash.new(@existing_user_hash)
-
- visit new_registrant_user_session_path
- click_link('Sign in')
-
- assert_text('Signed in successfully')
- end
-
- def test_new_user_is_created_and_signed_in
- OmniAuth.config.mock_auth[:rant_tara] = OmniAuth::AuthHash.new(@new_user_hash)
-
- assert_difference 'RegistrantUser.count' do
- visit new_registrant_user_session_path
- click_link('Sign in')
-
- assert_equal 'New Registrant User', RegistrantUser.last.username
- assert_equal 'EE-51007050604', RegistrantUser.last.registrant_ident
- assert_text('Signed in successfully')
- end
- end
-end
diff --git a/test/system/registrar_area/account_activities_test.rb b/test/system/registrar_area/account_activities_test.rb
new file mode 100644
index 000000000..1944dc2fb
--- /dev/null
+++ b/test/system/registrar_area/account_activities_test.rb
@@ -0,0 +1,28 @@
+require 'application_system_test_case'
+
+class RegistrarAccountActivitiesTest < ApplicationSystemTestCase
+ setup do
+ @registrar = registrars(:bestnames)
+ sign_in users(:api_bestnames)
+ end
+
+ def test_show_account_activity_page
+ account_activities(:one).update(sum: "123.00")
+ visit registrar_account_activities_path
+ assert_text 'Account activity'
+ end
+
+ def test_download_account_activity
+ now = Time.zone.parse('2010-07-05 08:00')
+ travel_to now
+ account_activities(:one).update(sum: "123.00")
+
+ get registrar_account_activities_path(format: :csv)
+
+ assert_response :ok
+ assert_equal "text/csv", response.headers['Content-Type']
+ assert_equal %(attachment; filename="account_activities_#{Time.zone.now.to_formatted_s(:number)}.csv"; filename*=UTF-8''account_activities_#{Time.zone.now.to_formatted_s(:number)}.csv),
+ response.headers['Content-Disposition']
+ assert_not_empty response.body
+ end
+end
\ No newline at end of file
diff --git a/test/system/registrar_area/bulk_change/admin_contact_test.rb b/test/system/registrar_area/bulk_change/admin_contact_test.rb
new file mode 100644
index 000000000..8847812cb
--- /dev/null
+++ b/test/system/registrar_area/bulk_change/admin_contact_test.rb
@@ -0,0 +1,49 @@
+require 'application_system_test_case'
+
+class RegistrarAreaAdminContactBulkChangeTest < ApplicationSystemTestCase
+ setup do
+ sign_in users(:api_bestnames)
+ end
+
+ def test_replace_domain_contacts_of_current_registrar
+ request_stub = stub_request(:patch, /domains\/admin_contacts/)
+ .with(body: { current_contact_id: 'william-001', new_contact_id: 'john-001' },
+ basic_auth: ['test_bestnames', 'testtest'])
+ .to_return(body: { data: { affected_domains: %w[foo.test bar.test],
+ skipped_domains: %w[baz.test qux.test] } }.to_json,
+ status: 200)
+
+ visit registrar_domains_url
+ click_link 'Bulk change'
+ click_link 'Admin contact'
+
+ find('.current_admin_contact').fill_in 'Current contact ID', with: 'william-001'
+ find('.new_admin_contact').fill_in 'New contact ID', with: 'john-001'
+ click_on 'Replace admin contacts'
+
+ assert_requested request_stub
+ assert_current_path registrar_domains_path
+ assert_text 'Admin contacts have been successfully replaced'
+ assert_text 'Affected domains: foo.test, bar.test'
+ assert_text 'Skipped domains: baz.test, qux.test'
+ end
+
+ def test_fails_gracefully
+ stub_request(:patch, /domains\/admin_contacts/)
+ .to_return(status: 400,
+ body: { message: 'epic fail' }.to_json,
+ headers: { 'Content-type' => Mime[:json] })
+
+ visit registrar_domains_url
+ click_link 'Bulk change'
+ click_link 'Admin contact'
+
+ find('.current_admin_contact').fill_in 'Current contact ID', with: 'william-001'
+ find('.new_admin_contact').fill_in 'New contact ID', with: 'john-001'
+ click_on 'Replace admin contacts'
+
+ assert_text 'epic fail'
+ assert_field 'Current contact ID', with: 'william-001'
+ assert_field 'New contact ID', with: 'john-001'
+ end
+end
diff --git a/test/system/registrar_area/bulk_change/tech_contact_test.rb b/test/system/registrar_area/bulk_change/tech_contact_test.rb
index e08457f60..055ec25ca 100644
--- a/test/system/registrar_area/bulk_change/tech_contact_test.rb
+++ b/test/system/registrar_area/bulk_change/tech_contact_test.rb
@@ -16,8 +16,8 @@ class RegistrarAreaTechContactBulkChangeTest < ApplicationSystemTestCase
visit registrar_domains_url
click_link 'Bulk change'
- fill_in 'Current contact ID', with: 'william-001'
- fill_in 'New contact ID', with: 'john-001'
+ find('.current_tech_contact').fill_in 'Current contact ID', with: 'william-001'
+ find('.new_tech_contact').fill_in 'New contact ID', with: 'john-001'
click_on 'Replace technical contacts'
assert_requested request_stub
@@ -36,8 +36,8 @@ class RegistrarAreaTechContactBulkChangeTest < ApplicationSystemTestCase
visit registrar_domains_url
click_link 'Bulk change'
- fill_in 'Current contact ID', with: 'william-001'
- fill_in 'New contact ID', with: 'john-001'
+ find('.current_tech_contact').fill_in 'Current contact ID', with: 'william-001'
+ find('.new_tech_contact').fill_in 'New contact ID', with: 'john-001'
click_on 'Replace technical contacts'
assert_text 'epic fail'
diff --git a/test/system/registrar_area/tara/tara_users_test.rb b/test/system/registrar_area/tara/tara_users_test.rb
index a2defd715..005504043 100644
--- a/test/system/registrar_area/tara/tara_users_test.rb
+++ b/test/system/registrar_area/tara/tara_users_test.rb
@@ -34,6 +34,18 @@ class TaraUsersTest < ApplicationSystemTestCase
assert_text('Signed in successfully')
end
+ def test_existing_user_logs_in_without_cookie_overflow
+ @existing_user_hash['credentials'] = massive_hash
+ OmniAuth.config.mock_auth[:tara] = OmniAuth::AuthHash.new(@existing_user_hash)
+
+ visit new_registrar_user_session_path
+ assert_nothing_raised do
+ click_link('Sign in')
+ end
+
+ assert_text('Signed in successfully')
+ end
+
def test_nonexisting_user_gets_error_message
OmniAuth.config.mock_auth[:tara] = OmniAuth::AuthHash.new(@new_user_hash)
@@ -42,4 +54,10 @@ class TaraUsersTest < ApplicationSystemTestCase
assert_text('No such user')
end
+
+ def massive_hash
+ o = [('a'..'z'), ('A'..'Z')].map(&:to_a).flatten
+ string = (0...5000).map { o[rand(o.length)] }.join
+ {"access_token":"AT-540-Fj5gbPvJp4jPkO-4EdgzIhIhhJapoRTM","token_type":"bearer","expires_in":600,"id_token":string}
+ end
end
diff --git a/test/tasks/contacts/archive_test.rb b/test/tasks/contacts/archive_test.rb
index eebfa7b68..f5ecff092 100644
--- a/test/tasks/contacts/archive_test.rb
+++ b/test/tasks/contacts/archive_test.rb
@@ -14,7 +14,7 @@ class ArchiveContactsTaskTest < ActiveSupport::TestCase
def archivable_contact
contact = contacts(:john)
Setting.orphans_contacts_in_months = 0
- DomainVersion.delete_all
+ Version::DomainVersion.delete_all
other_contact = contacts(:william)
assert_not_equal other_contact, contact
diff --git a/test/test_helper.rb b/test/test_helper.rb
index a1634f717..fe20f7a6e 100644
--- a/test/test_helper.rb
+++ b/test/test_helper.rb
@@ -42,7 +42,7 @@ EInvoice.provider = EInvoice::Providers::TestProvider.new
class ActiveSupport::TestCase
ActiveRecord::Migration.check_pending!
fixtures :all
- set_fixture_class log_domains: DomainVersion
+ set_fixture_class log_domains: Version::DomainVersion
teardown do
travel_back