RailsのI18nでyes/noが使えない

Railsで以下のようなlocaleファイルを書いたところ、translation missing となってしまった。

ja:
  yes: はい
  no: いいえ
I18n.t("yes")
# => "translation missing: ja.yes"

調べてみたところこれは YAML の仕様で、yes/no は真偽値と判定され、”yes”/”no” ではなく true/false と扱われるためらしい。

In YAML, untagged nodes are given an type depending on the application. The examples in this specification generally use the seqmap and str types from the YAML tag repository. A few examples also use the int and float types. The repository includes additional types such as nullboolset and others.

https://yaml.org/spec/1.1/#id858600

なので、”yes”ではなく”true”でアクセスできた。

I18n.t("true")
=> "はい"

YAML で yes/no を使いたい場合はクォートすれば良い。

ja:
  "yes": はい

ちなみに yes/no だけでなく、on/off も真偽値と判定されるよう。

https://yaml.org/type/bool.html

YAMLは型をもっていて文字列以外も扱えるのだけど、キーにも文字列以外が使えることが抜けがちだなと思いました。

irb(main):001:0> YAML.load("0xff: yes")
=> {255=>true}

Railsでコントローラーのアクションを強制終了させる

Railsでコントローラーのアクションを強制終了させてリダイレクトしたり何らか正常なレスポンスを返したりしたい時のやり方。

カスタムエラークラスを作り、rescue_from でキャッチしてあげれば良い。

class HogeController < ApplicationController
  class FugaError < ActionController::ActionControllerError
  end

  rescue_from FugaError do |error|
    redirect_to piyo_url, alert: error.message
  end

  def index
    do_somithing!
  end

  private

  def do_something!
    raise FugaError.new("Error!")
  end
end

AWS SDK for RubyでSNSショートメッセージを送る

AWS SDK for Ruby Version 3 でのやり方
https://github.com/aws/aws-sdk-ruby

IAMの設定

sns:Publish のActionを許可しておく。Resourceは指定できないのでワイルドカード。

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "VisualEditor0",
            "Effect": "Allow",
            "Action": "sns:Publish",
            "Resource": "*"
        }
    ]
}

コード

Gemfile で aws-sdk-sns を読み込んでおく。

gem "aws-sdk-sns"

クレデンシャルは環境変数に設定するなどしておいて、以下のコードでSMSを送信できる。

require 'aws-sdk-sns'
client = Aws::SNS::Client.new
result = client.publish(message: "test message", phone_number: "+819000000000")
result.message_id
#=> "af277fa2-5e77-517a-aebf-27f9c06114fd"

MessageAttributesを指定する場合は以下のようにする。

result = client.publish(
  message: "test message",
  phone_number: "+819000000000",
  message_attributes: {
    "AWS.SNS.SMS.SenderID" => {
      data_type: "String",
      string_value: "hoge"
    }
  }
)

UniFi セキュリティゲートウェイを Adopt した後、デバイスにログインできなくなる

UniFiセキュリティゲートウェイを Adopt し、ステータスがCONNECTEDになった後にセキュリティゲートウェイ(192.168.1.1)へデフォルトアカウント(ubnt / ubnt)でHTTPS、SSHのログインができなくなった。Adopt 前はログインできていた。

フォーラムなどを検索すると Settings > Site の Advanced Features を有効にして Device Authentication を確認しろとの情報が出てくるが、手元のコントローラー(バージョン 6.0.36)ではDevice Authenticationが見つけられなかった。

結局 Settings > System Settings > Controller Configuration > Device SSH Authentication というところにSSHのユーザー名とパスワードを見つけた。HTTPSも同じユーザー名とパスワードでログインできた。

ちなみにDevice Authenticationが見つけられないのは「New Settings」がONになっていてベータ版の管理画面が有効になっていたからだった。

SESのSMTPパスワードの署名を作るRubyワンライナー

Amazon SES で SMTP を使う場合、ユーザー名は IAM のアクセスキーID、パスワードはシークレットアクセスキーを使った署名を設定する必要があります。

https://docs.aws.amazon.com/ja_jp/ses/latest/DeveloperGuide/smtp-credentials.html

RubyでSESのSMTPパスワードを作るワンライナー。AWS_SECRET_ACCESS_KEY、AWS_REGIONを適宜変更してください。

ruby -rbase64 -ropenssl -e 'puts  Base64.encode64([0x04].pack("c*") + ["AWS4" + "AWS_SECRET_ACCESS_KEY", "11111111", "AWS_REGION", "ses", "aws4_request", "SendRawEmail"].inject { |k, v| OpenSSL::HMAC.digest("sha256", k, v) })'

HerokuでRails+MySQLを使うときのdatabase.ymlの設定

Herokuで ruby の buildpack を使うと、以下の条件の場合に config/database.yml が自動的に作成される。

  • config ディレクトリがある
  • activerecord がインストールされている
  • 環境変数に DATABASE_URL が設定されている

データベースに ClearDB などを使う場合、DATABASE_URL を以下のフォーマットで設定する。

mysql2://<username>:<password>@<host>/<database>?<key>=<value>(&<key>=<value>)

例:

mysql2://username:password@us-xxx-xxx-xxxxxxxxxxxx.xx.cleardb.net/rails_production?encoding=utf8&pool=5&timeout=5000

database.yml の内容は rails console から ActiveRecord::Base.connection_config で確認できる。

irb(main):001:0>  ActiveRecord::Base.connection_config
=> {:encoding=>"utf8", :pool=>"5", :timeout=>"5000", :adapter=>"mysql2", :username=>"xxxxx", :password=>"xxxxx", :database=>"heroku_xxxxx", :host=>"us-xxxx-xxxx-xxxx-xx.cleardb.net"}

注意点

ClrearDBで Ignite (Free) や Punch ($9.99/mo) などのプランを使うとCLEARDB_DATABASE_URLという環境変数(例: mysql://xxxxxxxxxxxxxx:xxxxxxxx@us-xxxx-xxxx-xxxx-xx.cleardb.net/heroku_xxxxxxxxxxxxxx?reconnect=true)が作成されるので、これをDATABASE_URLにコピーしてスキームのmysqlをmysql2に修正するだけで簡単に設定できる。

これをこのまま使うと、パラメータのreconnect=trueもdatabase.ymlに設定されてしまうので注意が必要。

WEBの創成

WEB(World Wide Web)の創始者のティム・バーナーズ・リーによる、WEBがどのように始まってどのように広がっていったのかというお話。絶版なのでクソ高かったけど中古で購入した。

WEBの重要な技術としてはHTML、URL、HTTPがあるのだけど、HTMLとURLには強い思い入れがあるのにHTTPの影が薄いのが気になったところ。

NeXTのOSやGUIが初期のWEBに大きく影響を与えてたりしてたようで、こんなとこにも出てくるのかジョブズ、って思ったりした。

Amazon LightsailのWordPressのphpMyAdminに接続する

LightsailのwordpressにはphpMyAdminがインストールされていますが、デフォルトではローカルホスト以外からの接続は拒否されてしまいます。SSHポートフォワーディングを使うことで安全にphpMyAdminに接続することができます。

ssh [HOST] -L 8080:localhost:80 -N

あとはブラウザで http://localhost:8080/phpmyadmin でphpMyAdminにアクセスできます。

ログインアカウント名は root、パスワードはホームディレクトリの bitnami_application_password です。

where all_month の罠

Rails (ActiveRecord) で月の集計を取りたい場合、all_month メソッドを使って、MyModel.where(created_at: time.all_month) のようにすると BETWEEN '2020-04-01 00:00:00' AND '2020-04-30 23:59:59.999999' のようなSQLになるので便利です。

ここで集計対象が DateTime なのに間違えて Date の all_month を使ってしまうと、SQLが BETWEEN '2020-04-01' AND '2020-04-30' となってしまい、月末が集計から漏れてしまうので注意!

ティマイオス/クリティアス

「国家」の後日のソクラテスさんたちの雑談。この世界や宇宙がどのようにでき、どのようなもので作られているのか、人の体がどのような仕組みなのか、などのお話。

海に沈んだアトランティス大陸の話が出てくる。