I was able to successfully deploy my Yii2 app to Heroku from my Github repo. However, when I try to access the domain provided by Heroku (https://portfolio-php.herokuapp.com) I get an error saying "Forbidden You don't have permission to access / on this server." My build logs are provided below. Can someone please offer any guidance?
-----> PHP app detected
-----> Resolved 'composer.lock' requirement for PHP to version 5.6.14.
-----> Installing system packages...
- PHP 5.6.14
- Apache 2.4.17
- Nginx 1.8.0
-----> Installing PHP extensions...
- mbstring (composer.lock; bundled)
- zend-opcache (automatic; bundled)
-----> Installing dependencies...
NOTICE: Using '/composer.phar' to install dependencies.
Composer version 1.0-dev (9e67bc761be98b45875855003eb8b2f23f4bf5a5) 2015-09-18 14:32:06
Loading composer repositories with package information
Installing dependencies from lock file
- Installing yiisoft/yii2-composer (2.0.3)
Loading from cache
- Installing bower-asset/jquery (2.1.4)
Loading from cache
- Installing bower-asset/jquery.inputmask (3.1.63)
Loading from cache
- Installing bower-asset/punycode (v1.3.2)
Loading from cache
- Installing bower-asset/yii2-pjax (v2.0.4)
Loading from cache
- Installing cebe/markdown (1.1.0)
Loading from cache
- Installing ezyang/htmlpurifier (v4.6.0)
Loading from cache
- Installing yiisoft/yii2 (2.0.6)
Loading from cache
- Installing bower-asset/bootstrap (v3.3.5)
Loading from cache
- Installing yiisoft/yii2-bootstrap (2.0.4)
Loading from cache
- Installing swiftmailer/swiftmailer (v5.4.1)
Loading from cache
- Installing yiisoft/yii2-swiftmailer (2.0.4)
Loading from cache
Generating optimized autoload files
-----> Preparing runtime environment...
NOTICE: No Procfile, using 'web: vendor/bin/heroku-php-apache2'.
-----> Discovering process types
Procfile declares types -> web
-----> Compressing... done, 80.9MB
-----> Launching... done, v12
https://portfolio-php.herokuapp.com/ deployed to Heroku
I am using the basic Yii2 template. There is no htaccess file and the config file reads:
<?php
$params = require(__DIR__ . '/params.php');
$config = [
'id' => 'basic',
'basePath' => dirname(__DIR__),
'bootstrap' => ['log'],
'components' => [
'request' => [
// !!! insert a secret key in the following (if it is empty) - this is required by cookie validation
'cookieValidationKey' => 'gfWIx3XdsOCYeUve6VVm1KF4VayT0z7t',
],
'cache' => [
'class' => 'yii\caching\FileCache',
],
'user' => [
'identityClass' => 'app\models\User',
'enableAutoLogin' => true,
],
'errorHandler' => [
'errorAction' => 'site/error',
],
'mailer' => [
'class' => 'yii\swiftmailer\Mailer',
// send all mails to a file by default. You have to set
// 'useFileTransport' to false and configure a transport
// for the mailer to send real emails.
'useFileTransport' => true,
],
'log' => [
'traceLevel' => YII_DEBUG ? 3 : 0,
'targets' => [
[
'class' => 'yii\log\FileTarget',
'levels' => ['error', 'warning'],
],
],
],
'db' => require(__DIR__ . '/db.php'),
],
'params' => $params,
];
if (YII_ENV_DEV) {
// configuration adjustments for 'dev' environment
$config['bootstrap'][] = 'debug';
$config['modules']['debug'] = [
'class' => 'yii\debug\Module',
];
$config['bootstrap'][] = 'gii';
$config['modules']['gii'] = [
'class' => 'yii\gii\Module',
];
}
return $config;
If your app is called basic, this url should work:
https://portfolio-php.herokuapp.com/basic/web
How to get the basic app working in domain/
1) Move all files from /web directory to public_html or whatever
2) Put the rest of files in the upper level, so you get something like that:
[...]
commands
config
controllers
models
web (empty)
...
public_html
- assets
- index.php
- css
- [...]
3) Change the index.php you've moved to /public_html and change paths to config files, vendor, etc.
4) Create an .htaccess in this directory with the following:
Options +FollowSymLinks -Indexes
IndexIgnore */*
RewriteEngine on
# if a directory or a file exists, use it directly
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
# otherwise forward it to index.php
====
Update
Check if https://portfolio-php.herokuapp.com/basic/requirements.php works, If not, you should reinstall all composer dependencies:
Backup your vendor folder and composer.lock
Delete all files in vendor folder
Do composer install --prefer-dist
Thank you for your help. It works now. The answer was the following:
"Your application is in the folder basic. That itself should be the repository. You instead put the parent folder of basic under version control, which means all the paths in Yii are wrong as you at some point tried moving composer.json up one level.
When you follow the instructions in the Yii manual, you need to cd basic/ after you created the project.
You also need to remove the dev/debug stuff from the top of web/index.php:
// defined('YII_DEBUG') or define('YII_DEBUG', true);
// defined('YII_ENV') or define('YII_ENV', 'dev');
and add fxp/composer-asset-plugin to your project's composer.json.
Then it all works just fine"
Related
I am on a cpanel shared hosting and don't have access to SSH. How can I install Collective\Html\HtmlServiceProvider without SSH?
If I had SSH access I would use:
composer require laravelcollective/html
But I don't know what to do now.
Another solution would be downloading it locally with composer and uploading the entire project (including the vendor folder) with a ftp client.
Step 1:
Go to https://github.com/LaravelCollective/html and download the repo.
Step 2
Copy the zip and navigate to your project. Inside the vendor folder create folder laravelcollective and then inside html. Inside the html folder place the repo.
Step 3
On your composer.json file on the root directory of your project add the following lines.
"autoload": {
"psr-4": {
"Collective\\Html\\": "vendor/laravelcollective/html/src/"
},
}
and then do
composer dump-autoload
Step 4
Next, add your new provider to the providers array of config/app.php:
'providers' => [
// ...
Collective\Html\HtmlServiceProvider::class,
// ...
],
Finally, add two class aliases to the aliases array of config/app.php:
'aliases' => [
// ...
'Form' => Collective\Html\FormFacade::class,
'Html' => Collective\Html\HtmlFacade::class,
// ...
],
Using composer, I have installed Socialite package to my local machine. It works well. Then I upload all the vendor/laravel/socialite directory as it is to server. Then on server, in composer.json added the line -
"laravel/socialite": "^2.0"
Also, in config/app.php make below changes -
In provider section add the line -
Laravel\Socialite\SocialiteServiceProvider::class,
In aliases section add this line -
'Socialite' => Laravel\Socialite\Facades\Socialite::class,
Then, as per documentation add below code in config/services.php file -
'facebook' => [
'client_id' => '{{my_client_id}}',
'client_secret' => '{{my_secret_key}}',
'redirect' => 'http://mydomain/public/callback',
],
The Controller, I am using has included use Socialite; at top.
Bur now, it gives me error as Class 'Socialite' not found on server. Where as it works fine on my local machine.
Am I missing something to upload on server?
Your help is appreciated.
Thanks.
You need to do dump autoload everytime you make changes in composer.json, composer dump-auto
I am begin to learn Yii2 and installed Advanced version. Add extensions. Configure application and load to server. After sometime I noticed that Yii save the assets cache to directory web/assets. But is logical use this directory for real assets. Because I use Twig web/assets uses for js and css files.
And I start search how to change assets cache directory, but not found this. Exist several questions on stackoverflow about like themes, but answer was not found.
Yii2 save ti this dir cache of bootstrap, jquery and any assets.
How to change this directory to web/cache?
You can configure the assets directory using the basePath and baseUrl properties of the Asset Manager. There's is a description in the documentation. you can do this in your config file, so
return [
// ...
'components' => [
'assetManager' => [
'baseUrl' => 'your/url',
'basePath => 'your/path'
],
],
];
I have installed a package (ipunkt/laravel-notify) that has assets that need to be published to the public folder. I have tried
php artisan asset:publish ipunkt/laravel-notify
and I get the message
Assets published for package: ipunkt\laravel-notify
however public/packages remains empty.
Any suggestions?
Had to change
'public' => __DIR__.'/../..'
to
'public' => __DIR__.'/../public'
in bootstrap/paths.php
I'm developing on a project which uses Monolog, which requires Psr/log.
When I use Monolog by autoload, it then complains about missing Psr\Log\LoggerInterface.
So I look through the composer generated autoload_namespaces.php, and I couldn't find Psr being registered.
Here's the contents of my vendor/autoload_namespaces.php
return array(
'Symfony\\Component\\Process' => $vendorDir . '/symfony/process/',
'Monolog' => $vendorDir . '/monolog/monolog/src/',
'Imagine' => $vendorDir . '/imagine/Imagine/lib/',
'Gedmo' => $vendorDir . '/gedmo/doctrine-extensions/lib/',
'Gaufrette' => $vendorDir . '/knplabs/gaufrette/src/',
'Evenement' => $vendorDir . '/evenement/evenement/src',
'Doctrine\\ORM' => $vendorDir . '/doctrine/orm/lib/',
'Doctrine\\DBAL' => $vendorDir . '/doctrine/dbal/lib/',
'Doctrine\\Common' => $vendorDir . '/doctrine/common/lib/',
'Assetic' => $vendorDir . '/kriswallsmith/assetic/src/',
'Analog' => $vendorDir . '/analog/analog/lib/',
);
Is composer supposed to register namespaces for all projects which has {autoload} defined in their composer.json files? (I checked both Monolog and Psr/Log, they both have {autoload} defined.)
Or am I getting the wrong idea about composer?
You need to explicitly add
"psr/log": "1.0.0"
in your composer.json require block. The project monolog/monolog doesn't require psr/log [you can verify that in monolog's composer.json file].
Then run composer update to update your autoloader file.
[UPDATE] Made a mistake.
I am using monolog 1.2.* and it doesn't require psr/log. After monolog 1.3.*, it does requires psr/log. In that case, composer should load psr/log namespace in vendor/autoload_namespaces.php.
For example, I just updated my composer.json to have
"monolog/monolog": "1.3.*",
in the require block. Then run composer update monolog/monolog [you can run this command again to see if it fixes your problem]
Loading composer repositories with package information
Updating dependencies (including require-dev)
- Installing psr/log (1.0.0)
Loading from cache
- Removing monolog/monolog (1.2.1)
- Installing monolog/monolog (1.3.1)
Downloading: connection...
Downloading: 100%
Then in my vendor/composer/autoload_namespaces.php, I found this proper entry:
'Psr\\Log\\' => $vendorDir . '/psr/log',
This should work. Sometimes I also just run
composer dump-autoload
to re-generate vendor/composer/autoload_namespaces.php file again.
I was actually confused by the number of autoload_namespaces.php there are.
The one I posted in my question was in vendor/, then I found another one in vendor/.composer/, and finally found the CORRECT one in vendor/composer/.
Sorry for the answering my own (stupid) question but it's worth mentioning in case some other developers have the same trouble.
And thanks to #Chuan Ma for the answer.
Composer registers classes based on the autoloadin the project's composer.json file, e.g.
{
"autoload": {
"classmap": [
"path/to/FirstClass.php",
"path/to/SecondClass.php"
]
}
}
Normally composer update will automatically regenerate autoload_namespaces.php lists all namespaces which your application can use (unless you're using multiple autoloaders).
If the namespaces are missing, here is the command to update the composer autoloader directly:
composer dump-autoload -o
Then you need to make sure you include the autoloader at the top of our scripts:
<?php
require_once __DIR__ . '/vendor/autoload.php';
See: How to directly autoload classes with Composer?
If it's still failing, double check the syntax in the failing project's composer.json file (especially autoload section). To debug, try running composer with -vvv or under XDebug.