zend-expressive-skeletonをGoogleAppEngine/PHPにインストール

Zend公式のPSR-7対応マイクロフレームワーク「zend-expressive」を使ってみようと思い、
Google App Engine にインストールしたので、備忘メモです。

安装的 zend-expressive 版本是 1.0.0。

追加时期为2016年6月10日开始

根据这篇文章的内容,在另一篇名为「为GoogleAppEngine/PHP定制的zend-expressive-skeleton」的文章中,我们提供了一个简便安装的定制版本的框架。

–补充于2016.06.10–

安装骨架

为了使动作易于确认,我们将安装骨架。
除了将模板引擎更改为“Plates”之外,其他都保持默认状态。

$ composer create-project zendframework/zend-expressive-skeleton <project dir>

Minimal skeleton? (no default middleware, templates, or assets; configuration only)
  [y] Yes (minimal)
  [n] No (full; recommended)
  Make your selection (No):

Which router do you want to use?
  [1] Aura.Router
  [2] FastRoute
  [3] Zend Router
  Make your selection or type a composer package name and version (FastRoute):

Which container do you want to use for dependency injection?
  [1] Aura.Di
  [2] Pimple
  [3] Zend ServiceManager
  Make your selection or type a composer package name and version (Zend ServiceManager):

Which template engine do you want to use?
  [1] Plates
  [2] Twig
  [3] Zend View installs Zend ServiceManager
  [n] None of the above
  Make your selection or type a composer package name and version (n): 1

Which error handler do you want to use during development?
  [1] Whoops
  [n] None of the above
  Make your selection or type a composer package name and version (Whoops):

在项目的根目录下添加app.yaml文件。

Google App Engine に必要な設定ファイルです。
とりあえず、サンプル画面を表示できる程度の設定にしました。

module: default
version: 1
runtime: php55
api_version: 1

handlers:
- url: /favicon.ico
  static_files: public/favicon.ico
  upload: public/favicon.ico

- url: /zf-logo.png
  static_files: public/zf-logo.png
  upload: public/zf-logo.png

- url: /.*
  script: public/index.php

在本地環境進行操作確認(未成功)

请参考以下链接: https://cloud.google.com/appengine/docs/php/quickstart#test_the_application

我将使用常规的SDK进行操作确认。

$ dev_appserver.py <project dir>

ブラウザで、localhost:8080 にアクセスしてみると。
すわ fatal error です。

Catchable fatal error: Argument 1 passed to Zend\ServiceManager\Config::__construct() must be of the type array, null given, called in /Users/shuhei/Documents/src/googleAppEngine/phpzend/config/container.php on line 11 and defined in /Users/shuhei/Documents/src/googleAppEngine/phpzend/vendor/zendframework/zend-servicemanager/src/Config.php on line 65

很清楚他们正困扰于无法使用 glob 函数来扫描 config/autoload 目录下的定义文件。

Load configuration for Google App Engine

在加载定义文件时存在两个问题,具体如下:

    • glob()関数を使っている

 

    定義ファイルの内容をキャッシュする際の出力先がファイル (file_put_contents)

我已经为Google App Engine创建了一个加载处理程序。

    • glob()関数を opendir()/readdir()関数に変更

 

    キャッシュ出力先を、ファイルからMemcacheへ変更

将以下内容配置为 config/config-gae.php。

<?php

use Zend\Stdlib\ArrayUtils;

/**
 * Configuration files are loaded in a specific order. First ``global.php``, then ``*.global.php``.
 * then ``local.php`` and finally ``*.local.php``. This way local settings overwrite global settings.
 *
 * The configuration can be cached. This can be done by setting ``config_cache_enabled`` to ``true``.
 *
 * Obviously, if you use closures in your config you can't cache it.
 */

$cachedConfigKey = 'cache_app_config';

$mc = new Memcached();

// Try to load the cached config
if(!($config = $mc->get($cachedConfigKey))) {
    if ($mc->getResultCode() == Memcached::RES_NOTFOUND) {
        $config = [];
    }
    $confdir = __DIR__ . '/autoload';
    if ($handle = opendir($confdir)) {
        $pattern = '/(global|local)\.php$/';
        $files = [];
        while (false !== ($file = readdir($handle))) {
            if (preg_match($pattern, $file) === 1) {
                $fn = implode('.', array_reverse(explode('.', $file)));
                $files[] = $fn;
            }
        }
        asort($files);
        foreach($files as $file) {
            $fn = implode('.', array_reverse(explode('.', $file)));
            $config = ArrayUtils::merge($config, include $confdir.'/'.$fn);
        }
        closedir($handle);
    }

    // Cache config if enabled
    if (isset($config['config_cache_enabled']) && $config['config_cache_enabled'] === true) {
        $mc->set($cachedConfigKey, $config);
    }
}

// Return an ArrayObject so we can inject the config as a service in Aura.Di
// and still use array checks like ``is_array``.
return new ArrayObject($config, ArrayObject::ARRAY_AS_PROPS);

编辑调用方的config/container.php文件。

// Load configuration
//$config = require __DIR__ . '/config.php';
$config = require __DIR__ . '/config-gae.php';

在本地環境中進行操作驗證(成功)

SDKのWebサーバが自動的にリロードしてくれるので、
ブラウザをリロードすれば、正常に表示されるはずです。

Zend Expressive

app_config.php の最後に記載しているように、
エラー画面テンプレートも用意されているので、404 Not Foundの画面も表示できます。

部署

请参考:https://cloud.google.com/appengine/docs/php/quickstart#deploy_your_app

使用此网址https://console.developers.google.com/来创建一个项目,并将其部署到相应的项目ID上。

$ appcfg.py -A YOUR_PROJECT_ID update app.yaml

http://(YOUR_PROJECT_ID).appspot.com/ 的中文释义

未来在推进开发过程中可能会出现哪些问题,我不清楚,但我们已经迈出了第一步,项目已完成。