ロゴ
HOME > 私的駄文 > CakePHP + Oracle環境での開発に関して

CakePHP + Oracle環境での開発に関して

駄文扱いになりますので、正確な情報では無い事を先に明記しておきます。

現在、データベースにOracleを使ったパッケージアプリケーションのWEBベースの管理システムを受注しており、相当な苦労をしております・・・例えばSymphonyとかzendFrameworkとか選択肢は有りますが、あくまで指定されたフレームワークを使う必要があるのが下請けの辛いとこ。

先ず大前提として、CakePHPの現バージョンはOracleに正式対応していない

バージョン1.3あたりでしょうか、その頃にはOracle用のドライバーも同封されていたのですが、現在は非対応で、有志が作成したものを利用するしか手が有りません。

https://searchcode.com/codesearch/view/40032847/
https://bitbucket.org/odin88/cakephp-2.0-oracle
https://github.com/kdyouri/cakephp-2.x_oracle-driver

シノニムでアクセス出来そうにない

Oracleはテーブル単位、フィールド単位と細かくアクセス権を設定する事が出来ますが、例えば別なスキーマに対して閲覧のみを行いたい場合、接続子を付けてアクセスする事は可能です。

db1.table1

ただ、cakeではこの方法はおそらく使えないはず。なので

CREATE SYNONYM table1 FOR db1.table1;

こんな感じでシノニムを作り、table1のModelを作ればアクセス出来そうですが、どうも参照すら出来ない状態。なので、Read権限を付けたビューを作る必要が有りそう。或いはModel側で

class table1 extends Model {
  public $useDbConfig = 'db1';

こんな感じでデータベース接続を切り替える方法。ただ、アソシエーションが出来ないので、あくまで単一テーブルへ参照が可能だってだけ。

日付の自動インサートは無理そう

cakephpって、createdとmodifiedというフィールドを作っておけば勝手に登録日、更新日をインサートしたり更新してくれますが、そもそもOracleのdate型式には沿わないので無理ぽい。

$this->query()によるプレースホルダが使え無さそう
  $arr = array( 
      ':name' => 'wanwan'
  );

  $sql  = "INSERT INTO test (name) ";
  $sql .= " VALUES(:name) ";
  $this->test->query($sql,$arr);

上記の例はqueryで書く必要は有りませんが、sql書き慣れてるとcakeの規則に縛られるのが億劫であったり、複雑なsqlの場合は書かなくてはならないケースも多々あります。で、その場合は上記のようにプレースホルダを作ってあげるのですが、これが出来ないぽい。

Error: SQLSTATE[HY000]: General error: 1008 OCIStmtExecute: ORA-01008: バインドされていない変数があります。

  $arr = array( 'wanwan' );

  $sql  = "INSERT INTO test (name) ";
  $sql .= " VALUES(?) ";
  $this->test->query($sql,$arr);

これも同様。

Transactionを細かく設定する事が難しそう

複数のテーブルに問い合わせたりインサートしたり、Transactionのセーブポイントをこまか~く管理したい事が有りますが、これが無理そう。

 

まぁ、例えばcakeを通さず、PHPから直でPDO使って処理するならば、mysqlなどのように割とスムーズに書けるのですが、いったんcakeを通すとこれが破綻します。故に公式に対応はしてないのかと思われます。

Oracleってそもそもあまり使う機会が有りません。なので余計に苦労しているって事もあるのですが、普段何気なく使っているIDのオートインクリメントやLIMITといった事が出来ないのも痛い。いちいちSequenceを作らないと自動採番出来ないってどうなんでしょう、何で実装しないのかな。

まだ序盤なんで此の程度ですが、まだまだ問題が出てきそうな予感