why does three.js loader requires webserver only for certain browsers? - three.js

After playing around a bit with three.js and the gltf loader I have noticed that Mozilla and Edge don't require the gltf file to be located in a web server, but ie11 does. Could anyone explain me why is this?
Thanks

This happens because of security restrictions in browsers. For example if you try load a glTF asset directly from file via the file protocol (file:///), Chrome logs the following error:
Access to XMLHttpRequest at 'file:///...DamagedHelmet.gltf' from origin 'null' has been blocked by CORS policy: Cross origin requests are only supported for protocol schemes: http, data, chrome, chrome-extension, https.
The behavior of browsers varies since they do not implement equal security policies.
In order to avoid security related problems, three.js recommends to use a local web server when developing/testing WebGL applications that load assets from external files.

Related

Cache assets from a CMS for offline PWA?

I'm writing a web media viewer for images/videos and I need to cache that media for offline use.
I have a manifest and service worker so it can be installed as a PWA, and I'm trying to cache media from a list of URLs with esentially:
let cache = await window.caches.open('pwa-assets');
for(let url of allAssetURLs) {
await cache.add(url);
}
This seems to work fine for local assets, but if those URLs are on a different domain (from a CMS/CDN) I get this CORS error.
Access to fetch at 'https://storage.googleapis.com/....appspot.com/...example.mp4' from origin 'https://127.0.0.1:4173' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.
Web.dev has a note that cross-domain caching is possible here, but doesn't say much about it.
The URLs I'm trying to cache are for files store in google cloud storage, for example:
https://storage.googleapis.com/....appspot.com/...example.mp4
These do work if used in <img/> or <video/> tags, so I don't think it's a CORS header issue on the CDN.
You write:
These do work if used in <img/> or <video/> tags, so I don't think it's a CORS header issue on the CDN.
Loading such subresources across origins is by default compatible with the Same-Origin Policy (SOP) and doesn't trigger CORS errors. See the relevant section of the MDN Web Docs about the SOP:
Here are some examples of resources which may be embedded cross-origin: [...]
Images displayed by <img>.
Media played by <video> and <audio>.
You write:
This seems to work fine for local assets, but if those URLs are on a different domain (from a CMS/CDN) I get this CORS error.
Invoking the add method on a Cache results in a GET request. If its argument is on a different origin, the resource in question needs to be configured for CORS or you'll get a CORS error, as you've experienced. See the note in the relevant MDN Web Docs:
Note that for opaque filtered responses [...]
we can't access to [sic] the response headers, so this check
will always fail and the font won't be cached. [...]
It is something to keep in mind if you're attempting to
cache other resources from a cross-origin domain that
doesn't support CORS, though!
You write:
The URLs I'm trying to cache are for files store in google cloud storage, for example https://storage.googleapis.com/....appspot.com/...example.mp4.
This page of the Google Storage documentation explains how to configure CORS for your bucket(s), assuming those buckets are indeed yours. Otherwise, you're out of luck and won't be able to cache those resources on the client side.

privateNetworkClientServer error when using geoserver with cesium

I have a geoserver hosting imagery over http. my client site uses https. I've been using openlayers and it all works perfectly. now i'm trying to move to cesiumjs and i'm not getting any imagery in IE or Edge (i am unable to test other browsers unfortunately). i can get imagery in my client if using bing maps, so the client code is functional otherwise. from the browser console i see:
SEC7117: Network request to http://[myserver]:8080/geoserver/cite/wms?service=WMS&version=1.1.1&request=GetMap&styles=&format=image%2Fjpeg&layers=cite%3Abmpyramid&srs=EPSG%3A3857&bbox=195678.7924100496%2C156543.03392804041%2C234814.55089206248%2C195678.7924100496&width=256&height=256 did not succeed. This Internet Explorer instance does not have the following capabilities: privateNetworkClientServer
and:
SEC7111: HTTPS security is compromised by http://[myserver]:8080/geoserver/cite/wms?service=WMS&version=1.1.1&request=GetMap&styles=&format=image%2Fjpeg&layers=cite%3Abmpyramid&srs=EPSG%3A3857&bbox=195678.7924100496%2C195678.7924100496%2C215246.6716510579%2C215246.6716510579&width=256&height=256
the URLs are good; i can copy/paste into a new browser and get tiles back. from the browser network tab of the dev tools i can see there are no outgoing image requests.
does anybody know of a way to get around this?
Despite the cryptic error messages, it seems this is not an HTTP/HTTPS issue like I thought; it's a Cross Origin Resource Sharing (CORS) problem specific to WebGL/CesiumJS. It is summarized near the bottom of this page: https://cesiumjs.org/tutorials/Imagery-Layers-Tutorial/ .
Basically there are two options. First, you can enable CORS in your geoserver. I confirmed this did indeed resolve the issue in my dev environment. However, this is not really an option for us in prod.
The other option is to set up a proxy where instead of cesium directly requesting tiles, it requests them from your own web server and your web server fetches them manually. when going this route, you modify your cesium like so:
layers.addImageryProvider(new Cesium.ArcGisMapServerImageryProvider({
url : '//server.arcgisonline.com/ArcGIS/rest/services/World_Street_Map/MapServer',
proxy : new Cesium.DefaultProxy('/proxy/')
}));

How to solve cross-domain error in Oracle Mapviewer hosted on Glassfish

I have made an HTML5 application (hosted on localhost) that interacts with a remote MapViewer server (hosted on a remote server using Glassfish 4) using it's JavaScript library.
<script src='http://192.168.1.99:8088/mapviewer/jslib/v2/oraclemapsv2.js'></script>
The JavaScript library is making calls to it's own domain http://192.168.1.99:8088to load CSS files, images and access web services, but returning cross domain error since I am actually hosting my HTML5 app on my localhost.
XMLHttpRequest cannot load http://192.168.1.99:8088/mapviewer/omserver?xml_request=%3Cnon_map_reques…rce%3D%22tcg_seff%22+style%3D%22T.ZIPCODE%22%2F%3E%3C%2Fnon_map_request%3E. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost' is therefore not allowed access.
Any idea how to solve this?
What you need to do is enable Cross Origin Resource Sharing on the MapViewer server.
You can find more information about this here: http://www.html5rocks.com/en/tutorials/cors/

About using http in Heroku server?

I am a newbie to Heroku server. I found the default connection method is https.
If I switched to http, I will received the following errors when accessing
No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin *** is therefore not allowed access.
Any idea to enable http access?
The problem here appears to the same-origin policy. Seems that some of your requests are mixed between plain http and https which all modern browsers interpret as having different origins.
Without seeing additional debug information, I'm going to guess the main page is still loaded via https, but the page assets (images, javascript, css etc.) are now loaded via http.
Assuming this is correct, the first step is to ensure the main html page is loaded using the same origin (same domain, same scheme (http or https) etc.).

Allow cors in Flask api for d3.xhr

I'm writing a simple Flask api that will serve data to a d3.js frontend and I am getting this error when I try to query for the data:
XMLHttpRequest cannot load localhost:5000/data/sample_data. Cross origin requests are only supported for protocol schemes: http, data, chrome-extension, https, chrome-extension-resource.
I am using the flask-cors extension for flask, even though I am querying from my own domain (localhost) so I thought that this shouldn't even count as "Cross-domain". Can anyone shed some light on why this isn't working?
URLs should have a valid schema for CORS to kick in. While Chrome's address bar can prefix the schema for URLs, most AJAX libraries (jQuery, d3, etc.) do not smartly do it before making the request.
Appending http:// to the URL(s) should fix the problem.

Resources