Erzsamatory Weblog


시중에서 소프트웨어를 구입하고 그 구입한 소프트웨어를 사용하려면 반드시 컴퓨터에 그 프로그램을 설치해야 합니다. 그리고 그 소프트웨어의 업데이트 버전이 발표되었을 때에는 수시로 업데이트 프로그램도 실행하여 해당 소프트웨어를 항상 최신 버전으로 유지합니다. 하지만 인터넷에서 배포되는 웹 프로그램은 약간 상황이 다릅니다. 이 블로그에서 사용하고 있는 텍스트큐브나 대한민국 대표 CMS인 익스프레스엔진과 같은 PHP 기반 웹 프로그램에는 제대로된 파일 관리 시스템이 적용되어 있지 않기 때문에, 초보자가 처음 사용할 때에는 업데이트조차 매우 힘들어합니다. 만약 이 글에서 소개하는 스크립트가 앞서 언급했던 웹 프로그램들에 적용되는 경우에는 초보자도 매우 쉽게 텍스트큐브를 업데이트 하고 익스프레스 엔진을 설치 할 수 있게 될 것입니다.


PHP 전용 파일 시스템이 필요한 이유


PHP는 웹 프로그래머가 매우 쉽게 웹 프로그램을 개발할 수 있게 해주는 매우 쉬운 프로그래밍 언어입니다. 그러나 PHP는 개발자가 아닌 그냥 일반적인 사용자라면 약간 어려울 수도 있는 언어입니다. 특히 웹 프로그램을 업데이트할 때 매우 어렵습니다. 왜냐하면 업데이트 버전이 발표되는 경우에는 사용자가 수정된 파일을 인터넷에서 직접 다운로드를 해야 하고, 설치를 할 때에는 FTP 프로그램을 이용하여 사용자가 직접 업데이트 된 파일을 웹 서버에 업로드해야 하는 이유 때문입니다. 만약 이와 같은 문제점들이 모두 해결되고 인터넷에서 모든 업데이트를 해결할 수 있다면 사용자는 매우 쉽고 빠르게 웹 사이트 또는 블로그를 관리할 수 있을 것입니다.

Windows의 NTFS 또는 리눅스의 ext3 와 같은 파일시스템을 PHP에서도 사용할 수 있다면, PHP 초보자가 어려워하는 웹 프로그램의 업데이트 문제를 매우 쉽게 해결할 수 있을 것입니다. 제가 생각하는 PHP 전용 파일 시스템이란, 운영체제에서의 파일시스템 개념을 넘어서 압축까지 지원하는 파일시스템입니다. 파일시스템이라는 이름이 매우 거창하게 들릴 수도 있겠지만, 하나의 파일 시스템을 만드는 것과 같은 방법으로 하나의 거대한 시스템을 만들어보고자 이와 같은 이름을 지어보았습니다.

PHP 전용 파일 시스템 소스코드


이 스크립트는 제가 직접 작성한 스크립트입니다. 제가 생각하는 이 스크립트의 최종적인 것은 완벽한 압축을 지원하고, 여러 개의 파일을 하나의 파일로 만들 수 있는 기능을 지원하여, 개발자가 업데이트 파일을 만들 때 또는 사용자가 웹 프로그램을 업데이트할 때 매우 편리한 기능을 제공하는 것입니다. 별도의 프로그램 없이 인터넷에서 곧바로 웹 프로그램을 업데이트를 할 수만 있다면 사용자는 매우 쉽게 해당 웹 소프트웨어를 사용할 수 있을 것입니다. 또한 개발자는 매우 쉽게 업데이트 파일을 배포할 수 있으므로 좀 더 빠른 개발이 가능할 것입니다.

※ 이 스크립트는 앞서 소개했던 암호화 시스템을 필요로 합니다.
PHP Mcrypt 라이브러리를 활용한 암호화 시스템

※ 이 스크립트의 사용 예제는 소스코드 하단에 있습니다.

require_once 'EES.class.php';

final class EPS
{
    protected static $_instance = NULL;
    protected $_ees = NULL;
    
    protected $_default_uid = NULL;
    protected $_packages = NULL;
    
    protected function __construct ()
    {
        $this->_ees = EES::getInstance()->setIv();
        $this->_default_uid = 0;
        $this->_packages = array();
    }
    
    public static function getInstance ()
    {
        if (self::$_instance === NULL) {
            self::$_instance = new self();
        }
        
        return self::$_instance;
    }
    
    public function create ($uid='')
    {
        if (!$uid) {
            if (isset($this->_packages[$this->_default_uid])) {
                $this->_default_uid++;
            }
        } else {
            $this->_default_uid = $uid;
        }
        
        $this->_packages[$this->_default_uid] = new stdClass();
        $this->_packages[$this->_default_uid]->root = new stdClass();
        
        return $this;
    }
    
    public function addFileByContents ($dir, $filename, $contents)
    {
        if (!($dir == '/' || $dir === '')) {
            if ($dir[strlen($dir)-1] == '/') {
                $temp = '';
                for ($i=0; $i<(strlen($dir)-1); $i++) {
                    $temp .= $dir[$i];
                }
                $dir = $temp;
                unset($temp);
            }
            if (!(preg_match('/^([a-zA-Z\/]+)$/', $dir))) {
                return $this;
            } else {
                if (preg_match('/([\/]+)/', $dir)) {
                    $temp = explode('/', $dir);
                    $temp2 = '';
                    for ($i=0; $i<count($temp); $i++) {
                        if (!$temp2) {
                            $temp2 .= $temp[$i];
                        } else {
                            $temp2 .= '->'.$temp[$i];
                        }
                        $this->_addDirectory($temp2);
                    }
                    $dir = $temp2;
                    unset($temp);
                    unset($temp2);
                } else {
                    $this->_addDirectory($dir);
                }
            }
        }
        
        if (preg_match('/^([a-zA-Z]*)\.([a-zA-Z]+)$/', $filename)) {
            $filename = str_replace('.', '_', $filename);
            
            eval("
                if (!isset(\$this->_packages[\$this->_default_uid]->root->{$dir}->{$filename})) {
                    \$this->_packages[\$this->_default_uid]->root->{$dir}->{$filename} = new stdClass();
                    \$this->_packages[\$this->_default_uid]->root->{$dir}->{$filename}->type = 'file';
                }
                \$this->_packages[\$this->_default_uid]->root->{$dir}->{$filename}->content = \$contents;
            ");
        }
        
        return $this;
    }
    
    public function setDefaultUid ($uid)
    {
        if (isset($this->_packages[$uid])) {
            $this->_default_uid = $uid;
        }
        
        return $this;
    }
    
    public function convertToGz ($uid = '')
    {
        if (!$uid) {
            $uid = $this->_default_uid;
        }
        
        if (isset($this->_packages[$uid])) {
            $temp = serialize($this->_packages[$uid]);
            $temp = $this->_ees->encrypt($temp);
            return gzcompress($temp, 9);
        } else {
            return $this;
        }
    }
    
    public function convertFromGz ($gz, $uid = '')
    {
        if (!$uid) {
            $uid = $this->_default_uid;
        }
        
        if (isset($this->_packages[$uid])) {
            return $this;
        }
        
        $temp = gzuncompress($gz);
        $temp = $this->_ees->decrypt($temp);
        $this->_packages[$uid] = unserialize($temp);
        
        return $this;
    }
    
    private function _addDirectory ($dir)
    {
        eval("
            if (!isset(\$this->_packages[\$this->_default_uid]->root->{$dir})) {
                \$this->_packages[\$this->_default_uid]->root->{$dir} = new stdClass();
                \$this->_packages[\$this->_default_uid]->root->{$dir}->type = 'directory';
            }
        ");
    }
    
    public function display ($uid = '')
    {
        if (!$uid) {
            $uid = $this->_default_uid;
        }
        
        print_r($this->_packages[$uid]);
    }
}


EPS::getInstance()->create()->addFileByContents('abc/one/', 'index.php', 'abcd1')
->addFileByContents('abc/two/', 'index.php', 'abcd2')
->addFileByContents('abc/two/', 'erzsamatory.php', 'abcd2(1)')
->addFileByContents('abc/two/', 'package.php', 'abcd2(2)')
->addFileByContents('abc/two/', 'system.php', 'abcd2(3)')
->addFileByContents('abc/three/', 'index.php', 'abcd3')
->addFileByContents('abc/three/a', 'a.php', 'abcd3a')
->addFileByContents('abc/three/b', 'b.php', 'abcd3b')
->addFileByContents('abc/three/b', 'c.php', 'abcd3c')
->addFileByContents('abc/three/', 'e.php', 'abcd3e')
->addFileByContents('abc/four/', 'index.php', 'abcd4')
->addFileByContents('abc/five/', 'index.php', 'abcd5')
->addFileByContents('abc/six/', 'index.php', 'abcd6');
EPS::getInstance()->convertFromGz(EPS::getInstance()->convertToGz(), 5)->display(5);


※ 위의 소스코드는 개발중인 소스코드이기 때문에 오류가 발생할 수 있습니다.
http://www.erzsamatory.net/trackback/17

건전한 댓글 문화를 만들어주시기 바랍니다 ^^
불건전한 댓글이 등록되는 경우 관리자의 임의적 판단으로 삭제될 수 있음을 미리 공지드립니다.

비밀글로 작성하기