カテゴリー: PHP

CentOS6.4にphp5.6.3をyumで入れる。

CentOS6.4にphp5.6.3をyumで入れる。

元々php5.3.3だったのを必要に駆られてphp5.6.3にしてみました。

以下作業メモ。

■まずepelの導入

# rpm -ivh http://ftp.jaist.ac.jp/pub/Linux/Fedora/epel/6/x86_64/epel-release-6-8.noarch.rpm

※既に入ってたのでOK

■remiを導入

# rpm -ivh http://rpms.famillecollet.com/enterprise/remi-release-6.rpm
http://rpms.famillecollet.com/enterprise/remi-release-6.rpm を取得中
準備中...                ########################################### [100%]
        ファイル /etc/yum.repos.d/remi.repo (パッケージ remi-release-6.5-1.el6.remi.noarch から) は、パッケージ remi-release-6-2.el6.remi.noarch からのファイルと競合しています。

※競合がとか出たので前のものを一回消す

■削除のテスト

# rpm -e --test remi-release-6

■削除実行

# rpm -e remi-release-6

■もう一度入れなおす

# rpm -ivh http://rpms.famillecollet.com/enterprise/remi-release-6.rpm

■phpのバージョン確認

# yum --enablerepo=remi-php56 info php

■先にgd-lastを入れないとエラーが出たので入れる

# yum install gd-last --enablerepo=remi

■全体的にupdate

#  yum --enablerepo=remi-php56 update php*

■phpのバージョン確認

# php -v
Failed loading /usr/lib/php/modules/xdebug.so:  /usr/lib/php/modules/xdebug.so: undefined symbol: zend_unmangle_property_name
PHP 5.6.3 (cli) (built: Nov 16 2014 08:34:59)
Copyright (c) 1997-2014 The PHP Group
Zend Engine v2.6.0, Copyright (c) 1998-2014 Zend Technologies

あれ。xdebugがおかしなことに。

■xdebugがあったので入れてみる

# yum --enablerepo=remi-php56 install php-pecl-xdebug

違うWarning出た。。

# php -v
PHP Warning:  Module 'xdebug' already loaded in Unknown on line 0
PHP 5.6.3 (cli) (built: Nov 16 2014 08:34:59)
Copyright (c) 1997-2014 The PHP Group
Zend Engine v2.6.0, Copyright (c) 1998-2014 Zend Technologies
    with Xdebug v2.2.6, Copyright (c) 2002-2014, by Derick Rethans

とりあえず以下のファイルの1行目をコメントアウト。。

# vim /etc/php.d/xdebug.ini

普通になりました。

# php -v
PHP 5.6.3 (cli) (built: Nov 16 2014 08:34:59)
Copyright (c) 1997-2014 The PHP Group
Zend Engine v2.6.0, Copyright (c) 1998-2014 Zend Technologies
    with Xdebug v2.2.6, Copyright (c) 2002-2014, by Derick Rethans

■参考
CentOS6にPHP5.6をyumでインストール
http://nob-log.info/2014/08/25/centos6-yum-install-php56/

【Fuel】Validationクラスのget_messageの前後に任意のタグを設定する

【Fuel】Validationクラスのget_messageの前後に任意のタグを設定する

FuelPHPのValidationクラスでget_messageメソッドでエラーを出力するときに
前後にデフォルトで指定のタグを付加する方法。

といっても\fuel\core\classes\validation\error.phpをのぞいたら
ドキュメントに無い設定項目があったのでそれをconfigに設定するだけ。
※試しているバージョンは1.7.2

■fuel/core/classes/validation/error.php

	/**
	 * Get Message
	 *
	 * Shows the error message which can be taken from loaded language file.
	 *
	 * @param   string  HTML to prefix error message
	 * @param   string  HTML to postfix error message
	 * @param   string  Message to use, or false to try and load it from Lang class
	 * @return  string
	 */
	public function get_message($msg = false, $open = '', $close = '')
	{
		$open   = empty($open)  ? \Config::get('validation.open_single_error', '')  : $open;
		$close  = empty($close) ? \Config::get('validation.close_single_error', '') : $close;

		if ($msg === false and ! ($msg = $this->field->get_error_message($this->rule)))
		{
			if (is_null($msg))
			{
				$msg = $this->field->fieldset()->validation()->get_message($this->rule);
			}
			if ($msg === false)
			{
				$msg = \Lang::get('validation.'.$this->rule) ?: \Lang::get('validation.'.\Arr::get(explode(':', $this->rule), 0));
			}
		}
		if ($msg == false)
		{
			return $open.'Validation rule '.$this->rule.' failed for '.$this->field->label.$close;
		}

		// only parse when there's tags in the message
		return $open.(strpos($msg, ':') === false ? $msg : $this->_replace_tags($msg)).$close;
	}

■fuel/app/config/config.php

・・・
        /**
         * Validation settings
         */
        'validation' => array(
                /**
                 * Wether to fallback to global when a value is not found in the input array.
                 */
                // 'global_input_fallback' => true,
                'open_single_error' => '<div class="error">',
                'close_single_error' => '</div>',
        ),
・・・

これでget_messageのたびにタグを渡さなくて済む。

FuelPHPのRestコントローラでBackbone.jsからPOSTのデータを受け取る方法

今頃「Backbone.jsアプリケーション開発ガイド」を
写経してみているのですが、チュートリアル2
「ライブラリ(RESTを使ったBackbone.jsアプリケーション)」
ではまったのでメモ。

バックエンドをFuelPHPのRestコントローラで
記述していたのですが、Backbone側でcollection.create(model.save)した
際に$_POSTが空っぽでデータが受け取れなかった。

調べてみると同様の症状を発見。

Backbone.emulateJSON = true;

上記を記述すればバックエンド側で以下のように取得できるようになった。

$model = json_decode(Input::post('model'));

Backbone.jsには以下のように書いてありました。

// Turn on `emulateJSON` to support legacy servers that can't deal with direct
// `application/json` requests ... will encode the body as
// `application/x-www-form-urlencoded` instead and will send the model in a
// form param named `model`.
Backbone.emulateJSON = false;

■参考URL
Backbone.js Model.save()によるPOSTデータをPHPで読み込む
FuelPHP application with Backbone.js model.save()
Backbone.SyncでSAStrutsにFormをPOSTする方法
Backbone.jsを使ってみた

さくらインターネットでPHPファイルをhtml拡張子で動かす

さくらインターネットでPHPファイルをhtml拡張子で動かす

久々にはまったのでメモ。
↓こんなエラーやInternalが出て全然動かなかった・・・。

Not Found
The requested URL /php.cgi/index.html was not found on this server.

マルチドメイン運用の場合です。

↓ここ以下でhtmlの拡張子でphpを動かしたい。

/home/ユーザ名/www/secure/

■まずphp.cgiを設置する。
最初FTPでアップしたてりしたけどそれがいけないようだったのでsshでログインしてコピーした。
使うPHPのバージョンは諸事情により5.2・・・。

cp /usr/local/php/5.2/bin/php-cgi-mysql5.1 /home/ユーザ名/www/secure/php.cgi

権限も振っておく。

chmod 705 /home/ユーザ名/www/secure/php.cgi

■.htaccessを設置
実際にhtmlをphpとして動かすフォルダに以下の内容の「.htaccess」を設置。

DirectoryIndex index.html index.php
Action myphp-script /php.cgi
AddHandler myphp-script .php .html

これで動いた。

みんながSSHでコピーしろって書いてあるのにFTPでいけるだろとか
思ってたのがいけませんでした。。

■参考URL
さくらサーバでhtmlをphpとして扱う方法

さくらインターネットで拡張子がhtmlのファイルでPHPを実行する方法

さくらのインターネット(拡張子HTMLでPHPを実行する)

■さくらインターネットにCodeIgniterを設置する

ついでに、、さくらインターネットにCodeIgniterのプログラム置いたら「No input file specified」出た。

CodeIgniterでNo input file specifiedの対処法

上記をみて対応。。

Laravel4でTwigbridgeを使ってForm作成

2014/07/04 時点での話し。

Laravel4でTwigbridgeを使ってお問い合わせフォームを作成してみることに。

laravel4 フォーム構築1
laravel4 フォーム構築2

上記サイトを参考に、テンプレートエンジン部分をTwigで作成することに。

Twigを使うためにはTwigbridgeというものがあるらしいのでインストール。

$ php artisan --version
Laravel Framework version 4.2.6

4.2系だとtwigbridgeは0.6系を指定しないと駄目らしい。

rcrowe/TwigBridge

requireの指定は「0.6.x-dev」にする

require: "rcrowe/twigbridge": "0.6.*@dev"

最初0.5系いれてて沢山エラーが出て大変だった・・・。
一応twigbridgeが動くようになったのでフォーム構築再開。
しかし途中で問題が発生。フォームヘルパーがtwig内で動かない。

https://github.com/rcrowe/TwigBridge/issues/29

【Laravel】Laravel+twigのフォームヘルパーで苦労した話

↑の内容でなんとか動いた。

上記以外で、Mail::sendでTwigbridgeのテンプレート
が読み込まれなくてエラーがでた。

Unrecognized extension in file #113

TwigBridge not working for Mail #91

サービスプロバイダーの一番上に移動したらメールとんだ。

ちょっとTwigBridge慣れないな。。

PHP:BDDを試す。Behat+Mink+Selenium編

PHP:BDDを試す。Behat+Mink+Selenium編

前回のページはこちら

今回はSeleniumも利用し実際にブラウザが立ち上がって挙動が確認できるようにする。
※前回のcomposer.jsonで「mink-selenium2-driver」入れてるので今回はcomposerは触らない。

Video: Quickstart to testing with Behat, Mink, and Selenium

今回も上記サイトを参考に。

今回の構成
■SeleniumServer
OS:Windows7
IP:192.168.1.10
seleniumで使うブラウザIE11
javaインストール済み

■開発サーバ
OS:CentOS6.5(Vagrant環境↑のwindows内にある)
IP:192.168.1.226

■SeleniumとIEのドライバーの取得(※SeleniumServer側PCでの作業)

http://docs.seleniumhq.org/download/
上記ページ内の「Selenium Server (formerly the Selenium RC Server)」をダウンロード
現時点では「Download version 2.40.0」

IEのドライバは「The Internet Explorer Driver Server」
Download version 2.40.0 for (recommended)
32 bit Windows IE
64 bit Windows IE
上記のどちらかを環境に合わせてダウンロードする。zipなので解凍して中身を
Seleniumの本体と同じところにおいておく

■Seleniumを起動しておく(※SeleniumServer側PCでの作業)

C:>java -jar selenium-server-standalone-2.40.0.jar -Dwebdriver.ie.driver=.\IEDriverServer.exe

※IEを使う場合の起動方法

■behatの設定ファイルであるbehat.ymlの変更(以下開発サーバ側での作業)

$ vim behat.yml
default:
  paths:
    features: features
    bootstrap: %behat.paths.features%/bootstrap
  context:
    parameters:
      browser: ie
      javascript_session: webdriver
  extensions:
    Behat\MinkExtension\Extension:
      browser_name: ie
      goutte: ~
      selenium2:
        wd_host: 'http://192.168.1.10:4444/wd/hub'
        capabilities: { "browser": "ie", "version": "11"}

■test.featureシナリオを変更

$ vim features/test.feature
Feature: Drupal.org search
  In order to find modules on Drupal.org
  As a Drupal user
  I need to be able to use Drupal.org search

  @javascript
  Scenario: Searching for "behat"
    Given I go to "https://drupal.org"
    When I fill in "Search Drupal.org" with "behat"
    And I press "Search"
    Then I should see "Behat Drupal Extension"

■behatを実行

$ ./vendor/bin/behat

※IEが立ち上がらない場合は以下を試す。
インターネットオプションのセキュリティ設定を統一する。
インターネットオプション>セキュリティ>4つの項目(インターネット、ローカルイントラネット、信頼済みサイト、制限済みサイト)
の保護モードを有効にするチェックを全て外す(もしくは全てチェックする)。
その後IEを再起動する。

PHP:BDDを試す。Behat+Mink編

PHP:BDDを試す。Behat+Mink編

BDDに興味をもったのでまずはbehatを試してみる。

Video: Quickstart to testing with Behat, Mink, and Selenium

上記の動画を参考に写経。

今回の構成
■開発サーバ
OS:CentOS6.5(Vagrant環境:windows7内にある)
IP:192.168.1.226

■composerの設定

適当なフォルダに移動してcomposer.jsonを作成する。
※composer自体はインストールしてるとする。

$ vim composer.json
{
  "require": {
    "behat/behat": "2.4.*@stable",
    "behat/mink": "1.5.*@stable",
    "behat/mink-goutte-driver": "*",
    "behat/mink-extension": "*",
    "behat/mink-selenium2-driver": "*"
  }
}

■behat,minkのインストール

$ php composer.phar install

■behatの設定ファイルであるbehat.ymlを作成

composer.jsonと同じ場所にbehat.ymlを作成する。

$ vim behat.yml
default:
  paths:
    features: features
    bootstrap: %behat.paths.features%/bootstrap
  extensions:
    Behat\MinkExtension\Extension:
      goutte: ~

■behatを初期化(featuresフォルダが作成される)

$ ./vender/bin/behat --init

■test.featureシナリオを作成

※ファイル名は適当です。

$ vim features/test.feature
Feature: Drupal.org search
  In order to find modules on Drupal.org
  As a Drupal user
  I need to be able to use Drupal.org search

  Scenario: Searching for "behat"
    Given I go to "https://drupal.org"
    When I fill in "Search Drupal.org" with "behat"
    And I press "Search"
    Then I should see "Behat Drupal Extension"

■minkを利用するために「FeatureContext.php」を修正

useやextendsを変更

$ vim features/bootstrap/FeatureContext.php
<?php

use Behat\Behat\Context\ClosuredContextInterface,
    Behat\Behat\Context\TranslatedContextInterface,
    Behat\Behat\Context\BehatContext,
    Behat\Behat\Exception\PendingException;
use Behat\Gherkin\Node\PyStringNode,
    Behat\Gherkin\Node\TableNode;
use Behat\MinkExtension\Context\MinkContext;
//
// Require 3rd-party libraries here:
//
//   require_once 'PHPUnit/Autoload.php';
//   require_once 'PHPUnit/Framework/Assert/Functions.php';
//

/**
 * Features context.
 */
class FeatureContext extends MinkContext
{
    /**
     * Initializes context.
     * Every scenario gets it's own context object.
     *
     * @param array $parameters context parameters (set them up through behat.yml)
     */
    public function __construct(array $parameters)
    {
        // Initialize your context here
    }

//
// Place your definition and hook methods here:
//
//    /**
//     * @Given /^I have done something with "([^"]*)"$/
//     */
//    public function iHaveDoneSomethingWith($argument)
//    {
//        doSomethingWith($argument);
//    }
//
}

■behatを実行

$ ./vendor/bin/behat
Feature: Drupal.org search
  In order to find modules on Drupal.org
  As a Drupal user
  I need to be able to use Drupal.org search

  Scenario: Searching for "behat"                   # features/test.feature:6
    Given I go to "https://drupal.org"              # FeatureContext::visit()
    When I fill in "Search Drupal.org" with "behat" # FeatureContext::fillField()
    And I press "Search"                            # FeatureContext::pressButton()
    Then I should see "Behat Drupal Extension"      # FeatureContext::assertPageContainsText()

1 scenario (1 passed)
4 steps (4 passed)
0m2.492s

とりあえず動いた。
次回はSeleniumを追加してブラウザでの挙動を確認する。

PHP5.3環境でPHP Parse error: syntax error, unexpected $end in …

PHP Parse error: syntax error, unexpected $end in …

いまさら感満載ですが、PHP5.1.6環境で正常に動作していたプログラムをPHP5.3.3環境に
移したら
「PHP Parse error: syntax error, unexpected $end in …」
このエラーが表示されるようになった。

Parse error: syntax error, unexpected $end in について

上記サイトにあるような対策を打とうにもそもそもPHP5.1.6
環境で動いていたので、多分そうじゃない。

色々やってみて結局PHPの「short_open_tag」の設定の違い
だとわかった。
PHP5.1.6環境では「On」になっていたがPHP5.3.3環境では「Off」
になっていた。

とりあえず.htaccessに

php_flag short_open_tag on

と記述して対応。

Symfony2既存のデータベースからEntityを作る方法メモ

How to generate Entities from an Existing Database

上記を参考に行ったけど、Resource/config/doctrine以下のxmlの設定を
利用するようになってしまい、あとでライフサイクルコールバックが使いづらくなったので
Entity内にマッピングされるようにEntityを作成する。

Symfony2.3.2の状態
まずはデータベースを作って、app/config/parameters.ymlに設定をしておく。

バンドルは↓と仮定します。
./src/Devel/TestBundle/

まず最初にDoctrineにデータベースの内部を調べさせて、
「./src/Devel/TestBundle/Resources/config/doctrine」以下にXMLのメタデータファイルを作成する。

$ php app/console doctrine:mapping:convert xml ./src/Devel/TestBundle/Resources/config/doctrine --from-database --force

次にメタデータを元にデータベース情報をマッピングしたEntitiyを作成する

$ php app/console doctrine:mapping:import DevelTestBundle annotation

一応リレーションも設定された状態でEntityができるのでうれしい。

XMLのメタデータファイルを削除しておく※これが大事

$ rm src/Devel/TestBundle/Resource/config/doctrine -rf

上記で作成したEntityはセッター、ゲッターがないので以下のコマンドで追加する

$ php app/console doctrine:generate:entities DevelTestBundle --no-backup

この状態で↓のページのCRUD生成を行うと素敵な状態からはじめられる。
Symfony2 でアプリを作る基礎

リレーション設定した状態でCRUDを作成すると、
新規登録時に__toStringが無いって言われるので、
Entityに__toStringメソッドを追加して表示したい内容を
返すとgood。

Symfony2のインストールに失敗した:[ERROR 3070] complex type ‘service’: The content model is not determinist.

自前のサーバにSymfony2をインストールしようとして失敗したのでメモ。
たぶん同じことになる人が出てくると思うので。。。

$  php composer.phar create-project symfony/framework-standard-edition webroot 2.2.1
・
・
・

  [Symfony\Component\DependencyInjection\Exception\InvalidArgumentException]
  Unable to parse file "/home/takeuchi/public_html/symfony2/webroot/vendor/symfony/symfony/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/../Resources/config/web.xml".

  [InvalidArgumentException]
  [ERROR 3070] complex type 'service': The content model is not determinist. (in file:////home/takeuchi/public_html/symfony2/webroot/vendor/symfony/symfony/src/Symfony/Component/DependencyInjection/Loader/schema/dic/services/services-1.0.xsd - line 75, column 0)
  [ERROR 3070] complex type 'argument': The content model is not determinist. (in file:////home/takeuchi/public_html/symfony2/webroot/vendor/symfony/symfony/src/Symfony/Component/DependencyInjection/Loader/schema/dic/services/services-1.0.xsd - line 131, column 0)
  [ERROR 3070] complex type 'call': The content model is not determinist. (in file:////home/takeuchi/public_html/symfony2/webroot/vendor/symfony/symfony/src/Symfony/Component/DependencyInjection/Loader/schema/dic/services/services-1.0.xsd - line 144, column 0)

Script Sensio\Bundle\DistributionBundle\Composer\ScriptHandler::clearCache handling the post-install-cmd event terminated with an exception

  [RuntimeException]
  An error occurred when executing the "'cache:clear --no-warmup'" command.

調べてみると同様の現象が起きてる人を発見。
[ERROR 3070] complex type ‘service’: The content model is not determinist.

どうもyum-cronでlibxml2のバージョンがあがったことが原因みたい。。。

コメントにあるように以下のコマンドを発行

# yum downgrade libxml2-2.6.26-2.1.21.el5_9.1
# chkconfig yum-cron off

その後再度
$ php composer.phar create-project symfony/framework-standard-edition webroot 2.2.1
を実行したら無事にインストールできた。

表側でエラーがでた場合はapacheの再起動が必要だったりする。

Symfony側の話しではなかったみたいですな。

※エラーはインストールに限らずapp/consoleコマンドのときにも発生してました。

■参考URL
新しいlibxml2 (2.6.26-2.1.21.el5_9.2) がバギーな様子