OpenLayers 3: Solicitação de origem cruzada bloqueada: a mesma política de origem não permite

8

Usando o OpenLayers 3, não consigo receber esta mensagem:

Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at http://myserver:8085/geoserver/sf/ows?service=WFS&version=1.0.0&request=GetFeature&typeName=sf:view1&maxFeatures=1&outputFormat=JSON. This can be fixed by moving the resource to the same domain or enabling CORS.

Este é o código:

// Ol3 only supports Projections "EPSG:4326" and "EPSG:3857". For every other projection you need proj4js
        proj4.defs("EPSG:2236", "+proj=tmerc +lat_0=24.33333333333333 +lon_0=-81 +k=0.999941177 +x_0=200000.0001016002 +y_0=0 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=us-ft +no_defs");

        // Leases Layer
        var myLayer = new ol.layer.Vector({
            source: new ol.source.GeoJSON({
                projection: 'EPSG:2236',
                url: 'http://myserver:8085/geoserver/sf/ows?service=WFS&version=1.0.0&request=GetFeature&typeName=sf:view1&maxFeatures=1&outputFormat=JSON',
                crossOrigin: null
            })
        });

// View
        var view = new ol.View({
            projection: 'EPSG:2236',
            center: [0, 0],
            zoom: 4
        });

        // Map
        var map = new ol.Map({
            target: 'map',
            renderer: 'canvas',
            layers: [myLayer],
            view: view
        });

Tentei definir a configuração crossOrigin para:

crossOrigin: null
crossOrigin: 'null'
crossOrigin: 'anonymous'

Só vejo o controle de aumento / redução de zoom, mas a camada não é renderizada.


Eu fui com a opção 3 do Simon abaixo. Habilitei o CORS no GeoServer, copiando os arquivos jar necessários dos jetty-servlets e habilitando-os no \ WEB-INF \ web.xml:

<filter>
    <filter-name>cross-origin</filter-name>
    <filter-class>org.eclipse.jetty.servlets.CrossOriginFilter</filter-class>
    <init-param>
        <param-name>allowedOrigins</param-name>
        <param-value>*</param-value>
    </init-param>
    <init-param>
        <param-name>allowedMethods</param-name>
        <param-value>*</param-value>
    </init-param>
    <init-param>
        <param-name>allowedHeaders</param-name>
        <param-value>*</param-value>
    </init-param>
</filter>
<filter-mapping>
    <filter-name>cross-origin</filter-name>
    <filter-pattern>/*</filter-pattern>
</filter-mapping>

Depois disso, testei a página novamente e recebi o mesmo erro:

Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at http://myserver:8085/geoserver/sf/ows?service=WFS&version=1.0.0&request=GetFeature&typeName=sf:view1&maxFeatures=1&outputFormat=JSON. This can be fixed by moving the resource to the same domain or enabling CORS.

Parece que ainda estou perdendo alguma coisa. Preciso fazer alguma coisa do OpenLayers Side?


Acabei me livrando do Jetty e desinstalando completamente o GeoServer. O problema é que quando você instala o instalador geoserver do Windows, ele instala uma versão do jetty com 4 anos de idade! (Jetty versão 6.1.8) Embora eu tenha copiado os arquivos jar para o CORS, ele é suportado apenas no Jetty 7+.

Descobri que você pode instalar um arquivo WAR. Decidi usar o Tomcat, pois é nisso que o GeoServer é mais testado, de acordo com esta nota no site do GeoServer:

Nota O GeoServer foi testado principalmente usando o Tomcat e, portanto, essas instruções podem não funcionar com outros aplicativos de contêiner.

Estas são as instruções para instalar o arquivo WAR:

http://docs.geoserver.org/stable/en/user/installation/war.html

Este é um bom vídeo de instruções também:

https://www.youtube.com/watch?v=YEOA8WWWVCw

Depois de concluir a instalação, você ativa o CORS:

http://enable-cors.org/server_tomcat.html

user3657279
fonte
Não posso testá-lo, o endereço que você forneceu não funciona.
Simon Zyx 14/09/14
Infelizmente, está tudo na intranet. Meus dois servidores (servidor geográfico e servidor OL) estão ambos na intranet.
user3657279
Peguei com êxito o caminho "Atualização # 2" descrito acima. Se você planeja fazer o mesmo, lembre-se de que o arquivo web.xml está localizado na pasta GeoServer recém-implantada, por exemplo: \ xampp \ tomcat \ webapps \ geoserver \ WEB-INF \ web.xml
Lauden,

Respostas:

4

Existe uma maneira fácil de contornar o problema usando JSONP:

  1. Você precisa ativar o JSONP no geoserver. Para ativar o JSONP, você precisa adicionar o seguinte no seu web.xml (por exemplo, C: \ Arquivos de Programas (x86) \ GeoServer 2.4.4 \ webapps \ geoserver \ WEB-INF \ web.xml)

... ENABLE_JSONP true ... 2. Reinicie seu servidor geográfico. Agora, para a solicitação GetFeatureInfo , o geoserver enviará parseResponse (dados JSON) para o cliente

  1. Como o JSONP funciona no cliente (JavaScript)? A chamada JSONP é simples. Você precisa adicionar um script com src = url (o URL é GetFeatureInfo) no cabeçalho

    var tag = document.createElement ("script"); tag.src = url; document.getElementsByTagName ("head") [0] .appendChild (tag);

Depois que o script é anexado, ele chama jsonp do servidor. chamando a função parseRespose. Portanto, você precisa definir uma função parseResponse da seguinte maneira. O escopo desta função deve ser global.

função parseResponse (dados) {var feature = data.features [0]; console.log (recurso);
};

Bikash
fonte
este é um post antigo, mas senti o mesmo problema, consegui contorná-lo com JSONP, mas é útil apenas para obter recursos do Geoserver; no entanto, se você pretende usar o WFS-T, está preso, escrevi alguns scripts php para operações de CRUD como um plano B e ainda à procura de uma maneira de permitir CORS em geoserver 2.9
Hicham Zouarhi
3

Eu mesmo enfrentei o mesmo problema e tentei muitas soluções discutidas aqui ou em outros fóruns e, finalmente, consegui resolver o problema de habilitar o Cross Origin no Geoserver.

Após muitos testes, descobri que a solução é bastante simples, seguindo as etapas exatas encontradas na página do Jetty Jetty Cross Origin Filter .

Mas, com uma pequena alteração, a página disse que precisamos copiar o seguinte filtro de origem cruzada para o arquivo de configuração ( Web.xml ), mas a solução que funcionou comigo é copiar essa configuração de xml do filtro para ( webdefault.xml ) arquivo de configuração, ao aplicar essa alteração, o geoserver funcionou como um encanto e eu poderia executar qualquer WFS, WMS GetFeatureInfoRequest no formato JSON usando AJAX em vez de usar a partição IFrame.

Estou usando as seguintes versões de software:

  • OpenGeo ilimitado v4.5.
  • Geoserver v 2.6.2.
  • Jetty v 7.6.13.v20130916.

Aqui estão as etapas detalhadas:

  1. Faça o download da versão correspondente dos servlets do Jetty, de acordo com a sua versão do jetty, nesta página Servlets do Jetty .
  2. Neste exemplo, estou usando o jetty v7.6.13.v20130916, para que o arquivo jar seja nomeado
    ( jetty-servlets-7.6.13.v20130916.jar ), o nome do arquivo será diferente de acordo com a versão do jetty - não mude seu nome porque jetty corresponde ao nome do servlet com sua versão como:
    jetty-servlets - <% JETTY_VERSION%>. jar, portanto, não o renomeie.
  3. Interrompa os serviços (GeoServer, Postgres) e tire uma cópia do diretório OpenGeo localizado em
    ( C: \ Arquivos de Programas (x86) \ boundless \ OpenGeo ) e copie também o diretório OpenGeo localizado em
    ( C: \ ProgramData \ boundless \ OpenGeo ) antes de iniciar este tutorial, como uma etapa de precaução.

  4. Copie o arquivo ( jetty-servlets-7.6.13.v20130916.jar ) (como está) no diretório Lib do jetty
    ( * C: \ Arquivos de Programas (x86) \ boundless \ OpenGeo \ jetty \ lib * ), também o diretório pode mude de acordo com o diretório de instalação.

  5. Copie e cole as seguintes linhas xml no ( webdefault.xml ) localizado em
    ( C: \ Arquivos de Programas (x86) \ boundless \ OpenGeo \ jetty \ ect \ webdefault.xml ), não tenho certeza de que o local dessas linhas colocar no arquivo é importante ou não, mas colo-os a partir da linha # 306 depois </serlet-mapping>.
<filter>
    <filter-name>cross-origin</filter-name>
    <filter-class>org.eclipse.jetty.servlets.CrossOriginFilter</filter-class>
</filter>
<filter-mapping>
    <filter-name>cross-origin</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>
  1. Inicie os serviços ( GeoServer , Postgres ), aguarde alguns segundos e navegue até a página do servidor geográfico, o servidor geográfico será iniciado corretamente.

Este tutorial funcionou para mim e espero que funcione para qualquer pessoa que esteja enfrentando o mesmo problema.

Ahmed GIS
fonte
Esta é a terceira pergunta na qual você postou a mesma resposta. Você seria capaz de revisar cada uma das suas três respostas para decidir se elas realmente estão respondendo à pergunta que está sendo feita ou são apenas conselhos genéricos, por favor?
PolyGeo
Eu estou simplesmente não sabia que como árbitro a minha outra resposta, então eu copiei-o aqui novamente
Ahmed GIS
No começo, eu estava procurando uma solução para o problema de origem cruzada com o Geoserver e o Openlayers, depois de descobrir uma solução, queria compartilhá-la com outras pessoas que enfrentam o mesmo problema, então procurei aqui por essas palavras-chave (CORS , Openlayers, Geoserver) e eu respondi as mesmas perguntas para o meu problema, mas não sabia como referenciar minha outra resposta, então copiei aqui novamente. Não pretendo repetir minha resposta, queria ajudar outros como este site incrível que me ajudaram em outros problemas.
Ahmed GIS
Não tenho acesso ao servidor geográfico da camada de origem e não sei o que o proprietário do servidor fez.
Magno C
@ MagnoC Você precisa verificar primeiro com o proprietário do servidor, talvez ele tenha alterado o nome das camadas ou outra coisa.
Ahmed GIS
1

A configuração crossOrigin existe apenas (?) Para ol.source.TileImage. ( http://openlayers.org/en/master/apidoc/ol.source.TileImage.html - desmarque a opção "Somente estável" no canto superior direito). ol.source.GeoJSON não tem uma configuração crossOrigin, porque você não pode acessar o JSON por meio de solicitações entre sites.

Você tem maneiras diferentes de contornar isso:

  1. use um proxy da web para chamadas ajax se você não tiver acesso ao servidor, de onde o json vem. (Procure por exemplo o proxy ajax)
  2. você pode usar o jsonp se tiver acesso ao servidor. Normalmente, essa é a solução preferida, mas não sei se ela funciona com o geojson e talvez você precise sobrescrever a função loader ( http://en.wikipedia.org/wiki/JSONP - Como obter o JSON do Geoserver usando Solicitação AJAX - http://openlayers.org/en/master/examples/vector-osm.js <- um exemplo para usar uma função do carregador personalizado)
  3. ative solicitações de origem cruzada no servidor. ( http://en.wikipedia.org/wiki/Cross-origin_resource_sharing )
  4. se os dados forem estáticos, faça o download e coloque-os no seu próprio servidor (apenas mencionando a integridade)

problema semelhante, mas não relacionado à região: /programming/5549068/json-how-do-i-make-cross-domain-json-call

Simon Zyx
fonte
Simon, consulte a Atualização # 1 acima por sua sugestão. Obrigado.
user3657279
0

Verifique os cabeçalhos de resposta do Geoserver na guia Rede do Firebug / Chrome Dev Tools para ver se o cabeçalho Acces-Control-Allow-Origin: * está realmente lá. Caso contrário, o problema está no lado do contêiner do servlet. Ou talvez, se o aplicativo for interno, configure um proxy no servidor da web principal em vez de ativar o CORS? Este último fará mais sentido se o seu Geoserver estiver disponível publicamente.

Michal Mackiewicz
fonte
Eu verifiquei os cabeçalhos de resposta, indo para o Firebug -> guia "Net" e cliquei na guia "Headers". Ele mostra 3 subseções: Cabeçalhos de resposta, Cabeçalhos de solicitação e Cabeçalhos de resposta do cache. Não há menção a "Access-Control-Allow-Origin".
user3657279
O cabeçalho Access-Control-Allow-Origin deve residir na subseção Response Headers. Caso contrário, tente reconfigurar o contêiner do servlet.
Michal Mackiewicz 22/09