sys238:blog

誰かが必要とするかもしれないから、なんでもメモしよう…

2011年12月13日
by fkit
コメントは受け付けていません。

Codaで公開ができなくなった話

Codaを使ってます。
ブラウザとメールの次に使用頻度が高いです。

Codaはローカルでの変更を監視してるので「すべて公開」ボタンを押すだけでアップロードが完了します。複数ファイル、複数フォルダにまたがった修正でも「すべて公開」一発でアップロード完了です。

この、ものすごく気に入っていた「すべて公開」が使えなくなりました。

Coda使いならわかると思うんですが、ファイルを修正するとファイルブラウザの該当ファイルに「青マル」が付きますよね、で次に保存すると「青マル」が「↑マル」に変わるじゃないですか、これが変わらない。消えちゃう。

「↑マル」のファイルがないから公開もできない。
困った。

初夏くらいから兆候はあったんです。

でも、再起動すれば直っていたんで騙し騙し使ってました。Lionにアップデートするまではこのままなんとか…って。

しかし今朝は違った、何回再起動しても直らない。「もうちょっとで今の仕事が一段落する、そしたらHDDをSDDに交換してLionにアップデートするんだ♪」とか言ってたらこれですよ。

まったく。なんなんだ。ガッ!!

——
直りました。

キャッシュと設定ファイル
 ~/Library/Caches/com.panic.Coda
 ~/Library/Preferences/com.panic.Coda*

を消して、ディスクユーティリティでディスクのアクセス権を修復して、OnyXでメンテナンスとクリーニングを実行したら直りました。

上記を順番に実行しては確認してたんですが、OnyXでクリーニングした時点で直りました。

Onyxでクリーニングするだけで直るのか、それとも他の操作との組み合わせが効いたのかは判りません。

とにかく直ってよかった。
ホントによかった。

2011年11月16日
by fkit
コメントは受け付けていません。

さくらのレンタルサーバのデータベースが大幅機能強化されていました

新規に作成したデータベースからになるけど、MySQLのバージョンが5.1から5.5にバージョンアップされました。

それにともない、ストレージエンジンに従来のMyISAMに加えInnoDBも選択できるようになりました。

それから作成できるデータベースの数が増えてます。
うちの場合は1個だったのが50個になりました。
50倍って…

9/21日から実施されてたみたいです。
今、知ったけど。

「あ〜あぁ、なんでInnoDBが使えないんだろ、参照整合性でdelete cascadeできたらラクチンなのに」とか文句を言いながら作ってたシステムが完成したのが先週末ですよ。

今日、さくらのレンタルサーバの仕様を別件で調べてて、MySQLで選択可能なストレージエンジンにInnoDBがあるのを見た時にはビックリしました。

「なんで?」って。

メンテナンスで停止するってメールは来てたけど、データベースの機能強化のお知らせメールはなかったよな。

メールくれればいいのに。

参考:
 「さくらのレンタルサーバ」データベース機能の強化について

2011年10月12日
by fkit
コメントは受け付けていません。

Smartyの簡易日付整形修飾子(プラグイン)

Smartyには日付整形のために「date_format修飾子」が用意されています。内部的にはPHPの strftime()関数のラッパのようです。

この「date_format修飾子」はテンプレート(デザイン)側で日付を色々と整形できて便利なんですが、修飾対象の値はUnixタイムスタンプでなければいけません。

DBで定義されている項目が日時型(PostgreSQLのTIMESTAMP型やMySQLのDATETIME型なんか)で定義されている場合、PHPで普通に値を取り出すと “2011-10-12 17:17:12.1234″のように「日付を示す文字列」が返ってきます。

この値を「date_format修飾子」で使用するためにはUnixタイムスタンプに変換してからSmartyに渡す必要があります…意外と面倒ですよね。

そこで、”2011-10-12 17:17:12.1234″のような「日付を示す文字列」を直接整形するプラグインをつくりました。

[modifier.s238_ts_edit.php]
<php
/**
 * タイムスタンプ編集
 * @access public
 * @param  string  $value DBから得られたタイムスタンプ値
 * @param  string  $opt   フォーマット種別 設定値はソースの「出力」以降を参照
 */
function smarty_modifier_s238_ts_edit($value, $opt){
  if ($value == '') return '';

  list($ymd, $time) = explode(' ', $value);

  //出力
  /* 日付をそのまま */   if     ($opt == 'D'){ return $ymd;}
  /* 時刻をそのまま */   elseif ($opt == 'T'){ return $time;}
  /* 日付を'/'区切り */  elseif ($opt == '/'){ return strtr($ymd, array('-'=>'/'));}
  /* 時刻を':'区切り */  elseif ($opt == ':'){ return substr(strtr($time, array('.'=>':')), 0, 8);}
  /* 日時を'/:'区切り */ elseif ($opt == '/:'){return strtr($ymd, array('-'=>'/')). ' '. substr(strtr($time, array('.'=>':')), 0, 8);}
}

以下は実行例です。

[smartyの定義]
{$str='2011-10-12 17:17:12.1234'}
{$str} //オリジナル<br>
{$str|s238_ts_edit:'D'} //日付をそのまま<br>
{$str|s238_ts_edit:'T'} //時刻をそのまま<br>
{$str|s238_ts_edit:'/'} //日付を'/'区切り<br>
{$str|s238_ts_edit:':'} //時刻を':'区切り<br>
{$str|s238_ts_edit:'/:'} //日時を'/:'区切り<br>

[実行結果]
2011-10-12 17:17:12.1234 //オリジナル
2011-10-12 //日付をそのまま<br>
17:17:12.1234 //時刻をそのまま<br>
2011/10/12 //日付を'/'区切り<br>
17:17:12 //時刻を':'区切り<br>
2011/10/12 17:17:12 //日時を'/:'区切り<br>

なんか、ベタであんまりカッッコ良いやり方じゃないとは思うんですが結構使えてます。

2011年09月10日
by fkit
コメントは受け付けていません。

Smarty3のtruncate修飾子はマルチバイト対応…だけど

Smarty3のtruncate修飾子がマルチバイト対応になりました。

Googleで「smarty truncate マルチバイト」で検索すると結構な数の「自前でマルチバイト対応のtruncate修飾子を作りました」ってサイトがヒットするので、みんなが待ち望んだ改善ですね。

でもね、ただちょっと、そのままだと微妙に使いづらいんですよ。

結論から言うと、3番目のパラメタ「切り捨てを単語の境界で行うか(FALSE)、厳密なキャラクタ数で行うか(TRUE)」に必ず「TRUE」をセットしないと結果がおかしくなる場合があります。

以下、実行例です。20文字で切り捨ててみます

[smartyの定義]
{$str='OS X Lionは Eメールにまったく新しい方法を採用しました。'}
{$str} //オリジナル<br>
{$str|truncate:20} //境界指定を省略<br>
{$str|truncate:20:'...':true} //境界をTRUE<br>

[実行結果]
Lionは Eメールにまったく新しい方法を採用しました。 //オリジナル
OS X Lionは... //境界指定を省略
OS X Lionは Eメールにま... //境界をTRUE

オリジナル文章の”Eメール”の前に半角のスペースが入ってます。
境界指定がfalseだとココで切り捨ててしまいます。
英語だと単語境界で切り捨てるのが便利なんでしょうが、日本語だと残念な事になります。

対応方法としては
 a){$str|truncate:20:’…’:true}と面倒でも書く
 b)Smarty/plugins/modifier.truncate.phpを修正してデフォルトをTRUEにする
 c)自前のマルチバイト対応truncate修飾子を作る
ぐらいでしょうか?

a)は面倒くさいし、b)は後々問題になりそうだし。
そういう事で、私はC)の自前マルチバイトtruncate修飾子を作る事にしました。
結局、Smarty2と同じになっちゃいました。(笑)

こういう場合のために、Smartyのインスタンス生成時に

Smarty->Lang = 'Japan';

とかできればいいんですけどね。

一応、SYS238版のマルチバイトtruncate修飾子を載せておきます。

[modifier.s238_mb_truncate.php]
<php
/**
 * 文字の切り捨て
 * Type:  modifier
 * Name:  s238_mb_truncate
 * @param string    $string   文字列
 * @param integer   $length   切り捨て長
 * @param string    $etc      付加文字
 * @param string    $encoding エンコーディング
 * @return string
 */
function smarty_modifier_s238_mb_truncate($string, $length=80, $etc='...', $encoding='UTF-8'){
  if($length == 0)	return '';

  if(mb_strlen($string, $encoding) > $length){
    $length -= mb_strlen($etc, $encoding);
    return mb_substr($string, 0, $length, $encoding).$etc;
  }else{
    return $string;
  }
}

2011年09月02日
by fkit
コメントは受け付けていません。

さくらのレンタルサーバにWebSVNをいれる

WebSVNはSubversionをwebブラウザから操作するアプリケーションです。これを、さくらのレンタルサーバに導入してみます。

以前のバージョンでは日本語の文字化けを回避するために色々と設定が必要だったようですが、最新バージョンでは管理対象のソースをutf-8で作成していれば面倒な設定なしに利用できます。

今回はソースのブラウズのみです。リポジトリ内容をtarballでダウンロードしたりとかの設定はやってません。

それから、このWebSVNのインストール手順は、前回のSubversionインストールを前提としています。

Continue Reading →

2011年08月27日
by fkit
コメントは受け付けていません。

Zend Frameworkでファイルにログを出力する

//include_pathは適切に設定されている前提で...
require_once('Zend/Log.php');
require_once('Zend/Log/Writer/Stream.php');

define('LOG_PATH',      '/ver/tmp/webapps/log');  //ログ出力先
define('LOG_FILE_NAME', 'weblog_#DT#.log');       //ログファイル名

/**
 * log writer
 * @param  String    $message  エラーメッセージ
 * @param  String    $level    ログレベル
 * @see    Zend/Log.php
 */
function logWrite($message, $level){
  //'#DT#'を日付に差替える。日毎にログを分割(1ヶ月でローテート)する。
  $logFile = LOG_PATH. '/'. strtr(LOG_FILE_NAME, array('#DT#'=>strftime('%d')));
  $logger = new Zend_Log(new Zend_Log_Writer_Stream($logFile));
  $logger->log($message, $level);
}

//エラーでログ出力
logWrite("エラーです。", Zend_Log::ERR);

//デバッグでログ出力
logWrite("デバッグ情報です。", Zend_Log::DEBUG);
//ログレベル
EMERG   = 0;  // 緊急事態 (Emergency): システムが使用不可能です
ALERT   = 1;  // 警報 (Alert): 至急対応が必要です
CRIT    = 2;  // 危機 (Critical): 危機的な状況です
ERR     = 3;  // エラー (Error): エラーが発生しました
WARN    = 4;  // 警告 (Warning): 警告が発生しました
NOTICE  = 5;  // 注意 (Notice): 通常動作ですが、注意すべき状況です
INFO    = 6;  // 情報 (Informational): 情報メッセージ
DEBUG   = 7;  // デバッグ (Debug): デバッグメッセージ

2011年08月23日
by fkit
コメントは受け付けていません。

Zend Frameworkで日本語のメールを送信する

//include_pathは適切に設定されている前提で...
require_once('Zend/Mail.php');

define('APP_CHARSET',  'UTF-8');
define('MAIL_CHARSET', 'ISO-2022-JP');

$title = "メール送信サンプル";

$body  = "Zend Framework はオープンソースのフレームワークで、\n";
$body .= "ウェブアプリケーションやウェブサービスを PHP5で開発\n";
$body .= "するためのものです。\n";

$mail  = new Zend_Mail(MAIL_CHARSET);

$mail->setFrom([送信者メールアドレス]);
$mail->addTo([受信者メールアドレス1]);
$mail->addTo([受信者メールアドレス2]);
$mail->setSubject(mailTextCnv($title));
$mail->setBodyText(mailTextCnv($body));

$mail->send();

// メールの文字コード変換
function mailTextCnv($str){
  return mb_convert_encoding($str, MAIL_CHARSET, APP_CHARSET);
}

2011年08月22日
by fkit
コメントは受け付けていません。

Zend FrameworkでSmartyを使う

Zend Framework(以下、ZFと略)からSmartyを使うためのメモ

ここここなんかではZend_View_Interfaceを継承して実現していますが、このメモでは違うアプローチで実現します。

まずやる事はフロントコントローラ(index.php)を以下のように修正してZFのZend_Viewによるレンダリングを無効にします。

    :
    省略
    :
require_once 'Zend/Controller/Front.php';
$front = Zend_Controller_Front::getInstance();
$front->setControllerDirectory(APP_BASE_PATH. '/application/controllers');
$front->setParam('noViewRenderer', true);  //Smartyを使うので標準view機構を無効にする
$front->dispatch();

「setParam(‘noViewRenderer’, true)」する事で標準View機構が無効になるので、あとは普通にSmartyが使えます。

簡単ですね。

これだけだとなんなんで続きではZFの標準ディレクトリ構成っぽいファイル配置ができるように、Zend_Controller_ActionとSmartyを拡張してみます。

Continue Reading →

2011年08月20日
by fkit
コメントは受け付けていません。

さくらのレンタルサーバのwebアプリのログインでアカウントを入力済みにする

Webメールやコントロールパネルなどのログイン画面でアカウントを入力済みにする方法。
ログインがちょっとだけ楽になる。

ブックマークのURLを以下のようにするとアカウントが入力済みでページが開く。

Webメール

https://secure.sakura.ad.jp/rscontrol/?webmail=1&domain=[ユーザID]@[ドメイン]

サーバコントロールパネル

https://secure.sakura.ad.jp/rscontrol/?domain=[ドメイン]

自動的にログインしたい場合は昨日の投稿を見てください。

2011年08月19日
by fkit
コメントは受け付けていません。

Webアプリで自動ログインする方法

MacFan(2011/09)を読んでいたら「iのコンシェルジェ」というコーナーにブックマークレットでWebアプリに自動ログインする方法が載っていた。

以前、同じ事をやろうとしてブックマークレットで実現するのを挫折した事があるのでムムッと読んでみたら…

[記事のブックマークレット]

javascript:
location.href=='http://mixi.jp/'
document.getElementsByName('email')[0].value='[ユーザID]';
document.getElementsByName('password')[0].value='[パスワード]';
document.getElementsByName('email')[0].form.submit();

この方法じゃダメ。
うまく行かないパターンがある。

ログインページを開いた状態で、このブックマークレットを実行すればうまくログインできるけど、他のページやブランクページで実行した場合はログインできない。

原因は実際の実行順が「ユーザID&パスワードをセット → ログイン実行 → ログインページを開く」になってしまうからだ。「ユーザID&パスワードをセット」の段階では対象ページがまだ無いから値をセットできなくてエラーになってしまう。

JavaScriptは各ステップの実行結果(終了)を待ってから次のステップに進むんじゃなく、時間のかかる処理は待たずに次のステップに進むのを考慮してないのがこのブックマークレットの敗因。

ちなみに、ページが開くまでsetTimeout()なんかを使って「ユーザID&パスワードをセット → ログイン実行」の処理を待たせてもダメ。今度はページ遷移した段階でsetTimeout()で待たせている後続処理がクリアされてしまう。なのでMacFanの例は二重にダメって事になります。

で、結局どうやって自動ログインを実現したかというと。

一連の自動ログイン処理をhtmlファイルに記述し、そのファイルに対してブックマークを設定して実現しました。

Continue Reading →