質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.35%
Vue.js

Vue.jsは、Webアプリケーションのインターフェースを構築するためのオープンソースJavaScriptフレームワークです。

Node.js

Node.jsとはGoogleのV8 JavaScriptエンジンを使用しているサーバーサイドのイベント駆動型プログラムです。

JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

Q&A

解決済

1回答

1730閲覧

axios(async/await)を使用した処理について

hiroki88

総合スコア66

Vue.js

Vue.jsは、Webアプリケーションのインターフェースを構築するためのオープンソースJavaScriptフレームワークです。

Node.js

Node.jsとはGoogleのV8 JavaScriptエンジンを使用しているサーバーサイドのイベント駆動型プログラムです。

JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

0グッド

0クリップ

投稿2021/03/31 09:32

編集2021/03/31 11:00

【バージョン】
laravel:6.18.40
PHP:7.2.31
nginx:1.19.0"

【やっていること】
現在フロント側でvue.js、バックエンドでLaravelを使用しECサイトのアプリケーションの開発をしております。
その中でフロント側からaxiosを使用しAPIを呼び必要なデータを取得する箇所があるのですが動作が
上手くいっておりません。

【処理について】
下記は行いたい処理の流れです。(場面としては管理画面のトップページにアクセスをします)
1.ローディングを表示させる
2.登録商品の情報を取得する
2-1.登録商品取得APIの呼び出し
2-2.APIの返り値が200かチェック
2-3.取得した情報をdata()メソッドで定義してあるオブジェクトの値に代入する
3.購入商品の情報を取得する
3-1.購入商品取得APIの呼び出し
3-2.APIの返り値が200かチェック
3-3.取得した情報をdata()メソッドで定義してあるオブジェクトの値に代入する
4.ローディングを非表示させる

javascript

1<script> 2export default{ 3 data(){ 4 return { 5 registerproduct: [],//登録商品の情報 6 buyproduct: [],//購入商品の情報 7 loading: false,//値がtrueならローディングを表示、falseなら非表示 8 } 9 }, 10 methods: { 11//トップページにアクセスされると呼び出される 12 async fetchProduct(){ 13 this.loading = true;//ローディング表示 14 await this.execRegister();//登録商品取得処理呼び出し 15 await this.execBuy();//購入商品取得処理呼び出し 16 this.loading = false;//ローディング非表示 17 }, 18 19//登録商品取得処理 20 async execRegister(){ 21 const response = await axios.get(`/api/getRegisterProducts`);//登録商品取得API呼び出し 22 23 if(response.status !== 200){//HTTPステータスのチェック 24 this.$store.commit('error/setCode', response.status); 25 return false; 26 } 27 28 this.registerproduct = response.data;//registerproductプロパティに代入 29 }, 30 31//購入商品取得処理 32 async execBuy(){ 33 const response = await axios.get(`/api/getBuyProducts`);//購入商品取得API呼び出し 34 35 if(response.status !== 200){//HTTPステータスのチェック 36 this.$store.commit('error/setCode', response.status); 37 return false; 38 } 39 40 this.buyproduct = response.data;//buyproductプロパティに代入 41 } 42 }, 43 44//監視プロパティ(アクセスがあった場合fetchProductメソッドを呼び出す) 45 watch: { 46 $route: { 47 async handler(){ 48 await this.fetchProduct(); 49 }, 50 immediate: true 51 } 52 } 53} 54</script>

【できないこと】
上手くいかないことが2番(登録商品の情報を取得する)と3番(購入商品の情報を取得する)の並行処理(非同期処理)です。

javascript

1async fetchProduct(){ 2 this.loading = true;//1.ローディング表示 3 await this.execRegister();//2.登録商品取得処理呼び出し 4 await this.execBuy();//3.購入商品取得処理呼び出し 5 this.loading = false;//4.ローディング非表示 6}

2番と3番でawaitを指定しているので同期処理になり非同期処理にならないのは分かるのですがawaitを指定していないと2番と3番の処理が終わる前に4番の処理が行われてしまいます。

自分が行いたい流れとしては
1.ローディング表示
↓(2,3番の処理を同時に開始)
2.登録商品取得処理呼び出し 3.購入商品取得処理呼び出し
↓(2,3番の処理が完了)
4.ローディング非表示
としたいです。

【試したこと】
いくつか実現するために試した内容を記載します。

1つ目:2番と3番の処理を1つにまとめる
結果:2番と3番が同期処理されてしまう。

javascript

1async fetchProduct(){ 2 this.loading = true;//1.ローディング表示 3 const exec = async ()=>{ 4 await this.execRegister();//2.登録商品取得処理呼び出し 5 await this.execBuy();//3.購入商品取得処理呼び出し 6 } 7 await exec(); 8 this.loading = false;//4.ローディング非表示 9}

2つ目:2番と3番の処理のawaitを指定しない
結果:2番と3番の処理は並行(非同期)で行われるが終わる前に4番の処理が行われる。

javascript

1async fetchProduct(){ 2 this.loading = true;//1.ローディング表示 3 const exec = async ()=>{ 4 this.execRegister();//2.登録商品取得処理呼び出し 5 this.execBuy();//3.購入商品取得処理呼び出し 6 } 7 await exec(); 8 this.loading = false;//4.ローディング非表示 9}

3つ目:4番の処理にasyncを指定する
結果:2番と3番の処理が終わる前に4番の処理が行われる。

javascript

1async fetchProduct(){ 2 this.loading = true;//1.ローディング表示 3 const exec = async ()=>{ 4 await this.execRegister();//2.登録商品取得処理呼び出し 5 await this.execBuy();//3.購入商品取得処理呼び出し 6 } 7 const exec2 = async ()=>{ 8 this.loading = false;//4.ローディング非表示 9 } 10 await exec(); 11 await exec2(); 12}

いずれも実現できませんでした。どうしても2番と3番を並行処理させると4番が先に実行されてしまいます。
2番と3番を並行処させてどちらも完了したら4番が実行されるようにするやり方が分かる方がいたらご教示お願いします。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Lhankor_Mhy

2021/03/31 09:56

1つ目が「2番と3番の処理が終わる前に4番の処理が行われる」とのことですが、そうはならないような気がしています。
hiroki88

2021/03/31 10:59

ご指摘ありがとうございます。そうですね。
guest

回答1

0

ベストアンサー

Promise.all() でよさそうな気がします。
Promise.all() - JavaScript | MDN

投稿2021/03/31 09:58

Lhankor_Mhy

総合スコア36960

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

hiroki88

2021/03/31 11:25

ご回答ありがとうございます。 ご教示いただいたようにPromise.allで並行処理をしてその後ローディングを非表示にできました!! 大変助かりました!ありがとうございます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.35%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問