@@ -40,6 +40,11 @@ class Resource
40
40
instance_accessor : false
41
41
class_attribute :add_defaults_to_changes ,
42
42
instance_writer : false
43
+
44
+ class_attribute :_immutable ,
45
+ instance_writer : false ,
46
+ default : false
47
+
43
48
self . primary_key = :id
44
49
self . parser = Parsers ::Parser
45
50
self . paginator = Paginating ::Paginator
@@ -94,6 +99,18 @@ def type
94
99
table_name
95
100
end
96
101
102
+ # Indicates whether this resource is mutable or immutable;
103
+ # by default, all resources are mutable.
104
+ #
105
+ # @return [Boolean]
106
+ def immutable ( flag = true )
107
+ self . _immutable = flag
108
+ end
109
+
110
+ def inherited ( subclass )
111
+ subclass . _immutable = false
112
+ end
113
+
97
114
# Specifies the relative path that should be used for this resource;
98
115
# by default, this is inferred from the resource class name.
99
116
#
@@ -215,6 +232,11 @@ def route_formatter
215
232
# @option [Symbol] :on One of [:collection or :member] to decide whether it's a collect or member method
216
233
# @option [Symbol] :request_method The request method (:get, :post, etc)
217
234
def custom_endpoint ( name , options = { } )
235
+ if _immutable
236
+ request_method = options . fetch ( :request_method , :get ) . to_sym
237
+ raise JsonApiClient ::Errors ::ResourceImmutableError if request_method != :get
238
+ end
239
+
218
240
if :collection == options . delete ( :on )
219
241
collection_endpoint ( name , options )
220
242
else
@@ -440,6 +462,7 @@ def valid?(context = nil)
440
462
# @return [Boolean] Whether or not the save succeeded
441
463
def save
442
464
return false unless valid?
465
+ raise JsonApiClient ::Errors ::ResourceImmutableError if _immutable
443
466
444
467
self . last_result_set = if persisted?
445
468
self . class . requestor . update ( self )
@@ -470,6 +493,8 @@ def save
470
493
#
471
494
# @return [Boolean] Whether or not the destroy succeeded
472
495
def destroy
496
+ raise JsonApiClient ::Errors ::ResourceImmutableError if _immutable
497
+
473
498
self . last_result_set = self . class . requestor . destroy ( self )
474
499
if last_result_set . has_errors?
475
500
fill_errors
0 commit comments