Help us understand the problem. What is going on with this article?

vue-metaを用いたOGPやJSON-LD用のメタタグ生成

vue-meta
https://github.com/nuxt/vue-meta

・Title and Description
・OGP
・JSON-LD
を生成するにはvue-metaが便利。
弊社ではNuxtを使わず、Vue.jsで作っています。
Vue-metaはNuxtプロジェクトの中で開発しているのでVue.jsでは使えないと思っていたのですが、Vue.jsでも使えました😍

この記事を書いたときのバージョン

"vue": "^2.6.10",
"vue-meta": "^2.3.1",

インストール

npm install vue-meta --save

コードの変更箇所

// src/main.ts
import VueMeta from 'vue-meta';
Vue.use(VueMeta);
// Page.vue
import {metatag} from @/metatag/metatag.ts'
export default Vue.extend({
    data() {
        return {
            this.initialized = false;
            this.param = {hoge: ‘bar'}
        }
    },
    mounted() {
        // ここでAPI通信などの非同期処理を行う。
        this.initialized = true;
    },
    metaInfo() {
      return this.initialized ? metatag(this.param) : null; // this.initializedが変更されると検知してくれる😂
    },
});
// src/metatag/metatag.ts
const TITLE = ’サイト名’;

export function metatag(params: any) {
  const description = `descriptionを書くよ ${JSON.stringify(params)}`;
  return {
    title: TITLE,
    meta: [
      {name: 'description', content: description},
      {property: 'twitter:card', content: 'summary'},
      {property: 'twitter:title', content: document.title},
      {property: 'twitter:site', content: '@anonymous'},
      {property: 'twitter:creator', content: '@anonymous'},
      {property: 'twitter:description', content: description},
      {
        property: 'twitter:image',
        content: 'https://FQDN/favicon256.jpg',
      },
      {property: 'og:title', content: document.title},
      {property: 'og:description', content: description},
      {property: 'og:type', content: 'website'},
      {property: 'og:url', content: location.href},
      {
        property: 'og:image',
        content: 'https://FQDN/favicon256.jpg',
      },
    ],
    script: [
      {
        type: 'application/ld+json',
        innerHTML: JSON.stringify(
          [{
            '@context': 'http://schema.org',
            '@type': 'Organization',
            'url': location.href,
            'logo': 'https://FQDN/favicon256.jpg',
          },
            {
              '@context': 'http://schema.org',
              '@type': 'WebSite',
              'name': document.title,
              'alternateName': description,
              'url': location.href,
            },
          ], null, 2,
        ),
      },
    ],
  };
}

vue-headという類似ライブラリを使っていたんですけど、
this.$emit(‘updateHead’);
というメソッドを非同期通信完了のタイミングで実行しなければならなかったのが辛かった・・・
また、JSON-LDの書き方がすごくスッキリしました。

これで最低限のOGPとGoogle対策ができました。
とはいえ、Twitter CardやGoogleに完全対応するには、DynamicRenderingやSSRが必要です。
Vue.jsで開発しているとSSR対応は難しいので、HeaderlessChrome(puppeteer)を使ったDynamicRenderingをやることにしました。
DynamicRenderingに関しては結構長い記事なので次回更新します。

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした