ciesta 0.2.3 → 0.2.4

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 686725e6d7930c99dafab26c796538ac28410261704491f9f676bb2204950481
4
- data.tar.gz: 16b64dd435105dcc1a66c778e4cd321137b47d4859588a1b9c5f4d19ae7c4e42
3
+ metadata.gz: bb2964e90401b855dc16d22aaa8f33634a4994080ec94b4db9a52f8cd3a6a519
4
+ data.tar.gz: 80631e5019a4e21759777edb3aaf70429699533a278ecad419d1c09ae11fe9c1
5
5
  SHA512:
6
- metadata.gz: 12cce79f11ee00426ad3675c2bb1506a28b526ab0b565dae0719945661261c9d62fe6c01210f2d68697b595e174fc1c4e6f015d823adae3cf9a9ab83c63a73f9
7
- data.tar.gz: 5b98c72dd163212fdea889553d501f486df12ddc7dfcd3ba73d6e09aae4e9d11afd0a61b0a1f5927fc0fd4fcbe4c937aef9ed5413b174d18923b9a07a25a9598
6
+ metadata.gz: 7c752c91de5d1a7d8f0d284193f19b61dbd76666ed013e1dc83f5ce597849636153fc3151c405dbe37e1635d5acb5f354c3ab9ed6d7580beb78270ed1497eac8
7
+ data.tar.gz: ea33aa1779f0bcb4d79df9c3218c3302113f111d9417dadec5d0e8171859006a0f3d24a4dbd943f9405bc6dae26c27d5fc56db52c973e4d2440c5e11a62118cc
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- ciesta (0.2.3)
4
+ ciesta (0.2.4)
5
5
  dry-types (~> 0.12.1)
6
6
  dry-validation (~> 0.11.1)
7
7
 
data/README.md CHANGED
@@ -18,6 +18,7 @@ You should keep it in mind that here uses [dry-validation](https://github.com/dr
18
18
  - [Advanced field declaration](#advanced-field-declaration)
19
19
  - [Types](#types)
20
20
  - [Default value](#default-value)
21
+ - [Virtual field](#virtual-field)
21
22
  - [Values mass update](#values-mass-update)
22
23
  - [Contributing](#contributing)
23
24
  - [License](#license)
@@ -122,6 +123,7 @@ field :age, type: Ciesta::Types::Coercible::Int
122
123
  form.age = "42"
123
124
  form.age # => 42
124
125
  ```
126
+
125
127
  Default type is `Ciesta::Types::Any`.
126
128
 
127
129
  #### Default value
@@ -149,6 +151,19 @@ field :age, default: -> { default_age }
149
151
  form.age # => 42
150
152
  ```
151
153
 
154
+ ### Virtual field
155
+ You can declare field as "virtual". It means that when you call `sync!` it will not raise an error "model attribute is not defined".
156
+
157
+ ```ruby
158
+ User = Struct.new(:name)
159
+ ...
160
+ field :age, virtual: true
161
+ ...
162
+ form.age = "42"
163
+ form.age # => 42
164
+ form.sync! # => true
165
+ ```
166
+
152
167
  ## Values mass update
153
168
  There are two methods for form fields mass update: `assign` and `assign!`.
154
169
 
@@ -10,6 +10,9 @@ module Ciesta
10
10
  # Error for missing field definition
11
11
  FieldNotDefined = Class.new(NoMethodError)
12
12
 
13
+ # Error for missing method of model
14
+ AttributeNotDefined = Class.new(NoMethodError)
15
+
13
16
  # Error for nil object
14
17
  ModelNotPresent = Class.new(StandardError)
15
18
  end
@@ -20,6 +20,7 @@ class Ciesta::Field
20
20
  @name = name.to_sym
21
21
  @type = options.delete(:type) || DEFAULT_TYPE
22
22
  @default = options.delete(:default)
23
+ @virtual = options.delete(:virtual) || false
23
24
  end
24
25
 
25
26
  # Sets a new value for field
@@ -51,13 +52,22 @@ class Ciesta::Field
51
52
  @binding = obj
52
53
  end
53
54
 
55
+ # Returns true if field is virtual
56
+ #
57
+ # @api private
58
+ #
59
+ # @return [Boolean]
60
+ def virtual?
61
+ @virtual
62
+ end
63
+
54
64
  private
55
65
 
56
66
  # Returns typed default value for field
57
67
  #
58
68
  # @api private
59
- # @return [any]
60
69
  # @raise Ciesta::ViolatesConstraints
70
+ # @return [any]
61
71
  def default
62
72
  type[raw_default]
63
73
  rescue Dry::Types::ConstraintError
@@ -84,7 +84,7 @@ class Ciesta::FieldList
84
84
  # @api private
85
85
  # @param [Block] block Block to iterate
86
86
  def each
87
- list.each { |name, field| yield(name, field.value) }
87
+ list.each_value { |field| yield(field) }
88
88
  end
89
89
 
90
90
  private
@@ -16,6 +16,11 @@ class Ciesta::Form
16
16
  # @see Ciesta::Validator
17
17
  delegate :errors, to: :validator
18
18
 
19
+ # @!method sync
20
+ # @!method sync!
21
+ # @see Ciesta::Syncer
22
+ delegate :sync, to: :syncer
23
+
19
24
  class << self
20
25
  # Declare new form field
21
26
  #
@@ -65,7 +70,10 @@ class Ciesta::Form
65
70
 
66
71
  return if object.nil?
67
72
 
68
- values = fields.keys.map { |key| [key, object.public_send(key)] }.to_h
73
+ values = fields.keys.each_with_object({}) do |key, mem|
74
+ mem[key] = object.public_send(key) if object.respond_to?(key)
75
+ end
76
+
69
77
  assign(values)
70
78
  end
71
79
 
@@ -89,21 +97,8 @@ class Ciesta::Form
89
97
  # @raise Ciesta::FormNotValid
90
98
  # @return [Boolean]
91
99
  def sync!(&block)
92
- raise Ciesta::ModelNotPresent, "Model not present" if object.nil?
93
100
  raise Ciesta::FormNotValid, "Form is not valid" unless valid?
94
- syncer.sync(&block)
95
- end
96
-
97
- # Sync form attributes to object
98
- #
99
- # @see Ciesta::Syncer
100
- #
101
- # @param [Block] block Block wich will be yielded after synfing
102
- #
103
- # @return [Boolean]
104
- def sync(&block)
105
- return if object.nil?
106
- syncer.sync(&block)
101
+ syncer.sync!(&block)
107
102
  end
108
103
 
109
104
  private
@@ -8,20 +8,45 @@ class Ciesta::Syncer
8
8
  # Constructor
9
9
  #
10
10
  # @api private
11
- # @param [Object] object Form objecr
11
+ # @param [Object] object Form object
12
12
  # @param [Ciesta::FieldList] fields Field list
13
13
  def initialize(object, fields)
14
14
  @object = object
15
15
  @fields = fields
16
16
  end
17
17
 
18
- # Sync attributes with objec
18
+ # Sync attributes with object
19
19
  #
20
20
  # @param [Block] block Block which will be yielded after syncing
21
21
  #
22
22
  # @return [Booelan]
23
23
  def sync
24
- fields.each { |name, value| object.send("#{name}=", value) }
24
+ return if object.nil?
25
+
26
+ fields.each do |field|
27
+ begin
28
+ save_to_object(field)
29
+ rescue StandardError
30
+ nil
31
+ end
32
+ end
33
+
34
+ yield(object) if block_given?
35
+
36
+ true
37
+ end
38
+
39
+ # Sync attributes with object
40
+ #
41
+ # @param [Block] block Block which will be yielded after syncing
42
+ #
43
+ # @raise Ciesta::ModelNotPresent
44
+ # @raise Ciesta::AttributeNotDefined
45
+ # @return [Booelan]
46
+ def sync!
47
+ raise Ciesta::ModelNotPresent, "Cannot sync without model" if object.nil?
48
+
49
+ fields.each { |field| save_to_object(field) }
25
50
 
26
51
  yield(object) if block_given?
27
52
 
@@ -31,4 +56,10 @@ class Ciesta::Syncer
31
56
  private
32
57
 
33
58
  attr_reader :object, :fields
59
+
60
+ def save_to_object(field)
61
+ object.send("#{field.name}=", field.value) unless field.virtual?
62
+ rescue NoMethodError
63
+ raise Ciesta::AttributeNotDefined, "Attribute #{field.name} is not defined on model"
64
+ end
34
65
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Ciesta
4
- VERSION = "0.2.3".freeze
4
+ VERSION = "0.2.4".freeze
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ciesta
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.3
4
+ version: 0.2.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Alexey