ruby on rails - ujs + remotipaart - when running jQuery `.html(...)` calls, the appended html becomes just text -
i using rails 5, remotipart. remotipart version is:
gem 'remotipart', github: 'mshibuya/remotipart'
(at moment of question, current commit 88d9a7d55bde66acb6cf3a3c6036a5a1fc991d5e).
when want submit form having multipart: true and
remote: true` but without sending attached file, works great. when send file, fails.
to illustrate case, consider response this:
(function() { modelerrors('<div class=\'alert alert-danger alert-dismissible\' role=\'alert\'>\n <div aria-label=\'close\' class=\'close fade in\' data-dismiss=\'alert\'>\n <span aria-hidden>\n ×\n <\/span>\n <\/div>\n code can\'t blank\n<\/div>\n'); }).call(this);
when response executed, after arriving (since js), form looks expected (in case, validation error right happen, , rendered danger alert right appear such text):
however, when fill file field, , repeat exact same case (exact same validation error), form looks quite different:
if can guess, contents passed text. actual response being received server bit different:
<script type="text/javascript">try{window.parent.document;}catch(err){document.domain=document.domain;}</script>(function() { modelerrors('<div class=\'alert alert-danger alert-dismissible\' role=\'alert\'>\n <div aria-label=\'close\' class=\'close fade in\' data-dismiss=\'alert\'>\n <span aria-hidden>\n ×\n <\/span>\n <\/div>\n code can\'t blank\n<\/div>\n'); }).call(this);
this actual body of response (it not bad copypaste, actual response wrapped remotipart).
the modalerrors
function quite dumb:
function modalerrors(html) { $('#main-modal > .modal-dialog > .modal-content > .modal-body > .errors').html(html); }
comparing jquery-appended html chunks (i them in browser's dom inspector), this:
good:
<div class="alert alert-danger" role="alert"> <ul style="list-style-type: none"> <li>code can't blank</li> </ul> </div>
bad:
code can't blank
what missing here? want allow resposes append html content when needed.
the remotipart
lib, uses named iframe-transport
, unwraps content later , executes response if fetched ajax.
however, tags stripped response, response converted this:
try{window.parent.document;}catch(err){document.domain=document.domain;}(function() { modelerrors('\n \n \n ×\n \n \n code can\'t blank\n\n'); }).call(this);
the solution found interact library in sane way, define helper helper, similar j
/ escape_javascript
:
module applicationhelper js_escape_map = { '\\' => '\\\\', '<' => '\\u003c', '&' => '\\u0026', '>' => '\\u003e', "\r\n" => '\n', "\n" => '\n', "\r" => '\n', '"' => '\\u0022', "'" => "\\u0027" } js_escape_map["\342\200\250".force_encoding(encoding::utf_8).encode!] = '
' js_escape_map["\342\200\251".force_encoding(encoding::utf_8).encode!] = '
' def escape_javascript_with_inside_html(javascript) if javascript result = javascript.gsub(/(\\|\r\n|\342\200\250|\342\200\251|[\n\r<>&"'])/u) {|match| js_escape_map[match] } javascript.html_safe? ? result.html_safe : result else '' end end alias_method :jh, :escape_javascript_with_inside_html end
in views susceptible of being sent both regular ajax , remotipart -in different scenarios, mean- replace j
calls jh
calls. example:
modalerrors('<%= j render 'shared/model_errors_alert', instance: @team %>')
was replaced with
modalerrors('<%= jh render 'shared/model_errors_alert', instance: @team %>')
Comments
Post a Comment