読者です 読者をやめる 読者になる 読者になる

$yuzu->log();

技術ネタなど。

SEOの初心者にはおすすめな本「10年使えるSEOの基本」を読んだ感想

SEO 読んだ本

SEOの専門家におすすめされて、読んだ本。とても良かったので紹介します。

「10年使えるSEOの基本」の感想

SEOの専門家である土居くんと、SEOに詳しくないすずちゃんが対話形式で例を交えながらSEOの話をする本です。
特にSEOのテクニック的なところは出てこず、「検索エンジンとは何か」、「Googleが目指す世界」から、SEOを紐解く至極真っ当な本です。
陳腐化する小手先なテクニックよりは、本質的なところにフォーカスをあてているため、「10年つかえる」の看板に偽りはないと思いました。
フルカラーで優しい言葉でかけあいしてるので、初心者にはすごく読みやすい本なんじゃないかと思います。 以下メモ。

検索にヒットするようになるには?

  • どういう言葉で検索されているのかを知る
  • 検索エンジンが正しく理解できるようにサイトを作る
  • みんなが検索を通じて知りたいことをコンテンツ化してサイトに掲載しておく
  • 継続的にサイトにリンクを集めていく

検索キーワードの見つけ方

  • どんなキーワードで検索しているのか?
  • キーワードボリュームは感覚ではなく必ず調べるようにする

検索キーワードをサイトに反映させる

  • titleタグにキーワードを含める
  • meta descriptionにキーワードを含める
  • 最初の見出しにはキーワードを含める
  • ページ内のテキスト要素にキーワードを含め、なるべくページ上部に出現させる
  • 「見てほしい人が使いそうな言葉」をなるべく選んで使う
  • 自然な文章で表記し、不自然な繰り返しを用いない

良いタイトル付け

  • 大事なキーワードを含めて、なんのページなのかが具体的にわかるように
  • 異なる内容のページに、同じタイトルを複数つけない ← プログラムで書いた場合はやりがち
  • 文字数は30文字以内
  • 重要なキーワードはなるべく前半に

meta descriptionの重要さ

  • 検索エンジンのランキングには関係ない
  • クリック率には関わってくる
  • 大事なキーワードを含めて、なんのページなのか具体的にわかるように
  • 異なる内容のページに、同じdescriptionを書かない
  • 50〜100文字以内

SEOとは

  • 検索エンジンで上位表示」ではなく「検索を通じて知りたい情報を見つけられるようにする」技術
  • 「自分が言いたいこと」ではなく「みんなが知りたいこと」を書く
  • コンテンツは量よりも品質を重視。

コンテンツ・マーケティングの正のスパイラル

  1. 良いコンテンツを作る
  2. 多くの人に見てもらえ、一定のリンクを獲得
  3. リンクを通じて更に見てもらえる機会が増える
  4. SEOも強くなって検索での露出が増える
  5. さらにリンクが増える
  6. 2に戻る

10年つかえるSEOの基本

10年つかえるSEOの基本

ポケモンGo!のアンテナサイトを作った。技術仕様やアプリケーション仕様などなど

Vagrant PHP Nginx Composer CentOS CakePHP 作ったもの

酔った勢いで、ポケモンGo!のアンテナサイトを作ってみました。

pokemongo-mtm.xyz

こういうのって、スピードが大事ですよね。検索ボリュームが多い時にリリースできたのでよかったです。 1時間ぐらいでさくっと。

使用した技術

サーバーはGMOクラウドのVPSのメモリ2GB、月額1,280円のプラン。

composer.json

 "require": {
        "cakephp/cakephp": "2.*",
        "cakephp/debug_kit": "*",
        "intervention/image": "dev-master",
        "intervention/imagecache" : "*",
        "cakedc/migrations": "*",
        "nanapi/cakephp-redis": "*"
    },

アプリケーションの仕様

  • hourlyで指定したRSSをクロール。
  • サムネイルの取得は対象サイトのog:image、なかったら、RSSのdescriptionに含まれている、imgタグから取得。
  • PVのカウントはRedisで貯めてって、デイリーバッチで、MariaDBに貯めこむ。

悲しかった事。

CakeDCのマイグレーションプラグインを使ったのですが、マイグレーションプラグインがStringクラスを使っていて、PHP7から「型と同じクラス名」を作れないという制約があるため、exception error が発生するという悲しみ。
なので手動でDB作りました。

今後やりたいこと

広告周りは適当にimobileのクリック広告しか貼ってないですが、ユーザの志向にあったものを採用していきたいです。

ポケモンGo!をやってみて。

電池の減り早い! モバイルバッテリー必須ですね。
軽くて大容量なおすすめモバイルバッテリー↓

エンジニア × 海外就職 × 英語で参考になりそうな記事まとめ

海外就職 英語

最近エンジニアの海外就職報告記を見かけるようになってきました。 エンジニアとしての技術力や英語力はどのぐらい必要だったのか、ビザはどうしたのか。 参考になりそうなものをまとめてみました。


kenzan100.hatenadiary.jp

ベルリンでウェブエンジニアとして働く事になった方の記事。 ワーホリビザから就労ビザに移行するやり方があるのですね。


nzmoyasystem.hatenablog.com

ニュージーランドプログラマとして働いている方のブログ。 英語力について、職場の文化について記載があります。


blog.kyanny.me

グローバル企業であるQuipperで働く上でどのぐらい英語力が求められるか詳細に書かれている記事。


hotchemi.hateblo.jp

ソフトウェアエンジニアとして英語を学ぶ上で良かったことまとめ。 「海外の会社の転職面接を受けるのは英語の勉強に良い」は、成る程と思いました。


shiumachi.hatenablog.com

英語が話せるようになれば、グローバルの人材市場で自分の価値を判断されるようになるので英語頑張ろうというお話。


d.hatena.ne.jp

Github経由でイスラエルから仕事をいただいたという話。 こういう働き方はどんどん増えていくだろうなぁ。


tango-ruby.hatenablog.com

シンガポールのスタートアップで、絶望的に英語力が無いけど技術力がある人が入社した話。 なんとか働けているようです。


chezou.hatenablog.com

「USに行きたいのなら日本法人に入るのが定石」


anond.hatelabo.jp

10年間海外で技術者として仕事をしている人からの、海外の会社で適応するためのアドバイス。


lifeiscolourful.hatenablog.com

海外移住先としてのニュージーランドのすすめ。
ニュージーランドってITのイメージなかったんですが、高給取りなのですね。


rebuild.fm

@miyagawaさんがMCをしているテック系ポッドキャスト。 IT技術やガジェットなどの話が中心ですが、@miyagawaさんがアメリカで働いていることもあり、英語やビザの細かい話などを聞ける回もある。 私は通勤時に1.5倍速で聞いてます。


タイトルが世界の最前線とかいてあるけど、中身はシリコンバレーの話です。 日本とアメリカとの仕事環境の違いや転職やレイオフの受け止め方。どのぐらい英語ができれば良いのか。ビザの話。面接突破方法など、シリコンバレーでエンジニアとして働くことを目指すなら絶対読んでおいた方がいい1冊でした。

他にも参考になりそうな記事やメディアがありましたらおしえてください。

FXシステムトレードフレームワーク Jiji をCentOS7にセットアップ

Jiji CentOS FX Docker

FXシステムトレードフレームワークJiji」のセットアップメモです。

「Jiji」のドキュメントにはHeroku、AWS、Dockerの3つの方法が載っており、前者2つは詳細に説明が書かれていますが、3つ目の「Dockerにインストール」はパッケージインストールが省略されています。

この記事はCentOS7での1からのセットアップ記事です。誰かの参考になれば。

Docker、Git、docker-composeのインストール

# システムをアップデート
$ sudo yum update -y

# Gitのインストール
$ sudo yum install -y git

# Dockerの最新版をインストール
$ curl -sSL https://get.docker.com/ | sh
$ docker -v
Docker version 1.10.2, build c3959b1
$ sudo systemctl start docker
$ sudo systemctl enable docker
$ sudo usermod -a -G docker YOURUSERNAME

# docker-composeをインストール
$ curl -L https://github.com/docker/compose/releases/download/1.6.0/docker-compose-`uname -s`-`uname -m` > /tmp/docker-compose
$ sudo mv /tmp/docker-compose /usr/local/bin/
$ sudo chmod +x /usr/local/bin/docker-compose

docker-compose設定ファイルのひな形をチェックアウト

$ git clone https://github.com/unageanu/docker-jiji2

オレオレ証明書の作成

# スーパーユーザにスイッチ
$ sudo su
# jiji用のディレクトリ作成、移動
$ mkdir -p /etc/ssl/certs/jiji
$ cd /etc/ssl/certs/jiji
# 秘密鍵を生成
$ openssl genrsa 2048 > server.key
# CSRを作成
$ openssl req -new -key server.key > server.csr
# サーバー証明書を作成
$ openssl x509 -sha256 -days 365 -req -signkey server.key < server.csr > server.crt
# アクセス権を制限
$ sudo chown root.root server.key
$ sudo chmod 600 server.key
# スーパーユーザから抜ける
$ exit

docker-compose.yml の編集

vim ~/docker-jiji2
jiji:
  container_name: jiji_jiji
  image: unageanu/jiji:latest
  environment:
    # サーバー内部で秘匿データの暗号化に使うキー
    # 必ず変更して使用してください。
    USER_SECRET: 20e43fa41e75c9fe958f5f11bc9e79d2174b50b
  links:
    - mongodb

mongodb:
  container_name: jiji_mongodb
  image: mongo:3.0.7
  ports:
    # MongoDBのポート番号
    # 必要に応じて変更してください。
    - "27018:27017"
  volumes:
    # MongoDBのデータを保存するディレクトリ
    # デフォルトでは、コンテナ内に作成します。(この場合、コンテナを再作成すると、データが初期化されます)
    # コメントアウトしてパスを設定することで、ホストマシンの任意のディレクトリに変更することができます。
    # './' で始めることで、docker-compose.ymlからの相対パスで指定可能です。
    # - ./path/to/data/dir:/data/db

nginx:
  container_name: jiji_nginx
  image: unageanu/jiji-nginx:latest
  links:
    - jiji
  ports:
    # Jijiのポート番号
    # 443に変更します
    - "443:443"
  volumes:
    # SSL証明書のパス
    # './path/to/server.crt' にサーバー証明書、
    # './path/to/server.key' に秘密鍵を指定します。
    # './' で始めることで、docker-compose.ymlからの相対パスで指定可能です。
    - /etc/ssl/certs/jiji/server.crt:/etc/nginx/cert/ssl.crt:ro
    - /etc/ssl/certs/jiji/server.key:/etc/nginx/cert/ssl.key:ro

Dockerコンテナ起動

$ sudo /usr/local/bin/docker-compose up -d
Creating jiji_mongodb
Creating jiji_jiji
Creating jiji_nginx

アクセス

https://<インストール先ホスト>:<docker-compose.ymlで設定したJijiのポート/デフォルトは8443>

iPhone7等の新製品を誰よりも早く予約する為に、予約サイトがオープンしたらSlackに通知する方法

Slack シェルスクリプト

Shell Script Advent Calendar 2015 8日目を担当させていただきます、@yudsuzukです。

今回は実用的なシェルスクリプトについて書きます。

GoogleのNexusやAppleiPhone等の新製品の発表は、日本時間で深夜なため、起きているのが辛いし、いつ購入サイトがオープンしたか分かり難いですよね。
気がついたら、新製品の予約サイトがオープンしてて、お目当ての製品が既に予約でいっぱい。お届け予定日数は1ヶ月後なんて事もしばしば。

そんなあなたのために、新製品の予約サイトがオープンしたらSlackに通知させるシェルスクリプトをつくりました。

今回は、実際にそのシェルスクリプトのお陰で予約ができたNexus5X、Nexus6Pの事例と、近い将来発売されるであろうiPhone7の予約サイトオープン通知スクリプトを紹介します。

Nexus5XとNexus6Pの予約サイトオープン事例

今回はGoogleの新製品、Nexus5XとNexus6Pの予約サイトがオープンした時の事例を紹介します。
予めSlackのIncoming WebHooksでWebhook URLを取得してください。

doneFile=done.txt
if [ ! -e $doneFile ]; then
    exit 0
fi

# 通知するSlackのチェンネル
channel="#test"
# 通知する時のユーザ名
username="incoming-webhook"
# 通知するユーザのアイコン
iconemoji=":shell:"
# WebHookURL
webhookUrl="https://hooks.slack.com/services/XXXXXXXX"
# 通知文言
text="nexus_5xとnexus_6pのサイトがオープンしたよ!"
# サイトURL prefix
prefixUrl="https://store.google.com/product/"
# 製品名
products=("nexus_5x" "nexus_6p")


for product in ${products[@]}
do
    status=`/usr/bin/curl -LI $prefixUrl$product -o /dev/null -w '%{http_code}' -s`
    if [ $status -eq '200' ]; then
        /usr/bin/curl -X POST --data-urlencode "payload={\"channel\": \"${channel}\", \"username\": \"${username}\", \"text\": \"${text}\", \"icon_emoji\": \"${iconemoji}\"}" ${webhookUrl}
        touch $doneFile
        exit 0
    fi
done

cronに仕込めば完成。
5分おきぐらいに実行すれば怒られないでしょう。
URLが下記のものであるだろうという予測を元に作ってあります。

https://store.google.com/product/nexus_5x
https://store.google.com/product/nexus_6p

ドキドキでしたが、このスクリプトを仕込んだ結果、ちゃんと通知されていました。

f:id:yuzurus:20150930151034p:plain

予約サイトがオープンした時間は日本時間AM2:20でした! この通知を見て無事予約できました。

iPhone7の予約サイトがオープンしたことをSlackに通知させたい

近い将来発売されるであろうiPhone7。
iPhone7の予約サイトがオープンしたことをSlackに通知させる場合は、先ほどのスクリプトを下記のように変更してください。

# サイトURL prefix
prefixUrl="http://www.apple.com/jp/shop/buy-iphone/"
# 製品名
products=("iphone7")

このスクリプトを仕込んだあなたは、きっと誰よりも早くiPhone7を手に入れる事ができるでしょう!

※URLを予測しているので、失敗したらごめんなさい。
※発表されるであろう日に仕込んでください。

ということでShell Script Advent Calendar 2015 8日目でした。
次は@ryoana14さんです。よろしくお願いします!

【PHP】たった1行コマンドを入力するだけでComposerを劇的に速くする方法【アジア圏限定】

Composer PHP

f:id:yuzurus:20151129163147p:plain

PHPerで使っていない人はいないというぐらい、メジャーなPHPの依存管理ツールComposer。 ですが、動作が遅いという欠点があります。 Composerが遅い原因は主に下記だそうです。

  • packagist.orgが日本から遠い
  • composerのアーキテクチャ的に、小さなjsonファイルを少しずつダウンロードするため、ネットワークの遅延がもろに影響する
  • composerがfile_get_contentsでjsonをダウンロードしていて、どうやらKeep-Aliveを使っていないし、並列ダウンロードもしていない

Qiita

またある日@cakephperさんがこんなことを呟いていました。

そしたら、packagistのミラーサイト作ればいいんじゃね?と思い、作ろうと思っていたところ、すでに@hirakuさんが作っていたので、こっちに乗っかりました。

するとびっくり。composer爆速になりました。

packagistのミラーサイトをComposerへ導入する

下記のコマンドを打つだけで幸せになります

composer config -g repositories.packagist composer http://packagist.jp

packagist.jpを導入するにあたっての注意点

  • packagist.jpはpackagist.orgと1日1回同期しているようです。ほぼ最新ですが、ほぼという点をお忘れなく
  • packagist.jpはさくらVPS(日本)で運用しているため、爆速になるのはアジア圏でComposerを使った場合のみです
  • やはり元のリポジトリを参照したい、となったら下記のコマンドを打ってください
composer config -g --unset repositories.packagist

Validation::notEmpty() is deprecated. Use Validation::notBlank() instead.

CakePHP

CakePHPをバージョンアップしたら以下のエラーが表示されるようになった。

Validation::notEmpty() is deprecated. Use Validation::notBlank() instead.

該当のソースコードには以下の記載があった。

/**
 * Backwards compatibility wrapper for Validation::notBlank().
 *
 * @param string|array $check Value to check.
 * @return bool Success.
 * @deprecated 2.7.0 Use Validation::notBlank() instead.
 * @see Validation::notBlank()
 */
    public static function notEmpty($check) {
        trigger_error('Validation::notEmpty() is deprecated. Use Validation::notBlank() instead.', E_USER_DEPRECATED);
        return static::notBlank($check);
    }

CakePHP2.7からnotEmptyではなくnotBlankを使用しないといけないらしい。 notEmptyを叩くとnotBlankをそのまま呼び出しているので、すべて置換してよさそう。

これによると3.0.7以降は使えなくなる模様。 https://github.com/cakephp/cakephp/issues/6752