パソコンをロックせずに放置する人をしつける12個のいたずら

Akerun Advent Calendar 3日目 〜セキュリティ意識の改善〜。

はじめまして! AkerunのAPIや管理画面を主に開発しているエンジニアのuchidaです。

みなさんはパソコンから離れるとき、ロックする習慣はついているでしょうか?

Photosynthでは「社内でもパソコンから離れる時はロックする」ということが社内規則で定められています。

こういったルールを規則として設けてる会社は多いのですが、守らない人というのは僕がこれまで努めたどの会社にもいました。

そういう人には離席した時にパソコンを操作して「実際に困る」という事を体験してもらえばいいのではないかと考え、今回は僕が考えた効果の高そうな方法を紹介します。

あくまでネタ記事として軽い気持ちで読んでいただけると幸いです。

今回の記事の対象OSはmacOSです(便宜上「パソコン」と表記します)。

1. ディスプレイの表示を回転させる

f:id:photosynth-inc:20171203232203p:plain

ディスプレイを回転させた状態で表示させます。 マウスカーソルの操作がとても大変になるので、もとに戻すのもイライラします。

作業時間

1分

手順

  1. 「システム環境設定」を開く
  2. [⌘command] キー + [⌥option] キーを押しながら 「ディスプレイ」 を選択
  3. 「回転」項目を「標準」から適当な角度のものに変更
  4. 表示されたダイアログの「確認」を選択

戻し方

  1. 「システム環境設定」を開く
  2. [⌘command] キー + [⌥option] キーを押しながら 「ディスプレイ」 を選択
  3. 「回転」項目を「標準」に変更

対策

パソコンから離れる時はロックしましょう。

2. ディスプレイの色を反転させる

f:id:photosynth-inc:20171203232532p:plain

表示する色を反転させます。 地味ですが、人によってはディスプレイが壊れたと勘違いするほどインパクトがあります。 あまり使うことがない機能なので戻し方がわからない人も多いと思います。

作業時間

1分

手順

  1. [⌘command] キー + [⌥オプション] キー + [⌃control] キー + [F5] キー でアクセシビリティオプションを開く
  2. 「ディスプレイの色を反転」 にチェックを入れる
  3. 「完了」を選択

一応ショートカットが用意されているので、こちらで動けば一発でいけます。

[⌘command] キー + [⌥オプション] キー + [⌃control] キー + [8] キー

戻し方

  1. [⌘command] キー + [⌥オプション] キー + [⌃control] キー + [F5] キー でアクセシビリティオプションを開く
  2. 「ディスプレイの色を反転」 のチェックをはずす
  3. 「完了」を選択

対策

パソコンから離れる時はロックしましょう。

3. デスクトップに紛らわしいファイルを沢山つくる

デスクトップに存在するファイルを沢山コピーして名前を似たものに変えます。 中身が同じなのでファイルを消す際にとても慎重になる悪質ないたずらです。 アイコンの並び順をシャッフルすると更に悪質ですね。

作業時間

1分

手順

  1. 既存のファイルを選択
  2. [⌘command] キー + [d] キー でファイルを複製
  3. ファイル名を変更
  4. 1 ~ 3を繰り返す

戻し方

手動で地道に不要なファイルを消すくらいでしょうか。

対策

パソコンから離れる時はロックしましょう。

4. デスクトップの壁紙をスクショに差し替える

デスクトップの壁紙を「デスクトップのスクリーンショット」に差し替えるいたずらです。 ファイルを消してもアイコンが残ったり、選択できない謎のファイルが存在するように見えます。 なかなか気づかないと思います。

作業時間

1分

手順

  1. Docを右クリック
  2. ["自動的に非表示"をオンにする]を選択
  3. Docが非表示になっている状態で [⌘command] キー + [⇧shift] キー + [3] キー でスクリーンショットを保存
  4. デスクトップを右クリック
  5. [デスクトップのバックグラウンドを変更]を選択
  6. 先程とったスクリーンショットに変更

戻し方

  1. デスクトップを右クリック
  2. [デスクトップのバックグラウンドを変更]を選択
  3. 元の壁紙ファイルを選択

対策

パソコンから離れる時はロックしましょう。

5. ログインシェルを変える

f:id:photosynth-inc:20171203230838p:plain

ターミナルのログインシェルはデフォルトではbashですが、普通のshに変えてしまういたずらです。 挙動はあまりかわりませんが、bash_profileやbashrcで追加しているパスやエイリアスなどが読み込まれないので、普段使ってるコマンドが使えないという事が起こります。

作業時間

1分

手順

  1. terminal.app を開く
  2. echo '/bin/sh' >> .bash_profile を実行

戻し方

.bash_profile から該当のコードを削除

対策

パソコンから離れる時はロックしましょう。

6. stressコマンドをバックグラウンドで走らせる

f:id:photosynth-inc:20171203231206p:plain

常にパソコンが重たくなり、本体は熱くなり、ファンがうなり始めます。 ハード・ウェアに負担がかかり寿命が短くなったりするので長時間やるのは避けたほうがいいと思います。

作業時間

1分

手順

  1. terminal.app を開く
  2. brew install stress && stress --cpu 4 --quiet & を実行

戻し方

  1. terminal.app を開く
  2. killall stress && brew uninstall stress を実行

対策

パソコンから離れる時はロックしましょう。

7. デフォルトのエディタをnanoに置き換える

f:id:photosynth-inc:20171204083357p:plain

普段 vimemacs などを使っている人をイラッとさせることができます。 コマンドを叩くとエディタが立ち上がってしまうので下手な操作ができなく、 普段 nano をつかっていない人は慎重に exit する操作をするはめになります。

作業時間

3分

手順

  1. terminal.app を開く
  2. 以下のコマンドを実行
# gitなどで立ち上がるエディターを変更
echo 'export EDITOR=nano' >> ~/.bash_profile

# nano用の関数を定義
echo 'hoge(){ nano "${$1}"}' >> ~/.bash_profile

# viをnanoに置き換え
echo 'alias vi="hoge"' >> ~/.bash_profile

# vimをnanoに置き換え
echo 'alias vim="hoge"' >> ~/.bash_profile

# emacsをnanoに置き換え
echo 'alias emacs="hoge"' >> ~/.bash_profile

# atomをnanoに置き換え
echo 'alias atom="hoge"' >> ~/.bash_profile

戻し方

.bash_profile から該当のコードを削除

対策

パソコンから離れる時はロックしましょう。

8. lsコマンドをslコマンドに置き換える

f:id:photosynth-inc:20171203231715p:plain

ファイル一覧を表示しようとすると蒸気機関車のSLが走ります。 個人的にこういうくだらないのが大好きです。

作業時間

3分

手順

  1. terminal.app を開く
  2. 以下のコマンドを実行
# slコマンドをインストール
brew install sl

# じゃまなエイリアスを貼っている場合があるので無効化
echo 'unalias sl' >> ~/.bash_profile
echo 'unalias ll' >> ~/.bash_profile
echo 'unalias tree' >> ~/.bash_profile

# lsをslに置き換え
echo 'alias ls="sl"' >> ~/.bash_profile

# llをslに置き換え
echo 'alias ll="sl"' >> ~/.bash_profile

# treeをslに置き換え
echo 'alias tree="sl"' >> ~/.bash_profile

戻し方

  1. .bash_profile から該当のコードを削除
  2. terminal.app を開く
  3. brew uninstall sl を実行

対策

パソコンから離れる時はロックしましょう。

9. 環境変数の$PATHを空にする

ほとんどのコマンドが叩けなくなります。 一歩間違うと元に戻せなくなる可能性があり、非常に危険ないたずらです。

作業時間

1分

手順

  1. terminal.app を開く
  2. 以下のコマンドを実行
echo 'export PATH=""' >> ~/.bash_profile

戻し方

.bash_profile から該当のコードを削除

対策

パソコンから離れる時はロックしましょう。

10. echoコマンドやcatコマンドを叩くと大音量で読み上げる

echoコマンドやcatコマンドを叩くと最大音量で出力を読み上げるいたずらです。 一瞬驚かせることができると思います。

作業時間

1分

手順

  1. terminal.app を開く
  2. 以下のコマンドを実行
# 引数を読み上げる関数を作成
echo 'hoge1(){ set Volume output volume 100; say "${$1}"}' >> ~/.bash_profile
echo 'alias echo="hoge"' >> ~/.bash_profile
echo 'alias print="hoge"' >> ~/.bash_profile

# 引数のファイルを読み上げる関数を作成
echo 'hoge2(){ set Volume output volume 100; say -f "${$1}"}' >> ~/.bash_profile
echo 'alias cat="hoge"' >> ~/.bash_profile
echo 'alias less="hoge"' >> ~/.bash_profile
echo 'alias tail="hoge"' >> ~/.bash_profile

戻し方

.bash_profile から該当のコードを削除

対策

パソコンから離れる時はロックしましょう。

11. ブラウザを差し替える

f:id:photosynth-inc:20171203231843p:plain

Firefoxを起動したはずなのに、Safariが起動するというものです。 ChromeOperaなども同じやり方で可能です。 人によってはデフォルトのブラウザが変わったと勘違いすると思います。

作業時間

1分

手順

  1. Finderで/Applicationsを開く
  2. Firefox.app の名前を _Firefox.app に変更
  3. Safari.app を選択して [⌘command] キー + [d] キー で複製して Firefox.app に変更

戻し方

  1. Finderで/Applicationsを開く
  2. Firefox.app を削除
  3. _Firefox.app の名前を Firefox.app に変更

対策

パソコンから離れる時はロックしましょう。

12. シェルログイン時に「うっ…」となるメッセージを吐かせる

f:id:photosynth-inc:20171203231949p:plain

ターミナルを開く度に「進捗どうですか?」など出力するようにして何とも言えない気持ちにさせることができます。

作業時間

1分

手順

  1. terminal.app を開く
  2. 以下のコマンドを実行
echo 'echo "\n\n\n\n\t進 捗 ど う で す か ?\n\n\n"' >> /.bash_profile

戻し方

.bash_profile から該当のコードを削除

対策

パソコンから離れる時はロックしましょう。

最後に

他にも、「パソコンを閉じた時にGetWildを大音量で流す」というのを仕込んだりするのも面白いですね。

毎回違ういたずらを仕掛けると効果的だと思います。

ただ、他人のパソコンを操作すること自体いいことではないですし、元に戻せなくなるとそれこそ仕事に支障をきたしてしまうので、実践される方は十分に注意してください。

CTOに話したら「alias emacs=viが鉄板やな」って言っていて、いたずらどころか宗教戦争になりかねないので、これもやめましょう。

それでは、以上のことは完全に自己責任でよろしくお願いします。


株式会社フォトシンスでは、セキュリティ意識の高いエンジニアを募集しています!

www.wantedly.com

Slack Emojiを支える技術

この記事はAkerun Advent Calendar の2日目の記事です。 今回は弊社のSlack Emojiを量産する技術についてです。

Emojiは全従業員共通の概念

f:id:photosynth-inc:20171202214637g:plain

最初にEmoji(当時はEmoticonと呼んでいた)がSlackに追加されたときには、弊社のエンジニアやデザイナーがちょっと盛り上がった程度で終わっていました。

ですが、社員も増えて来てタイミングで大量にEmojiを追加してみたら、なんと皆さんいい感じに食いついてきて、今では一部の社員だけでなく、アルバイト含めた全従業員がカジュアルにEmojiを使っています。

またコミュニケーションが円滑に進んだり、業務の完了やステータスを伝えるために使われていたりと、多種多様案使い方のために、各自でカスタムEmojiを追加したりもするようになってきたので、その辺のEmoji追加を支える技術について書きたいと思います。

代表的な二つのChrome Extensionを導入する

これがあるとないとでは、今後のEmoji生活が変わってきます。 絶対に入れましょう。

複数のEmoji画像を一度にアップロードする

chrome.google.com

まず、ネットにある沢山のEmoji画像を大量にぶち込みたいので、このChromeExtensionを導入します。 これを導入することで、SlackのEmojiの管理画面に、以下の用にEmojiをドラッグアンドドロップできる、Viewが追加されます。

f:id:photosynth-inc:20171202220948p:plain

アップロードするEmojiは世界中の有志の方が親切にgithubに固めて上げてくれているので、それを使いましょう。ぐぐるとたくさんあります。 弊社ではポケモンが人気ですね。

GitHub - Templarian/slack-emoji-pokemon: Slack Pokemon Emojis

Web上の画像を右クリックからアップロードする

chrome.google.com

こちらもめちゃくちゃ便利です。

f:id:photosynth-inc:20171202221626p:plain

何か突発的にEmojiを追加しないといけないタイミングが皆さんあると思うのですが、これでググってすぐに話題に対応できるタイミングでEmojiを追加することができます。慣れれば最速5秒程度で追加できます。

また、なぜかこのサイトと親和性があり、クリックすると本来画像がダウンロードされるサイトなのですが、すぐにアップロードしてくれます(名前も勝手に付けてくれます)。

なので、まずは、このサイトでいいやつを追加してもいいかもですね。

Slackmojis - The Best Custom Slack Emojis

コマンドラインからSlackEmojiをアップロード

ネット上にある様々なEmojiをこのツールを使ってCLIから自動アップロードできます。

github.com

見ずにアップロードが不安なので、確認はした方がいいと思いますが。

便利。

絵文字系のEmojiを量産する

emoji.pine.moe

よく使います。先程のExtensionを入れていれば作成後に右クリックして上げるだけでいいので便利です。

f:id:photosynth-inc:20171202224611p:plain

社員の顔写真を自動でEmojiにする

これは自作です。MSのVison APIを使ってカジュアルにつくって見ました。 弊社では、全員の顔が見えるように、Slackのプロフィール画像を顔社員にしているので、今回はそれを自動でダウンロードして、加工しています。

Gem

# frozen_string_literal: true
source "https://rubygems.org"

gem "microsoft_computer_vision"
gem "mini_magick"
gem 'rest-client'

MSのVison APIのgemあるの便利。また、画像加工は今回はmini_magickを使って見ました。

SourceCode

手順としては以下です。

  • SlackAPIを叩いて、プロフ画像のURL一覧を取得する
  • そのURLをそのままVision APIに渡して顔座標を得る
  • 画像URLと顔座標からMiniMagick自体のメソットで画像ダウンロード+画像加工を行う
#!/usr/bin/env ruby
# coding : utf-8

require 'microsoft_computer_vision'
require 'mini_magick'
require 'json'
require 'rest-client'

class SlackProfileImage2Emoji
  class << self
    def run
      members = slack_members
      members.each do |member|
        sleep 5
        puts member
        rect, err = detect_face member[:profile_image]
        unless err
          image = crop_face rect: rect, url: member[:profile_image]
          image.write "orgs/ps_#{member[:name]}.#{member[:profile_image].split('.').last}"

          # Slackにアップロードできるサイズに縮小する
          image.resize "128x128"
          image.write "icons/ps_#{member[:name]}.#{member[:profile_image].split('.').last}"
        end
      end
    end

    # 画像URLに対応する顔座標を返却する
    def detect_face image_url
      client = MicrosoftComputerVision::Client.new('<VISION_API_TOKEN>')
      options = {
        visual_features: 'Faces',
        details: 'Celebrities'
      }
      res = client.analyze(image_url, options)
      json = JSON.parse res.body
      puts json

      return {
        width:  json["faces"].first["faceRectangle"]["width"],
        height: json["faces"].first["faceRectangle"]["height"],
        left:   json["faces"].first["faceRectangle"]["left"],
        top:    json["faces"].first["faceRectangle"]["top"],
      }, nil
    rescue
      puts "------- Error: Can not get face info"
      return nil, true
    end

    # Slackの従業員のプロフィール画像のURL一覧を取得する
    def slack_members
      res = RestClient.get 'https://slack.com/api/users.list', {
        params: {
          token: "<YOUR_SLACK_TOKEN>",
        }
      }

      (JSON.parse res.body)["members"].select{|member|
        # 適当にフィルタ
        member["deleted"] == false &&
          member["is_restricted"] == true &&
          member["is_bot"] == false &&
          member["name"] != "slackbot"
      }.map{|member|
        # 名前と画像URLのハッシュにして返却
        {name: member["real_name"].downcase.gsub(/ /, '_'), profile_image: member["profile"]["image_original"]}
      }
    end

    # 顔座標とURLを受け取って加工する
    def crop_face rect:, url:
      image = MiniMagick::Image.open(url)
      image.crop "#{rect[:width]}x#{rect[:height]}+#{rect[:left]}+#{rect[:top]}"
      image
    end

  end
end

if __FILE__ == $0
  # 引数ありなら、単一のURLの画像についてだけ顔認識APIを叩く
  if ARGV[0]
    puts (SlackProfileImage2Emoji.detect_face ARGV[0])
  else
    SlackProfileImage2Emoji.run
  end
end

完成品

f:id:photosynth-inc:20171202224209p:plain

※わざと小さくしてます。

定期的に実行するだけでいいので、便利。

まとめ

皆様も素敵なEmojiライフを❗


株式会社フォトシンスでは、急成長するIoT製品「Akerun」を進化させるエンジニアを募集しております!

www.wantedly.com

IoT開発を加速する!!IoTツール開発、その後

はじめまして!

この記事はAkerun Advent Calendar の記念すべき1日目の記事です。 今回はAkerunをつくっている会社フォトシンスのCTOのkazuphが担当します!(`・ω・´)ゞ

IoTツール開発

弊社のメインプロダクトはAkerunというスマートロックですが、その開発や工場での生産の過程で様々なIoTツールを開発しています。

つまり、ネットワークに接続するツールを開発することで、開発生産性を高めたり工場での作業フローを改善して、品質と原価削減を行っています。

去年のbuildersconやAdvent Calendarではその一部を発表させていただきました。

kazuph.hateblo.jp

akerun.hateblo.jp

akerun.hateblo.jp

akerun.hateblo.jp

akerun.hateblo.jp

あれから1年

ちょこちょこ自分がつくったツールを晒してみます。詳しくは、別記事で掘るかも。

[mqtt-eater]MQTTの流れを保存し画面表示+Slackに通知する君

うちの開発だと登場人物が多くてテストをするときなどは、信号の発信役、中継役、受け取り役などパートごとに開発者が違うので、わざわざ動作を確認してもらうのが億劫なときがあります。そういうときに、Slackとかで見れると便利だろうということでつくりました。

今回は情報の発信元のログ(MQTTのPublish)をSlackに流し、中継役(ゲートウェイ)、受け取り役(スマートロック本体)の開発者がそれを見ます。

使用gemは以下(あ、rubyが前提になってる)。

ソースコードのイメージは以下のような感じです。

class Mqtt
  def self.run
    t = Thread.new do
      MQTT::Client.connect(
        remote_host: "<mqtt.broker.domain>",
        remote_port: <XXXX>,
        username:    "<user_name>",
        password:    "<password>",
        ssl:         true,
      ) do |client|
        client.subscribe('<your_topic>/#')
        client.get do |topic,message|
          Slack.post "#dev-mqtt-log , "[MQTT] pub #{topic}: #{message}"
          ary = topic.split('/')
          DB.create_or_update ary.last, ary.first, message
        end
      end
    end
  end
end

開発用にPOSTも付けるといいかなと思いましたが、社内向け管理画面に"Chamber"という名前のカッコいいツールがあるので、そっちと統合してもいいかなと思い一旦最低限までやってペンディング中。

Sinatraの部分は一旦僕がニヤニヤするためだけに、今後も開発を続けてもいいかなという感じです。

[auto-wifi-setting-changer]APの管理画面から自動でWi-Fi設定を更新する君

Wi-Fiの周波数・チャネルが切り替わるものが増えてきているので、それを連続で試験するためにつくりました。 APの管理画面はWebベースなことが多いので、スクレイピングすればほぼなんでもできます。

使用gem

  • capybara
  • selenium-webdriver
  • chromedriver-helper
  • pry

スクレイピングしたいと思う度にcapybaraは未だ顕在だし、調べれば調べるほどに簡単な書き方が出てきて本当に素晴らしいですね(無駄なsleepを徹底的に解除できる)。

最近はChromeDriverも安定していて、開発中はpryで止めてChromeのインスペクターでDOMを確認しながら、pryのconsoleにclick_onとか打ち込みながらどんどんつくれるので、一瞬でつくれていいです。

ソースコードのイメージは以下みたいな感じ。

#!/usr/bin/env ruby
# coding : utf-8

require 'capybara'
require 'capybara/dsl'
require 'selenium-webdriver'
require 'pry'
require 'logger'

class WifiSetting
  include Capybara::DSL

  def initialize()
    Capybara.run_server = false
    Capybara.default_driver = Capybara.javascript_driver = :selenium_chrome # or :rack_test, :selenium, :selenium_chrome, :selenium_chrome_headless, :mobile, :webkit
    Capybara.app_host = "https://ap.ip"
    @log = Logger.new(STDOUT)
    @log.info "initialize"
  end

  def login
    visit("/")
    fill_in('username', with: ENV['ID'])
    fill_in('password', with: ENV['PASS'])
    click_button('Login')
    @log.info "login"
  end

  def change_channel(number)
    select "Channel #{number}", from: 'channel'
    click_button('Update')
    @log.info "Update Channel #{number}"
  end

  def change_state(enable: nil)
    click_on "Wireless9"
    if enable
      choose "Enabled",  name: "wireless"
    else
      choose "Disabled",  name: "wireless"
    end
    click_button('Update')
    @log.info "Update Enable #{enable}"
  end

end

if __FILE__ == $0
  o = WifiSetting.new()
  o.login
  loop do
    o.change_state enable: true
    o.change_channel o.random_channel
    o.change_state enable: false
  end
end

これの派生で、サクッとAkerunのユーザー向け管理画面からユーザー追加や鍵発行をして、ハード側にその情報がちゃんと伝搬するかなどのテストとかも行っております。

[akerun-api]Rubyを使ってバイナリ書き換えーる君

これは、ツールというか、Akerun API本体についに組み込みました。

もともと、工場で動くツール(shellでperlワンライナーでバイナリ置換を行っていたのですが、Rails(Ruby)側で置換して単にダウンロードすればいいんじゃね?IoTっぽいしということで、クラウド側に置換処理を持っていきました。置換のくだりは、冒頭に紹介したリンク先の記事をご覧ください。

置換部分のソースコードはこんだけ。BINARY形式で読み込むと普通にsubで置換できる。知らなかった。。。shellでperlワンライナーしていたのはなんだったのか。

    # バイナリの文字列置換
    def binary_str_replace(path, org, new)
      binary = File.read(path).force_encoding('BINARY')
      binary.sub!(org, new)
      File.binwrite path, binary
    end

    # バイナリの数字置換
    def binary_num_replace(path, org, new)
      binary = File.read(path).force_encoding('BINARY')
      binary.sub!([org].pack("H*"), [new].pack("H*"))
      File.binwrite path, binary
    end

まとめ

僕がこの1年でつくったツールの一部を紹介してみました。 気分が乗ったら深掘りや別のツールの紹介をしたいと思います。

明日は非エンジニアも含め多くの従業員が使いこなしているSlack絵文字を量産する技術について書きたいと思います! お楽しみに!


株式会社フォトシンスでは、急成長するIoT製品「Akerun」を進化させるエンジニアを募集しております!

www.wantedly.com

BLE通信とコンカレントに利用可能な簡易ファイルシステム

Nordic nRF5ライブラリにFDS(Flash Data Storage)という簡易なファイルシステムライブラリがあるのでそれの紹介です。

サンプルコード

https://github.com/ksksue/fds-example

githubのコードでは以下の操作を行うサンプルを用意しています。

  1. 3ファイル書込
  2. 3ファイル検索
  3. 3ファイル削除
  4. 3ファイル検索(NOT FOUND期待)

実行結果

write file_id:0001 rec_key:0001, data:00001234
write file_id:0002 rec_key:0002, data:00005678
write file_id:0003 rec_key:0003, data:00009ABC
found file_id:0001 rec_key:0001, data:00001234 length:1
found file_id:0002 rec_key:0002, data:00005678 length:1
found file_id:0003 rec_key:0003, data:00009ABC length:1
delete file_id:0001 rec_key:0001
delete file_id:0002 rec_key:0002
delete file_id:0003 rec_key:0003
ERROR drv_fds_find(171)  : ErrNo. 10  // 削除した後、検索してもNotFoundエラーとなる
ERROR drv_fds_find(171)  : ErrNo. 10
ERROR drv_fds_find(171)  : ErrNo. 10

FDSを使う背景

IoT製品においてThings側(マイコン)にデータを保存したくなるケースがあります。 ログ情報、ID情報をマイコン側でキャッシュすることでユーザー体感レイテンシを下げ、UXを上げるといったテクニックがありますが、 それを実現するためにはマイコンでしっかりとデータ保存する仕組みを構築しなければなりません。

f:id:photosynth-inc:20170711123448j:plain

そこで立ちはだかる問題としては、まずマイコンにはサーバーやPCのような使いやすいストレージがあるわけではないので256kBほどの容量の少ないFlashを利用することになります。 またBLE通信をベースとすると、BLE通信もFlashアクセスもCPU占有時間が長いため排他処理方法を考慮しなければなりません。 そして、やっかいなのはFlashの書込/イレース10,000回上限がある点です。仮に1日10回ほど同じ箇所に上書き更新するだけで1.5年ほどで寿命がきてしまうという点です。

FDSは、以下の3つの特長をそろえつつ、小さい容量で実装できる優れたファイルシステムライブラリです。

  1. ほどよい検索:データに2種類の数値キー情報を付与することができます。そのキーで検索することができます。組込みにおいてはこれくらいのカンタンな検索性で十分です。

  2. BLE通信とコンカレントに利用可能:nRF5シリーズはBLE通信ができるのが最大の特長ですが、そのBLE通信とFDSはコンカレントに利用可能です。 Flashの書込/イレースは時間のかかる処理のため同時に処理するとFlashアクセス/BLE通信のいずれかを止めることになりますが、 FDSではタスクをペリフェラルに委譲するといった処理を内部でしているため開発者はそこを意識する必要はありません。

  3. ウェアレベリング:書込/イレース回数にかぎりのあるFlashにおいては重要な仕様です。 FDSでは削除しても実際にイレースするわけではなくフラグを立て、ガベージコレクトするときに実際にイレースするといった方法を取っています。

また、ハード的な制約としては2つありますので留意しておきましょう。

  • Nordicのチップにのみ対応(他社のマイコンでは使えません)
  • 内部Flashのみ対応(外部Flash対応にはポーティングが必要)

FDSの仕様

FDSの関数にはいわゆるCRUD(Create/Read/Update/Delete)が用意されていて FDSではwrite/find/update/deleteという名前が付いています。 以下、writeとfind, deleteについて見ていきます。

write

writeでは、データ情報の他に、後で検索するためのfile_idとrec_keyの数値を付与します。

writeのコード例

uint16_t file_id = 1;
uint16_t rec_key = 1;
uint32_t data = 0x1234;
FDS_DPRINTF("write file_id:%04x rec_key:%04x, data:%08x\n", file_id, rec_key, data);
ret = drv_fds_write(file_id, rec_key, &data, 1);
CHECK_ERR(ret);

実行結果

write file_id:0001 rec_key:0001, data:00001234

※ drv_fds_writeはこちらで用意したFDSのラッパーですが、FDSを使うには十分な引数を備えています。

file_idとrec_keyは、範囲が - file_id 0x0000 - 0xBFFF - rec_key 0x0001 - 0xBFFF という以外は制約はありません。重複もOKです。 これら情報は検索のキーとして使われます

dataはワードアライメントのデータ、その長さをワード長で指定します。

find

findのコード例

file_id = 1;
rec_key = 1;
ret = drv_fds_find(file_id, rec_key, &data, &length);
CHECK_ERR(ret);
FDS_DPRINTF("found file_id:%04x rec_key:%04x, data:%08x length:%d\n", file_id, rec_key, data, length);

先程のwriteを実行した後、このコードを実行すると以下の結果になります。

実行結果

found file_id:0001 rec_key:0001, data:00001234 length:1

もし該当するfile_id&rec_keyのファイルが見つからなかった場合は、ret に FDS_ERR_NOT_FOUND ( = 10 )が返ってきます。

delete

file_idとrec_keyを指定して削除します。

file_id = 1;
rec_key = 1;
FDS_DPRINTF("delete file_id:%04x rec_key:%04x\n", file_id, rec_key);
ret = drv_fds_delete(file_id, rec_key);
CHECK_ERR(ret);

実行結果

delete file_id:0001 rec_key:0001

ガベージコレクト

ガベージコレクトを走らせることでFlashから物理的にデータをイレースすることができます。

FDSでは、deleteをしたときにファイルの削除フラグを立てることで論理的に削除しますが実際にFlashをイレースするわけではありません。 つまり、何度もwrite/deleteし続けるとFlash容量がオーバーすることになります。 そうならないよう、定期的にガベージコレクトを実行する必要があります。

サンプルコード内では最後に実行しています。

ret = drv_fds_gc();
CHECK_ERR(ret);

利用する際の注意点

自身のプロジェクトでFDSを使うには以下の点に気をつける必要があります。

softdeviceのsys_evt_dispatchでfs_sys_event_handlerを呼ぶ

fds内で使われているfstorageでsoftdeviceからのコールバックを受け取る処理があります。 fstorageではsoftdeviceに対してflashのwrite/eraseを要求し、その結果がコールバックとして返ってきます。 そのコールバックはsys_evt_dispatchに飛んでくるためfs_sys_event_handlerでそれをキャッチするという仕組みです。

コード上ではsoftdeviceに対してsys_evt_dispatchを登録します。

    err_code = softdevice_sys_evt_handler_set((sys_evt_handler_t)sys_evt_dispatch);
    APP_ERROR_CHECK(err_code);

そのsys_evt_dispatchコールバック内でfs_sys_event_handlerを呼びます。

void sys_evt_dispatch(uint32_t sys_evt)
{
    fs_sys_event_handler(sys_evt);
}

SDK 12以上のFDSを使う

本記事では都合でSDK11のFDSを使っていますが、SDK12にてfds_gcにクリティカルな修正が入っています。 SDK12以上を使うか、SDK11にSDK12のfdsをポーティングすることをオススメします。

まとめ

FDSを使うことでnRF5 BLEマイコン上で簡易なファイルシステムを構築することができます。 FDSはNordicのnRF5シリーズ限定のライブラリではありますがIoT開発において非常に強力なツールになるでしょう。

告知

フォトシンスでは採用を強化しています。 IoT製品に興味のある方はぜひご検討ください。 www.wantedly.com

フォトシンスで社会人インターンが終わりました

前回に引き続いて
株式会社フォトシンスで社会人インターン?をしている(id:kazupyong)です。
本日でフォトシンスでの社会人インターンが終わります。

前回はインターンの経緯を書いたのですが、
今回は実際にインターンで何をやっているのかというのを書こうと思います。

Akerunのアーキテクチャー説明

まずはCTOの(id:kazuph1986)から
Akerunの歴史とAkerun Pro、Remote、ドアセンサー、NFCリーダーなどなど
Akerun本体のハードウェアの仕組みとWebやアプリで使ってるアーキテクチャーの説明と、
実際に鍵が空くまでのフローをレクチャーしてもらいました。

Redashのセットアップ

redash.io

公式だとAMIから起動するのが主流のようですが、
AMIのベースとなっっているのがUbuntuDebian系なので、
管理コスト的に社内のサーバーをAmazon Linux系に統一している関係で
Amazon LinuxにRedashを各種設定して設置することになりました。

設定方法などは公式の以下を参考にしつつ

github.com

ただメンテナンスされていないようなので、
試行錯誤しながらAmazon Linuxでの設定方法をフォトシンス社内Githubにドキュメント化しました。

Redashでデータ吸い出しSQL作成

DB構造をRailsのモデルやER図とか確認しながら1から把握して
社内のプロダクトの人と相談しながらいろいろな抽出したいデータをSQLゴリゴリ書きました。

今後エンジニアやデータアナリストがSQLをForkしてカスタマイズしやすいように
複数のサンプルSQLを書いておいておきました。

f:id:photosynth-inc:20170629151746p:plain

RedashとスプレッドシートとSlackの連携

Redashで作ったSQLデータをAPI経由でスプレッドシートのIMPORTDATA関数で読み取り、
それを定期的にSlackのチャンネルにPOSTするサンプル作りました。
今後KPIとかデータ抽出簡易化と情報共有をカスタマイズしやすいように書いておきました。

カスタマーサクセスチーム用の管理お問い合わせツール作成

カスタマーサクセスチームの電話サポートで
組織名検索→組織に設置されているAkerunの一覧+ログ閲覧など
Redashフォームを活用して最新のDBの値とかエラーログをダッシュボードで一覧表示できるようにしてみました。
まだ運用には乗ってないのですが、今後カスタマイズしつつ使いやすい形で作っておきました。

f:id:photosynth-inc:20170629152144j:plain

リリース前のQAお手伝い

今までWeb系やアプリしか経験なかったのですが、
IoT企業ということもあり実際のデバイスを含めた動作検証は新鮮でした。

Webの管理画面を操作して、アプリから実機を設定して、
実際のデバイスをアプリやNFCカードやボタンなどで操作して
実機動作とサーバーのログを確認するという机いっぱい使いながらの検証でした。

f:id:photosynth-inc:20170629152251j:plain

2週間のインターンを経て

IoTの企業での社会人インターンで、
ハードウェア系を初めてのことばかりの電光石火のような日々でした。

社内の色々な人とコミュニケーションを取ったり、 カフェスペースでランチを一緒に食べたり、自宅で使ってるラズベリーパイの雑談したりと
色々と無理を言った中で暖かく受け入れていただきましてフォトシンスの皆様には感謝です!

おまけ

フォトシンスにはPN制度という超素敵な制度があります。
正社員はもちろん、業務委託でもアルバイトでも社会人インターンでも
フォトシンスメンバー同士での飲み会や食事会の費用を1人あたり1回2000円
月5回まで会社が負担してくれる制度があります。

今週の水曜にその制度を使ってうしごろに焼肉食べに行ってきました!
通常5000円のコースがPN制度で一人3000円で美味しいお肉食べられました。

f:id:photosynth-inc:20170629152322j:plain

フォトシンスでは採用を強化しています!
興味ある人は以下のリンクからどうぞー

www.wantedly.com

フォトシンスで社会人インターンしています

どうもはじめまして 株式会社フォトシンスで社会人インターン?中の(id:kazupyong)です。

民泊やっている会社で働いていたのですが、色々とあり7月いっぱいで辞めることになりまして、
少し時間ができたのでCTOの(id:kazuph)に無理言って国内最大のスマートロックであるAkerunを作っている
フォトシンスにて2週間インターンさせてもらうことになりました。

インターンすることになった経緯

もともと前職のガイアックスで一緒だったという縁もあり 5月某日赤坂での焼肉を食べてたときの会話。

 ハードウェア系って経験ないですけど興味あるんですよー

 うち来ますか?

 次転職する前にフォトシンスでインターンしてみたいです!

 いいですよ!明日からどうですか?

 あざます!また連絡しますねーw

という話を冗談半分でしていたら、
まさかの6月頭に7月いっぱいで会社をやめることが急遽決まって、
エンジニアとプロダクトの方との面接を経て
6/19から6/30までの2週間インターンすることが正式に決まりました。

社内の雰囲気

ロジックボードを10台並べて性能チェックしてる人もいたり、
カスタマーサクセスチームも近く日々お客様の声を間近で聞くことができたり、
鍵というセキュアな物をデジタル化するためにセキュリティーをどう担保するかとか
非常に濃い日々を過ごしています。(もう4日も経ってしまった!)

スマートロックを作ってる会社ということもあってドアのサンプルが複数あったり

f:id:photosynth-inc:20170623143649j:plain

会社内もカフェスペースという広いゆっくりとした空間があり、
ランチやちょっとした社内ミーティングなどコミュニケーション取ることができます。
たまたま昨日は3ヶ月に1度のご飯会というイベントがありまして、飛び入り参加しました。

f:id:photosynth-inc:20170623145325j:plain

あとはお決まりのスタンディングデスクスペースがあったりしてすごい素敵なオフィスです。

f:id:photosynth-inc:20170623143730j:plain

具体的にインターンで何やっているかは次回書きたいと思います!

ちなみにフォトシンスでは採用を強化しているようです。
興味ある人は以下のリンクからどうぞー

www.wantedly.com

Akerun API Hackathon を開催しました

2017/03/04 co-baさんとAkerun API を使ったハッカソンを開催しました。 f:id:photosynth-inc:20170417090142j:plain

コミュニティとテクノロジーを掛け合わせるとどんなことができるだろう?を考えようというハッカソン

co-baさん主催、第一回目のハッカソンにAkerun Pro / Akerun APIを使ってもらいました。

とてもステキなco-ba shibuyaさんのコミュニティスペースでディスカッションがはかどります。

f:id:photosynth-inc:20170417095119j:plain

Akerun Pro を実際触りながら、チームで意見交換しアイデアを練ってもらいました。

f:id:photosynth-inc:20170417094743j:plain

発表会ではAkerun Proの利用履歴APIを使って

  • コワーキングスペース内の混雑状況を遠隔確認
  • 入室中のユーザー一覧を表示。趣味、興味を共有しコミュニケーションのきっかけに。
  • beaconと組み合わせて、在席位置情報と連携

といったおもしろいアイデアがたくさんでてきました。

f:id:photosynth-inc:20170417091951j:plain

Akerunとco-baについて1日真剣に考えた後は懇親会。

f:id:photosynth-inc:20170417091956j:plain

みなさんと未来の働き方など意見交換ができたことがとても刺激になりました。

ありがとうございました!


ロボスタさんに、詳しいレポートを書いていただきました! robotstart.info


Akerunをつくっている株式会社フォトシンスでは、次のをIoTを一緒につくってくれる、エンジニアを募集しています! www.wantedly.com

Akerun Developersサイトもやってます。Akerun APIについては、こちらをご覧ください。 photosynth-inc.github.io

Akerun Proのご購入はこちらからどうぞ! akerun.com