2017-08-23 8 views
1

私は、Axiusを使用してYahoo天気APIにajax GETリクエストを行うvuejsコンポーネントを開発中です。プリフライトチェックでアクセス制御チェックが合格しないというCORSエラーが表示されます。Axiosのyahoo天気APIへのリクエストの失敗

しかし、問題なしでjqueries ajaxメソッドを使用して同じエンドポイントにリクエストすることができ、期待されるデータがサービスから返されます。誰がなぜこのような場合があるのか​​知っていますか?ここで

は私のVUEのコンポーネントからのコードです:

<template> 
    <div class="tile" id="time-weather"> 
     <div class="date" v-text='this.date'></div> 
     <div class="time" v-text='this.time'></div> 
     <div class="temperature" v-text="this.temp"></div> 
    </div> 
</template> 

<script> 
    import moment from 'moment'; 

    export default { 
     created() { 
      this.refreshTime(); 
      setInterval(this.refreshTime, 1000); 

      this.fetchWeather(); 
     }, 
     data() { 
      return { 
       date: '', 
       time: '', 
       temp: '' 
      } 
     }, 
     methods: { 
      refreshTime() { 
       this.date = moment().format('ddd DD/MM'); 
       this.time = moment().format('HH:mm:ss'); 
      }, 
      fetchWeather() { 
       const endpoint = "https://query.yahooapis.com/v1/public/yql?q=select item.condition from weather.forecast where woeid in (select woeid from geo.places(1) where text='Sunderland') and u='c'&format=json"; 
       const yapi = axios.create({ 
        url: endpoint, 
        method: 'get', 
        withCredentials: false 
       }); 

       const response = yapi.request(); 
       console.log(response); 
      } 

     } 
    } 
</script> 

私はコンソールに取得しています正確なエラーメッセージは次のとおりです。

のXMLHttpRequestが https://query.yahooapis.com/v1/public/yql?q=select%20item.condition%20from%20weather.forecast%20where%20woeid%20in%20(select%20woeid%20from%20geo.places(1)%20where%20text=%27Sunderland%27)%20and%20u=%27c%27&format=jsonをロードすることはできません。 プリフライト要求への応答がアクセス制御チェックを通過しません。いいえ 要求された リソースに 'Access-Control-Allow-Origin'ヘッダーが存在します。したがって、オリジン 'http://dashboard.dev'は許可されません。

私が言及したように、同じエンドポイントに対してjQuery.ajax();を使用してリクエストを行うと、リクエストは問題なく送信されます。

私が紛失していると思われるものがありますが、この問題を解決できないようです。

ご協力いただきますようお願い申し上げます。

乾杯!

+0

を使用して、独自のCORSプロキシを設定することができ

はよろしいですか?与えられたエンドポイントは404を返します。単にそれをcURLでチェックします。 – lukaleli

+0

@jimmyweb httpsへのリンクを編集しました。それでも同じ結果が得られます。 – user2286026

+0

ちょうど今追加された答えを見てください。ブラウザのdevtoolsのネットワークペインに入り、ドキュメントを再読み込みして、そこにプリフライトOPTIONS要求を調べて、ブラウザが送信していることを確認できます。リクエストヘッダー、特に 'Access-Control-Request-Headers'リクエストヘッダーでブラウザの送信を確認する必要があります。これには、Axiosリクエストがリクエストに追加しようとしている(そしてプリフライトが失敗する)カスタムリクエストヘッダの名前が含まれます。おそらくhttps://stackoverflow.com/posts/45849535/editを使って質問を編集/更新し、それらのレスポンスヘッダに貼り付けてください。 – sideshowbarker

答えて

2

を、なぜブラウザの特定のために指示する方法はありませんCORS preflight OPTIONS request - ただし、決定できる1つの理由は、それが失敗する理由は、https://query.yahooapis.com/v1/public/yqlエンドポイントがAccess-Control-Allow-Originレスポンスヘッダーを0123に送信しないためですの回答。

あなたはこれを行うことにより、curlを使用していることを確認することができます:私はaxiosを使用してヤフーの天気APIへのAjaxのGET要求を行うvuejsコンポーネントに取り組んでいます

curl -X OPTIONS -i \ 
    -H 'http://dashboard.dev/' \ 
    'http://query.yahooapis.com/v1/public/yql?q=select%20item.condition%20from%20weather.forecast%20where%20woeid%20in%20(select%20woeid%20from%20geo.places(1)%20where%20text=%27Sunderland%27)%20and%20u=%27c%27&format=json' 

HTTP/1.1 200 OK 
Allow: GET, HEAD, POST, PUT, DELETE, TRACE, OPTIONS 
Content-Length: 0 
Date: Wed, 23 Aug 2017 22:12:40 GMT 
Age: 0 
Connection: keep-alive 
Via: http/1.1 a44.ue.sg3.yahoo.net (ApacheTrafficServer [c sSf ]) 
Server: ATS 

。プリフライトチェックでCORSエラーが発生しました...同じエンドポイントにjQuery.ajax()を使用してリクエストを行うと、リクエストは問題なく送信されます。 jQuery.ajax()は、プリフライトをトリガーするように要求を行うのではなく、axios要求があることを示し

。ほとんどの場合、リクエストは1つまたは複数のカスタムリクエストヘッダーを追加しています。おそらくX-Requested-Withヘッダー* - これはjQuery.ajax()ではありません。

* 更新:この場合、追加されたヘッダーはX-CSRF-TOKENです。

ことが起こっているのまさに特定のために言うと、そのOPTIONSリクエストでブラウザの送信-内の特定のAccess-Control-Request-HeadersリクエストヘッダOPTIONS要求を調べます。これには、Axiosリクエストがリクエストに追加しようとしているカスタムリクエストヘッダの名前が含まれます。

OPTIONSリクエストのヘッダーとその他の詳細は、ブラウザのdevtoolsの[ネットワーク]ペインに移動し、再ロードしてそこのOPTIONSリクエストを調べることで確認できます。


とにかく、そのエンドポイントに期待どおりに動作するように要求する方法があります。あなたはこれを持っているあなたのフロントエンドのコードを変更することで、CORSプロキシ経由でリクエストを作ることができます:それは、ブラウザのプリフライトOPTIONS要求し、あなたのGET要求-both https://cors-anywhere.herokuapp.comてリクエストをお送りします

const proxyurl = "https://cors-anywhere.herokuapp.com/"; 
const endpoint = "https://query.yahooapis.com/v1/public/yql?q=select item.condition from weather.forecast where woeid in (select woeid from geo.places(1) where text='Sunderland') and u='c'&format=json"; 
const yapi = axios.create({ 
    url: proxyurl + endpoint, 
    method: 'get', 
    withCredentials: false 
}); 

。そしてそこのバックエンドは、そのhttps://query.yahooapis.com/v1/public/yqlエンドポイントに要求を転送し、応答を受信します。

が、バックエンドは、その後も応答とOPTIONSの場合には、次にAccess-Control-Allow-HeadersAccess-Control-Allow-Methods応答ヘッダ、および自分の要求フロントエンドコードにそれをバック通過するAccess-Control-Allow-Originヘッダを付加します。

ブラウザでは、応答ヘッダーがAccess-Control-Allow-Originの応答がブラウザに表示されるため、フロントエンドコードが応答にアクセスできるようになります。あなたはまた、簡単にhttps://github.com/Rob--W/cors-anywhere/

+0

答えをありがとう。失敗したのは、Laravelのbootstrap.jsファイルで、axiosがX-CSRF-TOKENヘッダーを要求に追加したためです。一度削除すると、要求が送信され、データは期待どおりに返されました。助けてくれてありがとう! – user2286026

+0

OKです。リクエストにX-CSRF-TOKENヘッダーを追加すると、OPTIONSプリフライトを実行するブラウザが起動するためです。乾杯してうれしく思いました! – sideshowbarker

1

私は応答を得ていますが、httpではなくhttpsを使用する必要があります。これはAxiosとJQueryの両方に当てはまります。

が応答確認するには、以下のスニペットやこのCodePen Demoを実行します。問題のちょうど現在の詳細から

axios.get(
 
    "https://query.yahooapis.com/v1/public/yql?q=select item.condition from weather.forecast where woeid in (select woeid from geo.places(1) where text='Sunderland') and u='c'&format=json" 
 
) 
 
    .then(function(result) { 
 
    console.log(result); 
 
    });
<script src="https://cdnjs.cloudflare.com/ajax/libs/axios/0.12.0/axios.min.js"></script>

+0

応答Danに感謝します。コードスニペットを独自のコードで実行すると機能しますが、これも以前に試みました。私がLaravelアプリケーションの一部としてvuejsコンポーネントでそれを使用しようとするたびに、それはしません。なぜ完全にはわからない! – user2286026

+0

興味深い。 [このリンク](https://codepen.io/robinhuy/pen/VWLBYa/)は、vuejsのyahoo気象APIでaxiosを使用している人の興味深い例です。この人は、ajaxレスポンスのgetメソッドとthenメソッドも使用しています。うまくいけば、これは助けるかもしれません:) - –

+0

すでにDanでこれを渡って、まだ運が来なかった! – user2286026