prmd の辛いところ
HTTP/1.1 204 No Content
HTTP/1.1 200 OK
+Response は empty
みたいな表現ができない。 いや、正確にはカスタム erb テンプレートを全部自分で用意すればできるのだけど、 templates 全体をコピーして持ってくる必要があったりして、保守観点でやや懸念が残る。
手続きクラスをコールするだけのAPIの返り値は No Content
で構わないのだけど、
prmd
で No Content
を表現すると、rel: 'empty'
とするしかなくて、
これをやるとステータスコードは 202
となってしまう。
202
の Heroku における定義 だと、
202
は equest accepted, but the processing has not been completed
となっている。
元々 202
ってそういうものだよね、とは思いつつ 手続きクラスがコールされた時点で処理は完了しているのに、
202
を返すところにモヤモヤを感じてしまう。
overview
で、うちの 202
はこういう定義だって言い張るのありっちゃありだろうけど、
本当の意味で 202
を返したい場合はどうするやってなってしまうしなぁ・・・
う〜ん やっぱり適切なステータスコードを返すべきな気がするのでカスタムテンプレートでいくべきだ。
prmd と jdoc で JSON Schema の解釈が微妙に違う問題
要するに JSON Schema を解釈して何かするライブラリによって方言が存在する状態になっている。
jdoc
は 204
を表現できるけど、prmd
は 202
となっている他、
status code の表現に使う場所が
def has_response_body? @raw_link.media_type != "null" end # @return [Fixnum] Preferred respone status code for this endpoint def response_status case when method == "POST" 201 when has_response_body? 200 else 204 end end
HTTP/1.1 <%= case link['rel'] when 'create' '201 Created' when 'empty' '202 Accepted' else '200 OK' end %>
みたいな状態。
jdoc
は media_type
属性に null
を指定すれば 204
だし、
prmd
は rel
属性に empty
を指定すれば 202
・・・
prmd
のほうでは 202
の代わりに 204
にしないの?みたいな話が上がってたり
- empty should probably be 204 instead of 202 · Issue #208 · interagent/prmd
- issues with rel=empty · Issue #169 · interagent/prmd
結局 JSON Schema の仕様が完璧じゃないから、実装によってその辺りがブレるんじゃねっていう状態なのかも・・
とりあえず、利用者も多そうだし、Heroku がメンテしているということで、prmd
に寄せていくことにする。
Mac (El Capitan) で nokogiri のインストール @Ruby 2.3.1 でハマった
いつものように
$ ~/.rbenv/plugins/ruby-build $ git fetch origin $ git rebase origin/master $ rbenv install 2.3.1 $ rbenv global 2.3.1 $ gem install bundler $ rbenv rehash
ここまでは全く問題なし。
つづいて Rails ディレクトリへ、
$ ~/projext_hogehoge/ $ rm -rf vendor/bundle $ bundle install .... .... Installing nokogiri 1.6.7.2 with native extensions Gem::Ext::BuildError: ERROR: Failed to build gem native extension. current directory: /Users/nyangry/workspace/some_project/vendor/bundle/gems/nokogiri-1.6.7.2/ext/nokogiri /Users/nyangry/.rbenv/versions/2.3.1/bin/ruby -r ./siteconf20160513-85661-v1vt0k.rb extconf.rb --use-system-libraries checking if the C compiler accepts ... yes checking if the C compiler accepts -Wno-error=unused-command-line-argument-hard-error-in-future... no Building nokogiri using system libraries. libxml2 version 2.6.21 or later is required! *** extconf.rb failed *** Could not create Makefile due to some reason, probably lack of necessary libraries and/or headers. Check the mkmf.log file for more details. You may need configuration options. Provided configuration options: --with-opt-dir --without-opt-dir --with-opt-include --without-opt-include=${opt-dir}/include --with-opt-lib --without-opt-lib=${opt-dir}/lib --with-make-prog --without-make-prog --srcdir=. --curdir --ruby=/Users/nyangry/.rbenv/versions/2.3.1/bin/$(RUBY_BASE_NAME) --help --clean --use-system-libraries --with-zlib-dir --without-zlib-dir --with-zlib-include --without-zlib-include=${zlib-dir}/include --with-zlib-lib --without-zlib-lib=${zlib-dir}/lib --with-xml2-dir --without-xml2-dir --with-xml2-include --without-xml2-include=${xml2-dir}/include --with-xml2-lib --without-xml2-lib=${xml2-dir}/lib --with-libxml-2.0-config --without-libxml-2.0-config --with-pkg-config --without-pkg-config --with-xslt-dir --without-xslt-dir --with-xslt-include --without-xslt-include=${xslt-dir}/include --with-xslt-lib --without-xslt-lib=${xslt-dir}/lib --with-libxslt-config --without-libxslt-config --with-exslt-dir --without-exslt-dir --with-exslt-include --without-exslt-include=${exslt-dir}/include --with-exslt-lib --without-exslt-lib=${exslt-dir}/lib --with-libexslt-config --without-libexslt-config To see why this extension failed to compile, please check the mkmf.log which can be found here: /Users/nyangry/workspace/some_project/vendor/bundle/extensions/x86_64-darwin-15/2.3.0-static/nokogiri-1.6.7.2/mkmf.log extconf failed, exit code 1 Gem files will remain installed in /Users/nyangry/workspace/some_project/vendor/bundle/gems/nokogiri-1.6.7.2 for inspection. Results logged to /Users/nyangry/workspace/some_project/vendor/bundle/extensions/x86_64-darwin-15/2.3.0-static/nokogiri-1.6.7.2/gem_make.out An error occurred while installing nokogiri (1.6.7.2), and Bundler cannot continue. Make sure that `gem install nokogiri -v '1.6.7.2'` succeeds before bundling.
libxml2
あたりっぽい・・・当然設定は
$ cat ~/.bundle/config --- BUNDLE_BUILD__NOKOGIRI: "--use-system-libraries" BUNDLE_BUILD__LIBV8: "--with-system-v8" BUNDLE_PATH: vendor/bundle BUNDLE_BIN: vendor/bundle_bin BUNDLE_JOBS: '8' $ cat .bundle/config --- BUNDLE_DISABLE_SHARED_GEMS: true
で --use-system-libraries
しているし、
$ brew list | grep lib libevent libiconv libpng libtiff libtool libxml2 libxslt
libxml2 も入っている。
いろいろ試して結局
brew link --force libxml2
で解決。
少し前に El Capitan にアップデートした際にシンボリックリンク周りが壊れたっぽい。(アップデート /usr/local/ 周りが壊れるのはよくある・・)
何回も調べてしまう attribute? の定義箇所
ここを見ると query methods と書かれているので、 https://github.com/rails/rails/blob/master/activerecord/lib/active_record/base.rb
# == Attribute query methods # # In addition to the basic accessors, query methods are also automatically available on the Active Record object. # Query methods allow you to test whether an attribute value is present. # Additionally, when dealing with numeric values, a query method will return false if the value is zero. # # For example, an Active Record User with the <tt>name</tt> attribute has a <tt>name?</tt> method that you can call # to determine whether the user has a name: # # user = User.new(name: "David") # user.name? # => true # # anonymous = User.new(name: "") # anonymous.name? # => false
ここを見に行くとそれがある https://github.com/rails/rails/blob/master/activerecord/lib/active_record/attribute_methods/query.rb
Rails の save, destroy は自動的に transaction でラップされる
save and destroy are automatically wrapped in a transaction Both save and destroy come wrapped in a transaction that ensures that whatever you do in validations or callbacks will happen under its protected cover. So you can use validations to check for values that the transaction depends on or you can raise exceptions in the callbacks to rollback, including after_* callbacks. As a consequence changes to the database are not seen outside your connection until the operation is complete. For example, if you try to update the index of a search engine in after_save the indexer won't see the updated record. The after_commit callback is the only one that is triggered once the update is committed. See below.