Vue.jsにあまり詳しくないので勉強しながらwebサイトを作っております。
vue-metaやvue-routerを使用する方法も模索したのですが、今回のサイトではバックエンドをAPIで別途構築してあり、フロントをVue.jsという構成としております。
その為、動的にAPIで取得したデータをmeta情報に設定したく思いました。詳細ページに表示するデータ毎にmeta情報も変えたい次第です。
APIはaxiosを使用しています。
とりあえずコード
.vueファイルのscript部分です。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 |
<script> import axios from 'axios'; export default { name: 'MediaShow', props: { id: Number }, data () { return { medium: '', meta: { title: '', description: '', keywords: '', } } }, created () { this.requestMediaShow() }, watch: { meta: { handler: function () { // console.log('watch meta') this.updateMeta() }, deep: true // metaの子階層もwatchする為 } }, methods: { requestMediaShow () { axios.get('/api/v1/media/'+this.id, { xsrfHeaderName: 'X-CSRF-Token', withCredentials: true }) .then(response => { // console.log(response.data) this.medium = response.data this.meta.title = this.medium.name + "の一覧" this.meta.description = this.medium.name + "の一覧です。" this.meta.keywords = this.medium.name + ", の一覧, あああ" }).catch(err => { console.log('err:', err) }); }, updateMeta () { document.title = this.meta.title document.querySelector("meta[name='description']").setAttribute('content', this.meta.description) document.querySelector("meta[name='keywords']").setAttribute('content', this.meta.keywords) } }, } </script> |
解説
createdされたタイミングでAPIに非同期でデータを取得します。取得したデータをdataに設定します。
別途dataをwatchしているので、非同期で更新されたdataを元にmeta情報をupdateしています。
最初はwatchではなく、computeを使用しようとしたのですが、非同期でAPIからデータを取得する為、watchでないと出来ませんでした。
あと、上記スクリプトは現在のmeta情報を変更する作りになっている為、index.htmlにてダミーでも枠(description, keywords)を準備しておく必要があります。
index.html
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
<!DOCTYPE html> <html lang=""> <head> <title></title> <meta name="description" content=""> <meta name="keywords" content=""> <meta charset="utf-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width,initial-scale=1.0"> <link rel="icon" href="<%= BASE_URL %>favicon.ico"> <title><%= htmlWebpackPlugin.options.title %></title> </head> <body> <noscript> <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong> </noscript> <div id="app"></div> <!-- built files will be auto injected --> </body> </html> |
以上です。
誤り等ありましたらご指摘ください。参考まで。