Class: CamaleonCms::Post

Inherits:
PostDefault
  • Object
show all
Includes:
CategoriesTagsForPosts
Defined in:
app/models/camaleon_cms/post.rb

Constant Summary collapse

SANITIZE_EXTRA_TAGS =

Structural, non-executable markup that long-form post content legitimately uses but the sanitizer default drops. Superset of the default so upstream security additions are inherited.

%w[table thead tbody tfoot tr td th caption col colgroup
figure figcaption u s hr].freeze
SANITIZE_EXTRA_ATTRIBUTES =

These attributes are allowed knowing what they cost, none of which is script execution: style is CSS-scrubbed by the gate's scrubber (expression(), url(javascript:) and friends register as removals) but permits absolutely-positioned overlays; id widens DOM clobbering, which the scrubber's own default name already opened; and target without a forced rel=noopener is reverse tabnabbing on browsers predating the implicit default. The trade is deliberate: an untrusted author whose content needs more than this list has the save refused, and the role that wants more grants post_content_unfiltered_html.

%w[id style target rel colspan rowspan].freeze
CONTENT_ALLOWED_TAGS =
(ActionController::Base.helpers.sanitizer_vendor.safe_list_sanitizer
.allowed_tags.to_a + SANITIZE_EXTRA_TAGS).uniq.freeze
CONTENT_ALLOWED_ATTRIBUTES =
(ActionController::Base.helpers.sanitizer_vendor.safe_list_sanitizer
.allowed_attributes.to_a + SANITIZE_EXTRA_ATTRIBUTES).uniq.freeze

Instance Attribute Summary collapse

Instance Method Summary collapse

Methods included from CategoriesTagsForPosts

#assign_category, #manage_categories?, #manage_tags?, #unassign_category, #update_categories, #update_extra_data, #update_tags

Instance Attribute Details

#show_title_with_parentObject

Returns the value of attribute show_title_with_parent.



79
80
81
# File 'app/models/camaleon_cms/post.rb', line 79

def show_title_with_parent
  @show_title_with_parent
end

#unfiltered_contentObject (readonly)

Opt-out for trusted server-side pipelines (imports, seeds, plugin code) that would otherwise be sanitized by the fail-closed default. Exposed as a reader plus a bang enabler and NO unfiltered_content= writer, so assign_attributes/mass assignment cannot reach it — only explicit server-side code calling post.unfiltered_content! can.

It is sticky for the lifetime of the object, not for one save: an instance that has been opted out stays opted out for every subsequent save of that instance. That is what a pipeline staging a record over several steps wants; code that needs the opt-out to apply once should not reuse the instance afterwards.



31
32
33
# File 'app/models/camaleon_cms/post.rb', line 31

def unfiltered_content
  @unfiltered_content
end

Instance Method Details

#can_commented?TrueClass, FalseClass

Check if the post can be commented sample: @post.can_commented? to enable comments for current post, use this: post.set_meta('has_comments', '1'). Note: Parent PostType should be enabled for comments too: post_type.set_option('has_comments', true)

Returns:

  • (TrueClass, FalseClass)


174
175
176
# File 'app/models/camaleon_cms/post.rb', line 174

def can_commented?
  manage_comments? && get_meta('has_comments').to_s == '1'
end

#decorator_classObject

manage the custom decorators for posts sample: my_post_type.set_option('cama_post_decorator_class', 'ProductDecorator') Sample: https://github.com/owen2345/camaleon-ecommerce/tree/master/app/decorators/



282
283
284
285
286
287
288
# File 'app/models/camaleon_cms/post.rb', line 282

def decorator_class
  begin
    post_type.get_option('cama_post_decorator_class', 'CamaleonCms::PostDecorator')
  rescue StandardError
    'CamaleonCms::PostDecorator'
  end.constantize
end

#draft?Boolean

Check if this post is in the draft status

Returns:

  • (Boolean)


121
122
123
# File 'app/models/camaleon_cms/post.rb', line 121

def draft?
  %w[draft draft_child].include?(status)
end

#draft_child?Boolean

Returns:

  • (Boolean)


125
126
127
# File 'app/models/camaleon_cms/post.rb', line 125

def draft_child?
  status == 'draft_child'
end

#full_childrenObject

return all children elements for current post (page hierarchy)



97
98
99
100
101
102
103
# File 'app/models/camaleon_cms/post.rb', line 97

def full_children
  cama_fetch_cache("full_children_#{id}") do
    res = children.to_a
    res.each { |c| res += c.full_children }
    res
  end
end

#get_layout(posttype = nil) ⇒ Object

return the layout assigned to this post post_type: post type owner of this post



247
248
249
250
251
# File 'app/models/camaleon_cms/post.rb', line 247

def get_layout(posttype = nil)
  return get_option('default_layout') unless manage_layout?(posttype)

  get_meta('layout', get_option('default_layout') || (posttype || post_type).get_option('default_layout', nil))
end

#get_post_type_depreObject

Return the post type of this post (DEPRECATED), though used yet in migration, so let it stay



106
107
108
# File 'app/models/camaleon_cms/post.rb', line 106

def get_post_type_depre
  post_types.reorder(nil).first
end

#get_template(posttype = nil) ⇒ Object

return the template assigned to this post verify default template defined in post type post_type: post type owner of this post



256
257
258
259
260
261
# File 'app/models/camaleon_cms/post.rb', line 256

def get_template(posttype = nil)
  return get_option('default_template') unless manage_template?(posttype)

  get_meta('template',
           get_option('default_template') || (posttype || post_type).get_option('default_template', nil))
end

#increment_visits!Object

increment the counter of visitors



264
265
266
# File 'app/models/camaleon_cms/post.rb', line 264

def increment_visits!
  set_meta('visits', total_visits + 1)
end

#is_required_picture?Boolean

check if is required picture for current post

Returns:

  • (Boolean)


179
180
181
# File 'app/models/camaleon_cms/post.rb', line 179

def is_required_picture?
  post_type.get_option('is_required_picture', false)
end

#manage_comments?(posttype = nil) ⇒ Boolean

Check if the current post can manage comments return boolean

Returns:

  • (Boolean)


165
166
167
# File 'app/models/camaleon_cms/post.rb', line 165

def manage_comments?(posttype = nil)
  get_option('has_comments', (posttype || post_type).get_option('has_comments', false))
end

#manage_content?(posttype = nil) ⇒ Boolean

Check if the current post can manage content return boolean

Returns:

  • (Boolean)


136
137
138
# File 'app/models/camaleon_cms/post.rb', line 136

def manage_content?(posttype = nil)
  get_option('has_content', (posttype || post_type).get_option('has_content', true))
end

#manage_layout?(posttype = nil) ⇒ Boolean

return boolean

Returns:

  • (Boolean)


141
142
143
# File 'app/models/camaleon_cms/post.rb', line 141

def manage_layout?(posttype = nil)
  get_option('has_layout', (posttype || post_type).get_option('has_layout', false))
end

#manage_picture?(posttype = nil) ⇒ Boolean

Check if the current post can manage picture return boolean

Returns:

  • (Boolean)


159
160
161
# File 'app/models/camaleon_cms/post.rb', line 159

def manage_picture?(posttype = nil)
  get_option('has_picture', (posttype || post_type).get_option('has_picture', true))
end

#manage_seo?(posttype = nil) ⇒ Boolean Also known as: manage_keywords?

check if current post permit manage seo attrs has_keywords: used until next version (deprecated to use has_seo) return boolean

Returns:

  • (Boolean)


228
229
230
# File 'app/models/camaleon_cms/post.rb', line 228

def manage_seo?(posttype = nil)
  get_option('has_seo', get_option('has_keywords', false)) || (posttype || post_type).manage_seo?
end

#manage_summary?(posttype = nil) ⇒ Boolean

Check if the current post can manage summary return boolean

Returns:

  • (Boolean)


153
154
155
# File 'app/models/camaleon_cms/post.rb', line 153

def manage_summary?(posttype = nil)
  get_option('has_summary', (posttype || post_type).get_option('has_summary', true))
end

#manage_template?(posttype = nil) ⇒ Boolean

Check if current post can manage template return boolean

Returns:

  • (Boolean)


147
148
149
# File 'app/models/camaleon_cms/post.rb', line 147

def manage_template?(posttype = nil)
  get_option('has_template', (posttype || post_type).get_option('has_template', true))
end

#parentsObject

return all parents for current page hierarchy ordered bottom to top



84
85
86
87
88
89
90
91
92
93
94
# File 'app/models/camaleon_cms/post.rb', line 84

def parents
  cama_fetch_cache("parents_#{id}") do
    res = []
    p = parent
    while p
      res << p
      p = p.parent
    end
    res
  end
end

#pending?Boolean

Check if this post is in the pending status

Returns:

  • (Boolean)


116
117
118
# File 'app/models/camaleon_cms/post.rb', line 116

def pending?
  status == 'pending'
end

#published?Boolean

Check if this post was published

Returns:

  • (Boolean)


111
112
113
# File 'app/models/camaleon_cms/post.rb', line 111

def published?
  status == 'published'
end

#set_layout(layout_name) ⇒ Object

save the layout name to be used on render this post layout_name: String layout name: my_layout.html.erb => 'my_layout'



241
242
243
# File 'app/models/camaleon_cms/post.rb', line 241

def set_layout(layout_name)
  set_meta('layout', layout_name)
end

#set_position(new_order_position) ⇒ Object

put a new order position for this post new_order_position: (Integer) position number return nil



215
216
217
# File 'app/models/camaleon_cms/post.rb', line 215

def set_position(new_order_position)
  update_column(:post_order, new_order_position) # rubocop:disable Rails/SkipsModelValidations
end

#set_setting(key, val) ⇒ Object

define post configuration for current post possible key values (String):

has_content, boolean (default true)
has_summary, boolean (default true)
has_seo, boolean (default true)
has_picture, boolean (default true)
has_template, boolean (default false)
has_comments, boolean (default false)

the following is still used if post type was inactivated layout and overwritten by dropdown in post view
default_layout:  (string) (default layout)

the following is still used if post type was inactivated template and overwritten by dropdown in post view
default_template:  (string) (default template)
has_layout:  (boolean) (default false)
skip_fields:  (array) (default empty) array of custom field keys to avoid for this post,
sample: ["subtitle", "icon"]

val: value for the setting



201
202
203
# File 'app/models/camaleon_cms/post.rb', line 201

def set_setting(key, val)
  set_option(key, val)
end

#set_settings(settings = {}) ⇒ Object

assign multiple settings



206
207
208
209
210
# File 'app/models/camaleon_cms/post.rb', line 206

def set_settings(settings = {})
  settings.each do |key, val|
    set_setting(key, val)
  end
end

#set_summary(summary) ⇒ Object

save the summary for current post summary: Text String without html



221
222
223
# File 'app/models/camaleon_cms/post.rb', line 221

def set_summary(summary)
  set_meta('summary', summary)
end

#set_thumb(thumb_url) ⇒ Object

save the thumbnail url for current post thumb_url: String url



235
236
237
# File 'app/models/camaleon_cms/post.rb', line 235

def set_thumb(thumb_url)
  set_meta('thumb', thumb_url)
end

#total_commentsObject

return the quantity of comments for this post TODO comments count to move into cache counter



275
276
277
# File 'app/models/camaleon_cms/post.rb', line 275

def total_comments
  get_meta('comments_count', 0).to_i
end

#total_visitsObject

return the quantity of visits for this post



269
270
271
# File 'app/models/camaleon_cms/post.rb', line 269

def total_visits
  get_meta('visits', 0).to_i
end

#trash?Boolean

Check if this post is in the trash status

Returns:

  • (Boolean)


130
131
132
# File 'app/models/camaleon_cms/post.rb', line 130

def trash?
  status == 'trash'
end

#unfiltered_content!Object



33
34
35
36
# File 'app/models/camaleon_cms/post.rb', line 33

def unfiltered_content!
  @unfiltered_content = true
  self
end