upjs-rails 0.12.5 → 0.13.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (48) hide show
  1. checksums.yaml +4 -4
  2. data/.rdoc_options +23 -0
  3. data/CHANGELOG.md +20 -0
  4. data/design/up-validate.js.coffee +284 -0
  5. data/dist/up-bootstrap.js +4 -0
  6. data/dist/up-bootstrap.min.js +1 -1
  7. data/dist/up.js +547 -102
  8. data/dist/up.min.js +2 -2
  9. data/lib/assets/javascripts/up/browser.js.coffee +3 -2
  10. data/lib/assets/javascripts/up/flow.js.coffee +95 -17
  11. data/lib/assets/javascripts/up/form.js.coffee +327 -34
  12. data/lib/assets/javascripts/up/history.js.coffee +1 -1
  13. data/lib/assets/javascripts/up/layout.js.coffee +4 -4
  14. data/lib/assets/javascripts/up/link.js.coffee +5 -2
  15. data/lib/assets/javascripts/up/modal.js.coffee +1 -0
  16. data/lib/assets/javascripts/up/proxy.js.coffee +27 -12
  17. data/lib/assets/javascripts/up/syntax.js.coffee +39 -20
  18. data/lib/assets/javascripts/up/util.js.coffee +29 -12
  19. data/lib/assets/javascripts/up-bootstrap/form-ext.js.coffee +1 -0
  20. data/lib/upjs/rails/engine.rb +1 -1
  21. data/lib/upjs/rails/inspector.rb +63 -0
  22. data/lib/upjs/rails/inspector_accessor.rb +28 -0
  23. data/lib/upjs/rails/request_echo_headers.rb +7 -0
  24. data/lib/upjs/rails/request_method_cookie.rb +12 -4
  25. data/lib/upjs/rails/version.rb +5 -1
  26. data/lib/upjs-rails.rb +7 -5
  27. data/spec_app/.rspec +2 -0
  28. data/spec_app/Gemfile +0 -3
  29. data/spec_app/Gemfile.lock +43 -44
  30. data/spec_app/app/assets/stylesheets/application.css +1 -1
  31. data/spec_app/app/controllers/test_controller.rb +23 -0
  32. data/spec_app/config/routes.rb +2 -0
  33. data/spec_app/spec/controllers/test_controller_spec.rb +67 -0
  34. data/spec_app/spec/javascripts/helpers/append_fixture.js.coffee +8 -0
  35. data/spec_app/spec/javascripts/helpers/last_request.js.coffee +18 -0
  36. data/spec_app/spec/javascripts/helpers/reset_path.js.coffee +1 -0
  37. data/spec_app/spec/javascripts/up/flow_spec.js.coffee +93 -43
  38. data/spec_app/spec/javascripts/up/form_spec.js.coffee +80 -18
  39. data/spec_app/spec/javascripts/up/history_spec.js.coffee +1 -5
  40. data/spec_app/spec/javascripts/up/link_spec.js.coffee +18 -17
  41. data/spec_app/spec/javascripts/up/modal_spec.js.coffee +32 -37
  42. data/spec_app/spec/javascripts/up/navigation_spec.js.coffee +7 -26
  43. data/spec_app/spec/javascripts/up/popup_spec.js.coffee +1 -7
  44. data/spec_app/spec/javascripts/up/proxy_spec.js.coffee +26 -25
  45. data/spec_app/spec/javascripts/up/util_spec.js.coffee +23 -0
  46. data/spec_app/spec/spec_helper.rb +62 -0
  47. metadata +12 -3
  48. data/lib/upjs/rails/request_ext.rb +0 -13
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 0f13c82c612066844882580ed4073b0f025cda22
4
- data.tar.gz: a0cef27d64bfdd0ea2ae249d668b679b23321841
3
+ metadata.gz: 22234d5edc76355380cc9a8c1c4996a59bf53afe
4
+ data.tar.gz: ee6e5cd9ec9a5932389cf08de790f855c2f8b558
5
5
  SHA512:
6
- metadata.gz: 008081bdca8fe235b86454baf676c3e5e19e7f89f3d76a6b58ee47502852f448411b26f5a0d0b0234b1a344a1c23276948efae1eefb1f04cbbd238b53981fa04
7
- data.tar.gz: 1775166c4643ffdcd0d2801669ea94557b6fa75adf38b5176b9b159f319aeae1dce2e8ffd8e4b17f43597bb9d1bf765d2f9b17aaf75df83b49925f185913eb1c
6
+ metadata.gz: 3ec849ae6db3272550ba10cfc26d906389a403751f2c1a7c2e71a7b66a59572595729077eb5d3c282097e8e1f1fdad579da12da60cc40cea21b6e4fbe8b667bf
7
+ data.tar.gz: d7c90fd8186375cb8584e0ba4413fa296182208e804a361bdf9ffea63f5c29f5a3ceb50d8c7219b87b86ddbbd781b8c00cac6a6ba7d307a4cf3d354745b1ff95
data/.rdoc_options ADDED
@@ -0,0 +1,23 @@
1
+ --- !ruby/object:RDoc::Options
2
+ encoding: UTF-8
3
+ static_path: []
4
+ rdoc_include:
5
+ - "./README.md"
6
+ - "./lib"
7
+ charset: UTF-8
8
+ exclude:
9
+ hyperlink_all: false
10
+ line_numbers: false
11
+ locale:
12
+ locale_dir: locale
13
+ locale_name:
14
+ main_page: README.md
15
+ markup: markdown
16
+ output_decoration: true
17
+ page_dir:
18
+ show_hash: false
19
+ tab_width: 2
20
+ template_stylesheets: []
21
+ title: upjs-rails - Rails bindings for Up.js
22
+ visibility: :protected
23
+ webcvs:
data/CHANGELOG.md CHANGED
@@ -5,6 +5,26 @@ All notable changes to this project will be documented in this file.
5
5
  This project mostly adheres to [Semantic Versioning](http://semver.org/).
6
6
 
7
7
 
8
+ 0.13.0
9
+ ------
10
+
11
+ ### Compatible changes
12
+
13
+ - Support for server-side live validation of forms
14
+ using the [`[up-validate]`](/up-validate) selector.
15
+ - Support for [non-standard CSS selectors from jQuery](https://api.jquery.com/category/selectors/),
16
+ such as [`:has`](http://api.jquery.com/has-selector/) or [`:visible`](http://api.jquery.com/visible-selector/).
17
+ - Allow to refer to the current element as `&` in target selectors. This is useful
18
+ to reference containers that contain the triggering element, e.g.
19
+ `<a href="/path" up-target=".container:has(&)">`
20
+ - Improve automatic generation of selectors for elements when no
21
+ explicit selector is given.
22
+ - Forms with `file` inputs will now cause forms to fall back to a standard submission without AJAX.
23
+ In a future release we will be able to submit file inputs via AJAX.
24
+ - The [request cache](/up.proxy) now reuses responses for `body` and `html` when asked for other selectors.
25
+ - Server responses can now change the document title by including an `X-Up-Title` header.
26
+
27
+
8
28
  0.12.5
9
29
  ------
10
30
 
@@ -0,0 +1,284 @@
1
+ findSelector = (selector, $origin) ->
2
+
3
+ $match = undefined
4
+
5
+ if u.isPresent($origin)
6
+ $match ||= filterFirstReal($origin.find(selector))
7
+ $match ||= filterFirstReal($origin.closest(selector))
8
+ $match ||= filterFirstReal($origin.closest('form').find(selector))
9
+
10
+ $match ||= filterFirstReal($(".up-popup #{selector}"))
11
+ $match ||= filterFirstReal($(".up-modal #{selector}"))
12
+ $match ||= filterFirstReal($(selector))
13
+
14
+ $match
15
+
16
+
17
+
18
+
19
+ [1] Präferiert $origin selbst
20
+ [2] Präferiert ein direkter Nachfahr von $origin
21
+ [3] ein direkter Vorfahr von $origin
22
+ [4] Präferiert im gleichen <form> von $origin
23
+ [5] Präferiert in .up-modal
24
+ [6] Präferiert in .up-popup
25
+ [7] Sonst irgendwo im Dokument
26
+
27
+
28
+
29
+ first(".up-popup #{selector}") ||
30
+ first(".up-modal #{selector}") ||
31
+ first(selector) ||
32
+ fragmentNotFound(selector)
33
+
34
+
35
+
36
+
37
+
38
+
39
+
40
+
41
+
42
+
43
+
44
+
45
+
46
+
47
+ Vielleicht Mittelding aus Variante 3 + hinterlegte
48
+
49
+ Wie gehe ich damit um, dass .form-group nicht unique ist?
50
+
51
+ form.submit(origin: '[name=email]')
52
+
53
+ Oder in den CSS-Selektor mit Custom Selector? input[name=email]^^.form-group
54
+
55
+ Oder kann ich bei elementFromSelector schlauer sein?
56
+
57
+ Oder das hier passiert nicht mit replace?
58
+
59
+
60
+
61
+ Variante 3: up-validate definiert Control-Gruppe
62
+ ================================================
63
+
64
+ HTML
65
+ ----
66
+
67
+ <form>
68
+
69
+ <div class="form-group">
70
+ <label>E-mail</label>
71
+ <input type="text" name="email" up-validate=".form-group:has(&)" />
72
+ </div>
73
+
74
+ <div class="form-group">
75
+ <label>Password</label>
76
+ <input type="text" name="password" up-validate="& < .form-group" />
77
+ </div>
78
+
79
+ </form>
80
+
81
+ Con:
82
+ ----
83
+ So kann ich up-validate nicht mehr für change/input verwenden, oder vielleicht mal die URL zu benennen
84
+ Das könnten dann aber auch andere Attribute sein.
85
+
86
+ Pro:
87
+ ----
88
+ Das wäre vielleicht auch eine Lösung für das Selects-Visibility-For Problem:
89
+
90
+ <form>
91
+
92
+ <div class="form-group">
93
+ <label>Public card</label>
94
+ <input type="checkbox" name="is_public" up-validate=".form-group, .confidential" />
95
+ </div>
96
+
97
+ <% if @form.object.is_public? %>
98
+ <div class="form-group confidential">
99
+ <label>Confidentiality</label>
100
+ <input type="text" name="confidential" up-validate=".form-group" />
101
+ </div>
102
+ <% end %>
103
+
104
+ </form>
105
+
106
+
107
+
108
+ Implementierung
109
+ ---------------
110
+
111
+ createSelectorFromElement = ($element) ->
112
+ id = $element.attr("id")
113
+ upId = $element.attr("up-id")
114
+ name = $element.attr("name")
115
+ if present(upId)
116
+ selector = "[up-id='#{upId}']"
117
+ else if present(id)
118
+ selector = "##{id}" + id if present(id)
119
+ else if present(name)
120
+ tagName = $element.prop("tagName").toLowerCase()
121
+ selector = "#{tagName}[name='#{name}']"
122
+ else
123
+ error('...')
124
+ selector
125
+
126
+ isGoodSelector = (selector) ->
127
+ u.contains(selector, '#') || u.contains(selector, '[name=]')
128
+
129
+ enhanceSelector = (selector, $origin) ->
130
+ unless isGoodSelector(selector)
131
+ $form = $origin.closest('form')
132
+ selector = "#{u.selectorFromElement($form)}:has(#{selector})"
133
+ selector
134
+
135
+ validate = (elementOrSelector, options) ->
136
+ $input = $(elementOrSelector)
137
+ closestGroupSelector = u.option(u.presence($input.attr('up-validate')), config.groups, 'form')
138
+ $group = $start.closest(closestGroupSelector)
139
+ $form = $group.closest('form')
140
+ $validateFlag = $('<input type="hidden" name="up-validate" value="1" >')
141
+ $validateFlag.appendTo($form)
142
+
143
+ groupSelector = u.createSelectorFromElement($group)
144
+ groupSelector = enhanceSelector(groupSelector)
145
+
146
+ up.submit($form, target: groupSelector, failTarget: groupSelector)
147
+
148
+ up.on 'change', '[up-validate!="input"]', (event) -> validate(event.target)
149
+ up.on 'input', '[up-validate="input"]', (event) -> validate(event.target)
150
+
151
+
152
+
153
+
154
+
155
+
156
+
157
+ Alternatives HTML
158
+ ------------------
159
+
160
+ <form>
161
+
162
+ <div class="form-group">
163
+ <label>E-mail</label>
164
+ <input type="text" name="email" up-changes=".form-group" />
165
+ </div>
166
+
167
+ <div class="form-group">
168
+ <label>Password</label>
169
+ <input type="text" name="password" up-changes=".form-group" />
170
+ </div>
171
+
172
+ </form>
173
+
174
+
175
+
176
+
177
+
178
+
179
+
180
+ Variante 2: up-validate an der Control-Gruppe
181
+ ==============================================
182
+
183
+ HTML
184
+ ----
185
+
186
+ <form>
187
+
188
+ <div class="form-group" up-validate>
189
+ <label>E-mail</label>
190
+ <input type="text" name="email" />
191
+ </div>
192
+
193
+ <div class="form-group" up-validate>
194
+ <label>Password</label>
195
+ <input type="text" name="password" />
196
+ </div>
197
+
198
+ </form>
199
+
200
+
201
+ Implementierung
202
+ ---------------
203
+
204
+ validate = (elementOrSelector, options) ->
205
+ $start = $(elementOrSelector) # $start is either a control or a form group
206
+ $group = $start.closest('[up-validate], form')
207
+ $form = $formGroup.closest('form')
208
+ $validateFlag = $('<input type="hidden" name="up-validate" value="1" >')
209
+ $validateFlag.appendTo($form)
210
+ groupSelector = u.createSelectorFromElement($group)
211
+ up.submit($form, target: groupSelector, failTarget: groupSelector, origin: )
212
+
213
+ up.on 'change', '[up-validate!="input"]', (event) -> validate(event.target)
214
+ up.on 'input', '[up-validate="input"]', (event) -> validate(event.target)
215
+
216
+
217
+
218
+
219
+ Variante 2: up-validate am Input, Up.js weiß wie Control-Gruppen gefunden werden
220
+ ================================================================================
221
+
222
+ HTML
223
+ ----
224
+
225
+ <form>
226
+
227
+ <div class="form-group">
228
+ <label>E-mail</label>
229
+ <input type="text" name="email" up-validate />
230
+ </div>
231
+
232
+ <div class="form-group">
233
+ <label>Password</label>
234
+ <input type="text" name="password" up-validate />
235
+ </div>
236
+
237
+ </form>
238
+
239
+
240
+ Implementierung
241
+ ---------------
242
+
243
+ config.groups = ['.form-group']
244
+
245
+ validate = (elementOrSelector, options) ->
246
+ $control = $(elementOrSelector)
247
+ $formGroup = u.multiSelector(config.groups).seekUp($control) || $control.closest('form')
248
+ $form = $formGroup.closest('form')
249
+ $validateFlag = $('<input type="hidden" name="up-validate" value="1" >')
250
+ $validateFlag.appendTo($form)
251
+ groupSelector = u.createSelectorFromElement($formGroup)
252
+ up.submit($form, target: groupSelector, failTarget: groupSelector)
253
+
254
+ up.on 'change', '[up-validate!="input"]', (event) -> validate(this)
255
+ up.on 'input', '[up-validate="input"]', (event) -> validate(this)
256
+
257
+
258
+ Alle Varianten: In Rails Controller
259
+ ===================================
260
+
261
+
262
+ class UsersController < ApplicationController
263
+
264
+ def create
265
+ build_user
266
+
267
+ if up?
268
+
269
+ if up.validate?
270
+
271
+
272
+ if request.up.validate? # same as `params['up-validate'].present?`
273
+ @user.valid? # run validations
274
+ render 'new'
275
+ elsif @user.save?
276
+ sign_in @user
277
+ redirect_to root_path
278
+ else
279
+ render 'new', status: :bad_request
280
+ end
281
+ end
282
+
283
+ end
284
+
data/dist/up-bootstrap.js CHANGED
@@ -1,3 +1,7 @@
1
+ (function() {
2
+ up.form.config.validateTargets.unshift('.form-group:has(&)');
3
+
4
+ }).call(this);
1
5
  (function() {
2
6
  up.layout.config.fixedTop.push('.navbar-fixed-top');
3
7
 
@@ -1 +1 @@
1
- (function(){up.layout.config.fixedTop.push(".navbar-fixed-top"),up.layout.config.fixedBottom.push(".navbar-fixed-bottom"),up.layout.config.anchoredRight.push(".navbar-fixed-top"),up.layout.config.anchoredRight.push(".navbar-fixed-bottom"),up.layout.config.anchoredRight.push(".footer")}).call(this),function(){up.modal.config.template='<div class="up-modal">\n <div class="up-modal-dialog modal-dialog">\n <div class="up-modal-content modal-content"></div>\n </div>\n</div>'}.call(this),function(){up.navigation.config.currentClasses.push("active")}.call(this),function(){}.call(this);
1
+ (function(){up.form.config.validateTargets.unshift(".form-group:has(&)")}).call(this),function(){up.layout.config.fixedTop.push(".navbar-fixed-top"),up.layout.config.fixedBottom.push(".navbar-fixed-bottom"),up.layout.config.anchoredRight.push(".navbar-fixed-top"),up.layout.config.anchoredRight.push(".navbar-fixed-bottom"),up.layout.config.anchoredRight.push(".footer")}.call(this),function(){up.modal.config.template='<div class="up-modal">\n <div class="up-modal-dialog modal-dialog">\n <div class="up-modal-content modal-content"></div>\n </div>\n</div>'}.call(this),function(){up.navigation.config.currentClasses.push("active")}.call(this),function(){}.call(this);