ホーム ブログ ページ 35

「なんとなく」で終わらせてませんか?”いらすと”で覚える並列と並行の違い

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

プログラミングしてると「並行」とか「並列」とか用語が出てきますが、なんとなく使ってませんでしたか? 私がそうでした。 そこでちょっと踏み込んで、並行と並列の違いについて調べてみました。

定義

情報技術用語としての定義は以下のようになっているそうです。

システムが複数の動作(処理の流れ)を同時に実行状態(in progress)に保てる機能を備えている場合を 並行(concurrent)と言い、複数の動作を同時に実行できる場合を並列(parallel)と言います。 重要な概念、違いは「実行状態」という点です。

並行と並列について-並行コンピューティング技法-を読んで – M-Tea」から

なんだか、こむずかしいですね。これをざっくり解説すると以下のようになります。

並行

  • 英語では’concurrent’
  • 複数の作業(例えば、電話の応対・オンラインサポート・書類の決裁など)をそれぞれの進行状況を保ちつつ「同時」に進行している状態
  • この場合の「同時」とは、電話の応対を10:00〜10:30, オンラインサポートを9:00〜12:00, 書類の決裁を10:10 〜 10:15 というようにそれぞれの作業時間がオーバーラップしているだけで、ある瞬間に2つの作業を同時に行っているというわけでは有りません。
  • 複数のタスクを一人でタスクスイッチしながら同時にさばいているイメージです。
enter image description here

並列

  • 英語では’parallel’
  • 複数の作業が本当の意味で「同時」に進行している状態
  • この場合の「同時」は並行の場合とちがって、まさしく複数の作業がある瞬間において同時に進行している状態を指しています。
  • 並列は平行を包含しています。
  • 複数のタスクを複数人で同時にさばいているイメージです。
enter image description here

さいごに

今までなんとなくで使っていた言葉ですが、いろいろ調べてみると異なる概念であることがわかりました。

あと、Canvaってツールでアイキャッチ画像とかこのエントリの画像作ってみましたが簡単で良いですね。おすすめです。

参考

AWSでRedashを使ってみる

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

20分くらいで、BIツール・redashがAWSでシュッと使えるようになる記事です。 https://redash.io/

Redashとは

Redash はデータソースからのデータの取得・取得したデータの可視化ができるWebアプリです。
本当はredashで作ったかっこいいグラフの画像を記事に貼って紹介したかったのですが、かっこいいグラフにできるデータがまだありません。残念です。

この記事を読めば、20分くらいでとりあえずAWSでOSS版のredashが動くようにはなるはずです。

インストール

用意されているAMIを使いましょう。一瞬です。アジアパシフィック (東京) はap-northeast-1 なので、 ami-34cfe853 を使ってインスタンスを作ります。
https://redash.io/help-onpremise/setup/setting-up-redash-instance.html

最初は今使っているamazon linuxのインスタンスに同居させようかと思っていましたが、amazon linux向けの
プロビショニングスクリプト が古いこともあり、少し格闘して諦めました。やめましょう
ubuntuならなんとかなると思います。

用意されているAMIを使う場合は、とりあえずインスタンスタイプとセキュリティグループだけ気をつければなんとかなります。

インスタンスタイプ

for small deployments t2.small should be enough

だそうです。 素直にこのアドバイスに従ってt2.smallかそれ以上にメモリのあるインスタンスタイプを選びましょう

素直ではないので t2.micro を使っていたところ、しばらくするとメモリが足りなくなったようでどんどんもっさりしていきました。
起動してしばらくはなんとか動いていたので、少し試してみたい程度ならなんとかなりますが。

セキュリティグループ

http, https のために80,443番ポートをあけておきましょう。
AWSのデータソースを使うなら、このセキュリティグループからアクセスできるようにデータソースのセキュリティグループを編集する必要があるかもしれません。

インスタンスの作成・起動ができればこれでもうredashが使えます。
ブラウザでパブリックDNSなり http://ec2-xx-xxx-xxx-xxx.ap-northeast-1.compute.amazonaws.com/setup にアクセスしてみましょう。管理者アカウントが登録できるはずです。

管理者アカウントが登録できればデータソースやクエリの登録・ダッシュボードの作成ができるようになります。よかったですね。

アップデート

AMIのredashはそこそこ新しいバージョンなので、

cd /opt/redush/current
sudo bin/upgrade

だけでアップデートができます。
currentはシンボリックリンクなので、アップデート後はcurrentのリンク先は今いるのとは別のディレクトリになります。

設定

一人で使うぶんにはこれで使えるには使えるのですが、せっかくのWebアプリなので他の人にも共有・編集してもらいたいですよね。

新しくユーザーを登録するには2つ方法があります。

  • Googleアカウントで認証する
  • 名前・メールアドレスを入力して招待する

Googleアカウントで認証する

Googleアカウントを使う場合はドメインによる制限はできますが、それ以上に細かいユーザー登録の制限はできません。
例えば社内の誰でもアクセスしてもよいような場合ならば便利ですが、同じドメインの人全員に登録されてしまうと困る場合はこの方法を使わずにメールアドレスを入力して招待したほうがよいでしょう。
一応redashにはグループを作ってアクセス権限を管理する仕組みもありますが、デフォルトでは最初に入れられるグループの権限が強めです。
気をつけてやりましょう。

GoogleAPI側の設定

Google APIs コンソールから色々と登録します。
https://console.developers.google.com/projectselector/apis

プロジェクトを作成または選択して、認証情報を作成します。
作成する認証情報はOAuthクライアントID、アプリケーションの種類はWebアプリケーションです。

javascript生成元またはリダイレクトURIの入力を求められますが、

  • javascript生成元: http://[hostname]
  • リダイレクトURI: http://[hostname]/oauth/google_callback

です。

この認証情報のクライアントIDとクライアントシークレットをredash側に登録します。

redash側の設定

redashの本体は /opt/redash/current にあります。
sshでログインして、ドキュメントにある通りのことをしましょう(やっとそれっぽい作業が始まりましたね!)

  1. .env に二行ほど追加します。
export REDASH_GOOGLE_CLIENT_ID="さっきのクライアントID"
export REDASH_GOOGLE_CLIENT_SECRET="さっきのクライアントシークレット"
  1. ログインを許可するGoogleアカウントのドメインを指定します。
sudo -u redash bin/run ./manage.py org set_google_apps_domains "allowed-domain.com"
  1. redashを再起動します。
sudo supervisorctl start redash_server

晴れてGoogleアカウントでログインできるようになりました。よかったですね。

Googleアカウントを使わない場合

アプリ上で登録する

Webアプリ上の Settings > USERS から新しいユーザーの登録ができます。
メール送信の設定がちゃんとできていれば、招待用URLが記載されたメールが届きます。
ちゃんとできていなかった場合(または設定しない場合)でも招待用のページへのURLが表示されるので、別の方法で送りつけることができればなんとかなります。

招待用URLは環境変数 REDASH_HOST を設定しないとうまく表示されません。
今のところ真面目にメールを送信できる環境を作る気がないので、とりあえずこれだけ設定します。(気持ちの問題です)

redashの本体は /opt/redash/current 以下にあります(二回目)。

.envに以下を追加して、

export REDASH_HOST="http://[hostname]/"

redashを再起動します。

sudo supervisorctl start redash_server

コマンドラインから登録する

コマンドラインからもユーザーの管理ができます。
ドキュメントが見つからないので、 redash/cli/users.py を見てやることになりそうです。

一番害のないコマンドはユーザー一覧を表示する list です。

sudo -u redash bin/run ./manage.py users list

ユーザーの作成(+パスワードの設定)

sudo -u redash bin/run ./manage.py users create example@example.com "Example User"

admin権限の付与

sudo -u redash bin/run ./manage.py users create example@example.com "Example User"

あたりがコマンドラインから設定できます。

コマンドラインから他の設定変更もできるようです。

まとめ

きっと動くようにはなっているはずです。よかったですね。

ec2インスタンスは再起動するたびにIPアドレスが変わるので、Elastic IPで固定IPの取得・インスタンスへの紐付けくらいはしておいたほうがよさそうです。
20分くらいでできます!と書きましたが、amazon linuxにredashを入れようと奮闘したり、t2.microでmysqlクライアントを入れようとしてメモリが足りなかったりしてもっと時間がかかりました。素直にやりましょう。

かっこいいグラフが作れるようになったあかつきには、AWSで作ってあるMySQLサーバーをデータソースに設定したり、クエリ登録してみたり、グラフを作ってみたりした記事を書きたいです。

勇気が湧く!gitやらかし防止コマンド&オプション集!

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

皆さんはgitを使っていてミスをしてしまうことはありませんか?
ミスとまではいわずとも「あの変更いらなかったな」とか「間違えてコミットしちゃった」とかはあると思います。

それらをなくすために一番大事なのは「確認」です。

確認をより確信あるものにするために個人的によく使うコマンドやオプション、
ミスをしてしまったときになんとかするものを紹介しようと思います。

git diff –cached

git diff はほぼ必須の確認コマンドだと思います。
現在ブランチの変更した差分を表示してくれるので、僕はcommitする前には必ず確認しています。
ですが、先にaddをしてしまうと差分を表示してくれません。

--cachedオプションをつけることによって、addした後でも差分を表示できます。
git diffで確認し忘れたときに、いちいちgit reset HEADしてチェックするのはめんどくさいですよね。

git add test.txt

git diff

git add test.txt

git diff --cached

diff --git a/test.txt b/test.txt
index e6a6914..2b70263 100644
--- a/test.txt
+++ b/test.txt
@@ -1,5 +1,5 @@
....以下省略

git status -uall

git statusだけ打っても新しく追加したディレクトリ以下のファイルは表示してくれません。
-uallオプションをつけると全部追跡してくれるので確認することができます。

git status

On branch develop
Untracked files:
  (use "git add <file>..." to include in what will be committed)

    testDir/

nothing added to commit but untracked files present (use "git add" to track)

git status -uall

On branch develop
Untracked files:
  (use "git add <file>..." to include in what will be committed)

    testDir/a.txt
    testDir/b.txt
    testDir/c.txt

nothing added to commit but untracked files present (use "git add" to track)

git log –name-status

個人的に一番使うlogのオプションです。
下記のようにそのコミットで変更されたファイルが出力され、
git status + git log のようなイメージで使えます。

git log --name-status

commit 49d8d9c4ff2e3bdfc7fd4e18eb3fa9e5507ed89b
Author: ziguzagu
Date:   Tue Jul 4 16:16:40 2017 +0900

    テストファイル追加

A       test_00.txt

commit 53c55b128356aa960739b5f999b9917ed63a9784
Author: ziguzagu
Date:   Tue Jul 4 16:10:10 2017 +0900

    hugaクラスにメソッド追加

M       app/models/hoge.rb

git reflog

ローカルで行ったcommit, merge, resetなどのログを見ることができます。
マージしていないブランチを消してしまったり、
git reset --hardなどで戻しすぎてしまった場合などでも履歴を見れるので、
任意の時点まで戻すことができます。

git reflog

36336b7 HEAD@{0}: commit: xxxx => cccc
331f0b6 HEAD@{1}: commit (merge): Merge branch 'change_text' into develop
4d02134 HEAD@{2}: checkout: moving from change_text to develop
510169f HEAD@{3}: commit: bbbb => cccc
1ef1996 HEAD@{4}: checkout: moving from develop to change_text
4d02134 HEAD@{5}: commit: bbbb => aaaa
1ef1996 HEAD@{6}: commit: テキスト作成
3057744 HEAD@{7}: checkout: moving from master to develop
3057744 HEAD@{8}: commit (initial): 最初のコミット

git reset --hard 4d02134

上記の例ではcommit: bbbb => aaaaのブランチまでを戻すことができますが、
このやり方の注意点として、以下の点が挙げられるので使用するときは注意しましょう。

  • 現在編集中のファイルは消えてしまう
  • 作業していたブランチを問わずにもどせてしまう

終わりに

ミスをしないための「確認」についての記事になりましたが、
もしミスをしてしまったときの対処法も知っておけば、より勇気を持って動けると思います。
自分はgit reflogでhash値を調べられることを知ってからはmergeに対する恐れは減りました。

最終的には確認の方法を知っていても自分が確認を忘れたり、
間違っているものを正しいと思い込んでたりしたら意味がないのでコマンド以外に
他の人にチェックしてもらえたりするとさらにいいですね。

ゲーム業界の常識!売上に響く4つの基本KPI

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

ゲーム業界ではいったいどんなKPIが使われているのでしょうか?
今回は商品としてゲームを制作・運営するには避けては通れない「売上」に注目し、
「DAU」「ARPU」「DPU」「ARPPU」の4つのKPIをご紹介します。

KPIとは何か

KPI(Key Performance Indicator)とは、目的を達成するための過程を計測するための中間目標のことを指します。重要業績評価指標とも呼ばれていますね。
最終的なゴールとなる目標を定量的に示すものはKGI(Key Goal Indicator/重要目標達成指標)と言います。

KPIはKGIを達成するために、その構成要素を分解し、最終目標までどれくらい達成できているのか、達成できそうなのかを評価するために用いられます。

「売上」を分解!~ゲーム業界のKPI~

enter image description here

ゲーム業界ではいったいどんなKPIが使われているのでしょうか?
今回は商品としてゲームを制作・運営するには避けては通れない「売上」に注目したいと思います。
※本記事ではKPIを扱うことの多いソーシャルゲームについてのお話になります。

分解方法① 「売上」 = DAU × ARPU

最も基本的な分解方法は顧客数×顧客単価とすることです。
ゲーム業界では、日ごとのKPIを追うことが多いため、顧客数を一日の利用者数、顧客単価を一日の利用者一人当たりの売上としています。
以下で各KPIについて詳しく見ていきます。

DAU(Daily Active Users)

DAUとは、一日当たりに一回以上活動のあったユーザ数のことを指します。
要は「ゲームで遊んでくれている人はどれくらいいるのか」ってことです。

活動とは、ゲームにログインしただけといった場合も含まれています。
必ずしもゲームをプレイしているわけではないという点、注意が必要です。

ARPU(Average Revenue Per User)

ARPUとは、活動のあった一ユーザ当たりの支払い金額のことを指します。
今回は日次で見ているので一日当たりの指標になりますね。

分解方法② 「売上」 = DPU × ARPPU

もう一つの方法として課金者数×課金者一人当たりの顧客単価に分解する方法があります。
基本プレイが無料のゲームではユーザを課金者と非課金者と分けて捉えることもあるため、こういった捉え方もあるのです。
こちらも各KPIについて詳しく見ていきましょう。

DPU(Daily Paid Users)

DPUとは、一日当たりにお金を支払ったユーザ数のことを指します。
これは「有料で遊んでくれている人はどれだけいるのか」ってことですね。

このゲームにお金を支払う価値があると思ってくれている人数とも取れるので個人的にはかなり重要度の高い指標だと思っています。

ARPPU(Average Revenue Per Paid User)

ARPPUとは、お金を支払った一ユーザ当たりの支払い金額のことを指します。
つまり「有料で遊んでくれている人は平均どれだけお金を使っているのか」ということです。

ARPUと間違えやすいのでエーアールピーピーユーではなくきちんと意味を覚えておいた方が混同せずに済むでしょう。

まとめ

今回ご紹介したゲーム業界で使われているKPIは
「DAU(Daily Active Users)」
「ARPU(Average Revenue Per User)」
「DPU(Daily Paid Users)」
「ARPPU(Average Revenue Per Paid User)」

以上4つになります。
そう、基本を知るだけでは足りないのです。「どう活用するのか」が重要になります。
今後また機会ありましたらこれらのKPIをどう活用していくのか?といった記事も書きたいと思います。続くかも?

BoxのAPIを使って見よう。(その3)~EXCEL(VBA)から呼び出して、直接EXCELに結果を出力する

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

1.どうして、EXCEL(VBA)を使うのか

実は、下図のウェブサーバを作れる自信がないのと
出力結果を直接EXCELで加工してしまいたい!と思ったのがキッカケです。

enter image description here

1.1.作成イメージ

  1. EXCEL上にボタンを追加
  2. InternetExplorerを使用して、認証画面を表示  前回の説明(その1その2)参照
  3. 取得したいAPIを実行
  4. EXCELの別シートに出力
enter image description here

1.2.認可コード要求~アクセストークン取得までのイメージ

上記、項1.のウェブサーバを使用している部分を、VBAで実装して見よう。って事です。

enter image description here

2. 実際にどんなVBAコードを使えばよいか(一部)

2.1.BOXから認可コードを取得

InternetExplorerオブジェクトのNavigateメソッドを使って、認可コード要求をしてみます。

■以下はサンプルです。

    '-- IE を起動する
    Dim objBrowser As Object
    Set objBrowser = CreateObject("InternetExplorer.Application")

    With objBrowser
    '-- IEを表示
        .Visible = True

        '-- 表示位置を設定
        .Top = 100  'Y位置(上下)
        .Left = 200  'X位置(左右)
        .Width = 650 'IEウィンドウの幅
        .Height = 800  'IEウィンドウの高さ

        '-- 認証画面を表示
        .Navigate "https://account.box.com/api/oauth2/authorize?response_type=code&client_id=" & CLIENT_ID"

        '-- IEが表示されるまで待機
    Do While .Busy = True Or .readyState <> 4
        DoEvents
     Loop

    End With

2.2.アクセストークンを取得

次は、ブラウザを表示する必要がないため、msxml2.xmlhttpオブジェクトを使って、アクセストークン要求をしてみます。

■以下はサンプルです。

    '-- Access Token の取得 (HTTP POST 要求)
    Dim objXHttp1 As Object
    Set objXHttp1 = CreateObject("msxml2.xmlhttp")
    objXHttp1.Open "POST", "https://api.box.com/oauth2/token", False
    objXHttp1.setRequestHeader "Content-Type", "application/x-www-form-urlencoded"
    objXHttp1.send "grant_type=authorization_code&code=" & strCode & "&client_id=" & CLIENT_ID & "&client_secret=" & CLIENT_SECRET

2.3.JSONをパースする

EXCEL(VBA)でJSONを扱うには、VBA-JSONをダウンロードして使用するのが、オススメです。
※レスポンス結果はUnicodeに変換しないと、文字化けしてしまいます。

■文字コード変換のサンプル

    Dim strResult As String
    strResult = StrConv(objXHttp2.responsebody, vbUnicode)

■VBA-JSONを使って、パースするサンプル

    Dim Folders As Object
    Set Folders = JsonConverter.ParseJson(strResult)

3.サンプル

サンプルを作ってみましたので、試してみたい方はご自由にどうぞ
サンプルEXCELをダウンロード(2019.07.29リンク誤り修正)
※VBAのコードは、現時点では非公開です。
※2017.10.18時点で、実践サンプルも公開中 (その4)(その5) の記事を確認してみて。

enter image description here

EXCELを表示したときの初期画面

enter image description here

今回は、Get Folder InfoGet Folder Itemsを実行してみて、EXCEL上に出力してみました。

まとめ

次回は、EXCEL(VBA)から、グループ情報をEXCELに整形して出力してみたいと思います。
管理者向けの管理コンソールから取得できる情報ですが、CSVダウンロード等の機能が現時点(2017.6.23)では無かったので作成してみようと思います。

Boxの販売パートナーもしてます。

enter image description here

お問い合わせは、こちら へ
BOXを使ったのアプリケーション開発も可能です。気軽にご連絡お待ちしております。

記事は見た目が100%!読まれるタイトルを付ける3つのコツ!

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

タイトルって本当に重要なの?

まず、見てもらわないと何もはじまりません!
この文章を読んでいる人もタイトルを見て、興味を持ったから読んでいるのではないでしょうか。
多くの情報が飛び交う現在の世の中では、読んでもらうためにタイトルで惹きつける必要があるのです。

あ、もちろん中身も大事ですよ?
タイトルと内容が一致していないことや「釣り」や「煽り過ぎ」はサイトの信用を落としてしまい、最悪の場合、二度と読んでもらえません。

①タイトルには数字を入れよう!

数字を入れると何が変わるでしょう?

enter image description here

「PVを生む記事を書くための方法」

enter image description here

月10万PVを生む記事を書くための7つの方法」

前者に比べると、後者は記事を読めばどんなことが出来るようになるのかイメージしやすいです。
ただPVを生むというよりも月10万PVという具体的な数字を出すことで説得力が上がり、
7つの方法と情報量があることで記事のボリュームを伝える効果が期待できます。

ちなみに情報量はどれくらいがちょうどいいのでしょうか?
多くの人は「7」を好むようです。あと日本人は「3」を好むんだとか。
数字を使う際は意識してみるといいかもしれません。

参考:なぜ人は「7」 という数字が好きなのか?

とはいえなんでもかんでも数字を入れてしまうと一覧表示のとき、
どの記事も似たようなタイトルになってしまい、見た目が悪くなってしまうことも…
やり過ぎ注意です。

②タイトルは簡潔に!30文字以内で作ろう!

伝えるべき情報は絞るべき!というのもありますが
「検索エンジンの文字数表示に入るためにタイトルは30文字以内で」
という有名なルールが一番の理由でしょう。
一般的によく使われる検索エンジンでは、

  • Google … 全角30文字前後(ほぼ固定)
  • Yahoo … 全角28~33文字程度

これを超えてしまうと最後が「…」となってしまい、
せっかくタイトルを付けても表示されない!なんてことに…。
enter image description here
もったいない!

また、検索したとき記事のタイトルをじっくり読む人はなかなかいません。
パッと見で何が書いてあるか判断できるようなタイトルであるほど検索者の目に留まり、
読んでもらえる可能性が高まるのです。
enter image description here
イイネ!

③読んだら役立つことが一目でわかるようにしよう!

役に立つかどうかどうやって判断するのでしょう?

enter image description here

「魅力的なタイトルについて」

enter image description here

初心者でもすぐにできる!魅力的なタイトルを付けるためのテクニック

判断基準は自分にとって読む価値があるかどうか、です。

  • どんな人に対しての記事であるのか
  • 書いてある内容がイメージできるか

このあたりを意識すると役に立つタイトルが作れるようになるのではないでしょうか。

検索している人は基本的に何か知りたいから検索しています。
この記事を読めば、あなたの知りたいことがわかります!
あなたの悩みや問題解決できます!ということを伝えることが大切です。

よく使われる役立つことがわかる言い回しは、
「~のコツ」「~のルール」「~のヒント」「~方法」「~のテクニック」などでしょうか。

まとめ

さて今回ご紹介したコツは
「タイトルには数字を入れよう!」
「タイトルは簡潔に!30文字以内で作ろう!」
「読んだら役立つことが一目でわかるようにしよう!」

以上の3点になります。
他にも様々な方法が世の中溢れています。
しかし、無理に全部を詰め込む必要はありません。要所を押さえればOKです。
あとは素晴らしいタイトルが天から降りてくるよう一生懸命、神様に祈りましょう。
enter image description here

※本記事の内容は個人の見解によるものになります。

ゲームプランナーを目指す就活生必見!役立つプランナー本とゲームプランナーに大事なものとは!

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

います!

皆さんこんにちは!Lionと申します。
ゲームプランナーを目指す熱き魂を持つ新卒の方に少しでも役立つ情報を投稿いたしますので、
何卒読んでいただければ幸いです!

さて…。今日は、ゲームプランナーになるべく就職活動を行っている新卒生の方々に
私が就職活動中に愛読していた一冊の本をご紹介したいと思います。

「ゲーム屋が教える!売れるゲーム企画書の書き方」

enter image description here
ゲーム屋が教える!売れるゲーム企画書の書き方-吉成 隆杜 (宝島社)

この本は、株式会社サクセスの社長が自ら著作したものである。

ゲームプランナーを目指してる皆さんも様々な本を読んでいるとは思いますが、
こんな疑問を浮かんだことはないですか?

①「企画書の書き方などは書いてあるけど、実際はどう書いたら良い企画書が書けるかがわからないよぉ…」
②「書き方とかじゃなくて、実例などがあればなぁ…」
③「そもそも、良い企画書ってなんだ?」

など…。
それを上記の本は全て解決してくれます!

本物の企画書が実例で記載されている!

この本の凄いところは、「実際に世に出ているゲームの企画書が丸々載せてある」ところです。
普通は企業秘密なのですが、そこを全てオープンに記載しています。

また、企画書を書いた人物にインタビューしている内容も書いているので、
「この企画書はこういう意図や狙いがあって作成されたんだ!」が一目でわかります。

上手く企画書を書くテクニックなんてタイトルの本よりも、「現場の人が実際に書いた企画書」を参考にした方が何倍も勉強になります。

この本を読めば誰でも良い企画書が書けるようになるの?

この本を読めば企画書の何たるかは理解できるかと思います。
しかし、本だけを読んでも良い企画書を書くことはできないのです。
もし、「良い企画書が提案できるゲームプランナーになりたい!」と思うのであれば、この本を読むのと並行して以下のこと行ってみてください。
①沢山色々なタイトルのゲームをプレイする
②そのゲームが面白いか?面白くないか?を考える
③遊んだゲームをもっと面白くする方法はないかを考える

これが、できるプランナーは本当に面白い案を沢山生み出すことができます。
早い話が、「ゲームを沢山プレイして、自分だったらこういう風に面白くするのになぁー」と考えることができればOKです!

まとめ:ゲームプランナーに大事な物

さて、色々話しましたが、どうだったでしょうか?
まとめとして、皆さんにゲームプランナーに必要な3つの極意をお伝えします。
①沢山ゲームをするべし!
②なぜ、そのゲームが楽しいのかを考えるべし!※楽しくなかったらなぜ楽しくないかも考えるべし!
③「実際の企画書が記載されている」本を買って、なぜその企画書が通ったか考えるべし!

これをこなせるようになったら、ゲームプランナーへの近道になると思います!

さて…。次、投稿する記事は「Lionが考えた和風パッケージゲームと洋風パッケージゲームの違いはなんだ!?」です。
お楽しみに(´∀`)ノ
ここまで、お読みいただきありがとうございました。また読んでいただければ嬉しいです!では(‘ω’)ノシ

Googleデータポータルの計算フィールドが役立つ!CASE関数編

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

Googleデータポータルには計算フィールドというカスタマイズ機能があります。Googleアナリティクス上では編集できない、置換・統合といったデータ表現も可能です。計算フィールド内で使えるCASE関数について実例を踏まえてご紹介いたします。

この記事でまとめられていること

こんにちは。株式会社アピリッツでアナリストをしているssekiです。
以前、「情報共有ならデータポータルがおすすめ!マイレポートと比較してみた」という記事内で、GoogleアナリティクスのマイレポートよりGoogleデータポータルが使いやすいというお話をしましたね。

その後、データポータルを使って新卒一同の記事投稿状況を監視(もとい管理)していると、ふと小さな不満がわいてきました。

「ユーザー名が新卒の名前と一致しないから、わかりにくい・・・!!」

enter image description here

そうです。例えば、私のユーザー名「sseki」をURLから抽出して、ssekiが書いた記事の合計ページビュー数をアナリティクスやデータポータルで見るとこうなります。

私自身は/sseki/でも誰だかわかりますが、新卒全員分を監視するにはちょっと複雑ですよね。できれば実名で管理したい。

実は、そんな時にもデータポータルが役立つんです。

今回は、Googleアナリティクスデータを一部置換したレポートが作成できるデータポータルの機能について、使い方を交えてまとめてみました。

Googleデータポータルの計算フィールドとは

以前紹介し損ねましたが、GoogleデータポータルにはGoogleアナリティクスのマイレポートとは大きく異なる機能が搭載されています。それが計算フィールドです。

計算フィールドとは、データを元に新しいディメンションや指標をカスタマイズする機能です。

感覚的には、エクセルの関数やマクロに近いものになります。

2017年6月現在、データポータルには54個の関数が用意されています

これらの関数を使って、アナリティクスデータをもとに全く新しいディメンションや指標を作成できるのです。
マスターしたら、わざわざエクセルにエクスポートしなくてもレポート作成ができてしまうかもしれませんね!

計算フィールドの使い方

enter image description here
まず、ディメンションや指標の切り替え画面から「新しいディメンション/指標を作成」を押します。
すると、画像下側から現在設定されているディメンションと指標の表がせせり出てきます。

enter image description here
フィールドと書かれている右の「+」ボタンをクリックすると、計算フィールドが出現します。

カスタムフィールドに名前を付け、数式欄に関数やデータを組み合わせた数式を入力した後、「項目を作成」ボタンをクリックすると新しいディメンションや指標を作成できます。

CASE関数で条件付け置換が可能

データポータルの関数リストの中でも、私がイチオシしたいのがCASE関数です。
やや複雑ですが、エクセルのIF文のように条件付けを行ってデータを置換することができます。

例えば、私「sseki」の名前を「関」に置換する場合には次のようにCASE関数を使った数式が使えます。

CASE WHEN 第 2 階層 = "/sseki/" THEN "関" END

CASE関数はどんな条件のとき(WHEN)に、結果として何を表示するか(THEN)が基本文となっています。
そのため、条件文whenの中に「第 2 階層に”/sseki/”って文字があったら」を入れて、結果文thenの中に「”関”って表示して」と記述することで、条件別に置換することができます。

ちなみに、先頭のCASEと末尾のENDはCASE関数の開始・終了を知らせる文字なのでお忘れなく。

enter image description here
新しいディメンションを作成すると、ディメンション一覧に追加されて選択することで使用できます。
実際にディメンションを選択してみると、/sseki/が関になっているのがわかりますね。

複数条件の場合にはIN関数を使おう

前述した例の中では、条件文whenで「=」を使った単条件一致パターンを紹介しました。
実際には、複数条件に一致する場合の方がよく使うのかなと思います。
例えば、私が「sseki」と「mofumofu」という複数のアカウントを持っていたとします。
その両方のアカウントを「関」に統合したい場合、次の数式が使えます。

CASE WHEN 第 2 階層 IN ("/sseki/","/mofumofu/") THEN "関" END

IN関数は、カッコ内でカンマ区切りされた文字列に合致するデータを対象のディメンションや指標の中から探し出して出力する関数です。
もちろんOR条件のような論理演算子を使うこともできますが、たくさんの複数条件を記述する場合はIN関数のほうがお手軽です。

まとめ:CASE関数はどんなときにおすすめか

CASE関数はデータを一部置換したり、統合したいときに使える関数でした。
Googleアナリティクス上で置換する場合にはタグ改修などが必要となり面倒ですが、データポータル上で編集する分には数式を書くだけなのでお手軽です。

今回は、名前を変更したり統合することを例に出しましたが、その他にも例えば次のようなことが考えられるかなと思います。

1. アナリティクスデータの市区町村を漢字名に直す/都道府県や地方単位に統合する
2. 年齢層を若年層・中年層・高齢層に再区分する
3. アフィニティカテゴリを日本語訳する/大きなカテゴリに統合して管理する

ところで、ご紹介したCASE関数を含めた計算フィールドでの計算が元データを改変することはありません。
あくまでも元データをもとに計算するだけなので、アナリティクス上のデータが変わることはないということに注意しましょう。
逆に、「アナリティクスをいじって元データを変更したくないという人」や、「毎回エクスポートしてエクセルで作業している」という人にはおすすめの機能なので、ぜひ一度お使いになってみてはいかがでしょうか。

アニメ名探偵コナンの新一が出てる回だけを見たい

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

初投稿、新卒のいくたです。よろしくお願いします。
新一くんの声が好きなので、そればっかり見たいのです。
バーローなのです。

準備するもの

実装の概要

今回は、名探偵コナンの非公式ファンサイト「名探偵コナン応援サイト 毛利小五郎探偵事務所」から過去のアニメ各話の情報をとってきます。

とってきたデータをrubyのgemであるNokogiriでスクレイピング(解析)します。
ノコギリでギコギコ切って、必要なところ(新一くん登場回)だけを表示させる。
ざっくり言うとそんなイメージです。

コナン…ノコギリ…バラバラ死体…
なんだか事件の匂いがしますね。

webページの情報をとってくる

試しに以下のページをとってきて表示してみます。
名探偵コナン 事件データ・1996年度(TVアニメ)

# shinichi.rb

require 'open-uri' # open-uriライブラリを読み込みます

url = 'http://conan.aga-search.com/anime/1996/'
html = open(url).read # open-uriのおかげでURL先のデータを普通のファイルと同様に扱えます
puts html

実行結果

$ ruby shinichi.rb 
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>名探偵コナン 事件データ・1996年度(TVアニメ)</title>

(省略)

Webページがhtmlの形式でとってこられました。

Nokogiri の使い方

表の各話の登場人物の項目に着目して、’新一’を含む行だけを抜き出します。

# shinichi.rb

require 'open-uri'
require 'nokogiri'

url = 'http://conan.aga-search.com/anime/1996/'
html = open(url).read

doc = Nokogiri::HTML.parse(html)
trs = doc.xpath('//*[@id="leftpane"]/table[2]/tbody/tr[contains(.,'新一')]')

今回の肝となる、’新一’を含む行だけ抜き出す処理を見ていきましょう。

doc.xpath('//*[@id="leftpane"]/table[2]/tbody/tr[contains(.,'新一')]')

XpathとはHTMLのような木構造の分岐点(ノード)を指し示す表現です。
Xpathメソッドで抜き出すノードを指定できます。

自分の好きなところでXpathを指定しようとすると、HTMLを見てidやらタグやらを確認することになります。
これが正直めんどくさいんです…

が!実はXpathを指定する複雑なパターンを自分で考えなくても、簡単に好きな要素を抽出できるんです!
次は、Chromeを使ったXpathのパターン取得方法をご紹介しましょう。

Xpathパターンはchromeが知っている

chromeで解析したいwebページを開き、デベロッパーツールを表示させます。
Elementsタブから抽出したい要素を右クリックして、Copy > Copy Xpath を選びます。

copy_xpath.png
図1 Xpathの指定パターン取得方法

//*[@id="leftpane"]/table[2]/tbody

HTMLをいちいち読まなくても、特定の要素を指定するパターンをchromeが教えてくれるのです。便利!

あとは抽出する条件を付け加えるだけです。
今回は’新一’という文字列を含むtrタグの内容をとってくるので、以下のように条件を追加します。

//*[@id="leftpane"]/table[2]/tbody/tr[contains(.,'新一')]

こちらの記事にいろんな指定方法がまとめられます。
詳しく知りたい方はどうぞ〜

最後の仕上げ

最後にとってきたデータの形を整えて出力します。

# shinichi.rb

require 'open-uri'
require 'nokogiri'

url = 'http://conan.aga-search.com/anime/1996/'
html = open(url).read

doc = Nokogiri::HTML.parse(html)
trs = doc.xpath('//*[@id="leftpane"]/table[2]/tbody/tr[contains(.,'新一')]')

# HTMLの解析結果をtr要素ごとに処理します
trs.each do |tr|
  td = tr.xpath('./td') # tdタグを取り出します
  story_number = td[0].text # tdタグの1番目の要素のテキストを取り出します
  story_title = td[1].text  # tdタグの2番目の要素のテキストを取り出します
  puts "名探偵コナン 第#{story_number}#{story_title}"
end

実行結果

$ ruby shinichi.rb 
名探偵コナン 第1話 ジェットコースター殺人事件
名探偵コナン 第2話 社長令嬢誘拐事件
名探偵コナン 第3話 アイドル密室殺人事件
名探偵コナン 第7話 月いちプレゼント脅迫事件
名探偵コナン 第10話 プロサッカー選手脅迫事件
名探偵コナン 第29話 コンピューター殺人事件
名探偵コナン 第32話 コーヒーショップ殺人事件
名探偵コナン 第33話 探偵団サバイバル事件
名探偵コナン 第42話 カラオケボックス殺人事件

新一くんが出ている回の話数とタイトルがとってこられました!

このキーワードを元に動画配信サイトで検索すれば、新一くんが出ている回だけを永遠見続けることができますね。

実は、新一くんと怪盗キッドは同じ声優さんが演じています。
‘キッド’を含む回も取って来られるように、条件を追加してもいいかもしれませんね。

それでは、今日はこの辺で。
読んでいただき、ありがとうございました。

UnityのEventSystemのクリックイベント実装方法

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

Unityを使っていて実装で詰まったところの備忘録としてUIが重なった時の処理を書いていきます。 主に、EventSystemについて書いていきたいと思います。 EventSystemで制御している時は、EventSystemを介して制御しましょうと言う話です

はじめに

こんにちは、初めまして。今回初めて投稿させていただきます新卒でエンジニアとして入社した者です。

今回、Inputを使ったクリックイベントを実装しました。しかしEventSystemはそのクリックイベントには干渉してこないので何かしらのオブジェクトが重なってもInputのクリックイベントが実行されてしまうと言うバグが出ました。
その時のEventSystemで制御する方法を書いていきます。

EventSystem とは

これは、UIのイベントを制御するオブジェクトで、Unity上の入力をうまく処理してオブジェクトにイベントを送信する仕組みのことです。基本的にUnityのuGUIはこれで管理されています。

なぜこのバグが起こったのか?

このバグが起こった原因は、EventSystemとInputクラスの処理が連携していないことに原因がありました。
EventSystemは上記の通り、uGUIの入力を管理するコンポーネントです。ボタンなどに対しての入力エベントを管理しています。
対してInputクラスは座標を取得してその座標内にオブジェクトがあるならば、クリックイベントを実行する実装になっていました。

これでは、どちらも独立しているので、座標でイベントを管理しているとどんなにUIが重なってもその場所がタップされると実行されてしまうという状況でした。

解決方法

解決方法として、複数方法がありました。

  • raycastでどのオブジェクトが重なっているかを判定して一番上にあるもののクリックイベントを実行する方法
  • IPoinerClickHandlerインターフェースを使い、InputをEventSystemに組み込んで実装する方法

今回は後者で実装しました。

実装方法

IPoinerClickHandlerインターフェースをクラスに実装してください。そうすることで、InputでとっているクリックイベントをEventSystemに組み込むことができます。このようにするとInputクラスでの入力とEventSystemでの入力を連携させることができました。

ソースコードは以下のようになります。

class TestInput : IPoinerClickHandler {
  public void OnPointerClick(PointerEventData eventData) {
    //ここにタップ処理を追加する
  }
}

このインターフェースは様々な種類があります。
詳細は下記URLで詳しく書いてあります。
https://docs.unity3d.com/Manual/SupportedEvents.html

まとめ

EventSystemを挟むことで簡単に制御ができるようになりました。
EventSystemで管理しているUIは、EventSystemを介して制御してあげましょう。そうしないと今回の私のようにバグを生み出してしまうのでやめましょう。

もし、興味のある人はuGUIのソースコードは、BitbacketのUnity Technologies/Unity/UIにて公開されているので読んでみてはいかがでしょうか?

Unityのインストールが上手くいかなかった時の対処法まとめ

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

Unityのインストールが上手くいかなかったときに参考にしたサイトや方法のまとめです

初めてUnity(ver5.6)をDLした際全く起動が出来ず四苦八苦したときの思い出を元に試した方法を幾つかまとめました。
もし似たような環境でUnityが起動しない!という方は参考になれば幸いです。

作業環境

当初の私の作業環境がこちら。
【使用PC】IntelCorei7-4790K
【OS】Windows7
【主な使用ブラウザ】Internet Explorer11(以下IE)

今回起動したかったUnityはバージョン5.6。2017年現在最新バージョンのものです。
公式サイトを開き最新バージョンをDL。しかしインストールしてもエラー画面により一向に起動しない。そんな状態でした。
というわけでインターネットに頼りつつ幾つかの方法を試してみましたので箇条書きしていきます。
参考にしたサイトもリンクさせていただいておりますので詳しくはそちらをご参考ください。

対処方法

Unityログインアカウント名を確認してみる

Unityを起動する際に最初に設定した自身のUnityIDを入力するのですが、海外製ソフトの為か、日本語が混じると動作が不安定だったり不調が起こりやすくなるそうです。ログインアカウント名は全てアルファベットで作成してください。

再起動

まずは再起動してみましょう。たまたま起動が失敗した場合もありますのでUnityやPCを再起動してみてください。

再インストール

インストール自体がそもそも上手くいかない場合があります。この場合は前のデータをアンインストールし、PCを再起動してから再びWebサイトから最新バージョンのデータをDLしてみてください。
また再インストールした際以前の設定がそのまま使用されるパターンがあります。アンインストールだけでは消えないフォルダが存在している為なので、一から設定をしなおしたい場合はそれらを削除することをお奨めします。以下のリンクを参考にしてください。
FreelyApps:Unityの再インストール

前バージョンUnityを起動してみる

Unity5.6自体の問題やPC自体が新バージョンに対応してない可能性もあります。
もしそうであれば、前のバージョンのUnityなら起動できる場合がありますのでお試しください。

使用ブラウザを変えてみる

上記の古いバージョンのUnityをIEブラウザでDLしてみたところうまくDLがいかない、ファイルが開けないということがありました。
こちらの問題は使用ブラウザを変更することで解決されます。Unityにはブラウザとの互換性の問題もあるらしく、その中でもFireFoxがブラウザの中では最も互換性が良いようです。
IEやGoogleChromeではDLが上手くいかない場合はブラウザを変えてみてください。

セキュリティソフトの設定見直し

PCのセキュリティソフトの中でUnityと相性の悪いものも存在します。セキュリティソフトによって起動できないパターンもありますので、セキュリティソフト対象からUnityを除外に設定してみましょう。
SAKスタッフブログ:Unity起動時のエラーとその対処法

DEP有効にしてUnity.exeを追加

Windowsのアップデートか何かでUnityが起動しなくなった場合、
「コントロールパネル→システム→システムの詳細設定→パフォーマンス→データ実行防止→DEP有効にしてUnity.exeを追加」
で起動できた場合もあるそうです。ただセキュリティ上の問題があるかもしれないのできちんと調べたほうがよさそうとのこと。
商人の街ブログ:Unityで遊んでみようか 第1回 Unityを起動せよ<Unity起動エラー対策(仮)>
誰かのメモ:Unity が起動しなくなった

ディスプレイアダプターのドライバーを更新

ディスプレイアダプターのドライバーのバージョンが古いと最新バージョンのUnityと
噛み合わない可能性があります。もしその場合は最新バージョンにアップデートしてみてください。私はここが問題だったようで更新したら解決しました。
Windows 7 で、ディスプレイアダプターのドライバーを更新する⽅法についてpdf
また、ディスプレイアダプターにIntel HD Graphics系を使用しており、WindowsUpdateが上手くいかない場合は以下のリンクに対処法がありましたのでご参照ください
taccumanote:Windows UpdateでIntel HD Graphics系の更新プログラムのインストールが出来ないときの対処法

最後に

今回は使いませんでしたが色々記事を検索しているとサポートセンターに連絡するとすぐ解決した、みたいな人もいらっしゃったのでどうしても分からない場合はサポートセンターにお問い合わせください。
ユニティ・テクノロジーズ・ジャパン合同会社:無料サポート
Unityはそれ一つで2Dゲームから3Dゲームまで簡単につくることができてしまうのでぜひDLしてお楽しみください!

Box Drive パブリックベータ版(Windows)を使用して見た

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

Box DriveはWindowsおよびmacOSで動作するデスクトップアプリケーションです。
ファイルの編集、検索、共有などをエクスプローラーや、Finder から操作することが出来ます。
イメージ的には、NAS(ネットワーク接続ハードディスク)を使用している感覚に近いと思います。

いままでのBox Sync との違いは、使用しているPCのHDDを圧迫しない。不要なファイルがPCに残らない。
※厳密にはアップロードやファイルを編集する時には一時的にはHDDを使っているようですが。

Box Drive

待ち望んでいたBox Drive(以前までは、Box for Desktopという名称の予定でした)が
パブリックベータではありますが、リリースしたので早速使ってみました。
詳しくはこちらを参照

enter image description here

使用上の注意点(Windowsの場合)

  1. Box SyncとBox Drive は同時に実行しない。Box Syncはアインインストールしましょう。
  2. Box Driveは、Windows 7 64ビットおよびWindows 10 64ビットのみをサポートします。 32ビット版とWindows 8.xはサポートされていません。 その他の注意点はこちらを参照して下さい。

こんな所が便利??

メールを送信する時、(普段の仕事で使用するときには、)基本的に共有リンクを使うのですが、
BOXにアクセス出来ない会社様の場合、メールに直接ファイルを添付して送信しています。ファイルがBOX上にのみある場合は、ダウンロードしてから、メールに添付する操作をしていましたが、直接ドラッグ&ドロップでコピーできます(貼り付けられます。)

enter image description here

その他 使用方法

共有リンク

Drive から、共有リンクを作成する方法は、
対象のファイル・フォルダで、右クリックすることで、BOX  >  Copy Link で共有リンクが取得できます。

enter image description here

検索

BOXには強力な検索機能がありますが、
それを使用するには、タスクトレイのBox Driveアイコンを選択するか
Ctrl + Shift + Alt + B で下図のような検索ウィンドウを表示して、検索を実施することが可能です。
残念ながら、エクスプローラー上から検索は出来ません。

enter image description here

個人的に残念な事。(今後に期待)

BOX の新UIからアカウント設定よりブラウザでBOXに接続した時に表示されるホームページ(初期ページ)の設定で「お気に入り」を選択出来るようになったことで、使いやすくなりましたが、Box Driveでの表示されるのは、「すべてのファイル」を選択した時と同じなので、表示が切り換えられる仕組みに期待しています。

enter image description here

まとめ

とりあえず、待ち望んでいたアプリケーションが出てきたので簡単に使用してみました。
まだファイルをロックしたり、ロック解除したりする機能も、パブリックベータ版には実装されていないようなので、今後のアップデートに期待しています。

Boxの販売パートナーもしてます。

enter image description here

お問い合わせは、こちら へ
BOXを使ったのアプリケーション開発も。

Rubyを書くときに気をつけたいこと

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

Ruby初心者の私がコードを書くときに気をつけていることをまとめてみました。

はじめに

 こんにちは。今年新卒で入社したエンジニアです。
Rubyを学習し始めてからインターンの数日を除くと1ヶ月半ほどになりますが、先日初めてコードレビューを行った際に先輩方から「Rubyらしいコードで書こう」との指摘をいただいたのを機に色々調査しながらコードの修正を行いました。基本的なことですが備忘録という意味も兼ねてまとめたいと思います。
 

目次

 1. 適切なメソッドを使う
 2. 目的と同じ実装をしてくれるライブラリを使う
 3. 読み手に分かりやすいように書く

1. 適切なメソッドを使う

 この記事のきっかけとなったコード修正で一番多かったのがこれでした。
Rubyには初めから便利なメソッドが多数用意されており、それを利用することでRubyらしくちょっとだけクールなコードを書く事ができます。
今回この記事を書くきっかけになった実装が文字列処理を含むものだったので、文字列自体の処理を簡素化して実際にコードレビュー前と後の差に似せて出してみようと思います。
stringという小文字とコンマで表された文字列をコンマで区切って全て大文字にして配列に格納するコードを例にします。

# 修正前
str = []
string.split(",").each do |s|
  str << s.upcase
end

ここで使ったeachは単に各要素を参照して処理を行うだけで戻り値に変化はありません。
このコードをmapを使って修正すると以下のようになります。

# 修正後
str = st.split(",").map {|s| s.upcase}

mapは各要素を参照して処理をしたあと、結果を新しい配列にしてくれます。
Rubyには同じような処理をするメソッドでも明確な違いを持ったメソッドが多数あります。

今回例に挙げた配列の要素の数だけ各要素を参照してブロックを実行するメソッドについて基本的なものをまとめておきます。

  • each 要素を順番に参照してブロック内の処理を行う
  • reverse 要素を逆順に参照してブロック内の処理を行う
  • map 要素を順番に参照してブロック内の処理を行い、各要素の処理された結果を新しい配列として作成
  • select 要素を順番に参照してブロック内に書かれた条件を満たすものだけ返す(ブロックが真を返す要素だけで配列を作成)
  • reject selectとは真逆で要素を順番に参照してブロック内に書かれた条件を満たさないだけ返す(ブロックが偽を返す要素だけで配列を作成)

自分が実装したい処理、目的と合うメソッドを使う事で処理をシンプルにまとめることができるので、もっと適切なメソッドがないか、使いやすいメソッドがないか考えながらコードを書くと自然とRubyらしいコードが書けるようになると思います。

2. 目的と同じ実装をしてくれるライブラリを使う

Rubyを使っているとよくgemという言葉を耳にします。
gemとはRuby用のライブラリやアプリケーションを指す言葉で、誰でも簡単に公開することができます。
それゆえ大量のgemが存在し、目的のものが見つかりやすいうえgemの中でも同じような実装をするものも多数あるので目的に合わせて好みのものを選んで使うこともできます。
よく使われるものでbundlerやrails、知名度が高いものの中でもnokogiriやkaminari、kakurenboなど親近感の湧く和名のgemもよく見かけますね。
gemはコマンド1つでインストール出来るうえ簡単に実装することも出来るので1から全てを実装せずに済みます。
実装に直接関わるものだけでなく、デバッグ時に役立つブレークポイントをつけてくれるgemや好きな時刻に変更したり、とある時刻で止めたりしてくれるgemなど多数存在します。
これらを活用すると実装のコードをシンプルにしたり時間効率を上げることももちろん可能になります。
何か新しく実装を加える時は似たような実装ないか探してみたら夢を叶えてくれるgemに出会えるかもしれません。

3. 読み手が分かりやすいように書く

 これはどの言語にも言えることですが、他の言語に比べてRubyはやる気さえあればどこまでもコンパクトに書けてしまう言語だと思っています。
ですがコンパクトに書く事だけに意識を向けてコードを書いてしまっては読み手にとっては難解なコードになりかねません。
※後述するFizzBuzzの最短コードは文字数を減らすのが目的で書かれているので説明がないとどういう処理なのか分からない人がほとんどだと思います。
私が分かりやすいコードにするために心がけていることは以下の2点です。

  • 変数やメソッド、クラスの命名
     多少長くなってもいいのでその変数が何で使われているのか、何を意味しているのかを見てわかるように命名する
  • 改行やスペースを活用する
     稀に巡り会うずらずらとスペースも改行もなしで何行にも渡るコードは、見にくくて時折書いた本人でも嫌になることもあるので、見やすいように書く

1点目はごく当たり前のことですが、私は実装を進めていると2点目を忘れがちで必死にコードをガリガリと書いてしまいます。
配列や括弧の中であれば普通に改行しても問題ないですが、改行したら文末と解釈されてしまって正常にプログラムが動作しないからどうしようもない!という場合があります。その時はバックスラッシュ(option+¥)を文末に入れることで「ここは改行されているけど文末ではない」と教えることが出来ます。
今挙げた2つのルールはプロジェクトによって明確にこうだと決まっていることが大半なので合わせて書くことも大切ですが、もし特に決まっていない場合のことも考えて自分ルールを作っておくとコードを書くときに迷わずに済むかもしれません。

最後に

 これらは基本中の基本で、この他にももっと留意すべき点や使うと便利なものはまだまだあると思いますが基本が一番大切だと思うので書かせていただきました。
私がインターン時に初めてRubyを学習した際に先輩からRubyは「クールに書く」「車輪の再開発は良くない」と言われたのを覚えています。
正直その当時はあまりピンと来ていなかったのですが、これらは今回の1、2に通ずるもので実際に書いて修正しながらコードを書いていくうちに言葉の意味が理解できてきました。
先輩方のようなシンプルでかつ読みやすい優しいコードが書けるようにこれからも学習していきたいと思います。
 

おまけ: FizzBuzz

 おまけ程度に書くつもりが結構なボリュームになってしまいましたが、私がRubyを初めて学習したときに見つけたFizzBuzz最短実装を目指す人たちのコードや記事が面白かったので紹介したいと思います。
※FizzBuzzとは1から100まで順番に数え、3の倍数の時はFizz、5の倍数の時はBuzz、15の倍数の時はFizzBuzzと言うゲームのことです。
ちなみにこのFizzBuzzをRubyで何も考えずに実装すると以下のようになります。

(1..100).each do |number|
  if number % 15 == 0
    puts "FizzBuzz"
  elsif number % 3 == 0
    puts "Fizz"
  elsif number % 5 == 0
    puts "Buzz"
  else
    puts number
  end
end

条件文をどうにかしたい。15の倍数はどうにか省略できないものかと試行錯誤して書いてみたコードが以下です。

(1..100).each do |n|
  str = "#{['Fizz'][n%3]}#{['Buzz'][n%5]}"
  str = n.to_s  if str == ""
  puts str
end

配列アドレスに剰余を入れる事によって割り切れるときつまり剰余が0のときに配列の0番目が呼び出されるので3の倍数ならFizz、5の倍数ならBuzz、15の倍数ならFizzとBuzzが両方呼び出されてもしどちらも呼び出されなかったら数値自身を入れて出力するといった実装です。無茶苦茶なコードですが私にはこれが限界でした。
ちなみにRubyを用いた最短コードが51byteで書かれたこのコードのようです。

1.upto(100){|n|puts'FizzBuzz
'[i=n**4%-15,i+13]||n}

面白かったのでこのコードを書かれた方が解説しているページのリンクを載せておきます。
perlだともっと短いコード(最短30byte)で書けたり、FizzBuzzを実装してくれるgemやRubyでもっと変わった方法で実装されている方も多数いました。興味があったら是非調べてみてください。

知っておきたいgitコマンド

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

 addやcommitなどのメジャーなgitコマンドは知っていたが、gitを使用した開発で初めてお世話になったコマンドがあったので、紹介したいと思います。

作業中に別の作業に変更する

 優先度の高い仕事が手元から離れて優先度が低い作業に取り掛かっている時に、優先度の高い仕事が再度自分の手元に戻ってきた場合にstashコマンドが役に立ちます。
 stashコマンドとは、現在作業しているブランチの作業内容を一時的に保存することや保存されているstashを取得することができます。以下で自分がよく使用したコマンドの一部を紹介したいと思います。

変更内容の保存
git stash
保存されている中で最新のstashを取り出す
git stash pop
 指定したstashを取り出すには、popの後ろにstash@{0}と指定する。0の所は、stashの番号を入力する。
保存されているstashの一覧表示
git stash list
保存されているstashのファイルを確認
git stash show stash@{0}
保存されているstashの全削除
git stash drop
 一部のstashのみ削除する場合は、dropの後ろにstash@{0}と指定する。

add,commitの取り消し

 自分がadd,commitの取り消しを初めて行う際に、変更内容まで消えてしまうのではないかと不安になった為、まとめました。

addの取り消し
git reset HEAD 「取り消すファイル名」
 こちらのコマンドは、変更内容はそのままでaddされた状態のみ取り消します。
最新のcommitの取り消し
git reset --soft HEAD^
 こちらのコマンドは、最新のコミットの取り消しを行います。変更内容はそのままです。今回は、オプションに--softを使用していますが、--hardを使用すると変更内容まで取り消してしますので注意が必要です。
ファイルの変更内容の取り消し
 git statusコマンドを使用すると、作業しているブランチの変更ファイル一覧が表示されるのですが、その中には変更内容に必要ないファイルがあることがあります。このような場合は、git checkout 「変更内容を取り消すファイル名」コマンドを使用するとファイルが変更前の状態になります。

gitのgrepコマンド

 grepコマンドは、ファイルの中の文字列を検索する場合によく使用します。先輩に言われるまでLinuxのgrepコマンドを使用していたのですが、gitにもgrepコマンドがあるということでgitのgrepを使用してみました。
linuxのgrepコマンド grep -r 「検索する文字列」 「探すディレクトリ」
gitのgrepコマンド git grep 「検索する文字列」
こちらの2つのコマンドを調べた結果、gitのgrepには、メリット・デメリットがあります。

  • メリット gitのgrepはリポジトリ以外を検索しない為、linuxのgrepよりも速く見つけることができる。
  • デメリット gitのgrepはリポジトリの中しか検索対象にならない為、linuxのファイルを確認することができない。また、検索する場合は、リポジトリのディレクトリに移動する必要がある。

まとめ

 今回は、自分が知らなかったgitコマンドについてまとめてみました。内容に関しては初心者向けの記事になりましたが、git初心者の方の参考になれば幸いです。

ゲーム分析手法入門

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

ゲーム業界でプランナーやりたいけどどういうことをすればいいのかわからないという人たちに向けて自分なりの分析方法についてまとめてみました。

はじめに

はじめまして
新卒でプランナーをやっていますモツ太郎です。
記事を書くことが決まってから何を書こうかなーと思い悩んでいましたが、自分がプランナーとしてやってきたことをつらつらと書いていきたいと思います。
というわけでまず初めにアプリ分析のやり方について記事にしたいと思います。
※あくまで個人のやり方です。

アプリ分析する意味について

おそらくこの記事を読んでいる人はプランナーってなにをしているのだろう?と思っている人が多いのではないかと思います。
プランナーと一概に言ってもその仕事は多岐にわたっており、一言で表すのは難しいですが、今回のアプリ分析に関してはプランナーがやる仕事のうちの施策を考えるというところに役にたつものだと考えています。
プランナーとしてやっていこうと思ったらなぜそれが面白いと感じられるのかというところをきちんと考えアウトプットできないと意味がありません。
そこで以前自分が先輩に教えてもらった分析資料のフォーマットを使いながらどういうところに注目しているのかというのを見ていきましょう。

分析内容

基本情報

enter image description here

上記の画像を見てみれば大体わかると思いますが、タイトル通り基本的なものしかないです。ただここからきちんと書き出しておくことは大切で、自分たちが作ろうとしているゲームとあっているのかという前提を確認するために必要になります。
例えば、コンシューマのゲームを作ろうとしているのにプラットフォームがスマートフォンのゲームを参考にしたところで的が外れたものになってしまいます。また産出国も同様で自分たちが日本でだしたいのにアメリカで売れているものを参考にしたところでやりたいことが違ってきてしまいます。そういう前提の条件を確認するためのシートになります。

調査・考察

enter image description here

ここではそのアプリが「誰に」「何を」させたいのかというところを見ます。
「メインターゲット」「コンセプト」のところですね。
この部分は新規で作るときに必ず大事になってきます。この部分がないとゲーム作るときになにをすればいいのかということが全く分かりません。
そして、それは一人ならいいのですが、チームで開発する際にみんなでどんなゲームを作りたいかという完成系のイメージの共有ができず、バラバラの方向を向かってしまいます。

更新頻度系はユーザーを飽きさせないためにどういう頻度でやっているというのはわかりますが、最初は優先度低くてもいいと思います。
ただ「各ユーザー層向けのマネタイズ&要素」は重要です。
結局は売り上げが立たないとアプリは続けることができないのでその分析しようと思ったものが「どうやって」続けていくことができているのかというところはきちんとつかみましょう。

遷移画像

enter image description here

初めから細かくやっていこうと思うと先が続かなくなるところです。
最初あまり細かくやらずに大雑把にできるようにしましょう。
大雑把にどういう画面の遷移をたどっているか、どういう機能がまとめられているかというところを見ることが重要です。

総評

enter image description here

そのアプリを分析してどういう印象を得たか、どういうことをやっていると感じたかをまとめます。
そして、なぜ売れていると感じたか、どういうところが他と差別化できており、売り上げにつながっているかをまとめていきます。

おわりに

今回ゲームの分析手法を紹介してきましたがいかがだったでしょうか。
もちろん細かくやっていくとキリはないのであくまで簡易のものとなっていますが、プランナーを目指す人達はぜひ一度やってみてほしいです。
また、一人でやるだけではなく周りの人たちと同じものを分析してみて最後に見せあうor話し合うということでほかの人の考え方を学ぶことで色々な人たちの考え方も知ることができ、今後のプランナーとしてやっていくうえで大事なことになると思うのでぜひやってみてくださいね。
そして今後ゲーム業界で働こうと思った時には役に立ててくれると幸いです。

BoxのAPIを使って見よう。(その2)~実際にBoxへ認可要求・アクセストークンを取得しAPIで情報取得

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

今回は、前回(その1) で説明出来なかった部分の補足となっています。

1.認可コード要求・応答

1.1. 認可コード要求・応答

リファレンスサイト を参照して頂ければ解決しますが、ポイントになる部分のみを、抜き出して書いておきます。
前回(その1) で説明をした下図の遷移に関しての補足となります。

enter image description here

以下ののURLに対して、パラメタを設定して送信することで、認可コードを得る事ができます。
■URL
https://account.box.com/api/oauth2/authorize

■パラメタ
response_type
  「code」固定です。
client_id
  認証を要求するアプリケーションのクライアントID
redirect_uri
  認証が完了した場合に、ブラウザにリダイレクトされるURL
state
  認証が完了した場合のリダイレクトURLに同じ文字列が返ります。攻撃からの保護のため、リクエスト時にランダムなハッシュ値を格納し、応答時に、同じ値が返却されてくるかチェックに使用すると良いでしょう。

■リクエスト例

https://account.box.com/api/oauth2/authorize?response_type=code&client_id=<MY_CLIENT_ID>&redirect_uri=<MY_REDIRECT_URL>&state=<MY_SECURITY_TOKEN>

client_id と、redirect_uri は、下図の登録したアプリケーションの構成情報から取得します。

enter image description here

実行すると、下図のBoxの認証画面が表示され、ログインすることで登録したアプリケーションでBoxにアクセス許可を求めてきます。
Boxへのアクセスを許可」を選択することで、認証コードを得ることができます。

enter image description here

1.2.認可コード応答

認可コードは、以下のパラメタに格納されています。

code=<認可コード>

2.アクセストークン要求・応答

2.1.アクセストークン要求

enter image description here

以下ののURLに対して、パラメタを設定して送信することで、アクセストークンを得る事ができます。
■URL
https://api.box.com/oauth2/token

■パラメタ
grant_type
  「authorization_code」固定です。
code
  認可コード応答で取得した認可コード
client_id
  認証を要求するアプリケーションのクライアントID
client_secret
  認証を要求するアプリケーションのクライアント秘密コード

■リクエスト例

curl https://api.box.com/oauth2/token \
-d 'grant_type=authorization_code' \
-d 'code=<MY_AUTH_CODE>' \
-d 'client_id=<MY_CLIENT_ID>' \
-d 'client_secret=<MY_CLIENT_SECRET>' \
-X POST

client_id と、client_secret は、下図の登録したアプリケーションの構成情報から取得できます。

enter image description here

実行すると、アクセストークン を得ることができます。

2.2.アクセストークン応答

アクセストークンは、JSON型の応答 access_token に含まれています。

{
    "access_token": "T9cE5asGnuyYCCqIZFoWjFHvNbvVqHjl",
    "expires_in": 3600,
    "restricted_to": [],
    "token_type": "bearer",
    "refresh_token": "J7rxTiWOHMoSC1isKZKBZWizoRXjkQzig5C6jFgCVJ9bUnsUfGMinKBDLZWP9BgR"
}

3.Boxファイル情報取得(アクセス例)

以下のように、リクエストヘッダに Authorization: Bearer YOUR_ACCESS_TOKEN をセットして
送信することで、各種操作が可能となります。

curl -H "Authorization: Bearer YOUR_ACCESS_TOKEN" \
https://api.box.com/2.0/files/123456789

まとめ

次回は、BOXのAPIを使って、EXCEL(VBA)から呼び出して見たいと思います。

RailsでLoggerを使ってLogローテション

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

RailsでLogローテーションについて学んだのでそれの備忘録兼、復習です。

はじめに

 初めまして、17新卒でエンジニアとして入社したむらさきです。
 4月にエンジニアとして入社し、Ruby on Railsを使用してwebサイトの改修や機能の追加などを行っています。入社前のインターンに参加するまでRubyもRailsもwebサイト構築もしたことの無かったのですが、この3ヵ月弱で色々なことを学んで少しずつですが成長を日々実感しています。
 さて、今回から記事を書くわけですが、他のエンジニアの方々のような難しいことを書く知識はないので、実際に仕事で制作した「Rubyでlogを作成してローテーションさせる」機能について復習を兼ねてまとめたいと思います。

開発環境

Windows10(64bit)  CentOS7.3.1611  Rails 4.1.4   ruby2.2.0

今回の目的

 今回は以下の2つを目的としていきます

  • 処理ごとに出力される内容をLogとして日ごとにファイルに出力する。
  • 出力したLogファイルを定期的に削除する。

目次

  1. CustomLoogerの作成
  2. Logへの出力方法
  3. Logのフォーマットを変更する
  4. 古いLogを削除させる
  5. crontabの設定

1.CustomLoggerの作成

 Logを書き出す方法はいくつかありますが今回はrubyに標準搭載されているライブラリのLoggerを使用します。
Logファイルを格納するフォルダを/public/custom_log/に作成して、その直下にcustom.logを日付ごとに作成していくようにします。
開発環境、テスト環境、本番環境によって記述する場所が違うので気を付けましょう。今回は開発環境で行うのでdevelopment.rbに記述します。

#config/environments/development.rb
config.custom_logger = logger.new('public/custom_log/custom.log', 'daily')

第1引数で作成するファイルの場所と名称を、第2引数で期間を基準に新しいファイルを作ってくれるようになります。

  • ‘daily’は1日ごと
  • ‘weekly’は1週間ごと
  • ‘monthly’は1ヵ月ごと

となっています。
※サーバーを起動した際の翌日の0時がトリガーとなっているようで、サーバーを起動している状態で日付を跨がないと新しいファイルが作成されないのでlocal環境で作成している人は注意が必要です。
うまく作成された場合は

custom.log
custom.log.20170620
custom.log.20170621
custom.log.20170622
・
・
・

という感じで.logの後に年月日が付いて作られていきます。今日作られたばかりのファイルには後ろに何も付きません。
 
 ちなみに、第2引数に整数、第3引数にサイズを指定することで、第3引数で指定したファイルサイズごとにファイルが作成され、第2引数で指定した数を超えた場合は古いファイルから削除させていくことができます。

config.contact_logger = logger.new('public/contact_log/contact.log', 4, 10 * 1024 * 1024)

今回の場合は日付ごとに管理したいという要望があったため、日にち指定の’daily’で実装していきますが、こちらには古いファイルを削除していく機能はないので後で別で実装する必要があります。自分またはチームが管理しやすい方法で実装してください。

2.Logへの出力方法

 Logに出力するにはcontrollerなどに以下の記述をします。

Rails.application.config.custom_logger.info("ここの内容をLogに出力します")

.info()は表示したいLogのレベルを表しており、

enter image description here

の5つに分類されています。指定したレベル以上のログを出力するようになります。debugを指定した場合はすべての情報が表示されるようになります。
.info()の中身はブロックや文字列が指定でき、その値がメッセージとして使用されます。

3.Logのフォーマットを変更する

 ここまでくれば希望した出力先にLogが吐き出せるようになっていると思います。
public/custom_log/custom.logを見に行くと下図のように出力できています。
enter image description here
しかし今のままだとLogの先頭に色々書いてあって少し見づらいですね。

ここで使えるのがFormatterです。
FormatterはLoggerのフォーマット文字列を扱うクラスです。

call(severity, time, progname, msg) -> String
ログ情報をフォーマットして返します。
[PARAM] severity:
  ログレベル。
[PARAM] time:
  時間。Time クラスのオブジェクト。
[PARAM] progname:
  プログラム名
[PARAM] msg:
  メッセージ。

 https://docs.ruby-lang.org/ja/latest/class/Logger=3a=3aFormatter.html

ドキュメントにある様にcallメソッドの4つの引数によってフォーマットを変えられます。今回はserverity, time, prognameは必要なく、msgだけあればいいので

#config/environment.rb
# Load the Rails application.
require File.expand_path('../application', __FILE__)

#ここから記述
class CustomLogger
  class Formatter
    def call(_severity, _time, _progname, msg)
      "#{msg}\n"
    end
  end
end
#ここまで記述

# Initialize the Rails application.
Rails.application.initialize!

と書き込めばmsgだけが表示されるようになります。
あとはこれをcustom_loggerにセットします。

#config/environments/development.rb

config.custom_logger.formatter = CustomLogger::Formatter.new

こうすることでLogのフォーマットが変更されているはずです。実際に確かめてみましょう。
enter image description here
ちょっと画像が見づらいですが、前についていたものがなくなって変わっていることが確認できました。

4.古いLogを削除させる

 上記までの方法でLogを出力する機能の実装は完了しました。
「1.CustomLoggerの作成」の部分で触れましたが、’daily’等の日付を引数にした場合はローテーションで削除していく機能はありません。なのでcronを使用して自動的に古いファイルを削除していく機能を最後に実装していきます。
 いきなりcronという言葉が出てきましたが、知らない人のために説明しておくと(自分も知りませんでしたが)、UNIX系システムの常駐プログラム(デーモンの一種)で、ユーザーが設定したスケジュールに基づいてコマンドやスクリプトを自動で実行してくれるすごいやつらしいです。起動や設定方法まで書くと長くなってしまうので各自で調べてください。
 とりあえず今回はlib/tasks/にlog_rotate.rbを作成してそこに削除用のスクリプトを書き込んでいきます。

#lib/tasks/log_rotate.rb
module Tasks
  module LogRotate
    require 'fileutils'
    require 'active_support'
    class << self
      def rotate
        time = Time.current.months_ago(3).strftime('%Y%m%d%H%M%S')
        log_all = Dir.glob("#{Rails.root}/public/contact_log/*")
        log_all.each do |i|
          if File.stat(i).mtime.strftime('%Y%m%d%H%M%S') < time
            FileUtils.rm_f(i)
          end
        end
      end
    end
  end
end

他にもっと簡潔な書き方があるとは思いますが、自分はこのような感じで書きました。

  1. 3ヵ月前の年月日時分秒を取得してtimeに入れます(例:20170322155030)
  2. 作成されたLogファイルすべてを配列にしてlog_allに入れます
  3. そのファイルを1つずつ最終更新時間を年月日時分秒で取得してtimeと比較します
  4. timeよりも値が小さい(古い)場合はそのファイルを削除させます

これでこのスクリプトを呼べば3ヵ月前より古いファイルを削除できるようになりました。

5.crontabの設定

 さて、これで最後の実装です。cronに先ほどのスクリプトを動かしてもらうためにcrontabに設定を書いていきます。
 毎月1日に1度先ほどのスクリプトを走らせます。時間は0時ちょうどだと他のものが走っていたりした場合にサイトが重くなってしまう可能性があるので深夜3時5分頃に走らせるようにします。

% crontab -e

でエディタが起動して設定を書き込むことができます。

% crontab -r

としてしまうと確認もなく今まで設定していたものがすべて消去されるので注意が必要です!
‘e’と’r’はキーボードで隣り合わせなのでうっかり押し間違えないようにしましょう(っていうのがどこのサイトにも書いてあったので自分も言ってみたかった)

*/5 03 1 * * /bin/bash -lc 'cd /アプリケーションのディレクトリ && bundle exec rails runner Tasks::LogRotate.rotate'

分 時 日 月 曜日 で並んでおり*/5とすると5分おきとなります。曜日は0-7で設定でき、0と7が日曜日で1=月曜, 2=火曜…と続いていきます。
その後ろで自分が作っているアプリケーションのディレクトリまで移動し、runnnerでスクリプトを起動します。
すぐに確認したい場合は

*/1 * * * *

とすることで1分おきに起動させられます。

これで、Logの出力とローテーションでの削除が実装できました!

おわりに

 今更ですが自分の環境でのことを書いたので環境次第では動作が上手くいかない等あるかもしれません。それでも誰かの助けになっていれば幸いです。
 コードの細かいところとか全然理解できてないことだらけですがこれからも実際に使ったことを備忘録兼、復習として書いていきたいと思います。ここまでご覧いただきありがとうございました。
 さて、1行前に言ったことは忘れて、次は息抜き的なことを書こうかな(。・ ω<)ゞ

ELBでSSLオフロードしている場合のhttpアクセスをlocalhostで偽装する

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

ELBでSSLオフロードする構成を組んでいる状態で配下のEC2インスタンス自身からlocalhostのhttpを叩きたい場合のTipsです。

前提

以下の記事のように、ELBでSSLオフロードして、配下のEC2インスタンスへは常にhttpでアクセスされる構成にしている。

http://qiita.com/snoguchi/items/f5ccb67592f87942480d

問題

ELB配下のEC2インスタンスにcurlでhttpアクセスしたいけど、nginxの設定でhttpでアクセスされたらhttpsにリダイレクトする設定してるため、自分自身のlocalhostに対してhttpのurlを叩けなくて困ったりする。

たとえば、railsのインスタンスが稼働しているか単純に確認したくてヘルスチェックを叩いてみたくても

$ curl http://localhost/healthcheck
<html>
<head><title>301 Moved Permanently</title></head>
<body bgcolor="white">
<center><h1>301 Moved Permanently</h1></center>
<hr><center>nginx</center>
</body>

のようにリダイレクトされてしまう。

対処方法

ELBでSSLオフロード済みのhttpはヘッダに X-Forwarded-Proto: https がついてくるのでこれを明示的につけてあげれば良い。

$ curl -H "X-Forwarded-Proto: https" -v http://localhost/healthcheck

参考

pythonで梅雨対策

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

pythonで梅雨対策をします。
技術力が低いので、役に立つ技術記事はかけません。
その代わり、ちょっとだけ便利なものを手軽に作ります。

ざっくり概要

  1. APIから天気情報を取得
  2. いろいろする
  3. slackに投げる

結果

一時間後の天気がザーザー降り以上ならslackに通知するbotができました。
enter image description here

ちなみに、強さレベルで言うと
ザーザー<土砂<バケツ<滝<恐怖
となっています。恐怖が最強です。

APIから天気を取得

お天気APIは色々あって、OpenWeatherMapやDark Sky APIなど海外のものも触ってみたのですが、日本の詳細な天気が時間単位で取れなかったり、SSHがうんたらで怒られたりしたので、結局Yahoo! JAPANさんのYOLP 気象情報APIを使います。
ちなみに緯度経度が使えるので、大雑把に会社の近くの緯度経度にしました。
安心です。

色々する

APIから天気情報を取得して色々します。
簡単に言うと、APIからrainfallを抜いてきます。
rainfallは、どうやら降水強度という指標らしいです。
降水強度では分かりやすい目安がすぐに見当たらなかったので、似たような概念の時間降水量を参考に、rainfallをわかりやすくします。

気象庁に分かりやすい指標がありました。
上に書いた雨の強さレベルもこれに基づいてます。
http://www.jma.go.jp/jma/kishou/know/yougo_hp/amehyo.html

slackに投げます

Incoming Webhookというものを使います。

雑記

コード自体は単純ですが、APIの選定が地味に面倒でした。
せっかく作ったので、cronで回して、折りたたみ傘でも買って会社内でレンタル傘屋でもやろうかと思ったのですが、YOLPさんは商用利用に申請が必要そうなのでやめました。
では、良き梅雨を。

以下コード

メイン

# get_rainfall.py
import requests
import slack_post


def main():
    url = build_url()
    json_data = request_json(url)
    in_one_hour_rainfall = extract_rainfall(json_data)

    if in_one_hour_rainfall >= 10:
        rainfall_notice = notification_level(in_one_hour_rainfall)
        slack_post.post(rainfall_notice)


# url組み立て
def build_url():
    APP_ID = "YOLPのAPIキー"
    BASE_URL = "http://weather.olp.yahooapis.jp/v1/place"
    COORDINATES = "139.709008,35.669968"  # 緯度経度
    OUTPUT = "json"

    url = BASE_URL + "?appid=%s&coordinates=%s&output=%s" % (APP_ID, COORDINATES, OUTPUT)

    return url


# リクエスト
def request_json(url):
    req = requests.get(url)
    json_data = req.json()

    return json_data


# 降水強度の取得
def extract_rainfall(json_data):
    weather = json_data['Feature'][0]['Property']['WeatherList']['Weather']
    in_one_hour_rainfall = weather[1]['Rainfall']

    return in_one_hour_rainfall


# 降水レベル
def notification_level(in_one_hour_rainfall):
    if in_one_hour_rainfall >= 80:
        return "恐怖"
    elif 50 <= in_one_hour_rainfall < 80:
        return "滝"
    elif 30 <= in_one_hour_rainfall < 50:
        return "バケツ"
    elif 20 <= in_one_hour_rainfall < 30:
        return "どしゃ"
    elif 10 <= in_one_hour_rainfall < 20:
        return "ザーザー"


if __name__ == "__main__":
    main()

スラックになげる処理

import requests
import json


# slsckにpostするスクリプト
def post(text):
    requests.post('slackのAPI関連', data=json.dumps({
        'text': "一時間後に " + text + "降りの雨が降ります",  # 投稿するテキスト
        'username': 'baguette',  # ユーザー名
        'icon_url': 'http://2.bp.blogspot.com/-mhOboAyB0eA/VfS6MnLrttI/AAAAAAAAxOM/rqBqjtoezJ4/s800/fashion_ame_zubunure.png',  # プロフィール画像
        'link_names': 1,  # メンションを有効にする
        })
    )

フリップフロップと聞いてRubyを思い浮かべる方法

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

フリップフロップと聞いて、いきなりRubyやPerlの話を始める人はいないと思います が、今回の記事はRubyのフリップフロップのお話です。 論理回路のフリップフロップもRubyのフリップフロップも一度に確認できちゃうお得な記事にしたいと思います。

はじめに

みなさん初めまして、新卒エンジニアのくろすです。
今回の話、決してFlip Flopやフリップフラッパーズ、RWBYの話ではございませんのでご注意を。
個人的には3Dモデリングとかやってる人にRWBYの話とかして欲しかったりしますが。

そもそも フリップフロップ とは

flipflop とは (洗濯物・旗・サンダルなど)パタパタなる音、とんぼ返り、宙返り、(意見などの)急変、豹変(ひょうへん)、フリップフラップ [出典:Weblio]

なんのこっちゃわかりませんね。
とりあえず今回は普通の人(?)ならまず思い浮かべるであろうフリップフロップ回路の話から始めたいと思います。
要するにフリップフロップを使うと電源がある間は情報の保持が可能であるって話。
いきなり回路の話ですので、興味ない方は読み飛ばしておいていただけると。

メモリ って?

まずはエンジニアでない方でも聞いたことがあるであろうメモリの話から始めたいと思います。
メモリとはなんぞ?って質問にはとりあえずパソコンに入ってる4GBとか8GBとかの方のやつ。
くらいに思っておいてもらえればいいかと思います。

ざっくり言うとメモリには2通りの種類があり揮発性メモリと不揮発性メモリに分けることが可能です。

  • 不揮発性メモリ 電源の供給がなくても情報の保持が可能であるメモリ
  • 揮発性メモリ 電源の供給がないと情報の保持ができないメモリ

この揮発性メモリにはまた種類がありその中にはDRAMとSRAMと呼ばれる種類のものがあります。
DRAMは今回の話にあまり関係ないのでざっくりとしか紹介しませんが、
DRAMとはDynamic Random Access Memoryの略でコンデンサに電荷を蓄え、その電荷の有無で1bitの情報を記憶する半導体メモリです。この電荷をリフレッシュと言う作業で蓄え続けることによって情報を維持しています。
よくパソコンに刺すメモリなんかはこちらが多いかと思います。
そしてSRAMですがDRAMと比較して、回路が複雑でコストが高いがリフレッシュ作業がない分高速で消費電力が小さいと言う特徴を持っています。
SRAMとはStatic Random Access Memoryの略で、リフレッシュ作業がないことからStaticとの名前がついています。

フリップフロップ

さてこのSRAMの記憶部にはフリップフロップ回路というものが使われています。
ようやく出ましたね、フリップフロップくん。
最も基本的なフリップフロップはRSFFと呼ばれるもので以下の回路図で表されます。

enter image description here

Sがセット、Rがリセットで各入力に対する結果は以下のようになります。

SRQ¬Q
00前の状態を保持前の状態を保持
0101
1010
11禁止禁止

上の結果を見てもらえればわかりますが、セットSが立ち上がると無条件で出力は1に、リセットRが立ち上がると無条件で出力は0になります。出力の状態により(0, 0)を入力した際の状態が変わりますが、出力は直前の出力を保持します。
これがフリップフロップ回路が1bitの情報を記憶するメカニズムです。
一瞬の電気信号を回路自身がデータとして保持し続けるということなのですね。
※ ちなみにSRFFで(1, 1)入力は禁止です。これは入力を(1, 1)から(0, 0)に変化させた場合に、出力が(1, 0)で安定するか(0, 1)で安定するかが定まってないため禁止となっています。

Rubyのフリップフロップ

文字数稼ぎのはずが筆が乗りました。
ようやく本題です、むしろ本題の方がしょっぱい気さえします。

とりあえず、以下のコードを見てください。

string = "これからもよかったらかくりよの門をよろしくお願いします"
string.each_char do |char|
  if (char ==  'よ')..(char == 'よ')
    print char
  end
end

このコード実行するとこんな結果が帰ってきます。

よよよ

まぁ、見た感じそうなるでしょうって結果ですね。
次に上のコードそっくりだけどドットの数が違うだけの以下のコードを実行してみます。

string = "これからもよかったらかくりよの門をよろしくお願いします"
string.each_char do |char|
  if (char ==  'よ')...(char == 'よ')
    print char
  end
end

すると結果はこうなります

よかったらかくりよよろしくお願いします

ややっ、これは由々しき事態です。
どうしてこうなるのか、というのはだいたいリファレンスに書いてありますが説明していきます。

範囲式とは

リファレンスを読む限りではRangeクラスのインスタンスを生成する式のことを範囲式と言っているように思えます。

(a) 式1 .. 式2
(b) 式1 ... 式2

条件式の外側で使うと式1から式2までの範囲を表すオブジェクトを返してくれます。
また、(b)の書き方をすると範囲オブジェクトは式2の値を含みません。
Rangeクラスのリファレンスを見てもらえるとわかりますが、上の2つはRangeクラスのインスタンスとして宣言することも可能です。

(a) Range.new(式1, 式2, false) # default値がfalseなので実際はfalseいらない
(b) Range.new(式1, 式2, true )

ここで覚えておいて欲しいのは(b)式の場合は範囲オブジェクトが終端を含まないという点です。

条件式として範囲式を使う

さて、今回問題としているのは条件式として範囲式を使った場合です。
先に説明した、フリップフロップ回路の特性である「回路自身が状態を記憶する」ことと、範囲オブジェクトの終端の話を念頭に置くと理解しやすいかと思います。
少なくとも私は理解しやすかったです。
先ほども登場した範囲式についてのリファレンスには以下のように書いてあります。

「..」の場合:
1. 初期状態では式1だけを評価し、式1が真を返すまでは false を返します。
2. 式1が真を返すと true を返します。式2が真なら初期状態に戻ります。
3. この後は式2だけを評価し、式2が真を返すまで true を返します。
4. 式2が真を返すと true を返したあと、初期状態に戻ります。

「…」の場合:
1. 初期状態では式1だけを評価し、式1が真を返すまでは false を返します。
2. 式1が真を返すと true を返します。
3. この後は式2だけを評価し、式2が真を返すまで true を返します。
4. 式2が真を返すと true を返したあと、初期状態に戻ります。

つまりこの2つの違いは式1が真を返した時式2をその場で評価するかにあります。

(b)式の場合は終端である式2をその場で評価しないのですね。
そして、式2がtrueを返すまでの間は範囲式自身がtrueであるという状態を記憶してtrueを返します。
RSFFでいうなら、式1が入力S、式2が入力Rと考えながら見ると入力が(1, 0)
Rubyだとnilとfalse以外は全てtrueなのでこれはマズイですね。
入力が(true, *)の時に出力はtrueとなり範囲式としてはtrueを維持するようになります。
次からは式2を使い値を評価した結果、入力が(*, true)ならリセットが立ち上がり、
その場では範囲式の出力としてtrueを返した後に、範囲式の出力をfalseとして保持する
と言った具合です。

まとめ

(a) 式1 .. 式2
(b) 式1 ... 式2

今回の話は結局RSFFで禁止されていた(1, 1)入力、つまり(true, true)に対する出力とその時保持する値をどう定義したか?
っていうのに繋がる話なんですよね。

  • (a)式の場合 trueを返しfasleを保持している だから次に評価されるのはセットである式1
  • (b)式の場合 trueを返しtrueを保持している だから次に評価されるのはリセットである式2

以上のように定義されているのがrubyのフリップフロップというわけです。

ここまで読んでいただけたら、フリップフロップからRubyを連想できるようになり、かつ「式」という漢字がゲシュタルト崩壊を起こしていることでしょう。

BoxのAPIを使って見よう。(その1) ~概要とAPIのことについて

0

この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。

Box API を使う上でのポイント4つ

  1. RESTful API
  2. JSON
  3. OAuth2.0
  4. Box Developer アカウント

1.RESTful API とは

ウェブシステムのHTTPでの呼び出しインターフェース
GET、POST、PUT、DELETE等のHTTP標準のメソッドを使い、「何を」「どうする」というようにシンプルな表現されのが特徴です。

a.URL

https://api.box.com/2.0/files/123456789
  files の中の ID:123456789 のファイルを取得
https://api.box.com/2.0/files/123456789/versions
  files の中の ID:123456789 のファイルのバージョンを取得

b.HTTPメソッド(他にもありますが、今回は以下の4つ)

GET
  リソースの獲得
POST
  リソースの作成
PUT
  リソースの更新(状態変更)
DELETE
  リソースの削除

c.curl(データを転送するライブラリ) を使った例

$ curl -X GET https://api.box.com/2.0/files/123456789 

curl については、こちら 見て下さい。

2.JSON とは

JSONとはJavaScript Object Notationの略で、XMLなどと同様のテキストベースのデータフォーマットです。
{} (カッコ)で括られている文字で、整形すると下記のようになります。

  {
      "entries" : [
          {
              "created_at": "2012-08-20T10:20:30-07:00",
              "id": "672259576",
              "modified_at": "2012-11-28T13:14:58-08:00",
              "modified_by": {
                  "id": "183732129",
                  "login": "sean+apitest@box.com",
                  "name": "sean rose",
                  "type": "user"
              },
              "name": "Dragons.js",
              "sha1": "359c6c1ed98081b9a69eb3513b9deced59c957f9",
              "size": 92556,
              "type": "file_version"
          }
      ],
      "total_count": 1
  }

3.OAuth2.0 とは

a.概要

HTTP上で認可を行うためのプロトコル
通常、ログインが必要なサービスを利用する際はログインID/パスワードの情報が必要になります。
下図のようなサイトの場合、あまり問題にはなりませんが、

enter image description here

下図のようにウェブサーバ経由で、BOXへの操作を行う際、
ウェブサーバにBOXのID/パスワードを格納してしまうのは、セキュアな状態とは言えません。
それを解決するための仕組みとして使われるのが OAuth2.0 です。

enter image description here

b.一般的なフロー

利用者によって、BOXのログイン認証を行い、そこで得られるアクセストークンを使用して、
BOX のAPIを使って、各種操作を実行することで、ウェブサーバにID/パスワードを格納する必要がないのです。

enter image description here

4.Box Developer アカウント

Boxの開発を行う上で、デベロッパーサイトよりアカウントを作成して、アプリケーションを作成するため初期設定を行いましょう。

(1)Box Developers サイトより、アカウントを作成して下さい。

enter image description here

(2)マイアプリより、アプリの新規作成を選択

enter image description here

(3)アプリの種類を選択(ここでは、企業統合を選択しておきます)

enter image description here

(4)認証方法を選択(ここでは、標準OAuth2.0(ユーザー認証)を選択しておきます)

enter image description here

(5)アプリの名前をつけて、完了(あとで変更も可能です)

enter image description here

アクセストークン取得に必要な情報

構成情報から、クライアントID、クライアント秘密コード、リダイレクトURLをコピーして下さい。

enter image description here

BOX API reference

BOXでは、下図のようなリファレンスサイトが用意されています。

enter image description here

まとめ

次回は、BOXのAPIを使って、実際に簡単な情報取得処理を作成していきます。

最近人気な記事