請教各位前輩大大,因為工作需要最近在自學vue(vue-cli)以及laravel 8目前遇到一個問題,我在前端發一個POST請求到後端要撈資料庫中其中一頁的資料,但是資料庫中如果資料多到一定的筆數就會前端就會報跨域的錯誤,只要少於就正常接收,用Postman卻都正常抓到資料,也測試過後端確實有撈到資料,就是在回傳到前端時這段不知道是哪裡有問題。前端用npm run dev後端用php artisan serve啟動的。
只要資料庫筆數多於20筆就報錯。
少於20筆就正常返回資料
這是前端封裝過的post請求的程式碼
這是後端接收的程式碼
---更新一下------------------------------------------------------------------
我後端也有照https://medium.com/%E4%B8%80%E5%80%8B%E5%B0%8F%E5%B0%8F%E5%B7%A5%E7%A8%8B%E5%B8%AB%E7%9A%84%E9%9A%A8%E6%89%8B%E7%AD%86%E8%A8%98/laravel-%E4%BD%BF%E7%94%A8-middleware-%E8%A7%A3%E6%B1%BA-access-control-allow-origin-%E7%9A%84%E5%95%8F%E9%A1%8C-18237e4f77d4
這篇做了一個中間件如下,
我也測試過這支有在運作。
有勞各位前輩看看我問題到底出在哪,謝謝!
--------------------------------------以解決---------------------------------問題出在後端api返回的時候我用echo不知為何數據量少可以正常傳遞,但數據量大一點會報錯,把echo改成return就正常了,詳細可看樓下大大的解答。
如果遇到有時候噴CORS,有時候正常沒噴
通常很有可能是後端沒正確return 回應
或者過程中出現例外沒有做好try catch
因此程式碼遇到例外中止在後端,無法正確回應設定CORS之後的回應
前端那邊就會噴出CORS的錯誤訊息
基本上,跨域問題不會跟筆數多少有連帶關係。
我推測是筆數多有跑其它的地方去發生跨域的問題。
所以再來幾個建議。
1.本機開發也盡量用域名方式來開發。可以免掉一些上線後的bug存在。
2.如1說的,域名如果是在自已本機開發。可以不需要用真實域名。直接改host文件來開發處理就好
3.跨域的問題常發生在不同port的情況下。這點要很小心。
4.跨域的設定值可以先用直接對應域名設定。以下是先萬用的設定方式給你使用。
////////// 萬用模式(end) ///////
$url = request()->server('HTTP_REFERER');
$urlArr = parse_url($url);
$httpType = $urlArr['scheme'] ?? 'error';
$host = $urlArr['host'] ?? 'error';
$port = $urlArr['port'] ?? '';
$setHost = $httpType.'://'.$host.($port ? ':'.$port : '');
////////// 萬用模式(end) ///////
if($setHost){
return $response->header('Access-Control-Allow-Origin', $setHost)
->header('Access-Control-Allow-Methods', '*')
->header('Access-Control-Allow-Headers', 'Origin, Methods, Content-Type, Authorization')
->header('Access-Control-Allow-Credentials', true);
}else{
return $response;
}
利用上面的程式碼。可以先萬用模式處理。等要正式上線。再調整為安全的模式。
另外要注意到你用的中間件如有碰到需要輸出的。全都要加上。
我之前原本也是要做統一輸出。但常常會像你一樣突然發生cors的問題。
後來才注意到有先後執行的輸出問題。但我中間件又不好調整位置。(會依情況不同的應用)
所以索性我將輸出放到一個 Repositorys 。再用中間件去做輸出對應處理。
如
public function handle($request, Closure $next)
{
$url = $request->server('HTTP_REFERER');
if(!$url){
abort(404);
}
$userRep = new userRep;
if($userRep->siteToUser($url,$request)){
$next = $next($request);
$next = systemRep::responseCors($next);//這隻就是處理的
return $next;
}else{
abort(404);
}
}
以上給你參考吧。