Composer require-dev requireing dependencies in different packages require-dev - php

I have some tests that are namespaced being autoloaded in package A using
"autoload-dev": {
"psr-4": {
"Vendor\\PackageA\\PhpUnit\\": "tests/PhpUnit"
}
},
This works fine.
I have another package, package B which also have namespaced tests that require one of the namespaced tests in package A
"autoload-dev": {
"psr-4": {
"Vendor\\PackageB\\PhpUnit\\": "tests/PhpUnit"
}
},
However, when I try and include the file in Package B, the class is not found
use Vendor\PackageA\PhpUnit\MyTestFromA;
class MyTestFromB extends MyTestFromA
{
Making me think that the autoload-dev stuff from other packages is not being loaded.
PHP Fatal error: Class 'Vendor\PackageA\PhpUnit\MyTestFromA' not found in /full/path/to/PackageBClass.php on line 3
When I try and import a file that is being autoloaded using autoload from package B rather than autoload-dev, I get no error.
How can I overcome this?
Part of me is thinking to make a package just for the tests and have it autoloaded in both without autoload-dev but I want to confirm first.

Solution: Composer autoload-dev does not work.
Take a look at the docs. It says: "autoload-dev (root only)". root only means it only applies to the root package. As you included the package, the shown composer.json file is not the root package and the autoload-dev section is thus ignored.

Related

How can I check if PHP Composer autoload is working?

I am trying to transfer a small web application, which uses PHP Composer, from an old out of date server to a new server.
On the new server, I have run composer install to install the dependencies from the composer.lock file.
The web application requires a config file to set itself up (not that it does a lot of setting up), which includes the line
require_once __DIR__ . '/vendor/autoload.php';
…which should locate the autoloader relative to the config file, and make the packages installed by Composer known to the system.
However, this doesn't seem to be working properly, as when the web app tries to use SwiftMailer (which was installed via Composer), it says:
PHP Fatal error: Uncaught Error: Call to undefined method Swift_SmtpTransport::newInstance()
…in the file that calls it, which obviously suggests that it does not know about it and cannot find it.
Is there a way that I can meaningfully check what the result of the autoloader include is and see what it is (or is not) doing?
Make sure to add a use statement to your classes. You can arrange your classes and give your classes namespaces then allow composer to also auto-load your classes.
You can tell composer how your classes are arranged according to namespaces as follows:
In the autoload section of your composer.json file edit it to know how the namespaces of your classes is arranged
"autoload": {
"psr-4": {
"App\\": "src/",
"Mynamespace\\": "lib/src/ProjectSrc/"
}
},
The autoload section now tells composer the Classes in the ProjectSrc folder will have a root namespace of Mynamespace. From this information composer can determine all other sub namespaces in your directory tree. This will not happen automatically composer has to rebuild its mapping of classes with the composer dump-autoload command.

Composer complains about non-compliance to PSR-4, even though everything seems fine

In my project, I'm including a package I'm developing, which has a composer.json, which includes the following autoload entry:
(censored to not get in trouble with my company of course)
{
"autoload": {
"psr-4": {
"Vendor\\Package\\": "src/Package"
}
}
}
The main project and the package both have a composer.json, this is from the package's composer.json
I have also seen some examples that only used "Vendor\\", but this resulted in the exact same issue.
I am requiring the package on version tag (from a git repository), so it should get and install the package correctly.
Any time composer runs autoload, it complains the namespaces don't conform to PSR-4. I have checked the capitalisation, which all checks out. It complains about pretty much every php file in my project. Here's an example of the file structure:
vendor
|- package
|- src
|- Package
|- PackageServiceProvider.php
The namespace of PackageServiceProvider.php is Vendor\Package, and the class is PackageServiceProvider.
As far as I know, this is how it's supposed to be. Yet composer still gives the deprecation notice.
I should probably mention that I have also tried running composer clearcache between all of the things I've tried (which are mainly changing capitalisation), which didn't help.
I am completely out of ideas on how to fix this.
I'm on composer version 1.10.13, and Laravel version 5.8.38.
One of the many deprecation notices I'm getting:
Deprecation Notice: Class Vendor\Package\PackageServiceProvider located in D:/wwwroot/project/vendor/{package-vendor}/package/src/Package\PackageServiceProvider.php does not comply with psr-4 autoloading standard. It will not autoload anymore in Composer v2.0. in phar://C:/Users/me/AppData/Local/ComposerSetup/bin/composer.phar/src/Composer/Autoload/ClassMapGenerator.php:201
As it turns out, the version of the package that's on our git repository, had a mistake in its composer.json which I'd long fixed locally. But since it wasn't fixed on the repo, composer had never finished updating the dependencies, and hadn't updated its links to the packages.
All I had to do was change
{
"autoload": {
"psr-4": {
"Vendor\\": "src/Package"
},
}
}
to
{
"autoload": {
"psr-4": {
"Vendor\\Package\\": "src/Package"
},
}
}
and push it to the repository.
That's wrong approach. That package, which apparently you manually planted in your vendor/ folder (which is, let's say, moderately OK) should be valid composer package with own composer.json file. Then ordinary composer dumpautoload would perfectly suffice to build class map for autoloading. No oddities like yours needed.

Source from vendor loaded and compiled as files from src directory

I am trying the new Symfony4 (framework bundle) and I wanted to move some my reusable classes from src directory to vendor one (loaded via composer PSR-4).
So I created a package (new git repository), added classes there (into src directory), added PSR-4 configuration into package's composer.json like this:
"autoload": {
"psr-4": { "\\": "src/" }
}
and I ran composer require <name_of_my_package> and I dumped autoload.
All went smooth, but when I wanted to access any class from my package - for my surprise - Symfony cannot find and use any of these classes (even though they are in autoload files of composer).
I think that I need to somehow add these classes to Symfony container builder, but I am not sure how.
Thanks for all help.

Class for command controller not put to autoload

I have a composer based TYPO3 7.6 installation and want to create an Extbase extension with a command controller.
The controller is registered in ext_localconf.php but the commmand controller isn't found because the class is not found in typo3/sysext/extbase/Classes/Mvc/Cli/CommandManager.php in public function getAvailableCommands()
Namespace is also set: namespace Foo\FooT3monitoringNotification\Command;
The class is here Classes/Command/NotificationCommandController.php.
I've cleared all TYPO3 caches and did composer dump-autoload. Any idea, what I missed to do or what I can do to find out, why my class isn't put to autoload?
As your newly created extension is not installed via composer, you need to define where to look for the classes. Therefore you need to add an autoload section to your root composer.json (that' means not in your extension, but in your TYPO3 distribution root folder):
"autoload": {
"psr-4": {
"Foo\\FooT3monitoringNotification\\": "web/typo3conf/ext/foo_t3monitoring_notification/Classes"
}
}
More information: https://usetypo3.com/typo3-and-composer.html#c67

How can I autoload classes with composer where the filenames are suffixed with .class.php?

I am using composer autoloader for my classes too, but my problem is that files with my classes follow the pattern ClassName.class.php and composer can load files only with .php extension.
Is there any way how to define file pattern in composer.json? I was checking classmap, but it doesn't support patterns.
Classmap autoloading should be your friend, see https://getcomposer.org/doc/04-schema.md#classmap.
Just specify the path to wherever you've got your files, let's say when your files reside in src, for example, src/Foo/Bar.class.php, then update your composer.json like this
{
"autoload": {
"classmap": [
"src/"
]
}
}
You will need to regenerate the classmap, though, every time you add a new file:
$ composer dump-autoload

Categories