ESM アジャイル事業部 開発者ブログ

永和システムマネジメント アジャイル事業部の開発者ブログです。

Rubyでprivateなクラスメソッドを定義するには

先日、privateなクラスメソッドを定義しようとして、つまづきました。 なので、僕が実装に失敗したパターンと正しい実装方法を記載したいと思います。

失敗パターン

まず、僕が実装に失敗したパターンです。何事もなく呼び出せてしまっています。

class C
  private

  def self.def1
    p 'def1'
  end
end

C.def1 # "def1"

正しい実装方法

Module#private_class_methodを使う場合

次に、正しく実装した場合です。想定通りdef1がprivateメソッドになっているので、呼び出すことが出来ませんでした。

class C
  def self.def1
    p 'def1'
  end

  private_class_method :def1
end

C.def1 # a.rb:9:in `<main>': private method `def1' called for C:Class (NoMethodError)

class << selfの内部でprivateを指定する場合

また、class << selfの内部でprivateを指定しても、定義することが出来ました。

class C
  class << self
    private

    def def1
      p 'def1'
    end
  end
end

C.def1 # a.rb:11:in `<main>': private method `def1' called for C:Class (NoMethodError)

結論

privateなクラスメソッドを定義するには、Module#private_class_methodを使用する、class << selfの内部でprivateを指定するの2パターンの方法があることが分かりました。

RubyKaigi 2016 に参加していました

どうも、muryoimpl です。9/8 から 9/10 にかけて開催された RubyKaigi 2016 に総勢15名で参加してきました。

Bento Sponsor をやりました

事業部として3日に渡ってブースを出したり、 2日目の Bento Sponsor でお弁当を配ったりもしました。

f:id:muryoImpl:20160920023551j:plain

ブースでは、3 日間で 800 個阿闍梨餅を用意し、皆さんのお越しをお待ちしておりました。用意した阿闍梨餅は、全てお召し上がりいただけました。ブースに立ち寄ってくださった方、質問してくださった方、陳列されていた私をいじってくれた方ありがとうございました!

事業部の名にある「アジャイル」と「あじゃり」をかけたダジャレとわかってもらえる予定が、存外わかってもらえずにダジャレの説明を求められるという3日間を過ごしました……

Bento Sponsor としては、お弁当の配布と、のし紙に弊社のロゴを模したちょっとしたコードをつけてアピールさせていただきました。

アジャイル事業部ホームページのエントリ にコードが掲載されていますので、まだ見ていない方は是非読み解いたり実行してみたりしてください。

2日目 『Learn Programming Essence from Ruby patches』 by Mitsutaka Mimura

弊社の三村が上記のタイトルで発表をしました。 動画やスライドへのリンクは RubyKaigi 2016 Schedule Sep. 9 で観ることができるので、是非観てください。 大学で学習したようなアルゴリズムやどこかで読んだコードというのは思いがけないところで自分の礎になっている、というのはそのとおりですね。改めてコードの多読やアンテナを張っていろんなものを知っておくのは大事だな、と思いました。

セッションについて

今回の RubyKaigi では、今後の Ruby に対する Proposal や、Ruby に加わった変更について興味深く聴きました。

Matzの講演 では、実際のところどうなるかはわかりませんが、速度についての話はなくなって、より静的解析ツール寄りになってきたのかな?という印象をもちました。笹田さんの Guild の提案 も取り込まれると、スレッドを使うときに意識しなければならないことが減ってよさそうですね。

Fixnum と Bignum が Integer に統合された けれども一部を除き Ruby のレイヤーでは影響が少ないこと、upcase/downcaseの挙動が 2.4 で変わる ことについてはお仕事で遭遇しそうな情報なので、特に気になりました。

『Fearlessly Refactoring Legacy Ruby』で出てきた suture という gem がドキュメントがしっかりしていて、使うことになれば試してみたいなと思いました。でもそうならないようにテスト書いてメンテナンスするのが大事ですよね。

今回 mruby についての発表も多かったので、mruby 触ってみる詐欺になっている私はそろそろ mruby-cli を使って何か作ってみるタイミングなのかもしれない……

さいごに

RubyKaigi 2016 の運営に携わっていた皆様、発表者の皆様、興味深い話を聴ける場を提供してくださってありがとうございました。 また、ブースに立ち寄ってくださった皆様、お弁当ののし紙に興味をもってくださった皆様ありがとうございました。またお会いしましょう!

Rails5でミドルウェアの位置を変える

こんにちは、hibariya です。先日から、自分のかかわっている Rails アプリを 5.0.0 にアップグレードしています。そのときに意外な箇所でつまずいたことを書きたいと思います。なお、全体的なアップグレードについては公式の A Guide for Upgrading Ruby on Rails や、Release Notes、willnet さんの スライド が参考になります。

そのプロジェクトでは、理由あっていくつかのミドルウェアRails::Rack::Logger より手前にもってくる必要があります。アップグレードする前の 4.2 では次のような操作をすればミドルウェアの位置を変えられました。

# config/application.rb

# 中略...
    config.middleware.delete ActionDispatch::Cookies
    config.middleware.insert_before Rails::Rack::Logger, ActionDispatch::Cookies
# 中略...

ところが 5.0.0 ではある理由によりミドルウェアの削除操作が最後にまとめて実行されるようになりました。そのため、上記の操作は見た目どおりに読めば「ミドルウェアAを削除してBの手前に挿入」ですが、5.0.0 では「ミドルウェアAをBの手前に挿入して、最後にスタックの中のミドルウェアAをすべて削除」という意味になります。

経緯としては、Rails は Rack::Runtime がスタックに存在することを想定しているため、アプリケーション側で Rack::Runtime を削除すると Rails の起動時に例外が発生してしまうという問題があり、その対応としてこの変更があったようです。その影響により、削除して挿入しなおすというやり方ではミドルウェアの位置を変えられなくなりました。

手元では、一時的な対応としてミドルウェアを移動する操作を追加しました。

# config/application.rb

# 中略...
module MyRailsApp
  module MiddlewareStackProxyExtension
    refine Rails::Configuration::MiddlewareStackProxy do
      def move_before(dest, src)
        operations << [:delete, [src], nil] << [:insert_before, [dest, src], nil]
      end
    end
  end

  class Application < Rails::Application
    using MiddlewareStackProxyExtension

    config.middleware.move_before Rails::Rack::Logger, ActionDispatch::Cookies
    config.middleware.move_before Rails::Rack::Logger, ActionDispatch::Session::CookieStore

    # 中略...
  end
end

この変更についての記述はあまり目立たないこともあり、私は気付くのに少し時間がかかりました。ミドルウェアの位置を変えるような Rails アプリのアップグレードを行なう際の参考になればと思います。

合言葉は「デブオプス!!」 牛尾剛さんをお呼びして DevOps 勉強会を開きました

みなさんこんにちは!今年 8 月をもって無事に永和 4 年生に上がった @yucao24hours です。

多彩なご経験とパワフルな「デブオプス!!!!!」の掛け声で有名な(?)牛尾剛さんをお呼びした社内勉強会が、8 月 26 日(金) に弊社にて開催されました。

牛尾さんといえば... わたしは Agile Japan 2016 ではじめて牛尾さんの講演を直接聴き、そのインパクトの大きさと感動を自分のブログにぶつけていた過去があります。

Agile Japan 2016 に参加してきた #agilejapan | 走る http://www.yucao24hours.me/2016/06/02/agile-japan-2016-report/

そんなわけで今回の勉強会は本当に楽しみで、勉強会直前に会社のエントランスで牛尾さんと鉢合わせたときは一瞬頭が停止してしまったほどでした。


「今日の勉強会はやりづらいなあ〜。だってキミらもうアジャイルとか DevOps とか知ってんねやろ、何話したらええんや!」

という牛尾さんの苦笑まじりのセリフからはじまった勉強会。

われわれ参加者(アジャイル事業部の面々)はアジャイル開発の基礎知識や経験がすでにあるだろうからということで、牛尾さんはまず DevOps にまつわるいくつかのテーマを提示してくれました。

そしてそこからわたしたちが聞きたいと思ったものをいくつかピックアップし、そのテーマに沿ってお話してもらうという、なんともゼイタクなスタイルの勉強会になったのです。

冒頭にもふれた Agile Japan 2016 でわたしが感化された DevOps ジャーニーのお話、牛尾さん自身が実際に目で見て体感してきた DevOps 実践チームのレポートなど提示してもらったテーマ群のうちから、今回は DevOps についておさらいするための "基礎知識編" と、Microsoft Azure のライブデモもふんだんに盛り込んでの "現場実践編" 、そして実際に DevOps を取り入れているチームの興味深い "レポート編" といった感じでお話いただきました... あれ、結局最初に提示いただいていたものほとんど全て話していただいていましたね!

いろいろな角度からのためになるお話を聞かせていただき、感謝です(_ _)

f:id:yucao24hours:20160905192953j:plain

ほぼ 2 時間休憩なしで熱く語ってくれた牛尾さん。本当にありがとうございます!

終わった後は永和のスグ近くにあるお店で牛尾さんを交えて懇親会を行いました。乾杯のかけ声はもちろん「デブオプス!!!!」ですよ!

勉強会での牛尾さんのアツいお話に影響されて、永和メンバーもふだんの開発に関する課題や気づきについての話でたいそう盛り上がり、濃密な意見交換の機会となりました。

f:id:yucao24hours:20160905193246j:plain

Microsoft DevOps エバンジェリストとして日々活躍なさっている牛尾さんによるわかりやすいお話のおかげで、DevOps への理解と親近感が以前より増したように思います。

あと、 Microsoft Azure がなんやらすごいことになっててびっくりしました。UI は綺麗だし便利機能満載だし、よさそう。。

牛尾さん、貴重な会をありがとうございました。またこうして、いろいろなエキスパートの方にお話をうかがってみたいですね。

SpeeeCoffeeMeetup01 で adhoq を Rail5 に対応させた話を LT してきました

今月の頭に行われた SpeeeCoffeeMeetup01 へ参加するために、LT スピーカーとして登録し、発表してきました。 (いろいろあって、資料の公開がこの時期になってしまった…)

内容は、弊社の GitHub で公開している adhoq という RailsEngine を Rails5 に対応させた時のお話です。 Rails アプリケーションを Rails5 に対応させたお話はよく見かけると思い、RailsEngine を対応させてみたという話をしてみました。

スライド中で紹介している通り、adhoq は簡易的な集計レポートを作成するための SQL 発行を Rails アプリの画面でできるようにするための Gem です。 id:moro が作成したのを最近はわたしが細々とメンテしております。 RailsAdmin のようなアップデートまでできちゃう管理画面はいらないが、かといってデータを集計するためのシステム構築はできていないような状況のプロダクトに導入しておくと便利だと思います。 また今わたしがやっているプロジェクトでは、サーバへ乗り込まずにデータの調査をするために活躍しています。

なお、わたしの次の発表予定は 9/9(fri) となっているようです。その際はよろしくお願いします。

Google Apps Script で esa.io の記事を更新する

こんばんは。 @hrysd です。

弊事業部には @takkanm が管理しているアカウントリストというスプレッドシートがあります。 これには、メンバーが各サービスで使用しているアカウント名等が集約されていて新しいメンバーが増えた時なんかに更新されています。

スプレッドシートどこにあるの問題

スプレッドシートの URL を覚えていないので、どこにあるのか全く見当がつかないという理由から、 日常的に使用している esa.io に貼り付てみました。

f:id:hrysd:20160729185145p:plain

これだとスプレッドシートの内容で検索する事が出来ないため、Google Apps Script を使用してスプレッドシートの中身と記事の更新を連動させたいと思います。

Google Apps Script を書く

スプレッドシートを開きツールバーツール > スクリプト エディタ を開く事で Web 上から編集を行う事も出来ますが、npm のモジュールを使用したい等の理由から手元のTerminalで作成していきます。

$ mkdir post_to_esa && cd post_to_esa
$ npm init -y
$ npm install -D browserify gasify
$ npm install -S markdown-table

実際に記述したコードが以下になります。 内容としてはスプレッドシートをマークダウン形式のテーブルに変換して、esa.io の記事を更新するというものです。(POST_ID と ACCESS_TOKEN をベタに書いているけど、うまい方法がわからなかった...)

var table = require('markdown-table');

var POST_ID = 12345;
var ACCESS_TOKEN = 'ACCESS_TOKEN';

global.myFunction = function() {
  var sheet  = SpreadsheetApp.getActive().getSheetByName('シート1');
  var rows   = sheet.getDataRange().getValues();

  var stringifiedPayload = JSON.stringify({
    post: {
      name:       'アカウントリスト',
      body_md:    table(rows),
      tags:       [],
      category:   '',
      wip:        false,
      message:    '情報量が増えました',
      updated_by: 'esa_bot'
    }
  })

  UrlFetchApp.fetch(
    'https://api.esa.io/v1/teams/esminc/posts/POST_ID?access_token=ACCESS_TOKEN',
    {
      method:      'PUT',
      contentType: 'application/json',
      payload:     stringifiedPayload
    }
  );
}

これをコンパイルし、中身をスクリプトエディタに貼り付けます。

$ $(npm bin)/browserify main.js -p gasify -o bundle.gs

スプレッドシート更新のタイミングでスクリプトが動くようにする

スクリプトエディタを開き、ツールバーリソース > 現在のプロジェクトのトリガー より設定していきます。 今回は、更新時にスクリプトが呼ばれるようにしたました。

f:id:hrysd:20160729185351p:plain

結果

スプレッドシートを更新する事で自動的に esa.io の記事も更新されるようなりました。(モザイク処理には Pixelmator を使用)

f:id:hrysd:20160729185313p:plain

最後に

Google Apps Script を使う事で簡単にサービス間での連携を行う事ができました。生成物をコピーアンドペーストしている箇所がいけてない感が強いので、スクリプトをローカルで管理できる soundTricker/gas-manager みたいなのも試してみたいです。

参考

36期開発環境変更点ふりかえり

takkanmです。 弊社では8月から新しい期となるため、これを機会にこの一年自分の開発環境で変更してみたものについて、これまでの変遷を含めふりかえりたいと思います。 (多分読まれているみなさんにとって弊社の期が変わるタイミングなんて関係ないと思いますが、4月ぐらいに書こうと思っていたネタを放置しすぎてここまできてしまったため、無理やりこじつけた次第です。お付き合いください。)

Editor(before: Vim, after: Atom)

まずはエディタです。

大学生の後半から2015年の7月ぐらい(およそ10年)までVimを使用しておりました。(なお、大学で購入したWindowsノートPCに何故かすでにXkeymacsとMedowが入っており、メーラとしてWanderLustを使わされるということがあったため、それまではEmacsを使用)

それをなんの契機があったのか急にAtomに変えてみました。多分、10年使ってみたしモダンなエディタを使ってみるかという軽い気持ちからだったと思います。

モードとテキストオブジェクトがあるVimからモードがないAtomへの変更は、最初はかなり戸惑いがありました。 まずは、ショートカットキーやVimでできてたあの操作はできるのかがよくわからなかったので、Idobataにある弊社AtomルームでAtomユーザにどうするの?というのを聞いたりし、ノウハウを貯めていきました。また、第一回社内Atomユーザ現状確認会をし、みんなが使っているプラグインや困っていることなどを共有していったところ、一日Atomで過ごしても仕事ができるようになっていきました。

操作性に関しては、今でもVimの方が速いのではということを思う時がたまにあります。これはテキストオブジェクトでパッと操作できたり、Uniteの存在がVimにはあるというのが影響しているかもしれません。実際、マージのコンフリクト解消や書き捨てのコードを書くときなどは、Vimでパッとやってしまうことが多いです。

また、余談になりますが最近技術評論社から出版された、Atom実践入門はこれからAtomを始めてみようという人や、Atomを使っているけど使いこなせていないと感じている人にオススメの本でした。細かいキーの操作からカスタマイズの方法まで網羅されているのが特徴です。何より良かったところは、各操作に対してどういうコマンド名かが書かれているため知らなかった操作を知った場合、その操作を特定の使いやすいショートカットキーに自分で割り当てるというのが簡単にできます。

Shell(before: Zsh, after: fish)

以前はZshを使っていました。しかし、数年前弊社がまだ上野にオフィスを構えている時にあったいつぞやのAsakusa.rbのミートアップで@lchinさんがfishの存在を教えてくれて、そこからずっとfishが気になる存在となりました。

そして昨年の11月にid:yoshioriの人がZshからFishにしたという記事を書いてくれたので、乗り換えてみることを決意しました。決意したといっても実際乗り換えれたのは今年に入ってからになってしまいました。

パッケージマネージャですが、oh-my-fishではなく、fishermanを使っています。実は、最初はoh-my-fishを使っていたのですが、Twitterでoh-my-fishを使っていることを言っていたら、fishermanの中の人からおすすめいただいたので、乗り換えることにしました。fishermanはoh-my-fishのプラグインを読み込むこともできるので、すごく設定が楽でした。

fish の特徴ですが、強力な補完だと思います。1文字打つだけで過去に入力したコマンドから一致するものを補完候補として表示してくれます。また、履歴の検索も何文字か入力して上キーを押すだけで簡単にたどれます。ただし、この履歴の補完は、zsh の history-incremental-pattern-search-backward に慣れている人にとっては戸惑いを感じるかもしれません。わたしも最初は慣れず、peco を入れて似たようなインクリメンタル補完を実現してそちらを多用していましたが、慣れてくるとこちらの方が速いかもという気分になってきました。

Keyboard(before: Happy Hacking Keyboard, after: Kinesis Contoured Keyboard)

わたしは大学の時代に使っていたHappy Hacking Keyboard Liteを含めて10年ほどHappy Hacking Keyboardを使用していました。 何故Happy Hacking Keyboardを選んだのかというと大学時代に購入した本にHappy Hacking Keyboard設計思想やキーボードに対するこだわりが書かれており、それに惚れ込んだためというのがあります。また、社会人になってからHappy Hacking Keyboard Professional2を購入して、その打鍵感の心地よさも気に入ってました。

しかし今年に入り、肘に謎の痛みを感じるようになり、なんとなくエルゴノミクスキーボードのKinesis Contoured Keyboardを使用することにしました。弊社にはこのキーボードを使用する人が昔は多く在籍しており、数年前に借りて試してみたことがありました。この時はすぐに挫折してしまいました。今回は、理由が承認されれば開発に必要となる周辺機器を自由に購入できる部署の制度を利用し、購入していただきました。

やはり、購入して使い出した直後は目に見えるぐらいキーが打てず大変でしたが、頑張って1週間程度使っていったところで慣れてきました。このキーボードを使い出して感じたのは、いかに今まで親指を遊ばせていたかということです。Kinesis Contoured Keyboardの親指部分には各6つのキーが用意され、親指をいろんなことに使えます。慣れるまでは、今までキーを打つ時に使っていなかった筋肉を使うので手が疲れましたが、慣れてくるとこのキーがないと不便に感じるぐらいになってきました。

なお、この記事を書いている最中に個人で購入したErgoDox EZが届いたため、そちらを使いこの章を書いています。ErgoDox EZですが、Kinesis Contoured Keyboardより腕を開いてキーを入力できるのが良いのですが、キーがフラットなためKinesis Contoured Keyboardのお椀型が懐かしくなってきます。しばらく、使い込んでみようと思います。

最後に

今年はいろいろドラスティックに開発環境を変更した一年でした。慣れ親しんだ環境から別の環境に移行するのは大変ですが、新しいことを知ったりすることができるので、面白さもあります。今後も定期的に見直して、より快適な環境を目指していこうと思っています。

余談 IME

10年近く使っていたSKKを捨てて、Macの標準IMEのライブ変換も使うようになっていました。