enju_news 0.0.2

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 (108) hide show
  1. data/MIT-LICENSE +20 -0
  2. data/README.rdoc +3 -0
  3. data/Rakefile +47 -0
  4. data/app/controllers/news_feeds_controller.rb +101 -0
  5. data/app/controllers/news_posts_controller.rb +98 -0
  6. data/app/helpers/news_feeds_helper.rb +2 -0
  7. data/app/helpers/news_posts_helper.rb +2 -0
  8. data/app/models/news_feed.rb +83 -0
  9. data/app/models/news_feed_sweeper.rb +12 -0
  10. data/app/models/news_post.rb +15 -0
  11. data/app/views/news_feeds/_content.html.erb +9 -0
  12. data/app/views/news_feeds/_content_atom.html.erb +16 -0
  13. data/app/views/news_feeds/_content_rss.html.erb +16 -0
  14. data/app/views/news_feeds/_form.html.erb +14 -0
  15. data/app/views/news_feeds/_list.html.erb +7 -0
  16. data/app/views/news_feeds/edit.html.erb +29 -0
  17. data/app/views/news_feeds/index.html.erb +42 -0
  18. data/app/views/news_feeds/new.html.erb +28 -0
  19. data/app/views/news_feeds/show.html.erb +34 -0
  20. data/app/views/news_posts/_form.html.erb +44 -0
  21. data/app/views/news_posts/edit.html.erb +13 -0
  22. data/app/views/news_posts/index.atom.builder +11 -0
  23. data/app/views/news_posts/index.html.erb +42 -0
  24. data/app/views/news_posts/index.rss.builder +32 -0
  25. data/app/views/news_posts/new.html.erb +12 -0
  26. data/app/views/news_posts/show.html.erb +49 -0
  27. data/config/locales/translation_en.yml +28 -0
  28. data/config/locales/translation_ja.yml +28 -0
  29. data/config/routes.rb +4 -0
  30. data/db/migrate/20081031033632_create_news_feeds.rb +13 -0
  31. data/db/migrate/20090126071155_create_news_posts.rb +18 -0
  32. data/db/migrate/20110220103937_add_url_to_news_post.rb +9 -0
  33. data/lib/enju_news.rb +6 -0
  34. data/lib/enju_news/engine.rb +12 -0
  35. data/lib/enju_news/expire_editable_fragment.rb +15 -0
  36. data/lib/enju_news/version.rb +3 -0
  37. data/lib/tasks/enju_news_tasks.rake +4 -0
  38. data/spec/cassette_library/NewsFeed.yml +1998 -0
  39. data/spec/controllers/news_feeds_controller_spec.rb +445 -0
  40. data/spec/controllers/news_posts_controller_spec.rb +443 -0
  41. data/spec/dummy/Rakefile +7 -0
  42. data/spec/dummy/app/assets/javascripts/application.js +9 -0
  43. data/spec/dummy/app/assets/stylesheets/application.css +7 -0
  44. data/spec/dummy/app/controllers/application_controller.rb +52 -0
  45. data/spec/dummy/app/helpers/application_helper.rb +2 -0
  46. data/spec/dummy/app/models/ability.rb +22 -0
  47. data/spec/dummy/app/models/library_group.rb +86 -0
  48. data/spec/dummy/app/models/role.rb +46 -0
  49. data/spec/dummy/app/models/user.rb +94 -0
  50. data/spec/dummy/app/models/user_group.rb +40 -0
  51. data/spec/dummy/app/models/user_has_role.rb +5 -0
  52. data/spec/dummy/app/views/layouts/application.html.erb +14 -0
  53. data/spec/dummy/app/views/page/403.html.erb +9 -0
  54. data/spec/dummy/app/views/page/403.mobile.erb +5 -0
  55. data/spec/dummy/app/views/page/403.xml.erb +4 -0
  56. data/spec/dummy/app/views/page/404.html.erb +9 -0
  57. data/spec/dummy/app/views/page/404.mobile.erb +5 -0
  58. data/spec/dummy/app/views/page/404.xml.erb +4 -0
  59. data/spec/dummy/config.ru +4 -0
  60. data/spec/dummy/config/application.rb +47 -0
  61. data/spec/dummy/config/boot.rb +10 -0
  62. data/spec/dummy/config/database.yml +25 -0
  63. data/spec/dummy/config/environment.rb +5 -0
  64. data/spec/dummy/config/environments/development.rb +30 -0
  65. data/spec/dummy/config/environments/production.rb +60 -0
  66. data/spec/dummy/config/environments/test.rb +39 -0
  67. data/spec/dummy/config/initializers/backtrace_silencers.rb +7 -0
  68. data/spec/dummy/config/initializers/devise.rb +205 -0
  69. data/spec/dummy/config/initializers/inflections.rb +10 -0
  70. data/spec/dummy/config/initializers/mime_types.rb +5 -0
  71. data/spec/dummy/config/initializers/secret_token.rb +7 -0
  72. data/spec/dummy/config/initializers/session_store.rb +8 -0
  73. data/spec/dummy/config/initializers/wrap_parameters.rb +14 -0
  74. data/spec/dummy/config/locales/en.yml +5 -0
  75. data/spec/dummy/config/routes.rb +60 -0
  76. data/spec/dummy/db/migrate/077_create_user_groups.rb +16 -0
  77. data/spec/dummy/db/migrate/080_create_library_groups.rb +20 -0
  78. data/spec/dummy/db/migrate/20110222073537_add_url_to_library_group.rb +9 -0
  79. data/spec/dummy/db/migrate/20110318183304_add_valid_period_for_new_user_to_user_group.rb +13 -0
  80. data/spec/dummy/db/migrate/20111201121844_create_roles.rb +12 -0
  81. data/spec/dummy/db/migrate/20111201155456_create_users.rb +16 -0
  82. data/spec/dummy/db/migrate/20111201155513_add_devise_to_users.rb +44 -0
  83. data/spec/dummy/db/migrate/20111201163718_create_user_has_roles.rb +10 -0
  84. data/spec/dummy/db/schema.rb +116 -0
  85. data/spec/dummy/db/test.sqlite3 +0 -0
  86. data/spec/dummy/lib/master_model.rb +19 -0
  87. data/spec/dummy/lib/url_validator.rb +10 -0
  88. data/spec/dummy/public/404.html +26 -0
  89. data/spec/dummy/public/422.html +26 -0
  90. data/spec/dummy/public/500.html +26 -0
  91. data/spec/dummy/public/favicon.ico +0 -0
  92. data/spec/dummy/script/rails +6 -0
  93. data/spec/factories/news_feed.rb +6 -0
  94. data/spec/factories/news_post.rb +7 -0
  95. data/spec/factories/user.rb +37 -0
  96. data/spec/fixtures/library_groups.yml +33 -0
  97. data/spec/fixtures/news_feeds.yml +11 -0
  98. data/spec/fixtures/news_posts.yml +13 -0
  99. data/spec/fixtures/roles.yml +21 -0
  100. data/spec/fixtures/user_has_roles.yml +41 -0
  101. data/spec/fixtures/users.yml +93 -0
  102. data/spec/models/news_feed_spec.rb +31 -0
  103. data/spec/models/news_post_spec.rb +5 -0
  104. data/spec/spec_helper.rb +42 -0
  105. data/spec/support/controller_macros.rb +46 -0
  106. data/spec/support/devise.rb +4 -0
  107. data/spec/support/vcr.rb +9 -0
  108. metadata +430 -0
@@ -0,0 +1,7 @@
1
+ #!/usr/bin/env rake
2
+ # Add your own tasks in files placed in lib/tasks ending in .rake,
3
+ # for example lib/tasks/capistrano.rake, and they will automatically be available to Rake.
4
+
5
+ require File.expand_path('../config/application', __FILE__)
6
+
7
+ Dummy::Application.load_tasks
@@ -0,0 +1,9 @@
1
+ // This is a manifest file that'll be compiled into including all the files listed below.
2
+ // Add new JavaScript/Coffee code in separate files in this directory and they'll automatically
3
+ // be included in the compiled file accessible from http://example.com/assets/application.js
4
+ // It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
5
+ // the compiled file.
6
+ //
7
+ //= require jquery
8
+ //= require jquery_ujs
9
+ //= require_tree .
@@ -0,0 +1,7 @@
1
+ /*
2
+ * This is a manifest file that'll automatically include all the stylesheets available in this directory
3
+ * and any sub-directories. You're free to add application-wide styles to this file and they'll appear at
4
+ * the top of the compiled file, but it's generally better to create a new file per style scope.
5
+ *= require_self
6
+ *= require_tree .
7
+ */
@@ -0,0 +1,52 @@
1
+ class ApplicationController < ActionController::Base
2
+ protect_from_forgery
3
+
4
+ rescue_from CanCan::AccessDenied, :with => :render_403
5
+ rescue_from ActiveRecord::RecordNotFound, :with => :render_404
6
+
7
+ private
8
+ def render_403
9
+ return if performed?
10
+ if user_signed_in?
11
+ respond_to do |format|
12
+ format.html {render :template => 'page/403', :status => 403}
13
+ format.xml {render :template => 'page/403', :status => 403}
14
+ format.json
15
+ end
16
+ else
17
+ respond_to do |format|
18
+ format.html {redirect_to new_user_session_url}
19
+ format.xml {render :template => 'page/403', :status => 403}
20
+ format.json
21
+ end
22
+ end
23
+ end
24
+
25
+ def render_404
26
+ return if performed?
27
+ respond_to do |format|
28
+ format.html {render :template => 'page/404', :status => 404}
29
+ format.mobile {render :template => 'page/404', :status => 404}
30
+ format.xml {render :template => 'page/404', :status => 404}
31
+ format.json
32
+ end
33
+ end
34
+
35
+ def access_denied
36
+ raise CanCan::AccessDenied
37
+ end
38
+
39
+ def current_ability
40
+ @current_ability ||= Ability.new(current_user, request.remote_ip)
41
+ end
42
+
43
+ def move_position(resource, direction, redirect = true)
44
+ if ['higher', 'lower'].include?(direction)
45
+ resource.send("move_#{direction}")
46
+ if redirect
47
+ redirect_to url_for(:controller => resource.class.to_s.pluralize.underscore)
48
+ return
49
+ end
50
+ end
51
+ end
52
+ end
@@ -0,0 +1,2 @@
1
+ module ApplicationHelper
2
+ end
@@ -0,0 +1,22 @@
1
+ class Ability
2
+ include CanCan::Ability
3
+
4
+ def initialize(user, ip_addess = nil)
5
+ case user.try(:role).try(:name)
6
+ when 'Administrator'
7
+ can :manage, NewsFeed
8
+ can :manage, NewsPost
9
+ when 'Librarian'
10
+ can :read, NewsFeed
11
+ can :read, NewsPost
12
+ when 'User'
13
+ can :read, NewsPost do |news_post|
14
+ !news_post.draft?
15
+ end
16
+ else
17
+ can :read, NewsPost do |news_post|
18
+ !news_post.draft?
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,86 @@
1
+ # -*- encoding: utf-8 -*-
2
+ class LibraryGroup < ActiveRecord::Base
3
+ attr_accessible :name, :display_name, :short_name, :email, :my_networks,
4
+ :login_banner, :note, :country_id, :admin_networks, :url
5
+
6
+ #include Singleton
7
+ #include Configurator
8
+ include MasterModel
9
+
10
+ has_many :libraries
11
+ belongs_to :country
12
+
13
+ validates :email, :format => {:with => /\A([\w\.%\+\-]+)@([\w\-]+\.)+([\w]{2,})\z/i}, :presence => true
14
+ validates :url, :presence => true, :url => true
15
+ after_save :clear_site_config_cache
16
+
17
+ def clear_site_config_cache
18
+ Rails.cache.delete('library_site_config')
19
+ end
20
+
21
+ def self.site_config
22
+ #if Rails.env == 'production'
23
+ # Rails.cache.fetch('library_site_config'){LibraryGroup.find(1)}
24
+ #else
25
+ LibraryGroup.find(1)
26
+ #end
27
+ rescue ActiveRecord::RecordNotFound
28
+ nil
29
+ end
30
+
31
+ def self.system_name(locale = I18n.locale)
32
+ LibraryGroup.site_config.display_name.localize(locale)
33
+ end
34
+
35
+ def config?
36
+ true if self == LibraryGroup.site_config
37
+ end
38
+
39
+ def real_libraries
40
+ # 物理的な図書館 = IDが1以外
41
+ libraries.where('id != 1').all
42
+ end
43
+
44
+ def network_access_allowed?(ip_address, options = {})
45
+ options = {:network_type => :lan}.merge(options)
46
+ client_ip = IPAddr.new(ip_address)
47
+ case options[:network_type]
48
+ when :admin
49
+ allowed_networks = self.admin_networks.to_s.split
50
+ else
51
+ allowed_networks = self.my_networks.to_s.split
52
+ end
53
+ allowed_networks.each do |allowed_network|
54
+ begin
55
+ network = IPAddr.new(allowed_network)
56
+ return true if network.include?(client_ip)
57
+ rescue ArgumentError
58
+ nil
59
+ end
60
+ end
61
+ return false
62
+ end
63
+ end
64
+
65
+
66
+ # == Schema Information
67
+ #
68
+ # Table name: library_groups
69
+ #
70
+ # id :integer not null, primary key
71
+ # name :string(255) not null
72
+ # display_name :text
73
+ # short_name :string(255) not null
74
+ # email :string(255)
75
+ # my_networks :text
76
+ # login_banner :text
77
+ # note :text
78
+ # country_id :integer
79
+ # created_at :datetime not null
80
+ # updated_at :datetime not null
81
+ # admin_networks :text
82
+ # allow_bookmark_external_url :boolean default(FALSE), not null
83
+ # position :integer
84
+ # url :string(255) default("http://localhost:3000/")
85
+ #
86
+
@@ -0,0 +1,46 @@
1
+ class Role < ActiveRecord::Base
2
+ include MasterModel
3
+ default_scope :order => "roles.position"
4
+ has_many :user_has_roles
5
+ has_many :users, :through => :user_has_roles
6
+ after_save :clear_all_cache
7
+ after_destroy :clear_all_cache
8
+
9
+ extend FriendlyId
10
+ friendly_id :name
11
+
12
+ def localized_name
13
+ display_name.localize
14
+ end
15
+
16
+ def self.all_cache
17
+ if Rails.env == 'production'
18
+ Rails.cache.fetch('role_all'){Role.select(:name).all}
19
+ else
20
+ Role.select(:name)
21
+ end
22
+ end
23
+
24
+ def clear_all_cache
25
+ Rails.cache.delete('role_all')
26
+ end
27
+
28
+ def self.default_role
29
+ Rails.cache.fetch('default_role'){Role.find('Guest')}
30
+ end
31
+ end
32
+
33
+ # == Schema Information
34
+ #
35
+ # Table name: roles
36
+ #
37
+ # id :integer not null, primary key
38
+ # name :string(255) not null
39
+ # display_name :string(255)
40
+ # note :text
41
+ # created_at :datetime
42
+ # updated_at :datetime
43
+ # score :integer default(0), not null
44
+ # position :integer
45
+ #
46
+
@@ -0,0 +1,94 @@
1
+ class User < ActiveRecord::Base
2
+ # Include default devise modules. Others available are:
3
+ # :token_authenticatable, :encryptable, :confirmable, :lockable, :timeoutable and :omniauthable
4
+ devise :database_authenticatable, :registerable,
5
+ :recoverable, :rememberable, :trackable, :validatable
6
+
7
+ # Setup accessible (or protected) attributes for your model
8
+ attr_accessible :email, :password, :password_confirmation, :remember_me
9
+
10
+ has_one :patron
11
+ has_one :user_has_role
12
+ has_one :role, :through => :user_has_role
13
+ belongs_to :user_group
14
+ belongs_to :required_role, :class_name => 'Role', :foreign_key => 'required_role_id'
15
+ has_many :checkouts, :dependent => :nullify
16
+ has_many :reserves, :dependent => :destroy
17
+ has_many :reserved_manifestations, :through => :reserves, :source => :manifestation
18
+ has_many :checkout_stat_has_users
19
+ has_many :user_checkout_stats, :through => :checkout_stat_has_users
20
+ has_many :reserve_stat_has_users
21
+ has_many :user_reserve_stats, :through => :reserve_stat_has_users
22
+ has_many :baskets, :dependent => :destroy
23
+ belongs_to :library
24
+
25
+ before_destroy :check_item_before_destroy
26
+
27
+ extend FriendlyId
28
+ friendly_id :username
29
+
30
+ def check_item_before_destroy
31
+ # TODO: 貸出記録を残す場合
32
+ if checkouts.size > 0
33
+ raise 'This user has items still checked out.'
34
+ end
35
+ end
36
+
37
+ def reset_checkout_icalendar_token
38
+ self.checkout_icalendar_token = Devise.friendly_token
39
+ end
40
+
41
+ def delete_checkout_icalendar_token
42
+ self.checkout_icalendar_token = nil
43
+ end
44
+
45
+ def checked_item_count
46
+ checkout_count = {}
47
+ CheckoutType.all.each do |checkout_type|
48
+ # 資料種別ごとの貸出中の冊数を計算
49
+ checkout_count[:"#{checkout_type.name}"] = self.checkouts.count_by_sql(["
50
+ SELECT count(item_id) FROM checkouts
51
+ WHERE item_id IN (
52
+ SELECT id FROM items
53
+ WHERE checkout_type_id = ?
54
+ )
55
+ AND user_id = ? AND checkin_id IS NULL", checkout_type.id, self.id]
56
+ )
57
+ end
58
+ return checkout_count
59
+ end
60
+
61
+ def reached_reservation_limit?(manifestation)
62
+ return true if self.user_group.user_group_has_checkout_types.available_for_carrier_type(manifestation.carrier_type).where(:user_group_id => self.user_group.id).collect(&:reservation_limit).max.to_i <= self.reserves.waiting.size
63
+ false
64
+ end
65
+
66
+ def has_role?(role_in_question)
67
+ return false unless role
68
+ return true if role.name == role_in_question
69
+ case role.name
70
+ when 'Administrator'
71
+ return true
72
+ when 'Librarian'
73
+ return true if role_in_question == 'User'
74
+ else
75
+ false
76
+ end
77
+ end
78
+
79
+ if defined?(EnjuMessage)
80
+ has_many :sent_messages, :foreign_key => 'sender_id', :class_name => 'Message'
81
+ has_many :received_messages, :foreign_key => 'receiver_id', :class_name => 'Message'
82
+
83
+ def send_message(status, options = {})
84
+ MessageRequest.transaction do
85
+ request = MessageRequest.new
86
+ request.sender = User.find(1)
87
+ request.receiver = self
88
+ request.message_template = MessageTemplate.localized_template(status, self.locale)
89
+ request.save_message_body(options)
90
+ request.sm_send_message!
91
+ end
92
+ end
93
+ end
94
+ end
@@ -0,0 +1,40 @@
1
+ # -*- encoding: utf-8 -*-
2
+ class UserGroup < ActiveRecord::Base
3
+ attr_accessible :name, :display_name, :note, :valid_period_for_new_user,
4
+ :expired_at, :number_of_day_to_notify_overdue,
5
+ :number_of_day_to_notify_overdue,
6
+ :number_of_day_to_notify_due_date,
7
+ :number_of_time_to_notify_overdue
8
+
9
+ include MasterModel
10
+ default_scope :order => "user_groups.position"
11
+ has_many :users
12
+
13
+ validates_numericality_of :valid_period_for_new_user,
14
+ :greater_than_or_equal_to => 0,
15
+ :allow_blank => true
16
+
17
+ def self.per_page
18
+ 10
19
+ end
20
+ end
21
+
22
+ # == Schema Information
23
+ #
24
+ # Table name: user_groups
25
+ #
26
+ # id :integer not null, primary key
27
+ # name :string(255)
28
+ # display_name :text
29
+ # note :text
30
+ # position :integer
31
+ # created_at :datetime
32
+ # updated_at :datetime
33
+ # deleted_at :datetime
34
+ # valid_period_for_new_user :integer default(0), not null
35
+ # expired_at :datetime
36
+ # number_of_day_to_notify_overdue :integer default(1), not null
37
+ # number_of_day_to_notify_due_date :integer default(7), not null
38
+ # number_of_time_to_notify_overdue :integer default(3), not null
39
+ #
40
+
@@ -0,0 +1,5 @@
1
+ class UserHasRole < ActiveRecord::Base
2
+ attr_accessible :user_id, :role_id
3
+ belongs_to :user
4
+ belongs_to :role
5
+ end
@@ -0,0 +1,14 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>Dummy</title>
5
+ <%= stylesheet_link_tag "application" %>
6
+ <%= javascript_include_tag "application" %>
7
+ <%= csrf_meta_tags %>
8
+ </head>
9
+ <body>
10
+
11
+ <%= yield %>
12
+
13
+ </body>
14
+ </html>
@@ -0,0 +1,9 @@
1
+ <div id="content_detail" class="ui-corner-all">
2
+ <h1 class="title"><%= t('page.access_denied') -%></h1>
3
+ <div id="content_list">
4
+ <%= render 'page/search_form' %>
5
+ </div>
6
+ </div>
7
+
8
+ <div id="submenu" class="ui-corner-all">
9
+ </div>
@@ -0,0 +1,5 @@
1
+ <div data-role="header">
2
+ <h2 class="title"><%= t('page.access_denied') -%></h2>
3
+ </div>
4
+ <div data-role="content">
5
+ </div>
@@ -0,0 +1,4 @@
1
+ <?xml version="1.0" encoding="utf-8" ?>
2
+ <error>
3
+ <status>403</status>
4
+ </error>
@@ -0,0 +1,9 @@
1
+ <div id="content_detail" class="ui-corner-all">
2
+ <h1 class="title"><%= t('page.not_found') -%></h1>
3
+ <div id="content_list">
4
+ <%= render 'page/search_form' %>
5
+ </div>
6
+ </div>
7
+
8
+ <div id="submenu" class="ui-corner-all">
9
+ </div>
@@ -0,0 +1,5 @@
1
+ <div data-role="header">
2
+ <h2 class="title"><%= t('page.not_found') -%></h2>
3
+ </div>
4
+ <div data-role="content">
5
+ </div>
@@ -0,0 +1,4 @@
1
+ <?xml version="1.0" encoding="utf-8" ?>
2
+ <error>
3
+ <status>404</status>
4
+ </error>