iugusdk 1.0.0.alpha.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (207) hide show
  1. data/MIT-LICENSE +20 -0
  2. data/README.rdoc +3 -0
  3. data/Rakefile +39 -0
  4. data/app/assets/images/application_logo.png +0 -0
  5. data/app/assets/javascripts/settings.js +10 -0
  6. data/app/assets/javascripts/settings_code.js.coffee.erb +0 -0
  7. data/app/assets/stylesheets/settings.sass +120 -0
  8. data/app/controllers/iugu/account_controller.rb +63 -0
  9. data/app/controllers/iugu/account_domains_controller.rb +64 -0
  10. data/app/controllers/iugu/account_roles_controller.rb +20 -0
  11. data/app/controllers/iugu/account_settings_controller.rb +17 -0
  12. data/app/controllers/iugu/account_users_controller.rb +43 -0
  13. data/app/controllers/iugu/application_domain_controller.rb +11 -0
  14. data/app/controllers/iugu/confirmations_controller.rb +2 -0
  15. data/app/controllers/iugu/invitations_controller.rb +49 -0
  16. data/app/controllers/iugu/omniauth_callbacks_controller.rb +23 -0
  17. data/app/controllers/iugu/passwords_controller.rb +2 -0
  18. data/app/controllers/iugu/profile_controller.rb +44 -0
  19. data/app/controllers/iugu/registrations_controller.rb +3 -0
  20. data/app/controllers/iugu/sessions_controller.rb +2 -0
  21. data/app/controllers/iugu/settings_controller.rb +11 -0
  22. data/app/controllers/iugu/unlocks_controller.rb +2 -0
  23. data/app/mailers/iugu_mailer.rb +16 -0
  24. data/app/models/account.rb +53 -0
  25. data/app/models/account_domain.rb +69 -0
  26. data/app/models/account_role.rb +24 -0
  27. data/app/models/account_user.rb +55 -0
  28. data/app/models/available_language.rb +10 -0
  29. data/app/models/social_account.rb +14 -0
  30. data/app/models/user.rb +107 -0
  31. data/app/models/user_invitation.rb +39 -0
  32. data/app/validators/email_validator.rb +17 -0
  33. data/app/views/iugu-old/account_settings.html.haml +17 -0
  34. data/app/views/iugu-old/login.html.haml +28 -0
  35. data/app/views/iugu-old/mails/confirmation_instructions.html.erb +5 -0
  36. data/app/views/iugu-old/mails/reset_password_instructions.html.erb +8 -0
  37. data/app/views/iugu-old/mails/unlock_instructions.html.erb +7 -0
  38. data/app/views/iugu-old/profile_settings.html.haml +76 -0
  39. data/app/views/iugu-old/signup.html.haml +36 -0
  40. data/app/views/iugu/account_domains/index.html.haml +33 -0
  41. data/app/views/iugu/account_domains/instructions.html.haml +0 -0
  42. data/app/views/iugu/account_roles/edit.html.haml +17 -0
  43. data/app/views/iugu/account_roles/update.html.haml +0 -0
  44. data/app/views/iugu/account_users/index.html.haml +23 -0
  45. data/app/views/iugu/account_users/view.html.haml +0 -0
  46. data/app/views/iugu/confirmations/new.html.haml +8 -0
  47. data/app/views/iugu/invitations/edit.html.haml +8 -0
  48. data/app/views/iugu/invitations/new.html.haml +13 -0
  49. data/app/views/iugu/mailer/confirmation_instructions.html.haml +4 -0
  50. data/app/views/iugu/mailer/invitation.html.haml +1 -0
  51. data/app/views/iugu/mailer/reset_password_instructions.html.haml +4 -0
  52. data/app/views/iugu/mailer/unlock_instructions.html.haml +5 -0
  53. data/app/views/iugu/passwords/edit.html.haml +11 -0
  54. data/app/views/iugu/passwords/new.html.haml +8 -0
  55. data/app/views/iugu/registrations/edit.html.haml +15 -0
  56. data/app/views/iugu/registrations/new.html.haml +11 -0
  57. data/app/views/iugu/sessions/new.html.haml +9 -0
  58. data/app/views/iugu/settings/account.html.haml +48 -0
  59. data/app/views/iugu/settings/accounts.html.haml +33 -0
  60. data/app/views/iugu/settings/profile.html.haml +96 -0
  61. data/app/views/iugu/shared/_links.haml +19 -0
  62. data/app/views/iugu/unlocks/new.html.haml +8 -0
  63. data/app/views/layouts/settings.html.haml +46 -0
  64. data/config/initializers/account_roles.rb +5 -0
  65. data/config/initializers/devise.rb +242 -0
  66. data/config/initializers/social_accounts.rb +16 -0
  67. data/config/locales/devise.en.yml +57 -0
  68. data/config/locales/devise.pt-BR.yml +55 -0
  69. data/config/locales/iugu.en.yml +73 -0
  70. data/config/locales/iugu.pt-BR.yml +73 -0
  71. data/config/routes.rb +77 -0
  72. data/db/migrate/20120528164634_create_account.rb +11 -0
  73. data/db/migrate/20120529134109_add_devise_to_users.rb +53 -0
  74. data/db/migrate/20120529162901_add_birthdate_and_name_to_user.rb +12 -0
  75. data/db/migrate/20120529174755_add_name_and_subscription_id_and_user_id_to_account.rb +13 -0
  76. data/db/migrate/20120529180814_create_account_users.rb +12 -0
  77. data/db/migrate/20120530114709_remove_user_id_from_accounts.rb +9 -0
  78. data/db/migrate/20120531171438_create_account_roles.rb +12 -0
  79. data/db/migrate/20120604131034_add_locale_to_user.rb +9 -0
  80. data/db/migrate/20120605142527_create_social_account.rb +15 -0
  81. data/db/migrate/20120612141130_set_locale.rb +6 -0
  82. data/db/migrate/20120613173114_remove_unique_from_user_email.rb +11 -0
  83. data/db/migrate/20120615180728_create_delayed_jobs.rb +22 -0
  84. data/db/migrate/20120629154429_create_user_invitations.rb +14 -0
  85. data/db/migrate/20120629195345_add_token_to_user_invitations.rb +8 -0
  86. data/db/migrate/20120705202827_add_roles_to_user_invitations.rb +8 -0
  87. data/db/migrate/20120716145846_create_account_domain.rb +14 -0
  88. data/db/migrate/20120719162426_add_subdomain_to_account.rb +9 -0
  89. data/lib/iugusdk.rb +73 -0
  90. data/lib/iugusdk/controllers/helpers.rb +45 -0
  91. data/lib/iugusdk/engine.rb +13 -0
  92. data/lib/iugusdk/locale_filter.rb +12 -0
  93. data/lib/iugusdk/root_tenancy_url.rb +22 -0
  94. data/lib/iugusdk/valid_tenancy_urls.rb +27 -0
  95. data/lib/iugusdk/version.rb +3 -0
  96. data/lib/tasks/iugusdk_tasks.rake +4 -0
  97. data/spec/controller_macros.rb +41 -0
  98. data/spec/controllers/account_controller_spec.rb +155 -0
  99. data/spec/controllers/account_domains_controller_spec.rb +173 -0
  100. data/spec/controllers/account_roles_controller_spec.rb +48 -0
  101. data/spec/controllers/account_settings_controller_spec.rb +42 -0
  102. data/spec/controllers/account_users_controller_spec.rb +145 -0
  103. data/spec/controllers/application_domain_controller_spec.rb +29 -0
  104. data/spec/controllers/invitations_controller_spec.rb +102 -0
  105. data/spec/controllers/profile_controller_spec.rb +125 -0
  106. data/spec/controllers/settings_controller_spec.rb +14 -0
  107. data/spec/dummy/Rakefile +7 -0
  108. data/spec/dummy/app/assets/javascripts/application.js +9 -0
  109. data/spec/dummy/app/assets/stylesheets/application.css +7 -0
  110. data/spec/dummy/app/assets/stylesheets/default.sass +111 -0
  111. data/spec/dummy/app/controllers/application_controller.rb +3 -0
  112. data/spec/dummy/app/controllers/dashboard_controller.rb +8 -0
  113. data/spec/dummy/app/controllers/my_dummy_controller.rb +9 -0
  114. data/spec/dummy/app/helpers/application_helper.rb +2 -0
  115. data/spec/dummy/app/views/dashboard/index.html.haml +5 -0
  116. data/spec/dummy/app/views/dashboard/splash.html.haml +10 -0
  117. data/spec/dummy/app/views/layouts/application.html.erb +29 -0
  118. data/spec/dummy/app/views/layouts/dummy.html.erb +22 -0
  119. data/spec/dummy/app/views/my_dummy/index.html.haml +5 -0
  120. data/spec/dummy/config.ru +4 -0
  121. data/spec/dummy/config/account_roles.yml +3 -0
  122. data/spec/dummy/config/application.rb +66 -0
  123. data/spec/dummy/config/boot.rb +10 -0
  124. data/spec/dummy/config/database.yml +37 -0
  125. data/spec/dummy/config/environment.rb +5 -0
  126. data/spec/dummy/config/environments/development.rb +37 -0
  127. data/spec/dummy/config/environments/production.rb +60 -0
  128. data/spec/dummy/config/environments/test.rb +40 -0
  129. data/spec/dummy/config/initializers/backtrace_silencers.rb +7 -0
  130. data/spec/dummy/config/initializers/inflections.rb +10 -0
  131. data/spec/dummy/config/initializers/iugusdk.rb +4 -0
  132. data/spec/dummy/config/initializers/mime_types.rb +5 -0
  133. data/spec/dummy/config/initializers/secret_token.rb +7 -0
  134. data/spec/dummy/config/initializers/session_store.rb +8 -0
  135. data/spec/dummy/config/initializers/wrap_parameters.rb +14 -0
  136. data/spec/dummy/config/locales/en.yml +5 -0
  137. data/spec/dummy/config/routes.rb +69 -0
  138. data/spec/dummy/config/social_accounts.yml +6 -0
  139. data/spec/dummy/db/schema.rb +95 -0
  140. data/spec/dummy/public/404.html +26 -0
  141. data/spec/dummy/public/422.html +26 -0
  142. data/spec/dummy/public/500.html +26 -0
  143. data/spec/dummy/public/favicon.ico +0 -0
  144. data/spec/dummy/script/rails +6 -0
  145. data/spec/dummy/tmp/cache/sass/1f198e4a81e57d6c86c6fff1f0e13592b233ebc2/prettify.cssc +0 -0
  146. data/spec/dummy/tmp/cache/sass/40796b6ca2cf9112b889007328d8a4c5fdc634d8/_css3.scssc +0 -0
  147. data/spec/dummy/tmp/cache/sass/40796b6ca2cf9112b889007328d8a4c5fdc634d8/_support.scssc +0 -0
  148. data/spec/dummy/tmp/cache/sass/589e829967f8e21bd017e2d6a46ea53360f10fe0/components.sassc +0 -0
  149. data/spec/dummy/tmp/cache/sass/589e829967f8e21bd017e2d6a46ea53360f10fe0/iugu-ux.sassc +0 -0
  150. data/spec/dummy/tmp/cache/sass/589e829967f8e21bd017e2d6a46ea53360f10fe0/mixins.sassc +0 -0
  151. data/spec/dummy/tmp/cache/sass/589e829967f8e21bd017e2d6a46ea53360f10fe0/reset.sassc +0 -0
  152. data/spec/dummy/tmp/cache/sass/589e829967f8e21bd017e2d6a46ea53360f10fe0/typography.sassc +0 -0
  153. data/spec/dummy/tmp/cache/sass/589e829967f8e21bd017e2d6a46ea53360f10fe0/utilities.sassc +0 -0
  154. data/spec/dummy/tmp/cache/sass/589e829967f8e21bd017e2d6a46ea53360f10fe0/variables.sassc +0 -0
  155. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_appearance.scssc +0 -0
  156. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_background-clip.scssc +0 -0
  157. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_background-origin.scssc +0 -0
  158. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_background-size.scssc +0 -0
  159. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_border-radius.scssc +0 -0
  160. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_box-shadow.scssc +0 -0
  161. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_box-sizing.scssc +0 -0
  162. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_box.scssc +0 -0
  163. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_columns.scssc +0 -0
  164. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_font-face.scssc +0 -0
  165. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_images.scssc +0 -0
  166. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_inline-block.scssc +0 -0
  167. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_opacity.scssc +0 -0
  168. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_shared.scssc +0 -0
  169. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_text-shadow.scssc +0 -0
  170. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_transform.scssc +0 -0
  171. data/spec/dummy/tmp/cache/sass/7694fbc0853be2496915aae45b37e2d934ffc111/_transition.scssc +0 -0
  172. data/spec/dummy/tmp/cache/sass/9da4e62a062dae83baa33f29455be2ba30cf5dce/_sprites.scssc +0 -0
  173. data/spec/dummy/tmp/cache/sass/db2a23483187bf5625185da2d6f47de2a6de4989/_base.scssc +0 -0
  174. data/spec/dummy/tmp/cache/sass/db2a23483187bf5625185da2d6f47de2a6de4989/_sprite-img.scssc +0 -0
  175. data/spec/dummy/tmp/cache/sass/e5be18dde92936a4632e65289dad5788ed73dd60/base_settings.sassc +0 -0
  176. data/spec/dummy/tmp/cache/sass/e5be18dde92936a4632e65289dad5788ed73dd60/settings.sassc +0 -0
  177. data/spec/dummy/tmp/cache/sass/e764476e9a85279ad82622591ce49983ed21c149/application.sassc +0 -0
  178. data/spec/dummy/tmp/cache/sass/e764476e9a85279ad82622591ce49983ed21c149/base_settings.sassc +0 -0
  179. data/spec/dummy/tmp/cache/sass/e764476e9a85279ad82622591ce49983ed21c149/default.sassc +0 -0
  180. data/spec/dummy/tmp/cache/sass/eab9c0816f626278a6731ce2928de6fdbe99322b/_hacks.scssc +0 -0
  181. data/spec/dummy/tmp/restart.txt +0 -0
  182. data/spec/fabricators/account_domain_fabricator.rb +4 -0
  183. data/spec/fabricators/account_fabricator.rb +4 -0
  184. data/spec/fabricators/account_role_fabricator.rb +3 -0
  185. data/spec/fabricators/account_user_fabricator.rb +4 -0
  186. data/spec/fabricators/social_account_fabricator.rb +10 -0
  187. data/spec/fabricators/user_fabricator.rb +10 -0
  188. data/spec/fabricators/user_invitation_fabricator.rb +4 -0
  189. data/spec/mailers/iugu_mailer_spec.rb +22 -0
  190. data/spec/models/account_domain_spec.rb +111 -0
  191. data/spec/models/account_role_spec.rb +24 -0
  192. data/spec/models/account_spec.rb +155 -0
  193. data/spec/models/account_user_spec.rb +158 -0
  194. data/spec/models/social_account_spec.rb +36 -0
  195. data/spec/models/user_invitation_spec.rb +92 -0
  196. data/spec/models/user_spec.rb +187 -0
  197. data/spec/requests/account_domain_spec.rb +77 -0
  198. data/spec/requests/account_roles_spec.rb +45 -0
  199. data/spec/requests/account_spec.rb +97 -0
  200. data/spec/requests/account_users_spec.rb +129 -0
  201. data/spec/requests/omniauth_spec.rb +79 -0
  202. data/spec/requests/settings_spec.rb +53 -0
  203. data/spec/requests/user_invitation_spec.rb +40 -0
  204. data/spec/requests/user_spec.rb +34 -0
  205. data/spec/spec_helper.rb +116 -0
  206. data/spec/validators/email_validator_spec.rb +21 -0
  207. metadata +729 -0
@@ -0,0 +1,23 @@
1
+ class Iugu::OmniauthCallbacksController < Devise::OmniauthCallbacksController
2
+
3
+ def method_missing(provider)
4
+ if !User.omniauth_providers.index(provider).nil?
5
+ if current_user
6
+ current_user.find_or_create_social(env["omniauth.auth"])
7
+ redirect_to after_sign_in_path_for( current_user )
8
+ else
9
+ if user = User.find_or_create_by_social(env["omniauth.auth"])
10
+ select_account user
11
+ sign_in user
12
+ redirect_to after_sign_in_path_for( user )
13
+ else
14
+ redirect_to (env["omniauth.origin"] || root_path), :notice => I18n.t('errors.messages.email_already_in_use')
15
+ end
16
+ end
17
+ end
18
+ end
19
+
20
+ def passthru
21
+ render :status => 404, :text => "Not found. Authentication passthru."
22
+ end
23
+ end
@@ -0,0 +1,2 @@
1
+ class Iugu::PasswordsController < Devise::PasswordsController
2
+ end
@@ -0,0 +1,44 @@
1
+ class Iugu::ProfileController < Iugu::SettingsController
2
+
3
+ def index
4
+ @user = current_user
5
+ @social_accounts = @user.social_accounts
6
+ render 'iugu/settings/profile'
7
+ end
8
+
9
+ def update
10
+ @user = current_user
11
+ @social_accounts = @user.social_accounts
12
+ if @user.update_attributes(params[:user])
13
+ flash[:notice] = I18n.t('iugu.notices.user_update')
14
+ else
15
+ flash[:error] = @user.errors.full_messages
16
+ end
17
+ render 'iugu/settings/profile'
18
+ end
19
+
20
+ def destroy
21
+ (user = current_user).destroy
22
+ redirect_to(profile_settings_path, :notice => I18n.t("iugu.user_destruction_in") + user.destruction_job.run_at.to_s)
23
+ end
24
+
25
+ def cancel_destruction
26
+ current_user.cancel_destruction
27
+ redirect_to(profile_settings_path, :notice => I18n.t("iugu.user_destruction_undone"))
28
+ end
29
+
30
+ def destroy_social
31
+ begin
32
+ if social_account = current_user.social_accounts.where(:id => params[:id]).first.unlink
33
+ notice = I18n.t("iugu.social_unlinked")
34
+ else
35
+ notice = I18n.t("errors.messages.only_social_and_no_email")
36
+ end
37
+ rescue
38
+ notice = I18n.t("errors.messages.not_found")
39
+ end
40
+ flash[:social] = notice
41
+ redirect_to profile_settings_path
42
+ end
43
+
44
+ end
@@ -0,0 +1,3 @@
1
+ class Iugu::RegistrationsController < Devise::RegistrationsController
2
+ end
3
+
@@ -0,0 +1,2 @@
1
+ class Iugu::SessionsController < Devise::SessionsController
2
+ end
@@ -0,0 +1,11 @@
1
+ class Iugu::SettingsController < ApplicationController
2
+
3
+ before_filter :authenticate_user!, :except => :add_social
4
+
5
+ layout IuguSDK.default_layout
6
+
7
+ def index
8
+ redirect_to :profile_settings, :notice => flash[:notice]
9
+ end
10
+
11
+ end
@@ -0,0 +1,2 @@
1
+ class Iugu::UnlocksController < Devise::UnlocksController
2
+ end
@@ -0,0 +1,16 @@
1
+ class IuguMailer < Devise::Mailer
2
+
3
+ default from: "Kupz <equipe@kupz.com.br>",
4
+ reply_to: "Kupz <atendimento@kupz.com.br>"
5
+
6
+ def template_paths
7
+ "iugu/mailer"
8
+ end
9
+
10
+ def invitation(user_invitation)
11
+ @user_invitation = user_invitation
12
+ mail(to: @user_invitation.email, :subject => "Convite para sua conta") do |format|
13
+ format.html { render "iugu/mailer/invitation" }
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,53 @@
1
+ class Account < ActiveRecord::Base
2
+ # Validators
3
+
4
+ has_many :account_users, :dependent => :destroy, :include => [:roles,:account]
5
+ has_many :account_domains, :dependent => :destroy
6
+ has_many :users, :through => :account_users
7
+ handle_asynchronously :destroy, :queue => Proc.new { |p| "account_#{p.id}_destroy" },
8
+ :run_at => Proc.new { DateTime.now + IuguSDK::delay_account_exclusion }
9
+
10
+ validates :subdomain, :uniqueness => true
11
+ validate :subdomain_blacklist
12
+
13
+ def self.get_from_domain(domain)
14
+ AccountDomain.verified.find_by_url(domain).try(:account) || Account.find_by_subdomain(domain.gsub(".#{IuguSDK::application_main_host}",""))
15
+ end
16
+
17
+
18
+ def destruction_job
19
+ Delayed::Job.find_by_queue("account_#{id}_destroy")
20
+ end
21
+
22
+ def destroying?
23
+ !!destruction_job
24
+ end
25
+
26
+ def cancel_destruction
27
+ destruction_job.try(:destroy) unless destruction_job.try(:locked_at)
28
+ end
29
+
30
+ def valid_user_for_account?( user )
31
+ user = user.try(:id) if user.is_a? Object
32
+ users.exists? user
33
+ end
34
+
35
+ def is?(role, user)
36
+ account_users.find_by_user_id(user.id).is?(role.to_s)
37
+ end
38
+
39
+ def name
40
+ (super.blank? ? "#{I18n.t('iugu.account')} ##{id}" : super)
41
+ end
42
+
43
+ private
44
+
45
+ def subdomain_blacklist
46
+ if subdomain
47
+ IuguSDK::custom_domain_invalid_prefixes.each do |invalid_prefix|
48
+ errors.add(:subdomain, "Subdomain blacklisted") if subdomain == invalid_prefix
49
+ end
50
+ end
51
+ end
52
+
53
+ end
@@ -0,0 +1,69 @@
1
+ require 'resolv'
2
+ require 'uri'
3
+ class AccountDomain < ActiveRecord::Base
4
+ belongs_to :account
5
+ validates :url, :account_id, :presence => true
6
+ validate :validate_pattern, :validate_blacklist
7
+
8
+ scope :verified, where(:verified => true)
9
+
10
+ def normalize_host
11
+ begin
12
+ normalized_url = url
13
+ normalized_url = normalized_url.gsub('www.','')
14
+ normalized_url = normalized_url.gsub('http://','')
15
+ normalized_url = normalized_url.gsub('https://','')
16
+ normalized_url = 'http://' + normalized_url
17
+ URI.parse(normalized_url).host
18
+ rescue
19
+ nil
20
+ end
21
+ end
22
+
23
+ def calculate_token
24
+ url = normalize_host
25
+ Digest::SHA1.hexdigest( "#{id}#{url}" )[8..24]
26
+ end
27
+
28
+ def verify
29
+ url = normalize_host
30
+ ref_id = self.calculate_token
31
+ checked=false
32
+ begin
33
+ Socket.gethostbyname( "#{ref_id}.#{url}" )
34
+ checked=true
35
+ rescue SocketError
36
+ end
37
+ begin
38
+ response = Net::HTTP.start(url, 80) {|http| http.head("/#{ref_id}.html") }
39
+ checked = true if response.code == "200"
40
+ rescue
41
+ end
42
+ AccountDomain.where(:url => self.url).update_all(:verified => false) if checked == true
43
+ update_attribute(:verified, checked)
44
+ checked
45
+ end
46
+
47
+ def set_primary
48
+ AccountDomain.where(:account_id => account_id).update_all(:primary => false)
49
+ update_attribute(:primary, true)
50
+ end
51
+
52
+ private
53
+
54
+ def validate_pattern
55
+ if url
56
+ errors.add(:url, "Invalid Pattern") unless url.match /^([a-z0-9]*\.)*[a-z0-9]*$/
57
+ end
58
+ end
59
+
60
+ def validate_blacklist
61
+ if url
62
+ IuguSDK::custom_domain_invalid_hosts.each do |invalid_host|
63
+ errors.add(:url, "Domain on Blacklist") if url == invalid_host
64
+ end
65
+ end
66
+ end
67
+
68
+
69
+ end
@@ -0,0 +1,24 @@
1
+ class AccountRole < ActiveRecord::Base
2
+ belongs_to :account_user
3
+ validate :valid_role?
4
+
5
+ validates_uniqueness_of :name, :scope => :account_user_id, :allow_nil => false
6
+ validates_presence_of :account_user
7
+
8
+ before_destroy do
9
+ false if only_owner?
10
+ end
11
+
12
+ def self.roles
13
+ APP_ROLES['roles']
14
+ end
15
+
16
+ private
17
+ def valid_role?
18
+ errors.add(:name, "errors.messages.invalid_role") unless APP_ROLES['roles'].include? name
19
+ end
20
+
21
+ def only_owner?
22
+ self.name == APP_ROLES['owner_role'] && AccountRole.joins(:account_user).where('account_users.account_id = ? AND name = ?', account_user.account_id, :owner).count <= 1
23
+ end
24
+ end
@@ -0,0 +1,55 @@
1
+ class AccountUser < ActiveRecord::Base
2
+ has_many :roles, :class_name => "AccountRole", :dependent => :destroy
3
+ belongs_to :user
4
+ belongs_to :account
5
+
6
+ after_create :add_default_roles
7
+
8
+ validates_presence_of :user
9
+ validates_presence_of :account
10
+
11
+ handle_asynchronously :destroy, :queue => Proc.new { |p| "account_user_#{p.id}_destroy" },
12
+ :run_at => Proc.new { DateTime.now + IuguSDK::delay_account_user_exclusion }
13
+
14
+
15
+ def destruction_job
16
+ Delayed::Job.find_by_queue("account_user_#{id}_destroy")
17
+ end
18
+
19
+ def destroying?
20
+ !!destruction_job
21
+ end
22
+
23
+ def cancel_destruction
24
+ destruction_job.try(:destroy) unless destruction_job.try(:locked_at)
25
+ end
26
+
27
+ # Write tests for this
28
+ def add_default_roles
29
+ roles.create( { :name => APP_ROLES[ "owner_role" ] } )
30
+ roles.create( { :name => APP_ROLES[ "admin_role" ] } ) if APP_ROLES[ "owner_role" ] != APP_ROLES[ "admin_role" ]
31
+ end
32
+
33
+ def set_roles(new_roles)
34
+ if new_roles.nil?
35
+ roles.destroy_all
36
+ else
37
+ valid = true
38
+ new_roles.each do |new_role|
39
+ valid = false unless APP_ROLES['roles'].include? new_role
40
+ end
41
+ return false unless valid
42
+ roles.destroy_all
43
+ new_roles.each do |new_role|
44
+ roles.create( :name => new_role )
45
+ end
46
+ end
47
+ true
48
+ end
49
+
50
+ def is?(role)
51
+ role = APP_ROLES[ "owner_role" ] if role.to_s == "owner"
52
+ role = APP_ROLES[ "admin_role" ] if role.to_s == "admin"
53
+ roles.exists?(:name => role)
54
+ end
55
+ end
@@ -0,0 +1,10 @@
1
+ class AvailableLanguage
2
+ def self.all
3
+ begin
4
+ YAML.load_file("#{Rails.root.to_s}/config/available_language.yml")['locales']
5
+ rescue
6
+ ["en"]
7
+ end
8
+ end
9
+
10
+ end
@@ -0,0 +1,14 @@
1
+ class SocialAccount < ActiveRecord::Base
2
+
3
+ belongs_to :user
4
+
5
+ def unlink
6
+ if self.user.social_accounts.count == 1 && (self.user.email.blank? || self.user.encrypted_password.blank?)
7
+ errors.add(:base, "only_social_and_no_email")
8
+ false
9
+ else
10
+ self.destroy
11
+ end
12
+ end
13
+
14
+ end
@@ -0,0 +1,107 @@
1
+ class User < ActiveRecord::Base
2
+ # Include default devise modules. Others available are:
3
+ # :token_authenticatable, :trackable, :validatable,
4
+ # :lockable and :timeoutable
5
+
6
+ has_many :account_users, :dependent => :destroy, :include => [:roles,:account]
7
+ has_many :accounts, :through => :account_users
8
+ has_many :social_accounts, :dependent => :destroy
9
+
10
+ handle_asynchronously :destroy, :queue => Proc.new { |p| "user_#{p.id}_destroy" },
11
+ :run_at => Proc.new { DateTime.now + IuguSDK::delay_user_exclusion }
12
+
13
+ devise :database_authenticatable, :registerable, :confirmable,
14
+ :recoverable, :rememberable, :validatable, :omniauthable
15
+
16
+ # Setup accessible (or protected) attributes for your model
17
+ attr_accessible :email, :password, :password_confirmation, :remember_me, :locale, :name, :birthdate
18
+
19
+ after_create :create_account_for_user
20
+
21
+ validates :email, :email => true
22
+
23
+ def destruction_job
24
+ Delayed::Job.find_by_queue("user_#{id}_destroy")
25
+ end
26
+
27
+ def destroying?
28
+ !!destruction_job
29
+ end
30
+
31
+ def cancel_destruction
32
+ destruction_job.try(:destroy) unless destruction_job.try(:locked_at)
33
+ end
34
+
35
+ def is?(role, account)
36
+ account.account_users.find_by_user_id(self.id).is?(role.to_s)
37
+ end
38
+
39
+ def has_social?
40
+ !social_accounts.empty?
41
+ end
42
+
43
+ def find_or_create_social(auth)
44
+ social_accounts.where("provider = ? AND social_id = ?", auth["provider"], auth["uid"]).first || create_social(auth)
45
+ end
46
+
47
+ def self.find_or_create_by_social(auth)
48
+ social_account = SocialAccount.where("provider = ? AND social_id = ?", auth["provider"], auth["uid"]).first
49
+ unless user = social_account.try(:user)
50
+ user = User.new
51
+ if auth["extra"]["raw_info"]["email"]
52
+ return false if !User.where(:email => auth["extra"]["raw_info"]["email"]).empty?
53
+ user.email = auth["extra"]["raw_info"]["email"]
54
+ end
55
+ user.skip_confirmation!
56
+ user.save(:validate => false)
57
+ social_account = user.create_social(auth)
58
+ end
59
+ social_account.update_attribute( 'token' , auth['credentials']['token'] )
60
+ user
61
+ end
62
+
63
+ def create_social(auth)
64
+ social_accounts.create! do |social_account|
65
+ social_account.provider = auth["provider"]
66
+ social_account.social_id = auth["uid"]
67
+ social_account.token = auth["credentials"]["token"]
68
+ social_account.user_id = self.id
69
+ end
70
+ end
71
+
72
+ def devise_mailer
73
+ IuguMailer
74
+ end
75
+
76
+ def accountable?
77
+ !!!@skip_account_creation
78
+ end
79
+
80
+ def skip_create_account!
81
+ @skip_account_creation = true
82
+ end
83
+
84
+ def default_account( account_id=nil )
85
+ account_id = account_id.id if account_id.is_a? Account
86
+ self.accounts.where( [ "accounts.id = ?", account_id] ).first || self.accounts.first
87
+ end
88
+
89
+ private
90
+
91
+ def email_required?
92
+ !has_social?
93
+ end
94
+
95
+ #def self.reconfirmable
96
+ # true
97
+ #end
98
+
99
+ @reconfirmable = true
100
+
101
+ def create_account_for_user
102
+ if accountable?
103
+ new_account = Account.create({})
104
+ account_user = new_account.account_users.create( { :user => self } )
105
+ end
106
+ end
107
+ end