問(wèn)題描述
我很難嘗試使用跨域制作 jquery.form要求.我在使用 Firefox 和 Chrome 時(shí)遇到問(wèn)題(甚至還沒(méi)有嘗試過(guò) IE).
I'm having a hard time trying to make jquery.form with a cross-domain request. I'm having issues with Firefox and Chrome (didn't even try IE yet).
說(shuō)明:我的整個(gè)網(wǎng)站都位于 http://www.mysite.com 內(nèi).但是,我的聯(lián)系表單在另一臺(tái)服務(wù)器上,由 http://contact.mysite.com 引用.我認(rèn)為將其放在子域上會(huì)回避有關(guān)跨域請(qǐng)求的問(wèn)題,但顯然事實(shí)并非如此.http://contact.mysite.com 在 Sinatra.
Explanation: my whole site is located inside http://www.mysite.com. However, my contact form is on another server, referenced by http://contact.mysite.com . I thought that putting it on a subdomain would sidestep the issues regarding cross-domain requests, but apparently it didn't. http://contact.mysite.com is implemented in Sinatra.
我的 javascript 設(shè)置沒(méi)有什么花哨的.表單的action指向http://contact.mysite.com,方法是POST:
My javascript setup is nothing fancy. The form's action points to http://contact.mysite.com and the method is POST:
<form id="contact" action="http://contact.mysite.com/" method="post">
jquery.form 配置有 ajaxForm 調(diào)用:
jquery.form is configured with an ajaxForm call:
$(document).ready(function() {
$('#contact').ajaxForm({
success: function() { $('#success').fadeIn("slow"); },
error: function() { $('#error').fadeIn("slow"); }
});
});
我遇到的第一個(gè)問(wèn)題是 Firefox 3.5 - 顯然它發(fā)送了一個(gè) OPTIONS 請(qǐng)求,期望服務(wù)器提供特定的答案.我使用 this question 來(lái)配置我的 Sinatra 應(yīng)用程序,使其達(dá)到預(yù)期效果(似乎更多最新版本的 sinatra 包含一個(gè)選項(xiàng)動(dòng)詞):
The first problem I encountered was with Firefox 3.5 - apparently it sends an OPTIONS request expecting an specific answer from the server. I used this question to configure my Sinatra app so it did what was expected (it seems that more recent versions of sinatra include an options verb):
require 'rubygems'
require 'sinatra'
require 'pony'
# patch sinatra so it handles options requests - see https://stackoverflow.com/questions/4351904/sinatra-options-http-verb
configure do
class << Sinatra::Base
def options(path, opts={}, &block)
route 'OPTIONS', path, opts, &block
end
end
Sinatra::Delegator.delegate :options
end
# respond to options requests so that firefox can do cross-domain ajax requests
options '/' do
response['Access-Control-Allow-Origin'] = '*'
response['Access-Control-Allow-Methods'] = 'POST'
response['Access-Control-Max-Age'] = '2592000'
end
post '/' do
# use Pony to send an email
Pony.mail(...)
end
使用 jquery 1.4.3,我在 firebug 上看到一個(gè) OPTIONS 請(qǐng)求,然后是一個(gè) POST 請(qǐng)求(狀態(tài) 200.電子郵件已發(fā)送).使用 jquery 1.3.2 或 1.5,僅顯示 OPTIONS 請(qǐng)求(未發(fā)送電子郵件).
With jquery 1.4.3, I saw on firebug an OPTIONS request followed by a POST request (status 200. The email was sent). With jquery 1.3.2 or 1.5, only the OPTIONS request was shown (the email was not sent).
盡管如此,error
回調(diào)總是會(huì)在我嘗試過(guò)的所有 jquery 版本中觸發(fā).我將其追溯到 $.ajax(...)
調(diào)用,所以我不確定這個(gè)問(wèn)題是來(lái)自 jquery.form 還是 jquery 本身.
Nevertheless, the error
callback is always fired with all versions of jquery I tried. I traced that down to the $.ajax(...)
call, so I'm not sure of whether this problem comes from jquery.form or jquery itself.
我嘗試注銷來(lái)自錯(cuò)誤的信息:
I tried logging out the information coming from the error:
$('#contact').ajaxForm({
success: function() { $('#success').fadeIn("slow"); },
error: function(jqXHR, textStatus, errorThrown) {
console.log(jqXHR.status);
console.log(jqXHR.statusText);
}
});
jquery 1.4.3 上的輸出(發(fā)送 OPTIONS 和 POST 請(qǐng)求后,狀態(tài)均為 200):
Output on jquery 1.4.3 (after the OPTIONS & POST requests are sent, both with status 200):
0
(empty string)
jquery 1.5 上的輸出(在 OPTIONS 返回 200 狀態(tài)后;從不發(fā)送 POST)
Output on jquery 1.5 (after OPTIONS returns with a 200 status; POST is never sent)
302
error
我真的迷路了.
- 是否有插件可以處理這個(gè)問(wèn)題?
- 我是否在某處遺漏了什么?
任何幫助將不勝感激.
推薦答案
AJAX 請(qǐng)求無(wú)法跨域執(zhí)行(UPD: 不再正確,所有現(xiàn)代瀏覽器都支持 CORS),但您可以使用 JSONP 代替.雖然 JSONP 可以跨域工作,但它不能用于 POST 請(qǐng)求,您需要將表單的方法更改為 get
并使用:
AJAX requests cannot be executed cross-domain (UPD: not true anymore, all modern browsers support CORS), but you can use JSONP instead. Although JSONP works cross-domain, it can't be used for POST requests, and you'll need to change you form's method to get
and use this:
$('#contact').ajaxForm({
success: function() { $('#success').fadeIn("slow"); },
error: function() { $('#error').fadeIn("slow"); },
dataType: 'jsonp'
});
上述解決方案依賴于您的服務(wù)器以有效的 jsonp 響應(yīng)進(jìn)行響應(yīng),否則將不會(huì)執(zhí)行 success
處理程序.例如:response.write(request.callback + '(' + result.to_json + ')')
The solution above relies on your server responding with a valid jsonp response, otherwise success
handler won't be executed. e.g: response.write(request.callback + '(' + result.to_json + ')')
最新版本的 jQuery 可以在沒(méi)有 ajaxForm
插件的情況下序列化表單.如果你不需要文件上傳,你可以使用這個(gè):
Latest versions of jQuery can serialize forms without the ajaxForm
plugin. If you don't need file uploads you can use this:
$('form').submit(function() {
var url = $(this).attr('action')
var params = $(this).serialize()
$.getJSON(url + '?' + params + "&callback=?", function(data) {
// success
})
return false
});
這篇關(guān)于jquery.form 和跨域請(qǐng)求的文章就介紹到這了,希望我們推薦的答案對(duì)大家有所幫助,也希望大家多多支持html5模板網(wǎng)!