rails_admin 0.8.1 → 2.2.1

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of rails_admin might be problematic. Click here for more details.

Files changed (313) hide show
  1. checksums.yaml +5 -5
  2. data/Gemfile +17 -34
  3. data/LICENSE.md +1 -1
  4. data/README.md +34 -26
  5. data/app/assets/images/rails_admin/aristo/images/bg_fallback.png +0 -0
  6. data/app/assets/images/rails_admin/aristo/images/slider_handles.png +0 -0
  7. data/app/assets/images/rails_admin/aristo/images/ui-icons_222222_256x240.png +0 -0
  8. data/app/assets/images/rails_admin/aristo/images/ui-icons_454545_256x240.png +0 -0
  9. data/app/assets/images/rails_admin/bullet_black.png +0 -0
  10. data/app/assets/images/rails_admin/bullet_white.png +0 -0
  11. data/app/assets/images/rails_admin/calendar.png +0 -0
  12. data/app/assets/images/rails_admin/clock.png +0 -0
  13. data/app/assets/images/rails_admin/magnifier.png +0 -0
  14. data/app/assets/images/rails_admin/multiselect/ui-icon-circle-triangle-n-dark.png +0 -0
  15. data/app/assets/images/rails_admin/multiselect/ui-icon-circle-triangle-s-dark.png +0 -0
  16. data/app/assets/images/rails_admin/multiselect/ui-icon-circle-triangle-s-light.png +0 -0
  17. data/app/assets/javascripts/rails_admin/custom/ui.js +1 -0
  18. data/app/assets/javascripts/rails_admin/jquery-ui.js.erb +8 -0
  19. data/app/assets/javascripts/rails_admin/jquery.migrate.js +3 -0
  20. data/app/assets/javascripts/rails_admin/ra.filter-box.js +148 -60
  21. data/app/assets/javascripts/rails_admin/ra.filtering-multiselect.js +31 -26
  22. data/app/assets/javascripts/rails_admin/ra.filtering-select.js +211 -110
  23. data/app/assets/javascripts/rails_admin/ra.i18n.js +28 -0
  24. data/app/assets/javascripts/rails_admin/ra.nested-form-hooks.js +59 -0
  25. data/app/assets/javascripts/rails_admin/ra.sidescroll.js +31 -0
  26. data/app/assets/javascripts/rails_admin/ra.widgets.js +379 -0
  27. data/app/assets/javascripts/rails_admin/rails_admin.js +5 -5
  28. data/app/assets/javascripts/rails_admin/ui.js +135 -0
  29. data/app/assets/stylesheets/rails_admin/aristo/images/bg_fallback.png +0 -0
  30. data/app/assets/stylesheets/rails_admin/aristo/images/slider_handles.png +0 -0
  31. data/app/assets/stylesheets/rails_admin/aristo/images/ui-icons_222222_256x240.png +0 -0
  32. data/app/assets/stylesheets/rails_admin/aristo/images/ui-icons_454545_256x240.png +0 -0
  33. data/app/assets/stylesheets/rails_admin/aristo/jquery-ui-1.8.7.custom.scss +5 -5
  34. data/app/assets/stylesheets/rails_admin/ra.sidescroll.scss +29 -0
  35. data/app/assets/stylesheets/rails_admin/ra.widgets.scss +9 -1
  36. data/app/assets/stylesheets/rails_admin/rails_admin.scss.erb +2 -1
  37. data/app/controllers/rails_admin/application_controller.rb +14 -8
  38. data/app/controllers/rails_admin/main_controller.rb +9 -9
  39. data/app/helpers/rails_admin/application_helper.rb +26 -11
  40. data/app/helpers/rails_admin/form_builder.rb +20 -12
  41. data/app/helpers/rails_admin/main_helper.rb +8 -7
  42. data/app/views/kaminari/{twitter-bootstrap → ra-twitter-bootstrap}/_gap.html.haml +0 -0
  43. data/app/views/kaminari/{twitter-bootstrap → ra-twitter-bootstrap}/_next_page.html.haml +0 -0
  44. data/app/views/kaminari/{twitter-bootstrap → ra-twitter-bootstrap}/_page.html.haml +0 -0
  45. data/app/views/kaminari/{twitter-bootstrap → ra-twitter-bootstrap}/_paginator.html.haml +0 -0
  46. data/app/views/kaminari/{twitter-bootstrap → ra-twitter-bootstrap}/_prev_page.html.haml +0 -0
  47. data/app/views/kaminari/ra-twitter-bootstrap/without_count/_next_page.html.haml +4 -0
  48. data/app/views/kaminari/ra-twitter-bootstrap/without_count/_paginator.html.haml +4 -0
  49. data/app/views/kaminari/ra-twitter-bootstrap/without_count/_prev_page.html.haml +4 -0
  50. data/app/views/layouts/rails_admin/_head.html.haml +7 -0
  51. data/app/views/layouts/rails_admin/_secondary_navigation.html.haml +2 -2
  52. data/app/views/layouts/rails_admin/_sidebar_navigation.html.haml +2 -1
  53. data/app/views/layouts/rails_admin/application.html.haml +4 -10
  54. data/app/views/layouts/rails_admin/pjax.html.haml +1 -5
  55. data/app/views/rails_admin/main/_delete_notice.html.haml +14 -9
  56. data/app/views/rails_admin/main/_form_action_text.html.haml +7 -0
  57. data/app/views/rails_admin/main/_form_colorpicker.html.haml +1 -1
  58. data/app/views/rails_admin/main/_form_enumeration.html.haml +4 -3
  59. data/app/views/rails_admin/main/_form_file_upload.html.haml +5 -5
  60. data/app/views/rails_admin/main/_form_filtering_multiselect.html.haml +7 -6
  61. data/app/views/rails_admin/main/_form_filtering_select.html.haml +1 -1
  62. data/app/views/rails_admin/main/_form_multiple_file_upload.html.haml +16 -0
  63. data/app/views/rails_admin/main/_form_polymorphic_association.html.haml +18 -3
  64. data/app/views/rails_admin/main/_form_simple_mde.haml +8 -0
  65. data/app/views/rails_admin/main/dashboard.html.haml +5 -6
  66. data/app/views/rails_admin/main/export.html.haml +45 -36
  67. data/app/views/rails_admin/main/history.html.haml +3 -3
  68. data/app/views/rails_admin/main/index.html.haml +37 -26
  69. data/app/views/rails_admin/main/show.html.haml +6 -7
  70. data/config/initializers/active_record_extensions.rb +3 -3
  71. data/config/initializers/haml.rb +4 -1
  72. data/config/locales/rails_admin.en.yml +5 -2
  73. data/lib/generators/rails_admin/templates/initializer.erb +6 -2
  74. data/lib/rails_admin/abstract_model.rb +9 -10
  75. data/lib/rails_admin/adapters/active_record/abstract_object.rb +9 -3
  76. data/lib/rails_admin/adapters/active_record/property.rb +1 -5
  77. data/lib/rails_admin/adapters/active_record.rb +83 -28
  78. data/lib/rails_admin/adapters/mongoid/abstract_object.rb +3 -3
  79. data/lib/rails_admin/adapters/mongoid/association.rb +18 -6
  80. data/lib/rails_admin/adapters/mongoid/bson.rb +29 -0
  81. data/lib/rails_admin/adapters/mongoid/extension.rb +4 -2
  82. data/lib/rails_admin/adapters/mongoid/property.rb +3 -3
  83. data/lib/rails_admin/adapters/mongoid.rb +40 -26
  84. data/lib/rails_admin/bootstrap-sass/compass_functions.rb +1 -1
  85. data/lib/rails_admin/bootstrap-sass/sass_functions.rb +1 -3
  86. data/lib/rails_admin/bootstrap-sass.rb +8 -6
  87. data/lib/rails_admin/config/actions/base.rb +20 -5
  88. data/lib/rails_admin/config/actions/bulk_delete.rb +2 -4
  89. data/lib/rails_admin/config/actions/dashboard.rb +9 -5
  90. data/lib/rails_admin/config/actions/edit.rb +1 -3
  91. data/lib/rails_admin/config/actions/export.rb +1 -1
  92. data/lib/rails_admin/config/actions/index.rb +5 -3
  93. data/lib/rails_admin/config/actions/new.rb +4 -5
  94. data/lib/rails_admin/config/actions.rb +1 -1
  95. data/lib/rails_admin/config/configurable.rb +25 -18
  96. data/lib/rails_admin/config/fields/association.rb +11 -3
  97. data/lib/rails_admin/config/fields/base.rb +20 -27
  98. data/lib/rails_admin/config/fields/factories/action_text.rb +12 -0
  99. data/lib/rails_admin/config/fields/factories/active_storage.rb +30 -0
  100. data/lib/rails_admin/config/fields/factories/carrierwave.rb +4 -2
  101. data/lib/rails_admin/config/fields/factories/dragonfly.rb +1 -1
  102. data/lib/rails_admin/config/fields/factories/shrine.rb +27 -0
  103. data/lib/rails_admin/config/fields/types/action_text.rb +30 -0
  104. data/lib/rails_admin/config/fields/types/active_record_enum.rb +19 -2
  105. data/lib/rails_admin/config/fields/types/active_storage.rb +49 -0
  106. data/lib/rails_admin/config/fields/types/all.rb +7 -1
  107. data/lib/rails_admin/config/fields/types/belongs_to_association.rb +8 -0
  108. data/lib/rails_admin/config/fields/types/bson_object_id.rb +1 -15
  109. data/lib/rails_admin/config/fields/types/ck_editor.rb +7 -7
  110. data/lib/rails_admin/config/fields/types/code_mirror.rb +10 -12
  111. data/lib/rails_admin/config/fields/types/color.rb +2 -2
  112. data/lib/rails_admin/config/fields/types/datetime.rb +6 -3
  113. data/lib/rails_admin/config/fields/types/file_upload.rb +12 -4
  114. data/lib/rails_admin/config/fields/types/froala.rb +9 -11
  115. data/lib/rails_admin/config/fields/types/has_many_association.rb +1 -1
  116. data/lib/rails_admin/config/fields/types/hidden.rb +2 -2
  117. data/lib/rails_admin/config/fields/types/json.rb +9 -1
  118. data/lib/rails_admin/config/fields/types/multiple_active_storage.rb +53 -0
  119. data/lib/rails_admin/config/fields/types/multiple_carrierwave.rb +56 -0
  120. data/lib/rails_admin/config/fields/types/multiple_file_upload.rb +125 -0
  121. data/lib/rails_admin/config/fields/types/password.rb +5 -1
  122. data/lib/rails_admin/config/fields/types/polymorphic_association.rb +12 -1
  123. data/lib/rails_admin/config/fields/types/serialized.rb +2 -2
  124. data/lib/rails_admin/config/fields/types/shrine.rb +54 -0
  125. data/lib/rails_admin/config/fields/types/simple_mde.rb +36 -0
  126. data/lib/rails_admin/config/fields/types/string.rb +8 -7
  127. data/lib/rails_admin/config/fields/types/string_like.rb +19 -0
  128. data/lib/rails_admin/config/fields/types/text.rb +2 -20
  129. data/lib/rails_admin/config/fields/types/wysihtml5.rb +14 -10
  130. data/lib/rails_admin/config/fields/types.rb +1 -1
  131. data/lib/rails_admin/config/fields.rb +3 -1
  132. data/lib/rails_admin/config/has_fields.rb +1 -1
  133. data/lib/rails_admin/config/has_groups.rb +1 -1
  134. data/lib/rails_admin/config/hideable.rb +1 -1
  135. data/lib/rails_admin/config/inspectable.rb +39 -0
  136. data/lib/rails_admin/config/lazy_model.rb +48 -8
  137. data/lib/rails_admin/config/model.rb +10 -22
  138. data/lib/rails_admin/config/proxyable/proxy.rb +7 -9
  139. data/lib/rails_admin/config/proxyable.rb +13 -1
  140. data/lib/rails_admin/config/sections/base.rb +4 -17
  141. data/lib/rails_admin/config/sections/list.rb +37 -0
  142. data/lib/rails_admin/config.rb +46 -25
  143. data/lib/rails_admin/engine.rb +37 -4
  144. data/lib/rails_admin/extension.rb +16 -4
  145. data/lib/rails_admin/extensions/cancancan/authorization_adapter.rb +23 -7
  146. data/lib/rails_admin/extensions/cancancan.rb +1 -1
  147. data/lib/rails_admin/extensions/controller_extension.rb +6 -0
  148. data/lib/rails_admin/extensions/history/auditing_adapter.rb +2 -2
  149. data/lib/rails_admin/extensions/history/history.rb +2 -2
  150. data/lib/rails_admin/extensions/paper_trail/auditing_adapter.rb +59 -17
  151. data/lib/rails_admin/extensions/pundit/authorization_adapter.rb +11 -3
  152. data/lib/rails_admin/support/csv_converter.rb +20 -14
  153. data/lib/rails_admin/support/datetime.rb +7 -6
  154. data/lib/rails_admin/support/i18n.rb +7 -5
  155. data/lib/rails_admin/version.rb +2 -2
  156. data/lib/rails_admin.rb +23 -1
  157. data/lib/tasks/rails_admin.rake +16 -7
  158. data/vendor/assets/fonts/rails_admin/FontAwesome.otf +0 -0
  159. data/vendor/assets/fonts/rails_admin/fontawesome-webfont.eot +0 -0
  160. data/vendor/assets/fonts/rails_admin/fontawesome-webfont.svg +2671 -0
  161. data/vendor/assets/fonts/rails_admin/fontawesome-webfont.ttf +0 -0
  162. data/vendor/assets/fonts/rails_admin/fontawesome-webfont.woff +0 -0
  163. data/vendor/assets/fonts/rails_admin/fontawesome-webfont.woff2 +0 -0
  164. data/vendor/assets/images/rails_admin/bootstrap/glyphicons-halflings-white.png +0 -0
  165. data/vendor/assets/images/rails_admin/bootstrap/glyphicons-halflings.png +0 -0
  166. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_background.png +0 -0
  167. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_hex.png +0 -0
  168. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_hsb_b.png +0 -0
  169. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_hsb_h.png +0 -0
  170. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_hsb_s.png +0 -0
  171. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_indic.gif +0 -0
  172. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_overlay.png +0 -0
  173. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_rgb_b.png +0 -0
  174. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_rgb_g.png +0 -0
  175. data/{app → vendor}/assets/images/rails_admin/colorpicker/colorpicker_rgb_r.png +0 -0
  176. data/{app → vendor}/assets/images/rails_admin/colorpicker/colorpicker_select.gif +0 -0
  177. data/vendor/assets/images/rails_admin/colorpicker/colorpicker_submit.png +0 -0
  178. data/vendor/assets/images/rails_admin/colorpicker/custom_background.png +0 -0
  179. data/vendor/assets/images/rails_admin/colorpicker/custom_hex.png +0 -0
  180. data/vendor/assets/images/rails_admin/colorpicker/custom_hsb_b.png +0 -0
  181. data/vendor/assets/images/rails_admin/colorpicker/custom_hsb_h.png +0 -0
  182. data/vendor/assets/images/rails_admin/colorpicker/custom_hsb_s.png +0 -0
  183. data/vendor/assets/images/rails_admin/colorpicker/custom_indic.gif +0 -0
  184. data/{app → vendor}/assets/images/rails_admin/colorpicker/custom_rgb_b.png +0 -0
  185. data/{app → vendor}/assets/images/rails_admin/colorpicker/custom_rgb_g.png +0 -0
  186. data/{app → vendor}/assets/images/rails_admin/colorpicker/custom_rgb_r.png +0 -0
  187. data/vendor/assets/images/rails_admin/colorpicker/custom_submit.png +0 -0
  188. data/vendor/assets/images/rails_admin/colorpicker/select.png +0 -0
  189. data/{app → vendor}/assets/images/rails_admin/colorpicker/select2.png +0 -0
  190. data/vendor/assets/images/rails_admin/colorpicker/slider.png +0 -0
  191. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-affix.js +50 -28
  192. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-alert.js +10 -7
  193. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-button.js +35 -20
  194. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-carousel.js +48 -25
  195. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-collapse.js +70 -28
  196. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-dropdown.js +56 -42
  197. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-modal.js +118 -40
  198. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-popover.js +26 -16
  199. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-scrollspy.js +29 -27
  200. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-tab.js +46 -19
  201. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-tooltip.js +280 -60
  202. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-transition.js +5 -5
  203. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap-typeahead.js +0 -0
  204. data/{app → vendor}/assets/javascripts/rails_admin/bootstrap/bootstrap.js +0 -0
  205. data/vendor/assets/javascripts/rails_admin/bootstrap-datetimepicker.js +317 -150
  206. data/{app → vendor}/assets/javascripts/rails_admin/jquery.colorpicker.js +0 -0
  207. data/{app → vendor}/assets/javascripts/rails_admin/jquery.pjax.js +316 -161
  208. data/vendor/assets/javascripts/rails_admin/moment-with-locales.js +16528 -8420
  209. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_alerts.scss +0 -0
  210. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_badges.scss +0 -0
  211. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_breadcrumbs.scss +0 -0
  212. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_button-groups.scss +0 -0
  213. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_buttons.scss +0 -0
  214. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_carousel.scss +0 -0
  215. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_close.scss +0 -0
  216. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_code.scss +0 -0
  217. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_component-animations.scss +0 -0
  218. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_dropdowns.scss +0 -0
  219. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_forms.scss +0 -0
  220. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_glyphicons.scss +0 -0
  221. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_grid.scss +0 -0
  222. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_input-groups.scss +0 -0
  223. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_jumbotron.scss +0 -0
  224. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_labels.scss +0 -0
  225. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_list-group.scss +0 -0
  226. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_media.scss +0 -0
  227. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_mixins.scss +0 -0
  228. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_modals.scss +0 -0
  229. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_navbar.scss +0 -0
  230. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_navs.scss +0 -0
  231. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_normalize.scss +0 -0
  232. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_pager.scss +0 -0
  233. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_pagination.scss +0 -0
  234. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_panels.scss +0 -0
  235. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_popovers.scss +0 -0
  236. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_print.scss +0 -0
  237. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_progress-bars.scss +0 -0
  238. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_responsive-embed.scss +0 -0
  239. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_responsive-utilities.scss +0 -0
  240. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_scaffolding.scss +0 -0
  241. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_tables.scss +0 -0
  242. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_theme.scss +0 -0
  243. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_thumbnails.scss +0 -0
  244. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_tooltip.scss +0 -0
  245. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_type.scss +0 -0
  246. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_utilities.scss +0 -0
  247. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_variables.scss +0 -0
  248. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/_wells.scss +0 -0
  249. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/bootstrap.scss +0 -0
  250. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_alerts.scss +0 -0
  251. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_background-variant.scss +0 -0
  252. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_border-radius.scss +0 -0
  253. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_buttons.scss +0 -0
  254. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_center-block.scss +0 -0
  255. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_clearfix.scss +0 -0
  256. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_forms.scss +0 -0
  257. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_gradients.scss +0 -0
  258. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_grid-framework.scss +0 -0
  259. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_grid.scss +0 -0
  260. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_hide-text.scss +0 -0
  261. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_image.scss +0 -0
  262. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_labels.scss +0 -0
  263. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_list-group.scss +0 -0
  264. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_nav-divider.scss +0 -0
  265. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_nav-vertical-align.scss +0 -0
  266. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_opacity.scss +0 -0
  267. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_pagination.scss +0 -0
  268. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_panels.scss +0 -0
  269. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_progress-bar.scss +0 -0
  270. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_reset-filter.scss +0 -0
  271. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_resize.scss +0 -0
  272. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_responsive-visibility.scss +0 -0
  273. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_size.scss +0 -0
  274. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_tab-focus.scss +0 -0
  275. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_table-row.scss +0 -0
  276. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_text-emphasis.scss +0 -0
  277. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_text-overflow.scss +0 -0
  278. data/{app → vendor}/assets/stylesheets/rails_admin/bootstrap/mixins/_vendor-prefixes.scss +0 -0
  279. data/vendor/assets/stylesheets/rails_admin/font-awesome.scss +2342 -0
  280. data/{app → vendor}/assets/stylesheets/rails_admin/jquery.colorpicker.scss +0 -0
  281. metadata +214 -199
  282. data/app/assets/images/rails_admin/bootstrap/glyphicons-halflings-white.png +0 -0
  283. data/app/assets/images/rails_admin/bootstrap/glyphicons-halflings.png +0 -0
  284. data/app/assets/images/rails_admin/colorpicker/colorpicker_background.png +0 -0
  285. data/app/assets/images/rails_admin/colorpicker/colorpicker_hex.png +0 -0
  286. data/app/assets/images/rails_admin/colorpicker/colorpicker_hsb_b.png +0 -0
  287. data/app/assets/images/rails_admin/colorpicker/colorpicker_hsb_h.png +0 -0
  288. data/app/assets/images/rails_admin/colorpicker/colorpicker_hsb_s.png +0 -0
  289. data/app/assets/images/rails_admin/colorpicker/colorpicker_indic.gif +0 -0
  290. data/app/assets/images/rails_admin/colorpicker/colorpicker_overlay.png +0 -0
  291. data/app/assets/images/rails_admin/colorpicker/colorpicker_rgb_b.png +0 -0
  292. data/app/assets/images/rails_admin/colorpicker/colorpicker_rgb_g.png +0 -0
  293. data/app/assets/images/rails_admin/colorpicker/colorpicker_submit.png +0 -0
  294. data/app/assets/images/rails_admin/colorpicker/custom_background.png +0 -0
  295. data/app/assets/images/rails_admin/colorpicker/custom_hex.png +0 -0
  296. data/app/assets/images/rails_admin/colorpicker/custom_hsb_b.png +0 -0
  297. data/app/assets/images/rails_admin/colorpicker/custom_hsb_h.png +0 -0
  298. data/app/assets/images/rails_admin/colorpicker/custom_hsb_s.png +0 -0
  299. data/app/assets/images/rails_admin/colorpicker/custom_indic.gif +0 -0
  300. data/app/assets/images/rails_admin/colorpicker/custom_submit.png +0 -0
  301. data/app/assets/images/rails_admin/colorpicker/select.png +0 -0
  302. data/app/assets/images/rails_admin/colorpicker/slider.png +0 -0
  303. data/app/assets/javascripts/rails_admin/custom/ui.coffee +0 -1
  304. data/app/assets/javascripts/rails_admin/jquery.remotipart.fixed.js +0 -72
  305. data/app/assets/javascripts/rails_admin/ra.i18n.coffee +0 -8
  306. data/app/assets/javascripts/rails_admin/ra.nested-form-hooks.coffee +0 -52
  307. data/app/assets/javascripts/rails_admin/ra.widgets.coffee +0 -308
  308. data/app/assets/javascripts/rails_admin/ui.coffee +0 -102
  309. data/config/initializers/devise_patch.rb +0 -9
  310. data/lib/rails_admin/config/fields/factories/refile.rb +0 -25
  311. data/lib/rails_admin/config/fields/types/refile.rb +0 -27
  312. data/lib/rails_admin/extensions/cancan/authorization_adapter.rb +0 -57
  313. data/lib/rails_admin/extensions/cancan.rb +0 -3
@@ -1,6 +1,8 @@
1
- // jquery.pjax.js
2
- // copyright chris wanstrath
3
- // https://github.com/defunkt/jquery-pjax
1
+ /*!
2
+ * Copyright 2012, Chris Wanstrath
3
+ * Released under the MIT License
4
+ * https://github.com/defunkt/jquery-pjax
5
+ */
4
6
 
5
7
  (function($){
6
8
 
@@ -17,9 +19,7 @@
17
19
  // pjax specific options:
18
20
  //
19
21
  //
20
- // container - Where to stick the response body. Usually a String selector.
21
- // $(container).html(xhr.responseBody)
22
- // (default: current jquery context)
22
+ // container - String selector for the element where to place the response body.
23
23
  // push - Whether to pushState the URL. Defaults to true (of course).
24
24
  // replace - Want to use replaceState instead? That's cool.
25
25
  //
@@ -28,11 +28,13 @@
28
28
  //
29
29
  // Returns the jQuery object
30
30
  function fnPjax(selector, container, options) {
31
- var context = this
31
+ options = optionsFor(container, options)
32
32
  return this.on('click.pjax', selector, function(event) {
33
- var opts = $.extend({}, optionsFor(container, options))
34
- if (!opts.container)
35
- opts.container = $(this).attr('data-pjax') || context
33
+ var opts = options
34
+ if (!opts.container) {
35
+ opts = $.extend({}, options)
36
+ opts.container = $(this).attr('data-pjax')
37
+ }
36
38
  handleClick(event, opts)
37
39
  })
38
40
  }
@@ -50,16 +52,12 @@ function fnPjax(selector, container, options) {
50
52
  // // is the same as
51
53
  // $(document).pjax('a')
52
54
  //
53
- // $(document).on('click', 'a', function(event) {
54
- // var container = $(this).closest('[data-pjax-container]')
55
- // $.pjax.click(event, container)
56
- // })
57
- //
58
55
  // Returns nothing.
59
56
  function handleClick(event, container, options) {
60
57
  options = optionsFor(container, options)
61
58
 
62
59
  var link = event.currentTarget
60
+ var $link = $(link)
63
61
 
64
62
  if (link.tagName.toUpperCase() !== 'A')
65
63
  throw "$.fn.pjax or $.pjax.click requires an anchor element"
@@ -70,28 +68,32 @@ function handleClick(event, container, options) {
70
68
  return
71
69
 
72
70
  // Ignore cross origin links
73
- if ( location.protocol !== link.protocol || location.host !== link.host )
71
+ if ( location.protocol !== link.protocol || location.hostname !== link.hostname )
74
72
  return
75
73
 
76
- // Ignore anchors on the same page
77
- if (link.hash && link.href.replace(link.hash, '') ===
78
- location.href.replace(location.hash, ''))
74
+ // Ignore case when a hash is being tacked on the current URL
75
+ if ( link.href.indexOf('#') > -1 && stripHash(link) == stripHash(location) )
79
76
  return
80
77
 
81
- // Ignore empty anchor "foo.html#"
82
- if (link.href === location.href + '#')
78
+ // Ignore event with default prevented
79
+ if (event.isDefaultPrevented())
83
80
  return
84
81
 
85
82
  var defaults = {
86
83
  url: link.href,
87
- container: $(link).attr('data-pjax'),
88
- target: link,
89
- fragment: null
84
+ container: $link.attr('data-pjax'),
85
+ target: link
90
86
  }
91
87
 
92
- pjax($.extend({}, defaults, options))
88
+ var opts = $.extend({}, defaults, options)
89
+ var clickEvent = $.Event('pjax:click')
90
+ $link.trigger(clickEvent, [opts])
93
91
 
94
- event.preventDefault()
92
+ if (!clickEvent.isDefaultPrevented()) {
93
+ pjax(opts)
94
+ event.preventDefault()
95
+ $link.trigger('pjax:clicked', [opts])
96
+ }
95
97
  }
96
98
 
97
99
  // Public: pjax on form submit handler
@@ -104,8 +106,7 @@ function handleClick(event, container, options) {
104
106
  // Examples
105
107
  //
106
108
  // $(document).on('submit', 'form', function(event) {
107
- // var container = $(this).closest('[data-pjax-container]')
108
- // $.pjax.submit(event, container)
109
+ // $.pjax.submit(event, '[data-pjax-container]')
109
110
  // })
110
111
  //
111
112
  // Returns nothing.
@@ -113,17 +114,30 @@ function handleSubmit(event, container, options) {
113
114
  options = optionsFor(container, options)
114
115
 
115
116
  var form = event.currentTarget
117
+ var $form = $(form)
116
118
 
117
119
  if (form.tagName.toUpperCase() !== 'FORM')
118
120
  throw "$.pjax.submit requires a form element"
119
121
 
120
122
  var defaults = {
121
- type: form.method,
122
- url: form.action,
123
- data: $(form).serializeArray(),
124
- container: $(form).attr('data-pjax'),
125
- target: form,
126
- fragment: null
123
+ type: ($form.attr('method') || 'GET').toUpperCase(),
124
+ url: $form.attr('action'),
125
+ container: $form.attr('data-pjax'),
126
+ target: form
127
+ }
128
+
129
+ if (defaults.type !== 'GET' && window.FormData !== undefined) {
130
+ defaults.data = new FormData(form)
131
+ defaults.processData = false
132
+ defaults.contentType = false
133
+ } else {
134
+ // Can't handle file uploads, exit
135
+ if ($form.find(':file').length) {
136
+ return
137
+ }
138
+
139
+ // Fallback to manually serializing the fields
140
+ defaults.data = $form.serializeArray()
127
141
  }
128
142
 
129
143
  pjax($.extend({}, defaults, options))
@@ -139,8 +153,7 @@ function handleSubmit(event, container, options) {
139
153
  //
140
154
  // Accepts these extra keys:
141
155
  //
142
- // container - Where to stick the response body.
143
- // $(container).html(xhr.responseBody)
156
+ // container - String selector for where to stick the response body.
144
157
  // push - Whether to pushState the URL. Defaults to true (of course).
145
158
  // replace - Want to use replaceState instead? That's cool.
146
159
  //
@@ -157,21 +170,32 @@ function pjax(options) {
157
170
  options.url = options.url()
158
171
  }
159
172
 
160
- var target = options.target
161
-
162
173
  var hash = parseURL(options.url).hash
163
174
 
164
- var context = options.context = findContainerFor(options.container)
175
+ var containerType = $.type(options.container)
176
+ if (containerType !== 'string') {
177
+ throw "expected string value for 'container' option; got " + containerType
178
+ }
179
+ var context = options.context = $(options.container)
180
+ if (!context.length) {
181
+ throw "the container selector '" + options.container + "' did not match anything"
182
+ }
165
183
 
166
184
  // We want the browser to maintain two separate internal caches: one
167
185
  // for pjax'd partial page loads and one for normal page loads.
168
186
  // Without adding this secret parameter, some browsers will often
169
187
  // confuse the two.
170
188
  if (!options.data) options.data = {}
171
- options.data._pjax = context.selector
189
+ if ($.isArray(options.data)) {
190
+ options.data.push({name: '_pjax', value: options.container})
191
+ } else {
192
+ options.data._pjax = options.container
193
+ }
172
194
 
173
- function fire(type, args) {
174
- var event = $.Event(type, { relatedTarget: target })
195
+ function fire(type, args, props) {
196
+ if (!props) props = {}
197
+ props.relatedTarget = options.target
198
+ var event = $.Event(type, props)
175
199
  context.trigger(event, args)
176
200
  return !event.isDefaultPrevented()
177
201
  }
@@ -186,9 +210,7 @@ function pjax(options) {
186
210
  }
187
211
 
188
212
  xhr.setRequestHeader('X-PJAX', 'true')
189
- xhr.setRequestHeader('X-PJAX-Container', context.selector)
190
-
191
- var result
213
+ xhr.setRequestHeader('X-PJAX-Container', options.container)
192
214
 
193
215
  if (!fire('pjax:beforeSend', [xhr, settings]))
194
216
  return false
@@ -203,7 +225,9 @@ function pjax(options) {
203
225
  settings.timeout = 0
204
226
  }
205
227
 
206
- options.requestUrl = parseURL(settings.url).href
228
+ var url = parseURL(settings.url)
229
+ if (hash) url.hash = hash
230
+ options.requestUrl = stripInternalParams(url)
207
231
  }
208
232
 
209
233
  options.complete = function(xhr, textStatus) {
@@ -225,8 +249,31 @@ function pjax(options) {
225
249
  }
226
250
 
227
251
  options.success = function(data, status, xhr) {
252
+ var previousState = pjax.state
253
+
254
+ // If $.pjax.defaults.version is a function, invoke it first.
255
+ // Otherwise it can be a static string.
256
+ var currentVersion = (typeof $.pjax.defaults.version === 'function') ?
257
+ $.pjax.defaults.version() :
258
+ $.pjax.defaults.version
259
+
260
+ var latestVersion = xhr.getResponseHeader('X-PJAX-Version')
261
+
228
262
  var container = extractContainer(data, xhr, options)
229
263
 
264
+ var url = parseURL(container.url)
265
+ if (hash) {
266
+ url.hash = hash
267
+ container.url = url.href
268
+ }
269
+
270
+ // If there is a layout version mismatch, hard load the new url
271
+ if (currentVersion && latestVersion && currentVersion !== latestVersion) {
272
+ locationReplace(container.url)
273
+ return
274
+ }
275
+
276
+ // If the new response is missing a body, hard load the page
230
277
  if (!container.contents) {
231
278
  locationReplace(container.url)
232
279
  return
@@ -236,7 +283,7 @@ function pjax(options) {
236
283
  id: options.id || uniqueId(),
237
284
  url: container.url,
238
285
  title: container.title,
239
- container: context.selector,
286
+ container: options.container,
240
287
  fragment: options.fragment,
241
288
  timeout: options.timeout
242
289
  }
@@ -245,35 +292,47 @@ function pjax(options) {
245
292
  window.history.replaceState(pjax.state, container.title, container.url)
246
293
  }
247
294
 
295
+ // Only blur the focus if the focused element is within the container.
296
+ var blurFocus = $.contains(options.container, document.activeElement)
297
+
298
+ // Clear out any focused controls before inserting new page contents.
299
+ if (blurFocus) {
300
+ try {
301
+ document.activeElement.blur()
302
+ } catch (e) { }
303
+ }
304
+
248
305
  if (container.title) document.title = container.title
306
+
307
+ fire('pjax:beforeReplace', [container.contents, options], {
308
+ state: pjax.state,
309
+ previousState: previousState
310
+ })
249
311
  context.html(container.contents)
250
312
 
251
- // Scroll to top by default
252
- if (typeof options.scrollTo === 'number')
253
- $(window).scrollTop(options.scrollTo)
254
-
255
- // Google Analytics support
256
- if ( (options.replace || options.push) && window._gaq )
257
- _gaq.push(['_trackPageview'])
258
-
259
- // If the URL has a hash in it, make sure the browser
260
- // knows to navigate to the hash.
261
- if ( hash !== '' ) {
262
- // Avoid using simple hash set here. Will add another history
263
- // entry. Replace the url with replaceState and scroll to target
264
- // by hand.
265
- //
266
- // window.location.hash = hash
267
- var url = parseURL(container.url)
268
- url.hash = hash
313
+ // FF bug: Won't autofocus fields that are inserted via JS.
314
+ // This behavior is incorrect. So if theres no current focus, autofocus
315
+ // the last field.
316
+ //
317
+ // http://www.w3.org/html/wg/drafts/html/master/forms.html
318
+ var autofocusEl = context.find('input[autofocus], textarea[autofocus]').last()[0]
319
+ if (autofocusEl && document.activeElement !== autofocusEl) {
320
+ autofocusEl.focus()
321
+ }
322
+
323
+ executeScriptTags(container.scripts)
269
324
 
270
- pjax.state.url = url.href
271
- window.history.replaceState(pjax.state, container.title, url.href)
325
+ var scrollTo = options.scrollTo
272
326
 
273
- var target = $(url.hash)
274
- if (target.length) $(window).scrollTop(target.offset().top)
327
+ // Ensure browser scrolls to the element referenced by the URL anchor
328
+ if (hash) {
329
+ var name = decodeURIComponent(hash.slice(1))
330
+ var target = document.getElementById(name) || document.getElementsByName(name)[0]
331
+ if (target) scrollTo = $(target).offset().top
275
332
  }
276
333
 
334
+ if (typeof scrollTo == 'number') $(window).scrollTop(scrollTo)
335
+
277
336
  fire('pjax:success', [data, status, xhr, options])
278
337
  }
279
338
 
@@ -287,7 +346,7 @@ function pjax(options) {
287
346
  id: uniqueId(),
288
347
  url: window.location.href,
289
348
  title: document.title,
290
- container: context.selector,
349
+ container: options.container,
291
350
  fragment: options.fragment,
292
351
  timeout: options.timeout
293
352
  }
@@ -295,11 +354,7 @@ function pjax(options) {
295
354
  }
296
355
 
297
356
  // Cancel the current request if we're already pjaxing
298
- var xhr = pjax.xhr
299
- if ( xhr && xhr.readyState < 4) {
300
- xhr.onreadystatechange = $.noop
301
- xhr.abort()
302
- }
357
+ abortXHR(pjax.xhr)
303
358
 
304
359
  pjax.options = options
305
360
  var xhr = pjax.xhr = $.ajax(options)
@@ -307,9 +362,9 @@ function pjax(options) {
307
362
  if (xhr.readyState > 0) {
308
363
  if (options.push && !options.replace) {
309
364
  // Cache current container element before replacing it
310
- cachePush(pjax.state.id, context.clone().contents())
365
+ cachePush(pjax.state.id, [options.container, cloneContents(context)])
311
366
 
312
- window.history.pushState(null, "", stripPjaxParam(options.requestUrl))
367
+ window.history.pushState(null, "", options.requestUrl)
313
368
  }
314
369
 
315
370
  fire('pjax:start', [xhr, options])
@@ -340,35 +395,66 @@ function pjaxReload(container, options) {
340
395
  //
341
396
  // Returns nothing.
342
397
  function locationReplace(url) {
343
- window.history.replaceState(null, "", "#")
398
+ window.history.replaceState(null, "", pjax.state.url)
344
399
  window.location.replace(url)
345
400
  }
346
401
 
402
+
403
+ var initialPop = true
404
+ var initialURL = window.location.href
405
+ var initialState = window.history.state
406
+
407
+ // Initialize $.pjax.state if possible
408
+ // Happens when reloading a page and coming forward from a different
409
+ // session history.
410
+ if (initialState && initialState.container) {
411
+ pjax.state = initialState
412
+ }
413
+
414
+ // Non-webkit browsers don't fire an initial popstate event
415
+ if ('state' in window.history) {
416
+ initialPop = false
417
+ }
418
+
347
419
  // popstate handler takes care of the back and forward buttons
348
420
  //
349
421
  // You probably shouldn't use pjax on pages with other pushState
350
422
  // stuff yet.
351
423
  function onPjaxPopstate(event) {
424
+
425
+ // Hitting back or forward should override any pending PJAX request.
426
+ if (!initialPop) {
427
+ abortXHR(pjax.xhr)
428
+ }
429
+
430
+ var previousState = pjax.state
352
431
  var state = event.state
432
+ var direction
353
433
 
354
434
  if (state && state.container) {
355
- var container = $(state.container)
356
- if (container.length) {
357
- var contents = cacheMapping[state.id]
435
+ // When coming forward from a separate history session, will get an
436
+ // initial pop with a state we are already at. Skip reloading the current
437
+ // page.
438
+ if (initialPop && initialURL == state.url) return
439
+
440
+ if (previousState) {
441
+ // If popping back to the same state, just skip.
442
+ // Could be clicking back from hashchange rather than a pushState.
443
+ if (previousState.id === state.id) return
444
+
445
+ // Since state IDs always increase, we can deduce the navigation direction
446
+ direction = previousState.id < state.id ? 'forward' : 'back'
447
+ }
358
448
 
359
- if (pjax.state) {
360
- // Since state ids always increase, we can deduce the history
361
- // direction from the previous state.
362
- var direction = pjax.state.id < state.id ? 'forward' : 'back'
449
+ var cache = cacheMapping[state.id] || []
450
+ var containerSelector = cache[0] || state.container
451
+ var container = $(containerSelector), contents = cache[1]
363
452
 
453
+ if (container.length) {
454
+ if (previousState) {
364
455
  // Cache current container before replacement and inform the
365
456
  // cache which direction the history shifted.
366
- cachePop(direction, pjax.state.id, container.clone().contents())
367
- } else {
368
- // Page was reloaded but we have an existing history entry.
369
- // Set it to our initial state.
370
- pjax.state = state;
371
- return;
457
+ cachePop(direction, previousState.id, [containerSelector, cloneContents(container)])
372
458
  }
373
459
 
374
460
  var popstateEvent = $.Event('pjax:popstate', {
@@ -380,7 +466,7 @@ function onPjaxPopstate(event) {
380
466
  var options = {
381
467
  id: state.id,
382
468
  url: state.url,
383
- container: container,
469
+ container: containerSelector,
384
470
  push: false,
385
471
  fragment: state.fragment,
386
472
  timeout: state.timeout,
@@ -390,9 +476,14 @@ function onPjaxPopstate(event) {
390
476
  if (contents) {
391
477
  container.trigger('pjax:start', [null, options])
392
478
 
479
+ pjax.state = state
393
480
  if (state.title) document.title = state.title
481
+ var beforeReplaceEvent = $.Event('pjax:beforeReplace', {
482
+ state: state,
483
+ previousState: previousState
484
+ })
485
+ container.trigger(beforeReplaceEvent, [contents, options])
394
486
  container.html(contents)
395
- pjax.state = state
396
487
 
397
488
  container.trigger('pjax:end', [null, options])
398
489
  } else {
@@ -406,6 +497,7 @@ function onPjaxPopstate(event) {
406
497
  locationReplace(location.href)
407
498
  }
408
499
  }
500
+ initialPop = false
409
501
  }
410
502
 
411
503
  // Fallback version of main pjax function for browsers that don't
@@ -436,7 +528,12 @@ function fallbackPjax(options) {
436
528
  var pair = value.split('=')
437
529
  form.append($('<input>', {type: 'hidden', name: pair[0], value: pair[1]}))
438
530
  })
531
+ } else if ($.isArray(data)) {
532
+ $.each(data, function(index, value) {
533
+ form.append($('<input>', {type: 'hidden', name: value.name, value: value.value}))
534
+ })
439
535
  } else if (typeof data === 'object') {
536
+ var key
440
537
  for (key in data)
441
538
  form.append($('<input>', {type: 'hidden', name: key, value: data[key]}))
442
539
  }
@@ -445,6 +542,15 @@ function fallbackPjax(options) {
445
542
  form.submit()
446
543
  }
447
544
 
545
+ // Internal: Abort an XmlHttpRequest if it hasn't been completed,
546
+ // also removing its event handlers.
547
+ function abortXHR(xhr) {
548
+ if ( xhr && xhr.readyState < 4) {
549
+ xhr.onreadystatechange = $.noop
550
+ xhr.abort()
551
+ }
552
+ }
553
+
448
554
  // Internal: Generate unique id for state object.
449
555
  //
450
556
  // Use a timestamp instead of a counter since ids should still be
@@ -455,16 +561,22 @@ function uniqueId() {
455
561
  return (new Date).getTime()
456
562
  }
457
563
 
458
- // Internal: Strips _pjax param from url
459
- //
460
- // url - String
564
+ function cloneContents(container) {
565
+ var cloned = container.clone()
566
+ // Unmark script tags as already being eval'd so they can get executed again
567
+ // when restored from cache. HAXX: Uses jQuery internal method.
568
+ cloned.find('script').each(function(){
569
+ if (!this.src) jQuery._data(this, 'globalEval', false)
570
+ })
571
+ return cloned.contents()
572
+ }
573
+
574
+ // Internal: Strip internal query params from parsed URL.
461
575
  //
462
- // Returns String.
463
- function stripPjaxParam(url) {
464
- return url
465
- .replace(/\?_pjax=[^&]+&?/, '?')
466
- .replace(/_pjax=[^&]+&?/, '')
467
- .replace(/[\?&]$/, '')
576
+ // Returns sanitized url.href String.
577
+ function stripInternalParams(url) {
578
+ url.search = url.search.replace(/([?&])(_pjax|_)=[^&]*/g, '')
579
+ return url.href.replace(/\?($|#)/, '$1')
468
580
  }
469
581
 
470
582
  // Internal: Parse URL components and returns a Locationish object.
@@ -478,6 +590,16 @@ function parseURL(url) {
478
590
  return a
479
591
  }
480
592
 
593
+ // Internal: Return the `href` component of given URL object with the hash
594
+ // portion removed.
595
+ //
596
+ // location - Location or HTMLAnchorElement
597
+ //
598
+ // Returns String
599
+ function stripHash(location) {
600
+ return location.href.replace(/#.*/, '')
601
+ }
602
+
481
603
  // Internal: Build options Object for arguments.
482
604
  //
483
605
  // For convenience the first parameter can be either the container or
@@ -496,44 +618,14 @@ function parseURL(url) {
496
618
  //
497
619
  // Returns options Object.
498
620
  function optionsFor(container, options) {
499
- // Both container and options
500
- if ( container && options )
621
+ if (container && options) {
622
+ options = $.extend({}, options)
501
623
  options.container = container
502
-
503
- // First argument is options Object
504
- else if ( $.isPlainObject(container) )
505
- options = container
506
-
507
- // Only container
508
- else
509
- options = {container: container}
510
-
511
- // Find and validate container
512
- if (options.container)
513
- options.container = findContainerFor(options.container)
514
-
515
- return options
516
- }
517
-
518
- // Internal: Find container element for a variety of inputs.
519
- //
520
- // Because we can't persist elements using the history API, we must be
521
- // able to find a String selector that will consistently find the Element.
522
- //
523
- // container - A selector String, jQuery object, or DOM Element.
524
- //
525
- // Returns a jQuery object whose context is `document` and has a selector.
526
- function findContainerFor(container) {
527
- container = $(container)
528
-
529
- if ( !container.length ) {
530
- throw "no pjax container for " + container.selector
531
- } else if ( container.selector !== '' && container.context === document ) {
624
+ return options
625
+ } else if ($.isPlainObject(container)) {
532
626
  return container
533
- } else if ( container.attr('id') ) {
534
- return $('#' + container.attr('id'))
535
627
  } else {
536
- throw "cant get selector for pjax container!"
628
+ return {container: container}
537
629
  }
538
630
  }
539
631
 
@@ -547,7 +639,11 @@ function findContainerFor(container) {
547
639
  //
548
640
  // Returns a jQuery object.
549
641
  function findAll(elems, selector) {
550
- return elems.filter(selector).add(elems.find(selector));
642
+ return elems.filter(selector).add(elems.find(selector))
643
+ }
644
+
645
+ function parseHTML(html) {
646
+ return $.parseHTML(html, document, true)
551
647
  }
552
648
 
553
649
  // Internal: Extracts container and metadata from response.
@@ -562,18 +658,19 @@ function findAll(elems, selector) {
562
658
  //
563
659
  // Returns an Object with url, title, and contents keys.
564
660
  function extractContainer(data, xhr, options) {
565
- var obj = {}
661
+ var obj = {}, fullDocument = /<html/i.test(data)
566
662
 
567
663
  // Prefer X-PJAX-URL header if it was set, otherwise fallback to
568
664
  // using the original requested url.
569
- obj.url = stripPjaxParam(xhr.getResponseHeader('X-PJAX-URL') || options.requestUrl)
665
+ var serverUrl = xhr.getResponseHeader('X-PJAX-URL')
666
+ obj.url = serverUrl ? stripInternalParams(parseURL(serverUrl)) : options.requestUrl
570
667
 
571
668
  // Attempt to parse response html into elements
572
- if (/<html/i.test(data)) {
573
- var $head = $(data.match(/<head[^>]*>([\s\S.]*)<\/head>/i)[0])
574
- var $body = $(data.match(/<body[^>]*>([\s\S.]*)<\/body>/i)[0])
669
+ if (fullDocument) {
670
+ var $head = $(parseHTML(data.match(/<head[^>]*>([\s\S.]*)<\/head>/i)[0]))
671
+ var $body = $(parseHTML(data.match(/<body[^>]*>([\s\S.]*)<\/body>/i)[0]))
575
672
  } else {
576
- var $head = $body = $(data)
673
+ var $head = $body = $(parseHTML(data))
577
674
  }
578
675
 
579
676
  // If response data is empty, return fast
@@ -594,7 +691,7 @@ function extractContainer(data, xhr, options) {
594
691
  }
595
692
 
596
693
  if ($fragment.length) {
597
- obj.contents = $fragment.contents()
694
+ obj.contents = options.fragment === 'body' ? $fragment : $fragment.contents()
598
695
 
599
696
  // If there's no title, look for data-title and title attributes
600
697
  // on the fragment
@@ -602,17 +699,21 @@ function extractContainer(data, xhr, options) {
602
699
  obj.title = $fragment.attr('title') || $fragment.data('title')
603
700
  }
604
701
 
605
- } else if (!/<html/i.test(data)) {
702
+ } else if (!fullDocument) {
606
703
  obj.contents = $body
607
704
  }
608
705
 
609
706
  // Clean up any <title> tags
610
707
  if (obj.contents) {
611
708
  // Remove any parent title elements
612
- obj.contents = obj.contents.not('title')
709
+ obj.contents = obj.contents.not(function() { return $(this).is('title') })
613
710
 
614
- // Then scrub any titles from their descendents
711
+ // Then scrub any titles from their descendants
615
712
  obj.contents.find('title').remove()
713
+
714
+ // Gather all script[src] elements
715
+ obj.scripts = findAll(obj.contents, 'script[src]').remove()
716
+ obj.contents = obj.contents.not(obj.scripts)
616
717
  }
617
718
 
618
719
  // Trim any whitespace off the title
@@ -621,6 +722,34 @@ function extractContainer(data, xhr, options) {
621
722
  return obj
622
723
  }
623
724
 
725
+ // Load an execute scripts using standard script request.
726
+ //
727
+ // Avoids jQuery's traditional $.getScript which does a XHR request and
728
+ // globalEval.
729
+ //
730
+ // scripts - jQuery object of script Elements
731
+ //
732
+ // Returns nothing.
733
+ function executeScriptTags(scripts) {
734
+ if (!scripts) return
735
+
736
+ var existingScripts = $('script[src]')
737
+
738
+ scripts.each(function() {
739
+ var src = this.src
740
+ var matchedScripts = existingScripts.filter(function() {
741
+ return this.src === src
742
+ })
743
+ if (matchedScripts.length) return
744
+
745
+ var script = document.createElement('script')
746
+ var type = $(this).attr('type')
747
+ if (type) script.type = type
748
+ script.src = $(this).attr('src')
749
+ document.head.appendChild(script)
750
+ })
751
+ }
752
+
624
753
  // Internal: History DOM caching class.
625
754
  var cacheMapping = {}
626
755
  var cacheForwardStack = []
@@ -638,14 +767,11 @@ function cachePush(id, value) {
638
767
  cacheMapping[id] = value
639
768
  cacheBackStack.push(id)
640
769
 
641
- // Remove all entires in forward history stack after pushing
642
- // a new page.
643
- while (cacheForwardStack.length)
644
- delete cacheMapping[cacheForwardStack.shift()]
770
+ // Remove all entries in forward history stack after pushing a new page.
771
+ trimCacheStack(cacheForwardStack, 0)
645
772
 
646
773
  // Trim back history stack to max cache length.
647
- while (cacheBackStack.length > pjax.defaults.maxCacheLength)
648
- delete cacheMapping[cacheBackStack.shift()]
774
+ trimCacheStack(cacheBackStack, pjax.defaults.maxCacheLength)
649
775
  }
650
776
 
651
777
  // Shifts cache from directional history cache. Should be
@@ -672,6 +798,31 @@ function cachePop(direction, id, value) {
672
798
  pushStack.push(id)
673
799
  if (id = popStack.pop())
674
800
  delete cacheMapping[id]
801
+
802
+ // Trim whichever stack we just pushed to to max cache length.
803
+ trimCacheStack(pushStack, pjax.defaults.maxCacheLength)
804
+ }
805
+
806
+ // Trim a cache stack (either cacheBackStack or cacheForwardStack) to be no
807
+ // longer than the specified length, deleting cached DOM elements as necessary.
808
+ //
809
+ // stack - Array of state IDs
810
+ // length - Maximum length to trim to
811
+ //
812
+ // Returns nothing.
813
+ function trimCacheStack(stack, length) {
814
+ while (stack.length > length)
815
+ delete cacheMapping[stack.shift()]
816
+ }
817
+
818
+ // Public: Find version identifier for the initial page load.
819
+ //
820
+ // Returns String version or undefined.
821
+ function findVersion() {
822
+ return $('meta').filter(function() {
823
+ var name = $(this).attr('http-equiv')
824
+ return name && name.toUpperCase() === 'X-PJAX-VERSION'
825
+ }).attr('content')
675
826
  }
676
827
 
677
828
  // Install pjax functions on $.pjax to enable pushState behavior.
@@ -698,9 +849,10 @@ function enable() {
698
849
  type: 'GET',
699
850
  dataType: 'html',
700
851
  scrollTo: 0,
701
- maxCacheLength: 20
852
+ maxCacheLength: 20,
853
+ version: findVersion
702
854
  }
703
- $(window).bind('popstate.pjax', onPjaxPopstate)
855
+ $(window).on('popstate.pjax', onPjaxPopstate)
704
856
  }
705
857
 
706
858
  // Disable pushState behavior.
@@ -723,21 +875,24 @@ function disable() {
723
875
  $.pjax.submit = $.noop
724
876
  $.pjax.reload = function() { window.location.reload() }
725
877
 
726
- $(window).unbind('popstate.pjax', onPjaxPopstate)
878
+ $(window).off('popstate.pjax', onPjaxPopstate)
727
879
  }
728
880
 
729
881
 
730
882
  // Add the state property to jQuery's event object so we can use it in
731
883
  // $(window).bind('popstate')
732
- if ( $.inArray('state', $.event.props) < 0 )
884
+ if ($.event.props && $.inArray('state', $.event.props) < 0) {
733
885
  $.event.props.push('state')
886
+ } else if (!('state' in $.Event.prototype)) {
887
+ $.event.addProp('state')
888
+ }
734
889
 
735
- // Is pjax supported by this browser?
890
+ // Is pjax supported by this browser?
736
891
  $.support.pjax =
737
892
  window.history && window.history.pushState && window.history.replaceState &&
738
893
  // pushState isn't reliable on iOS until 5.
739
- !navigator.userAgent.match(/((iPod|iPhone|iPad).+\bOS\s+[1-4]|WebApps\/.+CFNetwork)/)
894
+ !navigator.userAgent.match(/((iPod|iPhone|iPad).+\bOS\s+[1-4]\D|WebApps\/.+CFNetwork)/)
740
895
 
741
896
  $.support.pjax ? enable() : disable()
742
897
 
743
- })(jQuery);
898
+ })(jQuery)