composer itself is managed by composer? - php

Maybe just a stupid question.
After I download/clone composer source code from github.com, how can I run it or compile it into a phar file?
When running "php bin/composer -v", it shows such errors:
php bin/composer -v
You must set up the project dependencies using `composer install`
See https://getcomposer.org/download/ for instructions on installing Composer
Is it said that I must download another composer.phar file and run "php composer.phar install" first?
I think it is a recursive way, "composer" itself is managed by composer :(

At first: if someone wants just to use composer, they must not install it from GitHub, just follow the installation guide: https://getcomposer.org/download/
OK, back to the question.
"composer" itself is managed by composer
Yes, and why do you think it is bad?
See the official documentation for contributors. It encourages exactly that way:
Run git clone https://github.com/composer/composer.git
Download the composer.phar executable
Run Composer to get the dependencies: cd composer && php ../composer.phar install
Then you can actually use composer by launching bin/composer, or you can compile it into phar by bin/compile.
If you wonder how are composer binaries actually built, you can see it in their Travis config. They just grab previous composer release provided by Travis, and build new composer release with it.

Composer's job is to locate and install dependencies for a particular project. Everything it does could be done by hand, mostly simply by placing files in the right location, and referencing a series of autoloaders.
In order to build Composer from scratch, you need certain code that is outside of the main Composer repository, such as command-line and logging helpers. You could download all of these manually, but the natural way is to use an existing install of Composer to fetch them.
This is only necessary if you are working on Composer itself, because once you have a successful build, you can produce a PHAR file, which contains all the required code including those third-party dependencies. These are the files distributed as official releases, and are all most people need; the tool even has a self-update command which downloads a new PHAR file and overwrites the one you ran.
This kind of bootstrapping - using an existing build of a tool as part of its own build process - is actually quite common. There are some parts of PHP itself which are generated using a PHP script, and I believe the first feature-complete C++ compiler was written in C++.

Related

What exactly is the difference between project and library types in composer?

I have a hard time figuring this out; I am also puzzled of the connection - if any - with the create-project command.
As far as I can tell, the only difference between install and create-project is the execution of post-root-package-install and post-create-project-cmd hooks...
Can someone shed some more light on this?
My goal is to set up a composer infrastructure where I run create-project and this sets up a project skeleton (creates and sets directory permissions, creates default configuration files, creates blank data stores)
What exactly is the difference between project and library types in composer?
Practically, there is none. It doesn't affect how composer gets executed. You can use both install and create-project with both types of package types.
This metadata is meant to inform plugins, IDE, or even packagist.org when parsing composer.json, but on a vainilla installation, there is no practical difference in using one or the other.
(Docs on package types)
As far as I can tell, the only difference between install and create-project is the execution of post-root-package-install and post-create-project-cmd hooks.
The docs are your friends:
You can use Composer to create new projects from an existing package. This is the equivalent of doing a git clone/svn checkout followed by a composer install of the vendors.
Any time you do create-project, install is executed as well. Which means that the install hooks are executed as well.
First it clones the whole package via the appropriate CVS (git, usually), and then immediately executes composer install. By default, it removes CVS information (e.g. the .git directory), unless one uses the --keep-vcs option.
create-project is useful to bootstrap applications, so the app's directory is setup beyond what downloading composer`s dependencies would do. You can create a skeleton directory structure, etc.
Usually one would have a package proper (that could be required into an application), and a "application-skeleton" package, that would include the directory structure and would depend on the original package.
I'm posting a more succint answer to my questions, based on experimentation:
What is the difference between project and library types?
Absolutely none as far as composer is concerned. Some plugins might implement logic to treat the two package types differently though.
How does that relate to require, install, create-project commands?
In no way whatsoever. The project in package type has nothing to do with project in create-project.
How does create-project work?
Let's say we are talking about a single <package>. We have 2 workflows:
composer init <project_path> && composer require <package>
composer create-project <package> <project_path>
The first workflow will create a blank root package and add <package> as a requirement to it.
The second workflow will "clone" <package> into <project_path> as the root package.
NB: If you are working with local path type repos for development, create-project will actually create <project_path> as a symlink to <package>'s source dir. This is the default behavior of path repos, and probably a miss for composer in the need to treat create-project differently. This can create a heap of confusion (as you might be inadvertently changing and adding to <package>s sources while thinking you are just editing project_path). So for local development and testing, you are better off with cp -A rather than composer create-project.

How can I run Composer from source and/or allow step-through debugging with PhpStorm?

I'm trying to troubleshoot a Composer command failure, and I'd like to step-through Composer's code so that I can inspect the program state at the time of failure.
Is it possible to run Composer from source, so that PhpStorm can more easily use Xdebug's step through debugging tool?
You can clone source code from repository and use it directly by bin/composer:
git clone https://github.com/composer/composer.git composer-src
cd composer-src
composer install
bin/composer --version
Add composer.phar to your project, and run that copy, not the global composer instance.
If you do that, PhpStorm includes support for working wit an debugging Phar files directly, as described here:
https://blog.jetbrains.com/phpstorm/2013/05/working-with-phar-packages-in-phpstorm/ (web archive link)
Or of course, you could simply download/clone the whole composer code inside your project, and use that. The source code includes a composer executable on bin/composer which you could execute directly. You'd need to do a full composer install as well to get the project's dependencies (which are already included in the phar file).
If you are running composer remotely (e.g. within a docker container), and using a global composer installation within your container (e.g. outside your project directory); when you start the debug session PhpStorm would complain about not being able to map the code.
In that case you could simply use path mappings under "Language and Frameworks -> PHP -> Server" to map the remote composer instance to a host installation.

How to get vendor folder in github project

Ive downloaded a helper library of an API written in PHP from GITHUB, but when I download the .zip file it doesnt contain vendor folder, but everywhere in the code it is seeking some files from vendor folder-which is error in running.
Can you help me how to get these? new to the system.
If you're working with PHP and you can't find a vendor/ directory that you expect to see, that PHP codebase probably uses Composer:
Composer is a tool for dependency management in PHP. It allows you to declare the dependent libraries your project needs and it will install them in your project for you.
One surefire way to know that a project uses Composer (aside from reading its documentation) is to see if there are composer.json and composer.lock files (probably) in the root of the repository. These files define the project's dependencies.
To generate the vendor/ directory,
install Composer,
there are a few ways to do this, and it is OS-dependent, but something like curl -sS https://getcomposer.org/installer | php should work if you're on Linux or OSX,
open a terminal and cd into the project directory,
run composer install,
depending on how you installed Composer, you may have to run php composer.phar install instead,
wait for Composer to do its thing.
Composer will download your dependencies, putting the code into vendor/, and generate an autoloader class that hooks everything together. Depending on what the dependencies are it might also do other things, like linking all CLI binaries to vendor/bin/.

installing laravel --prefer-dist

I am following the Laravel installation on their website
and I came across this line
composer create-project laravel/laravel --prefer-dist
Now, what exactly does the --prefer-dist part mean? I can't see anything on their documentation.
Thanks in advance.
--prefer-dist and --prefer-source are the two options of composer which included in various documentations with a lack of proper explanation.
--prefer-dist would try to download and unzip archives of the dependencies using GitHub or another API when available. This is used for faster downloading of dependencies in most cases. It doesn't download the whole VCS history of the dependencies and it should be better cached. Also archives on GitHub could exclude some files you don't need for just using the dependency with .gitattributes exclude directive.
--prefer-source would try to clone and keep the whole VCS repository of the dependencies when available. This is useful when you want to have the original VCS repositories cloned in your vendor/ folder. E.g. you might want to work on the dependencies - modify them, fork them, submit pull requests etc. while also using them as part of the bigger project which requires them in the first place.
Simply speaking, the --prefer-source option will prefer to create a package directory that is a "version control repository", which is equivalent to you typing:
$ git clone ...
or
$ svn checkout ...
On the other hand, the --prefer-dist option will prefer to create a non-"version control repository", which is equivalent to you typing:
$ git clone ... ; rm -fr dir/.git
or
$ svn export ...
Remember that, these are only preferences, if a dependency is required using a VCS repository which does not provide archives such as GitHub API, then the only available option is to clone the repository.
It's all available here: https://getcomposer.org/doc/03-cli.md#install
--prefer-dist: Reverse of --prefer-source, composer will install from dist if possible. This can speed up installs substantially on build
servers and other use cases where you typically do not run updates of
the vendors. It is also a way to circumvent problems with git if you
do not have a proper setup.
As per the link :
https://getcomposer.org/doc/03-cli.md#install
Here is the documentation statement for the question :-
--prefer-install: There are two ways of downloading a package: source and dist. Composer uses dist by default. If you pass --prefer-install=source (or --prefer-source) Composer will install from source if there is one. This is useful if you want to make a bugfix to a project and get a local git clone of the dependency directly. To get the legacy behavior where Composer use source automatically for dev versions of packages, use --prefer-install=auto. See also config.preferred-install. Passing this flag will override the config value.

How to create composer library package that auto generates code when included

Every time I create a new PHP project I basically use the same MVC folder structure that I adopted and like, I use the same base classes, interfaces, and the same PDO DAL implementation.
When I'm creating a new project I copy&paste all the needed files to the new project in addition to few changes, like changes to namespaces (to match the new project name) etc.
I thought, why not creating a simple script to copy those files and folders, and make the additional changes.
So now, when I create a new project I just run the script and the code is generated automatically, which is much nicer.
And then I thought, I want it to be even simpler. I don't want to save the code in my computer, I want to save it on Github, and since I use and love composer, I thought I will make the Github project a composer package.
But when trying to implement it I realized that I can't make the new composer package auto generate the code that I want, or at least I don't know how to make it do that.
I tried googling it with no success.
Does anyone knows how to achieve this?
I don't see any need to generate code here. Simply add your skeleton files to your Git repository and use Composer's create-project feature. See the third point:
You can use Composer to create new projects from an existing package. This is the equivalent of doing a git clone/svn checkout followed by a composer install of the vendors.
There are several applications for this:
You can deploy application packages.
You can check out any package and start developing on patches for example.
Projects with multiple developers can use this feature to bootstrap the initial application for development.
An example of a major PHP project that supports this approach is Laravel. From its installation instructions:
Via Composer
The Laravel framework utilizes Composer for installation and dependency management. If you haven't already, start by installing Composer.
Now you can install Laravel by issuing the following command from your terminal:
composer create-project laravel/laravel your-project-name --prefer-dist
This command will download and install a fresh copy of Laravel in a new your-project-name folder within your current directory.
If you prefer, you can alternatively download a copy of the Laravel repository from Github manually. Next run the composer install command in the root of your manually created project directory. This command will download and install the framework's dependencies.
Edit:
To have a script run after composer create-project completes you should be able to use a Composer script:
A script, in Composer's terms, can either be a PHP callback (defined as a static method) or any command-line executable command. Scripts are useful for executing a package's custom code or package-specific commands during the Composer execution process.
You are probably looking for the post-create-project-cmd event:
occurs after the create-project command is executed
Depending on whether your script is a static PHP method or a shell executable, you should define it as follows (modified from Composer documentation):
{
"scripts": {
"post-create-project-cmd": "MyVendor\\MyClass::postUpdate"
}
}
or
{
"scripts": {
"post-create-project-cmd": "my-shell-script arg1 arg2"
}
}

Categories