PHP Autoloader 在 Ubuntu 生产服务器上不起作用



我必须使用我正在开发API(基于PHP)的环境:

  1. 本地开发:Mac OS Yosemite-运行PHP 5.5.20
  2. 生产服务器:Ubuntu服务器-运行PHP 5.5.9

我的代码使用composer进行自动加载,如下所示:

{
    "require": {
        "facebook/php-sdk": "@stable",
        "everyman/neo4jphp": "dev-master",
        "predis/predis": "1.0.1",
        "aws/aws-sdk-php": "2.*"
    },
    "autoload": {
        "psr-0": {
            "PicoCore\": "",
            "PicoCore\Authentication\" : "PicoCore/authentication",
            "PicoCore\Aws\" : "PicoCore/aws",
            "PicoCore\Cache\" : "PicoCore/cache",
            "PicoCore\Database\" : "PicoCore/database",
            "PicoCore\Database\Managers\" : "PicoCore/database/managers",
            "PicoCore\Facebook\" : "PicoCore/facebook",
            "PicoCore\Objects\" : "PicoCore/objects",
            "PicoCore\Rest\" : "PicoCore/rest",
            "PicoCore\Configuration\" : "PicoCore/configuration",
            "PicoCore\Configuration\Api\" : "PicoCore/configuration/api",
            "PicoCore\Configuration\PictureReceiver\" : "PicoCore/configuration/pictureReceiver",
            "PicoCore\Configuration\PictureUploader\" : "PicoCore/configuration/pictureUploader",
            "PicoCore\Scripts\" : "PicoCore/scripts",
            "PicoCore\Times" : "PicoCore/times"
        }
    }
}

这是我的加载功能:

// autoload_namespaces.php @generated by Composer
$vendorDir = dirname(dirname(__FILE__));
$baseDir = dirname($vendorDir);
return array(
    'PicoCore\Times' => array($baseDir . '/PicoCore/times'),
    'PicoCore\Scripts\' => array($baseDir . '/PicoCore/scripts'),
    'PicoCore\Rest\' => array($baseDir . '/PicoCore/rest'),
    'PicoCore\Objects\' => array($baseDir . '/PicoCore/objects'),
    'PicoCore\Facebook\' => array($baseDir . '/PicoCore/facebook'),
    'PicoCore\Database\Managers\' => array($baseDir . '/PicoCore/database/managers'),
    'PicoCore\Database\' => array($baseDir . '/PicoCore/database'),
    'PicoCore\Configuration\PictureUploader\' => array($baseDir . '/PicoCore/configuration/pictureUploader'),
    'PicoCore\Configuration\PictureReceiver\' => array($baseDir . '/PicoCore/configuration/pictureReceiver'),
    'PicoCore\Configuration\Api\' => array($baseDir . '/PicoCore/configuration/api'),
    'PicoCore\Configuration\' => array($baseDir . '/PicoCore/configuration'),
    'PicoCore\Cache\' => array($baseDir . '/PicoCore/cache'),
    'PicoCore\Aws\' => array($baseDir . '/PicoCore/aws'),
    'PicoCore\Authentication\' => array($baseDir . '/PicoCore/authentication'),
    'PicoCore\' => array($baseDir . '/'),
    'Guzzle\Tests' => array($vendorDir . '/guzzle/guzzle/tests'),
    'Guzzle' => array($vendorDir . '/guzzle/guzzle/src'),
    'Everyman\Neo4j' => array($vendorDir . '/everyman/neo4jphp/lib'),
    'Aws' => array($vendorDir . '/aws/aws-sdk-php/src'),
);

当我在本地开发中运行代码时,它运行得很好,所以我把它推送到远程存储库,并从生产服务器中提取它。

当我试图在生产服务器中运行代码时,我收到一个Class not found错误,表明我的自动加载没有正确运行。

有什么想法吗?原因是什么?

更新:当我试图加载外部libs(如AWS)时,它确实有效,所以问题在于如何加载我的文件夹。

更新:这是我试图从index.php:加载的类

<?php
//require Pico Core autoload
require 'core/vendor/autoload.php';
//require Pico Api autoload
require 'vendor/autoload.php';
use PicoCoreRestApiInitializer;
use PicoCoreConfigurationError;
use PicoApiManagersApiManager;
try {
    //initialize the API
    ApiInitializer::initialize();
    //initialize a new Api with the request
    $api = new ApiManager($_REQUEST['request']);
    echo utf8_encode($api->processApi());
} catch (Exception $e) {
    echo json_encode(Array(Error::jsonErrorField() => $e->getMessage()));
}

这是我收到Class 'PicoCoreRestApiInitializer' not found 的错误

结构为:

api
 |
 core
   |
   PicoCore
      |
     folders..
     rest
      |
      ApiInitializer.php
     folders...
    vender
 PicoApi (folder)
 vendor (foldeR)
 index.php

这是错误的自动加载定义。

你想使用类

PicoCoreRestApiInitializer

你有这些文件:

api/index.php
api/vendor/...    (with your required external dependencies)
api/composer.json (with the autoloading mentioned in your question)
api/core/PicoCore/rest/ApiInitializer.php

你已经配置了这个自动加载:

"自动加载":{"psr-0":{"PicoCore\Rest\":"PicoCore/Rest"}}

这是不匹配的。当您使用类PicoCoreRestApiInitializer时,composer将尝试查找具有该类前缀的条目。它将成功地检测到,在目录(相对于composer.json的位置)PicoCore/rest中,可以通过PSR-0规则找到前缀为PicoCodeRest的类。

第一件奇怪的事情:这里有一个名为"core"的额外目录,并且您似乎包括两个自动加载器。不要这么做,Composer只使用一个自动加载器效果最好。

第二件事:如果我忽略"核心"目录一段时间,PSR-0规则规定类名将被转换为路径,然后在给定的前缀路径中进行搜索。

作为路径的PicoCoreRestApiInitializerPicoCore/Rest/ApiInitializer.php(注意"Rest"中的大写"R"),要找到的路径是PicoCore/rest/PicoCore/Rest/ApiInitializer.php

你没有这个文件。这就是为什么Composer找不到并加载它的原因。即使不计算这个"核心"目录级别,如果你使用两个composer.json文件,一个在apiapi/core,而api/core中的一个用于查找类,也不会找到它。

建议:

  1. 对命名空间中的每个类使用PSR-4
  2. 文件系统的命名空间或类名部分不要小写
  3. 缩短自动加载定义。如果您将PicoCore以下的所有小写目录重命名为命名空间中使用的正确大写变体,则只需要一行自动加载定义,即定义PicoCore前缀。其余部分由PSR-4(或PSR-0)完成

默认情况下,MacOS使用不区分大小写的文件系统,将其切换为区分大小写被认为是一件坏事:https://apple.stackexchange.com/questions/71357/how-to-check-if-my-hd-is-case-sensitive-or-not这就是为什么它可以在Mac上运行,但不能在Linux上运行。

相关内容

  • 没有找到相关文章

最新更新