diff --git a/app/controllers/activity_notification/notifications_api_controller.rb b/app/controllers/activity_notification/notifications_api_controller.rb index 4e86ed1e..3f88157a 100644 --- a/app/controllers/activity_notification/notifications_api_controller.rb +++ b/app/controllers/activity_notification/notifications_api_controller.rb @@ -29,7 +29,7 @@ def index super render json: { count: @notifications.size, - notifications: @notifications.as_json(include: notification_json_include_option, methods: notification_json_methods_option) + notifications: @notifications.as_json(notification_json_options) } end @@ -49,7 +49,7 @@ def open_all super render json: { count: @opened_notifications.size, - notifications: @opened_notifications.as_json(include: notification_json_include_option, methods: notification_json_methods_option) + notifications: @opened_notifications.as_json(notification_json_options) } end @@ -80,7 +80,7 @@ def destroy # PUT /:target_type/:target_id/notifications/:id/open # @overload open(params) # @param [Hash] params Request parameters - # @option params [String] :move ('false') Whether it redirects to notifiable_path after the notification is opened + # @option params [String] :move ('false') Whether it redirects to notifiable_path after the notification is opened # @return [JSON] count: number of opened notification records, notification: opened notification def open super @@ -97,7 +97,7 @@ def open # GET /:target_type/:target_id/notifications/:id/move # @overload open(params) # @param [Hash] params Request parameters - # @option params [String] :open ('false') Whether the notification will be opened + # @option params [String] :open ('false') Whether the notification will be opened # @return [JSON] location: notifiable path, count: number of opened notification records, notification: specified notification def move super @@ -110,22 +110,25 @@ def move protected - # Returns include option for notification JSON + # Returns options for notification JSON # @api protected - def notification_json_include_option - [:target, :notifiable, :group, :notifier, :group_members].freeze - end - - # Returns methods option for notification JSON - # @api protected - def notification_json_methods_option - [:notifiable_path].freeze + def notification_json_options + { + include: { + target: { methods: [:printable_type, :printable_target_name] }, + notifiable: { methods: [:printable_type] }, + group: { methods: [:printable_type, :printable_group_name] }, + notifier: { methods: [:printable_type, :printable_notifier_name] }, + group_members: {} + }, + methods: [:notifiable_path, :printable_notifiable_name, :group_member_notifier_count, :group_notification_count] + } end # Returns JSON of @notification # @api protected def notification_json - @notification.as_json(include: notification_json_include_option, methods: notification_json_methods_option) + @notification.as_json(notification_json_options) end # Render associated notifiable record not found error with 500 status diff --git a/lib/activity_notification/apis/notification_api.rb b/lib/activity_notification/apis/notification_api.rb index 5b22ea7b..259328e0 100644 --- a/lib/activity_notification/apis/notification_api.rb +++ b/lib/activity_notification/apis/notification_api.rb @@ -676,6 +676,12 @@ def notifiable_path notifiable.notifiable_path(target_type, key) end + # Returns printable notifiable model name to show in view or email. + # @return [String] Printable notifiable model name + def printable_notifiable_name + notifiable.printable_notifiable_name(target, key) + end + # Returns if the target subscribes this notification. # @return [Boolean] If the target subscribes the notification def subscribed? diff --git a/lib/activity_notification/models/concerns/swagger/notification_schema.rb b/lib/activity_notification/models/concerns/swagger/notification_schema.rb index 06afc36e..ec847d53 100644 --- a/lib/activity_notification/models/concerns/swagger/notification_schema.rb +++ b/lib/activity_notification/models/concerns/swagger/notification_schema.rb @@ -122,6 +122,19 @@ module Swagger::NotificationSchema #:nodoc: key :format, :uri key :example, "/articles/11" end + property :printable_notifiable_name do + key :type, :string + key :format, :uri + key :example, "comment \"This is the first Stephen's comment to Ichiro's article.\"" + end + property :group_member_notifier_count do + key :type, :integer + key :example, 1 + end + property :group_notification_count do + key :type, :integer + key :example, 2 + end property :target do key :type, :object key :description, "Associated target model in your application" @@ -130,7 +143,11 @@ module Swagger::NotificationSchema #:nodoc: "email": "ichiro@example.com", "name": "Ichiro", "created_at": Time.current, - "updated_at": Time.current + "updated_at": Time.current, + "provider": "email", + "uid": "", + "printable_type": "User", + "printable_target_name": "Ichiro" } end property :notifiable do @@ -142,7 +159,8 @@ module Swagger::NotificationSchema #:nodoc: "article_id": 11, "body": "This is the first Stephen's comment to Ichiro's article.", "created_at": Time.current, - "updated_at": Time.current + "updated_at": Time.current, + "printable_type": "Comment" } end property :group do @@ -155,7 +173,9 @@ module Swagger::NotificationSchema #:nodoc: "title": "Ichiro's great article", "body": "This is Ichiro's great article. Please read it!", "created_at": Time.current, - "updated_at": Time.current + "updated_at": Time.current, + "printable_type": "Article", + "printable_group_name": "article \"Ichiro's great article\"" } end property :notifier do @@ -167,7 +187,11 @@ module Swagger::NotificationSchema #:nodoc: "email": "stephen@example.com", "name": "Stephen", "created_at": Time.current, - "updated_at": Time.current + "updated_at": Time.current, + "provider": "email", + "uid": "", + "printable_type": "User", + "printable_notifier_name": "Stephen" } end property :group_members do diff --git a/lib/activity_notification/orm/mongoid.rb b/lib/activity_notification/orm/mongoid.rb index 4b33d69c..65b62566 100644 --- a/lib/activity_notification/orm/mongoid.rb +++ b/lib/activity_notification/orm/mongoid.rb @@ -82,8 +82,12 @@ module Document def as_json(options = {}) json = super(options) json["id"] = json["_id"].to_s.start_with?("{\"$oid\"=>") ? self.id.to_s : json["_id"].to_s - (options[:include] || []).each do |associated_model| - json[associated_model] = self.send(associated_model).as_json + if options.has_key?(:include) + case options[:include] + when Symbol then json[options[:include].to_s] = self.send(options[:include]).as_json + when Array then options[:include].each {|model| json[model.to_s] = self.send(model).as_json } + when Hash then options[:include].each {|model, options| json[model.to_s] = self.send(model).as_json(options) } + end end json end diff --git a/spec/models/notification_spec.rb b/spec/models/notification_spec.rb index 22f68590..15d0b789 100644 --- a/spec/models/notification_spec.rb +++ b/spec/models/notification_spec.rb @@ -56,6 +56,23 @@ notification = create(:notification, notifier: notifier) expect(notification.reload.notifier).to eq(notifier) end + + context "returns as_json including associated models" do + it "returns as_json with include option as Symbol" do + notification = create(:notification) + expect(notification.as_json(include: :target)["target"]["id"].to_s).to eq(notification.target.id.to_s) + end + + it "returns as_json with include option as Array" do + notification = create(:notification) + expect(notification.as_json(include: [:target])["target"]["id"].to_s).to eq(notification.target.id.to_s) + end + + it "returns as_json with include option as Hash" do + notification = create(:notification) + expect(notification.as_json(include: { target: { methods: [:printable_target_name] } })["target"]["id"].to_s).to eq(notification.target.id.to_s) + end + end end describe "with serializable column" do