1
0
Fork 0

Add docs about satis & why repositories are not loaded recursively

pull/495/merge
Jordi Boggiano 2012-03-23 20:58:12 +01:00
parent 202dc99b02
commit 04d2acda29
3 changed files with 116 additions and 9 deletions

View File

@ -20,7 +20,7 @@ In fact, internally composer sees every version as a separate package. While
this distinction does not matter when you are using composer, it's quite this distinction does not matter when you are using composer, it's quite
important when you want to change it. important when you want to change it.
In addition to the name and the version, there is useful data. The information In addition to the name and the version, there is useful metadata. The information
most relevant for installation is the source definition, which describes where most relevant for installation is the source definition, which describes where
to get the package contents. The package data points to the contents of the to get the package contents. The package data points to the contents of the
package. And there are two options here: dist and source. package. And there are two options here: dist and source.
@ -38,11 +38,16 @@ be preferred.
### Repository ### Repository
A repository is a package source. It's a list of packages, of which you can A repository is a package source. It's a list of packages/versions. Composer
pick some to install. will look in all your repositories to find the packages your project requires.
You can also add more repositories to your project by declaring them in By default only the Packagist repository is registered in Composer. You can
`composer.json`. add more repositories to your project by declaring them in `composer.json`.
Repositories are only available to the root package and the repositories
defined in your dependencies will not be loaded. Read the
[FAQ entry](faqs/why-can't-composer-load-repositories-recursively.md) if you
want to learn why.
## Types ## Types
@ -229,7 +234,9 @@ There are a few tools that can help you create a `composer` repository.
The underlying application used by packagist is open source. This means that you The underlying application used by packagist is open source. This means that you
can just install your own copy of packagist, re-brand, and use it. It's really can just install your own copy of packagist, re-brand, and use it. It's really
quite straight-forward to do. quite straight-forward to do. However due to its size and complexity, for most
small and medium sized companies willing to track a few packages will be better
off using Satis.
Packagist is a Symfony2 application, and it is [available on Packagist is a Symfony2 application, and it is [available on
GitHub](https://github.com/composer/packagist). It uses composer internally and GitHub](https://github.com/composer/packagist). It uses composer internally and
@ -249,12 +256,13 @@ You give it a `composer.json` containing repositories, typically VCS and
package repository definitions. It will fetch all the packages that are package repository definitions. It will fetch all the packages that are
`require`d and dump a `packages.json` that is your `composer` repository. `require`d and dump a `packages.json` that is your `composer` repository.
Check [the satis GitHub repository](https://github.com/composer/satis) for more Check [the satis GitHub repository](https://github.com/composer/satis) and
the [Satis article](articles/handling-private-packages-with-satis.md) for more
information. information.
## Disabling packagist ## Disabling Packagist
You can disable the default packagist repository by adding this to your You can disable the default Packagist repository by adding this to your
`composer.json`: `composer.json`:
{ {

View File

@ -0,0 +1,65 @@
# Handling private packages with Satis
Satis can be used to host the metadata of your company's private packages, or
your own. It basically acts as a micro-packagist. You can get it from
[GitHub](http://github.com/composer/satis).
## Setup
For example let's assume you have a few packages you want to reuse across your
company but don't really want to open-source. You would first define a Satis
configuration file, which is basically a stripped-down version of a
`composer.json` file. It contains a few repositories, and then you use the require
key to say which packages it should dump in the static repository it creates.
Here is an example configuration, you see that it holds a few VCS repositories,
but those could be any types of [repositories](../05-repositories.md). Then
the require just lists all the packages we need, using a `"*"` constraint to
make sure all versions are selected.
{
"repositories": [
{ "type": "vcs", "url": "http://github.com/mycompany/privaterepo" },
{ "type": "vcs", "url": "http://svn.example.org/private/repo" },
{ "type": "vcs", "url": "http://github.com/mycompany/privaterepo2" }
],
"require": {
"company/package": "*",
"company/package2": "*",
"company/package3": "*"
}
}
Once you did this, you just run `php bin/satis build <configuration file> <build dir>`.
For example `php bin/satis build config.json web/` would read the `config.json`
file and build a static repository inside the `web/` directory.
When you ironed out that process, what you would typically do is run this
command as a cron job on a server. It would then update all your package info
much like Packagist does.
Note that if your private packages are hosted on GitHub, your server should have
an ssh key that gives it access to those packages, and then you should add
the `--no-interaction` (or `-n`) flag to the command to make sure it falls back
to ssh key authentication instead of prompting for a password. This is also a
good trick for continuous integration servers.
Set up a virtual-host that points to that `web/` directory, let's say it is
`packages.example.org`.
## Usage
In your projects all you need to add now is your own composer repository using
the `packages.example.org` as URL, then you can require your private packages and
everything should work smoothly. You don't need to copy all your repositories
in every project anymore. Only that one unique repository that will update
itself.
{
"repositories": [ { "type": "composer", "url": "http://packages.example.org/" } ],
"require": {
"company/package": "1.2.0",
"company/package2": "1.5.2",
"company/package3": "dev-master"
}
}

View File

@ -0,0 +1,34 @@
# Why can't Composer load repositories recursively?
You may run into problems when using custom repositories because Composer does
not load the repositories of your requirements, so you have to redefine those
repositories in all your `composer.json` files.
Before going into details as to why this is like that, you have to understand
that the main use of custom VCS & package repositories is to temporarily try
some things, or use a fork of a project until your pull request is merged, etc.
You should not use them to keep track of private packages. For that you should
look into [setting up Satis](../articles/handling-private-packages-with-satis.md)
for your company or even for yourself.
There are three ways the dependency solver could work with custom repositories:
- Fetch the repositories of root package, get all the packages from the defined
repositories, resolve requirements. This is the current state and it works well
except for the limitation of not loading repositories recursively.
- Fetch the repositories of root package, while initializing packages from the
defined repos, initialize recursively all repos found in those packages, and
their package's packages, etc, then resolve requirements. It could work, but it
slows down the initialization a lot since VCS repos can each take a few seconds,
and it could end up in a completely broken state since many versions of a package
could define the same packages inside a package repository, but with different
dist/source. There are many many ways this could go wrong.
- Fetch the repositories of root package, then fetch the repositories of the
first level depencies, then fetch the repositories of their dependencies, etc,
then resolve requirements. This sounds more efficient, but it suffers from the
same problems than the second solution, because loading the repositories of the
dependencies is not as easy as it sounds. You need to load all the repos of all
the potential matches for a requirement, which again might have conflicting
package definitions.