]> git.openstreetmap.org Git - rails.git/blob - app/controllers/diary_entries_controller.rb
Merge remote-tracking branch 'upstream/pull/5049'
[rails.git] / app / controllers / diary_entries_controller.rb
1 class DiaryEntriesController < ApplicationController
2   include UserMethods
3   include PaginationMethods
4
5   layout "site", :except => :rss
6
7   before_action :authorize_web
8   before_action :set_locale
9   before_action :check_database_readable
10
11   authorize_resource
12
13   before_action :lookup_user, :only => :show
14   before_action :check_database_writable, :only => [:new, :create, :edit, :update, :hide, :unhide, :subscribe, :unsubscribe]
15
16   allow_thirdparty_images :only => [:new, :create, :edit, :update, :index, :show]
17
18   def index
19     if params[:display_name]
20       @user = User.active.find_by(:display_name => params[:display_name])
21
22       if @user
23         @title = t ".user_title", :user => @user.display_name
24         entries = @user.diary_entries
25       else
26         render_unknown_user params[:display_name]
27         return
28       end
29     elsif params[:friends]
30       if current_user
31         @title = t ".title_friends"
32         entries = DiaryEntry.where(:user => current_user.friends)
33       else
34         require_user
35         return
36       end
37     elsif params[:nearby]
38       if current_user
39         @title = t ".title_nearby"
40         entries = DiaryEntry.where(:user => current_user.nearby)
41       else
42         require_user
43         return
44       end
45     else
46       entries = DiaryEntry.joins(:user).where(:users => { :status => %w[active confirmed] })
47
48       if params[:language]
49         @title = t ".in_language_title", :language => Language.find(params[:language]).english_name
50         entries = entries.where(:language_code => params[:language])
51       else
52         candidate_codes = preferred_languages.flat_map(&:candidates).uniq.map(&:to_s)
53         @languages = Language.where(:code => candidate_codes).in_order_of(:code, candidate_codes)
54         @title = t ".title"
55       end
56     end
57
58     entries = entries.visible unless can? :unhide, DiaryEntry
59
60     @params = params.permit(:display_name, :friends, :nearby, :language)
61
62     @entries, @newer_entries_id, @older_entries_id = get_page_items(entries, :includes => [:user, :language])
63   end
64
65   def show
66     entries = @user.diary_entries
67     entries = entries.visible unless can? :unhide, DiaryEntry
68     @entry = entries.find_by(:id => params[:id])
69     if @entry
70       @title = t ".title", :user => params[:display_name], :title => @entry.title
71       @og_image = @entry.body.image
72       @og_image_alt = @entry.body.image_alt
73       @comments = can?(:unhide, DiaryComment) ? @entry.comments : @entry.visible_comments
74     else
75       @title = t "diary_entries.no_such_entry.title", :id => params[:id]
76       render :action => "no_such_entry", :status => :not_found
77     end
78   end
79
80   def new
81     @title = t ".title"
82
83     default_lang = current_user.preferences.find_by(:k => "diary.default_language")
84     lang_code = default_lang ? default_lang.v : current_user.preferred_language
85     @diary_entry = DiaryEntry.new(entry_params.merge(:language_code => lang_code))
86     set_map_location
87     render :action => "new"
88   end
89
90   def edit
91     @title = t ".title"
92     @diary_entry = DiaryEntry.find(params[:id])
93
94     redirect_to diary_entry_path(@diary_entry.user, @diary_entry) if current_user != @diary_entry.user
95
96     set_map_location
97   rescue ActiveRecord::RecordNotFound
98     render :action => "no_such_entry", :status => :not_found
99   end
100
101   def create
102     @title = t "diary_entries.new.title"
103
104     @diary_entry = DiaryEntry.new(entry_params)
105     @diary_entry.user = current_user
106
107     if @diary_entry.save
108       default_lang = current_user.preferences.find_by(:k => "diary.default_language")
109       if default_lang
110         default_lang.v = @diary_entry.language_code
111         default_lang.save!
112       else
113         current_user.preferences.create(:k => "diary.default_language", :v => @diary_entry.language_code)
114       end
115
116       # Subscribe user to diary comments
117       @diary_entry.subscriptions.create(:user => current_user)
118
119       redirect_to :action => "index", :display_name => current_user.display_name
120     else
121       render :action => "new"
122     end
123   end
124
125   def update
126     @title = t "diary_entries.edit.title"
127     @diary_entry = DiaryEntry.find(params[:id])
128
129     if cannot?(:update, @diary_entry) ||
130        (params[:diary_entry] && @diary_entry.update(entry_params))
131       redirect_to diary_entry_path(@diary_entry.user, @diary_entry)
132     else
133       set_map_location
134       render :action => "edit"
135     end
136   rescue ActiveRecord::RecordNotFound
137     render :action => "no_such_entry", :status => :not_found
138   end
139
140   def subscribe
141     @diary_entry = DiaryEntry.find(params[:id])
142
143     if request.post?
144       @diary_entry.subscriptions.create(:user => current_user) unless @diary_entry.subscribers.exists?(current_user.id)
145
146       redirect_to diary_entry_path(@diary_entry.user, @diary_entry)
147     end
148   rescue ActiveRecord::RecordNotFound
149     render :action => "no_such_entry", :status => :not_found
150   end
151
152   def unsubscribe
153     @diary_entry = DiaryEntry.find(params[:id])
154
155     if request.post?
156       @diary_entry.subscriptions.where(:user => current_user).delete_all if @diary_entry.subscribers.exists?(current_user.id)
157
158       redirect_to diary_entry_path(@diary_entry.user, @diary_entry)
159     end
160   rescue ActiveRecord::RecordNotFound
161     render :action => "no_such_entry", :status => :not_found
162   end
163
164   def rss
165     if params[:display_name]
166       user = User.active.find_by(:display_name => params[:display_name])
167
168       if user
169         @entries = user.diary_entries
170         @title = t("diary_entries.feed.user.title", :user => user.display_name)
171         @description = t("diary_entries.feed.user.description", :user => user.display_name)
172         @link = url_for :action => "index", :display_name => user.display_name, :host => Settings.server_url, :protocol => Settings.server_protocol
173       else
174         head :not_found
175         return
176       end
177     else
178       @entries = DiaryEntry.joins(:user).where(:users => { :status => %w[active confirmed] })
179
180       # Items can't be flagged as deleted in the RSS format.
181       # For the general feeds, allow a delay before publishing, to help spam fighting
182       @entries = @entries.where("created_at < :time", :time => Settings.diary_feed_delay.hours.ago)
183
184       if params[:language]
185         @entries = @entries.where(:language_code => params[:language])
186         @title = t("diary_entries.feed.language.title", :language_name => Language.find(params[:language]).english_name)
187         @description = t("diary_entries.feed.language.description", :language_name => Language.find(params[:language]).english_name)
188         @link = url_for :action => "index", :language => params[:language], :host => Settings.server_url, :protocol => Settings.server_protocol
189       else
190         @title = t("diary_entries.feed.all.title")
191         @description = t("diary_entries.feed.all.description")
192         @link = url_for :action => "index", :host => Settings.server_url, :protocol => Settings.server_protocol
193       end
194     end
195     @entries = @entries.visible.includes(:user).order("created_at DESC").limit(20)
196   end
197
198   def hide
199     entry = DiaryEntry.find(params[:id])
200     entry.update(:visible => false)
201     redirect_to :action => "index", :display_name => entry.user.display_name
202   end
203
204   def unhide
205     entry = DiaryEntry.find(params[:id])
206     entry.update(:visible => true)
207     redirect_to :action => "index", :display_name => entry.user.display_name
208   end
209
210   private
211
212   ##
213   # return permitted diary entry parameters
214   def entry_params
215     params.require(:diary_entry).permit(:title, :body, :language_code, :latitude, :longitude)
216   rescue ActionController::ParameterMissing
217     ActionController::Parameters.new.permit(:title, :body, :language_code, :latitude, :longitude)
218   end
219
220   ##
221   # decide on a location for the diary entry map
222   def set_map_location
223     if @diary_entry.latitude && @diary_entry.longitude
224       @lon = @diary_entry.longitude
225       @lat = @diary_entry.latitude
226       @zoom = 12
227     elsif !current_user.home_location?
228       @lon = params[:lon] || -0.1
229       @lat = params[:lat] || 51.5
230       @zoom = params[:zoom] || 4
231     else
232       @lon = current_user.home_lon
233       @lat = current_user.home_lat
234       @zoom = 12
235     end
236   end
237 end