サーバー側でGrailsを使用してクロスオリジン通信を行いたいのですが。私が見つけた唯一のドキュメントはこれです
https://grails.org/plugin/cors
しかし、これは古いバージョンのGrails用です。私が見つけた他のドキュメントは春のものです:
https://spring.io/guides/gs/rest-service-cors/
そのため、ファイルSimpleCorsFilter.groovy
をinit/myproject/
フォルダーに追加しましたが、このコンポーネントをresources.groovy
に接続する方法がわかりません。
したがって、ここに到達した場合grails3.2。+を使用デフォルトの方法を使用できます。
application.yml
に移動し、以下を追加します。
grails:
cors:
enabled: true
Access-Control-Allow-Origin '*'
が追加されます。何か違うものが欲しいなら このページを見てください
この問題を解決するために、resources.groovyにエントリを持つ通常のサーブレットフィルタを使用しました。
public class CorsFilter extends OncePerRequestFilter {
@Override
protected void doFilterInternal(HttpServletRequest req, HttpServletResponse resp, FilterChain chain)
throws ServletException, IOException {
String Origin = req.getHeader("Origin");
boolean options = "OPTIONS".equals(req.getMethod());
if (options) {
if (Origin == null) return;
resp.addHeader("Access-Control-Allow-Headers", "Origin, authorization, accept, content-type, x-requested-with");
resp.addHeader("Access-Control-Allow-Methods", "GET, HEAD, POST, PUT, DELETE, TRACE, OPTIONS");
resp.addHeader("Access-Control-Max-Age", "3600");
}
resp.addHeader("Access-Control-Allow-Origin", Origin == null ? "*" : Origin);
resp.addHeader("Access-Control-Allow-Credentials", "true");
if (!options) chain.doFilter(req, resp);
}
}
resources.groovy:
beans = {
corsFilter(CorsFilter)
}
これは、基本認証を使用するCORSリクエストで機能します。 Grails 2.xプラグインを作成しましたが、これはGrails3で動作させるよりも簡単なようです。
具体的には、これが機能するコードです。インターセプター名はコントローラー名(ここではworkRequest)と一致する必要があり、ドメインは呼び出し元(ここではlocalhost:8081)である必要があり、必要なbefore()メソッドであることに注意してください。
package rest
class WorkRequestInterceptor {
boolean before() {
header( "Access-Control-Allow-Origin", "http://localhost:8081" )
header( "Access-Control-Allow-Credentials", "true" )
header( "Access-Control-Allow-Methods", "POST, GET, OPTIONS, DELETE" )
header( "Access-Control-Max-Age", "3600" )
true
}
boolean after() { true }
}
CORSの問題に見舞われたとき、私はemberjsフレームワークをGrails3.0のRESTアプリケーションと一緒に遊んでいました。この記事の手順に従う http://www.greggbolinger.com/rendering-json-in-grails-for-ember-js/ 私がさらに進むのを助けました。
この記事では、新しいインターセプターを使用して、正しいヘッダーを設定するCorsInterceptorクラスを作成する方法を示しています。
class CorsInterceptor {
CorsInterceptor() {
matchAll()
}
boolean before() {
header( "Access-Control-Allow-Origin", "http://localhost:4200" )
header( "Access-Control-Allow-Credentials", "true" )
header( "Access-Control-Allow-Methods", "POST, GET, OPTIONS, DELETE")
header( "Access-Control-Max-Age", "3600" )
true
}
boolean after() { true }
}
これはGETリクエストでは期待どおりに機能しましたが、POSTおよびPUTリクエストでは失敗しました。これは、OPTIONSプリフライトリクエストが最初に http:// localhost:8080)に送信されたためです。/mycontroller/1234 、これにより、私の場合は404 not foundが返されました。
この答えの助けを借りて https://stackoverflow.com/a/31834551 代わりにCorsInterceptorクラスをこれに変更しました:
class CorsInterceptor {
CorsInterceptor() {
matchAll()
}
boolean before() {
header( "Access-Control-Allow-Origin", "http://localhost:4200" )
boolean options = ("OPTIONS" == request.method)
if (options) {
header( "Access-Control-Allow-Origin", "http://localhost:4200" )
header( "Access-Control-Allow-Credentials", "true" )
header( "Access-Control-Allow-Methods", "POST, GET, OPTIONS, DELETE")
header( "Access-Control-Max-Age", "3600" )
response.status = 200
}
true
}
boolean after() { true }
}
これでPOSTおよびPUTリクエストが機能していました。
Grails3の新しいInterceptorAPIを使用する必要があります。 ( https://grails.github.io/grails-doc/3.0.x/guide/single.html#interceptors )
_grails create-interceptor
_コマンドを使用してインターセプターを作成できます。 CORSインターセプターの場合、このインターセプターのafter()
メソッドを使用し、すべてのリクエスト(または必要なリクエストのみ)に一致するように設定します。このメソッドではresponse
オブジェクトを使用できるため、ヘッダーの設定は、Springのドキュメントで説明されている場合と同様にする必要があります。
私が見つけたgrails3.1.xの最もクリーンでシンプルなソリューションは、ApacheのデフォルトのCorsFilterを追加することです。
import org.Apache.catalina.filters.CorsFilter
// Place your Spring DSL code here
beans = {
corsFilter(CorsFilter) //Custom CorsFilter under src/main/Java/ works as well. I prefer Apache though...
}
#user215556からの回答も同様に機能しますが、ApacheCorsフィルターのデフォルト設定も問題ありません。
Spring Securityコア/レストプラグインによって提供されるエンドポイントに対してCORSを有効にする必要がある場合は、次を追加する必要があります。
Bootstrap.groovy:
SpringSecurityUtils.clientRegisterFilter("corsFilter",
SecurityFilterPosition.SECURITY_CONTEXT_FILTER.order - 1)
resources.groovy:
beans = {
corsFilter(CorsFilter)
}