Hatena::ブログ(Diary)

おっさんプログラマの戯れ言

2017-10-31

Xcodeで入力補完が効かなくなった

macOS 10.12.6, Xcode 8.3.3, CocoaPods 1.3.1, Ruby 2.4.2p198, rbenv 1.1.1-6-g2d7cefe

最近どうもiMacが重い。
特にXcodeが重い。
生成、リンクされるバイナリーが多いことが原因なのか、特にCocoaPodsを使用するプロジェクトが極めて重い。
起動するだけで、"Indexing | Processing files" となって、そいつがなかなか終わらない。

そしていつからか入力補完やJump To Definitionが効かなくなっていた。
既存のでかいプロジェクトだけでなく、新規プロジェクトにおいてすら効かない。

結局原因は判らずじまいだが、やった手順はこちら↓

  • まずこちらを試してみたがダメ
  • こちらのChinmay氏の投稿(現時点で133Votes)を参考に同じ手順を実行してみたがダメ
  • 1つ下のバージョンである 8.2.1 をインストールしてみたがダメ
  • 8.2.1 を削除して、ゴミ箱を空にしてから8.3.3 を再インストールしてみたら直った

結果から見るに、どうもゴミ箱に捨てた古いXcode.app内のデータにリンクして動いていたような雰囲気を感じるが、原因不明。迷宮入り。

今回のことから得るべき教訓は、「ゴミ箱は定期的に空にしようね!」ということ。
どんだけ溜めていたのか、ゴミ箱を空にするだけで30分くらいかかった。(私のMac重すぎぃ〜)

相変わらず動作は重いけれども、入力補完と関数ジャンプは機能するようになった。

どこかで誰かが言っていたが、XcodeやEclipseが重くて作業効率が悪いというのは我々開発者にとって致命的なストレスである。自宅PCなら買い換えれば良いだけなのだが、仕事だとなかなか難しい。エンジニアの作業効率に注文をつけるマネージャーは多いが、エンジニアの作業環境に気配りしてくれるマネージャーなんてなかなかいない。与えられた環境でパフォーマンスを出すのが我々の仕事だ。ゆえにプログラマーというのはOSやPCのコンフィギュレーションにも精通していなければならない。

2017-10-17

ふぁびこんのつくりかた

ウェブサイトを立ち上げる時に忘れないようにすることのひとつに、ファビコンを設置するというものがある。
ウェブブラウザーのアドレスバーやお気に入りに表示されるあのアイコンである。
よくやるやり方は、httpdocs配下にfavicon.icoというファイルをセットして、

<link rel="shortcut icon" href="favicon.ico" />

とするものであるが、これだけだと不十分な場合がある。

各種ブラウザー向け、スマートデバイスのホーム画面へのセットまで考慮するなら、以下の手順がおすすめ。

  • まず、260 x 260 のPNG画像を用意する
  • こちらの Favicon Generator. For real. というサイトを使う
  • Select your Favicon picture から用意したファビコン画像をアップロードする
  • 見た目のオプションをお好みで調節する(デフォルトで問題ない)
  • Favicon Generator Options にファビコン画像を格納するパスをセットする*1
  • 諸々の設定を終えたら、Generate your Favicons and HTML code をクリックする
  • Favicon package をクリックして.zipをダウンロードする
  • .zipを解凍して自分のサイトに配備する(3つ前の手順で指定したパスに置くこと)
  • 画面に表示されたHTMLコードをコピーして、自分のサイトのトップページのHTMLのhead内に貼り付ける


まあ、このサイトに限らず、これ系のツールを使って、1つの元画像から各種プラットフォーム向けのファビコンを自動生成するのが楽かと思われ。
てか、こういうのも規格で統一してくれないのかねぇ。

*1:デフォルトではドキュメントルートに配置するようになっているが、個人的にはそれはお勧めしない。サイズ調節されたアイコン画像やメタ情報を含むファイルが多数生成されるので、/favicons とかに隔離した方が良い

2017-08-30

ついにWITH句が使えるようになったらしい

MariaDBがついに、ようやく、SQL99のWITH句をサポート。
10.1までは使えなかった。
10.2.1からWITH句がサポートされ、10.2.2からは WITH RECURSIVE も使えるそうだ。(私が使いこなせるとは言っていない)

https://mariadb.com/kb/en/the-mariadb-library/with/

2017-07-07

stdoutのエンコーディングは環境変数LANG

Python 3.6.1

備忘録

まだPythonは全然勉強できていない。
それゆえひどく初歩的なところでハマったりしている。

どうも環境によって日本語がうまくエンコード、デコードできていないな、と思ったら、
どうもPythonのprint文の文字列エンコーディングは、ソースコードのエンコーディングとは関係なく、LANG環境変数に依存しているらしい。


test.py

s = '日本語'
print(s)

# UnicodeEncodeError: 'ascii' codec can't encode characters in position 0-2: ordinal not in range(128)

LANGをUTF-8にしてやったら普通に動いた。

export LANG=ja_JP.UTF-8
python test.py
日本語

この値が何になっているかは、sys.stdout.encodingで取得できるみたい。

import sys
print(sys.stdout.encoding)
# ANSI_X3.4-1968

2017-06-20

Java EEアプリを本リリースする際にやるべきこと

Apache, Tomcat, ajp, Java

Java EEのアプリというのは、大抵、独自のサブディレクトリーに配置されるものである。

例えば、myapp.war を Tomcat で開発しているときに、開発者は http://localhost:8080/myapp/ にアクセスして動作確認するだろう。

開発作業についてはそれで何も問題ないのだが、実際にウェブサイトを公開することを考えると、2つの点でこれは現実的ではない。

1つは、8080ポートでウェブサイトを公開すべきでないという、ごく当たり前のことだ。
インターネットからアクセスされるサーバーが余計なポートを解放すべきではないし、ウェブサーバーとしてはTomcatよりもApache httpdの方が信頼できる。
この点についてはajpで解決するのが一般的だ。
Java以外のウェブアプリについても、Apache経由でアクセスさせるのはよくある一般的なやり方だと思われる。

もう1点、これはおそらくJava EE特有の問題だと思うのだが、/myapp というサブディレクトリー必要になってしまうという点だ。

webapps/myapp.war

としてデプロイする限りこれは仕様上必然である。

コンテキストルートへデプロイするには、ROOT.war という名前にしなければならない。

しかしROOT.warにすると、1つのTomcatインスタンスで1つのウェブアプリしか公開できないことになってしまう。

例えば、1つのウェブサーバーで、2つのJavaウェブアプリを公開したいとする。

2つドメイン名を取得して、それらを1つのサーバー(IPアドレス)としてDNSのAレコードを登録したとしよう。

http://my-site.com/
http://my-other-site.com/

本来↑このようにしたいところだが、ROOT.warを2つ作ることはできないので、

http://my-site.com/myapp1
http://my-other-site.com/myapp2

という不細工なURLになってしまう。


こういった問題は、Apache側の設定で回避することができる。

例えば、以下のようにリダイレクトさせてしまう。


httpd.conf

<VirtualHost *:80>
    ServerName example.com
    ServerAlias www.example.com
    ProxyPass /myapp !
    ProxyPass / ajp://localhost:8009/myapp/
    ProxyPassReverse / ajp://localhost:8009/myapp/
    RedirectMatch 301 ^/myapp$ /
    RedirectMatch 301 ^/myapp/(.*)$ /$1
</VirtualHost>


ProxyPass / ajp://localhost:8009/myapp/
ProxyPassReverse / ajp://localhost:8009/myapp/
この設定で、example.comという仮想ホストに対するアクセスをajpでTomcatに流すようにする。


ProxyPass /myapp !
Java EEアプリはmyapp.warとして開発しているとすると、内部からは /myapp/some-servlet のURLにアクセスしているはずなので、それはプロキシーしない。(後の設定でリダイレクトする)


RedirectMatch 301 ^/myapp$ /
RedirectMatch 301 ^/myapp/(.*)$ /$1
/myapp 以下に対するアクセスは / へリダイレクトして、先のプロキシー設定により、ajpを経てTomcatへ流す。


とまあ、こんな感じで対応できるのだが、301の使い方として適切ではないと思うし、毎回のようにリダイレクトが発生するのは通信効率上よろしくないと言えるだろう。

もっとまともなソリューションはないものか。

と悩んでいたところ、Tomcatのserver.xmlとドメインごとのROOT.xmlで対処できるそうな。


【参考】
http://www.matsuaz.com/matsumotojs/2011/02/02/1296583161582.html


なるほど。

サイトごとに、

$CATALINA_HOME/conf/Catalina/my-site.com/ROOT.xml

を作成して、docBaseに.warファイルのパスを指定すれば良いのか。

かぁんたんですね。

Connection: close