PHP FPM のチューニング

このサイトはNginx + WordPress で運用しているだが、設置当初はサイトが重くて仕方なかった。
top コマンドで状況を調べてみるとメモリを使い切っていたので、途方に暮れて解決策をググったところ、以下の記事を発見。 有用な記事をありがとうございました。

CentOS php-fpmの設定を変更してメモリ消費を減らした方法 | CrystalSnowman.com

サーバーはさくらのVPS (Cent OS 6、メモリ 1GB) なので、この記事とまさに同じ状況らしい。 これを参考に PHP FPM の設定 (/etc/php-fpm.d/www.conf) を以下のように変更し、現状運用中。

pm = dynamic
pm.max_children = 10 ; default 50
pm.start_servers = 5
pm.min_spare_servers = 2 ; default 5
pm.max_spare_servers = 6 ; default 35

設定変更前と比較にならないくらい軽く(というか普通に)なった。ここのようにアクセス数の少ないサイトはこういった設定で問題ないらしい。

PHP FPM はデフォルトで最大50ものプロセスを立ち上げようとするということは、比較的ハイスペックな環境を想定して設計されているのだろうか。果たして。

[React.js] setStateしても直ちにstateは変更されない

最近仕事でReactをやっている。
今回のネタはひとこと(ひとコード?)で言うと以下のようなこと。

getInitialState () {
  return { clicked: false };
},
clickHandler () {
  this.setState({ clicked: true });
  console.log(this.state.clicked); // -> false
},
render () {
  console.log(this.state.clicked); // -> true
  return <button onClick={this.clickHandler}>Click Me</button>;
}

インタラクションのハンドラで this.setState したとして、そのハンドラ内でthis.state を参照しても、まだ更新後の値は取れない。render() が呼ばれるタイミングでは更新後の値になっている。実際にステートが更新されるタイミングは意図的に制御されているらしい。トリッキーだ。

更新後の値は変数に入れておいて this.setState しつつ、ハンドラ内ではその変数の値を使うのがおそらく正解だろう。

getInitialState () {
  return { clicked: false };
},
clickHandler () {
  var value = true;
  this.setState({ clicked: value });
  console.log(value); // -> true
},
render () {
  console.log(this.state.clicked); // -> true
  return <button onClick={this.clickHandler}>Click Me</button>;
}

Chrome 43 からは DOM attribute が prototype プロパティに変更される

DOM Attributes now on the prototype chain

それによって…

  • hasOwnProperty()/getOwnPropertyDescriptor()/JSON.stringify() で、DOM attribute が検出できなくなる
  • read-only な DOM attribute を上書きしようとすると例外を投げるようになる

だそうな。
他人が作ったフレームワークは特に、それで動かなくなったりするものも出てくるかもしれないので頭の片隅に置いておくとよい。

Maxのドキュメントを読む その2(Javascript in Max 02 – Basic Techniques)

JavaScript in Max ドキュメントの日本語備忘録的なエントリー第2弾。

Global Methods

Document

以下のメソッドはグローバルコンテキストにあり、どこでも使うことができる。


messnamed (Max object name, message name, any arguments)

Document

グローバルシンボルに紐付けてネーミングされた Max オブジェクトにメッセージを送る。例えば receive オブジェクトなど。 以下の例は “jsmessage” と名付けられたオブジェクトに “hogehoge” とメッセージを送る例である。

Test Code

function loadbang () {
    messnamed("jsmessage", "hogehoge");
}

messnamed


cpost (any arguments)

Document

コンソールにメッセージを出力する。引数とかは次項の post() と同じ。

Test Code

function foo(a, b, c) {
  cpost(a, b, c);
}
function loadbang() {
  foo('foo', [ 'a', 'b', 'c' ], { 'hoge': 'fuga' });
}

How Input to the js Object is Handled


なお、グローバルスコープは jsthis オブジェクト(ブラウザ JavaScript でいうwindow オブジェクト)とドキュメントには書いてあるが、jsthisオブジェクトを呼び出そうとしてもMAXウィンドウに Javascript ReferenceErrod: jsthis is not defined と出て怒られる。 一方、一般的な this オブジェクトは機能している。

function foo() { }
post(this.foo === foo); // 1 (true)

post (any arguments)

Document

MAXウィンドウにメッセージを出力する。 \n を含めると改行になる。 post() を新しい行から初めても改行が出力される。

Test Code

function foo(a, b, c) {
  post(a, b, c);
}
function loadbang() {
  foo('bar', [ 'a', 'b', 'c' ], { 'hoge': 'fuga' });
}

How Input to the js Object is Handled


The jsthis Object

Document

Browser JavaScript だと ”window” にあたるもの。 jsthis オブジェクトはグローバルコードにおける ”this” を表す。グローバルコードで関数を定義すればそれは jsthis のメソッドになり、変数を定義すれば jsthis のメソッドになる。jsthis オブジェクトは以下のようなビルトインプロパティとメソッドを持つ。

autowatch (Number, get/set)

Document

これはとりわけ、1つのソースファイルからいくつかの js インスタンスを作っていて、ソースファイルを変更したらすべてのインスタンスを更新したいような時に便利。外部のテキストエディタでソースファイルを書いている場合も、これを使えばパッチ中の js オブジェクトは自動的に再コンパイルされる。 デフォルトではこの autowatch は 0 (off) に設定されている。on にしたいときはグローバルコード中で行うことがベスト。

box (Maxobj, get)

Document

js オブジェクトを含む Maxobj を返す。jsui オブジェクトからオブジェクトボックスの長方形を取得する際に便利。 詳しくは the Max Object を参照のこと

editfontsize (Number, get/set)

Document スクリプトを編集するウィンドウのフォントサイズを制御する。グローバルコードで書くと、テキスト編集のデフォルトフォントサイズ(Maxウィンドウのフォントサイズ)が変更される。

inlet (Number, get)

Document 関数の実行中、 inlet プロパティには、その関数を呼び出したメッセージを受け取ったインレット番号が格納されている。 この番号は一番左のインレットから0で始まる。 グローバルコード中ではこのプロパティは 0 になる。

inlets (Number, get/set)

Document インスタンスがいくつのインレットを持つべきかを指定する。”inlets” プロパティはグローバルコード中で指定しなければ効果がない。指定されなかった場合、インレットを1つ持ったオブジェクトが作られる。

Test Code 1

function msg_int(a) { // a == 1
  post(a); // 1
}

msg_int

Test Code 2

function msg_int(a) { // a == 1
  post(a); // 1
}
function msg_float(a) { // a == 1.23456
  post(a); // 1.23
}

msg_float


list

Document

inlet に最初の値が int もしくは float の list が入力されると list() が呼ばれる。 上記の例のように最初の値が String の list はその String 名の関数が呼ばれる。

Test Code 1

function list(a, b, c) { // a == 1, b == 2, c == hoge
  post(a, b, c); // 1 2 hoge
  post(arguments.length); // 3
}

list


anything

inlet に入力されたものに該当する function が定義されていなかった場合、anything() で受け取ることができる。例えば int が入力されたときに msg_int() が未定義だったら anything() が呼ばれる。float や list でも同様。
anything() 内部では messagenameinlet 変数が定義されており、それぞれ inlet に入ったメッセージの種類と、inlet 番号を参照できる。

Test Code 1

function anything(a, b, c) { // a == 1, b == 2, c == hoge
  post("messagename", messagename); // messagename list
  post("inlet", inlet); // inlet 0
  post("anything", a, b, c); // anything 1 2 hoge
}

anything


loadbang

Document

loadbang() はパッチ起動時に呼ばれる。js オブジェクトや jsui オブジェクトを追加した時ではなく、あくまでそれを予め含むパッチ起動時に呼ばれることに注意。
Cmd+Shiftを押しながらパッチを起動すると loadbang を無効化できるが、無効になっているかどうかは max.loadbangdisabled プロパティに 1 が入っているかどうかで分かる。

Test Code 1

function loadbang() {
  if (max.loadbangdisabled == 1) {
    post("no loadbang");
  } else {
    post("loadbang!");
  }
}
function bang() {
  post("bang!");
}

普通にパッチを起動した場合
loadbang

Cmd+Shiftを押しながらパッチを起動した場合
noloadbang


getvalueof

Document

JavaScript 内で定義した変数の値(String か Number)を pattr 関連オブジェクトから呼び出せるようにする関数。 → pattr オブジェクトのことがよく分からないので、テストコードが書けない。後で復習する。


setvalueof

Document

pattr 関連オブジェクトから JavaScript 内に変数(Number か String)をパスできるインターフェースを提供する関数。 value が複数の場合、jsthis オブジェクトの arrayfromargs() メソッドで引数を扱うと良いとのこと。
→ pattr オブジェクトのことがよく分からないので、テストコードが書けない。後で復習する。


save

Document

save() を定義すると、JavaScript 内の状態をパッチに保持することができる。 パッチが再読み込みされると、JavaScript 内の状態が復元される。

save() 内だけで使える embedmessage() を使い、値を保存する。

  • embedmessage() の第1引数には保存された値を渡したいコールバック関数名を文字列で渡す
  • embedmessage() の第2引数以降には保存したい値を渡し、これがコールバック関数の引数に渡される

Test Code 1

var valuetosave = 0;
function foo(v) {
  valuetosave = v;
}
function save() {
  embedmessage("callback", valuetosave);
}
function callback(v) {
  valuetosave = v;
  post(v);
}

foo 1 メッセージを送ったあと、パッチを再起動した場合
save

foo 2 メッセージを送ったあと、パッチを再起動した場合
save


notifydeleted

Document

js オブジェクトが削除されたときに呼ばれる

Test Code 1

function notifydeleted() {
  post('js object was deleted.');
}

notifydeleted


Global Code

Document

グローバルスコープに書かれたコードは編集された後、スクリプトがロードされるかコンパイルされたタイミングで評価される。 js / jsui オブジェクトが完全に作られる前に評価される。 js オブジェクトがいくつ inlet / outlet を持つかはグローバルコードからは分からない。これはグローバルコードから inlet / outlet をいくつにするか定義できることを意味する。しかし言い換えれば、まだ outlet が存在しなければ、使うことはできない。 初期化処理を書きたい場合は loadbang() の中に書くべし。

グローバルコードでやるべきこと

  • inlet / outlet の数を定義する
  • jsarguments[] プロパティ(js オブジェクトの引数)にアクセスする
  • inlet / outlet の値の操作
  • グローバル変数の定義と初期化
  • グローバルアプリケーション環境にアクセス&操作するため、Max オブジェクトを使う

グローバルコードでやるべきでないこと

  • outlet から何か出力すること
  • js オブジェクトが置かれたパッチ側を参照しようとすること

Private (Local) Function

Document

js オブジェクトへの inlet メッセージから参照されたくないローカル関数を作りたい場合、local プロパティに 1 をセットする。

Test Code 1

function foo() {
  post("Welcome to 'foo' method!");
}
foo.local = 1;

private function


未完

Maxのドキュメントを読む その1 (Javascript in Max 01 – Basic Techniques)

最近 Max というビジュアルプログラミング言語を学んでいる。js / jsui オブジェクトというのがあり、その中で JavaScript が書ける、ということでドキュメントを読んでいる。 正直流行っていない言語なので情報が少なく、とにかく公式ドキュメントを読むしかないのである。

読んだドキュメントを備忘録的にエントリーしておく。その第1弾。


注意事項

  • JavaScriptファイルを更新した場合、MAXパッチを開き直さないと変更が反映されない

Arguments

Document

js オブジェクトに渡した引数は JavaScript 内では jsarguments[] 配列で参照できる。

  • jsarguments[0] => ファイル名 (required)
  • jsarguments[1] 以降 => その他の引数 (optional)

ということになる。

Test Code

function bang() {
  post(jsarguments[0], jsarguments[1], jsarguments[2], jsarguments[3]);
}

Arguments test


How Input to the js Object is Handled

Document

js オブジェクトの inlet に foo 1 2 3 というメッセージを送った場合、グローバルスコープの foo() 関数を引数 1,2,3 と共に実行するということになる。

Test Code

function foo(a, b, c) {
  post(a, b, c);
}

How Input to the js Object is Handled

なお、グローバルスコープは jsthis オブジェクト(ブラウザ JavaScript でいう window オブジェクト)とドキュメントには書いてあるが、jsthisオブジェクトを呼び 出そうとしてもMAXウィンドウに Javascript ReferenceErrod: jsthis is not defined と出て怒られる。なんだこれは。 一方、一般的な this オブジェクトは機能している。

function foo() { }
post(this.foo === foo); // 1 (true)

Special Function Names

Document

msg_int, msg_float

Document

inlet に int が入力されると msg_int() が呼ばれる。inlet に float が入力されると msg_float() が呼ばれる。msg_float() が未定義の場合、 msg_int() が代用で呼ばれるが、少数点以下は切り飛ばされる。 なお msg_float() は少数点第3位以下を受け取ることができない。

Test Code 1

function msg_int(a) { // a == 1
  post(a); // 1
}

msg_int

Test Code 2

function msg_int(a) { // a == 1
  post(a); // 1
}
function msg_float(a) { // a == 1.23456
  post(a); // 1.23
}

msg_float


list

Document

inlet に最初の値が int もしくは float の list が入力されると list() が呼ばれる。 上記の例のように最初の値が String の list はその String 名の関数が呼ばれる。

Test Code 1

function list(a, b, c) { // a == 1, b == 2, c == hoge
  post(a, b, c); // 1 2 hoge
  post(arguments.length); // 3
}

list


anything

inlet に入力されたものに該当する function が定義されていなかった場合、anything() で受け取ることができる。例えば int が入力されたときに msg_int() が未定義だったら anything() が呼ばれる。float や list でも同様。
anything() 内部では messagenameinlet 変数が定義されており、それぞれ inlet に入ったメッセージの種類と、inlet 番号を参照できる。

Test Code 1

function anything(a, b, c) { // a == 1, b == 2, c == hoge
  post("messagename", messagename); // messagename list
  post("inlet", inlet); // inlet 0
  post("anything", a, b, c); // anything 1 2 hoge
}

anything


loadbang

Document

loadbang() はパッチ起動時に呼ばれる。js オブジェクトや jsui オブジェクトを追加した時ではなく、あくまでそれを予め含むパッチ起動時に呼ばれることに注意。
Cmd+Shiftを押しながらパッチを起動すると loadbang を無効化できるが、無効になっているかどうかは max.loadbangdisabled プロパティに 1 が入っているかどうかで分かる。

Test Code 1

function loadbang() {
  if (max.loadbangdisabled == 1) {
    post("no loadbang");
  } else {
    post("loadbang!");
  }
}
function bang() {
  post("bang!");
}

普通にパッチを起動した場合
loadbang

Cmd+Shiftを押しながらパッチを起動した場合
noloadbang


getvalueof

Document

JavaScript 内で定義した変数の値(String か Number)を pattr 関連オブジェクトから呼び出せるようにする関数。 → pattr オブジェクトのことがよく分からないので、テストコードが書けない。後で復習する。


setvalueof

Document

pattr 関連オブジェクトから JavaScript 内に変数(Number か String)をパスできるインターフェースを提供する関数。 value が複数の場合、jsthis オブジェクトの arrayfromargs() メソッドで引数を扱うと良いとのこと。
→ pattr オブジェクトのことがよく分からないので、テストコードが書けない。後で復習する。


save

Document

save() を定義すると、JavaScript 内の状態をパッチに保持することができる。 パッチが再読み込みされると、JavaScript 内の状態が復元される。

save() 内だけで使える embedmessage() を使い、値を保存する。

  • embedmessage() の第1引数には保存された値を渡したいコールバック関数名を文字列で渡す
  • embedmessage() の第2引数以降には保存したい値を渡し、これがコールバック関数の引数に渡される

Test Code 1

var valuetosave = 0;
function foo(v) {
  valuetosave = v;
}
function save() {
  embedmessage("callback", valuetosave);
}
function callback(v) {
  valuetosave = v;
  post(v);
}

foo 1 メッセージを送ったあと、パッチを再起動した場合
save

foo 2 メッセージを送ったあと、パッチを再起動した場合
save


notifydeleted

Document

js オブジェクトが削除されたときに呼ばれる

Test Code 1

function notifydeleted() {
  post('js object was deleted.');
}

notifydeleted


Global Code

Document

グローバルスコープに書かれたコードは編集された後、スクリプトがロードされるかコンパイルされたタイミングで評価される。 js / jsui オブジェクトが完全に作られる前に評価される。 js オブジェクトがいくつ inlet / outlet を持つかはグローバルコードからは分からない。これはグローバルコードから inlet / outlet をいくつにするか定義できることを意味する。しかし言い換えれば、まだ outlet が存在しなければ、使うことはできない。 初期化処理を書きたい場合は loadbang() の中に書くべし。

グローバルコードでやるべきこと

  • inlet / outlet の数を定義する
  • jsarguments[] プロパティ(js オブジェクトの引数)にアクセスする
  • inlet / outlet の値の操作
  • グローバル変数の定義と初期化
  • グローバルアプリケーション環境にアクセス&操作するため、Max オブジェクトを使う

グローバルコードでやるべきでないこと

  • outlet から何か出力すること
  • js オブジェクトが置かれたパッチ側を参照しようとすること

Private (Local) Function

Document

js オブジェクトへの inlet メッセージから参照されたくないローカル関数を作りたい場合、local プロパティに 1 をセットする。

Test Code 1

function foo() {
  post("Welcome to 'foo' method!");
}
foo.local = 1;

private function