Pochodzenie null jest niedozwolone przez Access-Control-Allow-Origin


184

Zrobiłem mały plik xslt, aby utworzyć wyjście html o nazwie weather.xsl z kodem w następujący sposób:

<!-- DWXMLSource="http://weather.yahooapis.com/forecastrss?w=38325&u=c" -->
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
exclude-result-prefixes="yweather"
xmlns:yweather="http://xml.weather.yahoo.com/ns/rss/1.0" xmlns:geo="http://www.w3.org/2003/01/geo/wgs84_pos#">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:strip-space elements="*"/>

<xsl:template match="/">
    <img src="{/*/*/item/yweather:condition/@text}.jpg"/>
</xsl:template>
</xsl:stylesheet>

Chcę załadować dane wyjściowe HTML do pliku div w pliku HTML, który próbuję wykonać przy użyciu jQuery w następujący sposób:

<div id="result">
<script type="text/javascript">
$('#result').load('weather.xsl');
</script>
</div>

Ale pojawia się następujący błąd: Początek null nie jest dozwolony przez Access-Control-Allow-Origin.

Czytałem o dodawaniu nagłówka do xslt, ale nie jestem pewien, jak to zrobić, więc każda pomoc byłaby mile widziana, a jeśli załadowanie pliku HTML nie może być wykonane w ten sposób, to porady dotyczące tego, jak inaczej robić to byłoby świetnie.


Jest to, że rzeczywiste load wezwanie? W ogóle nie ma na to ścieżki?
— TJ Crowder,

Odpowiedzi:


227

Pochodzenie nullto lokalny system plików, co sugeruje, że ładujesz stronę HTML wykonującą loadwywołanie za pomocą file:///adresu URL (np. Wystarczy dwukrotnie kliknąć ją w lokalnej przeglądarce plików lub podobnej). Różne przeglądarki stosują różne podejścia do stosowania zasad tego samego pochodzenia do plików lokalnych.

Domyślam się, że widzisz to w Chrome. Zasady Chrome dotyczące stosowania SOP do plików lokalnych są bardzo ścisłe, nie pozwala nawet na ładowanie plików z tego samego katalogu co dokument. Podobnie Opera. Niektóre inne przeglądarki, takie jak Firefox, umożliwiają ograniczony dostęp do plików lokalnych. Ale w zasadzie używanie ajax z lokalnymi zasobami nie będzie działać w różnych przeglądarkach.

Jeśli testujesz tylko lokalnie coś, co naprawdę wdrożysz w Internecie, zamiast używać plików lokalnych, zainstaluj prosty serwer internetowy i przetestuj za pomocą http://adresów URL. To daje znacznie dokładniejszy obraz bezpieczeństwa.


1
Po przesłaniu nie otrzymuję już Origin zera, ale wciąż dostaję „niedozwolone przez Access-Control-Allow-Origin”.
— dudledok,

3
Jeśli ładowany zasób jest zgodny z tym, co pokazano ( $('#result').load('weather.xsl');), nie powinno się to zdarzyć, ponieważ żądanie jest wyraźnie tego samego źródła. Jeśli próbujesz załadować się z innego miejsca (np. $('#result').load('http://somewhere.else/weather.xsl');), To ponownie uruchamiasz SOP, ale w inny sposób. Żądania Ajax są ograniczone do tego samego źródła (patrz link w odpowiedzi) lub jeśli używasz przeglądarki obsługującej CORS, a serwer obsługuje COR, serwer może zdecydować, czy zezwolić na żądanie krzyżowego pochodzenia.
— TJ Crowder,

Zmieniłem adres ładowania. Zmiana go z powrotem na pytanie powoduje, że ładuje się dobrze. Dzięki za pomoc
— dudledok,

2
Jaki jest najprostszy i najszybszy sposób na skonfigurowanie prostego serwera WWW? Czy usługi IIS byłyby tutaj najprostszym sposobem?
— Ciaran Gallagher

13
@CiaranG pobiegłem python -m SimpleHTTPServerz wiersza poleceń, a następnie poszedłem do localhost: 8000, pracowałem dla mnie. Python jest fabrycznie zainstalowany z systemem Mac OS X; może być konieczne zainstalowanie, jeśli używasz innego systemu operacyjnego.
— Dave Liepmann

216

Chrome i Safari mają ograniczenia w używaniu ajax z lokalnymi zasobami. Dlatego generuje błąd taki jak

Pochodzenie null jest niedozwolone przez Access-Control-Allow-Origin.

Rozwiązanie: użyj Firefoxa lub prześlij swoje dane na serwer tymczasowy. Jeśli nadal chcesz korzystać z Chrome, zacznij od poniższej opcji;

--allow-file-access-from-files

Więcej informacji, jak dodać powyższy parametr do Chrome: Kliknij prawym przyciskiem myszy ikonę Chrome na pasku zadań, kliknij prawym przyciskiem myszy Google Chrome w wyskakującym oknie i kliknij właściwości i dodaj powyższy parametr w polu tekstowym Cel na karcie Skrót. Będzie to jak poniżej;

C:\Users\XXX_USER\AppData\Local\Google\Chrome\Application\chrome.exe --allow-file-access-from-files

Mam nadzieję, że to pomoże!


19
W Mac OS X możesz uruchomić Chrome z tą opcją, otwierając terminal i wpisując: /Applications/Google\ Chrome.app/Contents/MacOS/Google\ Chrome --allow-file-access-from-files & Uwaga : wersja ostateczna & jest tylko po to, abyś mógł nadal korzystać z terminala i nie jest wymagany. UWAGA: zamknięcie terminalu spowoduje zamknięcie okna Chrome.
— Bruno Bernardino,

3
Zrobiłem to wszystko, zamknąłem i otworzyłem. wciąż nie ma (Chrome 27.0.1453.116 m na XP)
— mplungjan

Nie mogę dodać tego parametru w systemie Windows 8 ... czy ktoś wie, jak to zrobić? ...
— Morty

I 'm uruchomiony z serwera WWW. Co za cholera? Jak mogę dowiedzieć się, gdzie ładuje się lokalne pliki?
— Andy,

Kiedy próbuję dodać --allow-file-access-from-files do ścieżki docelowej, pojawia się komunikat „.... niepoprawny”, czy rozwiązanie jest nadal ważne?
— alex

48

Chciałem tylko dodać, że odpowiedź „uruchom serwer WWW” wydaje się dość zniechęcająca, ale jeśli masz python w swoim systemie (domyślnie zainstalowany przynajmniej na MacOS i dowolnej dystrybucji Linuksa), jest to tak proste jak:

python -m http.server  # with python3

lub

python -m SimpleHTTPServer  # with python2

Więc jeśli masz plik HTML myfile.htmlw folderze, powiedzmy mydir, wszystko co musisz zrobić to:

cd /path/to/mydir
python -m http.server  # or the python2 alternative above

Następnie skieruj przeglądarkę na:

http://localhost:8000/myfile.html

I gotowe! Działa we wszystkich przeglądarkach , nie wyłączając zabezpieczeń internetowych, zezwalając na lokalne pliki, a nawet ponownie uruchamiając przeglądarkę z opcjami wiersza poleceń.


2
odpowiednikiem Pythona 3 w systemie Windows jest: python -m http.server [<portNo>]
— Aragorn

Python 3: python3 -m http.server
— João Nunes

Python 2 w systemie Linux, wybierając port 8080 (lub dowolny inny):python -m SimpleHTTPServer 8080
— Rodrigo

2

Chciałbym pokornie dodać, że zgodnie z tym źródłem SO: https://stackoverflow.com/a/14671362/1743693 , tego rodzaju problemy można teraz częściowo rozwiązać, po prostu stosując następującą instrukcję jQuery:

<script> 
    $.support.cors = true;
</script>

Wypróbowałem to na IE10.0.9200 i zadziałało natychmiast (przy użyciu jquery-1.9.0.js).

Na chrome 28.0.1500.95 - ta instrukcja nie działa (dzieje się tak jak w przypadku Davida narzeka w komentarzach pod linkiem powyżej)

Uruchamianie chrome z opcją --allow-file-access-from-files nie działało dla mnie (jak twierdzą Maistora powyżej)


2

Dodając trochę, aby użyć rozwiązania Gokhan do używania:

--allow-file-access-from-files

Teraz wystarczy dołączyć tekst powyżej tekstu docelowego, a następnie spację. pamiętaj, aby zamknąć wszystkie instancje przeglądarki Chrome po dodaniu powyższej właściwości. Teraz uruchom ponownie Chrome przy ikonie, w której dodałeś tę właściwość. To powinno działać dla wszystkich.


Ten parametr został już przedstawiony przez Ghokan Tank, a ustalenie, jak zawsze przeglądarka zaczyna się od tego parametru, nie jest częścią pytania. Ponadto nie można zakładać, że wszyscy korzystają z systemu Microsoft Windows.
— jnns

0

Szukałem rozwiązania umożliwiającego wysłanie żądania XHR do serwera z lokalnego pliku HTML i znalazłem rozwiązanie za pomocą Chrome i PHP. (bez Jquery)

JavaScript:

var x = new XMLHttpRequest(); 
if(x) x.onreadystatechange=function(){ 
    if (x.readyState === 4 && x.status===200){
        console.log(x.responseText); //Success
    }else{ 
        console.log(x); //Failed
    }
};
x.open(GET, 'http://example.com/', true);
x.withCredentials = true;
x.send();

Nagłówek żądania mojego Chrome Origin: null

Mój nagłówek odpowiedzi PHP (zauważ, że „null” to ciąg znaków ). HTTP_REFERER pozwala na cross-origin ze zdalnego serwera na inny.

header('Access-Control-Allow-Origin: '.(trim($_SERVER['HTTP_REFERER'],'/')?:'null'),true);
header('Access-Control-Allow-Credentials:true',true);

Udało mi się połączyć z moim serwerem. Możesz zignorować nagłówki Poświadczeń, ale działa to dla mnie z ApacheAuthType Basic włączonym

Testowałem zgodność z FF i Operą, Działa w wielu przypadkach, takich jak:

Od adresu IP VM LAN (192.168.0.x) z powrotem do adresu WAN VM (publicznego): port
Od adresu IP VM LAN z powrotem do nazwy domeny zdalnego serwera.
Z lokalnego pliku .HTML na IP VM LAN i / lub VM WAN IP: port,
Z lokalnego pliku .HTML na nazwę domeny zdalnego serwera.
I tak dalej.


0

Można załadować lokalny plik JavaScript (w drzewie poniżej swojej file:/stronie źródłowej) za pomocą znacznika źródło:

<script src="my_data.js"></script>

Jeśli kodujesz swoje dane wejściowe w JavaScript, tak jak w tym przypadku:

mydata.js :

$xsl_text = "<xsl:stylesheet version="1.0" + ....

(jest to łatwiejsze dla JSON), wtedy masz swoje „dane” w globalnej zmiennej Javascript do wykorzystania, jak chcesz.

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.