scrivito_sdk 0.66.0 → 0.70.0.rc1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (73) hide show
  1. checksums.yaml +4 -4
  2. data/app/controllers/scrivito/blobs_controller.rb +5 -0
  3. data/app/controllers/scrivito/objs_controller.rb +2 -1
  4. data/app/controllers/scrivito/ui_controller.rb +33 -3
  5. data/app/helpers/scrivito_helper.rb +14 -20
  6. data/app/views/scrivito/objs/update.json.jbuilder +1 -1
  7. data/app/views/scrivito/ui/index.html.erb +1 -1
  8. data/app/views/scrivito/webservice/_workspace.json.jbuilder +2 -1
  9. data/config/ca-bundle.crt +1 -1
  10. data/config/precedence_routes.rb +3 -2
  11. data/lib/assets/javascripts/scrivito.js +46 -0
  12. data/lib/assets/javascripts/scrivito_ui.js +931 -501
  13. data/lib/assets/stylesheets/scrivito.css +1 -0
  14. data/lib/assets/stylesheets/scrivito_ui.css +1 -1
  15. data/lib/generators/scrivito/install/templates/app/views/page/index.html.erb +3 -3
  16. data/lib/generators/scrivito/page/page_generator.rb +3 -0
  17. data/lib/generators/scrivito/page/templates/model.erb +3 -0
  18. data/lib/generators/scrivito/widget/templates/model.erb +3 -0
  19. data/lib/generators/scrivito/widget/widget_generator.rb +3 -0
  20. data/lib/scrivito/attribute_content.rb +93 -60
  21. data/lib/scrivito/attribute_definition.rb +3 -3
  22. data/lib/scrivito/attribute_serializer.rb +2 -2
  23. data/lib/scrivito/backend/obj_data_cache.rb +22 -9
  24. data/lib/scrivito/basic_obj.rb +238 -130
  25. data/lib/scrivito/basic_widget.rb +32 -20
  26. data/lib/scrivito/binary.rb +74 -45
  27. data/lib/scrivito/binary_routing.rb +52 -0
  28. data/lib/scrivito/cache_middleware.rb +0 -5
  29. data/lib/scrivito/client_attribute_serializer.rb +134 -0
  30. data/lib/scrivito/cms_backend.rb +51 -33
  31. data/lib/scrivito/cms_data_cache.rb +1 -0
  32. data/lib/scrivito/cms_dispatch_controller.rb +1 -1
  33. data/lib/scrivito/cms_env.rb +1 -11
  34. data/lib/scrivito/cms_field_tag.rb +10 -7
  35. data/lib/scrivito/cms_rest_api/rate_limit.rb +5 -5
  36. data/lib/scrivito/cms_rest_api/request_timer.rb +27 -0
  37. data/lib/scrivito/cms_rest_api/widget_extractor.rb +8 -6
  38. data/lib/scrivito/cms_rest_api.rb +107 -54
  39. data/lib/scrivito/cms_routing.rb +13 -25
  40. data/lib/scrivito/configuration.rb +5 -2
  41. data/lib/scrivito/controller_actions.rb +68 -7
  42. data/lib/scrivito/controller_runtime.rb +8 -0
  43. data/lib/scrivito/date_attribute.rb +8 -0
  44. data/lib/scrivito/errors.rb +6 -3
  45. data/lib/scrivito/generator_helper.rb +13 -0
  46. data/lib/scrivito/image_tag.rb +24 -30
  47. data/lib/scrivito/layout_tags.rb +12 -6
  48. data/lib/scrivito/link.rb +46 -30
  49. data/lib/scrivito/log_subscriber.rb +15 -0
  50. data/lib/scrivito/membership.rb +3 -3
  51. data/lib/scrivito/membership_collection.rb +10 -10
  52. data/lib/scrivito/meta_data_collection.rb +22 -0
  53. data/lib/scrivito/model_library.rb +7 -1
  54. data/lib/scrivito/obj_collection.rb +18 -16
  55. data/lib/scrivito/obj_params_parser.rb +1 -1
  56. data/lib/scrivito/obj_search_enumerator.rb +35 -35
  57. data/lib/scrivito/page_config.rb +55 -0
  58. data/lib/scrivito/request_homepage.rb +23 -0
  59. data/lib/scrivito/routing_helper.rb +8 -8
  60. data/lib/scrivito/sdk_engine.rb +2 -3
  61. data/lib/scrivito/ui_config.rb +85 -0
  62. data/lib/scrivito/user.rb +30 -23
  63. data/lib/scrivito/user_definition.rb +48 -47
  64. data/lib/scrivito/widget_tag.rb +11 -0
  65. data/lib/scrivito/workspace.rb +93 -35
  66. data/lib/scrivito/workspace_selection_middleware.rb +8 -1
  67. data/lib/scrivito_sdk.rb +24 -24
  68. metadata +24 -33
  69. data/lib/assets/javascripts/scrivito_sdk.js +0 -57
  70. data/lib/assets/stylesheets/scrivito_sdk.css +0 -1
  71. data/lib/scrivito/client_config.rb +0 -113
  72. data/lib/scrivito/editing_context_helper.rb +0 -19
  73. data/lib/scrivito/named_link.rb +0 -39
@@ -1,6 +1,10 @@
1
1
  module Scrivito
2
2
 
3
- # The CMS widget class
3
+ # The CMS widget class. Widget classes let you create widget types for the individual kinds
4
+ # of content editors want to place on pages or into widgets. All widget classes are based on
5
+ # subclasses of {Scrivito::BasicWidget Widget}. As with CMS objects, the content of a widget
6
+ # is stored in its attributes.
7
+ # @see http://scrivito.com/page-with-widgets Creating a page type with widgets
4
8
  # @api public
5
9
  class BasicWidget
6
10
  extend AttributeContent::ClassMethods
@@ -67,13 +71,13 @@ class BasicWidget
67
71
  # @api public
68
72
  # @param [Hash] attributes
69
73
  #
70
- # @example Create a widget using a subclass
71
- # # you can create widgets by explicitly providing the attribute `_obj_class`
74
+ # @example Create a widget using a subclass:
75
+ # # you can create widgets by explicitly providing the '_obj_class' attribute
72
76
  # new_widget = Widget.new(_obj_class: "MyWidget")
73
77
  # # but it is better to simply use the constructor of a subclass
74
78
  # new_widget = MyWidget.new
75
79
  #
76
- # @example Create a widget and store it inside an Obj
80
+ # @example Create a widget and store it inside an Obj:
77
81
  # # create the widget
78
82
  # new_widget = Widget.new(_obj_class: "MyWidget")
79
83
  # # store it inside an obj
@@ -85,12 +89,15 @@ class BasicWidget
85
89
  end
86
90
 
87
91
  #
88
- # Creates a new {Scrivito::BasicWidget Widget}.
92
+ # Creates a new {Scrivito::BasicWidget Widget}. The defaults set via
93
+ # {Scrivito::AttributeContent::ClassMethods#default_for Widget.default_for}
94
+ # are taken into account.
89
95
  #
90
96
  # @api public
91
97
  #
92
- # It also considers the defaults set via
93
- # {Scrivito::AttributeContent::ClassMethods#default_for Widget.default_for}.
98
+ # @note Note that creating a widget does not implicitly persist it. The widget is only persisted
99
+ # if its creation is part of the creation of the object containing it, or as the object or
100
+ # widget containing it is updated.
94
101
  #
95
102
  # @param [Hash] attributes for the new widget
96
103
  # @param [Hash] context in which the object creating should happen
@@ -112,9 +119,14 @@ class BasicWidget
112
119
  obj.revision
113
120
  end
114
121
 
115
- # Update the attributes of this Widget
122
+ # Updates the attributes of this {Scrivito::BasicWidget Widget}.
123
+ # See {Scrivito::BasicObj.create Obj.create} for a detailed overview of how to set attributes.
124
+ # @example Set the title of a specific widget contained in the 'main_content' attribute of an Obj:
125
+ # obj.main_content[4].update(title: "New Title")
116
126
  #
117
- # See {Scrivito::BasicObj.create Obj.create} for a detailed overview of how to set attributes
127
+ # @example Add a widget to the 'main_content' widgetlist attribute:
128
+ # widgets = obj.main_content << MyWidget.new(title: "Fresh")
129
+ # obj.update(main_content: widgets)
118
130
  # @api public
119
131
  # @param [Hash] attributes
120
132
  def update(attributes)
@@ -122,7 +134,7 @@ class BasicWidget
122
134
  reload
123
135
  end
124
136
 
125
- # Destroys the {Scrivito::BasicWidget Widget} in the current {Workspace}
137
+ # Destroys the {Scrivito::BasicWidget Widget} in the current {Workspace}.
126
138
  # @api public
127
139
  def destroy
128
140
  new_widget_list = container[container_attribute_name] - [self]
@@ -134,11 +146,11 @@ class BasicWidget
134
146
  #
135
147
  # @api public
136
148
  #
137
- # The copy will have all attributes of the original widget including its widgets.
138
- # Its attributes can be accessed only after it has been stored in a widget field of an
139
- # {Scrivito::BasicObj Obj}, since initially the copy is not stored in any widget field.
149
+ # The copy will have all the attributes of the original widget including its widgets.
150
+ # Its attributes can be accessed only after it has been stored in a +widgetlist+ field of an
151
+ # {Scrivito::BasicObj Obj}, since initially the copy is not stored in such a field.
140
152
  #
141
- # @example Duplicate the first widget in field +my_widget+
153
+ # @example Duplicate the first widget contained in the +my_widget+ field.
142
154
  # obj.update(my_widgets: obj.my_widgets.push(obj.my_widgets.first.copy))
143
155
  #
144
156
  def copy
@@ -197,9 +209,9 @@ class BasicWidget
197
209
  #
198
210
  # @api public
199
211
  #
200
- # @note This method does not support +Widget+s, which are +new+.
212
+ # @note This method does not support +new+ +Widget+s.
201
213
  # Please use {Scrivito::BasicWidget#destroy Widget#destroy} to destroy them.
202
- # @note This method does not support +Widget+s, which are +deleted+.
214
+ # @note This method does not support +deleted+ +Widget+s.
203
215
  # Please use {Scrivito::BasicObj#revert Obj#revert} to restore them.
204
216
  #
205
217
  # @raise [ScrivitoError] If the current workspace is +published+.
@@ -265,19 +277,19 @@ class BasicWidget
265
277
  end
266
278
  end
267
279
 
268
- # returns the entity ({Scrivito::BasicObj} or {Scrivito::BasicWidget}) that references this widget
280
+ # Returns the entity ({Scrivito::BasicObj} or {Scrivito::BasicWidget}) that references this widget.
269
281
  # @api public
270
282
  def container
271
283
  @container || container_and_attribute_name.first
272
284
  end
273
285
 
274
- # returns the name of the widget attribute that references this widget
286
+ # Returns the name of the +widgetlist+ attribute that references this widget.
275
287
  # @api public
276
288
  def container_attribute_name
277
289
  @container_attribute_name || container_and_attribute_name.second
278
290
  end
279
291
 
280
- # returns the name of the widget field that references this widget
292
+ # Returns the name of the 'widgetlist' field that references this widget.
281
293
  # @api public
282
294
  # @deprecated
283
295
  def container_field_name
@@ -328,7 +340,7 @@ class BasicWidget
328
340
  end
329
341
 
330
342
  # @api public
331
- # This method determines the description to be shown in the widget tooltips. By default,
343
+ # This method determines the description to be shown as widget tooltips. By default,
332
344
  # it uses the value of the +Widget.description_for_editor+ class method.
333
345
  #
334
346
  # This method can be overridden to customize the description displayed to the editor.
@@ -1,8 +1,8 @@
1
1
  module Scrivito
2
2
 
3
3
  # @api public
4
- # The Binary class represents the data stored in a binary attribute of an Obj
5
- # or Widget
4
+ # The Binary class represents the data stored in a binary attribute of an {Scrivito::BasicObj Obj}
5
+ # or a {Scrivito::BasicWidget Widget}.
6
6
  class Binary
7
7
  attr_reader :id, :transformation_definition
8
8
 
@@ -29,6 +29,12 @@ class Binary
29
29
  # @api public
30
30
  # The URL for accessing the binary data and downloading it using an HTTP GET request.
31
31
  #
32
+ # @note The URL is calculated on demand, i.e. if the URL has not been cached yet,
33
+ # this method calls the Scrivito API to retrieve the URL.
34
+ # If you want to link to a Binary, consider using {Scrivito::RoutingHelper#scrivito_url}
35
+ # instead. This is generally much faster,
36
+ # as it performs the Scrivito API call asynchronously.
37
+ #
32
38
  # @note URLs for private content have an expiration time in order to protect them.
33
39
  # Therefore, the URL should be accessed immediately after it has been returned
34
40
  # (i.e. within a couple of minutes). Accessing it after expiration causes an error.
@@ -49,39 +55,40 @@ class Binary
49
55
  end
50
56
 
51
57
  # @api public
52
- # the filename of this binary data, for example "my_image.jpg"
53
- # @return [String] the filename of binary
58
+ # The filename of this binary data, for example "my_image.jpg".
59
+ # @return [String] the filename of the binary
54
60
  def filename
55
61
  File.basename(URI(url).path)
56
62
  end
57
63
 
58
64
  # @api public
59
- # the content type of this binary data, for example "image/jpeg"
65
+ # The content type of this binary data, for example "image/jpeg".
60
66
  # @return [String] content type
61
67
  def content_type
62
68
  headers[:content_type]
63
69
  end
64
70
 
65
71
  # @api public
66
- # the length of this binary data, in bytes.
72
+ # The length of this binary data, in bytes.
67
73
  # @return [Integer] number of bytes
68
74
  def content_length
69
75
  headers[:content_length].to_i
70
76
  end
71
77
 
72
78
  #
73
- # Returns a transformed {Scrivito::Binary}.
79
+ # Use this method to transform images, i.e. to scale down large images or to generate thumbnails of images.
80
+ # Only applicable if this {Scrivito::Binary} is an image.
74
81
  #
75
- # @api beta
82
+ # @api public
76
83
  #
77
- # Calling this method will not change the binary, but instead return a copy of it,
84
+ # This method does not change the binary. Instead, it returns a copy of it,
78
85
  # transformed using the +definition+.
79
86
  #
80
- # If the original binary has already been transformed, then the returned binary will be a
81
- # combination of the transformations. Thus the transformations can be chained (see examples).
87
+ # If the original binary has already been transformed, the returned binary will be a
88
+ # combination of the transformations. Thus, the transformations can be chained (see examples).
82
89
  #
83
- # The transformed data is calculated "lazily", so calling {Scrivito::Binary#transform} will not
84
- # trigger any calculation. The calculation will be triggered only if data is accessed, for example
90
+ # The transformed data is calculated "lazily", so calling {Scrivito::Binary#transform} does not
91
+ # trigger any calculation. The calculation is triggered only when data is accessed, for example
85
92
  # via {Scrivito::Binary#url}.
86
93
  #
87
94
  # @param [Hash] definition transformation definition
@@ -89,87 +96,90 @@ class Binary
89
96
  # @option definition [Fixnum,String] :width The width in pixels of the output image. Must be a
90
97
  # positive integer.
91
98
  #
92
- # If only this dimension is specified, the other dimension will be calculated automatically to
99
+ # If only this dimension has been specified, the other dimension is calculated automatically to
93
100
  # preserve the aspect ratio of the input image.
94
101
  #
95
- # If the +fit+ parameter is set to +:clip+, then the actual output one of width and height may
96
- # be equal to or less than the dimensions you specify to prevent distortion.
102
+ # If the +fit+ parameter is set to +:clip+, then either the actual output width or the output
103
+ # height may be less than the amount you specified to prevent distortion.
97
104
  #
98
105
  # If neither +width+ nor +height+ is given, the width and height of the input image
99
- # will be used.
106
+ # is used.
100
107
  #
101
- # The maximum output image size width + height = 4096 pixels. The given width and height may be
102
- # adjusted to accomodate this limit. The output image will never be larger than the source
103
- # image, i.e. the given width and height may be adjusted to keep the output image from exceeding
104
- # the dimensions of the input image.
108
+ # The maximum size of the output image is defined as width + height = 4096 pixels. The given
109
+ # width and height may be adjusted to accommodate this limit. The output image will never be
110
+ # larger than the source image, i.e. the given width and height may be adjusted to prevent the
111
+ # dimensions of the output image from exceeding those of the input image.
105
112
  #
106
- # When the given width and height are adjusted, the aspect ratio is preserved.
113
+ # If the given width and height are adjusted, the aspect ratio is preserved.
107
114
  #
108
115
  # @option definition [Fixnum,String] :height The height in pixels of the output image. Must be a
109
116
  # positive integer.
110
117
  #
111
- # If only this dimension is specified, the other dimension will be calculated automatically to
118
+ # If only this dimension has been specified, the other dimension is calculated automatically to
112
119
  # preserve the aspect ratio of the input image.
113
120
  #
114
- # If the +fit+ parameter is set to +:clip+, then the actual output one of width and height may
115
- # be equal to or less than the dimensions you specify to prevent distortion.
121
+ # If the +fit+ parameter is set to +:clip+, then either the actual output width or the output
122
+ # height may be less than the amount you specified to prevent distortion.
116
123
  #
117
124
  # If neither +width+ nor +height+ is given, the width and height of the input image
118
- # will be used.
125
+ # is used.
119
126
  #
120
- # The maximum output image size width + height = 4096 pixels. The given width and height may be
121
- # adjusted to accomodate this limit. The output image will never be larger than the source
122
- # image, i.e. the given width and height may be adjusted to keep the output image from exceeding
123
- # the dimensions of the input image.
127
+ # The maximum size of the output image is defined as width + height = 4096 pixels. The given
128
+ # width and height may be adjusted to accommodate this limit. The output image will never be
129
+ # larger than the source image, i.e. the given width and height may be adjusted to prevent the
130
+ # dimensions of the output image from exceeding those of the input image.
124
131
  #
125
- # When the given width and height are adjusted, the aspect ratio is preserved.
132
+ # If the given width and height are adjusted, the aspect ratio is preserved.
126
133
  #
127
134
  # @option definition [Symbol,String] :fit Controls how the tranformed image is fitted to the
128
135
  # given width and heigth. Valid values are +:clip+ and +:crop+. The default value is +:clip+.
129
136
  #
130
- # If set to +:clip+ it resizes the image to fit within the width and height boundaries without
131
- # cropping or distorting the image. The resulting image is assured to match one of the
137
+ # If set to +:clip+, the image is resized so as to fit within the width and height boundaries
138
+ # without cropping or distorting the image. The resulting image is assured to match one of the
132
139
  # constraining dimensions, while the other dimension is altered to maintain the same aspect
133
140
  # ratio of the input image.
134
141
  #
135
- # If set to +:crop+ it resizes the image to fill the given width and height and preserves the
136
- # aspect ration by cropping any excess image data. The resulting image will match both the given
137
- # width and height without distorting the image. The crop is done centered, i.e. the center of
142
+ # If set to +:crop+, the image is resized so as to fill the given width and height, preserving
143
+ # the aspect ratio by cropping any excess image data. The resulting image will match both the given
144
+ # width and height without distorting the image. Cropping is done centered, i.e. the center of
138
145
  # the image is preserved.
139
146
  #
140
147
  # @option definition [Fixnum,String] :quality Controls the output quality of lossy file formats.
141
- # Applies when the format is +"jpg"+. Valid values are in the range from +0+ to +100+.
148
+ # Applies if the format is +"jpg"+. Valid values are in the range from +0+ to +100+.
142
149
  # The default value is +75+.
143
150
  #
144
151
  # @return [Scrivito::Binary] transformed binary
145
152
  #
146
- # @example Crop image to fit into 50 x 50 pixel square
153
+ # @example Crop image to fit into 50 x 50 pixel square.
147
154
  # @obj.blob.transform(width: 50, height: 50, fit: :crop)
148
155
  #
149
- # @example Convert image to a low quality JPEG
156
+ # @example Convert image to a low quality JPEG.
150
157
  # @obj.blob.transform(quality: 25)
151
158
  #
152
- # @example Combine the both transformations
159
+ # @example Combine two transformations.
153
160
  # @obj.blob.transform(width: 50, height: 50, fit: :crop).transform(quality: 25)
154
161
  #
162
+ # @see Scrivito::Configuration
163
+ # @see ScrivitoHelper#scrivito_image_tag
164
+ #
155
165
  def transform(definition)
156
166
  self.class.new(id, public?, (transformation_definition || {}).merge(definition), original)
157
167
  end
158
168
 
159
169
  #
160
- # Returns whether a binary is transformed.
161
- # @api beta
170
+ # Returns whether a binary has been transformed.
171
+ # @api public
162
172
  #
163
173
  def transformed?
164
174
  !!transformation_definition
165
175
  end
166
176
 
167
177
  #
168
- # Returns the transformation original of a binary.
178
+ # Returns the original version of a transformed binary.
169
179
  #
170
- # @api beta
180
+ # @api public
171
181
  #
172
- # If a binary is a result of a transformation, then its original binary is returned.
182
+ # If a binary is the result of a transformation, the original version of the binary is returned.
173
183
  # Otherwise +self+.
174
184
  #
175
185
  # @return [Scrivito::Binary] original binary
@@ -184,6 +194,13 @@ class Binary
184
194
  @original || self
185
195
  end
186
196
 
197
+ def meta_data
198
+ @meta_data ||= begin
199
+ deserialized_meta_data = deserialize_meta_data(CmsBackend.instance.find_binary_meta_data(id))
200
+ MetaDataCollection.new(deserialized_meta_data)
201
+ end
202
+ end
203
+
187
204
  private
188
205
 
189
206
  def public_content?
@@ -211,6 +228,18 @@ class Binary
211
228
  def access_type
212
229
  public? ? 'public_access' : 'private_access'
213
230
  end
231
+
232
+ def deserialize_meta_data(raw_meta_data)
233
+ deserialized_meta_data = {}
234
+ raw_meta_data.each_pair do |key, (type, value)|
235
+ deserialized_meta_data[key] = case type
236
+ when 'date' then DateAttribute.parse(value)
237
+ when 'number' then value.to_i
238
+ else value
239
+ end
240
+ end
241
+ deserialized_meta_data
242
+ end
214
243
  end
215
244
 
216
245
  end
@@ -0,0 +1,52 @@
1
+ module Scrivito
2
+
3
+ class BinaryRouting < Struct.new(:request, :scrivito_engine)
4
+ def binary_url(binary)
5
+ binary_url_from_cache(binary) || binary_redirect_url(binary)
6
+ end
7
+
8
+ def binary_obj_url(obj, binary, image_options = {})
9
+ binary = if image_options.has_key?(:transform)
10
+ apply_custom_transformation(binary, image_options[:transform])
11
+ else
12
+ apply_default_transformation(binary, obj)
13
+ end
14
+ binary_url(binary)
15
+ end
16
+
17
+ def resolved_binary_obj_url(obj, binary)
18
+ apply_default_transformation(binary, obj).url
19
+ end
20
+
21
+ private
22
+
23
+ def binary_url_from_cache(binary)
24
+ if url_from_cache = binary.url_from_cache
25
+ BinaryRewrite.call(request, url_from_cache)
26
+ end
27
+ end
28
+
29
+ def binary_redirect_url(binary)
30
+ encrypted_params = BinaryParamVerifier.generate(binary)
31
+ scrivito_engine.binary_path(encrypted_params: encrypted_params)
32
+ end
33
+
34
+ def apply_custom_transformation(binary, transformation_definition)
35
+ if transformation_definition
36
+ binary.transform(transformation_definition)
37
+ else
38
+ binary
39
+ end
40
+ end
41
+
42
+ def apply_default_transformation(binary, obj)
43
+ if (transformation_definition = Scrivito::Configuration.default_image_transformation) &&
44
+ obj.apply_image_transformation?
45
+ binary.transform(transformation_definition)
46
+ else
47
+ binary
48
+ end
49
+ end
50
+ end
51
+
52
+ end
@@ -7,7 +7,6 @@ class CacheMiddleware
7
7
 
8
8
  def call(env)
9
9
  clear_caches
10
- clear_runtime
11
10
 
12
11
  @app.call(env)
13
12
  end
@@ -15,10 +14,6 @@ class CacheMiddleware
15
14
 
16
15
  private
17
16
 
18
- def clear_runtime
19
- Scrivito::LogSubscriber.reset_runtime
20
- end
21
-
22
17
  def clear_caches
23
18
  Workspace.cache.clear
24
19
  CmsBackend.instance.clear_cache
@@ -0,0 +1,134 @@
1
+ module Scrivito
2
+
3
+ module ClientAttributeSerializer
4
+ def self.serialize_obj(obj)
5
+ serialized_output = {}
6
+
7
+ # system attributes
8
+ serialized_output.merge!(serialize_system_attrs(obj))
9
+
10
+ # custom attributes
11
+ serialized_output.merge!(serialize_custom_attrs(obj))
12
+
13
+ # _widget_pool
14
+ serialized_output.merge!(serialize_widget_pool(obj.widgets))
15
+
16
+ serialized_output
17
+ end
18
+
19
+ def self.serialize_system_attrs(obj)
20
+ {
21
+ '_id' => obj.id,
22
+ '_obj_class' => obj.obj_class_name,
23
+ '_path' => obj.path,
24
+ '_permalink' => obj.permalink,
25
+ }
26
+ end
27
+
28
+ def self.serialize_custom_attrs(obj_or_widget)
29
+ Hash[
30
+ obj_or_widget.attribute_definitions.map do |definition|
31
+ name = definition.name
32
+ type = definition.type
33
+ value = obj_or_widget[name]
34
+
35
+ [name, serialize_custom_attr_value(type, value)]
36
+ end
37
+ ]
38
+ end
39
+
40
+ def self.serialize_widget_pool(widgets)
41
+ {
42
+ '_widget_pool' => Hash[
43
+ widgets.map do |widget|
44
+ [widget.id, serialize_widget(widget)]
45
+ end
46
+ ]
47
+ }
48
+ end
49
+
50
+ def self.serialize_custom_attr_value(type, value)
51
+ return unless value
52
+
53
+ case type
54
+ when 'binary' then serialize_binary_value(value)
55
+ when 'date' then serialize_date_value(value)
56
+ when 'enum' then serialize_enum_value(value)
57
+ when 'html' then serialize_html_value(value)
58
+ when 'link' then serialize_link_value(value)
59
+ when 'linklist' then serialize_linklist_value(value)
60
+ when 'multienum' then serialize_multienum_value(value)
61
+ when 'reference' then serialize_reference_value(value)
62
+ when 'referencelist' then serialize_referencelist_value(value)
63
+ when 'string' then serialize_string_value(value)
64
+ when 'stringlist' then serialize_stringlist_value(value)
65
+ when 'widgetlist' then serialize_widgetlist_value(value)
66
+ end
67
+ end
68
+
69
+ def self.serialize_binary_value(value)
70
+ {'url' => value.url, 'filename' => value.filename}
71
+ end
72
+
73
+ def self.serialize_date_value(value)
74
+ value.utc.iso8601
75
+ end
76
+
77
+ def self.serialize_enum_value(value)
78
+ value
79
+ end
80
+
81
+ def self.serialize_html_value(value)
82
+ value
83
+ end
84
+
85
+ def self.serialize_link_value(value)
86
+ value.to_cms_api_linklist_params.stringify_keys
87
+ end
88
+
89
+ def self.serialize_linklist_value(value)
90
+ value.map do |link|
91
+ serialize_link_value(link)
92
+ end
93
+ end
94
+
95
+ def self.serialize_multienum_value(value)
96
+ value.map do |enum|
97
+ serialize_enum_value(enum)
98
+ end
99
+ end
100
+
101
+ def self.serialize_reference_value(value)
102
+ value.id
103
+ end
104
+
105
+ def self.serialize_referencelist_value(value)
106
+ value.map do |reference|
107
+ serialize_reference_value(reference)
108
+ end
109
+ end
110
+
111
+ def self.serialize_string_value(value)
112
+ value
113
+ end
114
+
115
+ def self.serialize_stringlist_value(value)
116
+ value.map do |string|
117
+ serialize_string_value(string)
118
+ end
119
+ end
120
+
121
+ def self.serialize_widgetlist_value(value)
122
+ value.map do |widget|
123
+ widget.id
124
+ end
125
+ end
126
+
127
+ def self.serialize_widget(widget)
128
+ {
129
+ '_obj_class' => widget.obj_class_name
130
+ }.merge(serialize_custom_attrs(widget))
131
+ end
132
+ end
133
+
134
+ end