カテゴリー : PHP

[Symfony1.4] 同じテーブルのカラムへの複数リレーションを持たせる方法

Symfony1.4にて、schema.yml を作成しているときに、同じテーブルのカラムへの複数リレーションを持たせるのに苦労したのでメモ。

本の情報を登録したユーザと変更したユーザの情報を持つために、registry_user_id と edit_user_id というレコードを Book テーブルに持たせています。

それぞれ、User テーブルのid とリレーションを持たせたいのですが、下記のように書くと、後ろの edit_user_id しかリレーションを持てません。

Book:
  actAs:
    Timestampable: ~
    Sluggable: ~
  columns:
    .
    .
    registry_user_id:
      type:             integer
      notnull:          true
    edit_user_id:
      type:             integer
    .
    .
  relations:
    User:
      onDelete:         CASCADE
      local:            registry_user_id
      type:             one
      alias:            RegistryUser
      foreign:          id
      foreignType:      one
    User:
      onDelete:         CASCADE
      local:            edit_user_id
      type:             one
      alias:            EditUser
      foreign:          id
      foreignType:      one

これを下記のように、クラス名を直接指定するのではなく、それぞれに名前を持たせて class: User と指定すればOKです。

    RegistryUser:
      onDelete:         CASCADE
      class:            User
      local:            registry_user_id
      type:             one
      foreign:          id
      foreignType:      one
    EditUser:
      onDelete:         CASCADE
      class:            User
      local:            edit_user_id
      type:             one
      foreign:          id
      foreignType:      one

以上です。

[PEAR] install を使うための認証付きproxy 用の設定方法

pear で install したらエラーが発生しました。

原因は、認証付きproxy 用の設定をしていなかったためです。

# pear install Services_Amazon-0.8.0

■ エラー内容

No releases available for package "pear.php.net/Services_Amazon"
install failed

pear の設定を確認します。

# pear config-show
 
Configuration (channel pear.php.net):
=====================================
Auto-discover new Channels     auto_discover    <not set>
Default Channel                default_channel  pear.php.net
HTTP Proxy Server Address      http_proxy       <not set>
PEAR server [DEPRECATED]       master_server    pear.php.net
.
.
.

config-set http_proxy で認証付きプロキシの情報を設定します。

# pear config-set http_proxy http://user@pass:proxyserver:port/

user/pass/proxyserver/port は自分のもの。

設定後、 # pear config-show して、HTTP Proxy Server Address http_proxy の部分に設定した http://user@pass:proxyserver:port/ が入っていれば設定は反映されています。

以上です。

[Symfony1.4] テンプレートの変更:setTemplate

Symfony1.4にて、テンプレートの変更について調べたのでメモ。テンプレートの変更には、setTemplateメソッドを使います。

■ テンプレートファイルのパスを直接指定する方法

$this->setTemplate('テンプレートファイルの絶対パス、または、相対パス');

■ アクションに対応するテンプレートを指定する方法

$this->setTemplate('Edit');

この場合、Editアクションに対応するテンプレートを呼び出しています。

■ return sfView::SUCCESS

アクションの処理が全て終わったら、何も書かれていない場合、sfView::SUCCESS がreturnされる。

他にも、sfView::NONE, sfView::ERROR などがある。

■ テンプレートについて調べるときに読む記事。

(公式)

A Gentle Introduction to symfony | 第6章 – コントローラーレイヤーの内側 | symfony | Web PHP Framework

Practical symfony | 14日目: フィード | symfony | Web PHP Framework
 

(ブログ記事など)

例外発生時のテンプレートの変更 – ゆっくり*ゆっくり

symfonyでsymfuldaze

WEBアプリケーション研究室 開発ノート [symfony] 特定のテンプレートを強制的に表示
 

[エラー] Invalid row key specified: ~ , referred to in ~

Symfony1.4にて、フィクスチャーファイルからデータベースにデータを入れようとしたらエラー。

# php symfony doctrine:data-load

■ エラー内容

Invalid row key specified: (user) , referred to in (rental) Rental_4

MySQLの外部キー制約のため、関連付けのある部分に値がを入れておらず、エラーになっていました。

mysql> show create table rental;
+--------+--| Table  | Create Table
---------------------------------------+
| rental | CREATE TABLE `rental` (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `user_id` bigint(20) DEFAULT NULL,
  `rented_at` datetime DEFAULT NULL,
  `returned_at` datetime DEFAULT NULL,
  `delete_flag` tinyint(1) NOT NULL DEFAULT '0',
  `created_at` datetime NOT NULL,
  `updated_at` datetime NOT NULL,
  `slug` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `rental_sluggable_idx` (`slug`),
  KEY `user_id_idx` (`user_id`),
  CONSTRAINT `rental_user_id_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci |
+--------+----------------------------+

ここの設定のせいで、外部キーがあるカラムをNULLにできませんでした。

CONSTRAINT `rental_user_id_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE CASCADE

■ 解決方法

MySQLにログインして、下記のコマンドで外部キーを削除します。

・参考:MySQL :: MySQL 5.1 リファレンスマニュアル (オンラインヘルプ) :: 9.4.4 FOREIGN KEY 制約

ALTER TABLE tbl_name DROP FOREIGN KEY fk_symbol;

あと、関連付けのあるカラムのfixtureファイルの書き方なんですが、以下のように書いてはいけません。

Rental:
  Rental_1:
    User:               [User_1]
    rented_at:          '2011-01-01'
    returned_at:
    delete_flag:        0
  Rental_2:
    User:
    rented_at:
    returned_at:
    delete_flag:        0

Rental_2 の User: のように書くと、Userに対応するオブジェクトを探しに行って、なくてエラーになるそうです。

代わりに、User: の部分を user_id: と書けばOKです。もしくは、値を入れないので user_id: そのものを書かないという選択肢もあります。

以上です。

[エラー] Unable to parse string: Unable to parse line ~. [Symfony1.4]

Symfony1.4にて、データベースにフィクスチャーファイルを読み込んだ際にエラーが出ました。

# php symfony doctrine:data-load

■ fixture.yml

Book:
  Book1
    isbn:               9784478012031
    asin:               4478012032
    title:              もし高校野球の女子マネージャーがドラッカーの『マネジメント』を読んだら
    memo:               |
                        敏腕マネージャーと野球部の仲間たちが甲子園を目指して奮闘する青春小説。

■ エラー発生その1

Unable to parse string: Unable to parse line 34 (Book1).

Book1 の後に : がありませんでした。 : を付けて解決。
 

■ エラー発生その2

Unable to parse string: A YAML file cannot contain tabs as indentation at line 46 ( 敏腕マネージャーと野球部の仲間たちが甲子園を目指して奮闘する青春小説。).

タブがいけなかった。YAMLは行の先頭付近はタブでのインデントはダメらしいです。

以上です。

[Symfony] Apache標準の404 Not Found が表示されるので mod_rewrite を有効にする

Symfony 1.4 にて、prod環境にするとApache標準の404 Not Found が表示されるという症状に陥りました。

Apache の mod_rewrite を有効にすることで解決したので、その手順をメモ。

他にもdev環境からprod環境へ切り替えると動作しない時の対処方法があるみたいなので、困ったら下記の記事を読みましょう。

dev環境からprod環境に変えると動かなくなる時の対処方法 « symfonyで開発日記 はてなブックマーク - dev環境からprod環境に変えると動かなくなる時の対処方法 « symfonyで開発日記

今回の症状は、

http://example.com/index.php/login
http://example.com/frontend_dev.php/login

とかだとアクセスできるけど、

http://example.com/login

だとアクセスできない状態でした。
 

Apache の mod_rewrite が有効か確認する

まず、mod_rewrite が有効になっているか確認するには、apachectl に -l オプションを付けて、コンパイル済みのモジュールリストを確認します。

# /usr/local/apache2/bin/apachectl -l
Compiled in modules:
 
  mod_rewrite.c

mod_rewrite.c があればOK.

なければ、config.nice に –enable-rewrite オプションを付けて再コンパイルして、インストールし直します。
 

mod_rewrite を有効にして再インストールする

# /usr/local/src/httpd-2.2.21/config.nice --enable-rewrite
# make
# make install

ちなみに、make install を実行しても今あるドキュメント、 ログファイル、設定ファイルは上書きされないみたいです。

・参考:コンパイルとインストール – Apache HTTP サーバ はてなブックマーク - コンパイルとインストール - Apache HTTP サーバ

インストール後に、もう一度 apachectl -l で mod_rewrite.c があるか確認します。

以上です。

CentOS 5.7 に PHP5.3.8 をソースコードからインストールする手順

CentOS 5.7 に PHP5.3.8 をソースコードからインストールしたので、手順をメモ。
 

PHPのアンインストール

まず、ソースコードからPHPをインストールする前に、CentOSにデフォルトでインストールされているPHPをアンインストールします。

# php -v
PHP 5.1.6 (cli) (built: Nov 29 2010 16:47:46)
Copyright (c) 1997-2006 The PHP Group
Zend Engine v2.1.0, Copyright (c) 1998-2006 Zend Technologies
 
# yum remove php-*
# php -v
-bash: /usr/bin/php: そのようなファイルやディレクトリはありません

 

PHPのソースコードをダウンロード・展開する

・DLサイト:PHP: Downloads はてなブックマーク - PHP: Downloads

# cd /usr/local/src
# wget http://jp.php.net/get/php-5.3.8.tar.gz/from/this/mirror
# tar zxvf php-5.3.8.tar.gz
# cd php-5.3.8
./configure \
--enable-mbstring \
--with-apxs2=/usr/local/apache2/bin/apxs \
--with-mysql=/usr/local/mysql \
--enable-pdo \
--with-pdo-mysql=/usr/local/mysql \
--enable-xml

■ エラー

configure: error: xml2-config not found. Please check your libxml2 installation.

libxml2(本体)と libxml2-devel(開発ツール)をインストールすると解決しました。

yum install -y libxml2
yum install -y libxml2-devel

PHPが正常にインストールされていることを確認します。

# /usr/local/bin/php -v
PHP 5.3.8 (cli) (built: Nov  2 2011 20:24:31)
Copyright (c) 1997-2011 The PHP Group
Zend Engine v2.3.0, Copyright (c) 1998-2011 Zend Technologies

 

PHPのPathを通す

# vi ~/.bashrc
 
PATH="$PATH":/usr/local/bin/php
# source ~/.bashrc
# php -v
PHP 5.3.8 (cli) (built: Nov  2 2011 20:24:31)
Copyright (c) 1997-2011 The PHP Group
Zend Engine v2.3.0, Copyright (c) 1998-2011 Zend Technologies

ITmedia エンタープライズ : Linux Tips「パスを追加したい~.bashrc編~」 はてなブックマーク - ITmedia エンタープライズ : Linux Tips「パスを追加したい~.bashrc編~」
 

PHPの設定

■ php.ini のコピー

# cp -p /usr/local/src/php-5.3.8/php.ini-development /usr/local/lib/php.ini

※コピー先は /usr/local/lib/php/php.ini ではなく、/usr/local/lib/php.ini なので注意

■ php.ini の編集

# vi /usr/local/lib/php/php.ini
[PHP]
output_handler = mb_output_handler
expose_php = On
default_charset = "UTF-8"
 
[Date]
date.timezone = Asia/Tokyo
 
[mbstring]
mbstring.language = Japanese
mbstring.internal_encoding = UTF-8
mbstring.http_input = auto
mbstring.http_output = UTF-8
mbstring.encoding_translation = On
mbstring.detect_order = auto
mbstring.substitute_character = none;

【参考】

PHP: INIファイル の扱いに関する変更 – Manual はてなブックマーク - PHP: INIファイル の扱いに関する変更 - Manual

CentOS/PHP/PHP5/設定 – ひつじ帳 はてなブックマーク - CentOS/PHP/PHP5/設定 - ひつじ帳

CentOS 再構築記録13th php.ini 設定を見直す(´・ω・) ス|WEB系技術電脳日記 はてなブックマーク - CentOS 再構築記録13th php.ini 設定を見直す(´・ω・) ス|WEB系技術電脳日記

PHPの日付関数でWarningエラー – ema725の日記 はてなブックマーク - PHPの日付関数でWarningエラー - ema725の日記

自宅サーバー(Windows+Apache)へのPHPインストール はてなブックマーク - 自宅サーバー(Windows+Apache)へのPHPインストール
 

Apacheとの連携

まず、httpd.conf の の中に下記の内容を追記して、phpを有効にします。

# vi /usr/local/apache2/conf/httpd.conf
<IfModule mime_module>
    # ...
 
    # php conf
    AddType application/x-httpd-php .php
    AddType application/x-httpd-php-source .phps
</IfModule>

次に、DirectoryIndex の行に index.php を追記します。

<IfModule dir_module>
    DirectoryIndex index.html index.php
</IfModule>

httpd.conf の編集後、Apacheを再起動させます。

# service httpd restart

 

PHPの動作確認

Apacheのドキュメントルートにテスト用のPHPファイルを作成して、phpinfo メソッドを呼び出すだけの内容を入力して保存します。

# vi /usr/local/apache2/htdocs/phpinfo.php
<?php phpinfo(); ?>

ブラウザから確認するために、ifconfigコマンドで IPアドレスを確認します。

# ifconfig
eth0      Link encap:Ethernet  HWaddr D2:9B:E2:9A:9D:14
          inet addr:192.168.16.130  Bcast:192.168.128.255  Mask:255.255.255.0
          ...

ブラウザから http://192.168.16.130/phpinfo.php にアクセスして、Apache上でPHPが動作するか確認します。

「PHP Version 5.3.8」という見出しの画面が表示されればOKです。

Apache の httpd.conf を編集して、サーバにアクセス時のルートを var/www に変更します。

# vi /usr/local/apache2/conf/httpd.conf
DocumentRoot "/usr/local/apache2/htdocs"
↓(変更する)
DocumentRoot "/var/www/html"

その他、”/usr/local/apache2/” を “/var/www/” に変更します。

以上です。


参考情報

古い php のアンインストールと php 5.3 のインストール – Debian GNU/Linux 3.1 on PowerMac G4

[PHP][JavaScript] urlencode と encodeURI でのエンコードと文字化け問題

 

PHP と JavaScript でエンコードするタイミングによりIEで文字化け問題が発生しました。
 

解決方法としては、PHP側でエンコードしてJavaScript側に渡さないようにして、PHP側からはそのまま値を渡してJavaScript側でエンコードすればOKでした。
 

■ 文字化け問題が発生するパターン
 

[PHP]

コントローラで urlencode して、テンプレートに出力する。

1
2
$url = urlencode('http://example.com/?p=2&keyword=テスト');
$smarty->assign('url', $url);


 

[HTML]

1
<a href="javascript:formsubmitt('http://example.com/?p=2&keyword=%E3%83%86%E3%82%B9%E3%83%88');">次へ</a>


 

[JavaScript]

1
2
3
4
function formsubmitt (action_url) {
    form.action = action_url;
    form.submit();
}

 

■ IEでも正常に処理できるパターン
 

[PHP]

コントローラでエンコードせずに、そのままテンプレートに渡す。

1
2
$url = 'http://example.com/?p=2&keyword=テスト';
$smarty->assign('url', $url);


 

[HTML]

1
<a href="javascript:formsubmitt('http://example.com/?p=2&keyword=テスト');">次へ</a>


 

[JavaScript]

1
2
3
4
function formsubmitt (action_url) {
    form.action = encodeURI(action_url);
    form.submit();
}

 

以上です。
 

【参考】

javascript: escape(), encodeURI(), encodeURIComponent() 比較 (groundwalker.com) はてなブックマーク - javascript: escape(), encodeURI(), encodeURIComponent() 比較 (groundwalker.com)

URL(URI)エンコード・デコードを行う – JavaScript TIPSふぁくとりー はてなブックマーク - URL(URI)エンコード・デコードを行う - JavaScript TIPSふぁくとりー

PHP: urlencode – Manual はてなブックマーク - PHP: urlencode - Manual
 

[ZF] Zend_Db_Select でFROM句/WHERE句に副問合せ(subquery)

 

Zend Framework の Zend_Db_Select でFROM句/WHERE句に副問合せ(subquery)する方法を調べたのでメモ。
 

以下のサイトを参考にしました。
 

U2Kの覚え書き  Zend_Db_Select でFROM句に副問合せ(subquery) はてなブックマーク - U2Kの覚え書き  Zend_Db_Select でFROM句に副問合せ(subquery)

U2Kの覚え書き  Zend_Db_Select でWHERE句に副問合せ(subquery) はてなブックマーク - U2Kの覚え書き  Zend_Db_Select でWHERE句に副問合せ(subquery)

サブクエリをZendのDBを使用して作成 はてなブックマーク - サブクエリをZendのDBを使用して作成
 

[PHP] エラーログ error_log の出力先ディレクトリを確認する方法

PHP の エラーログ error_log の出力先ディレクトリを確認する方法をご紹介します。

コマンドライン上で以下のコマンドを入力すれば確認できます。

1
2
3
$ php -i | grep error_log
 
error_log => /home/log/php/error.log => /home/log/php/error.log

以上です。