Merge branch 'master' of github.com:domify/registry

This commit is contained in:
Priit Tark 2015-05-20 16:31:42 +03:00
commit 2863cd6749
36 changed files with 534 additions and 92 deletions

View file

@ -20,8 +20,8 @@ Documentation
### Updating documentation
AUTODOC=true rspec spec/requests
EPP_DOC=true rspec spec/epp --tag epp --require support/epp_doc.rb --format EppDoc > doc/epp-examples.md
AUTODOC=true rspec spec/requests
EPP_DOC=true rspec spec/epp --tag epp --require support/epp_doc.rb --format EppDoc > doc/epp-examples.md
Installation
------------
@ -32,41 +32,41 @@ Registry based on Rails 4 installation (rbenv install is under Debian build doc)
Manual demo install and database setup:
cd /home/registry
git clone git@github.com:internetee/registry.git demo-registry
cd demo-registry
rbenv local 2.2.2
bundle
cp config/application-example.yml config/application.yml # and edit it
cp config/database-example.yml config/database.yml # and edit it
bundle exec rake db:all:setup # for production, please follow deployment howto
bundle exec rake assets:precompile
cd /home/registry
git clone git@github.com:internetee/registry.git demo-registry
cd demo-registry
rbenv local 2.2.2
bundle
cp config/application-example.yml config/application.yml # and edit it
cp config/database-example.yml config/database.yml # and edit it
bundle exec rake db:all:setup # for production, please follow deployment howto
bundle exec rake assets:precompile
### Apache with patched mod_epp (Debian 7/Ubuntu 14.04 LTS)
sudo apt-get install apache2
sudo apt-get install apache2
sudo apt-get install apache2-threaded-dev # needed to compile mod_epp
wget sourceforge.net/projects/aepps/files/mod_epp/1.10/mod_epp-1.10.tar.gz
tar -xzvf mod_epp-1.10.tar.gz
cd mod_epp-1.10
sudo apt-get install apache2-threaded-dev # needed to compile mod_epp
wget sourceforge.net/projects/aepps/files/mod_epp/1.10/mod_epp-1.10.tar.gz
tar -xzvf mod_epp-1.10.tar.gz
cd mod_epp-1.10
Patch mod_epp for Rack. Beacause Rack multipart parser expects specifically
formatted content boundaries, the mod_epp needs to be modified before building:
wget https://github.com/internetee/registry/raw/master/doc/patches/mod_epp_1.10-rack-friendly.patch
wget https://raw.githubusercontent.com/domify/registry/master/doc/patches/mod_epp_1.10-frame-size.patch
patch < mod_epp_1.10-rack-friendly.patch
patch < mod_epp_1.10-frame-size.patch
sudo apxs2 -a -c -i mod_epp.c
wget https://github.com/internetee/registry/raw/master/doc/patches/mod_epp_1.10-rack-friendly.patch
wget https://raw.githubusercontent.com/domify/registry/master/doc/patches/mod_epp_1.10-frame-size.patch
patch < mod_epp_1.10-rack-friendly.patch
patch < mod_epp_1.10-frame-size.patch
sudo apxs2 -a -c -i mod_epp.c
Enable ssl:
sudo a2enmod proxy_http
sudo mkdir /etc/apache2/ssl
sudo openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout /etc/apache2/ssl/apache.key -out /etc/apache2/ssl/apache.crt
sudo a2enmod ssl
sudo nano /etc/apache2/sites-enabled/epp_ssl.conf
sudo a2enmod proxy_http
sudo mkdir /etc/apache2/ssl
sudo openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout /etc/apache2/ssl/apache.key -out /etc/apache2/ssl/apache.crt
sudo a2enmod ssl
sudo nano /etc/apache2/sites-enabled/epp_ssl.conf
For Apache, registry admin goes to port 443 in production, /etc/apache2/sites-enabled/registry.conf short example:

View file

@ -8,6 +8,10 @@ module Repp
end
before do
unless Rails.env.development?
error! I18n.t('ip_is_not_whitelisted'), 401 unless @current_user.registrar.repp_ip_white?(request.ip)
end
next if Rails.env.test? || Rails.env.development?
message = 'Certificate mismatch! Cert common name should be:'
request_name = env['HTTP_SSL_CLIENT_S_DN_CN']
@ -18,6 +22,7 @@ module Repp
else
error! "#{message} #{@current_user.username}", 401 if @current_user.username != request_name
end
end
helpers do

View file

@ -0,0 +1,56 @@
class Admin::WhiteIpsController < AdminController
load_and_authorize_resource
before_action :set_registrar, only: [:new, :show, :edit, :destroy, :update]
def new
@white_ip = WhiteIp.new(registrar: @registrar)
end
def show; end
def edit; end
def destroy
if @white_ip.destroy
flash[:notice] = I18n.t('record_deleted')
redirect_to admin_registrar_path(@registrar)
else
flash.now[:alert] = I18n.t('failed_to_delete_record')
render 'show'
end
end
def create
@white_ip = WhiteIp.new(white_ip_params)
@registrar = @white_ip.registrar
if @white_ip.save
flash[:notice] = I18n.t('record_created')
redirect_to [:admin, @registrar, @white_ip]
else
flash.now[:alert] = I18n.t('failed_to_create_record')
render 'new'
end
end
def update
if @white_ip.update(white_ip_params)
flash[:notice] = I18n.t('record_updated')
redirect_to [:admin, @registrar, @white_ip]
else
flash.now[:alert] = I18n.t('failed_to_update_record')
render 'edit'
end
end
private
def set_registrar
@registrar = Registrar.find_by(id: params[:registrar_id])
end
def white_ip_params
params.require(:white_ip).permit(:ipv4, :ipv6, :interface, :registrar_id)
end
end

View file

@ -18,7 +18,7 @@ class Epp::SessionsController < EppController
@api_user = ApiUser.find_by(login_params)
end
if @api_user.try(:active) && cert_valid
if @api_user.try(:active) && cert_valid && ip_white?
if parsed_frame.css('newPW').first
unless @api_user.update(password: parsed_frame.css('newPW').first.text)
response.headers['X-EPP-Returncode'] = '2200'
@ -33,6 +33,17 @@ class Epp::SessionsController < EppController
render_epp_response('login_fail')
end
end
def ip_white?
if @api_user
unless @api_user.registrar.epp_ip_white?(request.ip)
@msg = t('ip_is_not_whitelisted')
return false
end
end
true
end
# rubocop: enable Metrics/PerceivedComplexity
# rubocop: enable Metrics/CyclomaticComplexity

View file

@ -236,6 +236,8 @@ class EppController < ApplicationController
end
# rubocop: enable Style/PredicateName
# rubocop: disable Metrics/PerceivedComplexity
# rubocop: disable Metrics/CyclomaticComplexity
def write_to_epp_log
# return nil if EPP_LOG_ENABLED
request_command = params[:command] || params[:action] # error receives :command, other methods receive :action
@ -257,4 +259,6 @@ class EppController < ApplicationController
ip: request.ip
})
end
# rubocop: enable Metrics/PerceivedComplexity
# rubocop: enable Metrics/CyclomaticComplexity
end

View file

@ -8,6 +8,8 @@ class Registrant::DomainUpdateConfirmsController < RegistrantController
@domain = nil unless @domain.registrant_update_confirmable?(params[:token])
end
# rubocop: disable Metrics/PerceivedComplexity
# rubocop: disable Metrics/CyclomaticComplexity
def update
@domain = Domain.find(params[:id])
unless @domain.registrant_update_confirmable?(params[:token])
@ -37,4 +39,6 @@ class Registrant::DomainUpdateConfirmsController < RegistrantController
end
end
end
# rubocop: enable Metrics/PerceivedComplexity
# rubocop: enable Metrics/CyclomaticComplexity
end

View file

@ -24,7 +24,7 @@ class Registrar::DomainsController < Registrar::DeppController # EPP controller
if response_ok?
render 'info'
else
flash[:alert] = t(:domain_not_found)
flash[:alert] = @data.css('msg').text
redirect_to registrar_domains_url and return
end
end
@ -118,9 +118,9 @@ class Registrar::DomainsController < Registrar::DeppController # EPP controller
end
def init_contacts_autocomplete_map
@contacts_autocomplete_map ||=
@contacts_autocomplete_map ||=
current_user.registrar.contacts.pluck(:name, :code).map { |c| ["#{c.second} #{c.first}", c.second] }
# @priv_contacts_autocomplete_map ||=
# @priv_contacts_autocomplete_map ||=
# current_user.registrar.priv_contacts.pluck(:name, :code).map { |c| ["#{c.second} #{c.first}", c.second] }
end
end

View file

@ -5,6 +5,8 @@ class Registrar::SessionsController < Devise::SessionsController
false
end
before_action :check_ip
def login
@depp_user = Depp::User.new
end
@ -139,4 +141,11 @@ class Registrar::SessionsController < Devise::SessionsController
return User.new unless idc
ApiUser.find_by(identity_code: idc) || User.new
end
private
def check_ip
return if WhiteIp.registrar_ip_white?(request.ip)
render text: t('ip_is_not_whitelisted') and return
end
end

View file

@ -1,5 +1,6 @@
class RegistrarController < ApplicationController
before_action :authenticate_user!
before_action :authenticate_user!, :check_ip
# before_action :check_ip
layout 'registrar/application'
include Registrar::ApplicationHelper
@ -9,6 +10,14 @@ class RegistrarController < ApplicationController
false
end
def check_ip
return unless current_user
return if current_user.registrar.registrar_ip_white?(request.ip)
flash[:alert] = t('ip_is_not_whitelisted')
sign_out(current_user)
redirect_to registrar_login_path and return
end
helper_method :head_title_sufix
def head_title_sufix
t(:registrar_head_title_sufix)

View file

@ -98,6 +98,7 @@ class Ability
can :manage, BankStatement
can :manage, BankTransaction
can :manage, Invoice
can :manage, WhiteIp
can :read, ApiLog::EppLog
can :read, ApiLog::ReppLog
# can :index, :delayed_job

View file

@ -14,9 +14,8 @@ class Certificate < ActiveRecord::Base
validate :validate_csr_and_crt
def validate_csr_and_crt
if csr.blank? && crt.blank?
errors.add(:base, I18n.t(:crt_or_csr_must_be_present))
end
return if csr.present? || crt.present?
errors.add(:base, I18n.t(:crt_or_csr_must_be_present))
end
def parsed_crt

View file

@ -32,6 +32,8 @@ module Depp
def request(xml)
Nokogiri::XML(server.request(xml)).remove_namespaces!
rescue EppErrorResponse => e
Nokogiri::XML(e.response_xml.to_s).remove_namespaces!
end
def repp_request(path, params = {})
@ -82,7 +84,7 @@ module Depp
res = server.send_request(xml)
if Nokogiri::XML(res).css('result').first['code'] != '1000'
errors.add(:base, :authorization_error)
errors.add(:base, Nokogiri::XML(res).css('result').text)
end
server.close_connection

View file

@ -297,7 +297,6 @@ class Domain < ActiveRecord::Base
registrant.try(:name)
end
# rubocop:disable Lint/Loop
def generate_auth_info
begin

View file

@ -10,6 +10,7 @@ class Registrar < ActiveRecord::Base
has_many :nameservers, through: :domains
has_many :whois_records
has_many :priv_contacts, -> { privs }, class_name: 'Contact'
has_many :white_ips, dependent: :destroy
validates :name, :reg_no, :country_code, :email, :code, presence: true
validates :name, :reg_no, :reference_no, :code, uniqueness: true
@ -48,7 +49,7 @@ class Registrar < ActiveRecord::Base
after_save :update_whois_records
def update_whois_records
return true unless changed? && (changes.keys & WHOIS_TRIGGERS).present?
return true unless changed? && (changes.keys & WHOIS_TRIGGERS).present?
whois_records.map(&:save) # slow currently
end
@ -145,4 +146,20 @@ class Registrar < ActiveRecord::Base
def code=(code)
self[:code] = code.gsub(/[ :]/, '').upcase if new_record? && code.present?
end
def repp_ip_white?(ip)
white_ips.repp.pluck(:ipv4, :ipv6).flatten.include?(ip) || global_ip_white?(ip)
end
def epp_ip_white?(ip)
white_ips.epp.pluck(:ipv4, :ipv6).flatten.include?(ip) || global_ip_white?(ip)
end
def registrar_ip_white?(ip)
white_ips.registrar.pluck(:ipv4, :ipv6).flatten.include?(ip) || global_ip_white?(ip)
end
def global_ip_white?(ip)
white_ips.global.pluck(:ipv4, :ipv6).flatten.include?(ip)
end
end

View file

@ -0,0 +1,5 @@
class WhiteIpVersion < PaperTrail::Version
include VersionSession
self.table_name = :log_white_ips
self.sequence_name = :log_white_ips_id_seq
end

40
app/models/white_ip.rb Normal file
View file

@ -0,0 +1,40 @@
class WhiteIp < ActiveRecord::Base
include Versions
belongs_to :registrar
# rubocop: disable Metrics/LineLength
validates :ipv4, format: { with: /\A(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\z/, allow_blank: true }
validates :ipv6, format: { with: /(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:)|fe80:(:[0-9a-fA-F]{0,4}){0,4}%[0-9a-zA-Z]{1,}|::(ffff(:0{1,4}){0,1}:){0,1}((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9]).){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])|([0-9a-fA-F]{1,4}:){1,4}:((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9]).){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9]))/, allow_blank: true }
# rubocop: enable Metrics/LineLength
validate :validate_ipv4_and_ipv6
def validate_ipv4_and_ipv6
return if ipv4.present? || ipv6.present?
errors.add(:base, I18n.t(:ipv4_or_ipv6_must_be_present))
end
EPP = 'epp'
REPP = 'repp'
REGISTRAR = 'registrar'
GLOBAL = 'global'
INTERFACES = [GLOBAL, EPP, REPP, REGISTRAR]
scope :epp, -> { where(interface: EPP) }
scope :repp, -> { where(interface: REPP) }
scope :registrar, -> { where(interface: REGISTRAR) }
scope :global, -> { where(interface: GLOBAL) }
class << self
def registrar_ip_white?(ip)
at = WhiteIp.arel_table
WhiteIp.where(
at[:interface].eq(REGISTRAR).or(
at[:interface].eq(GLOBAL)
).and(
at[:ipv4].eq(ip)
)
)
end
end
end

View file

@ -63,7 +63,7 @@
.pull-left
= t(:api_users)
.pull-right
= link_to(t(:create_new_api_user), new_admin_registrar_api_user_path(@registrar), class: 'btn btn-primary btn-xs')
= link_to(t(:create_new_api_user), new_admin_registrar_api_user_path(@registrar), class: 'btn btn-default btn-xs')
.table-responsive
%table.table.table-hover.table-bordered.table-condensed
@ -76,3 +76,26 @@
%tr
%td= link_to(x, [:admin, x])
%td= x.active
.row
.col-md-12
#epp-users.panel.panel-default
.panel-heading.clearfix
.pull-left
= t(:white_ips)
.pull-right
= link_to(t(:create_new_white_ip), new_admin_registrar_white_ip_path(@registrar), class: 'btn btn-default btn-xs')
.table-responsive
%table.table.table-hover.table-bordered.table-condensed
%thead
%tr
%th{class: 'col-xs-4'}= t(:ipv4)
%th{class: 'col-xs-6'}= t(:ipv6)
%th{class: 'col-xs-2'}= t(:interface)
%tbody
- @registrar.white_ips.order(:interface).each do |x|
%tr
%td= link_to(x.ipv4, [:admin, @registrar, x])
%td= link_to(x.ipv6, [:admin, @registrar, x])
%td= x.interface.upcase

View file

@ -0,0 +1,30 @@
= form_for([:admin, @registrar, @white_ip], html: {class: 'form-horizontal'}) do |f|
= render 'shared/full_errors', object: @white_ip
.row
.col-md-8
.form-group
.col-md-4.control-label
= f.label :registrar
.col-md-7
= f.text_field(:registrar, class: 'form-control', disabled: :disabled)
= f.hidden_field(:registrar_id, class: 'js-registrar-id')
.form-group
.col-md-4.control-label
= f.label :ipv4
.col-md-7
= f.text_field(:ipv4, class: 'form-control', ipv4: true)
.form-group
.col-md-4.control-label
= f.label :ipv6
.col-md-7
= f.text_field(:ipv6, class: 'form-control', ipv6: true)
.form-group
.col-md-4.control-label
= f.label :interface
.col-md-7
= f.select :interface, WhiteIp::INTERFACES.map {|x| [x.upcase, x]}, {}, class: 'form-control selectize'
%hr
.row
.col-md-8.text-right
= button_tag(t(:save), class: 'btn btn-primary')

View file

@ -0,0 +1,5 @@
- content_for :actions do
= link_to(t(:back_to_registrar), admin_registrar_path(@registrar), class: 'btn btn-default')
= render 'shared/title', name: t(:edit_white_ip)
= render 'form'

View file

@ -0,0 +1,5 @@
- content_for :actions do
= link_to(t(:back_to_registrar), admin_registrar_path(@registrar), class: 'btn btn-default')
= render 'shared/title', name: t(:create_new_white_ip)
= render 'form'

View file

@ -0,0 +1,24 @@
- content_for :actions do
= link_to(t(:edit), edit_admin_registrar_white_ip_path(@registrar, @white_ip), class: 'btn btn-primary')
= link_to(t(:delete), admin_registrar_white_ip_path(@registrar, @white_ip),
method: :delete, data: { confirm: t(:are_you_sure) }, class: 'btn btn-danger')
= render 'shared/title', name: t('white_ip')
.row
.col-md-12
.panel.panel-default
.panel-heading
%h3.panel-title= t(:general)
.panel-body
%dl.dl-horizontal
%dt= t(:registrar)
%dd= link_to(@registrar, [:admin, @registrar])
%dt= t(:ipv4)
%dd= @white_ip.ipv4
%dt= t(:ipv6)
%dd= @white_ip.ipv6
%dt= t(:interface)
%dd= @white_ip.interface.upcase

View file

@ -1,7 +1,7 @@
xml.epp_head do
xml.response do
xml.result('code' => '2501') do
xml.msg('Authentication error; server closing connection')
xml.msg(@msg || 'Authentication error; server closing connection')
end
end

View file

@ -1,28 +0,0 @@
#!/bin/bash
CRL_PATH='/home/registry/registry/shared/ca/crl'
mkdir -p $CRL_PATH/crl-temp
cd $CRL_PATH/crl-temp
wget https://sk.ee/crls/esteid/esteid2007.crl
wget https://sk.ee/crls/juur/crl.crl
wget https://sk.ee/crls/eeccrca/eeccrca.crl
wget https://sk.ee/repository/crls/esteid2011.crl
openssl crl -in esteid2007.crl -out esteid2007.crl -inform DER
openssl crl -in crl.crl -out crl.crl -inform DER
openssl crl -in eeccrca.crl -out eeccrca.crl -inform DER
openssl crl -in esteid2011.crl -out esteid2011.crl -inform DER
ln -s crl.crl `openssl crl -hash -noout -in crl.crl`.r0
ln -s esteid2007.crl `openssl crl -hash -noout -in esteid2007.crl`.r0
ln -s eeccrca.crl `openssl crl -hash -noout -in eeccrca.crl`.r0
ln -s esteid2011.crl `openssl crl -hash -noout -in esteid2011.crl`.r0
rm -rf ../*.crl ../*.r0
mv * ..
cd ..
rm -rf crl-temp
/etc/init.d/apache2 reload

View file

@ -225,6 +225,9 @@ en:
state: 'State / Province'
deposit:
amount: 'Amount'
white_ip:
ipv4: 'IPv4'
ipv6: 'IPv6'
errors:
messages:
@ -560,8 +563,6 @@ en:
code: 'Code'
nameservers: 'Nameservers'
hostname: 'Hostname'
ipv4: 'IPv4'
ipv6: 'IPv6'
dnskeys: 'DNS Keys'
flag: 'Flag'
protocol: 'Protocol'
@ -772,6 +773,11 @@ en:
not_valid_domain_verification_body: This could mean your verification has been expired or done already.<br><br>Please contact us if you think something is wrong.
upload_crt: 'Upload CRT'
crt_or_csr_must_be_present: 'CRT or CSR must be present'
white_ips: 'White IP-s'
create_new_white_ip: 'Create new white IP'
ipv4_or_ipv6_must_be_present: 'IPv4 or IPv6 must be present'
white_ip: 'White IP'
edit_white_ip: 'Edit white IP'
confirm_domain_delete: 'Confirm domain delete'
reject_domain_delete: 'Reject domain delete'
confirm_domain_registrant_update: 'Confirm domain ownership change'
@ -780,7 +786,7 @@ en:
domain_registrant_change_body: 'There is a request to change domain ownership. Before doing it we need your confirmation.'
new_pending_registrant: 'New owner'
current_registrant: 'Current owner'
registrant_domain_verification_failed: 'Domain verification not available'
registrant_domain_verification_failed: 'Domain verification not available'
domain_registrant_change_confirmed_title: 'Domain owner change has been confirmed'
domain_registrant_change_confirmed_body: 'You have successfully confirmed domain owner change.'
registrant_domain_verification_confirmed: 'Domain owner change has successfully confirmed.'
@ -789,3 +795,4 @@ en:
domain_registrant_change_rejected_body: 'You have rejected domain owner change.'
registrant_domain_verification_rejected: 'Domain owner change has been rejected successfully.'
registrant_domain_verification_rejected_failed: 'Something went wrong'
ip_is_not_whitelisted: 'IP is not whitelisted'

View file

@ -181,8 +181,10 @@ Rails.application.routes.draw do
end
resources :settings
resources :registrars do
resources :api_users
resources :white_ips
collection do
get :search
end

View file

@ -0,0 +1,11 @@
class CreateWhiteIp < ActiveRecord::Migration
def change
create_table :white_ips do |t|
t.integer :registrar_id
t.string :ipv4
t.string :ipv6
t.string :interface
t.timestamps
end
end
end

View file

@ -0,0 +1,18 @@
class CreateWhiteIpLog < ActiveRecord::Migration
def change
create_table :log_white_ips do |t|
t.string "item_type", null: false
t.integer "item_id", null: false
t.string "event", null: false
t.string "whodunnit"
t.json "object"
t.json "object_changes"
t.datetime "created_at"
t.string "session"
t.json "children"
end
add_column :white_ips, :creator_str, :string
add_column :white_ips, :updator_str, :string
end
end

View file

@ -797,6 +797,18 @@ ActiveRecord::Schema.define(version: 20150519144118) do
add_index "log_users", ["item_type", "item_id"], name: "index_log_users_on_item_type_and_item_id", using: :btree
add_index "log_users", ["whodunnit"], name: "index_log_users_on_whodunnit", using: :btree
create_table "log_white_ips", force: :cascade do |t|
t.string "item_type", null: false
t.integer "item_id", null: false
t.string "event", null: false
t.string "whodunnit"
t.json "object"
t.json "object_changes"
t.datetime "created_at"
t.string "session"
t.json "children"
end
create_table "log_zonefile_settings", force: :cascade do |t|
t.string "item_type", null: false
t.integer "item_id", null: false
@ -954,6 +966,17 @@ ActiveRecord::Schema.define(version: 20150519144118) do
t.text "depricated_table_but_somehow_paper_trail_tests_fails_without_it"
end
create_table "white_ips", force: :cascade do |t|
t.integer "registrar_id"
t.string "ipv4"
t.string "ipv6"
t.string "interface"
t.datetime "created_at"
t.datetime "updated_at"
t.string "creator_str"
t.string "updator_str"
end
create_table "whois_records", force: :cascade do |t|
t.integer "domain_id"
t.string "name"

View file

@ -39,6 +39,19 @@ describe 'EPP Session', epp: true do
response[:result_code].should == '2501'
end
it 'does not log in with ip that is not whitelisted' do
@registrar = Fabricate(:registrar,
{ name: 'registrar123', reg_no: '1234', white_ips: [Fabricate(:white_ip_repp), Fabricate(:white_ip_registrar)] }
)
Fabricate(:api_user, username: 'invalid-ip-user', registrar: @registrar)
inactive = @epp_xml.session.login(clID: { value: 'invalid-ip-user' }, pw: { value: 'ghyt9e4fu' })
response = epp_plain_request(inactive, :xml)
response[:msg].should == 'IP is not whitelisted'
response[:result_code].should == '2501'
end
it 'prohibits further actions unless logged in' do
response = epp_plain_request(@epp_xml.domain.create, :xml)
response[:msg].should == 'You need to login first.'

View file

@ -10,6 +10,7 @@ Fabricator(:registrar) do
code { sequence(:code) { |i| "REGISTRAR#{i}" } }
reference_no { sequence(:reference_no) { |i| "RF#{i}" } }
accounts(count: 1)
white_ips { [Fabricate(:white_ip)] }
end
Fabricator(:registrar_with_no_account_activities, from: :registrar) do

View file

@ -0,0 +1,16 @@
Fabricator(:white_ip) do
ipv4 '127.0.0.1'
interface WhiteIp::GLOBAL
end
Fabricator(:white_ip_repp, from: :white_ip) do
interface WhiteIp::REPP
end
Fabricator(:white_ip_epp, from: :white_ip) do
interface WhiteIp::EPP
end
Fabricator(:white_ip_registrar, from: :white_ip) do
interface WhiteIp::REGISTRAR
end

View file

@ -15,14 +15,14 @@ feature 'Api users', type: :feature do
it 'should redirect to login path' do
visit admin_api_user_url(@api_user)
current_path.should == '/admin/login'
end
end
context 'as logged in user' do
it 'should show index of contacts' do
it 'should show index of api users' do
sign_in @user
visit admin_api_users_url

View file

@ -0,0 +1,63 @@
require 'rails_helper'
feature 'Api users', type: :feature do
before :all do
@user = Fabricate(:admin_user, username: 'user1', identity_code: '37810013087')
@registrar = Fabricate(:registrar)
end
context 'as unknown user' do
it 'should redirect to login path' do
visit new_admin_registrar_white_ip_url(@registrar)
current_path.should == '/admin/login'
end
end
context 'as logged in user' do
before { sign_in @user }
it 'should add new white ip to registrar' do
visit admin_registrar_url(@registrar)
page.should_not have_text('192.168.1.1')
click_link 'Create new white IP'
fill_in 'IPv4', with: '192.168.1.1'
fill_in 'IPv6', with: 'FE80:0000:0000:0000:0202:B3FF:FE1E:8329'
select 'REPP', from: 'Interface'
click_button 'Save'
page.should have_text('Record created')
page.should have_text('White IP')
page.should have_link(@registrar.to_s)
page.should have_text('192.168.1.1')
page.should have_text('FE80:0000:0000:0000:0202:B3FF:FE1E:8329')
page.should have_text('REPP')
click_link @registrar.to_s
current_path.should == "/admin/registrars/#{@registrar.id}"
page.should have_text('192.168.1.1')
page.should have_text('FE80:0000:0000:0000:0202:B3FF:FE1E:8329')
page.should have_text('REPP')
end
it 'should not add invalid ip to registrar' do
visit new_admin_registrar_white_ip_url(@registrar)
click_button 'Save'
page.should have_text('IPv4 or IPv6 must be present')
page.should have_text('Failed to create record')
fill_in 'IPv4', with: 'bla'
fill_in 'IPv6', with: 'bla'
click_button 'Save'
page.should have_text('IPv4 is invalid')
page.should have_text('IPv6 is invalid')
end
end
end

View file

@ -4,6 +4,7 @@ describe Registrar do
it { should have_many(:domains) }
it { should have_many(:api_users) }
it { should have_many(:messages) }
it { should have_many(:white_ips) }
context 'with invalid attribute' do
before :all do

View file

@ -0,0 +1,54 @@
require 'rails_helper'
describe WhiteIp do
it { should belong_to(:registrar) }
context 'with invalid attribute' do
before :all do
@white_ip = WhiteIp.new
end
it 'is not valid' do
@white_ip.valid?
@white_ip.errors.full_messages.should match_array([
'IPv4 or IPv6 must be present'
])
end
it 'returns an error with invalid ips' do
@white_ip.ipv4 = 'bla'
@white_ip.ipv6 = 'bla'
@white_ip.valid?
@white_ip.errors[:ipv4].should == ['is invalid']
@white_ip.errors[:ipv6].should == ['is invalid']
end
end
context 'with valid attributes' do
before :all do
@white_ip = Fabricate(:white_ip)
end
it 'should be valid' do
@white_ip.valid?
@white_ip.errors.full_messages.should match_array([])
end
it 'should be valid twice' do
@white_ip = Fabricate(:white_ip)
@white_ip.valid?
@white_ip.errors.full_messages.should match_array([])
end
it 'should have one version' do
with_versioning do
@white_ip.versions.should == []
@white_ip.ipv4 = '192.168.1.2'
@white_ip.save
@white_ip.errors.full_messages.should match_array([])
@white_ip.versions.size.should == 1
end
end
end
end

View file

@ -1,30 +1,43 @@
require 'rails_helper'
describe Repp::AccountV1 do
before :all do
@registrar1 = Fabricate(:registrar1, accounts:
[Fabricate(:account, { balance: '324.45', account_activities: [] })]
)
@api_user = Fabricate(:gitlab_api_user, registrar: @registrar1)
it 'should fail without whitelisted IP' do
@registrar1 = Fabricate(:registrar, white_ips: [Fabricate(:white_ip_epp), Fabricate(:white_ip_registrar)])
@api_user = Fabricate(:api_user, registrar: @registrar1)
get_with_auth '/repp/v1/accounts/balance', {}, @api_user
response.status.should == 401
body = JSON.parse(response.body)
body['error'].should == 'IP is not whitelisted'
end
describe 'GET /repp/v1/accounts/balance' do
it 'returns account balance of the current registrar', autodoc: true, route_info_doc: true do
get_with_auth '/repp/v1/accounts/balance', {}, @api_user
response.status.should == 200
context 'with valid registrar' do
before :all do
@registrar1 = Fabricate(:registrar1, accounts:
[Fabricate(:account, { balance: '324.45', account_activities: [] })]
)
@api_user = Fabricate(:gitlab_api_user, registrar: @registrar1)
end
body = JSON.parse(response.body)
body['balance'].should == '324.45'
body['currency'].should == 'EUR'
describe 'GET /repp/v1/accounts/balance' do
it 'returns account balance of the current registrar', autodoc: true, route_info_doc: true do
get_with_auth '/repp/v1/accounts/balance', {}, @api_user
response.status.should == 200
log = ApiLog::ReppLog.last
log[:request_path].should == '/repp/v1/accounts/balance'
log[:request_method].should == 'GET'
log[:request_params].should == '{}'
log[:response_code].should == '200'
log[:api_user_name].should == 'gitlab'
log[:api_user_registrar].should == 'registrar1'
log[:ip].should == '127.0.0.1'
body = JSON.parse(response.body)
body['balance'].should == '324.45'
body['currency'].should == 'EUR'
log = ApiLog::ReppLog.last
log[:request_path].should == '/repp/v1/accounts/balance'
log[:request_method].should == 'GET'
log[:request_params].should == '{}'
log[:response_code].should == '200'
log[:api_user_name].should == 'gitlab'
log[:api_user_registrar].should == 'registrar1'
log[:ip].should == '127.0.0.1'
end
end
end
end