summaryrefslogtreecommitdiff
path: root/app/controllers
diff options
context:
space:
mode:
Diffstat (limited to 'app/controllers')
-rw-r--r--app/controllers/access_authorizations_controller.rb68
-rw-r--r--app/controllers/acd_agents_controller.rb73
-rw-r--r--app/controllers/acd_callers_controller.rb41
-rw-r--r--app/controllers/addresses_controller.rb41
-rw-r--r--app/controllers/api/rows_controller.rb91
-rw-r--r--app/controllers/application_controller.rb161
-rw-r--r--app/controllers/automatic_call_distributors_controller.rb100
-rw-r--r--app/controllers/call_forwards_controller.rb127
-rw-r--r--app/controllers/call_histories_controller.rb100
-rw-r--r--app/controllers/calls_controller.rb6
-rw-r--r--app/controllers/callthroughs_controller.rb75
-rw-r--r--app/controllers/conference_invitees_controller.rb93
-rw-r--r--app/controllers/conferences_controller.rb82
-rw-r--r--app/controllers/config_polycom_controller.rb330
-rw-r--r--app/controllers/config_siemens_controller.rb1239
-rw-r--r--app/controllers/config_siemens_sort_controller.rb371
-rw-r--r--app/controllers/config_snom_controller.rb1169
-rw-r--r--app/controllers/fax_accounts_controller.rb82
-rw-r--r--app/controllers/fax_documents_controller.rb82
-rw-r--r--app/controllers/freeswitch_voicemail_msgs_controller.rb7
-rw-r--r--app/controllers/gemeinschaft_setups_controller.rb61
-rw-r--r--app/controllers/gs_cluster_sync_log_entries_controller.rb25
-rw-r--r--app/controllers/gs_nodes_controller.rb170
-rw-r--r--app/controllers/gui_functions_controller.rb73
-rw-r--r--app/controllers/hunt_group_members_controller.rb67
-rw-r--r--app/controllers/hunt_groups_controller.rb55
-rw-r--r--app/controllers/manufacturers_controller.rb49
-rw-r--r--app/controllers/page_controller.rb24
-rw-r--r--app/controllers/phone_book_entries_controller.rb135
-rw-r--r--app/controllers/phone_books_controller.rb105
-rw-r--r--app/controllers/phone_models_controller.rb52
-rw-r--r--app/controllers/phone_number_ranges_controller.rb56
-rw-r--r--app/controllers/phone_numbers_controller.rb226
-rw-r--r--app/controllers/phone_sip_accounts_controller.rb60
-rw-r--r--app/controllers/phones_controller.rb72
-rw-r--r--app/controllers/ringtones_controller.rb67
-rw-r--r--app/controllers/sessions_controller.rb44
-rw-r--r--app/controllers/sip_accounts_controller.rb98
-rw-r--r--app/controllers/sip_domains_controller.rb41
-rw-r--r--app/controllers/softkeys_controller.rb91
-rw-r--r--app/controllers/system_messages_controller.rb30
-rw-r--r--app/controllers/tenants_controller.rb91
-rw-r--r--app/controllers/user_group_memberships_controller.rb48
-rw-r--r--app/controllers/user_groups_controller.rb69
-rw-r--r--app/controllers/users_controller.rb85
-rw-r--r--app/controllers/voicemail_messages_controller.rb140
-rw-r--r--app/controllers/voicemail_settings_controller.rb91
-rw-r--r--app/controllers/whitelists_controller.rb61
48 files changed, 6524 insertions, 0 deletions
diff --git a/app/controllers/access_authorizations_controller.rb b/app/controllers/access_authorizations_controller.rb
new file mode 100644
index 0000000..54365e7
--- /dev/null
+++ b/app/controllers/access_authorizations_controller.rb
@@ -0,0 +1,68 @@
+class AccessAuthorizationsController < ApplicationController
+ load_and_authorize_resource :callthrough
+ load_and_authorize_resource :access_authorization, :through => [:callthrough]
+
+ before_filter :set_parent_and_path_methods
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @access_authorization = @parent.access_authorizations.build
+ @access_authorization.name = generate_a_new_name(@parent, @access_authorization)
+ @access_authorization.phone_numbers.build
+ @access_authorization.login = random_pin + random_pin
+ @access_authorization.pin = random_pin
+ end
+
+ def create
+ @access_authorization = @parent.access_authorizations.build(params[:access_authorization])
+ if @access_authorization.save
+ redirect_to @show_path_method.(@parent, @access_authorization), :notice => t('access_authorizations.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @access_authorization.update_attributes(params[:access_authorization])
+ redirect_to @show_path_method.(@parent, @access_authorization), :notice => t('access_authorizations.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @access_authorization.destroy
+ redirect_to @index_path_method.(@parent), :notice => t('access_authorizations.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def set_parent_and_path_methods
+ @parent = @callthrough
+ @show_path_method = method( :"#{@parent.class.name.underscore}_access_authorization_path" )
+ @index_path_method = method( :"#{@parent.class.name.underscore}_access_authorizations_path" )
+ @new_path_method = method( :"new_#{@parent.class.name.underscore}_access_authorization_path" )
+ @edit_path_method = method( :"edit_#{@parent.class.name.underscore}_access_authorization_path" )
+ end
+
+ def spread_breadcrumbs
+ if @callthrough
+ add_breadcrumb t("#{@parent.class.name.underscore.pluralize}.index.page_title"), tenant_callthroughs_path(@callthrough.tenant)
+ add_breadcrumb @callthrough, tenant_callthrough_path(@callthrough.tenant, @callthrough)
+ add_breadcrumb t("access_authorizations.index.page_title"), callthrough_access_authorizations_path(@callthrough)
+ if @access_authorization && !@access_authorization.new_record?
+ add_breadcrumb @access_authorization, callthrough_access_authorization_path(@callthrough, @access_authorization)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/acd_agents_controller.rb b/app/controllers/acd_agents_controller.rb
new file mode 100644
index 0000000..1d119b3
--- /dev/null
+++ b/app/controllers/acd_agents_controller.rb
@@ -0,0 +1,73 @@
+class AcdAgentsController < ApplicationController
+ load_and_authorize_resource :automatic_call_distributor
+ load_and_authorize_resource :acd_agent, :through => [:automatic_call_distributor]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ if params[:active]
+ if params[:active].downcase == 'true'
+ @acd_agents = @acd_agents.where(:active => true)
+ elsif params[:active].downcase == 'false'
+ @acd_agents = @acd_agents.where(:active => false)
+ end
+ end
+ end
+
+ def show
+ @acd_agent = AcdAgent.find(params[:id])
+ end
+
+ def new
+ @acd_agent = @automatic_call_distributor.acd_agents.build
+ i = @automatic_call_distributor.acd_agents.count
+ loop do
+ i += 1
+ break unless @automatic_call_distributor.acd_agents.where(:name => "#{t('acd_agents.name')} #{i}").count > 0
+ end
+ @acd_agent.name = "#{t('acd_agents.name')} #{i}"
+ @acd_agent.status = 'active'
+ @acd_agent.calls_answered = 0
+ end
+
+ def create
+ @acd_agent = @automatic_call_distributor.acd_agents.build(params[:acd_agent])
+ if @acd_agent.save
+ redirect_to automatic_call_distributor_acd_agent_path(@automatic_call_distributor, @acd_agent), :notice => t('acd_agents.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ @acd_agent = AcdAgent.find(params[:id])
+ end
+
+ def update
+ @acd_agent = AcdAgent.find(params[:id])
+ if @acd_agent.update_attributes(params[:acd_agent])
+ redirect_to automatic_call_distributor_acd_agent_path(@automatic_call_distributor, @acd_agent), :notice => t('acd_agents.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @acd_agent = AcdAgent.find(params[:id])
+ @acd_agent.destroy
+ redirect_to automatic_call_distributor_acd_agents_path(@automatic_call_distributor), :notice => t('acd_agents.controller.successfuly_destroyed')
+ end
+
+ def spread_breadcrumbs
+ if @automatic_call_distributor.automatic_call_distributorable.class == User
+ add_breadcrumb t("#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore.pluralize}.index.page_title"), method( :"tenant_#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore.pluralize}_path" ).(@automatic_call_distributor.tenant)
+ add_breadcrumb @automatic_call_distributor.automatic_call_distributorable, method( :"tenant_#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore}_path" ).(@automatic_call_distributor.tenant, @automatic_call_distributor.automatic_call_distributorable)
+ end
+ add_breadcrumb t("automatic_call_distributors.index.page_title"), method( :"#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore}_automatic_call_distributors_path" ).(@automatic_call_distributor.automatic_call_distributorable)
+ add_breadcrumb @automatic_call_distributor, method( :"#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore}_automatic_call_distributor_path" ).(@automatic_call_distributor.automatic_call_distributorable, @automatic_call_distributor)
+ add_breadcrumb t("acd_agents.index.page_title"), automatic_call_distributor_acd_agents_path(@automatic_call_distributor)
+ if @acd_agent && !@acd_agent.new_record?
+ add_breadcrumb @acd_agent, automatic_call_distributor_acd_agent_path(@automatic_call_distributor, @acd_agent)
+ end
+ end
+end
diff --git a/app/controllers/acd_callers_controller.rb b/app/controllers/acd_callers_controller.rb
new file mode 100644
index 0000000..ab58064
--- /dev/null
+++ b/app/controllers/acd_callers_controller.rb
@@ -0,0 +1,41 @@
+class AcdCallersController < ApplicationController
+ def index
+ @acd_callers = AcdCaller.all
+ end
+
+ def show
+ @acd_caller = AcdCaller.find(params[:id])
+ end
+
+ def new
+ @acd_caller = AcdCaller.new
+ end
+
+ def create
+ @acd_caller = AcdCaller.new(params[:acd_caller])
+ if @acd_caller.save
+ redirect_to @acd_caller, :notice => t('acd_callers.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ @acd_caller = AcdCaller.find(params[:id])
+ end
+
+ def update
+ @acd_caller = AcdCaller.find(params[:id])
+ if @acd_caller.update_attributes(params[:acd_caller])
+ redirect_to @acd_caller, :notice => t('acd_callers.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @acd_caller = AcdCaller.find(params[:id])
+ @acd_caller.destroy
+ redirect_to acd_callers_url, :notice => t('acd_callers.controller.successfuly_destroyed')
+ end
+end
diff --git a/app/controllers/addresses_controller.rb b/app/controllers/addresses_controller.rb
new file mode 100644
index 0000000..a70b1f4
--- /dev/null
+++ b/app/controllers/addresses_controller.rb
@@ -0,0 +1,41 @@
+class AddressesController < ApplicationController
+ def index
+ @addresses = Address.all
+ end
+
+ def show
+ @address = Address.find(params[:id])
+ end
+
+ def new
+ @address = Address.new
+ end
+
+ def create
+ @address = Address.new(params[:address])
+ if @address.save
+ redirect_to @address, :notice => t('addresses.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ @address = Address.find(params[:id])
+ end
+
+ def update
+ @address = Address.find(params[:id])
+ if @address.update_attributes(params[:address])
+ redirect_to @address, :notice => t('addresses.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @address = Address.find(params[:id])
+ @address.destroy
+ redirect_to addresses_url, :notice => t('addresses.controller.successfuly_destroyed')
+ end
+end
diff --git a/app/controllers/api/rows_controller.rb b/app/controllers/api/rows_controller.rb
new file mode 100644
index 0000000..6e815eb
--- /dev/null
+++ b/app/controllers/api/rows_controller.rb
@@ -0,0 +1,91 @@
+class Api::RowsController < ApplicationController
+ before_filter :check_remote_ip_address_whitelist
+
+ def index
+ @rows = Api::Row.all
+
+ respond_to do |format|
+ format.xml { render xml: @rows }
+ end
+ end
+
+ def show
+ if params[:user_name]
+ @row = Api::Row.find_by_user_name(params[:user_name])
+ else
+ @row = Api::Row.find(params[:id])
+ end
+
+ respond_to do |format|
+ format.xml { render xml: @row }
+ end
+ end
+
+ def new
+ @row = Api::Row.new
+
+ respond_to do |format|
+ format.xml { render xml: @row }
+ end
+ end
+
+ def edit
+ if params[:user_name]
+ @row = Api::Row.find_by_user_name(params[:user_name])
+ else
+ @row = Api::Row.find(params[:id])
+ end
+ end
+
+ def create
+ @row = Api::Row.new(params[:row])
+
+ respond_to do |format|
+ if @row.save
+ @row.create_a_new_gemeinschaft_user
+
+ format.xml { render xml: @row, status: :created, location: @row }
+ else
+ format.xml { render xml: @row.errors, status: :unprocessable_entity }
+ end
+ end
+ end
+
+ def update
+ if params[:user_name]
+ @row = Api::Row.find_by_user_name(params[:user_name])
+ else
+ @row = Api::Row.find(params[:id])
+ end
+
+ respond_to do |format|
+ if @row.update_attributes(params[:row])
+ @row.update_user_data
+ format.xml { head :no_content }
+ else
+ format.xml { render xml: @row.errors, status: :unprocessable_entity }
+ end
+ end
+ end
+
+ def destroy
+ if params[:user_name]
+ @row = Api::Row.find_by_user_name(params[:user_name])
+ else
+ @row = Api::Row.find(params[:id])
+ end
+ @row.destroy
+
+ respond_to do |format|
+ format.xml { head :no_content }
+ end
+ end
+
+ private
+
+ def check_remote_ip_address_whitelist
+ if !(REMOTE_IP_ADDRESS_WHITELIST.empty? or REMOTE_IP_ADDRESS_WHITELIST.include?(ENV['REMOTE_ADDR']))
+ redirect_to root_url
+ end
+ end
+end
diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb
new file mode 100644
index 0000000..c675f5c
--- /dev/null
+++ b/app/controllers/application_controller.rb
@@ -0,0 +1,161 @@
+class ApplicationController < ActionController::Base
+
+ protect_from_forgery
+
+ before_filter :set_locale
+
+ before_filter :go_to_setup_if_new_installation
+ before_filter :home_breadcrumb
+
+ helper_method :current_user
+
+ helper_method :guess_local_ip_address
+ helper_method :guess_local_host
+
+ helper_method :'have_https?'
+
+ helper_method :random_pin
+
+
+ #TODO Add check_authorization. See
+ # https://github.com/ryanb/cancan
+ # https://github.com/ryanb/cancan/wiki/Ensure-Authorization
+ # and Gemeinschaft 4
+
+ # Generate a new name for an Object
+ #
+ def generate_a_new_name(parent, child = nil)
+ if child
+ i = parent.send(child.class.name.underscore.pluralize).count
+ loop do
+ i += 1
+ if I18n.t("#{child.class.name.underscore.pluralize}.new_name_scaffold").include?('translation missing')
+ @guess_a_new_name = I18n.t(child.class.name.underscore.pluralize + '.name') + " #{i}"
+ else
+ @guess_a_new_name = I18n.t("#{child.class.name.underscore.pluralize}.new_name_scaffold", :counter => i.to_s)
+ end
+ break unless parent.send(child.class.name.underscore.pluralize).where(:name => "#{@guess_a_new_name}").count > 0
+ end
+ else
+ i = parent.class.count
+ loop do
+ i += 1
+ if I18n.t("#{parent.class.name.underscore.pluralize}.new_name_scaffold").include?('translation missing')
+ @guess_a_new_name = I18n.t(parent.class.name.underscore.pluralize + '.name') + " #{i}"
+ else
+ @guess_a_new_name = I18n.t("#{parent.class.name.underscore.pluralize}.new_name_scaffold", :counter => i.to_s)
+ end
+ break unless parent.class.where(:name => "#{@guess_a_new_name}").count > 0
+ end
+ end
+ return @guess_a_new_name
+ end
+
+ # Generate a new random PIN
+ #
+ def random_pin
+ if MINIMUM_PIN_LENGTH > 0
+ (1..MINIMUM_PIN_LENGTH).map{|i| (0 .. 9).to_a.sample}.join
+ end
+ end
+
+ # return the IP address (preferred) or hostname at which the
+ # current request arrived
+ def server_host
+ return (
+ request.env['SERVER_ADDR'] ||
+ request.env['SERVER_NAME'] ||
+ request.env['HTTP_HOST']
+ )
+ end
+
+ def have_https?
+ return Connectivity::port_open?( server_host(), 443 )
+ end
+
+
+ def guess_local_ip_address
+ ret = nil
+ begin
+ ipsocket_addr_info = UDPSocket.open {|s| s.connect("255.255.255.254", 1); s.addr(false) }
+ ret = ipsocket_addr_info.last if ipsocket_addr_info
+ rescue
+ end
+ return ret
+ end
+
+ def guess_local_host
+ ret = guess_local_ip_address()
+ if ! ret
+ begin
+ if request
+ ret = request.env['SERVER_NAME']
+ end
+ rescue
+ end
+ end
+ if ret && [
+ '',
+ 'localhost',
+ '127.0.0.1',
+ '0.0.0.0',
+ ].include?(ret)
+ ret = nil
+ end
+ return ret
+ end
+
+ rescue_from CanCan::AccessDenied do |exception|
+ if @current_user
+ redirect_to root_url, :alert => 'Access denied! Please ask your admin to grant you the necessary rights.'
+ else
+ if Tenant.count == 0 && User.count == 0
+ # This is a brand new system. We need to run a setup first.
+ redirect_to wizards_new_initial_setup_path
+ else
+ # You need to login first.
+ redirect_to log_in_path, :alert => 'Access denied! You need to login first.'
+ end
+ end
+ end
+
+ private
+
+ def current_user
+ begin
+ @current_user ||= User.find(session[:user_id]) if session[:user_id]
+ rescue ActiveRecord::RecordNotFound
+ session[:user_id] = nil
+ end
+ @current_user
+ end
+
+ def go_to_setup_if_new_installation
+ if Rails.env != 'test'
+ if GemeinschaftSetup.all.count == 0
+ redirect_to new_gemeinschaft_setup_path
+ end
+ end
+ end
+
+ def home_breadcrumb
+ if current_user
+ if current_user && Tenant.find(current_user.current_tenant_id)
+ add_breadcrumb( current_user.current_tenant, tenant_path(current_user.current_tenant) )
+ else
+ add_breadcrumb I18n.t('pages.controller.index.name'), :root_path
+ end
+ end
+ end
+
+ def set_locale
+ if current_user && Language.find(current_user.language_id)
+ I18n.locale = current_user.language.code.downcase
+ else
+ logger.debug "* Accept-Language: #{request.env['HTTP_ACCEPT_LANGUAGE']}"
+ I18n.locale = request.compatible_language_from(Language.all.map{|x| x.code})
+ end
+ logger.debug "* Locale set to '#{I18n.locale}'"
+ end
+
+end
diff --git a/app/controllers/automatic_call_distributors_controller.rb b/app/controllers/automatic_call_distributors_controller.rb
new file mode 100644
index 0000000..cc0c7e6
--- /dev/null
+++ b/app/controllers/automatic_call_distributors_controller.rb
@@ -0,0 +1,100 @@
+class AutomaticCallDistributorsController < ApplicationController
+ DEFAULT_STRATEGY = 'round_robin'
+ DEFAULT_MAX_CALLERS = 50
+ DEFAULT_AGENT_TIMEOUT = 20
+ DEFAULT_RETRY_TIMEOUT = 10
+ DEFAULT_JOIN = 'agents_active'
+ DEFAULT_LEAVE = 'no_agents_active'
+
+ load_resource :user
+ load_resource :tenant
+ load_and_authorize_resource :automatic_call_distributor, :through => [:user, :tenant ]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ @automatic_call_distributors = AutomaticCallDistributor.all
+ end
+
+ def show
+ @automatic_call_distributor = AutomaticCallDistributor.find(params[:id])
+ end
+
+ def new
+ i = @parent.automatic_call_distributors.count
+ loop do
+ i += 1
+ break unless @parent.automatic_call_distributors.where(:name => "#{t('automatic_call_distributors.name')} #{i}").count > 0
+ end
+ @strategies = AutomaticCallDistributor::STRATEGIES.collect {|r| [ t("automatic_call_distributors.strategies.#{r.to_s}"), r.to_s ] }
+ @join_on = AutomaticCallDistributor::JOIN_ON.collect {|r| [ t("automatic_call_distributors.join_on.#{r.to_s}"), r.to_s ] }
+ @leave_on = AutomaticCallDistributor::LEAVE_ON.collect {|r| [ t("automatic_call_distributors.leave_on.#{r.to_s}"), r.to_s ] }
+ @automatic_call_distributor = @parent.automatic_call_distributors.build(
+ :name => "#{t('automatic_call_distributors.name')} #{i}",
+ :strategy => DEFAULT_STRATEGY,
+ :max_callers => DEFAULT_MAX_CALLERS,
+ :retry_timeout => DEFAULT_RETRY_TIMEOUT,
+ :agent_timeout => DEFAULT_AGENT_TIMEOUT,
+ :join => DEFAULT_JOIN,
+ :leave => DEFAULT_LEAVE,
+ )
+
+ end
+
+ def create
+ @automatic_call_distributor = @parent.automatic_call_distributors.build(params[:automatic_call_distributor])
+ if @automatic_call_distributor.save
+ m = method( :"#{@parent.class.name.underscore}_automatic_call_distributor_path" )
+ redirect_to m.( @parent, @automatic_call_distributor ), :notice => t('automatic_call_distributors.controller.successfuly_created', :resource => @parent)
+ else
+ render :new
+ end
+ end
+
+ def edit
+ @strategies = AutomaticCallDistributor::STRATEGIES.collect {|r| [ t("automatic_call_distributors.strategies.#{r.to_s}"), r.to_s ] }
+ @join_on = AutomaticCallDistributor::JOIN_ON.collect {|r| [ t("automatic_call_distributors.join_on.#{r.to_s}"), r.to_s ] }
+ @leave_on = AutomaticCallDistributor::LEAVE_ON.collect {|r| [ t("automatic_call_distributors.leave_on.#{r.to_s}"), r.to_s ] }
+ @automatic_call_distributor = AutomaticCallDistributor.find(params[:id])
+ end
+
+ def update
+ if @automatic_call_distributor.update_attributes(params[:automatic_call_distributor])
+ m = method( :"#{@parent.class.name.underscore}_automatic_call_distributor_path" )
+ redirect_to m.( @parent, @automatic_call_distributor ), :notice => t('automatic_call_distributors.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @automatic_call_distributor = AutomaticCallDistributor.find(params[:id])
+ @automatic_call_distributor.destroy
+ m = method( :"#{@parent.class.name.underscore}_automatic_call_distributors_url" )
+ redirect_to m.( @parent ), :notice => t('automatic_call_distributors.controller.successfuly_destroyed')
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @user || @tenant
+ authorize! :read, @parent
+ end
+
+ def spread_breadcrumbs
+ if @user
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t("automatic_call_distributors.index.page_title"), user_automatic_call_distributors_path(@user)
+ if @automatic_call_distributor && !@automatic_call_distributor.new_record?
+ add_breadcrumb @automatic_call_distributor, user_automatic_call_distributor_path(@user, @automatic_call_distributor)
+ end
+ end
+ if @tenant
+ add_breadcrumb t("automatic_call_distributors.index.page_title"), tenant_automatic_call_distributors_path(@tenant)
+ if @automatic_call_distributor && !@automatic_call_distributor.new_record?
+ add_breadcrumb @automatic_call_distributor, tenant_automatic_call_distributor_path(@tenant, @automatic_call_distributor)
+ end
+ end
+ end
+end
diff --git a/app/controllers/call_forwards_controller.rb b/app/controllers/call_forwards_controller.rb
new file mode 100644
index 0000000..5321b35
--- /dev/null
+++ b/app/controllers/call_forwards_controller.rb
@@ -0,0 +1,127 @@
+class CallForwardsController < ApplicationController
+ load_and_authorize_resource :phone_number
+ load_and_authorize_resource :call_forward, :through => [:phone_number]
+
+ before_filter :spread_breadcrumbs
+
+ class CallForwardingDestination
+ attr_accessor :id, :label
+
+ def to_s
+ return label
+ end
+ end
+
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @call_forward = @phone_number.call_forwards.build
+ @call_forward.depth = DEFAULT_CALL_FORWARD_DEPTH
+ @call_forward.active = true
+ @call_forwarding_destinations = call_forwarding_destination_types()
+ @call_forward.destination = CALLFORWARD_DESTINATION_DEFAULT.to_s if defined?(CALLFORWARD_DESTINATION_DEFAULT)
+
+ @available_call_forward_cases = []
+ CallForwardCase.all.each do |available_call_forward_case|
+ if GuiFunction.display?("call_forward_case_#{available_call_forward_case.value}_field_in_call_forward_form", @current_user)
+ @available_call_forward_cases << available_call_forward_case
+ end
+ end
+
+ if @phone_number.call_forwards.where(
+ :call_forward_case_id => CallForwardCase.find_by_value('noanswer').id,
+ :active => true
+ ).count == 0
+ @call_forward.call_forward_case_id = CallForwardCase.find_by_value('noanswer').id
+ @call_forward.timeout = 45
+ end
+ end
+
+ def create
+ @call_forward = @phone_number.call_forwards.build( params[:call_forward] )
+
+ if @call_forward.save
+ redirect_to phone_number_call_forward_path( @phone_number, @call_forward ), :notice => t('call_forwards.controller.successfuly_created')
+ else
+ @available_call_forward_cases = CallForwardCase.all
+ render :new
+ end
+ end
+
+ def edit
+ @available_call_forward_cases = CallForwardCase.all
+ @call_forwarding_destinations = call_forwarding_destination_types()
+ end
+
+ def update
+ @available_call_forward_cases = CallForwardCase.all
+ if @call_forward.update_attributes(params[:call_forward])
+ redirect_to phone_number_call_forward_path( @phone_number, @call_forward ), :notice => t('call_forwards.controller.successfuly_updated')
+ else
+ @call_forwarding_destinations = call_forwarding_destination_types()
+ render :edit
+ end
+ end
+
+ def destroy
+ @call_forward.destroy
+ redirect_to phone_number_call_forwards_path( @phone_number ), :notice => t('call_forwards.controller.successfuly_destroyed')
+ end
+
+ private
+ def spread_breadcrumbs
+ if @phone_number && @phone_number.phone_numberable_type == 'SipAccount'
+ @sip_account = @phone_number.phone_numberable
+ if @sip_account.sip_accountable_type == 'User'
+ @user = @phone_number.phone_numberable.sip_accountable
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_users_path(@user.current_tenant, @user)
+ add_breadcrumb t("sip_accounts.index.page_title"), user_sip_accounts_path(@user)
+ add_breadcrumb @sip_account, user_sip_account_path(@user, @sip_account)
+ end
+ if @sip_account.sip_accountable_type == 'Tenant'
+ @tenant = @sip_account.sip_accountable
+ add_breadcrumb t("sip_accounts.index.page_title"), tenant_sip_accounts_path(@tenant)
+ add_breadcrumb @sip_account, tenant_sip_account_path(@tenant, @sip_account)
+ end
+ add_breadcrumb t("phone_numbers.index.page_title"), sip_account_phone_numbers_path(@sip_account)
+ add_breadcrumb @phone_number, sip_account_phone_number_path(@sip_account, @phone_number)
+ add_breadcrumb t("call_forwards.index.page_title"), phone_number_call_forwards_path(@phone_number)
+ if @call_forward && !@call_forward.new_record?
+ add_breadcrumb @call_forward, phone_number_call_forward_path(@phone_number, @call_forward)
+ end
+ end
+ end
+
+ def call_forwarding_destination_types
+
+ phone_number_destination = CallForwardingDestination.new()
+ phone_number_destination.id = ':PhoneNumber'
+ phone_number_destination.label = 'Phone Number'
+ voice_mail_destination = CallForwardingDestination.new()
+ voice_mail_destination.id = ':Voicemail'
+ voice_mail_destination.label = 'Voice Mail'
+
+ call_forwarding_destinations = [
+ phone_number_destination,
+ voice_mail_destination,
+ ]
+
+ if GuiFunction.display?('huntgroup_in_destination_field_in_call_forward_form', @current_user)
+ HuntGroup.all.each do |hunt_group|
+ hunt_group_destination = CallForwardingDestination.new()
+ hunt_group_destination.id = "#{hunt_group.id}:HuntGroup"
+ hunt_group_destination.label = "HuntGroup: #{hunt_group.to_s}"
+ call_forwarding_destinations.push(hunt_group_destination)
+ end
+ end
+
+ return call_forwarding_destinations
+ end
+
+end
diff --git a/app/controllers/call_histories_controller.rb b/app/controllers/call_histories_controller.rb
new file mode 100644
index 0000000..f956f88
--- /dev/null
+++ b/app/controllers/call_histories_controller.rb
@@ -0,0 +1,100 @@
+class CallHistoriesController < ApplicationController
+
+ load_resource :sip_account
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ before_filter { |controller|
+ if ! params[:type].blank? then
+ @type = params[:type].to_s
+ end
+
+ if ! params[:page].blank? then
+ @pagination_page_number = params[:page].to_i
+ end
+ }
+
+ def index
+ hunt_group_member_ids = PhoneNumber.where(:phone_numberable_type => 'HuntGroupMember', :number => @sip_account.phone_numbers.map {|a| a.number}).map {|a| a.phone_numberable_id}
+ hunt_group_ids = HuntGroupMember.where(:id => hunt_group_member_ids, :active => true).map {|a| a.hunt_group_id}
+ calls = CallHistory.where('(call_historyable_type = "SipAccount" AND call_historyable_id = ?) OR (call_historyable_type = "HuntGroup" AND call_historyable_id IN (?))', @sip_account.id, hunt_group_ids).order('start_stamp DESC')
+
+ @call_histories = calls.paginate(
+ :page => @pagination_page_number,
+ :per_page => DEFAULT_PAGINATION_ENTRIES_PER_PAGE
+ )
+
+ @calls_count = calls.count
+ @calls_received_count = calls.where(:entry_type => 'received').count
+ @calls_dialed_count = calls.where(:entry_type => 'dialed').count
+ @calls_missed_count = calls.where(:entry_type => 'missed').count
+ @calls_forwarded_count = calls.where(:entry_type => 'forwarded').count
+
+ if ! @type.blank?
+ @call_histories = @call_histories.where(:entry_type => @type)
+ end
+ end
+
+
+ def destroy
+ @call_history = CallHistory.where(:id => params[:id]).first
+ if can?(:destroy, @call_history)
+ @call_history.destroy
+ m = method( :"#{@parent.class.name.underscore}_call_histories_url" )
+ redirect_to m.(), :notice => t('call_histories.controller.successfuly_destroyed')
+ end
+ end
+
+ def destroy_multiple
+ if ! params[:selected_ids].blank? then
+ result = @sip_account.call_histories.where(:id => params[:selected_ids]).destroy_all();
+ end
+
+ m = method( :"#{@parent.class.name.underscore}_call_histories_url" )
+ if result
+ redirect_to m.(), :notice => t('call_histories.controller.successfuly_destroyed')
+ else
+ redirect_to m.()
+ end
+ end
+
+ def call
+ @call_history = CallHistory.where(:id => params[:id]).first
+ if can?(:call, @call_history) && @sip_account.registration
+ phone_number = @call_history.display_number
+ if ! phone_number.blank?
+ @sip_account.call(phone_number)
+ end
+ end
+ redirect_to(:back)
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @sip_account
+
+ authorize! :read, @parent
+
+ @show_path_method = method( :"#{@parent.class.name.underscore}_call_history_path" )
+ @index_path_method = method( :"#{@parent.class.name.underscore}_call_histories_path" )
+ @new_path_method = method( :"new_#{@parent.class.name.underscore}_call_history_path" )
+ @edit_path_method = method( :"edit_#{@parent.class.name.underscore}_call_history_path" )
+ end
+
+ def spread_breadcrumbs
+ if @parent.class == SipAccount
+ if @sip_account.sip_accountable.class == User
+ add_breadcrumb t("#{@sip_account.sip_accountable.class.name.underscore.pluralize}.index.page_title"), method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore.pluralize}_path" ).(@sip_account.tenant)
+ add_breadcrumb @sip_account.sip_accountable, method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore}_path" ).(@sip_account.tenant, @sip_account.sip_accountable)
+ end
+ add_breadcrumb t("sip_accounts.index.page_title"), method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_accounts_path" ).(@sip_account.sip_accountable)
+ add_breadcrumb @sip_account, method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_account_path" ).(@sip_account.sip_accountable, @sip_account)
+ add_breadcrumb t("call_histories.index.page_title"), sip_account_call_histories_path(@sip_account)
+ if @call_history && !@call_history.new_record?
+ add_breadcrumb @call_history, sip_account_call_history_path(@sip_account, @call_history)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/calls_controller.rb b/app/controllers/calls_controller.rb
new file mode 100644
index 0000000..d5f3b42
--- /dev/null
+++ b/app/controllers/calls_controller.rb
@@ -0,0 +1,6 @@
+class CallsController < ApplicationController
+
+ def index
+ @calls = Call.all
+ end
+end
diff --git a/app/controllers/callthroughs_controller.rb b/app/controllers/callthroughs_controller.rb
new file mode 100644
index 0000000..f489622
--- /dev/null
+++ b/app/controllers/callthroughs_controller.rb
@@ -0,0 +1,75 @@
+class CallthroughsController < ApplicationController
+ load_and_authorize_resource :tenant
+ load_and_authorize_resource :callthrough, :through => [:tenant]
+
+ before_filter :set_parent_and_path_methods
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @callthrough = @tenant.callthroughs.build
+ @callthrough.name = generate_a_new_name(@tenant, @callthrough)
+ @callthrough.phone_numbers.build
+ @callthrough.access_authorizations.build(:name => "#{t('access_authorizations.name')} #{@callthrough.access_authorizations.count + 1}", :pin => random_pin).phone_numbers.build
+ @callthrough.whitelists.build.phone_numbers.build
+ end
+
+ def create
+ @callthrough = @tenant.callthroughs.build(params[:callthrough])
+ if @callthrough.save
+ redirect_to tenant_callthrough_path(@tenant, @callthrough), :notice => t('callthroughs.controller.successfuly_created')
+ else
+ @callthrough.phone_numbers.build if @callthrough.phone_numbers.size == 0
+ render :new
+ end
+ end
+
+ def edit
+ @callthrough.phone_numbers.build
+ @callthrough.access_authorizations.build.phone_numbers.build
+ if @callthrough.whitelisted_phone_numbers.count == 0
+ if @callthrough.whitelists.count == 0
+ @callthrough.whitelists.build.phone_numbers.build
+ else
+ @callthrough.whitelists.first.phone_numbers.build
+ end
+ end
+ end
+
+ def update
+ if @callthrough.update_attributes(params[:callthrough])
+ redirect_to tenant_callthrough_path(@tenant, @callthrough), :notice => t('callthroughs.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @callthrough.destroy
+ redirect_to tenant_callthroughs_path(@tenant), :notice => t('callthroughs.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def set_parent_and_path_methods
+ @parent = @tenant
+ @show_path_method = method( :"#{@parent.class.name.underscore}_callthrough_path" )
+ @index_path_method = method( :"#{@parent.class.name.underscore}_callthroughs_path" )
+ @new_path_method = method( :"new_#{@parent.class.name.underscore}_callthrough_path" )
+ @edit_path_method = method( :"edit_#{@parent.class.name.underscore}_callthrough_path" )
+ end
+
+ def spread_breadcrumbs
+ if @parent && @parent.class == Tenant
+ add_breadcrumb t("callthroughs.name").pluralize, tenant_callthroughs_path(@parent)
+ if @callthrough && !@callthrough.new_record?
+ add_breadcrumb @callthrough, tenant_callthrough_path(@parent, @callthrough)
+ end
+ end
+ end
+end
diff --git a/app/controllers/conference_invitees_controller.rb b/app/controllers/conference_invitees_controller.rb
new file mode 100644
index 0000000..ce55b5a
--- /dev/null
+++ b/app/controllers/conference_invitees_controller.rb
@@ -0,0 +1,93 @@
+class ConferenceInviteesController < ApplicationController
+ load_and_authorize_resource :conference
+ load_and_authorize_resource :conference_invitee, :through => [:conference]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @conference_invitee = @conference.conference_invitees.build
+ @conference_invitee.speaker = true
+ @conference_invitee.moderator = false
+ @phone_number = @conference_invitee.build_phone_number
+ end
+
+ def create
+ @conference_invitee = @conference.conference_invitees.build(params[:conference_invitee])
+
+ # Try to find this phone_number in phone_books the current_user can read.
+ # Save the found entry as phone_book_entry.
+ #
+ @conference_invitee.phone_number.parse_and_split_number!
+ phone_numbers = PhoneNumber.where(:number => @conference_invitee.phone_number.number).
+ where(:phone_numberable_type => 'PhoneBookEntry')
+ phone_numbers.each do |phone_number|
+ phone_book = phone_number.phone_numberable.phone_book
+ if can?(:read, phone_book)
+ @conference_invitee.phone_book_entry = phone_number.phone_numberable
+ break
+ end
+ end
+
+ if @conference_invitee.save
+ # m = method( :"#{@parent_in_route.class.name.underscore}_path" )
+ # redirect_to m.( @parent_in_route ), :notice => t('conference_invitees.controller.successfuly_created', :resource => @conference_invitees)
+ m = method( :"#{@conference_invitee.conference.conferenceable_type.underscore}_conference_path")
+ redirect_to m.( @conference_invitee.conference.conferenceable, @conference_invitee.conference), :notice => t('conference_invitees.controller.successfuly_created', :resource => @conference_invitees)
+ else
+ render :new
+ end
+ end
+
+ def edit
+ authorize! :edit, @parent_in_route
+ end
+
+ def update
+ if @conference_invitee.update_attributes(params[:conference_invitee])
+ redirect_to @conference_invitee, :notice => t('conference_invitees.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @conference_invitee.destroy
+ redirect_to conference_invitees_url, :notice => t('conference_invitees.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def spread_breadcrumbs
+ if @conference
+ @parent = @conference.conferenceable
+ if @parent && @parent.class == User
+ @user = @parent
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_users_path(@user.current_tenant, @user)
+ add_breadcrumb t("conferences.index.page_title"), user_conferences_path(@user)
+ if @conference && !@conference.new_record?
+ add_breadcrumb @conference, user_conference_path(@user, @conference)
+ end
+ end
+ if @parent && @parent.class == Tenant
+ @tenant = @parent
+ add_breadcrumb t("conferences.index.page_title"), tenant_conferences_path(@tenant)
+ if @conference && !@conference.new_record?
+ add_breadcrumb @conference, tenant_conference_path(@tenant, @conference)
+ end
+ end
+
+ add_breadcrumb t("conference_invitees.index.page_title"), conference_conference_invitees_path(@conference)
+ if @conference_invitee && !@conference_invitee.new_record?
+ add_breadcrumb @conference_invitee, conference_conference_invitee_path(@conference, @conference_invitee)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/conferences_controller.rb b/app/controllers/conferences_controller.rb
new file mode 100644
index 0000000..302a23b
--- /dev/null
+++ b/app/controllers/conferences_controller.rb
@@ -0,0 +1,82 @@
+class ConferencesController < ApplicationController
+ load_resource :user
+ load_resource :tenant
+ load_and_authorize_resource :conference, :through => [:user, :tenant]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ @phone_numbers = @conference.phone_numbers
+ end
+
+ def new
+ @conference = @parent.conferences.build
+ @conference.name = generate_a_new_name(@parent, @conference)
+ @conference.start = nil
+ @conference.end = nil
+ @conference.open_for_anybody = true
+ @conference.max_members = DEFAULT_MAX_CONFERENCE_MEMBERS
+ @conference.pin = random_pin
+
+ @conference.open_for_anybody = true
+ @conference.announce_new_member_by_name = true
+ @conference.announce_left_member_by_name = true
+ end
+
+ def create
+ @conference = @parent.conferences.build(params[:conference])
+ if @conference.save
+ m = method( :"#{@parent.class.name.underscore}_conference_path" )
+ redirect_to m.( @parent, @conference ), :notice => t('conferences.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @conference.update_attributes(params[:conference])
+ m = method( :"#{@parent.class.name.underscore}_conference_path" )
+ redirect_to m.( @parent, @conference ), :notice => t('conferences.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @conference.destroy
+ m = method( :"#{@parent.class.name.underscore}_conferences_url" )
+ redirect_to m.( @parent ), :notice => t('conferences.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def set_and_authorize_parent
+ @parent = @tenant || @user
+ authorize! :read, @parent
+ end
+
+ def spread_breadcrumbs
+ if @parent && @parent.class == User
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t("conferences.index.page_title"), user_conferences_path(@user)
+ if @conference && !@conference.new_record?
+ add_breadcrumb @conference, user_conference_path(@user, @conference)
+ end
+ end
+ if @parent && @parent.class == Tenant
+ add_breadcrumb t("conferences.index.page_title"), tenant_conferences_path(@tenant)
+ if @conference && !@conference.new_record?
+ add_breadcrumb @conference, tenant_conference_path(@tenant, @conference)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/config_polycom_controller.rb b/app/controllers/config_polycom_controller.rb
new file mode 100644
index 0000000..9d44e51
--- /dev/null
+++ b/app/controllers/config_polycom_controller.rb
@@ -0,0 +1,330 @@
+class ConfigPolycomController < ApplicationController
+ MAX_SIP_ACCOUNTS_COUNT = 11
+ MAX_SOFTKEYS_COUNT = 12
+ MAX_DIRECTORY_ENTRIES = 20
+ SIP_DEFAULT_PORT = 5060
+
+ skip_authorization_check
+
+ before_filter { |controller|
+ if ! params[:mac_address].blank? then
+ @mac_address = params[:mac_address].upcase.gsub(/[^0-9A-F]/,'')
+ @phone = Phone.where({ :mac_address => @mac_address }).first
+ elsif ! params[:phone].blank? then
+ @phone = Phone.where({ :id => params[:phone].to_i }).first
+ end
+
+ if ! @phone
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Phone not found -->",
+ )
+ return false
+ end
+
+ if ! params[:sip_account].blank?
+ @sip_account = @phone.sip_accounts.where({ :id => params[:sip_account].to_i }).first
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return false
+ end
+ end
+
+ if ! params[:type].blank?
+ @type = params[:type].to_s.strip.downcase
+ end
+ }
+
+ def config_files
+ if params[:mac_address].blank? then
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- MAC not specified -->",
+ )
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render
+ }
+ }
+ end
+
+ def settings
+ if ! request.env['HTTP_USER_AGENT'].index('polycom')
+ Rails.logger.info "---> User-Agent indicates not a Polycom phone (#{request.env['HTTP_USER_AGENT'].inspect})"
+ else
+ Rails.logger.info "---> Phone #{@mac_address.inspect}, IP address #{request.remote_ip.inspect}"
+ @phone.update_attributes({ :ip_address => request.remote_ip })
+ end
+
+ xml_applications_url = "#{request.protocol}#{request.host_with_port}/config_polycom/#{@phone.id}/0"
+
+ @settings = {
+ 'device.sntp.serverName' => 'pool.ntp.org',
+ 'device.sntp.gmtOffset' => 3600,
+ 'up.welcomeSoundOnWarmBootEnabled' => 0,
+ 'up.welcomeSoundEnabled' => 0,
+ 'bg.hiRes.color.selection' => '2,1',
+ 'msg.mwi.1.callBackMode' => 'contact',
+ 'msg.mwi.1.callBack' => 'f-vmcheck',
+ 'feature.enhancedFeatureKeys.enabled' => 1,
+ 'softkey.feature.basicCallManagement.redundant' => 0,
+ 'softkey.feature.buddies' => 0,
+ 'softkey.feature.callers' => 0,
+ 'softkey.feature.directories' => 0,
+ 'softkey.feature.endcall' => 1,
+ 'softkey.feature.forward' => 0,
+ 'softkey.feature.mystatus' => 0,
+ 'softkey.feature.newcall' => 0,
+ 'call.directedCallPickupMethod' => 'legacy',
+ 'call.directedCallPickupString' => 'f-ia-',
+ 'call.advancedMissedCalls.enabled' => 0,
+ 'lineKey.reassignment.enabled' => 1,
+ 'lineKey.1.category' => 'Line',
+ 'lineKey.1.index' => 1,
+ }
+
+ for key_index in 2..42
+ @settings["lineKey.#{key_index}.category"] = 'Unassigned'
+ end
+
+ for ring_class in 1..17
+ @settings["se.rt.custom#{ring_class}.name"] = "Ringer#{ring_class-1}"
+ @settings["se.rt.custom#{ring_class}.ringer"] = "ringer#{ring_class}"
+ end
+ @settings["se.rt.custom1.type"] = 'visual'
+
+ for ring_class in 1..17
+ @settings["voIpProt.SIP.alertInfo.#{ring_class}.class"] = "custom#{ring_class}"
+ @settings["voIpProt.SIP.alertInfo.#{ring_class}.value"] = "Ringer#{ring_class-1}"
+ end
+
+ softkey_index = 1
+ blf_index = 0
+
+ @phone.sip_accounts.each do |sip_account|
+ sip_account_index = 0
+ if (sip_account.sip_accountable_type == @phone.phoneable_type) and (sip_account.sip_accountable_id == @phone.phoneable_id)
+ sip_account_index += 1
+ if sip_account_index == 1
+ xml_applications_url = "#{request.protocol}#{request.host_with_port}/config_polycom/#{@phone.id}/#{sip_account.id}"
+ @settings['voIpProt.SIP.outboundProxy.address'] = sip_account.host
+ @settings['voIpProt.SIP.outboundProxy.port'] = SIP_DEFAULT_PORT
+ end
+
+ @settings["reg.#{sip_account_index}.address"] = "#{sip_account.auth_name}@#{sip_account.host}"
+ @settings["reg.#{sip_account_index}.auth.password"] = sip_account.password
+ @settings["reg.#{sip_account_index}.auth.userId"] = sip_account.auth_name
+ @settings["reg.#{sip_account_index}.displayName"] = 'Call'
+ @settings["reg.#{sip_account_index}.label"] = sip_account.caller_name
+ @settings["voIpProt.server.#{sip_account_index}.address"] = sip_account.host
+ @settings["voIpProt.server.#{sip_account_index}.port"] = SIP_DEFAULT_PORT
+ @settings["call.missedCallTracking.#{sip_account_index}.enabled"] = 0
+
+ sip_account.softkeys.order(:position).each do |softkey|
+ softkey_index += 1
+ if softkey.softkey_function
+ softkey_function = softkey.softkey_function.name
+ end
+ case softkey_function
+ when 'blf'
+ blf_index += 1
+ @settings["lineKey.#{softkey_index}.category"] = 'BLF'
+ @settings["attendant.resourceList.#{blf_index}.address"] = "#{softkey.number}@#{sip_account.host}"
+ @settings["attendant.resourceList.#{blf_index}.label"] = softkey.label
+ end
+ end
+ end
+ end
+
+ @settings['mb.idleDisplay.home'] = "#{xml_applications_url}/idle_screen.xml"
+ @settings['mb.idleDisplay.refresh'] = 60
+
+ @settings['efk.efklist.1.mname'] = "directory"
+ @settings['efk.efklist.1.status'] = 1
+ @settings['efk.efklist.1.action.string'] = "#{xml_applications_url}/phone_book.xml"
+ @settings['efk.efklist.2.mname'] = "callhistory"
+ @settings['efk.efklist.2.status'] = 1
+ @settings['efk.efklist.2.action.string'] = "#{xml_applications_url}/call_history.xml"
+ @settings['efk.efklist.3.mname'] = "applications"
+ @settings['efk.efklist.3.status'] = 1
+ @settings['efk.efklist.3.action.string'] = "#{xml_applications_url}/applications.xml"
+
+ @settings['softkey.1.action'] = "#{xml_applications_url}/phone_book.xml"
+ @settings['softkey.1.enable'] = 1
+ @settings['softkey.1.insert'] = 1
+ @settings['softkey.1.label'] = 'Directory'
+ @settings['softkey.1.precede'] = 1
+ @settings['softkey.1.use.active'] = 1
+ @settings['softkey.1.use.alerting'] = 0
+ @settings['softkey.1.use.dialtone'] = 1
+ @settings['softkey.1.use.hold'] = 1
+ @settings['softkey.1.use.idle'] = 1
+ @settings['softkey.1.use.proceeding'] = 0
+ @settings['softkey.1.use.setup'] = 0
+ @settings['softkey.2.action'] = "#{xml_applications_url}/call_history.xml"
+ @settings['softkey.2.enable'] = 1
+ @settings['softkey.2.insert'] = 2
+ @settings['softkey.2.label'] = 'Call History'
+ @settings['softkey.2.precede'] = 1
+ @settings['softkey.2.use.active'] = 1
+ @settings['softkey.2.use.alerting'] = 0
+ @settings['softkey.2.use.dialtone'] = 1
+ @settings['softkey.2.use.hold'] = 1
+ @settings['softkey.2.use.idle'] = 1
+ @settings['softkey.2.use.proceeding'] = 0
+ @settings['softkey.2.use.setup'] = 0
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render
+ }
+ }
+ end
+
+
+ def settings_directory
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render
+ }
+ }
+ end
+
+
+ def call_history
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ if ['dialed', 'missed', 'received'].include? @type
+ @phone_xml_object = {
+ :name => "call_history",
+ :title => @type.titleize,
+ :entries => []
+ }
+
+ calls = @sip_account.call_histories.where(:entry_type => @type).order('start_stamp DESC').limit(MAX_DIRECTORY_ENTRIES)
+
+ calls.each do |call|
+ display_name = call.display_name
+ phone_number = call.display_number
+ phone_book_entry = call.phone_book_entry_by_number(phone_number)
+ if display_name.blank?
+ display_name = phone_book_entry.to_s
+ end
+
+ @phone_xml_object[:entries].push({
+ :selected => false,
+ :number => phone_number,
+ :date => call.start_stamp.strftime('%d.%m %H:%M'),
+ :text => display_name,
+ :url => "tel:#{phone_number}",
+ })
+ end
+ else
+ base_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.split("?")[0]}"
+ @phone_xml_object = {
+ :name => 'call_history_menu',
+ :title => 'Call History Lists',
+ :entries => [
+ {:text => 'Missed Calls', :url => "#{base_url}?&type=missed", :selected => false},
+ {:text => 'Received Calls', :url => "#{base_url}?&type=received", :selected => false},
+ {:text => 'Placed Calls', :url => "#{base_url}?&type=dialed", :selected => false},
+ ]
+ }
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}", :content_type => Mime::HTML
+ }
+ }
+
+ end
+
+
+ def phone_book
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ @phone_xml_object = {
+ :name => 'phone_book',
+ :title => "Phone Book".strip,
+ :entries => [],
+ :softkeys => [],
+ }
+
+ phone_books = Array.new()
+ phone_books = phone_books + @sip_account.sip_accountable.try(:phone_books).all
+ if @sip_account.sip_accountable.class == User
+ phone_books = phone_books + @sip_account.sip_accountable.try(:current_tenant).try(:phone_books).all
+ end
+
+ phone_book_ids = Array.new()
+ phone_books.each do |phone_book|
+ phone_book_ids << phone_book.id
+ end
+
+ PhoneBookEntry.where(:phone_book_id => phone_book_ids).order(:last_name).order(:first_name).limit(MAX_DIRECTORY_ENTRIES).each do |phone_book_entry|
+ phone_numbers_count = 0
+ phone_book_entry.phone_numbers.each do |phone_number|
+ phone_numbers_count += 1
+ if phone_numbers_count > 1
+ entry_name = ''
+ else
+ entry_name = phone_book_entry.to_s
+ end
+
+ @phone_xml_object[:entries] << { :text => entry_name, :type => phone_number.name, :number => phone_number.number, :url => "tel:#{phone_number.number}" }
+ end
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}", :content_type => Mime::HTML
+ }
+ }
+
+ end
+
+
+ def idle_screen
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "idle_screen", :content_type => Mime::HTML
+ }
+ }
+ end
+end
diff --git a/app/controllers/config_siemens_controller.rb b/app/controllers/config_siemens_controller.rb
new file mode 100644
index 0000000..f398b1a
--- /dev/null
+++ b/app/controllers/config_siemens_controller.rb
@@ -0,0 +1,1239 @@
+require 'nokogiri'
+#doc.search('Message/ItemList').each do |a| puts a.children end
+class ConfigSiemensController < ApplicationController
+#TODO Authentication
+ # No access for admins though as this contains personal data.
+
+ # We can't use load_and_authorize_resource() here because
+ # ConfigSiemensController isn't a resource.
+ # We can try client certificates
+ MAX_DIRECTORY_ENTRIES = 20
+
+ skip_authorization_check
+
+ before_filter { |controller|
+ if ! params[:phone].blank?
+ @phone = Phone.where({ :id => params[:phone].to_i }).first
+ end
+
+ if ! params[:sip_account].blank?
+ @sip_account = SipAccount.where({ :id => params[:sip_account].to_i }).first
+ end
+
+ if ! @sip_account && @phone
+ @sip_account = @phone.sip_accounts.where(:sip_accountable_id => @phone.phoneable_id, :sip_accountable_type => @phone.phoneable_type).first
+ end
+ }
+
+
+ def index
+ os40_keys=6
+ os60_keys=8
+ os80_keys=9
+ doc = Nokogiri::XML(request.body.read)
+ #logger.debug("#{params[:WorkpointMessage].to_xml}")
+ #logger.debug("#{params[:WorkpointMessage][:Message][:ItemList].to_xml}")
+ @phone_items=Hash.new
+ contact_reason = params[:WorkpointMessage][:Message][:ReasonForContact]
+ fragment = params[:WorkpointMessage][:Message][:fragment]
+
+ reply_status = doc.search('Message/ReasonForContact').first[:status]
+ reply_action = doc.search('Message/ReasonForContact').first[:action]
+
+ doc.search('Message/ItemList/Item').each do |post_item|
+ @phone_items[post_item[:name]]=post_item.children.to_s
+ end
+ if @phone_items['mac-addr']
+ mac_address = @phone_items['mac-addr']
+ end
+ phone_type = @phone_items['device-type']
+ if phone_type == "OpenStage 40"
+ max_keys = (os40_keys) * 2
+ elsif phone_type == "OpenStage 60"
+ max_keys = (os60_keys) * 2
+ elsif phone_type == "OpenStage 80"
+ max_keys = (os80_keys) * 2
+ else
+ max_keys = 0
+ end
+
+ blf_keys_max = max_keys / 2
+ shift_key_position = blf_keys_max
+
+ #logger.debug(request.body.read)
+ if mac_address
+ @phone = Phone.find_by_mac_address(mac_address.gsub(':','').upcase)
+
+ if ! @phone && PROVISIONING_AUTO_ADD_PHONE
+ tenant = Tenant.where(:id => PROVISIONING_AUTO_TENANT_ID).first
+ if ! tenant
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Tenant not found -->",
+ )
+ return
+ end
+
+ @phone = tenant.phones.build
+ @phone.mac_address = mac_address
+ @phone.hot_deskable = true
+ @phone.phone_model = PhoneModel.where('name LIKE ?', "#{phone_type}").first
+ if ! @phone.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{@phone.errors.messages.inspect} -->",
+ )
+ return
+ end
+
+ if ! PROVISIONING_AUTO_ADD_SIP_ACCOUNT
+ return
+ end
+
+ caller_name_index = 0
+ sip_account_last = tenant.sip_accounts.where('caller_name LIKE ?', "#{PROVISIONING_AUTO_SIP_ACCOUNT_CALLER_PREFIX}%").sort { |item1, item2|
+ item1.caller_name.gsub(/[^0-9]/, '').to_i <=> item2.caller_name.gsub(/[^0-9]/, '').to_i
+ }.last
+
+ if sip_account_last
+ caller_name_index = sip_account_last.caller_name.gsub(/[^0-9]/, '').to_i
+ end
+ caller_name_index = caller_name_index + 1
+
+ @sip_account = tenant.sip_accounts.build
+ @sip_account.caller_name = "#{PROVISIONING_AUTO_SIP_ACCOUNT_CALLER_PREFIX}#{caller_name_index}"
+ @sip_account.call_waiting = CALL_WAITING
+ @sip_account.clir = DEFAULT_CLIR_SETTING
+ @sip_account.clip = DEFAULT_CLIP_SETTING
+ @sip_account.voicemail_pin = random_pin
+ @sip_account.callforward_rules_act_per_sip_account = CALLFORWARD_RULES_ACT_PER_SIP_ACCOUNT_DEFAULT
+ @sip_account.hotdeskable = false
+ loop do
+ @sip_account.auth_name = SecureRandom.hex(DEFAULT_LENGTH_SIP_AUTH_NAME)
+ break unless SipAccount.exists?(:auth_name => @sip_account.auth_name)
+ end
+ @sip_account.password = SecureRandom.hex(DEFAULT_LENGTH_SIP_PASSWORD)
+
+ if ! @sip_account.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{@sip_account.errors.messages.inspect} -->",
+ )
+ return
+ end
+
+ phone_sip_account = PhoneSipAccount.new()
+ phone_sip_account.phone_id = @phone.id
+ phone_sip_account.sip_account_id = @sip_account.id
+
+ if ! phone_sip_account.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{phone_sip_account.errors.messages.inspect} -->",
+ )
+ return
+ end
+ end
+ end
+
+
+ country = 'US'
+ language = 'en'
+ if ! @phone.nil?
+ @phone.update_attributes(:ip_address => request.remote_ip)
+ @sip_account = @phone.sip_accounts.where(:sip_accountable_type => @phone.phoneable_type,
+ :sip_accountable_id => @phone.phoneable_id).first
+
+ if @phone.phoneable
+ if @phone.phoneable_type == 'Tenant'
+ tenant = @phone.phoneable
+ language = tenant.language.code
+ elsif @phone.phoneable_type == 'User'
+ language = @phone.phoneable.language.code
+ tenant = @phone.phoneable.current_tenant
+ end
+ end
+
+ if tenant && tenant.country
+ country_map = {
+ '61' => 'AU', # Australia
+ '43' => 'AT', # Austria
+ '86' => 'CN', # China
+ '45' => 'DK', # Denmark
+ '33' => 'FA', # France
+ '49' => 'DE', # Germany
+ '44' => 'GB', # Great Britain
+ '91' => 'IN', # India
+ '39' => 'IT', # Italy
+ '81' => 'JP', # Japan
+ '52' => 'MX', # Mexico
+ '31' => 'NL', # Netherlands
+ '47' => 'NO', # Norway
+ '64' => 'NZ', # New Zealand
+ '34' => 'ES', # Spain
+ '46' => 'SE', # Sweden
+ '41' => 'CH', # Switzerland
+ }
+ if country_map.include?(tenant.country.country_code)
+ country = country_map[tenant.country.country_code]
+ end
+ end
+ end
+
+ if ! @phone.nil? && ! @sip_account.blank?
+ #logger.debug(@phone_items)
+ @my_nonce = params[:WorkpointMessage][:Message][:nonce]
+ @new_settings = Array.new
+
+ @new_settings << ['dhcp', nil, 'true']
+ @new_settings << ['hostname', nil, mac_address.gsub(':', '') ]
+ #@new_settings << ['e164-hostname', nil, 'false']
+ @new_settings << ['mobility-enabled', nil, 'false']
+ @new_settings << ['mobility-password-on-logoff', nil, 'false']
+ @new_settings << ['e164', nil, @sip_account.auth_name]
+ @new_settings << ['sip-user-id', nil, @sip_account.auth_name]
+ #Not supported
+ #@new_settings << ['reg-id', nil, @sip_account.auth_name]
+ #@new_settings << ['reg-number', nil, @sip_account.auth_name]
+ #@new_settings << ['fully-qualified-phone-no', nil, @sip_account.auth_name]
+ @new_settings << ['sip-pwd', nil, @sip_account.password]
+ @new_settings << ['sip-name', nil, @sip_account.caller_name]
+ @new_settings << ['register-by-name', nil, 'false']
+ @new_settings << ['display-id-unicode', nil, @sip_account.caller_name]
+ @new_settings << ['use-display-id', nil, 'true']
+ @new_settings << ['reg-addr', nil, @sip_account.sip_domain.host]
+ @new_settings << ['reg-port', nil, '5060']
+ @new_settings << ['registrar-addr', nil, @sip_account.sip_domain.host]
+ @new_settings << ['registrar-port', nil, '5060']
+ #@new_settings << ['outbound-proxy', nil, @sip_account.sip_domain.host]
+ @new_settings << ['outbound-proxy-user', nil, @sip_account.auth_name]
+ #@new_settings << ['sgnl-gateway-addr', nil, @sip_account.sip_domain.host]
+ #@new_settings << ['sgnl-gateway-port', nil, '5060' ]
+ @new_settings << ['sgnl-gateway-addr-user', nil, @sip_account.sip_domain.host]
+ @new_settings << ['sgnl-gateway-port-user', nil, '5060']
+ @new_settings << ['sgnl-route', nil, '0' ]
+ @new_settings << ['mwi-e164', nil, '' ]
+ @new_settings << ['rtp-base-port', nil, '5004']
+ @new_settings << ['default-domain', nil, '' ]
+ #@new_settings << ['sip-transport', nil, '0' ]
+ @new_settings << ['sip-transport-user', nil, '0' ]
+ @new_settings << ['server-type', nil, '0' ]
+ @new_settings << ['session-timer', nil, 'false' ]
+ @new_settings << ['session-duration', nil, '3600' ]
+ @new_settings << ['reg-ttl', nil, '3600' ]
+ @new_settings << ['realm', nil, @sip_account.sip_domain.realm]
+ @new_settings << ['emergency-e164', nil, '0110' ]
+ @new_settings << ['voice-mail-e164', nil, 'f-vmcheck']
+ @new_settings << ['auto-answer', nil, 'false']
+ @new_settings << ['beep-on-auto-answer', nil, 'true']
+ @new_settings << ['auto-reconnect', nil, 'false' ]
+ @new_settings << ['beep-on-auto-reconnect', nil, 'true']
+ #@new_settings << ['permit-decline-call', nil, 'true']
+ @new_settings << ['transfer-on-ring', nil, 'false' ]
+ @new_settings << ['join-allowed-in-conference', nil, 'true']
+ @new_settings << ['pickup-group-uri', nil, "f-ig-#{@sip_account.id}"]
+ @new_settings << ['pickup-group-uri', nil, '' ]
+ @new_settings << ['hot-line-warm-line-digits', nil, '' ]
+ @new_settings << ['initial-digit-timer', nil, '30' ]
+ @new_settings << ['conference-factory-uri', nil, '']
+ @new_settings << ['callback-busy-allow', nil, 'false']
+ @new_settings << ['callback-busy-code', nil, '' ]
+ @new_settings << ['callback-ring-allow', nil, 'false']
+ @new_settings << ['callback-ring-code', nil, '']
+ @new_settings << ['callback-cancel-code', nil, '']
+ @new_settings << ['park-server', nil, '']
+ #OPTIMIZE Callwaiting
+ @new_settings << ['call-waiting-enabled', nil, 'true']
+ @new_settings << ['qos-layer2', nil, 'true']
+ @new_settings << ['l2qos-voice', nil, '5' ]
+ @new_settings << ['l2qos-signalling', nil, '3' ]
+ @new_settings << ['l2qos-default', nil, '0']
+ @new_settings << ['qos-layer3', nil, 'true']
+ @new_settings << ['l3qos-voice', nil, '46']
+ @new_settings << ['l3qos-signalling', nil, '26']
+ @new_settings << ['vlan-method', nil, '1']
+ #OPTIMIZE Timezone settings
+ @new_settings << ['time', nil, Time.new.localtime.to_i]
+ @new_settings << ['sntp-addr', nil, 'NULL']
+ @new_settings << ['sntp-tz-offset', nil, (Time.new.utc_offset/60).to_i]
+ @new_settings << ['daylight-save', nil, 'true']
+ @new_settings << ['daylight-save-minutes', nil, '0']
+ @new_settings << ['auto-daylight-save', nil, 'true']
+ @new_settings << ['daylight-save-zone-id', nil, '9']
+ #OPTIMIZE Use SNMP?
+ @new_settings << ['snmp-trap-addr', nil, 'NULL']
+ @new_settings << ['snmp-trap-port', nil, '162']
+ @new_settings << ['snmp-trap-pwd', nil, 'snmp' ]
+ @new_settings << ['snmp-traps-active', nil, 'false' ]
+ @new_settings << ['diagnostic-trap-addr', nil, 'NULL']
+ @new_settings << ['diagnostic-trap-port', nil, '162']
+ @new_settings << ['diagnostic-trap-pwd', nil, 'snmp' ]
+ @new_settings << ['diagnostic-traps-active', nil, 'false' ]
+ @new_settings << ['diagnostic-snmp-active', nil, 'false']
+ @new_settings << ['qdc-collection-unit-addr', nil, 'NULL']
+ @new_settings << ['qdc-collection-unit-port', nil, '12010']
+
+ @new_settings << ['qdc-trap-pwd', nil, 'QOSDC']
+ @new_settings << ['qdc-snmp-active', nil, 'false']
+ @new_settings << ['qdc-qcu-active', nil, 'false']
+ @new_settings << ['snmp-queries-allowed', nil, 'false']
+ #@new_settings << ['snmp-pwd', nil, '']
+ @new_settings << ['disable-microphone', nil, 'false']
+ @new_settings << ['loudspeech-enabled', nil, 'true']
+ @new_settings << ['audio-silence-suppression', nil, 'false']
+
+ @new_settings << ['port1', nil, '0' ] # 0=Automatic (speed)
+ @new_settings << ['port2', nil, '0' ]
+ @new_settings << ['port2-mode', nil, '1' ]
+ @new_settings << ['port2-auto-mdix-enabled', nil, 'true' ]
+ @new_settings << ['originating-line-preference', nil, '0']
+ @new_settings << ['terminating-line-preference', nil, '0']
+ @new_settings << ['line-key-operating-mode', nil, '0']
+ @new_settings << ['line-rollover-type', nil, '2']
+ @new_settings << ['line-rollover-volume', nil, '5' ]# 1-5
+ @new_settings << ['line-registration-leds', nil, 'true']
+ @new_settings << ['keyset-use-focus', nil, 'true' ]
+ @new_settings << ['keyset-remote-forward-ind', nil, 'true']
+ @new_settings << ['keyset-reservation-timer', nil, '60' ] # 0-300
+ @new_settings << ['dial-plan-enabled', nil, 'false' ]
+ @new_settings << ['Canonical-dialing-international-prefix', nil, '']
+ @new_settings << ['Canonical-dialing-local-country-code', nil, '']
+ @new_settings << ['Canonical-dialing-national-prefix', nil, '']
+ @new_settings << ['Canonical-dialing-local-area-code', nil, '']
+ @new_settings << ['Canonical-dialing-local-node', nil, '']
+ @new_settings << ['Canonical-dialing-external-access', nil, '0']
+ @new_settings << ['Canonical-dialing-operator-code', nil, '']
+ @new_settings << ['Canonical-dialing-emergency-number', nil, '']
+ @new_settings << ['Canonical-dialing-dial-needs-access-code', nil, '0']
+ @new_settings << ['Canonical-dialing-dial-needs-intGWcode', nil, '1']
+ @new_settings << ['Canonical-dialing-min-local-number-length', nil, '10']
+ @new_settings << ['Canonical-dialing-extension-initial-digits', nil, '']
+ @new_settings << ['Canonical-dialing-dial-internal-form', nil, '0' ]
+ @new_settings << ['Canonical-dialing-dial-external-form', nil, '0' ]
+ #@new_settings << ['Canonical-lookup-local-code', nil, '' ]
+ #@new_settings << ['Canonical-lookup-international-code', nil, '']
+ @new_settings << ['hot-keypad-dialing', nil, 'false']
+ @new_settings << ['ldap-transport', nil, '0']
+ @new_settings << ['ldap-server-address', nil, 'NULL' ]
+ @new_settings << ['ldap-server-port', nil, '389' ]
+ @new_settings << ['ldap-authentication', nil, '1']
+ @new_settings << ['ldap-user', nil, 'NULL' ]
+ @new_settings << ['ldap-pwd', nil, 'NULL' ]
+ @new_settings << ['ldap-max-responses', nil, '25']
+ @new_settings << ['backup-addr', nil, 'NULL']
+ @new_settings << ['backup-registration', nil, 'false']
+ @new_settings << ['qdc-qcu-active', nil, 'false' ]
+ @new_settings << ['min-admin-passw-length', nil, '6' ]
+ #@new_settings << ['default-locked-config-menus', nil, 'true' ]
+ @new_settings << ['locked-config-menus', nil, 'true' ]
+ #@new_settings << ['default-locked-local-function-menus', nil, 'true' ]
+ @new_settings << ['locked-local-function-menus', nil, 'true' ]
+ #@new_settings << ['dls-mode-secure', nil, '0' ]
+ @new_settings << ['dls-chunk-size', nil, '9492']
+ #@new_settings << ['default-passw-policy', nil, 'false']
+ @new_settings << ['deflect-destination', nil, '']
+ @new_settings << ['display-skin', nil, (@phone.phoneable_type == 'User' ? '0' : '1')]
+ @new_settings << ['enable-bluetooth-interface', nil, 'true']
+ @new_settings << ['usb-access-enabled', nil, 'false' ]
+ @new_settings << ['usb-backup-enabled', nil, 'false' ]
+ @new_settings << ['line-button-mode', nil, '0' ]
+ @new_settings << ['lock-forwarding', nil, '' ]
+ @new_settings << ['loudspeaker-function-mode', nil, '0' ]
+ @new_settings << ['max-pin-retries', nil, '10' ]
+ @new_settings << ['screensaver-enabled', nil, 'false' ]
+ @new_settings << ['inactivity-timeout', nil, '60' ]
+ @new_settings << ['not-used-timeout', nil, '5' ]
+ @new_settings << ['passw-char-set', nil, '0' ]
+ @new_settings << ['refuse-call', nil, 'true' ]
+ @new_settings << ['restart-password', nil, '124816']
+ #OPTIMIZE clock format
+ @new_settings << ['time-format', nil, '0' ]# 1=12 h
+ @new_settings << ['uaCSTA-enabled', nil, 'false' ]
+ @new_settings << ['enable-test-interface', nil, 'false']
+ @new_settings << ['enable-WBM', nil, 'true']
+ #@new_settings << ['pixelsaver-timeout', nil, '2' ]# 2 hours?
+ #@new_settings << ['voice-message-dial-tone', nil, '' ]
+ #@new_settings << ['call-pickup-allowed', nil, 'true' ]
+ @new_settings << ['group-pickup-tone-allowed', nil, 'true']
+ @new_settings << ['group-pickup-as-ringer', nil, 'false']
+ @new_settings << ['group-pickup-alert-type', nil, '0' ]
+ #@new_settings << ['default-profile', nil, '' ]
+ @new_settings << ['count-medium-priority', nil, '5']
+ @new_settings << ['timer-medium-priority', nil, '60'] # 1 - 999
+ @new_settings << ['timer-high-priority', nil, '5'] # 0 - 999
+ @new_settings << ['dss-sip-detect-timer', nil, '10']
+ @new_settings << ['dss-sip-deflect', nil, 'false' ]
+ @new_settings << ['dss-sip-refuse', nil, 'false' ]
+ @new_settings << ['feature-availability', nil, 'false']
+ @new_settings << ['feature-availability', nil, 'true' ]
+ @new_settings << ['feature-availability', nil, 'true' ]
+ @new_settings << ['local-control-feature-availability', nil, 'false' ]
+ @new_settings << ['trace-level', nil, '0' ] # Off
+ #@new_settings << ['default-locked-function-keys', nil, 'true' ]# "unknown item"
+ @new_settings << ['blf-code', nil, 'f-ia-'] # pickup prefix for softkey function 59 (BLF)
+ @new_settings << ['stimulus-feature-code', nil, true]
+ @new_settings << ['stimulus-led-control-uri', nil, true]
+
+ @new_settings << ['min-user-passw-length', nil, '6' ]# 6 - 24
+ #OPTIMIZE language
+ @new_settings << ['country-iso', nil, country ]
+ @new_settings << ['language-iso', nil, language]
+ @new_settings << ['date-format', nil, '0' ] # DD.MM.YYYY
+ #OPTIMIZE ringtones
+ @new_settings << ['ringer-melody', nil, '1']
+
+ @new_settings << ['ringer-melody', nil, '2']
+ @new_settings << ['ringer-tone-sequence', nil, '2']
+
+ 1.upto(8) do |index|
+ @new_settings << ['alert', index, "Ringer#{index}^#{index}^2^60"]
+ end
+ @new_settings << ['alert', 9, "Ringer9^1^1^60"]
+ @new_settings << ['alert', 10, "Ringer10^1^3^60"]
+ @new_settings << ['alert', 11, "Ringer0^0^2^60"]
+
+ #Applications
+ @new_settings << ['XML-app-name', 1, 'call_history']
+ @new_settings << ['XML-app-control-key', 1, '3']
+ @new_settings << ['XML-app-action', 1, 'update']
+ @new_settings << ['XML-app-display-name', 1, 'Call History']
+ @new_settings << ['XML-app-program-name', 1, "config_siemens/#{@phone.id}/call_history.xml"]
+ @new_settings << ['XML-app-special-instance', 1, '3']
+ @new_settings << ['XML-app-server-addr', 1, request.host]
+ @new_settings << ['XML-app-server-port', 1, '80']
+ @new_settings << ['XML-app-transport', 1, '0']
+ @new_settings << ['XML-app-proxy-enabled', 1, 'false']
+ @new_settings << ['XML-app-remote-debug', 1, 'false']
+ @new_settings << ['XML-app-debug-prog-name', 1, '']
+ @new_settings << ['XML-app-num-tabs', 1, '3']
+ @new_settings << ['XML-app-restart', 1, 'true']
+ @new_settings << ['XML-app-auto-start', 1, 'true']
+ @new_settings << ['XML-app-tab1-display-name', 1, 'Missed']
+ @new_settings << ['XML-app-tab1-name', 1, 'call_history']
+ @new_settings << ['XML-app-tab2-display-name', 1, 'Received']
+ @new_settings << ['XML-app-tab2-name', 1, 'call_history_received']
+ @new_settings << ['XML-app-tab3-display-name', 1, 'Dialed']
+ @new_settings << ['XML-app-tab3-name', 1, 'call_history_dialed']
+
+ @new_settings << ['XML-app-name', 2, 'menu']
+ @new_settings << ['XML-app-control-key', 2, '6']
+ @new_settings << ['XML-app-action', 2, 'update']
+ @new_settings << ['XML-app-display-name', 2, 'Menu']
+ @new_settings << ['XML-app-program-name', 2, "config_siemens/#{@phone.id}/menu.xml"]
+ @new_settings << ['XML-app-special-instance', 2, '0']
+ @new_settings << ['XML-app-server-addr', 2, request.host]
+ @new_settings << ['XML-app-server-port', 2, '80']
+ @new_settings << ['XML-app-transport', 2, '0']
+ @new_settings << ['XML-app-proxy-enabled', 2, 'false']
+ @new_settings << ['XML-app-remote-debug', 2, 'false']
+ @new_settings << ['XML-app-debug-prog-name', 2, '']
+ @new_settings << ['XML-app-num-tabs', 2, '3']
+ @new_settings << ['XML-app-restart', 2, 'true']
+ @new_settings << ['XML-app-tab1-display-name', 2, "Gemeinschaft #{GEMEINSCHAFT_VERSION}"]
+ @new_settings << ['XML-app-tab1-name', 2, 'menu']
+ @new_settings << ['XML-app-tab2-display-name', 2, 'Status']
+ @new_settings << ['XML-app-tab2-name', 2, 'menu_status']
+ @new_settings << ['XML-app-tab3-display-name', 2, 'Help']
+ @new_settings << ['XML-app-tab3-name', 2, 'menu_help']
+
+
+ @new_settings << ['clear-calllog', nil, 'true']
+ @new_settings << ['server-based-features', nil, 'true']
+
+
+ if ! @sip_account.call_forwards.blank?
+ call_forwarding_object = @sip_account.call_forwards.where(:call_forward_case_id => CallForwardCase.where(:value => 'always').first).first
+ if call_forwarding_object
+ @new_settings << ['key-functionality', 4002, '1']
+ @new_settings << ['function-key-def', 4002, '63']
+ @new_settings << ['stimulus-led-control-uri', 4002, "f-cftg-#{call_forwarding_object.id}" ]
+ @new_settings << ['send-url-address', 4002, request.host]
+ @new_settings << ['send-url-protocol', 4002, 3] # 0=https, 3=http
+ @new_settings << ['send-url-port', 4002, '80']
+ @new_settings << ['send-url-path', 4002, "/config_siemens/#{@phone.id}/#{@sip_account.id}/call_forwarding.xml"]
+ @new_settings << ['send-url-query', 4002, "id=#{call_forwarding_object.id}&function=toggle"]
+ @new_settings << ['send-url-method', 4002, '0'] # 0=get, 1=post
+ else
+ @new_settings << ['key-functionality', 4002, '0']
+ end
+ else
+ @new_settings << ['key-functionality', 4002, '0']
+ end
+
+ @new_settings << ['function-key-def', 4003, '10'] # Hold
+
+ @new_settings << ['feature-availability', 2, 'false' ] # call forwarding
+ @new_settings << ['feature-availability', 11, 'false' ] # DND
+ @new_settings << ['feature-availability', 30, 'false'] # DSS
+ @new_settings << ['feature-availability', 31, 'false'] # feature toggle
+ @new_settings << ['feature-availability', 33, 'true'] # line overview
+ @new_settings << ['feature-availability', 33, 'false'] # phone lock
+
+
+ @soft_keys = Array.new
+ # Fill softkeys with keys dependent on limit of phone
+ @sip_account.softkeys.order(:position).each do |sk|
+ @soft_keys << sk
+ end
+ # Delete unset softkeys
+ # OPTIMIZE 40 should be enough for 2 modules, but for some reason array is empty o early
+ max_keys = max_keys + 50
+ while @soft_keys.length <= max_keys
+ @soft_keys << Softkey.new
+ end
+
+ @key_pos=1
+
+ #@soft_keys.each do |sk|
+
+ while @key_pos < shift_key_position
+
+ (1..shift_key_position-1).each do |idx|
+ first_level_keys(idx)
+ end
+ end
+ if @key_pos == shift_key_position
+ @new_settings << ['function-key-def', shift_key_position, '18']
+ @new_settings << ['key-label', shift_key_position, 'Shift']
+ @new_settings << ['key-label-unicode', shift_key_position, 'Shift']
+ @key_pos = @key_pos+1
+ end
+
+ (1001..1000+shift_key_position-1).each do |idx|
+ second_level_keys(idx)
+ end
+ # First key-module first level
+ (301..311).each do |idx|
+ first_level_keys(idx)
+ end
+ # First key-module shift level
+ (1301..1311).each do |idx|
+ second_level_keys(idx)
+ end
+ # Second key-module first level
+ (401..411).each do |idx|
+ first_level_keys(idx)
+ end
+ # Second key-module shift level
+ (1401..1411).each do |idx|
+ second_level_keys(idx)
+ end
+ [312, 412].each do |idx|
+ @new_settings << ['function-key-def', idx, '18']
+ @new_settings << ['key-label', idx, 'Shift']
+ @new_settings << ['key-label-unicode', idx, 'Shift']
+ end
+ #end
+ logger.debug(@new_settings)
+ end
+
+ if (@phone.nil? || @sip_account.blank?) && fragment != "final"
+ @new_settings = Array.new
+ @my_nonce = params[:WorkpointMessage][:Message][:nonce]
+ @new_settings << ['e164', nil, 'NULL']
+ @new_settings << ['sip-user-id', nil, ""]
+ @new_settings << ['sip-pwd', nil, ""]
+ @new_settings << ['sip-name', nil, ""]
+ @new_settings << ['display-id-unicode', nil, ""]
+ @new_settings << ['reg-addr', nil, ""]
+ @new_settings << ['registrar-addr', nil, "NULL"]
+ @new_settings << ['outbound-proxy-user', nil, ""]
+ @new_settings << ['sgnl-gateway-addr-user', nil, ""]
+ @new_settings << ['realm', nil, ""]
+ @new_settings << ['pickup-group-uri', nil, ""]
+ logger.debug(@new_settings)
+
+ respond_to { |format|
+ format.xml { render :action => "write" }
+ }
+ elsif contact_reason == 'local-changes'
+ respond_to { |format|
+ format.xml { render :action => "clean-up" }
+ }
+ elsif (reply_status == 'accepted' && contact_reason == 'reply-to' && reply_action == 'ReadAllItems')
+ respond_to { |format|
+ format.xml { render :action => "write" }
+ }
+
+ elsif ["reply-to"].include? contact_reason
+ respond_to { |format|
+ format.xml { render :action => "clean-up" }
+ }
+
+ else
+ respond_to { |format|
+ format.xml { render :action => "index" }
+ }
+ end
+
+ end
+
+ def first_level_keys(key_idx)
+ sk = @soft_keys.shift
+ if sk.softkey_function
+ softkey_function = sk.softkey_function.name
+ end
+ case softkey_function
+ when 'blf'
+ @new_settings << ['function-key-def', key_idx, '59']
+ @new_settings << ['stimulus-led-control-uri', key_idx, sk.number ]
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, sk.number ]
+ @new_settings << ['blf-popup', key_idx, 'true']
+ when 'log_out'
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, 'f-lo' ]
+ @new_settings << ['stimulus-led-control-uri', key_idx, '' ]
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, '' ]
+ when 'log_in'
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, "f-li-#{sk.number}" ]
+ @new_settings << ['stimulus-led-control-uri', key_idx, '' ]
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, '' ]
+ when 'hold'
+ @new_settings << ['function-key-def', key_idx, '10']
+ @new_settings << ['select-dial', key_idx, '' ]
+ @new_settings << ['stimulus-led-control-uri', key_idx, '' ]
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, '' ]
+ when 'dtmf'
+ @new_settings << ['function-key-def', key_idx, '54']
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, sk.number ]
+ @new_settings << ['stimulus-led-control-uri', key_idx, '' ]
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, '' ]
+ when 'call_forwarding'
+ @new_settings << ['function-key-def', key_idx, '63']
+ @new_settings << ['stimulus-led-control-uri', key_idx, "f-cftg-#{sk.call_forward_id}" ]
+ @new_settings << ['send-url-address', key_idx, request.host]
+ @new_settings << ['send-url-protocol', key_idx, 3]
+ @new_settings << ['send-url-port', key_idx, '80']
+ @new_settings << ['send-url-path', key_idx, "/config_siemens/#{@phone.id}/#{@sip_account.id}/call_forwarding.xml"]
+ @new_settings << ['send-url-query', key_idx, "id=#{sk.call_forward_id}&function=toggle"]
+ @new_settings << ['send-url-method', key_idx, '0']
+ @new_settings << ['blf-popup', key_idx, 'false']
+ when 'call_forwarding_always'
+ phone_number = PhoneNumber.where(:number => sk.number, :phone_numberable_type => 'SipAccount').first
+ if phone_number
+ account_param = (phone_number.phone_numberable_id != @sip_account.id ? "&account=#{phone_number.phone_numberable_id}" : '')
+ else
+ phone_number = @sip_account.phone_numbers.first
+ account_param = ''
+ end
+
+ if phone_number
+ @new_settings << ['function-key-def', key_idx, '63']
+ @new_settings << ['stimulus-led-control-uri', key_idx, "f-cfutg-#{phone_number.id}" ]
+ @new_settings << ['send-url-address', key_idx, request.host]
+ @new_settings << ['send-url-protocol', key_idx, 3] # 0=https, 3=http
+ @new_settings << ['send-url-port', key_idx, '80']
+ @new_settings << ['send-url-path', key_idx, "/config_siemens/#{@phone.id}/#{@sip_account.id}/call_forwarding.xml"]
+ @new_settings << ['send-url-query', key_idx, "type=always&function=toggle#{account_param}"]
+ @new_settings << ['send-url-method', key_idx, '0'] # 0=get, 1=post
+ # @new_settings << ['send-url-user-id', key_idx, 'user']
+ # @new_settings << ['send-url-passwd', key_idx, 'secret']
+ @new_settings << ['blf-popup', key_idx, 'false']
+ end
+ when 'call_forwarding_assistant'
+ phone_number = PhoneNumber.where(:number => sk.number, :phone_numberable_type => 'SipAccount').first
+ if phone_number
+ account_param = (phone_number.phone_numberable_id != @sip_account.id ? "&account=#{phone_number.phone_numberable_id}" : '')
+ else
+ phone_number = @sip_account.phone_numbers.first
+ account_param = ''
+ end
+
+ if phone_number
+ @new_settings << ['function-key-def', key_idx, '63']
+ @new_settings << ['stimulus-led-control-uri', key_idx, "f-cfatg-#{phone_number.id}" ]
+ @new_settings << ['send-url-address', key_idx, request.host]
+ @new_settings << ['send-url-protocol', key_idx, 3] # 0=https, 3=http
+ @new_settings << ['send-url-port', key_idx, '80']
+ @new_settings << ['send-url-path', key_idx, "/config_siemens/#{@phone.id}/#{@sip_account.id}/call_forwarding.xml"]
+ @new_settings << ['send-url-query', key_idx, "type=assistant&function=toggle#{account_param}"]
+ @new_settings << ['send-url-method', key_idx, '0'] # 0=get, 1=post
+ @new_settings << ['blf-popup', key_idx, 'false']
+ end
+ when 'hunt_group_membership'
+ phone_number = PhoneNumber.where(:number => sk.number, :phone_numberable_type => 'HuntGroup').first
+ if phone_number
+ hunt_group = HuntGroup.where(:id => phone_number.phone_numberable_id).first
+ end
+
+ sip_account_phone_numbers = Array.new()
+ @sip_account.phone_numbers.each do |pn|
+ sip_account_phone_numbers.push(pn.number)
+ end
+
+ hunt_group_member_numbers = PhoneNumber.where(:number => sip_account_phone_numbers, :phone_numberable_type => 'HuntGroupMember')
+
+ hunt_group_member = nil
+ if hunt_group and hunt_group_member_numbers
+ hunt_group_member_numbers.each do |hunt_group_member_number|
+ hunt_group_member = hunt_group.hunt_group_members.where(:id => hunt_group_member_number.phone_numberable_id).first
+ if hunt_group_member
+ break
+ end
+ end
+ end
+
+ if hunt_group_member
+ @new_settings << ['function-key-def', key_idx, '63']
+ @new_settings << ['stimulus-led-control-uri', key_idx, "f-hgmtg-#{hunt_group_member.id}" ]
+ @new_settings << ['send-url-address', key_idx, request.host]
+ @new_settings << ['send-url-protocol', key_idx, 3] # 0=https, 3=http
+ @new_settings << ['send-url-port', key_idx, '80']
+ @new_settings << ['send-url-path', key_idx, "/config_siemens/#{@phone.id}/#{@sip_account.id}/hunt_group.xml"]
+ @new_settings << ['send-url-query', key_idx, "group=#{hunt_group.id}&account=#{hunt_group_member.id}&function=toggle"]
+ @new_settings << ['send-url-method', key_idx, '0'] # 0=get, 1=post
+ @new_settings << ['blf-popup', key_idx, 'false']
+ end
+ when nil
+ @new_settings << ['function-key-def', key_idx, '0']
+ @new_settings << ['stimulus-led-control-uri', key_idx, '' ]
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, '' ]
+ else
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, sk.number ]
+ @new_settings << ['stimulus-led-control-uri', key_idx, '' ]
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, '' ]
+ end
+ @new_settings << ['key-label', key_idx, sk.label ]
+ @new_settings << ['key-label-unicode', key_idx, sk.label ]
+ @key_pos = @key_pos+1
+ end
+
+ def second_level_keys(key_idx)
+ sk = @soft_keys.shift
+ softkey_function = nil
+ if sk.softkey_function
+ softkey_function = sk.softkey_function.name
+ end
+ case softkey_function
+ when 'log_out'
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, 'f-lo' ]
+ when 'log_in'
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, "f-li-#{sk.number}" ]
+ when 'dtmf'
+ @new_settings << ['function-key-def', key_idx, '54']
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, sk.number ]
+ when nil
+ @new_settings << ['function-key-def', key_idx, '0']
+ else
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, sk.number ]
+ end
+ @new_settings << ['key-label', key_idx, sk.label ]
+ @new_settings << ['key-label-unicode', key_idx, sk.label ]
+ @key_pos = @key_pos+1
+ end
+
+ def call_history
+ if ! params[:number].blank?
+ number = params[:number]
+ end
+
+ if ! params[:function].blank?
+ function = params[:function].to_s.downcase
+ end
+
+ if ! params[:sip_account].blank?
+ @sip_account = SipAccount.where({ :id => params[:sip_account].to_i }).first
+ end
+
+ if ! @sip_account and ! params[:phonenumber].blank?
+ @sip_account = SipAccount.where(:auth_name => params[:phonenumber]).first
+ end
+
+ if ! params[:type].blank?
+ @type = params[:type]
+ elsif ! params[:tab].blank?
+ @type = params[:tab].rpartition("_")[2]
+ end
+
+ if ! ['dialed', 'missed', 'received'].include? @type
+ @type = 'missed'
+ end
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ base_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.split("?")[0]}"
+
+ @phone_xml_object = {
+ :name => "menu_list",
+ :columns => 1,
+ :url => base_url,
+ :make_call => (function.to_s == 'dial' ? number.to_s : nil),
+ :hidden => {:sip_account => @sip_account.id, :type => @type},
+ :commands => [{
+ :type => 'SELECT',
+ :label => 'Dial',
+ :display_on => 'LISTITEM',
+ :key => 'function',
+ :value => 'dial',
+ }],
+ :entries => [],
+ }
+
+ if function.to_s == 'clear_notification'
+ @sip_account.call_histories.update_all({:read_flag => true})
+ end
+
+ last_missed_call = @sip_account.call_histories.where(:entry_type => 'missed').order('start_stamp DESC').first
+ if last_missed_call and !last_missed_call.read_flag
+ @phone_xml_object[:led] = true
+ else
+ @phone_xml_object[:led] = false
+ end
+
+ calls = @sip_account.call_histories.where(:entry_type => @type).order('start_stamp DESC').limit(MAX_DIRECTORY_ENTRIES)
+
+ if @type == 'missed' && @phone_xml_object[:led] == true
+ @phone_xml_object[:commands].push({
+ :type => 'SELECT',
+ :label => 'Clear Notification',
+ :key => 'function',
+ :value => 'clear_notification',
+ })
+ end
+
+ auto_reload_time = 60
+
+ SIEMENS_HISTORY_RELOAD_TIMES.each_pair do |time_range, reload_value|
+ if time_range === Time.now.localtime.hour
+ auto_reload_time = reload_value
+ end
+ end
+
+ @phone_xml_object[:commands].push({
+ :type => 'UPDATE',
+ :auto => auto_reload_time,
+ :label => 'Update',
+ })
+
+ calls.each do |call|
+ display_name = call.display_name
+ phone_number = call.display_number
+ phone_book_entry = call.phone_book_entry_by_number(phone_number)
+ if display_name.blank?
+ display_name = phone_book_entry.to_s
+ end
+
+ @phone_xml_object[:entries].push({
+ :selected => false,
+ :key => 'number',
+ :value => phone_number,
+ :text => "#{call_date_compact(call.start_stamp)} #{display_name} #{phone_number}",
+ })
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+ end
+
+ def call_forwarding
+ if ! params[:type].blank?
+ @type = params[:type]
+ end
+
+ if ! params[:function].blank?
+ @function = params[:function]
+ end
+
+ if ! params[:id].blank?
+ @call_forwarding_id = params[:id].to_i
+ end
+
+ if ! params[:sip_account].blank?
+ @sip_account = SipAccount.where({ :id => params[:sip_account].to_i }).first
+ end
+
+ if ! params[:account].blank?
+ @sip_account = SipAccount.where({ :id => params[:account].to_i }).first
+ end
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ if @function == 'toggle'
+ if @call_forwarding_id
+ call_forwarding = @sip_account.call_forwards.where(:id => @call_forwarding_id).first
+
+ if !call_forwarding and @sip_account.softkeys.where(:call_forward_id => @call_forwarding_id).count > 0
+ call_forwarding = CallForward.where(:id => @call_forwarding_id).first
+ end
+
+ if call_forwarding
+ call_forwarding.toggle
+ end
+ elsif @type
+ call_forwarding = @sip_account.call_forwarding_toggle(@type)
+ end
+ if !call_forwarding
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Call forwarding not set: #{@sip_account.errors.messages.inspect} -->",
+ )
+ return
+ end
+
+ if !call_forwarding.errors.blank?
+ error_messages = Array.new()
+ call_forwarding.errors.messages.each_pair do |key, message|
+ error_messages.push(message.join(';'))
+ end
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- ERROR #{error_messages.join(',')} #{call_forwarding.to_s}) -->",
+ )
+ elsif call_forwarding.active
+ render(
+ :status => 200,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- ON #{call_forwarding.to_s} -->",
+ )
+ else
+ render(
+ :status => 200,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- OFF #{call_forwarding.to_s} -->",
+ )
+ end
+ return
+ end
+
+ base_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.split("?")[0]}"
+
+ @phone_xml_object = {
+ :name => "number_list",
+ :columns => 1,
+ :url => base_url,
+ :hidden => {:sip_account => @sip_account.id, :type => @type},
+ :entries => []
+ }
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render
+ }
+ }
+ end
+
+
+ def hunt_group
+ if ! params[:goto].blank?
+ redirect_to params[:goto]
+ return;
+ end
+
+ if ! params[:function].blank?
+ @function = params[:function]
+ end
+
+ if ! params[:group].blank?
+ @hunt_group = HuntGroup.where({ :id => params[:group].to_i }).first
+ end
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ if ! params[:account].blank?
+ hunt_group_member = @hunt_group.hunt_group_members.where({ :id => params[:account].to_i }).first
+ end
+
+ base_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.split("?")[0]}"
+
+ if @function == 'toggle'
+ if ! hunt_group_member
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- HuntGroupMember not found -->",
+ )
+ return
+ end
+
+ if hunt_group_member.can_switch_status_itself == true
+ if hunt_group_member.active
+ hunt_group_member.active = false
+ else
+ hunt_group_member.active = true
+ end
+
+ if ! hunt_group_member.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{hunt_group_member.errors.inspect} -->",
+ )
+ else
+ render(
+ :status => 200,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Member #{hunt_group_member.id} toggled -->",
+ )
+ end
+ return
+ end
+ elsif @function == 'members'
+ commands = [{
+ :type => 'UPDATE',
+ :auto => 20,
+ :label => 'Update',
+ },{
+ :type => 'BACK',
+ :label => 'Back',
+ :display_on => 'OPTIONS',
+ },{
+ :type => 'EXIT',
+ :label => 'Exit',
+ :display_on => 'OPTIONS',
+ },{
+ :type => 'SELECT',
+ :label => 'Show',
+ :display_on => 'LISTITEM',
+ }]
+
+ @phone_xml_object = {
+ :name => "menu_list",
+ :columns => 1,
+ :url => base_url,
+ :hidden => {:function => @function, :group => @hunt_group.id},
+ :entries => [],
+ :commands => commands,
+ }
+
+ @hunt_group.hunt_group_members.where(:active => true).each do |member|
+ @phone_xml_object[:entries].push({
+ :selected => false,
+ :value => member.id,
+ :text => member.name,
+ })
+ end
+ else
+ hunt_groups = Array.new()
+ phone_numbers = Array.new()
+ @sip_account.phone_numbers.each do |phone_number|
+ phone_numbers.push(phone_number.number)
+ assistant_call_forwardings = phone_number.call_forwards.where(:call_forward_case_id => CallForwardCase.where(:value => 'assistant').first.id)
+ assistant_call_forwardings.each do |assistant_call_forwarding|
+ if assistant_call_forwarding.call_forwardable_type == 'HuntGroup' && assistant_call_forwarding.call_forwardable_id.to_i > 0
+ hunt_groups.push(assistant_call_forwarding.call_forwardable_id.to_i)
+ end
+ end
+ end
+
+ hunt_group_members = Array.new()
+ if phone_numbers.length > 0
+ hunt_group_members = PhoneNumber.where(:phone_numberable_type => 'HuntGroupMember', :number => phone_numbers)
+ end
+
+ hunt_group_members.each do |hunt_group|
+ hunt_groups.push(hunt_group.phone_numberable.hunt_group_id)
+ end
+
+ hunt_groups = HuntGroup.where(:id => hunt_groups)
+
+ @phone_xml_object = {
+ :name => "menu_list",
+ :columns => 1,
+ :url => base_url,
+ :hidden => {:function => 'members'},
+ :entries => [],
+ :commands => [{
+ :type => 'EXIT',
+ :label => 'Exit',
+ :display_on => 'OPTIONS',
+ },{
+ :type => 'BACK',
+ :label => 'Back',
+ :display_on => 'OPTIONS',
+ },{
+ :type => 'SELECT',
+ :label => 'Select',
+ :display_on => 'LISTITEM',
+ }],
+ }
+
+ hunt_groups.each do |hunt_group|
+ @phone_xml_object[:entries].push({
+ :selected => false,
+ :key => 'group',
+ :value => hunt_group.id,
+ :text => hunt_group.name,
+ })
+ end
+
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+ end
+
+
+ def menu
+ if ! @phone or ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Phone or SipAccount not found -->",
+ )
+ return
+ end
+
+ type = 'menu'
+ if ! params[:type].blank?
+ type = params[:type]
+ elsif ! params[:tab].blank?
+ tab = params[:tab].rpartition("_")
+ if tab[1] != ''
+ type = tab[2]
+ end
+ end
+
+ if ! params[:item].blank?
+ item = params[:item]
+ end
+
+ menu_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.split("?")[0]}"
+ base_url = "#{request.protocol}#{request.host_with_port}/config_siemens/#{@phone.id}"
+
+ @phone_xml_object = {
+ :name => "menu_list",
+ :columns => 1,
+ :url => menu_url,
+ :hidden => {:type => type},
+ :entries => []
+ }
+
+ case type
+ when 'menu'
+ items = [
+ {
+ :value => 'phone_directory',
+ :text => "Directory",
+ :url => "#{menu_url}?type=#{type}",
+ },{
+ :value => 'call_history',
+ :text => "Call History",
+ :url => "#{menu_url}?type=call_history",
+ },
+ ]
+ when 'status'
+ items = [
+ {
+ :value => 'hunt_group',
+ :text => "Hunt Group",
+ :url => "#{base_url}/hunt_group.xml"
+ },
+ ]
+
+ commands = [
+ {
+ :type => 'UPDATE',
+ :auto => 10,
+ :label => 'Update',
+ }
+ ]
+ when 'help'
+ items = [
+ {
+ :key => 'item',
+ :value => 'help',
+ :text => "Help",
+ :url => "#{menu_url}?type=#{type}",
+ },
+ ]
+ when 'call_history'
+ items = [
+ {
+ :value => 'missed',
+ :text => "Missed",
+ :url => "#{base_url}/call_history.xml?type=missed",
+ },{
+ :value => 'dialed',
+ :text => "Dialed",
+ :url => "#{base_url}/call_history.xml?type=dialed",
+ },{
+ :value => 'received',
+ :text => "Received",
+ :url => "#{base_url}/call_history.xml?type=received",
+ },
+ ]
+ end
+
+ if item
+ items.each do |entry|
+ if entry[:value] == item
+ redirect_to entry[:url]
+ return;
+ end
+ end
+ end
+
+ @phone_xml_object[:entries] = items
+ @phone_xml_object[:commands] = commands
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+ end
+
+ def call_date_compact(date)
+ if date.strftime('%Y%m%d') == DateTime::now.strftime('%Y%m%d')
+ return date.strftime('%H:%M')
+ end
+ return date.strftime('%d.%m %H:%M')
+ end
+end
diff --git a/app/controllers/config_siemens_sort_controller.rb b/app/controllers/config_siemens_sort_controller.rb
new file mode 100644
index 0000000..c0739e5
--- /dev/null
+++ b/app/controllers/config_siemens_sort_controller.rb
@@ -0,0 +1,371 @@
+require 'nokogiri'
+#doc.search('Message/ItemList').each do |a| puts a.children end
+class ConfigSiemensController < ApplicationController
+#TODO Authentication
+ # No access for admins though as this contains personal data.
+
+ # We can't use load_and_authorize_resource() here because
+ # ConfigSiemensController isn't a resource.
+ # We can try client certificates
+
+ skip_authorization_check
+
+
+ def index
+ os40_keys=7
+ os60_keys=8
+ os80_keys=9
+ doc = Nokogiri::XML(request.body.read)
+ #logger.debug("#{params[:WorkpointMessage].to_xml}")
+ #logger.debug("#{params[:WorkpointMessage][:Message][:ItemList].to_xml}")
+ @phone_items=Hash.new
+ contact_reason = params[:WorkpointMessage][:Message][:ReasonForContact]
+ reply_status = doc.search('Message/ReasonForContact').first[:status]
+ reply_action = doc.search('Message/ReasonForContact').first[:action]
+
+ doc.search('Message/ItemList/Item').each do |post_item|
+ @phone_items[post_item[:name]]=post_item.children.to_s
+ end
+
+ mac_address = @phone_items['mac-addr']
+ phone_type = @phone_items['device-type']
+ if phone_type == "OpenStage 40"
+ max_keys = (os40_keys) * 2
+ elsif phone_type == "OpenStage 60"
+ max_keys = (os60_keys) * 2
+ elsif phone_type == "OpenStage 80"
+ max_keys = (os80_keys) * 2
+ else
+ max_keys = 0
+ end
+
+ blf_keys_max = max_keys / 2
+ shift_key_position = blf_keys_max - 1
+
+ #logger.debug(request.body.read)
+ @phone = Phone.find_by_mac_address(mac_address.gsub(':','').upcase)
+ if ! @phone.nil?
+ @phone.update_attributes(:ip_address => request.remote_ip)
+ sip_account = SipAccount.where(:sip_accountable_type == @phone.phoneable_type,
+ :sip_accountable_id == @phone.phoneable_id).first
+ end
+
+ if ! @phone.nil? && ! sip_account.nil?
+ #logger.debug(@phone_items)
+ @my_nonce = params[:WorkpointMessage][:Message][:nonce]
+ @new_settings = Array.new
+
+ @new_settings << ['dhcp', nil, 'true']
+ @new_settings << ['hostname', nil, mac_address.gsub(':', '') ]
+ @new_settings << ['e164-hostname', nil, 'false']
+ @new_settings << ['mobility-enabled', nil, 'false']
+ @new_settings << ['mobility-password-on-logoff', nil, 'false']
+ @new_settings << ['e164', nil, sip_account.try(:phone_numbers).first.number]
+ @new_settings << ['sip-user-id', nil, sip_account.auth_name]
+ @new_settings << ['reg-id', nil, sip_account.auth_name]
+ @new_settings << ['reg-number', nil, sip_account.auth_name]
+ @new_settings << ['fully-qualified-phone-no', nil, sip_account.auth_name]
+ @new_settings << ['sip-pwd', nil, sip_account.password]
+ @new_settings << ['sip-name', nil, sip_account.caller_name]
+ @new_settings << ['register-by-name', nil, 'false']
+ #OPTIMIZE Display ID ?
+ @new_settings << ['display-id', nil, sip_account.try(:phone_numbers).first.number]
+ @new_settings << ['display-id-unicode', nil, sip_account.caller_name]
+ @new_settings << ['use-display-id', nil, 'true']
+ @new_settings << ['reg-addr', nil, sip_account.sip_domain.host]
+ @new_settings << ['reg-port', nil, '5060']
+ @new_settings << ['registrar-addr', nil, sip_account.sip_domain.host]
+ @new_settings << ['registrar-port', nil, '5060']
+ @new_settings << ['outbound-proxy', nil, sip_account.sip_domain.host]
+ @new_settings << ['outbound-proxy-user', nil, sip_account.sip_domain.host]
+ @new_settings << ['sgnl-gateway-addr', nil, sip_account.sip_domain.host]
+ @new_settings << ['sgnl-gateway-addr-user', nil, sip_account.sip_domain.host]
+ @new_settings << ['sgnl-gateway-port', nil, '5060' ]
+ @new_settings << ['sgnl-gateway-port-user', nil, '5060']
+ @new_settings << ['sgnl-route', nil, '0' ]
+ @new_settings << ['mwi-e164', nil, '' ]
+ @new_settings << ['rtp-base-port', nil, '5004']
+ @new_settings << ['default-domain', nil, '' ]
+ @new_settings << ['sip-transport', nil, '0' ]
+ @new_settings << ['sip-transport-user', nil, '0' ]
+ @new_settings << ['server-type', nil, '0' ]
+ @new_settings << ['session-timer', nil, 'true']
+ @new_settings << ['session-duration', nil, '3600' ]
+ @new_settings << ['reg-ttl', nil, '3600' ]
+ @new_settings << ['realm', nil, sip_account.sip_domain.realm]
+ @new_settings << ['emergency-e164', nil, '0110' ]
+ @new_settings << ['voice-mail-e164', nil, 'voicemail']
+ @new_settings << ['auto-answer', nil, 'false']
+ @new_settings << ['beep-on-auto-answer', nil, 'true']
+ @new_settings << ['auto-reconnect', nil, 'false' ]
+ @new_settings << ['beep-on-auto-reconnect', nil, 'true']
+ @new_settings << ['permit-decline-call', nil, 'true']
+ @new_settings << ['transfer-on-ring', nil, 'false' ]
+ @new_settings << ['join-allowed-in-conference', nil, 'true']
+ @new_settings << ['pickup-group-uri', nil, '*8*']
+ @new_settings << ['pickup-group-uri', nil, '' ]
+ @new_settings << ['hot-line-warm-line-digits', nil, '' ]
+ @new_settings << ['initial-digit-timer', nil, '30' ]
+ @new_settings << ['conference-factory-uri', nil, '']
+ @new_settings << ['callback-busy-allow', nil, 'false']
+ @new_settings << ['callback-busy-code', nil, '' ]
+ @new_settings << ['callback-ring-allow', nil, 'false']
+ @new_settings << ['callback-ring-code', nil, '']
+ @new_settings << ['callback-cancel-code', nil, '']
+ @new_settings << ['park-server', nil, '']
+ #OPTIMIZE Callwaiting
+ @new_settings << ['call-waiting-enabled', nil, 'true']
+ @new_settings << ['qos-layer2', nil, 'true']
+ @new_settings << ['l2qos-voice', nil, '5' ]
+ @new_settings << ['l2qos-signalling', nil, '3' ]
+ @new_settings << ['l2qos-default', nil, '0']
+ @new_settings << ['qos-layer3', nil, 'true']
+ @new_settings << ['l3qos-voice', nil, '46']
+ @new_settings << ['l3qos-signalling', nil, '26']
+ @new_settings << ['vlan-method', nil, '1']
+ #OPTIMIZE Timezone
+ @new_settings << ['sntp-tz-offset', nil, '']
+ @new_settings << ['daylight-save', nil, '']
+ @new_settings << ['daylight-save-minutes', nil, '']
+ #OPTIMIZE Use SNMP?
+ @new_settings << ['snmp-trap-addr', nil, '']
+ @new_settings << ['snmp-trap-port', nil, '']
+ @new_settings << ['snmp-trap-pwd', nil, 'snmp' ]
+ @new_settings << ['snmp-traps-active', nil, 'false' ]
+ @new_settings << ['diagnostic-trap-addr', nil, '']
+ @new_settings << ['diagnostic-trap-port', nil, '']
+ @new_settings << ['diagnostic-trap-pwd', nil, 'snmp' ]
+ @new_settings << ['diagnostic-traps-active', nil, 'false' ]
+ @new_settings << ['diagnostic-snmp-active', nil, 'false']
+ @new_settings << ['qdc-collection-unit-addr', nil, '']
+ @new_settings << ['qdc-collection-unit-port', nil, '12010']
+
+ @new_settings << ['qdc-trap-pwd', nil, 'QOSDC']
+ @new_settings << ['qdc-snmp-active', nil, 'false']
+ @new_settings << ['qdc-qcu-active', nil, 'false']
+ @new_settings << ['snmp-queries-allowed', nil, 'false']
+ @new_settings << ['snmp-pwd', nil, '']
+ @new_settings << ['disable-microphone', nil, 'false']
+ @new_settings << ['loudspeech-enabled', nil, 'true']
+ @new_settings << ['audio-silence-suppression', nil, 'false']
+
+ @new_settings << ['port1', nil, '0' ] # 0=Automatic (speed)
+ @new_settings << ['port2', nil, '0' ]
+ @new_settings << ['port2-mode', nil, '1' ]
+ @new_settings << ['port2-auto-mdix-enabled', nil, 'true' ]
+ @new_settings << ['originating-line-preference', nil, '0']
+ @new_settings << ['terminating-line-preference', nil, '0']
+ @new_settings << ['line-key-operating-mode', nil, '0']
+ @new_settings << ['line-rollover-type', nil, '2']
+ @new_settings << ['line-rollover-volume', nil, '5' ]# 1-5
+ @new_settings << ['line-registration-leds', nil, 'true']
+ @new_settings << ['keyset-use-focus', nil, 'true' ]
+ @new_settings << ['keyset-remote-forward-ind', nil, 'true']
+ @new_settings << ['keyset-reservation-timer', nil, '60' ] # 0-300
+ @new_settings << ['dial-plan-enabled', nil, '' ]
+ @new_settings << ['Canonical-dialing-international-prefix', nil, '']
+ @new_settings << ['Canonical-dialing-local-country-code', nil, '']
+ @new_settings << ['Canonical-dialing-national-prefix', nil, '']
+ @new_settings << ['Canonical-dialing-local-area-code', nil, '']
+ @new_settings << ['Canonical-dialing-local-node', nil, '']
+ @new_settings << ['Canonical-dialing-external-access', nil, '0']
+ @new_settings << ['Canonical-dialing-operator-code', nil, '']
+ @new_settings << ['Canonical-dialing-emergency-number', nil, '']
+ @new_settings << ['Canonical-dialing-dial-needs-access-code', nil, '0']
+ @new_settings << ['Canonical-dialing-dial-needs-intGWcode', nil, '0']
+ @new_settings << ['Canonical-dialing-min-local-number-length', nil, '10']
+ @new_settings << ['Canonical-dialing-extension-initial-digits', nil, '']
+ @new_settings << ['Canonical-dialing-dial-internal-form', nil, '0' ]
+ @new_settings << ['Canonical-dialing-dial-external-form', nil, '0' ]
+ @new_settings << ['Canonical-lookup-local-code', nil, '' ]
+ @new_settings << ['Canonical-lookup-international-code', nil, '']
+ @new_settings << ['hot-keypad-dialing', nil, '']
+ @new_settings << ['ldap-transport', nil, '0']
+ @new_settings << ['ldap-server-address', nil, '' ]
+ @new_settings << ['ldap-server-port', nil, '389' ]
+ @new_settings << ['ldap-authentication', nil, '1']
+ @new_settings << ['ldap-user', nil, '' ]
+ @new_settings << ['ldap-pwd', nil, '' ]
+ @new_settings << ['ldap-max-responses', nil, '25']
+ @new_settings << ['backup-addr', nil, '']
+ @new_settings << ['backup-registration', nil, 'false']
+ @new_settings << ['qdc-qcu-active', nil, 'false' ]
+ @new_settings << ['min-admin-passw-length', nil, '6' ]
+ @new_settings << ['default-locked-config-menus', nil, 'true' ]
+ @new_settings << ['locked-config-menus', nil, 'true' ]
+ @new_settings << ['default-locked-local-function-menus', nil, 'true' ]
+ @new_settings << ['locked-local-function-menus', nil, 'true' ]
+ @new_settings << ['dls-mode-secure', nil, '0' ]
+ @new_settings << ['dls-chunk-size', nil, '9492']
+ @new_settings << ['default-passw-policy', nil, 'false']
+ @new_settings << ['deflect-destination', nil, '']
+ @new_settings << ['display-skin', nil, '']
+ @new_settings << ['enable-bluetooth-interface', nil, 'true']
+ @new_settings << ['usb-access-enabled', nil, 'false' ]
+ @new_settings << ['usb-backup-enabled', nil, 'false' ]
+ @new_settings << ['line-button-mode', nil, '0' ]
+ @new_settings << ['lock-forwarding', nil, '' ]
+ @new_settings << ['loudspeaker-function-mode', nil, '0' ]
+ @new_settings << ['max-pin-retries', nil, '' ]
+ @new_settings << ['inactivity-timeout', nil, '30' ]
+ @new_settings << ['not-used-timeout', nil, '2' ]
+ @new_settings << ['passw-char-set', nil, '0' ]
+ @new_settings << ['refuse-call', nil, 'true' ]
+ @new_settings << ['restart-password', nil, '']
+ #OPTIMIZE clock format
+ @new_settings << ['time-format', nil, '0' ]# 1=12 h
+ @new_settings << ['uaCSTA-enabled', nil, 'false' ]
+ @new_settings << ['enable-test-interface', nil, 'false']
+ @new_settings << ['enable-WBM', nil, 'true']
+ @new_settings << ['pixelsaver-timeout', nil, '2' ]# 2 hours?
+ @new_settings << ['voice-message-dial-tone', nil, '' ]
+ @new_settings << ['call-pickup-allowed', nil, 'true' ]
+ @new_settings << ['group-pickup-tone-allowed', nil, 'true']
+ @new_settings << ['group-pickup-as-ringer', nil, 'false']
+ @new_settings << ['group-pickup-alert-type', nil, '0' ]
+ @new_settings << ['default-profile', nil, '' ]
+ @new_settings << ['count-medium-priority', nil, '5']
+ @new_settings << ['timer-medium-priority', nil, '60'] # 1 - 999
+ @new_settings << ['timer-high-priority', nil, '5'] # 0 - 999
+ @new_settings << ['dss-sip-detect-timer', nil, '10']
+ @new_settings << ['dss-sip-deflect', nil, 'false' ]
+ @new_settings << ['dss-sip-refuse', nil, 'false' ]
+ @new_settings << ['feature-availability', nil, 'false']
+ @new_settings << ['feature-availability', nil, 'true' ]
+ @new_settings << ['feature-availability', nil, 'true' ]
+ @new_settings << ['local-control-feature-availability', nil, 'false' ]
+ @new_settings << ['trace-level', nil, '0' ] # Off
+ @new_settings << ['default-locked-function-keys', nil, 'true' ]# "unknown item"
+ #OPTIMIZE Put pickup prefix into database/global constant?
+ @new_settings << ['blf-code', nil, 'f_ia_'] # pickup prefix for softkey function 59 (BLF)
+ @new_settings << ['stimulus-feature-code', nil, true]
+ @new_settings << ['stimulus-led-control-uri', nil, true]
+
+
+ @new_settings << ['min-user-passw-length', nil, '6' ]# 6 - 24
+ #OPTIMIZE language
+ @new_settings << ['country-iso', nil, 'DE' ]
+ @new_settings << ['language-iso', nil, 'de']
+ @new_settings << ['date-format', nil, '0' ] # DD.MM.YYYY
+ #OPTIMIZE ringtones
+ @new_settings << ['ringer-melody', nil, '1']
+
+ @new_settings << ['ringer-melody', nil, '2']
+ @new_settings << ['ringer-tone-sequence', nil, '2']
+
+ soft_keys = Array.new
+ # Getting BLF keys only for the first level
+ blf_keys = sip_account.softkeys.find(
+ :all,
+ :conditions => {:function => ['blf', 'conference']},
+ :limit => blf_keys_max)
+ #Getting other keys
+ non_blf_keys = sip_account.softkeys.find(
+ :all,
+ :conditions => {:function => ['speed_dial']})
+
+ # Fill softkey array with BLF keys up to shift key
+ blf_keys.each do |k|
+ soft_keys << k
+ end
+ # Fill sofkey with other keys up to end
+ non_blf_keys.each do |k|
+ if soft_keys.length < max_keys
+ soft_keys << k
+ end
+ end
+ # Delete unset softkeys
+ while soft_keys.length < max_keys
+ soft_keys << Softkey.new
+ end
+
+ key_pos=1
+
+ #soft_keys.each do |sk|
+
+ while key_pos < shift_key_position
+
+ (1..shift_key_position-1).each do |key_idx|
+ sk = soft_keys.shift
+ logger.debug(sk.function, key_idx)
+ if sk.function == "blf"
+ @new_settings << ['function-key-def', key_idx, '59']
+ @new_settings << ['select-dial', key_idx, sk.number ]
+ elsif sk.function == "log_out"
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, 'f_lo' ]
+ elsif sk.function == "log_in"
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, "f_li_#{sk.number}" ]
+ elsif sk.function == "dtmf"
+ @new_settings << ['function-key-def', key_idx, '54']
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, sk.number ]
+ elsif sk.function.nil?
+ @new_settings << ['function-key-def', key_idx, '0']
+ else
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, sk.number ]
+ end
+ @new_settings << ['key-label', key_idx, sk.label ]
+ @new_settings << ['key-label-unicode', key_idx, sk.label ]
+ key_pos = key_pos+1
+
+ end
+ end
+ if key_pos == shift_key_position
+ @new_settings << ['function-key-def', shift_key_position, '18']
+ @new_settings << ['key-label', shift_key_position, 'Shift']
+ @new_settings << ['key-label-unicode', shift_key_position, 'Shift']
+ key_pos = key_pos+1
+ end
+
+ (1001..1000+shift_key_position-1).each do |key_idx|
+ sk = soft_keys.shift
+ if sk.function == "log_out"
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, 'f_lo' ]
+ elsif sk.function == "log_in"
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, "f_li_#{sk.number}" ]
+ elsif sk.function == "dtmf"
+ @new_settings << ['function-key-def', key_idx, '54']
+ @new_settings << ['stimulus-DTMF-sequence', key_idx, sk.number ]
+ elsif sk.function.nil?
+ @new_settings << ['function-key-def', key_idx, '0']
+ else
+ @new_settings << ['function-key-def', key_idx, '1']
+ @new_settings << ['select-dial', key_idx, sk.number ]
+ end
+ @new_settings << ['key-label', key_idx, sk.label ]
+ @new_settings << ['key-label-unicode', key_idx, sk.label ]
+ key_pos = key_pos+1
+
+ end
+
+ #end
+ logger.debug(@new_settings)
+ end
+
+ if @phone.nil? || sip_account.nil?
+ respond_to { |format|
+ format.xml { render :action => "clean-up" }
+ }
+
+ elsif (reply_status == 'accepted' && contact_reason == 'reply-to' && reply_action == 'ReadAllItems')
+ respond_to { |format|
+ format.xml { render :action => "write" }
+ }
+
+ elsif ["reply-to"].include? contact_reason
+ respond_to { |format|
+ format.xml { render :action => "clean-up" }
+ }
+
+ else
+ respond_to { |format|
+ format.xml { render :action => "index" }
+ }
+ end
+
+ end
+end
diff --git a/app/controllers/config_snom_controller.rb b/app/controllers/config_snom_controller.rb
new file mode 100644
index 0000000..40f0c4e
--- /dev/null
+++ b/app/controllers/config_snom_controller.rb
@@ -0,0 +1,1169 @@
+class ConfigSnomController < ApplicationController
+ MAX_SIP_ACCOUNTS_COUNT = 11
+ MAX_SOFTKEYS_COUNT = 12 + (42 * 3) - 1
+ MAX_DIRECTORY_ENTRIES = 20
+ KEYPAD_TO_CHAR = {
+ '0' => [' ','-','.',',','0'],
+ '1' => [' ','-','.',',','1'],
+ '2' => ['a','b','c','2'],
+ '3' => ['d','e','f','3'],
+ '4' => ['g','h','i','4'],
+ '5' => ['j','k','l','5'],
+ '6' => ['m','n','o','6'],
+ '7' => ['p','q','r','s','7'],
+ '8' => ['t','u','v','8'],
+ '9' => ['w','x','y','z','9'],
+ }
+
+ skip_authorization_check
+
+ before_filter { |controller|
+ @mac_address = params[:mac_address].to_s.upcase.gsub(/[^0-9A-F]/,'')
+ @provisioning_authenticated = false
+
+ if !params[:provisioning_key].blank?
+ @phone = Phone.where({ :provisioning_key => params[:provisioning_key] }).first
+ if @phone
+ @provisioning_authenticated = true
+ @mac_address = @phone.mac_address
+ end
+ end
+
+ if ! @mac_address.blank? then
+ if !@phone
+ @phone = Phone.where({ :mac_address => @mac_address }).first
+ end
+
+ if ! @phone && PROVISIONING_AUTO_ADD_PHONE
+ tenant = Tenant.where(:id => PROVISIONING_AUTO_TENANT_ID).first
+ if ! tenant
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Tenant not found -->",
+ )
+ return
+ end
+
+ @phone = tenant.phones.build
+ @phone.mac_address = @mac_address
+ @phone.hot_deskable = true
+
+ mac_address_to_model = {
+ '00041325' => 'Snom 300',
+ '00041328' => 'Snom 300',
+ '0004132D' => 'Snom 300',
+ '0004132F' => 'Snom 300',
+ '00041334' => 'Snom 300',
+ '00041350' => 'Snom 300',
+ '0004133B' => 'Snom 300',
+ '00041337' => 'Snom 300',
+ '00041324' => 'Snom 320',
+ '00041327' => 'Snom 320',
+ '0004132C' => 'Snom 320',
+ '00041331' => 'Snom 320',
+ '00041335' => 'Snom 320',
+ '00041338' => 'Snom 320',
+ '00041351' => 'Snom 320',
+ '00041323' => 'Snom 360',
+ '00041329' => 'Snom 360',
+ '0004132B' => 'Snom 360',
+ '00041339' => 'Snom 360',
+ '00041390' => 'Snom 360',
+ '00041326' => 'Snom 370',
+ '0004132E' => 'Snom 370',
+ '0004133A' => 'Snom 370',
+ '00041352' => 'Snom 370',
+ '00041340' => 'Snom 820',
+ '00041345' => 'Snom 821',
+ '00041348' => 'Snom 821',
+ '00041341' => 'Snom 870',
+ }
+
+ @phone.phone_model = PhoneModel.where(:name => mac_address_to_model[@mac_address[0, 8]]).first
+ if ! @phone.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{@phone.errors.messages.inspect} -->",
+ )
+ return
+ end
+
+ if ! PROVISIONING_AUTO_ADD_SIP_ACCOUNT
+ return
+ end
+
+ caller_name_index = 0
+ sip_account_last = tenant.sip_accounts.where('caller_name LIKE ?', "#{PROVISIONING_AUTO_SIP_ACCOUNT_CALLER_PREFIX}%").sort { |item1, item2|
+ item1.caller_name.gsub(/[^0-9]/, '').to_i <=> item2.caller_name.gsub(/[^0-9]/, '').to_i
+ }.last
+
+ if sip_account_last
+ caller_name_index = sip_account_last.caller_name.gsub(/[^0-9]/, '').to_i
+ end
+ caller_name_index = caller_name_index + 1
+
+ @sip_account = tenant.sip_accounts.build
+ @sip_account.caller_name = "#{PROVISIONING_AUTO_SIP_ACCOUNT_CALLER_PREFIX}#{caller_name_index}"
+ @sip_account.call_waiting = CALL_WAITING
+ @sip_account.clir = DEFAULT_CLIR_SETTING
+ @sip_account.clip = DEFAULT_CLIP_SETTING
+ @sip_account.voicemail_pin = random_pin
+ @sip_account.callforward_rules_act_per_sip_account = CALLFORWARD_RULES_ACT_PER_SIP_ACCOUNT_DEFAULT
+ @sip_account.hotdeskable = false
+ loop do
+ @sip_account.auth_name = SecureRandom.hex(DEFAULT_LENGTH_SIP_AUTH_NAME)
+ break unless SipAccount.exists?(:auth_name => @sip_account.auth_name)
+ end
+ @sip_account.password = SecureRandom.hex(DEFAULT_LENGTH_SIP_PASSWORD)
+
+ if ! @sip_account.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{@sip_account.errors.messages.inspect} -->",
+ )
+ return
+ end
+
+ phone_sip_account = PhoneSipAccount.new()
+ phone_sip_account.phone_id = @phone.id
+ phone_sip_account.sip_account_id = @sip_account.id
+
+ if ! phone_sip_account.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{phone_sip_account.errors.messages.inspect} -->",
+ )
+ return
+ end
+
+ end
+ elsif ! params[:phone].blank? then
+ @phone = Phone.where({ :id => params[:phone].to_i }).first
+ end
+
+ if ! @phone
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Phone not found -->",
+ )
+ end
+
+ if ! params[:sip_account].blank?
+ @sip_account = @phone.sip_accounts.where({ :id => params[:sip_account].to_i }).first
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ end
+ end
+
+ if ! params[:type].blank?
+ @type = params[:type].to_s.strip.downcase
+ end
+
+ if ! params[:keys].blank?
+ @dialpad_keys = params[:keys].to_s.strip
+ end
+ }
+
+
+ def show
+ send_sensitve = @provisioning_authenticated || !@phone.provisioning_key_active
+ @phone_settings = Hash.new()
+
+ if defined?(PROVISIONING_KEY_LENGTH) && PROVISIONING_KEY_LENGTH > 0
+ if @phone.provisioning_key.blank?
+ @phone.update_attributes({ :provisioning_key => SecureRandom.hex(PROVISIONING_KEY_LENGTH), :provisioning_key_active => false })
+ elsif @provisioning_authenticated
+ @phone.update_attributes({ :provisioning_key_active => true })
+ end
+
+ if send_sensitve
+ if defined?(PROVISIONING_PROTOCOL) && PROVISIONING_PROTOCOL
+ provisioning_protocol = PROVISIONING_PROTOCOL
+ else
+ provisioning_protocol = request.protocol
+ end
+ @phone_settings[:setting_server] = "#{provisioning_protocol}#{request.host_with_port}/snom-#{@phone.provisioning_key}.xml"
+ end
+ end
+
+ if defined?(PROVISIONING_SET_HTTP_USER) && @phone.http_user.blank?
+ if PROVISIONING_SET_HTTP_USER.class == Fixnum
+ @phone.update_attributes({ :http_user => SecureRandom.hex(PROVISIONING_SET_HTTP_USER) })
+ elsif PROVISIONING_SET_HTTP_USER.class == String
+ @phone.update_attributes({ :http_user => PROVISIONING_SET_HTTP_USER })
+ end
+ end
+
+ if defined?(PROVISIONING_SET_HTTP_PASSWORD) && @phone.http_password.blank?
+ if PROVISIONING_SET_HTTP_PASSWORD.class == Fixnum
+ @phone.update_attributes({ :http_password => SecureRandom.hex(PROVISIONING_SET_HTTP_PASSWORD) })
+ elsif PROVISIONING_SET_HTTP_PASSWORD.class == String
+ @phone.update_attributes({ :http_password => PROVISIONING_SET_HTTP_PASSWORD })
+ end
+ end
+
+ if send_sensitve
+ @phone_settings[:http_user] = @phone.http_user
+ @phone_settings[:http_pass] = @phone.http_password
+ if defined?(PROVISIONING_ADMIN_PASSWORD)
+ if PROVISIONING_ADMIN_PASSWORD.class == TrueClass
+ @phone_settings[:admin_mode_password] = @phone.http_password
+ elsif PROVISIONING_ADMIN_PASSWORD.class == String
+ @phone_settings[:admin_mode_password] = PROVISIONING_ADMIN_PASSWORD
+ end
+ end
+ end
+
+ if ! request.env['HTTP_USER_AGENT'].index('snom')
+ Rails.logger.info "---> User-Agent indicates not a Snom phone (#{request.env['HTTP_USER_AGENT'].inspect})"
+ else
+ Rails.logger.info "---> Phone #{@mac_address.inspect}, IP address #{request.remote_ip.inspect}"
+ @phone.update_attributes({ :ip_address => request.remote_ip })
+ end
+
+ @softkeys = Array.new()
+ @sip_accounts = Array.new()
+
+ if send_sensitve
+ @phone.sip_accounts.each do |sip_account|
+ if (sip_account.sip_accountable_type == @phone.phoneable_type) and (sip_account.sip_accountable_id == @phone.phoneable_id)
+ snom_sip_account = {
+ :id => sip_account.id,
+ :active => 'on',
+ :pname => sip_account.auth_name,
+ :pass => sip_account.password,
+ :host => sip_account.host,
+ :outbound => sip_account.host,
+ :name => sip_account.auth_name,
+ :realname => 'Call',
+ :idle_text => sip_account.caller_name,
+ :mailbox => "<sip:#{sip_account.auth_name}@#{sip_account.host}>"
+ }
+ @sip_accounts.push(snom_sip_account)
+ sip_account_index = @sip_accounts.length
+ sip_account.softkeys.order(:position).each do |softkey|
+ if softkey.softkey_function
+ softkey_function = softkey.softkey_function.name
+ end
+ case softkey_function
+ when 'blf'
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => "blf <sip:#{softkey.number}@#{sip_account.host}>|f-ia-"})
+ when 'speed_dial'
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => "speed #{softkey.number}"})
+ when 'dtmf'
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => "dtmf #{softkey.number}"})
+ when 'log_out'
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => "speed f-lo"})
+ when 'log_in'
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => "speed f-li-#{softkey.number}"})
+ when 'conference'
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => "blf <sip:#{softkey.number}@#{sip_account.host}>|f-ta-"})
+ when 'call_forwarding'
+ @softkeys.push({
+ :context => sip_account_index,
+ :function => softkey.function,
+ :label => softkey.label,
+ :softkey => softkey,
+ :general_type => t("softkeys.functions.#{softkey.softkey_function.name}"),
+ :subscription => {
+ :to => "f-cftg-#{softkey.call_forward_id}@#{sip_account.host}",
+ :for => "#{sip_account.auth_name}@#{sip_account.host}"
+ },
+ :actions => [{
+ :type => :url,
+ :target => "#{request.protocol}#{request.host_with_port}/config_snom/#{@phone.id}/#{snom_sip_account[:id]}/call_forwarding.xml?id=#{softkey.call_forward_id}&function=toggle",
+ :when => 'on press',
+ }],
+ })
+ when 'call_forwarding_always'
+ phone_number = PhoneNumber.where(:number => softkey.number, :phone_numberable_type => 'SipAccount').first
+ if phone_number
+ account_param = (phone_number.phone_numberable_id != snom_sip_account[:id] ? "&account=#{phone_number.phone_numberable_id}" : '')
+ else
+ phone_number = sip_account.phone_numbers.first
+ account_param = ''
+ end
+
+ @softkeys.push({
+ :context => sip_account_index,
+ :function => softkey.function,
+ :label => softkey.label,
+ :softkey => softkey,
+ :general_type => t("softkeys.functions.#{softkey.softkey_function.name}"),
+ :subscription => {
+ :to => "f-cfutg-#{phone_number.id}@#{sip_account.host}",
+ :for => "#{sip_account.auth_name}@#{sip_account.host}"
+ },
+ :actions => [{
+ :type => :url,
+ :target => "#{request.protocol}#{request.host_with_port}/config_snom/#{@phone.id}/#{snom_sip_account[:id]}/call_forwarding.xml?type=always&function=toggle#{account_param}",
+ :when => 'on press',
+ }],
+ })
+ when 'call_forwarding_assistant'
+ phone_number = PhoneNumber.where(:number => softkey.number, :phone_numberable_type => 'SipAccount').first
+ if phone_number
+ account_param = (phone_number.phone_numberable_id != snom_sip_account[:id] ? "&account=#{phone_number.phone_numberable_id}" : '')
+ else
+ phone_number = sip_account.phone_numbers.first
+ account_param = ''
+ end
+
+ @softkeys.push({
+ :context => sip_account_index,
+ :function => softkey.function,
+ :label => softkey.label,
+ :softkey => softkey,
+ :general_type => t("softkeys.functions.#{softkey.softkey_function.name}"),
+ :subscription => {
+ :to => "f-cfatg-#{phone_number.id}@#{sip_account.host}",
+ :for => "#{sip_account.auth_name}@#{sip_account.host}"
+ },
+ :actions => [{
+ :type => :url,
+ :target => "#{request.protocol}#{request.host_with_port}/config_snom/#{@phone.id}/#{snom_sip_account[:id]}/call_forwarding.xml?type=assistant&function=toggle#{account_param}",
+ :when => 'on press',
+ }],
+ })
+ when 'hunt_group_membership'
+ phone_number = PhoneNumber.where(:number => softkey.number, :phone_numberable_type => 'HuntGroup').first
+ if phone_number
+ hunt_group = HuntGroup.where(:id => phone_number.phone_numberable_id).first
+ end
+
+ sip_account_phone_numbers = Array.new()
+ SipAccount.where(:id => @sip_accounts.first[:id]).first.phone_numbers.each do |phone_number|
+ sip_account_phone_numbers.push(phone_number.number)
+ end
+
+ hunt_group_member_numbers = PhoneNumber.where(:number => sip_account_phone_numbers, :phone_numberable_type => 'HuntGroupMember')
+
+ hunt_group_member = nil
+ if hunt_group and hunt_group_member_numbers
+ hunt_group_member_numbers.each do |hunt_group_member_number|
+ hunt_group_member = hunt_group.hunt_group_members.where(:id => hunt_group_member_number.phone_numberable_id).first
+ if hunt_group_member
+ break
+ end
+ end
+ end
+
+ if hunt_group_member
+ @softkeys.push({
+ :context => sip_account_index,
+ :function => softkey.function,
+ :label => softkey.label,
+ :softkey => softkey,
+ :general_type => t("softkeys.functions.#{softkey.softkey_function.name}"),
+ :subscription => {
+ :to => "f-hgmtg-#{hunt_group_member.id}@#{sip_account.host}",
+ :for => "#{sip_account.auth_name}@#{sip_account.host}"
+ },
+ :actions => [{
+ :type => :url,
+ :target => "#{request.protocol}#{request.host_with_port}/config_snom/#{@phone.id}/#{snom_sip_account[:id]}/hunt_group.xml?group=#{hunt_group.id}&account=#{hunt_group_member.id}&function=toggle",
+ :when => 'on press',
+ }],
+ })
+ else
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => 'none'})
+ end
+ when 'acd_membership'
+ acd_agent = nil
+ phone_number = PhoneNumber.where(:number => softkey.number, :phone_numberable_type => 'AutomaticCallDistributor').first
+ if phone_number
+ acd = AutomaticCallDistributor.where(:id => phone_number.phone_numberable_id).first
+ if acd
+ acd_agent = acd.acd_agents.where(:destination_type => 'SipAccount', :destination_id => sip_account.id).first
+ end
+ end
+
+ if acd_agent
+ @softkeys.push({
+ :context => sip_account_index,
+ :function => softkey.function,
+ :label => softkey.label,
+ :softkey => softkey,
+ :general_type => t("softkeys.functions.#{softkey.softkey_function.name}"),
+ :subscription => {
+ :to => "f-acdmtg-#{acd_agent.id}@#{sip_account.host}",
+ :for => "#{sip_account.auth_name}@#{sip_account.host}"
+ },
+ :actions => [{
+ :type => :url,
+ :target => "#{request.protocol}#{request.host_with_port}/config_snom/#{@phone.id}/#{snom_sip_account[:id]}/acd.xml?acd=#{acd.id}&agent=#{acd_agent.id}&function=toggle",
+ :when => 'on press',
+ }],
+ })
+ else
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => 'none'})
+ end
+ when 'hold'
+ @softkeys.push({:context => sip_account_index, :label => softkey.label, :data => "keyevent F_R"})
+ else
+ @softkeys.push({:label => softkey.label, :data => 'none'})
+ end
+ end
+ end
+ end
+ end
+
+ languages_map = {
+ 'ca' => 'Catalan',
+ 'bs' => 'Bosanski',
+ 'da' => 'Dansk',
+ 'de' => 'Deutsch',
+ 'cs' => 'Cestina',
+ 'en' => 'English',
+ 'es' => 'Espanol',
+ 'fi' => 'Suomi',
+ 'et' => 'Estonian',
+ 'fr' => 'Francais',
+ 'he' => 'Hebrew',
+ 'hu' => 'Hungarian',
+ 'it' => 'Italiano',
+ 'nl' => 'Dutch',
+ 'no' => 'Norsk',
+ 'pl' => 'Polski',
+ 'pt' => 'Portugues',
+ 'si' => 'Slovenian',
+ 'sk' => 'Slovencina',
+ 'ru' => 'Russian',
+ 'sv' => 'Svenska',
+ 'tr' => 'Turkce',
+ }
+
+ tone_schemes_map = {
+ '1' => 'USA', # United States
+ '61' => 'AUS', # Australia
+ '43' => 'AUT', # Austria
+ '86' => 'CHN', # China
+ '45' => 'DNK', # Denmark
+ '33' => 'FRA', # France
+ '49' => 'GER', # Germany
+ '44' => 'GBR', # Great Britain
+ '91' => 'IND', # India
+ '39' => 'ITA', # Italy
+ '81' => 'JPN', # Japan
+ '52' => 'MEX', # Mexico
+ '31' => 'NLD', # Netherlands
+ '47' => 'NOR', # Norway
+ '64' => 'NZL', # New Zealand
+ '34' => 'ESP', # Spain
+ '46' => 'SWE', # Sweden
+ '41' => 'SWI', # Switzerland
+ }
+
+ if @phone.phoneable
+ if @phone.phoneable_type == 'Tenant'
+ tenant = @phone.phoneable
+ language = tenant.language.code
+ elsif @phone.phoneable_type == 'User'
+ tenant = @phone.phoneable.current_tenant
+ language = @phone.phoneable.language.code
+ end
+ end
+
+ if tenant && tenant.country
+ tone_scheme = tenant.country.country_code
+ end
+
+ @phone_settings[:tone_scheme] = tone_schemes_map.include?(tone_scheme.to_s) ? tone_schemes_map[tone_scheme.to_s] : 'USA'
+ @phone_settings[:language] = languages_map.include?(language.to_s) ? languages_map[language.to_s] : 'English'
+
+ xml_applications_url = "#{request.protocol}#{request.host_with_port}/config_snom/#{@phone.id}/#{(@sip_accounts.blank? ? '0' : @sip_accounts.first[:id])}"
+ @dkeys = {
+ :menu => 'keyevent F_SETTINGS',
+ :retrieve => 'speed f-vmcheck',
+ :conf => 'keyevent F_CONFERENCE',
+ :redial => "url #{xml_applications_url}/call_history.xml?type=dialed",
+ :directory => "url #{xml_applications_url}/phone_book.xml",
+ :idle_ok => "url #{xml_applications_url}/call_history.xml?type=dialed",
+ :idle_cancel => "keyevent F_CANCEL",
+ :idle_up => "keyevent F_PREV_ID",
+ :idle_down => "keyevent F_NEXT_ID",
+ :idle_left => "url #{xml_applications_url}/call_history.xml?type=received",
+ :idle_right => "url #{xml_applications_url}/call_history.xml?type=missed",
+ }
+
+ # Remap conference key to first conference if found
+ #conference = Conference.where(:conferenceable_type => @phone.phoneable_type, :conferenceable_id => @phone.phoneable_id).first
+ #if conference and conference.phone_numbers
+ # @dkeys[:conf] = "speed f_ta_#{conference.phone_numbers.first.number}"
+ #end
+
+ @sip_accounts.length().upto(MAX_SIP_ACCOUNTS_COUNT) do |index|
+ snom_sip_account = {
+ :id => index,
+ :active => 'off',
+ :pname => '',
+ :pass => '',
+ :host => '',
+ :outbound => '',
+ :name => '',
+ :realname => '',
+ :idle_text => '',
+ }
+ @sip_accounts.push(snom_sip_account)
+ end
+
+ @softkeys.length().upto(MAX_SOFTKEYS_COUNT) do |index|
+ @softkeys.push({:label => "", :data => "none"})
+ end
+
+ @state_settings_url = "#{request.protocol}#{request.host_with_port}/config_snom/#{@phone.id}/state_settings.xml"
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render
+ }
+ }
+ end
+
+ def idle_screen
+
+ snom_360_bg = 'Qk0+BAAAAAAAAD4AAAAoAAAAgAAAAEAAAAABAAEAAAAAAAAEAAATCwAAEwsAAAIAAAACAAAA////
+AAAAAAAAAAAAAAAAAAAAAbbZxzbbAAAAAAAAAAAAAAG222222wAAAAAAAAAAAAAB9ttttt8AAAAA
+AAAAAAAAAbbbbbbbAAAAAAAAAAAAAAG222222wAAAAAAAAAAAAABttttttsAAAAAAAAAAAAAAOPx
+xx+OAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAkkkkkkkkkkkkkkAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAJJJJJJJJJJJJJJAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAACSSSSSSSSSSSSSQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAA'
+
+ @phone_xml_object = {
+ :image => {
+ :data => snom_360_bg,
+ :location_x => 0,
+ :location_y => 0,
+ :invert => 0
+ },
+ :clock => {
+ :location_x => 128,
+ :location_y => 0,
+ },
+ :date => {
+ :location_x => 100,
+ :location_y => 40,
+ },
+ :line => {
+ :location_x => 0,
+ :location_y => 0,
+ },
+ }
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render
+ }
+ }
+ end
+
+ def log_in
+
+ base_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.split("?")[0]}"
+ exit_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.rpartition("/")[0]}/exit.xml"
+
+ log_in_number = params[:log_in].to_s.gsub(/[^0-9]/,'')
+ pin = params[:pin].to_s.gsub(/[^0-9]/,'')
+
+ if ! params[:user].blank?
+ user = User.where(:id => params[:user].to_i).first
+ phone_number = PhoneNumber.where(:number => log_in_number, :phone_numberable_type => 'SipAccount').first
+ if phone_number
+ sip_account = phone_number.phone_numberable
+ end
+ elsif ! params[:log_in].blank?
+ phone_number = PhoneNumber.where(:number => log_in_number, :phone_numberable_type => 'SipAccount').first
+ if phone_number && phone_number.phone_numberable && phone_number.phone_numberable.sip_accountable && phone_number.phone_numberable.sip_accountable_type == 'User'
+ user = phone_number.phone_numberable.sip_accountable
+ end
+ end
+
+ @phone_xml_object = {
+ :name => "snom_phone_text",
+ :title => "Error",
+ :prompt => "Log in",
+ :text => 'Log in failed!',
+ :fetch_url => base_url,
+ :fetch_mil => '2000',
+ }
+
+ if ! user
+ @phone_xml_object = {
+ :name => "snom_phone_input",
+ :title => "Log In",
+ :prompt => "Log In",
+ :url => base_url,
+ :display_name => "Log In",
+ :query_string_param => "log_in",
+ :default_value => log_in_number,
+ :input_flags => "n",
+ :softkeys => [
+ {:name => "F1", :label => "Exit", :url => exit_url}
+ ]
+ }
+ elsif pin.blank?
+ @phone_xml_object = {
+ :name => "snom_phone_input",
+ :title => "PIN",
+ :prompt => "PIN",
+ :url => base_url,
+ :display_name => "PIN",
+ :query_string_param => "user=#{user.id}&log_in=#{log_in_number}&pin",
+ :default_value => "",
+ :input_flags => "pn",
+ :softkeys => [
+ {:name => "F1", :label => "Exit", :url => exit_url}
+ ]
+ }
+ elsif user.authenticate_by_pin?(pin)
+ if @phone.user_login(user, sip_account)
+ @phone_xml_object = {
+ :name => "snom_phone_text",
+ :title => "Log in successful",
+ :prompt => "Log in",
+ :text => "#{user.to_s} logged in",
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ end
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+ end
+
+ def log_out
+ if ! @phone
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Phone not found -->",
+ )
+ return
+ end
+
+ exit_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.rpartition("/")[0]}/exit.xml"
+
+ if @phone.user_logout()
+ @phone_xml_object = {
+ :name => "snom_phone_text",
+ :title => "Log out successful",
+ :prompt => "Log out",
+ :text => 'Log out successful',
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ else
+ @phone_xml_object = {
+ :name => "snom_phone_text",
+ :title => "Error",
+ :prompt => "Log out",
+ :text => 'Log out failed!',
+ :fetch_url => exit_url,
+ :fetch_mil => '2000',
+ }
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+ end
+
+ def phone_book
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ @phone_xml_object = {
+ :name => 'snom_phone_directory',
+ :title => "$(lang:menu100_phone_book) #{@dialpad_keys}".strip,
+ :entries => [],
+ :softkeys => [],
+ }
+
+ phone_books = Array.new()
+ phone_books = phone_books + @sip_account.sip_accountable.try(:phone_books).all
+ if @sip_account.sip_accountable.class == User
+ phone_books = phone_books + @sip_account.sip_accountable.try(:current_tenant).try(:phone_books).all
+ end
+
+ phone_book_ids = Array.new()
+ phone_books.each do |phone_book|
+ phone_book_ids << phone_book.id
+ end
+
+ PhoneBookEntry.where(:phone_book_id => phone_book_ids).order(:last_name).order(:first_name).limit(MAX_DIRECTORY_ENTRIES).each do |phone_book_entry|
+ if phone_book_entry.phone_numbers.count > 1
+ @phone_xml_object[:entries] << { :text => phone_book_entry.to_s, :number => phone_book_entry.phone_numbers.first }
+ end
+ phone_book_entry.phone_numbers.each do |phone_number|
+ if phone_book_entry.phone_numbers.count > 1
+ entry_name = " #{phone_number.name} #{phone_number.number}"
+ else
+ entry_name = "#{phone_book_entry.to_s} #{phone_number.number}"
+ end
+
+ @phone_xml_object[:entries] << { :text => entry_name, :number => phone_number.number }
+ end
+ end
+
+ base_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.split("?")[0]}"
+ phone_book_url = "#{base_url}?type=#{@type.to_s}"
+ for key_id in (0..9)
+ @phone_xml_object[:softkeys] << {:name => key_id, :url => "#{phone_book_url}&keys=#{@dialpad_keys.to_s}#{key_id}" }
+ end
+ @phone_xml_object[:softkeys] << {:name => '*', :url => "#{phone_book_url}&keys=#{@dialpad_keys.to_s[0..-2]}" }
+ @phone_xml_object[:softkeys] << {:name => '#', :url => "#{phone_book_url}&keys=" }
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+
+ end
+
+ def call_history
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ if ['dialed', 'missed', 'received'].include? @type
+ @phone_xml_object = {
+ :name => "snom_phone_directory",
+ :title => "$(lang:menu100_call_lists) - #{@type.to_s.camelize}",
+ :entries => []
+ }
+
+ if @type == 'missed'
+ hunt_group_member_ids = PhoneNumber.where(:phone_numberable_type => 'HuntGroupMember', :number => @sip_account.phone_numbers.map {|a| a.number}).map {|a| a.phone_numberable_id}
+ hunt_group_ids = HuntGroupMember.where(:id => hunt_group_member_ids, :active => true).map {|a| a.hunt_group_id}
+ calls = CallHistory.where('entry_type = ? AND ((call_historyable_type = "SipAccount" AND call_historyable_id = ?) OR (call_historyable_type = "HuntGroup" AND call_historyable_id IN (?)))', @type, @sip_account.id, hunt_group_ids).order('start_stamp DESC').limit(MAX_DIRECTORY_ENTRIES)
+ else
+ calls = @sip_account.call_histories.where(:entry_type => @type).order('start_stamp DESC').limit(MAX_DIRECTORY_ENTRIES)
+ end
+
+ calls.each do |call|
+ display_name = call.display_name
+ phone_number = call.display_number
+ phone_book_entry = call.phone_book_entry_by_number(phone_number)
+ if display_name.blank?
+ display_name = phone_book_entry.to_s
+ end
+
+ @phone_xml_object[:entries].push({
+ :selected => false,
+ :number => phone_number,
+ :text => "#{call_date_compact(call.start_stamp)} #{display_name} #{call.display_number}",
+ })
+ end
+ else
+ base_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.split("?")[0]}"
+ @phone_xml_object = {
+ :name => 'snom_phone_menu',
+ :title => '$(lang:menu100_call_lists)',
+ :entries => [
+ {:text => '$(lang:list_missed)', :url => "#{base_url}?&type=missed", :selected => false},
+ {:text => '$(lang:list_taken)', :url => "#{base_url}?&type=received", :selected => false},
+ {:text => '$(lang:list_dialed)', :url => "#{base_url}?&type=dialed", :selected => false},
+ ]
+ }
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+
+ end
+
+ def state_settings
+ @base_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.rpartition("/")[0]}"
+
+ @sip_account_ids = Array.new()
+ @phone.sip_accounts.each do |sip_account|
+ if (sip_account.sip_accountable_type == @phone.phoneable_type) and (sip_account.sip_accountable_id == @phone.phoneable_id)
+ @sip_account_ids.push(sip_account.id)
+ end
+ end
+
+ if @phone.hot_deskable
+ @enable_login = true
+ if @phone.phoneable_type != 'Tenant'
+ @enable_logout = true
+ end
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render
+ }
+ }
+ end
+
+ def call_forwarding
+ if ! params[:type].blank?
+ @type = params[:type]
+ end
+
+ if ! params[:function].blank?
+ @function = params[:function]
+ end
+
+ if ! params[:id].blank?
+ @call_forwarding_id = params[:id].to_i
+ end
+
+ if ! params[:sip_account].blank?
+ @sip_account = SipAccount.where({ :id => params[:sip_account].to_i }).first
+ end
+
+ if ! params[:account].blank?
+ @sip_account = SipAccount.where({ :id => params[:account].to_i }).first
+ end
+
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ exit_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.rpartition("/")[0]}/exit.xml"
+
+ if @function == 'toggle'
+ if @call_forwarding_id
+ call_forwarding = @sip_account.call_forwards.where(:id => @call_forwarding_id).first
+
+ if !call_forwarding and @sip_account.softkeys.where(:call_forward_id => @call_forwarding_id).count > 0
+ call_forwarding = CallForward.where(:id => @call_forwarding_id).first
+ end
+
+ if call_forwarding
+ call_forwarding.toggle
+ end
+ elsif @type
+ call_forwarding = @sip_account.call_forwarding_toggle(@type)
+ end
+ if !call_forwarding
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Call forwarding not set: #{@sip_account.errors.messages.inspect} -->",
+ )
+ return
+ end
+
+ if !call_forwarding.errors.blank?
+ error_messages = Array.new()
+ call_forwarding.errors.messages.each_pair do |key, message|
+ error_messages.push(message.join(';'))
+ end
+ @phone_xml_object = {
+ :name => 'snom_phone_text',
+ :title => t("call_forwards.name"),
+ :prompt => t("call_forwards.name"),
+ :text => "ERROR #{error_messages.join(',')} #{call_forwarding.to_s})",
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ elsif call_forwarding.active
+ @phone_xml_object = {
+ :name => 'snom_phone_text',
+ :title => t("call_forwards.name"),
+ :prompt => t("call_forwards.name"),
+ :text => "ON #{call_forwarding.to_s})",
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ else
+ @phone_xml_object = {
+ :name => 'snom_phone_text',
+ :title => t("call_forwards.name"),
+ :prompt => t("call_forwards.name"),
+ :text => "OFF #{call_forwarding.to_s}",
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ end
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+ end
+
+ def hunt_group
+ if ! params[:function].blank?
+ @function = params[:function]
+ end
+
+ if ! params[:sip_account].blank?
+ @sip_account = SipAccount.where({ :id => params[:sip_account].to_i }).first
+ end
+
+ if ! params[:group].blank?
+ @hunt_group = HuntGroup.where({ :id => params[:group].to_i }).first
+ end
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ if ! @hunt_group
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- HuntGroup not found -->",
+ )
+ return
+ end
+
+ if ! params[:account].blank?
+ hunt_group_member = @hunt_group.hunt_group_members.where({ :id => params[:account].to_i }).first
+ end
+
+ if ! hunt_group_member
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- HuntGroupMember not found -->",
+ )
+ return
+ end
+
+ exit_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.rpartition("/")[0]}/exit.xml"
+
+ if @function == 'toggle'
+ if hunt_group_member.can_switch_status_itself == true
+ if hunt_group_member.active
+ hunt_group_member.active = false
+ else
+ hunt_group_member.active = true
+ end
+
+ if ! hunt_group_member.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{hunt_group_member.errors.inspect} -->",
+ )
+ return
+ end
+ end
+
+ if hunt_group_member.active
+ @phone_xml_object = {
+ :name => 'snom_phone_text',
+ :title => 'Hunt Group',
+ :prompt => 'Hunt Group',
+ :text => "#{@hunt_group.name} on",
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ else
+ @phone_xml_object = {
+ :name => 'snom_phone_text',
+ :title => 'Hunt Group',
+ :prompt => 'Hunt Group',
+ :text => "#{@hunt_group.name} off",
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+ end
+ end
+
+ def acd
+ if ! params[:function].blank?
+ @function = params[:function]
+ end
+
+ if ! params[:sip_account].blank?
+ @sip_account = SipAccount.where({ :id => params[:sip_account].to_i }).first
+ end
+
+ if ! params[:acd].blank?
+ @acd = AutomaticCallDistributor.where({ :id => params[:acd].to_i }).first
+ end
+
+ if ! @sip_account
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- SipAccount not found -->",
+ )
+ return
+ end
+
+ if ! @acd
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- AutomaticCallDistributor not found -->",
+ )
+ return
+ end
+
+ if ! params[:agent].blank?
+ acd_agent = @acd.acd_agents.where({ :id => params[:agent].to_i }).first
+ end
+
+ if ! acd_agent
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- ACD Agent not found -->",
+ )
+ return
+ end
+
+ exit_url = "#{request.protocol}#{request.host_with_port}#{request.fullpath.rpartition("/")[0]}/exit.xml"
+
+ if @function == 'toggle'
+ if acd_agent.status == 'active'
+ acd_agent.status = 'inactive'
+ else
+ acd_agent.status = 'active'
+ end
+
+ if ! acd_agent.save
+ render(
+ :status => 500,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- #{acd_agent.errors.inspect} -->",
+ )
+ return
+ end
+
+ if acd_agent.status == 'active'
+ @phone_xml_object = {
+ :name => 'snom_phone_text',
+ :title => 'ACD',
+ :prompt => 'ACD',
+ :text => "#{@acd.name} on",
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ else
+ @phone_xml_object = {
+ :name => 'snom_phone_text',
+ :title => 'ACD',
+ :prompt => 'ACD',
+ :text => "#{@acd.name} off",
+ :fetch_url => exit_url,
+ :fetch_mil => '1000',
+ }
+ end
+
+ respond_to { |format|
+ format.any {
+ self.formats = [ :xml ]
+ render :action => "_#{@phone_xml_object[:name]}"
+ }
+ }
+ end
+ end
+
+ def exit
+ render(
+ :status => 200,
+ :layout => false,
+ :content_type => 'text/xml',
+ :text => "<exit />",
+ )
+ end
+
+ def call_date_compact(date)
+ if date.strftime('%Y%m%d') == DateTime::now.strftime('%Y%m%d')
+ return date.strftime('%H:%M')
+ end
+ return date.strftime('%d.%m %H:%M')
+ end
+
+end
diff --git a/app/controllers/fax_accounts_controller.rb b/app/controllers/fax_accounts_controller.rb
new file mode 100644
index 0000000..ce03bc5
--- /dev/null
+++ b/app/controllers/fax_accounts_controller.rb
@@ -0,0 +1,82 @@
+class FaxAccountsController < ApplicationController
+ load_resource :user
+ load_resource :user_group
+ load_and_authorize_resource :fax_account, :through => [:user, :user_group]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @fax_account = @parent.fax_accounts.build
+ @fax_account.name = generate_a_new_name(@parent, @fax_account)
+ @fax_account.days_till_auto_delete = DAYS_TILL_AUTO_DELETE
+ @fax_account.retries = DEFAULT_NUMBER_OF_RETRIES
+ @fax_account.station_id = @parent.to_s
+ @fax_account.phone_numbers.build
+ if @parent.class == User && !@parent.email.blank?
+ @fax_account.email = @parent.email
+ end
+ end
+
+ def create
+ @fax_account = @parent.fax_accounts.build(params[:fax_account])
+ if @fax_account.save
+ m = method( :"#{@parent.class.name.underscore}_fax_account_path" )
+ redirect_to m.( @parent, @fax_account ), :notice => t('fax_accounts.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @fax_account.update_attributes(params[:fax_account])
+ m = method( :"#{@parent.class.name.underscore}_fax_account_path" )
+ redirect_to m.( @parent, @fax_account ), :notice => t('fax_accounts.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @fax_account.destroy
+ m = method( :"#{@parent.class.name.underscore}_fax_accounts_url" )
+ redirect_to m.( @parent ), :notice => t('fax_accounts.controller.successfuly_destroyed')
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @user || @user_group
+ authorize! :read, @parent
+ end
+
+ def spread_breadcrumbs
+ if @parent && @parent.class == User
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t("fax_accounts.index.page_title"), user_fax_accounts_path(@user)
+ if @fax_account && !@fax_account.new_record?
+ add_breadcrumb @fax_account, user_fax_account_path(@user, @fax_account)
+ end
+ end
+
+ if @parent && @parent.class == UserGroup
+ @user_group = @parent
+ add_breadcrumb t("user_groups.index.page_title"), tenant_user_groups_path(@user_group.tenant)
+ add_breadcrumb @user_group, tenant_user_group_path(@user_group.tenant, @user_group)
+ add_breadcrumb t("fax_accounts.index.page_title"), user_group_fax_accounts_path(@user_group)
+ if @fax_account && !@fax_account.new_record?
+ add_breadcrumb @fax_account, user_group_fax_account_path(@user_group, @fax_account)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/fax_documents_controller.rb b/app/controllers/fax_documents_controller.rb
new file mode 100644
index 0000000..eff9604
--- /dev/null
+++ b/app/controllers/fax_documents_controller.rb
@@ -0,0 +1,82 @@
+class FaxDocumentsController < ApplicationController
+ load_and_authorize_resource :fax_account
+ load_and_authorize_resource :fax_document, :through => [:fax_account]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ @fax_documents = @fax_documents.order(:created_at).reverse_order
+ end
+
+ def show
+ respond_to do |format|
+ @fax_document = FaxDocument.find(params[:id])
+ format.html
+ format.xml { render :xml => @fax_document }
+ format.pdf {
+ caller_number = @fax_document.caller_id_number.to_s.gsub(/[^0-9]/, '')
+ if caller_number.blank?
+ caller_number = 'anonymous'
+ end
+
+ if @fax_document.document.path
+ send_file @fax_document.document.path, :type => "application/pdf",
+ :filename => "#{@fax_document.created_at.strftime('%Y%m%d-%H%M%S')}-#{caller_number}.pdf"
+ else
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Document not found -->",
+ )
+ end
+ }
+ end
+ end
+
+ def new
+ @fax_document = @fax_account.fax_documents.build
+ @phone_number = @fax_document.build_destination_phone_number
+ end
+
+ def create
+ @fax_document = @fax_account.fax_documents.build(params[:fax_document])
+ @fax_document.retry_counter = @fax_account.retries
+ if @fax_document.save
+ @fax_document.queue_for_sending!
+ redirect_to fax_account_fax_document_path(@fax_document.fax_account, @fax_document), :notice => t('fax_documents.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def destroy
+ @fax_account = FaxAccount.find(params[:fax_account_id])
+ @fax_document = @fax_account.fax_documents.find(params[:id])
+ @fax_document.destroy
+ redirect_to fax_account_fax_documents_url, :notice => t('fax_documents.controller.successfuly_destroyed')
+ end
+
+ private
+ def spread_breadcrumbs
+ breadcrumbs = []
+ breadcrumbs = case @fax_account.fax_accountable.class.to_s
+ when 'User' ; [
+ [@fax_account.fax_accountable.to_s, user_path(@fax_account.fax_accountable)],
+ [t('fax_accounts.name').pluralize, user_fax_accounts_path(@fax_account.fax_accountable)],
+ [t('fax_documents.name').pluralize, fax_account_fax_documents_path(@fax_account)],
+ ]
+ when 'UserGroup' ; [
+ [@fax_account.fax_accountable, user_group_path(@fax_account.fax_accountable)],
+ [t('fax_accounts.name').pluralize, user_group_fax_accounts_path(@fax_account.fax_accountable)],
+ [t('fax_documents.name').pluralize, fax_account_fax_documents_path(@fax_account)],
+ ]
+ end
+ if !breadcrumbs.blank?
+ breadcrumbs.each do |breadcrumb|
+ add_breadcrumb breadcrumb[0], breadcrumb[1]
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/freeswitch_voicemail_msgs_controller.rb b/app/controllers/freeswitch_voicemail_msgs_controller.rb
new file mode 100644
index 0000000..085db3d
--- /dev/null
+++ b/app/controllers/freeswitch_voicemail_msgs_controller.rb
@@ -0,0 +1,7 @@
+class FreeswitchVoicemailMsgsController < ApplicationController
+ load_and_authorize_resource :sip_account
+ load_and_authorize_resource :freeswitch_voicemail_msg, :through => [:sip_account]
+
+ def index
+ end
+end
diff --git a/app/controllers/gemeinschaft_setups_controller.rb b/app/controllers/gemeinschaft_setups_controller.rb
new file mode 100644
index 0000000..cafb8a3
--- /dev/null
+++ b/app/controllers/gemeinschaft_setups_controller.rb
@@ -0,0 +1,61 @@
+class GemeinschaftSetupsController < ApplicationController
+ load_and_authorize_resource :gemeinschaft_setup
+
+ skip_before_filter :go_to_setup_if_new_installation
+ # before_filter :redirect_if_not_a_fresh_installation
+
+ def new
+ @user = @gemeinschaft_setup.build_user(
+ :user_name => t('gemeinschaft_setups.initial_setup.admin_name'),
+ :male => true,
+ :email => 'admin@localhost',
+ )
+ @sip_domain = @gemeinschaft_setup.build_sip_domain(
+ :host => guess_local_host(),
+ :realm => guess_local_host(),
+ )
+ @gemeinschaft_setup.country = Country.find_by_name('Germany')
+ @gemeinschaft_setup.language = Language.find_by_name('Deutsch')
+ end
+
+ def create
+ if @gemeinschaft_setup.save
+ super_tenant = Tenant.create(
+ :name => SUPER_TENANT_NAME,
+ :country_id => @gemeinschaft_setup.country.id,
+ :language_id => @gemeinschaft_setup.language_id,
+ :description => t('gemeinschaft_setups.initial_setup.super_tenant_description'),
+ )
+
+ # Admin
+ user = @gemeinschaft_setup.user
+ super_tenant.tenant_memberships.create(:user_id => user.id)
+ user.update_attributes(:current_tenant_id => super_tenant.id)
+
+ # Create the Super-Tenant's group:
+ super_tenant_super_admin_group = super_tenant.user_groups.create(:name => t('gemeinschaft_setups.initial_setup.super_admin_group_name'))
+ super_tenant_super_admin_group.user_group_memberships.create(:user_id => user.id)
+
+ # Auto-Login:
+ session[:user_id] = user.id
+
+ # Redirect to the user
+ redirect_to new_tenant_url, :notice => t('gemeinschaft_setups.initial_setup.successful_setup')
+ else
+ render :new
+ end
+ end
+
+ private
+
+ def redirect_if_not_a_fresh_installation
+ if GemeinschaftSetup.all.count > 0
+ if current_user
+ redirect_to root_url , :alert => t('gemeinschaft_setups.initial_setup.access_denied_only_available_on_a_new_system')
+ else
+ redirect_to log_in_path , :alert => t('gemeinschaft_setups.initial_setup.access_denied_only_available_on_a_new_system')
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/gs_cluster_sync_log_entries_controller.rb b/app/controllers/gs_cluster_sync_log_entries_controller.rb
new file mode 100644
index 0000000..3e65037
--- /dev/null
+++ b/app/controllers/gs_cluster_sync_log_entries_controller.rb
@@ -0,0 +1,25 @@
+class GsClusterSyncLogEntriesController < ApplicationController
+
+ # GET /gs_cluster_sync_log_entries/new.json
+ def new
+ @gs_cluster_sync_log_entry = GsClusterSyncLogEntry.new
+
+ respond_to do |format|
+ format.json { render json: @gs_cluster_sync_log_entry }
+ end
+ end
+
+ # POST /gs_cluster_sync_log_entries.json
+ def create
+ @gs_cluster_sync_log_entry = GsClusterSyncLogEntry.new(params[:gs_cluster_sync_log_entry])
+
+ respond_to do |format|
+ if @gs_cluster_sync_log_entry.save
+ format.json { render json: @gs_cluster_sync_log_entry, status: :created, location: @gs_cluster_sync_log_entry }
+ else
+ format.json { render json: @gs_cluster_sync_log_entry.errors, status: :unprocessable_entity }
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/gs_nodes_controller.rb b/app/controllers/gs_nodes_controller.rb
new file mode 100644
index 0000000..3667775
--- /dev/null
+++ b/app/controllers/gs_nodes_controller.rb
@@ -0,0 +1,170 @@
+class GsNodesController < ApplicationController
+
+ load_and_authorize_resource :gs_node, :only => [:index, :show, :new, :create, :edit, :update, :destroy]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+
+ end
+
+ def show
+
+ end
+
+ def new
+ @gs_node = GsNode.new
+ @gs_node.push_updates_to = true
+ @gs_node.accepts_updates_from = true
+ @gs_node.element_name = 'gs_cluster_sync_log_entry'
+ end
+
+ def create
+ @gs_node = GsNode.new(params[:gs_node])
+ if @gs_node.save
+ redirect_to @gs_node, :notice => t('gs_nodes.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ @gs_node = GsNode.find(params[:id])
+ end
+
+ def update
+ @gs_node = GsNode.find(params[:id])
+ if @gs_node.update_attributes(params[:gs_node])
+ redirect_to @gs_node, :notice => t('gs_nodes.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @gs_node = GsNode.find(params[:id])
+ @gs_node.destroy
+ redirect_to gs_nodes_url, :notice => t('gs_nodes.controller.successfuly_destroyed')
+ end
+
+ def sync
+ if !GsNode.where(:ip_address => request.remote_ip).first
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Node not found -->",
+ )
+ return
+ end
+
+ if ! params[:newer].blank?
+ @newer_as = Time.at(params[:newer].to_i)
+ else
+ @newer_as = Time.at(0)
+ end
+
+ if ! params[:class].blank?
+ @request_class = params[:class].to_s
+ else
+ @request_class = '';
+ end
+
+ @node = GsNode.where(:ip_address => HOMEBASE_IP_ADDRESS).first
+
+ if @request_class.blank? || @request_class == "tenants"
+ @tenants = Tenant.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "user_groups"
+ @user_groups = UserGroup.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "users"
+ @users = User.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "user_group_memberships"
+ @user_group_memberships = UserGroupMembership.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "sip_accounts"
+ @sip_accounts = SipAccount.where('updated_at > ?',@newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "conferences"
+ @conferences = Conference.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "fax_accounts"
+ @fax_accounts = FaxAccount.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "phone_books"
+ @phone_books = PhoneBook.where('updated_at > ?',@newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "phone_book_entries"
+ @phone_book_entries = PhoneBookEntry.where('updated_at > ?',@newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "phone_numbers"
+ @phone_numbers = PhoneNumber.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "call_forwards"
+ @call_forwards = CallForward.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "softkeys"
+ @softkeys = Softkey.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "ringtones"
+ @ringtones = Ringtone.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "conference_invitees"
+ @conference_invitees = ConferenceInvitee.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class == "fax_documents"
+ @fax_documents = FaxDocument.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class == "call_histories"
+ @call_histories = CallHistory.where('updated_at > ?', @newer_as)
+ end
+
+ if @request_class.blank? || @request_class == "deleted_items"
+ @deleted_items = Array.new
+ deleted_items_log = GsClusterSyncLogEntry.where('action = "destroy" AND updated_at > ?', @newer_as)
+ deleted_items_log.each do |deleted_item_log_entry|
+ content = JSON(deleted_item_log_entry.content)
+ content['class_name'] = deleted_item_log_entry.class_name
+ if content['uuid']
+ @deleted_items << content
+ end
+ end
+ end
+
+ if params[:image].to_s == 'false'
+ @image_include = false
+ else
+ @image_include = true
+ end
+
+ end
+
+ private
+
+ def spread_breadcrumbs
+ if @gs_node
+ add_breadcrumb t("gs_nodes.index.page_title"), gs_nodes_path
+
+ if @gs_node && !@gs_node.new_record?
+ add_breadcrumb @gs_node, gs_node_path(@gs_node)
+ end
+ end
+ end
+end
diff --git a/app/controllers/gui_functions_controller.rb b/app/controllers/gui_functions_controller.rb
new file mode 100644
index 0000000..2ab2c5e
--- /dev/null
+++ b/app/controllers/gui_functions_controller.rb
@@ -0,0 +1,73 @@
+class GuiFunctionsController < ApplicationController
+ before_filter :load_user_groups
+ before_filter :spread_breadcrumbs
+
+ def index
+ @gui_functions = GuiFunction.order(:category, :name)
+ end
+
+ def show
+ @gui_function = GuiFunction.find(params[:id])
+ end
+
+ def new
+ @gui_function = GuiFunction.new
+
+ @user_groups.each do |user_group|
+ if @gui_function.user_groups.where(:id => user_group.id).count == 0
+ @gui_function.gui_function_memberships.build(:user_group_id => user_group.id, :activated => true)
+ end
+ end
+ end
+
+ def create
+ @gui_function = GuiFunction.new(params[:gui_function])
+
+ if @gui_function.save
+ redirect_to @gui_function, :notice => t('gui_functions.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ @gui_function = GuiFunction.find(params[:id])
+ @user_groups.each do |user_group|
+ if @gui_function.user_groups.where(:id => user_group.id).count == 0
+ @gui_function.gui_function_memberships.build(:user_group_id => user_group.id, :activated => true)
+ end
+ end
+ end
+
+ def update
+ @gui_function = GuiFunction.find(params[:id])
+ if @gui_function.update_attributes(params[:gui_function])
+ redirect_to @gui_function, :notice => t('gui_functions.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @gui_function = GuiFunction.find(params[:id])
+ @gui_function.destroy
+ redirect_to gui_functions_url, :notice => t('gui_functions.controller.successfuly_destroyed')
+ end
+
+ private
+ def load_user_groups
+ @user_groups = Tenant.find(@current_user.current_tenant).user_groups.order(:position)
+ end
+
+ def spread_breadcrumbs
+ if @tenant
+ add_breadcrumb t("user_groups.index.page_title"), tenant_user_groups_path(@tenant)
+ if @user_group && !@user_group.new_record?
+ add_breadcrumb @user_group, tenant_user_group_path(@tenant, @user_group)
+ end
+ end
+
+ add_breadcrumb t("gui_functions.index.page_title"), gui_functions_path
+ end
+
+end
diff --git a/app/controllers/hunt_group_members_controller.rb b/app/controllers/hunt_group_members_controller.rb
new file mode 100644
index 0000000..90206ee
--- /dev/null
+++ b/app/controllers/hunt_group_members_controller.rb
@@ -0,0 +1,67 @@
+class HuntGroupMembersController < ApplicationController
+ load_and_authorize_resource :hunt_group
+ load_and_authorize_resource :hunt_group_member, :through => [:hunt_group]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ if params[:active]
+ if params[:active].downcase == 'true'
+ @hunt_group_members = @hunt_group_members.where(:active => true)
+ elsif params[:active].downcase == 'false'
+ @hunt_group_members = @hunt_group_members.where(:active => false)
+ end
+ end
+ end
+
+ def show
+ end
+
+ def new
+ @hunt_group_member = @hunt_group.hunt_group_members.build
+
+ i = @hunt_group.hunt_group_members.count
+ loop do
+ i += 1
+ break unless @hunt_group.hunt_group_members.where(:name => "#{t('hunt_group_members.name')} #{i}").count > 0
+ end
+ @hunt_group_member.name = "#{t('hunt_group_members.name')} #{i}"
+ @hunt_group_member.active = true
+ @hunt_group_member.can_switch_status_itself = true
+ end
+
+ def create
+ @hunt_group_member = @hunt_group.hunt_group_members.build(params[:hunt_group_member])
+ if @hunt_group_member.save
+ redirect_to hunt_group_hunt_group_member_path(@hunt_group, @hunt_group_member), :notice => t('hunt_group_members.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @hunt_group_member.update_attributes(params[:hunt_group_member])
+ redirect_to hunt_group_hunt_group_member_path(@hunt_group, @hunt_group_member), :notice => t('hunt_group_members.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @hunt_group_member.destroy
+ redirect_to hunt_group_hunt_group_members_path(@hunt_group), :notice => t('hunt_group_members.controller.successfuly_destroyed')
+ end
+
+ def spread_breadcrumbs
+ add_breadcrumb t("hunt_groups.index.page_title"), tenant_hunt_groups_path(@hunt_group.tenant)
+ add_breadcrumb @hunt_group, tenant_hunt_group_path(@hunt_group.tenant, @hunt_group)
+ add_breadcrumb t("hunt_group_members.index.page_title"), hunt_group_hunt_group_members_path(@hunt_group)
+ if @hunt_group_member && !@hunt_group_member.new_record?
+ add_breadcrumb @hunt_group_member, hunt_group_hunt_group_member_path(@hunt_group, @hunt_group_member)
+ end
+ end
+
+end
diff --git a/app/controllers/hunt_groups_controller.rb b/app/controllers/hunt_groups_controller.rb
new file mode 100644
index 0000000..13a556a
--- /dev/null
+++ b/app/controllers/hunt_groups_controller.rb
@@ -0,0 +1,55 @@
+class HuntGroupsController < ApplicationController
+ load_and_authorize_resource :tenant
+ load_and_authorize_resource :hunt_group, :through => [:tenant]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ i = @tenant.hunt_groups.count
+ loop do
+ i += 1
+ break unless @tenant.hunt_groups.where(:name => "#{t('hunt_groups.name')} #{i}").count > 0
+ end
+ @hunt_group = @tenant.hunt_groups.build(:name => "#{t('hunt_groups.name')} #{i}")
+ end
+
+ def create
+ @hunt_group = @tenant.hunt_groups.build(params[:hunt_group])
+ if @hunt_group.save
+ redirect_to tenant_hunt_group_path(@tenant, @hunt_group), :notice => t('hunt_groups.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ @hunt_group = HuntGroup.find(params[:id])
+ if @hunt_group.update_attributes(params[:hunt_group])
+ redirect_to tenant_hunt_group_path(@tenant, @hunt_group), :notice => t('hunt_groups.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @hunt_group.destroy
+ redirect_to tenant_hunt_groups_path(@tenant), :notice => t('hunt_groups.controller.successfuly_destroyed')
+ end
+
+ private
+ def spread_breadcrumbs
+ add_breadcrumb t("hunt_groups.index.page_title"), tenant_hunt_groups_path(@tenant)
+ if @hunt_group && !@hunt_group.new_record?
+ add_breadcrumb @hunt_group, tenant_hunt_group_path(@tenant, @hunt_group)
+ end
+ end
+end
diff --git a/app/controllers/manufacturers_controller.rb b/app/controllers/manufacturers_controller.rb
new file mode 100644
index 0000000..1bcf9de
--- /dev/null
+++ b/app/controllers/manufacturers_controller.rb
@@ -0,0 +1,49 @@
+class ManufacturersController < ApplicationController
+ load_and_authorize_resource :manufacturer
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ end
+
+ def create
+ @manufacturer = Manufacturer.new(params[:manufacturer])
+ if @manufacturer.save
+ redirect_to @manufacturer, :notice => t('manufacturers.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @manufacturer.update_attributes(params[:manufacturer])
+ redirect_to @manufacturer, :notice => t('manufacturers.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @manufacturer.destroy
+ redirect_to manufacturers_url, :notice => t('manufacturers.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def spread_breadcrumbs
+ add_breadcrumb t("manufacturers.index.page_title"), manufacturers_path
+ if @manufacturer && !@manufacturer.new_record?
+ add_breadcrumb @manufacturer, manufacturer_path(@manufacturer)
+ end
+ end
+
+end
diff --git a/app/controllers/page_controller.rb b/app/controllers/page_controller.rb
new file mode 100644
index 0000000..1f37449
--- /dev/null
+++ b/app/controllers/page_controller.rb
@@ -0,0 +1,24 @@
+class PageController < ApplicationController
+ # load_and_authorize_resource :class => false
+ # CanCan doesn't work here really good because Page is not a resource.
+
+ before_filter :if_fresh_system_then_go_to_wizard
+ skip_before_filter :home_breadcrumb, :only => [:index]
+
+ def index;end
+ def conference;end
+
+ private
+ def if_fresh_system_then_go_to_wizard
+ if Tenant.count == 0 && User.count == 0
+ # This is a brand new system. We need to run a setup first.
+ redirect_to wizards_new_initial_setup_path
+ else
+ if current_user.nil?
+ # You need to login first.
+ redirect_to log_in_path, :alert => I18n.t('pages.controller.access_denied_login_first')
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/phone_book_entries_controller.rb b/app/controllers/phone_book_entries_controller.rb
new file mode 100644
index 0000000..823d50e
--- /dev/null
+++ b/app/controllers/phone_book_entries_controller.rb
@@ -0,0 +1,135 @@
+class PhoneBookEntriesController < ApplicationController
+ load_and_authorize_resource :phone_book
+ load_and_authorize_resource :phone_book_entry, :through => :phone_book, :shallow => true
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ # In case this is a search params[:q] or params[:name] will contain the query.
+ #
+ @query = params[:q]
+ @query ||= params[:name]
+ @query = @query.strip if @query
+
+ if !@query.blank?
+ if @query.match(/^\+?\d+$/) != nil
+ # Find by phone number
+ phone_book_entries_ids = @phone_book_entries.map{|entry| entry.id}
+ @found_phone_numbers = PhoneNumber.
+ where(:phone_numberable_type => 'PhoneBookEntry', :phone_numberable_id => phone_book_entries_ids).
+ where('number LIKE ?', "#{@query}%")
+ @search_result = @phone_book_entries.where(:id => @found_phone_numbers.map{|entry| entry.phone_numberable_id})
+ elsif @query.match(/^[\"\'](.*)[\"\']$/) != nil
+ # The User searched for =>'example'<= so he wants an EXACT search for that.
+ # This is the fasted and most accurate way of searching.
+ # The order to search is: last_name, first_name and organization.
+ # It stops searching as soon as it finds results.
+ #
+ @query = $1
+ @search_result = @phone_book_entries.where(:last_name => @query)
+ @search_result = @phone_book_entries.where(:first_name => @query) if @search_result.count == 0
+ @search_result = @phone_book_entries.where(:organization => @query) if @search_result.count == 0
+
+ @exact_search = true
+ else
+ # Search with SQL LIKE
+ #
+ @search_result = @phone_book_entries.
+ where( '( ( last_name LIKE ? ) OR ( first_name LIKE ? ) OR ( organization LIKE ? ) )',
+ "#{@query}%", "#{@query}%", "#{@query}%" )
+
+ @exact_search = false
+ end
+
+ # Let's have a run with our phonetic search.
+ #
+ phonetic_query = PhoneBookEntry.koelner_phonetik(@query)
+ @phonetic_search_result = @phone_book_entries.where(:last_name_phonetic => phonetic_query)
+ @phonetic_search_result = @phone_book_entries.where(:first_name_phonetic => phonetic_query) if @phonetic_search_result.count == 0
+ @phonetic_search_result = @phone_book_entries.where(:organization_phonetic => phonetic_query) if @phonetic_search_result.count == 0
+
+ if @phonetic_search_result.count == 0
+ # Let's try the search with SQL LIKE. Just in case.
+ #
+ @phonetic_search_result = @phone_book_entries.where( 'last_name_phonetic LIKE ?', "#{phonetic_query}%" )
+ @phonetic_search_result = @phone_book_entries.where( 'first_name_phonetic LIKE ?', "#{phonetic_query}%" ) if @phonetic_search_result.count == 0
+ @phonetic_search_result = @phone_book_entries.where( 'organization_phonetic LIKE ?', "#{phonetic_query}%" ) if @phonetic_search_result.count == 0
+ end
+
+ @phonetic_search = true if @phonetic_search_result.count > 0
+
+ @phone_book_entries = @search_result
+
+ if @phone_book_entries.count == 0 && @exact_search == false && @phonetic_search
+ @phone_book_entries = @phonetic_search_result
+ end
+ end
+
+ # Let's sort the results and do pagination.
+ #
+ @phone_book_entries = @phone_book_entries.
+ order([ :last_name, :first_name, :organization ]).
+ paginate(
+ :page => @pagination_page_number,
+ :per_page => DEFAULT_PAGINATION_ENTRIES_PER_PAGE
+ )
+ end
+
+ def show
+ end
+
+ def new
+ @phone_book_entry = @phone_book.phone_book_entries.build
+ @phone_book_entry.is_male = true
+ end
+
+ def create
+ @phone_book_entry = @phone_book.phone_book_entries.build( params[:phone_book_entry] )
+ if @phone_book_entry.save
+ redirect_to phone_book_phone_book_entry_path( @phone_book, @phone_book_entry ), :notice => t('phone_book_entries.controller.successfuly_created', :resource => @phone_book_entry)
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @phone_book_entry.update_attributes(params[:phone_book_entry])
+ redirect_to @phone_book_entry, :notice => t('phone_book_entries.controller.successfuly_updated', :resource => @phone_book_entry)
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @phone_book_entry.destroy
+ redirect_to phone_book_entries_url, :notice => t('phone_book_entries.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def spread_breadcrumbs
+ if @phone_book
+ if @phone_book.phone_bookable.class == Tenant
+ add_breadcrumb t("phone_books.index.page_title"), tenant_phone_books_path(@phone_book.phone_bookable)
+ add_breadcrumb @phone_book, tenant_phone_book_path(@phone_book.phone_bookable, @phone_book)
+ add_breadcrumb t("phone_book_entries.index.page_title"), phone_book_phone_book_entries_path(@phone_book)
+ end
+
+ if @phone_book.phone_bookable.class == User
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@phone_book.phone_bookable.current_tenant)
+ add_breadcrumb @phone_book.phone_bookable, tenant_user_path(@phone_book.phone_bookable.current_tenant, @phone_book.phone_bookable)
+ add_breadcrumb t("phone_books.index.page_title"), user_phone_books_path(@phone_book.phone_bookable)
+ add_breadcrumb @phone_book, user_phone_book_path(@phone_book.phone_bookable, @phone_book)
+ add_breadcrumb t("phone_book_entries.index.page_title"), phone_book_phone_book_entries_path(@phone_book)
+ end
+
+ if @phone_book_entry && !@phone_book_entry.new_record?
+ add_breadcrumb @phone_book_entry, phone_book_phone_book_entry_path(@phone_book, @phone_book_entry)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/phone_books_controller.rb b/app/controllers/phone_books_controller.rb
new file mode 100644
index 0000000..54e7889
--- /dev/null
+++ b/app/controllers/phone_books_controller.rb
@@ -0,0 +1,105 @@
+class PhoneBooksController < ApplicationController
+ load_resource :user
+ load_resource :user_group
+ load_resource :tenant
+ load_and_authorize_resource :phone_book, :through => [:user, :user_group, :tenant]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ @by_name = params[:name]
+
+ @pagination_page_number = params[:page].to_i
+ @pagination_page_number = 1 if @pagination_page_number < 1
+
+ if @by_name.blank?
+ @phone_book_entries = @phone_book.
+ phone_book_entries.
+ order([ :last_name, :first_name ]).
+ paginate(
+ :page => @pagination_page_number,
+ :per_page => DEFAULT_PAGINATION_ENTRIES_PER_PAGE
+ )
+ else
+ # search by name
+ @by_name = @by_name.
+ gsub( /[^A-Za-z0-9#]/, '' ).
+ gsub('*','?').
+ gsub('%','_').
+ gsub(/^#/,'').
+ upcase
+
+ @phone_book_entries = @phone_book.
+ phone_book_entries.
+ where( '( ( last_name LIKE ? ) OR ( first_name LIKE ? ) )', "#{@by_name}%", "#{@by_name}%" ).
+ order([ :last_name, :first_name ]).
+ paginate(
+ :page => @pagination_page_number,
+ :per_page => DEFAULT_PAGINATION_ENTRIES_PER_PAGE
+ )
+ end
+ end
+
+ def new
+ @phone_book = @parent.phone_books.build
+ @phone_book.name = generate_a_new_name(@parent, @phone_book)
+ end
+
+ def create
+ @phone_book = @parent.phone_books.build( params[:phone_book] )
+ if @phone_book.save
+ m = method( :"#{@parent.class.name.underscore}_phone_book_path" )
+ redirect_to m.( @parent, @phone_book ), :notice => t('phone_books.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @phone_book.update_attributes(params[:phone_book])
+ m = method( :"#{@parent.class.name.underscore}_phone_book_path" )
+ redirect_to m.( @parent, @phone_book ), :notice => t('phone_books.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @phone_book.destroy
+ m = method( :"#{@parent.class.name.underscore}_phone_books_url" )
+ redirect_to m.( @parent ), :notice => t('phone_books.controller.successfuly_destroyed')
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @user || @user_group || @tenant
+ authorize! :read, @parent
+ end
+
+ def spread_breadcrumbs
+ if @parent.class == Tenant
+ add_breadcrumb t("phone_books.index.page_title"), tenant_phone_books_path(@tenant)
+ if @phone_book && !@phone_book.new_record?
+ add_breadcrumb @phone_book, tenant_phone_book_path(@tenant, @phone_book)
+ end
+ end
+
+ if @parent.class == User
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t("phone_books.index.page_title"), user_phone_books_path(@user)
+ if @phone_book && !@phone_book.new_record?
+ add_breadcrumb @phone_book, user_phone_book_path(@user, @phone_book)
+ end
+ end
+
+ end
+
+end
diff --git a/app/controllers/phone_models_controller.rb b/app/controllers/phone_models_controller.rb
new file mode 100644
index 0000000..59facdf
--- /dev/null
+++ b/app/controllers/phone_models_controller.rb
@@ -0,0 +1,52 @@
+class PhoneModelsController < ApplicationController
+ load_and_authorize_resource :manufacturer
+ load_and_authorize_resource :phone_model, :through => [:manufacturer]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @phone_model = @manufacturer.phone_models.build
+ end
+
+ def create
+ @phone_model = @manufacturer.phone_models.build.new(params[:phone_model])
+ if @phone_model.save
+ redirect_to manufacturer_phone_model_path( @manufacturer, @phone_model ), :notice => t('phone_models.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @phone_model.update_attributes(params[:phone_model])
+ redirect_to manufacturer_phone_model_path( @manufacturer, @phone_model ), :notice => t('phone_models.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @phone_model.destroy
+ redirect_to manufacturer_phone_models_url( @manufacturer ), :notice => t('phone_models.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def spread_breadcrumbs
+ add_breadcrumb t("manufacturers.index.page_title"), manufacturers_path
+ add_breadcrumb @manufacturer, manufacturer_path(@manufacturer)
+ add_breadcrumb t("phone_models.index.page_title"), manufacturer_phone_models_path(@manufacturer)
+ if @phone_model && !@phone_model.new_record?
+ add_breadcrumb @phone_model, manufacturer_phone_model_path(@manufacturer, @phone_model)
+ end
+ end
+end
diff --git a/app/controllers/phone_number_ranges_controller.rb b/app/controllers/phone_number_ranges_controller.rb
new file mode 100644
index 0000000..a4e7238
--- /dev/null
+++ b/app/controllers/phone_number_ranges_controller.rb
@@ -0,0 +1,56 @@
+class PhoneNumberRangesController < ApplicationController
+ load_and_authorize_resource :tenant
+ load_and_authorize_resource :phone_number_range, :through => [:tenant]
+
+ before_filter :set_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @phone_number_range = @parent.phone_number_ranges.build
+ end
+
+ def create
+ @phone_number_range = @parent.phone_number_ranges.build(params[:phone_number_range])
+ if @phone_number_range.save
+ redirect_to @phone_number_range, :notice => t('phone_number_ranges.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @phone_number_range.update_attributes(params[:phone_number_range])
+ redirect_to @phone_number_range, :notice => t('phone_number_ranges.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @phone_number_range.destroy
+ redirect_to phone_number_ranges_url, :notice => t('phone_number_ranges.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def set_parent
+ @parent = @tenant
+ end
+
+ def spread_breadcrumbs
+ add_breadcrumb t("phone_number_ranges.index.page_title"), tenant_phone_number_ranges_path(@tenant)
+ if @phone_number_range && !@phone_number_range.new_record?
+ add_breadcrumb t("phone_number_ranges.ranges.#{@phone_number_range}.label"), tenant_phone_number_range_path(@tenant, @phone_number_range)
+ end
+ end
+
+end
diff --git a/app/controllers/phone_numbers_controller.rb b/app/controllers/phone_numbers_controller.rb
new file mode 100644
index 0000000..065934c
--- /dev/null
+++ b/app/controllers/phone_numbers_controller.rb
@@ -0,0 +1,226 @@
+class PhoneNumbersController < ApplicationController
+ load_resource :phone_book_entry
+ load_resource :sip_account
+ load_resource :conference
+ load_resource :fax_account
+ load_resource :phone_number_range
+ load_resource :callthrough
+ load_resource :whitelist
+ load_resource :access_authorization
+ load_resource :hunt_group
+ load_resource :hunt_group_member
+ load_resource :automatic_call_distributor
+ load_and_authorize_resource :phone_number, :through => [:phone_book_entry, :sip_account, :conference,
+ :fax_account, :phone_number_range, :callthrough,
+ :whitelist, :access_authorization, :hunt_group,
+ :hunt_group_member, :automatic_call_distributor]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ @ringtoneable_classes = {
+ 'SipAccount' => true,
+ 'HuntGroup' => true,
+ 'AutomaticCallDistributor' => true,
+ 'PhoneBookEntry' => true,
+ }
+ @forwardable_classes = {
+ 'SipAccount' => true,
+ 'HuntGroup' => true,
+ 'AutomaticCallDistributor' => true,
+ }
+ end
+
+ def new
+ @phone_number = @parent.phone_numbers.build()
+ end
+
+ def create
+ @phone_number = @parent.phone_numbers.new( params[:phone_number] )
+ if @phone_number.save
+ m = method( :"#{@parent.class.name.underscore}_phone_number_path" )
+ redirect_to m.( @parent, @phone_number ), :notice => t('phone_numbers.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @phone_number.update_attributes(params[:phone_number])
+ m = method( :"#{@parent.class.name.underscore}_phone_number_path" )
+ redirect_to m.( @parent, @phone_number ), :notice => t('phone_numbers.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @phone_number.destroy
+ m = method( :"#{@parent.class.name.underscore}_phone_numbers_url" )
+ redirect_to m.(), :notice => t('phone_numbers.controller.successfuly_destroyed')
+ end
+
+ def move_higher
+ @phone_number.move_higher
+ redirect_to :back
+ end
+
+ def move_lower
+ @phone_number.move_lower
+ redirect_to :back
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @phone_book_entry || @sip_account || @conference || @fax_account ||
+ @phone_number_range || @callthrough || @whitelist || @access_authorization ||
+ @hunt_group || @hunt_group_member || @automatic_call_distributor
+
+ authorize! :read, @parent
+
+ @show_path_method = method( :"#{@parent.class.name.underscore}_phone_number_path" )
+ @index_path_method = method( :"#{@parent.class.name.underscore}_phone_numbers_path" )
+ @new_path_method = method( :"new_#{@parent.class.name.underscore}_phone_number_path" )
+ @edit_path_method = method( :"edit_#{@parent.class.name.underscore}_phone_number_path" )
+ end
+
+ def spread_breadcrumbs
+ if @parent.class == Callthrough
+ add_breadcrumb t("#{@parent.class.name.underscore.pluralize}.index.page_title"), tenant_callthroughs_path(@parent.tenant)
+ add_breadcrumb @callthrough, tenant_callthrough_path(@parent.tenant, @callthrough)
+ add_breadcrumb t("phone_numbers.index.page_title"), callthrough_phone_numbers_path(@parent)
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, callthrough_phone_number_path(@callthrough, @phone_number)
+ end
+ end
+
+ if @parent.class == SipAccount
+ if @sip_account.sip_accountable.class == User
+ add_breadcrumb t("#{@sip_account.sip_accountable.class.name.underscore.pluralize}.index.page_title"), method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore.pluralize}_path" ).(@sip_account.tenant)
+ add_breadcrumb @sip_account.sip_accountable, method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore}_path" ).(@sip_account.tenant, @sip_account.sip_accountable)
+ end
+ add_breadcrumb t("sip_accounts.index.page_title"), method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_accounts_path" ).(@sip_account.sip_accountable)
+ add_breadcrumb @sip_account, method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_account_path" ).(@sip_account.sip_accountable, @sip_account)
+ add_breadcrumb t("phone_numbers.index.page_title"), sip_account_phone_numbers_path(@sip_account)
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, sip_account_phone_number_path(@sip_account, @phone_number)
+ end
+ end
+
+ if @parent.class == Conference
+ @conference = @parent
+ conference_parent = @conference.conferenceable
+ if conference_parent && conference_parent.class == User
+ @user = conference_parent
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t("conferences.index.page_title"), user_conferences_path(@user)
+ add_breadcrumb @conference, user_conference_path(@user, @conference)
+ end
+ if conference_parent && conference_parent.class == Tenant
+ @tenant = conference_parent
+ add_breadcrumb t("conferences.index.page_title"), tenant_conferences_path(@tenant)
+ add_breadcrumb @conference, tenant_conference_path(@tenant, @conference)
+ end
+ add_breadcrumb t("phone_numbers.index.page_title"), conference_phone_numbers_path(@conference)
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, conference_phone_number_path(@conference, @phone_number)
+ end
+ end
+
+ if @parent.class == HuntGroup
+ add_breadcrumb t("#{@parent.class.name.underscore.pluralize}.index.page_title"), tenant_hunt_groups_path(@parent.tenant)
+ add_breadcrumb @hunt_group, tenant_hunt_group_path(@parent.tenant, @hunt_group)
+ add_breadcrumb t("phone_numbers.index.page_title"), hunt_group_phone_numbers_path(@parent)
+ end
+
+ if @parent.class == HuntGroupMember
+ add_breadcrumb t("hunt_groups.index.page_title"), tenant_hunt_groups_path(@parent.hunt_group.tenant)
+ add_breadcrumb @parent.hunt_group, tenant_hunt_group_path(@parent.hunt_group.tenant, @parent.hunt_group)
+ add_breadcrumb t("hunt_group_members.index.page_title"), hunt_group_hunt_group_members_path(@parent.hunt_group)
+ add_breadcrumb @parent, hunt_group_hunt_group_member_path(@parent.hunt_group, @parent)
+ add_breadcrumb t("phone_numbers.index.page_title"), hunt_group_member_phone_numbers_path(@parent)
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, hunt_group_member_phone_number_path(@parent, @phone_number)
+ end
+ end
+
+ if @parent.class == AccessAuthorization
+ if @parent.access_authorizationable.class == Callthrough
+ callthrough = @parent.access_authorizationable
+ tenant = callthrough.tenant
+ add_breadcrumb t("callthroughs.index.page_title"), tenant_callthroughs_path(tenant)
+ add_breadcrumb callthrough, tenant_callthrough_path(tenant, callthrough)
+ add_breadcrumb t("access_authorizations.index.page_title"), callthrough_access_authorizations_path(callthrough)
+ add_breadcrumb @parent, callthrough_access_authorization_path(callthrough, @parent)
+ add_breadcrumb t("phone_numbers.index.page_title"), access_authorization_phone_numbers_path(@parent)
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, access_authorization_phone_number_path(@parent, @phone_number)
+ end
+ end
+ end
+
+ if @parent.class == PhoneBookEntry
+ @phone_book = @parent.phone_book
+ if @parent.phone_book.phone_bookable.class == Tenant
+ @tenant = @parent.phone_book.phone_bookable
+ add_breadcrumb t("phone_books.index.page_title"), tenant_phone_books_path(@tenant)
+ add_breadcrumb @phone_book, tenant_phone_book_path(@tenant, @phone_book)
+ add_breadcrumb @phone_book_entry, phone_book_phone_book_entry_path(@phone_book, @phone_book_entry)
+
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, phone_book_entry_phone_number_path(@phone_book_entry, @phone_number)
+ end
+ end
+
+ if @parent.phone_book.phone_bookable.class == User
+ @user = @parent.phone_book.phone_bookable
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t("phone_books.index.page_title"), user_phone_books_path(@user)
+ add_breadcrumb @phone_book, user_phone_book_path(@user, @phone_book)
+ add_breadcrumb @phone_book_entry, phone_book_phone_book_entry_path(@phone_book, @phone_book_entry)
+
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, phone_book_entry_phone_number_path(@phone_book_entry, @phone_number)
+ end
+ end
+ end
+
+ if @parent.class == Whitelist
+ @tenant = @parent.whitelistable.tenant
+ @callthrough = @parent.whitelistable
+ @whitelist = @parent
+ add_breadcrumb t("callthroughs.name").pluralize, tenant_callthroughs_path(@tenant)
+ add_breadcrumb @callthrough, tenant_callthrough_path(@tenant, @callthrough)
+ add_breadcrumb t("whitelists.index.page_title"), callthrough_whitelists_path(@callthrough)
+ add_breadcrumb @whitelist, callthrough_whitelist_path(@callthrough, @whitelist)
+ add_breadcrumb t("phone_numbers.index.page_title"), whitelist_phone_numbers_path(@whitelist)
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, whitelist_phone_number_path(@whitelist, @phone_number)
+ end
+ end
+
+ if @parent.class == AutomaticCallDistributor
+ if @automatic_call_distributor.automatic_call_distributorable.class == User
+ add_breadcrumb t("#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore.pluralize}.index.page_title"), method( :"tenant_#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore.pluralize}_path" ).(@automatic_call_distributor.tenant)
+ add_breadcrumb @automatic_call_distributor.automatic_call_distributorable, method( :"tenant_#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore}_path" ).(@automatic_call_distributor.tenant, @automatic_call_distributor.automatic_call_distributorable)
+ end
+ add_breadcrumb t("automatic_call_distributors.index.page_title"), method( :"#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore}_automatic_call_distributors_path" ).(@automatic_call_distributor.automatic_call_distributorable)
+ add_breadcrumb @automatic_call_distributor, method( :"#{@automatic_call_distributor.automatic_call_distributorable.class.name.underscore}_automatic_call_distributor_path" ).(@automatic_call_distributor.automatic_call_distributorable, @automatic_call_distributor)
+ add_breadcrumb t("phone_numbers.index.page_title"), automatic_call_distributor_phone_numbers_path(@automatic_call_distributor)
+ if @phone_number && !@phone_number.new_record?
+ add_breadcrumb @phone_number, automatic_call_distributor_phone_number_path(@automatic_call_distributor, @phone_number)
+ end
+ end
+
+ end
+
+end
diff --git a/app/controllers/phone_sip_accounts_controller.rb b/app/controllers/phone_sip_accounts_controller.rb
new file mode 100644
index 0000000..8558c55
--- /dev/null
+++ b/app/controllers/phone_sip_accounts_controller.rb
@@ -0,0 +1,60 @@
+class PhoneSipAccountsController < ApplicationController
+ load_and_authorize_resource :phone
+ load_and_authorize_resource :phone_sip_account, :through => [:phone]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @available_sip_accounts = @phone.phoneable.sip_accounts
+
+ # Ensure a SipAccount is used on a single phone only.
+ #
+ @available_sip_accounts = @available_sip_accounts.delete_if { |x| x.phone_sip_account_ids.count > 0 }
+
+ if @available_sip_accounts.count == 0
+ redirect_to method( :"new_#{@phone.phoneable.class.name.underscore}_sip_account_path" ).(@phone.phoneable), :alert => t('phone_sip_accounts.controller.no_existing_sip_accounts_warning')
+ else
+ @phone_sip_account = @phone.phone_sip_accounts.build(:sip_account_id => @available_sip_accounts.first.try(:id))
+ end
+ end
+
+ def create
+ @phone_sip_account = @phone.phone_sip_accounts.build(params[:phone_sip_account])
+ if @phone_sip_account.save
+ redirect_to method( :"#{@phone_sip_account.phone.phoneable.class.name.underscore}_phone_path" ).(@phone_sip_account.phone.phoneable, @phone_sip_account.phone), :notice => t('phone_sip_accounts.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def destroy
+ @phone_sip_account.destroy
+ redirect_to method( :"#{@phone_sip_account.phone.phoneable.class.name.underscore}_phone_path" ).(@phone_sip_account.phone.phoneable, @phone_sip_account.phone), :notice => t('phone_sip_accounts.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def spread_breadcrumbs
+ if @phone.phoneable.class == User
+ user = @phone.phoneable
+ add_breadcrumb t('users.index.page_title'), tenant_users_path(user.current_tenant)
+ add_breadcrumb user, tenant_user_path(user.current_tenant, user)
+ add_breadcrumb t('phones.index.page_title'), user_phones_path(user)
+ elsif @phone.phoneable.class == Tenant
+ tenant = @phone.phoneable
+ add_breadcrumb t('phones.index.page_title'), tenant_phones_path(tenant)
+ end
+ add_breadcrumb @phone, method( :"#{@phone.phoneable.class.name.underscore}_phone_path" ).(@phone.phoneable, @phone)
+ add_breadcrumb t('phone_sip_accounts.index.page_title'), phone_phone_sip_accounts_path(@phone)
+ if @phone_sip_account && !@phone_sip_account.new_record?
+ add_breadcrumb @phone_sip_account, phone_phone_sip_account_path(@phone, @phone_sip_account)
+ end
+ end
+
+end
diff --git a/app/controllers/phones_controller.rb b/app/controllers/phones_controller.rb
new file mode 100644
index 0000000..d46bf86
--- /dev/null
+++ b/app/controllers/phones_controller.rb
@@ -0,0 +1,72 @@
+class PhonesController < ApplicationController
+ load_resource :tenant
+ load_resource :user
+ load_and_authorize_resource :phone, :through => [:tenant, :user]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @phone = @phoneable.phones.build()
+
+ # Use the last phone.phone_model as the default.
+ #
+ @phone.phone_model_id = Phone.last.try(:phone_model).try(:id)
+ end
+
+ def create
+ @phone = @phoneable.phones.build(params[:phone])
+ if @phone.save
+ m = method( :"#{@phoneable.class.name.underscore}_phone_path" )
+ redirect_to m.( @phoneable, @phone ), :notice => t('phones.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @phone.update_attributes(params[:phone])
+ m = method( :"#{@phoneable.class.name.underscore}_phone_path" )
+ redirect_to m.( @phoneable, @phone ), :notice => t('phones.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @phone.destroy
+ m = method( :"#{@phoneable.class.name.underscore}_phones_url" )
+ redirect_to m.( @phoneable ), :notice => t('phones.controller.successfuly_destroyed')
+ end
+
+ private
+ def set_and_authorize_parent
+ @phoneable = (@user || @tenant)
+ @parent = @phoneable
+ authorize! :read, @parent
+ @nesting_prefix = @phoneable ? "#{@phoneable.class.name.underscore}_" : ''
+ end
+
+ def spread_breadcrumbs
+ if @user
+ add_breadcrumb t('users.index.page_title'), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t('phones.index.page_title'), user_phones_path(@user)
+ elsif @tenant
+ add_breadcrumb t('phones.index.page_title'), tenant_phones_path(@tenant)
+ end
+ if @phone && !@phone.new_record?
+ add_breadcrumb @phone, method( :"#{@phone.phoneable.class.name.underscore}_phone_path" ).(@phone.phoneable, @phone)
+ end
+ end
+
+end
diff --git a/app/controllers/ringtones_controller.rb b/app/controllers/ringtones_controller.rb
new file mode 100644
index 0000000..7ffe30e
--- /dev/null
+++ b/app/controllers/ringtones_controller.rb
@@ -0,0 +1,67 @@
+class RingtonesController < ApplicationController
+ load_resource :phone_number
+ load_resource :boss_assistant_cooperation
+ load_and_authorize_resource :ringtone, :through => [:phone_number, :boss_assistant_cooperation]
+
+ before_filter :set_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @ringtone = @parent.ringtones.build
+ end
+
+ def create
+ @ringtone = @parent.ringtones.build(params[:ringtone])
+ if @ringtone.save
+ redirect_to phone_number_ringtone_path(@parent, @ringtone), :notice => t('ringtones.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @ringtone.update_attributes(params[:ringtone])
+ redirect_to method( :"#{@parent.class.name.underscore}_ringtone_path" ).(@ringtone.ringtoneable, @ringtone), :notice => t('ringtones.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @ringtone.destroy
+ redirect_to phone_number_ringtones_path(@parent), :notice => t('ringtones.controller.successfuly_destroyed')
+ end
+
+ private
+ def set_parent
+ @parent = @phone_number || @boss_assistant_cooperation
+ end
+
+ def spread_breadcrumbs
+ if @parent.class == PhoneNumber && @parent.phone_numberable.class == SipAccount
+ @sip_account = @parent.phone_numberable
+ if @sip_account.sip_accountable.class == User
+ add_breadcrumb t("#{@sip_account.sip_accountable.class.name.underscore.pluralize}.index.page_title"), method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore.pluralize}_path" ).(@sip_account.tenant)
+ add_breadcrumb @sip_account.sip_accountable, method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore}_path" ).(@sip_account.tenant, @sip_account.sip_accountable)
+ end
+ add_breadcrumb t("sip_accounts.index.page_title"), method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_accounts_path" ).(@sip_account.sip_accountable)
+ add_breadcrumb @sip_account, method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_account_path" ).(@sip_account.sip_accountable, @sip_account)
+ add_breadcrumb t("phone_numbers.index.page_title"), sip_account_phone_numbers_path(@sip_account)
+ add_breadcrumb @phone_number, sip_account_phone_number_path(@sip_account, @phone_number)
+ add_breadcrumb t("ringtones.index.page_title"), phone_number_ringtones_path(@phone_number)
+ if @ringtone && !@ringtone.new_record?
+ add_breadcrumb @ringtone, phone_number_ringtone_path(@phone_number, @ringtone)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/sessions_controller.rb b/app/controllers/sessions_controller.rb
new file mode 100644
index 0000000..f92ae1c
--- /dev/null
+++ b/app/controllers/sessions_controller.rb
@@ -0,0 +1,44 @@
+class SessionsController < ApplicationController
+
+ before_filter :redirect_to_https
+ skip_before_filter :home_breadcrumb
+
+ def new
+ end
+
+ def create
+ user = User.find_by_email(params[:sessions][:login_data].downcase.strip)
+ if user.nil?
+ user = User.find_by_user_name(params[:sessions][:login_data].downcase.strip)
+ end
+ if user && user.authenticate(params[:sessions][:password])
+ session[:user_id] = user.id
+ redirect_to tenant_user_path(user.current_tenant, user), :notice => t('sessions.controller.successfully_created', :resource => user)
+ elsif user && !user.email.blank? && params[:sessions][:reset_password] =~ (/(1|t|y|yes|true)$/i)
+ password = SecureRandom.base64(8)[0..7]
+ if user.update_attributes(:password => password)
+ Notifications.new_password(user, password).deliver
+ flash.now.notice = t('sessions.flash_messages.password_recovery_successful', :resource => user)
+ else
+ flash.now.alert = t('sessions.flash_messages.password_recovery_failed', :resource => user)
+ end
+ render "new"
+ else
+ flash.now.alert = t('sessions.flash_messages.invalid_email_or_password', :resource => user)
+ render "new"
+ end
+ end
+
+ def destroy
+ session[:user_id] = nil
+ redirect_to root_url, :notice => t('sessions.controller.successfully_destroyed')
+ end
+
+ private
+ def redirect_to_https
+ if GUI_REDIRECT_HTTPS and ! request.ssl?
+ redirect_to :protocol => "https://"
+ end
+ end
+
+end
diff --git a/app/controllers/sip_accounts_controller.rb b/app/controllers/sip_accounts_controller.rb
new file mode 100644
index 0000000..1f3166e
--- /dev/null
+++ b/app/controllers/sip_accounts_controller.rb
@@ -0,0 +1,98 @@
+class SipAccountsController < ApplicationController
+ load_resource :user
+ load_resource :tenant
+ load_and_authorize_resource :sip_account, :through => [:user, :tenant ]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @sip_account = @parent.sip_accounts.build
+ @sip_account.caller_name = @parent
+ @sip_account.call_waiting = CALL_WAITING
+ @sip_account.clir = DEFAULT_CLIR_SETTING
+ @sip_account.clip = DEFAULT_CLIP_SETTING
+ @sip_account.voicemail_pin = random_pin
+ @sip_account.callforward_rules_act_per_sip_account = CALLFORWARD_RULES_ACT_PER_SIP_ACCOUNT_DEFAULT
+ @sip_account.hotdeskable = true
+
+ # Make sure that we don't use an already taken auth_name
+ #
+ loop do
+ @sip_account.auth_name = SecureRandom.hex(DEFAULT_LENGTH_SIP_AUTH_NAME)
+
+ break unless SipAccount.exists?(:auth_name => @sip_account.auth_name)
+ end
+ @sip_account.password = SecureRandom.hex(DEFAULT_LENGTH_SIP_PASSWORD)
+ end
+
+ def create
+ @sip_account = @parent.sip_accounts.build(params[:sip_account])
+
+ if @sip_account.auth_name.blank?
+ loop do
+ @sip_account.auth_name = SecureRandom.hex(DEFAULT_LENGTH_SIP_AUTH_NAME)
+
+ break unless SipAccount.exists?(:auth_name => @sip_account.auth_name)
+ end
+ end
+ if @sip_account.password.blank?
+ @sip_account.password = SecureRandom.hex(DEFAULT_LENGTH_SIP_PASSWORD)
+ end
+
+ if @sip_account.save
+ m = method( :"#{@parent.class.name.underscore}_sip_account_path" )
+ redirect_to m.( @parent, @sip_account ), :notice => t('sip_accounts.controller.successfuly_created', :resource => @parent)
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @sip_account.update_attributes(params[:sip_account])
+ m = method( :"#{@parent.class.name.underscore}_sip_account_path" )
+ redirect_to m.( @parent, @sip_account ), :notice => t('sip_accounts.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @sip_account.destroy
+ m = method( :"#{@parent.class.name.underscore}_sip_accounts_url" )
+ redirect_to m.( @parent ), :notice => t('sip_accounts.controller.successfuly_destroyed')
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @user || @tenant
+ authorize! :read, @parent
+ end
+
+ def spread_breadcrumbs
+ if @user
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@user.current_tenant)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t("sip_accounts.index.page_title"), user_sip_accounts_path(@user)
+ if @sip_account && !@sip_account.new_record?
+ add_breadcrumb @sip_account, user_sip_account_path(@user, @sip_account)
+ end
+ end
+ if @tenant
+ add_breadcrumb t("sip_accounts.index.page_title"), tenant_sip_accounts_path(@tenant)
+ if @sip_account && !@sip_account.new_record?
+ add_breadcrumb @sip_account, tenant_sip_account_path(@tenant, @sip_account)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/sip_domains_controller.rb b/app/controllers/sip_domains_controller.rb
new file mode 100644
index 0000000..7301192
--- /dev/null
+++ b/app/controllers/sip_domains_controller.rb
@@ -0,0 +1,41 @@
+class SipDomainsController < ApplicationController
+ def index
+ @sip_domains = SipDomain.all
+ end
+
+ def show
+ @sip_domain = SipDomain.find(params[:id])
+ end
+
+ def new
+ @sip_domain = SipDomain.new
+ end
+
+ def create
+ @sip_domain = SipDomain.new(params[:sip_domain])
+ if @sip_domain.save
+ redirect_to @sip_domain, :notice => t('sip_domains.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ @sip_domain = SipDomain.find(params[:id])
+ end
+
+ def update
+ @sip_domain = SipDomain.find(params[:id])
+ if @sip_domain.update_attributes(params[:sip_domain])
+ redirect_to @sip_domain, :notice => t('sip_domains.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @sip_domain = SipDomain.find(params[:id])
+ @sip_domain.destroy
+ redirect_to sip_domains_url, :notice => t('sip_domains.controller.successfuly_destroyed')
+ end
+end
diff --git a/app/controllers/softkeys_controller.rb b/app/controllers/softkeys_controller.rb
new file mode 100644
index 0000000..d2a2bb9
--- /dev/null
+++ b/app/controllers/softkeys_controller.rb
@@ -0,0 +1,91 @@
+class SoftkeysController < ApplicationController
+ load_and_authorize_resource :sip_account
+ load_and_authorize_resource :softkey, :through => [:sip_account]
+
+ before_filter :set_available_call_forwards_and_softkey_functions, :only => [ :new, :edit, :update ]
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @softkey = @sip_account.softkeys.build
+
+ delete_call_forward_softkey_if_no_callforward_is_available
+ end
+
+ def create
+ @softkey = @sip_account.softkeys.build(params[:softkey])
+ if @softkey.save
+ redirect_to sip_account_softkey_path(@softkey.sip_account, @softkey), :notice => t('softkeys.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ delete_call_forward_softkey_if_no_callforward_is_available
+ end
+
+ def update
+ if @softkey.update_attributes(params[:softkey])
+ redirect_to sip_account_softkey_path(@softkey.sip_account, @softkey), :notice => t('softkeys.controller.successfuly_updated')
+ else
+ delete_call_forward_softkey_if_no_callforward_is_available
+ render :edit
+ end
+ end
+
+ def destroy
+ @softkey.destroy
+ redirect_to sip_account_softkeys_path(@softkey.sip_account), :notice => t('softkeys.controller.successfuly_destroyed')
+ end
+
+ def move_higher
+ @softkey.move_higher
+ redirect_to :back
+ end
+
+ def move_lower
+ @softkey.move_lower
+ redirect_to :back
+ end
+
+ private
+
+ def set_available_call_forwards_and_softkey_functions
+ @available_call_forwards = @softkey.possible_blf_call_forwards
+
+ @softkey_functions = []
+ SoftkeyFunction.accessible_by(current_ability, :read).each do |softkey_function|
+ if GuiFunction.display?("softkey_function_#{softkey_function.name.downcase}_field_in_softkey_form", @current_user)
+ @softkey_functions << softkey_function
+ end
+ end
+ end
+
+ def spread_breadcrumbs
+ if @sip_account.sip_accountable.class == User
+ add_breadcrumb t('users.name'), tenant_users_path(@sip_account.sip_accountable.current_tenant)
+ add_breadcrumb @sip_account.sip_accountable, tenant_user_path(@sip_account.sip_accountable.current_tenant, @sip_account.sip_accountable)
+ add_breadcrumb t('sip_accounts.index.page_title'), user_sip_accounts_path(@sip_account.sip_accountable)
+ add_breadcrumb @sip_account, user_sip_account_path(@sip_account.sip_accountable, @sip_account)
+ add_breadcrumb t('softkeys.index.page_title'), sip_account_softkeys_path(@sip_account)
+ elsif @sip_account.sip_accountable.class == Tenant
+ add_breadcrumb t('sip_accounts.index.page_title'), tenant_sip_accounts_path(@sip_account.sip_accountable)
+ add_breadcrumb @sip_account, tenant_sip_account_path(@sip_account.sip_accountable, @sip_account)
+ add_breadcrumb t('softkeys.index.page_title'), sip_account_softkeys_path(@sip_account)
+ end
+ end
+
+ def delete_call_forward_softkey_if_no_callforward_is_available
+ # Don't display the call_forward option if there aren't any call_forwards to choose from.
+ #
+ if @softkey.sip_account.phone_numbers.map{|phone_number| phone_number.call_forwards}.flatten.count == 0
+ @softkey_functions.delete_if { |softkey_function| softkey_function == SoftkeyFunction.find_by_name('call_forwarding') }
+ end
+ end
+end
diff --git a/app/controllers/system_messages_controller.rb b/app/controllers/system_messages_controller.rb
new file mode 100644
index 0000000..d7fe515
--- /dev/null
+++ b/app/controllers/system_messages_controller.rb
@@ -0,0 +1,30 @@
+class SystemMessagesController < ApplicationController
+ load_and_authorize_resource :user
+ load_and_authorize_resource :system_message, :through => [:user]
+
+ def index
+ @system_messages = @system_messages.where(:created_at => Time.now - 6.hours .. Time.now)
+ end
+
+ def show
+ end
+
+ def new
+ @system_message = @user.system_messages.build
+ end
+
+ def create
+ @system_message = @user.system_messages.build(params[:system_message])
+ if @system_message.save
+ # Push the new message via AJAX to the browser.
+ #
+ # PrivatePub.publish_to("/users/#{@system_message.user.id}/system_messages",
+ # "$('#system_message').empty();$('#system_message').append('<span class=\"created_at\">#{(I18n.l @system_message.created_at, :format => :short )}</span> #{@system_message.content}');$('#system_message_display').fadeIn();"
+ # )
+
+ redirect_to user_system_message_path(@user, @system_message), :notice => t('system_messages.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+end
diff --git a/app/controllers/tenants_controller.rb b/app/controllers/tenants_controller.rb
new file mode 100644
index 0000000..724d179
--- /dev/null
+++ b/app/controllers/tenants_controller.rb
@@ -0,0 +1,91 @@
+class TenantsController < ApplicationController
+ load_and_authorize_resource :tenant
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @tenant.name = generate_a_new_name(@tenant)
+ @tenant.sip_domain = SipDomain.last
+ @tenant.country = GemeinschaftSetup.first.country
+ @tenant.language = GemeinschaftSetup.first.language
+ @tenant.internal_extension_ranges = '10-99'
+ @tenant.from_field_voicemail_email = 'admin@localhost'
+ @tenant.from_field_pin_change_email = 'admin@localhost'
+ end
+
+ def create
+ if @tenant.save
+ # Become a member of this tenant.
+ #
+ @tenant.tenant_memberships.create(:user_id => @current_user.id)
+
+ # Groups
+ #
+ admin_group = @tenant.user_groups.create(:name => t('gemeinschaft_setups.initial_setup.admin_group_name'))
+ admin_group.users << @current_user
+
+ user_group = @tenant.user_groups.create(:name => t('gemeinschaft_setups.initial_setup.user_group_name'))
+ user_group.users << @current_user
+
+ @current_user.update_attributes!(:current_tenant_id => @tenant.id)
+
+ # Generate the internal_extensions
+ #
+ if !@tenant.internal_extension_ranges.blank?
+ if @tenant.array_of_internal_extension_numbers.count < 105
+ # This can be done more or less quick.
+ @tenant.generate_internal_extensions
+ else
+ # Better be on the save side and start a delayed job for this.
+ @tenant.delay.generate_internal_extensions
+ end
+ end
+
+ # Generate the external numbers (DIDs)
+ #
+ if !@tenant.did_list.blank?
+ if @tenant.array_of_dids.count < 105
+ # This can be done more or less quick.
+ @tenant.generate_dids
+ else
+ # Better be on the save side and start a delayed job for this.
+ @tenant.delay.generate_dids
+ end
+ end
+
+ if Delayed::Job.count > 0
+ redirect_to @tenant, :notice => t('tenants.controller.successfuly_created_plus_delayed_jobs',
+ :resource => @tenant,
+ :amount_of_numbers => @tenant.array_of_internal_extension_numbers.count + @tenant.array_of_dids.count
+ )
+ else
+ redirect_to @tenant, :notice => t('tenants.controller.successfuly_created',
+ :resource => @tenant
+ )
+ end
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @tenant.update_attributes(params[:tenant])
+ redirect_to @tenant, :notice => t('tenants.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @tenant.destroy
+ redirect_to tenants_url, :notice => t('tenants.controller.successfuly_destroyed')
+ end
+
+end
diff --git a/app/controllers/user_group_memberships_controller.rb b/app/controllers/user_group_memberships_controller.rb
new file mode 100644
index 0000000..1cbbd48
--- /dev/null
+++ b/app/controllers/user_group_memberships_controller.rb
@@ -0,0 +1,48 @@
+class UserGroupMembershipsController < ApplicationController
+ load_and_authorize_resource :user_group
+ load_and_authorize_resource :user_group_membership, :through => [:user_group]
+
+ before_filter :spread_breadcrumbs
+
+ def index
+ @potential_users_count = @user_group.tenant.users.count - @user_group.users.count
+ end
+
+ def show
+ end
+
+ def new
+ @user_group_membership = @user_group.user_group_memberships.build
+ @potential_users = (@user_group.tenant.users.order(:last_name) - @user_group.users)
+ if @potential_users.count == 0
+ redirect_to user_group_user_group_memberships_path(@user_group), :alert => t('user_group_memberships.controller.no_more_user_to_add')
+ end
+ end
+
+ def create
+ @user_group_membership = @user_group.user_group_memberships.build(params[:user_group_membership])
+ if @user_group_membership.save
+ redirect_to user_group_user_group_membership_path(@user_group, @user_group_membership), :notice => t('user_group_memberships.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def destroy
+ @user_group_membership.destroy
+ redirect_to user_group_user_group_memberships_path(@user_group), :notice => t('user_group_memberships.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def spread_breadcrumbs
+ add_breadcrumb t("user_groups.index.page_title"), tenant_user_groups_path(@user_group.tenant)
+ add_breadcrumb @user_group, tenant_user_group_path(@user_group.tenant, @user_group)
+ add_breadcrumb t("user_group_memberships.index.page_title"), user_group_user_group_memberships_path(@user_group)
+
+ if @user_group_membership && !@user_group_membership.new_record?
+ add_breadcrumb @user_group_membership, user_group_user_group_membership_path(@user_group, @user_group_membership)
+ end
+ end
+
+end
diff --git a/app/controllers/user_groups_controller.rb b/app/controllers/user_groups_controller.rb
new file mode 100644
index 0000000..158abaa
--- /dev/null
+++ b/app/controllers/user_groups_controller.rb
@@ -0,0 +1,69 @@
+class UserGroupsController < ApplicationController
+ load_resource :tenant
+ load_resource :user
+ load_and_authorize_resource :user_group, :through => [:tenant, :user]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @user_group = @parent.user_groups.build
+ end
+
+ def create
+ @user_group = @parent.user_groups.build(params[:user_group])
+ if @user_group.save
+ redirect_to @user_group, :notice => t('user_groups.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @user_group.update_attributes(params[:user_group])
+ redirect_to @user_group, :notice => t('user_groups.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @user_group.destroy
+ redirect_to user_groups_url, :notice => t('user_groups.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def set_and_authorize_parent
+ @parent = @user || @tenant
+ authorize! :read, @parent
+ end
+
+ def spread_breadcrumbs
+ if @tenant
+ add_breadcrumb t("user_groups.index.page_title"), tenant_user_groups_path(@tenant)
+ if @user_group && !@user_group.new_record?
+ add_breadcrumb @user_group, tenant_user_group_path(@tenant, @user_group)
+ end
+ end
+
+ if @user
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@parent)
+ add_breadcrumb @user, tenant_user_path(@user.current_tenant, @user)
+ add_breadcrumb t("user_groups.index.page_title"), user_user_groups_path(@user)
+ if @user_group && !@user_group.new_record?
+ add_breadcrumb @user_group, user_user_group_path(@user, @user_group)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/users_controller.rb b/app/controllers/users_controller.rb
new file mode 100644
index 0000000..454c26b
--- /dev/null
+++ b/app/controllers/users_controller.rb
@@ -0,0 +1,85 @@
+class UsersController < ApplicationController
+ load_resource :tenant
+ load_resource :user_group
+ load_and_authorize_resource :user, :through => [:tenant, :user_group]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ @phone_books = PhoneBook.accessible_by( Ability.new( @user ) ).all
+ end
+
+ def new
+ @user = @parent.users.build(params[:user])
+ @user.male = true
+ @user.send_voicemail_as_email_attachment = true
+ end
+
+ def create
+ @user = @parent.users.build(params[:user])
+ if @user.save
+ if @parent.class == Tenant
+ @parent.tenant_memberships.create(:user => @user)
+ if @parent.user_groups.exists?(:name => 'Users')
+ @parent.user_groups.where(:name => 'Users').first.user_group_memberships.create(:user => @user)
+ end
+ redirect_to tenant_user_url( @parent, @user), :notice => t('users.controller.successfuly_created', :resource => @user)
+ else
+ redirect_to tenant_user_path(@user.current_tenant, @user), :notice => t('users.controller.successfuly_created_and_login', :resource => @user)
+ end
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @user.update_attributes(params[:user])
+ # Make sure that the flash notice gets rendered in the correct language.
+ I18n.locale = @user.language.code.downcase
+
+ redirect_to tenant_user_path(@user.current_tenant, @user), :notice => t('users.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @user.destroy
+ redirect_to @parent, :notice => t('users.controller.successfuly_destroyed')
+ end
+
+ def destroy_avatar
+ user = User.find(params[:user_id])
+ user.remove_image = true # https://github.com/jnicklas/carrierwave/issues/360
+ user.remove_image!
+ user.save
+ user.reload
+ user.image.remove!
+ user.save
+ redirect_to @parent, :notice => t('users.controller.avatar_destroyed')
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @tenant || @user_group
+ authorize! :read, @parent
+ end
+
+ def spread_breadcrumbs
+ if @tenant
+ add_breadcrumb t("users.index.page_title"), tenant_users_path(@tenant)
+
+ if @user && !@user.new_record?
+ add_breadcrumb @user, tenant_user_path(@tenant, @user)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/voicemail_messages_controller.rb b/app/controllers/voicemail_messages_controller.rb
new file mode 100644
index 0000000..58f5265
--- /dev/null
+++ b/app/controllers/voicemail_messages_controller.rb
@@ -0,0 +1,140 @@
+class VoicemailMessagesController < ApplicationController
+
+ load_resource :sip_account
+ load_and_authorize_resource :voicemail_message, :through => [:sip_account]
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+
+ before_filter { |controller|
+ if ! params[:type].blank? then
+ @type = params[:type].to_s
+ end
+
+ if ! params[:page].blank? then
+ @pagination_page_number = params[:page].to_i
+ end
+ }
+
+ def index
+ @messages_count = @sip_account.voicemail_messages.count
+ @messages_unread_count = @sip_account.voicemail_messages.where(:read_epoch => 0).count
+ @messages_read_count = @messages_count - @messages_unread_count
+
+ if @type == 'read'
+ @voicemail_messages = @sip_account.voicemail_messages.where('read_epoch > 0').order('created_epoch DESC').paginate(
+ :page => @pagination_page_number,
+ :per_page => DEFAULT_PAGINATION_ENTRIES_PER_PAGE
+ )
+ elsif @type == 'unread'
+ @voicemail_messages = @sip_account.voicemail_messages.where(:read_epoch => 0).order('created_epoch DESC').paginate(
+ :page => @pagination_page_number,
+ :per_page => DEFAULT_PAGINATION_ENTRIES_PER_PAGE
+ )
+ else
+ @voicemail_messages = @sip_account.voicemail_messages.order('created_epoch DESC').paginate(
+ :page => @pagination_page_number,
+ :per_page => DEFAULT_PAGINATION_ENTRIES_PER_PAGE
+ )
+ end
+ end
+
+ def show
+ respond_to do |format|
+ format.wav {
+ if @voicemail_message.file_path
+ send_file @voicemail_message.file_path, :type => "audio/x-wav",
+ :filename => "#{Time.at(@voicemail_message.created_epoch).strftime('%Y%m%d-%H%M%S')}-#{@voicemail_message.cid_number}.wav"
+ else
+ render(
+ :status => 404,
+ :layout => false,
+ :content_type => 'text/plain',
+ :text => "<!-- Message not found -->",
+ )
+ end
+ }
+ end
+ end
+
+ def new
+ end
+
+ def create
+ end
+
+ def edit
+ end
+
+ def update
+ end
+
+ def destroy
+ @voicemail_message.destroy
+ m = method( :"#{@parent.class.name.underscore}_voicemail_messages_url" )
+ redirect_to m.(), :notice => t('voicemail_messages.controller.successfuly_destroyed')
+ end
+
+ def destroy_multiple
+ result = false
+ if ! params[:selected_uuids].blank? then
+ voicemail_messages = @sip_account.voicemail_messages.where(:uuid => params[:selected_uuids])
+ voicemail_messages.each do |voicemail_message|
+ result = voicemail_message.destroy
+ end
+ end
+
+ m = method( :"#{@parent.class.name.underscore}_voicemail_messages_url" )
+ if result
+ redirect_to m.(), :notice => t('voicemail_messages.controller.successfuly_destroyed')
+ else
+ redirect_to m.()
+ end
+ end
+
+ def call
+ phone_number = @voicemail_message.cid_number
+ if ! phone_number.blank? && @sip_account.registration
+ @sip_account.call(phone_number)
+ end
+ redirect_to(:back)
+ end
+
+ def mark_read
+ @voicemail_message.mark_read
+ redirect_to(:back)
+ end
+
+ def mark_unread
+ @voicemail_message.mark_read(false)
+ redirect_to(:back)
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @sip_account
+
+ authorize! :read, @parent
+
+ @show_path_method = method( :"#{@parent.class.name.underscore}_voicemail_message_path" )
+ @index_path_method = method( :"#{@parent.class.name.underscore}_voicemail_messages_path" )
+ @new_path_method = method( :"new_#{@parent.class.name.underscore}_voicemail_message_path" )
+ @edit_path_method = method( :"edit_#{@parent.class.name.underscore}_voicemail_message_path" )
+ end
+
+ def spread_breadcrumbs
+ if @parent.class == SipAccount
+ if @sip_account.sip_accountable.class == User
+ add_breadcrumb t("#{@sip_account.sip_accountable.class.name.underscore.pluralize}.index.page_title"), method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore.pluralize}_path" ).(@sip_account.tenant)
+ add_breadcrumb @sip_account.sip_accountable, method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore}_path" ).(@sip_account.tenant, @sip_account.sip_accountable)
+ end
+ add_breadcrumb t("sip_accounts.index.page_title"), method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_accounts_path" ).(@sip_account.sip_accountable)
+ add_breadcrumb @sip_account, method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_account_path" ).(@sip_account.sip_accountable, @sip_account)
+ add_breadcrumb t("voicemail_messages.index.page_title"), sip_account_voicemail_messages_path(@sip_account)
+ if @voicemail_message && !@voicemail_message.new_record?
+ add_breadcrumb @voicemail_message, sip_account_voicemail_message_path(@sip_account, @voicemail_message)
+ end
+ end
+ end
+
+end
diff --git a/app/controllers/voicemail_settings_controller.rb b/app/controllers/voicemail_settings_controller.rb
new file mode 100644
index 0000000..d31de8f
--- /dev/null
+++ b/app/controllers/voicemail_settings_controller.rb
@@ -0,0 +1,91 @@
+class VoicemailSettingsController < ApplicationController
+ load_resource :sip_account
+ load_and_authorize_resource :voicemail_setting, :through => :sip_account, :singleton => true
+
+ before_filter :set_and_authorize_parent
+ before_filter :spread_breadcrumbs
+ before_filter :voicemail_defaults, :only => [:index, :show, :new, :create, :edit]
+
+ def index
+ render :edit
+ end
+
+ def show
+ render :edit
+ end
+
+ def new
+ render :edit
+ end
+
+ def create
+ @sip_account = SipAccount.where(:id => params[:sip_account_id]).first
+ params[:voicemail_setting][:username] = @sip_account.auth_name
+ params[:voicemail_setting][:domain] = @sip_account.sip_domain.try(:host)
+ @voicemail_setting = VoicemailSetting.new(params[:voicemail_setting])
+ if @voicemail_setting.save
+ redirect_to sip_account_voicemail_settings_path(@sip_account), :notice => t('voicemail_settings.controller.successfuly_created')
+ else
+ render :action => 'edit'
+ end
+ end
+
+ def edit
+
+ end
+
+ def update
+ if @voicemail_setting.update_attributes(params[:voicemail_setting])
+ redirect_to sip_account_voicemail_settings_path(@sip_account), :notice => t('voicemail_settings.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+
+ end
+
+ private
+ def set_and_authorize_parent
+ @parent = @sip_account
+
+ authorize! :read, @parent
+
+ @show_path_method = method( :"#{@parent.class.name.underscore}_voicemail_setting_path" )
+ @index_path_method = method( :"#{@parent.class.name.underscore}_voicemail_settings_path" )
+ @new_path_method = method( :"new_#{@parent.class.name.underscore}_voicemail_setting_path" )
+ @edit_path_method = method( :"edit_#{@parent.class.name.underscore}_voicemail_setting_path" )
+ end
+
+ def spread_breadcrumbs
+ if @parent.class == SipAccount
+ if @sip_account.sip_accountable.class == User
+ add_breadcrumb t("#{@sip_account.sip_accountable.class.name.underscore.pluralize}.index.page_title"), method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore.pluralize}_path" ).(@sip_account.tenant)
+ add_breadcrumb @sip_account.sip_accountable, method( :"tenant_#{@sip_account.sip_accountable.class.name.underscore}_path" ).(@sip_account.tenant, @sip_account.sip_accountable)
+ end
+ add_breadcrumb t("sip_accounts.index.page_title"), method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_accounts_path" ).(@sip_account.sip_accountable)
+ add_breadcrumb @sip_account, method( :"#{@sip_account.sip_accountable.class.name.underscore}_sip_account_path" ).(@sip_account.sip_accountable, @sip_account)
+ add_breadcrumb t("voicemail_settings.index.page_title"), sip_account_voicemail_settings_path(@sip_account)
+ end
+ end
+
+ def voicemail_defaults
+ path = "/opt/freeswitch/storage/voicemail/default/#{@sip_account.sip_domain.host}/#{@sip_account.auth_name}/"
+ @greeting_files = Dir.glob("#{path}*greeting*.wav").collect {|r| [ File.basename(r), File.expand_path(r) ] }
+ @name_files = Dir.glob("#{path}*name*.wav").collect {|r| [ File.basename(r), File.expand_path(r) ] }
+
+ if @voicemail_setting.blank? then
+ @voicemail_setting = @sip_account.voicemail_setting
+ end
+
+ if @voicemail_setting.blank?
+ @voicemail_setting = VoicemailSetting.new
+ @voicemail_setting.notify = true
+ @voicemail_setting.attachment = true
+ @voicemail_setting.mark_read = true
+ @voicemail_setting.purge = false
+ end
+ end
+
+end
diff --git a/app/controllers/whitelists_controller.rb b/app/controllers/whitelists_controller.rb
new file mode 100644
index 0000000..0526844
--- /dev/null
+++ b/app/controllers/whitelists_controller.rb
@@ -0,0 +1,61 @@
+class WhitelistsController < ApplicationController
+ load_and_authorize_resource :callthrough
+ load_and_authorize_resource :whitelist, :through => [:callthrough]
+
+ before_filter :set_parent_and_path_methods
+ before_filter :spread_breadcrumbs
+
+ def index
+ end
+
+ def show
+ end
+
+ def new
+ @whitelist.phone_numbers.build
+ end
+
+ def create
+ @whitelist = @parent.whitelists.build(params[:whitelist])
+ if @whitelist.save
+ redirect_to @show_path_method.(@parent, @whitelist), :notice => t('whitelists.controller.successfuly_created')
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @whitelist.update_attributes(params[:whitelist])
+ redirect_to @show_path_method.(@parent, @whitelist), :notice => t('whitelists.controller.successfuly_updated')
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @whitelist.destroy
+ redirect_to @index_path_method.(@parent), :notice => t('whitelists.controller.successfuly_destroyed')
+ end
+
+ private
+
+ def set_parent_and_path_methods
+ @parent = @callthrough
+ @show_path_method = method( :"#{@parent.class.name.underscore}_whitelist_path" )
+ @index_path_method = method( :"#{@parent.class.name.underscore}_whitelists_path" )
+ @new_path_method = method( :"new_#{@parent.class.name.underscore}_whitelist_path" )
+ @edit_path_method = method( :"edit_#{@parent.class.name.underscore}_whitelist_path" )
+ end
+
+ def spread_breadcrumbs
+ if @parent && @parent.class == Callthrough
+ add_breadcrumb t("#{@parent.class.name.underscore.pluralize}.name").pluralize, tenant_callthroughs_path(@parent.tenant)
+ add_breadcrumb @callthrough, tenant_callthrough_path(@parent.tenant, @callthrough)
+ add_breadcrumb t("whitelists.index.page_title"), callthrough_whitelists_path(@parent)
+ end
+ end
+
+end