0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

素のPHPで理解する絶対PATH 相対PATH

Posted at

はじめに

今回は素のPHPでアプリ開発をしている際に発生した相対PATHによるエラーです。
高機能なフレームワークを使用していると、実行したスクリプトの場所によるエラーが発生しないので、はまりポイントだなと思いました。

ファイル構造

以下のような構造のプロジェクトがあるとします

app/
  src/
    - main.php
    - sub.php

相対PATHとは?

現在のファイル(カレントディレクトリ)から見た相対位置で指定

// main.php
require './sub.php'
// ./ 同じディレクトリ
// ../ 1つ上のディレクトリ

絶対PATHとは?

ルート(一番上の階層)からのフルPATH

// main.php 
// __DIR__は現在のファイルまでのPATHが入ります。
require __DIR__ . '/sub.php';

index.php

require './sub.php'

この時上記は正しく機能します。index.phpはsub.phpと同じ階層です。

エラーが発生する例

構造を少し変えます。

app/
  src/
    - main.php
    - sub.php
  dir/
    - add.php

add.phpからmain.phpを読み込んでみます

require '../main.php'

main.phpを開いた時、つまり
localhost:8000/main.phpでエラーは発生しません。
localhost:8000/dir/add.phpを開いた時にエラーが発生します。

add.phpが起点になります。main.phpの読み込みには成功しますが、main.phpの内のrequire './sub.php'でエラーが発生します。

これは実行されたスクリプトがadd.phpなので、カレントディレクトリはapp/src/dir/になります。
main.php内のrequire './sub.php'は実際にはこのような構成を期待します

app/
  src/
    - main.php
  dir/
    - add.php
    - sub.php # sub.phpがこの位置にいることを期待

このように相対PATHが起点とするカレントディレクトリは実行されたスクリプトの位置によって決まるため、思わぬバグを引き起こす可能性があります。

ちなみにこの例では以下のようにするとエラーが発生しません

絶対PATHを使用する

rootから見たsub.phpの位置をフルPATHで指定します。
この方法が一番確実です.

// main.php
require __DIR__ . '/sub.php'

PATHの書き方を変える

この方法は挙動が複雑で、お勧めしません。

// main.php
require 'sub.php'

PHPは以下のような順序で探索を行います。

  • 1 インクルードパス
  • 2 カレントディレクトリ(実行ファイルのディレクトリ)
  • 3 その親ディレクトリをrootにたどり着くまで順に探索

ポイントはカレントディレクトリはapp/src/dir/addですので、変わらずdir/配下にsub.phpがあることを期待しますが、存在しなかった場合、親ディレクトリを探索、そこでも見つけられない場合は、更に親ディレクトリを探索するという挙動です。

localhost:8080/dir/add.phpを開いた時、結果的に以下のような状態になります。

app/
  src/
    - main.php
    - sub.php # カレントディレクトリに存在しない場合この位置で探索にヒット
    dir/
      - add.php
      - sub.php # main.phpのrequireはsub.phpがこの位置にいることを期待
      dir2/
        - sub.php # この位置は探索しない
    hoge/
      - sub.php # この位置は探索しない

大分複雑ですね。

このような問題を抱えてしまうため、絶対PATHを使用するのが良いと思います。

終わりに

モダンな開発で使われるフレームワークでは、相対PATHで記述しても、上記のような問題が発生しないような仕組みが備わっています。 先人に感謝を
そして、フレームワークを使う時に相対PATHで書くこともあると思いますが、このような前提を体験すると、絶対PATHで統一したくなっちゃいますね。
フレームワークを使わない開発を体験してみて、大きな発見でした。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?