Leveraging Composer
in Existing Projects
Mark Niebergall

https://joind.in/talk/774d7
About Mark Niebergall
• PHP since 2005
• Masters degree in MIS
• Senior Software Engineer
• Drug screening project
• UPHPU President
• CSSLP, SSCP Certified and SME
• Drones, fishing, skiing, father, husband
Leveraging Composer in
Existing Projects
Leveraging Composer in
Existing Projects
• Survey

- Have heard of composer?

- Are familiar with what composer is?

- Have used composer?

- Have contributed to composer?
Leveraging Composer in
Existing Projects
• My experience

- Large project that has been around a while

- Some older code areas

- Various architectural styles over the years

- Various libraries within the project
Leveraging Composer in
Existing Projects
• My experience

- Libraries scattered in project

- Some libraries were old

- Some libraries were even altered
Leveraging Composer in
Existing Projects
• My experience

- Made the effort to clean up libraries

- Identify libraries and versions

- Created user stories

- Made the migration
Leveraging Composer in
Existing Projects
• My experience

- Libraries were organized

- Visibility into libraries used

- Much easier to manage and upgrade

- Much easier to add new libraries
Leveraging Composer in
Existing Projects
• Objectives

- Know why and how to use composer

- Leverage composer in your projects
Leveraging Composer in
Existing Projects
• Topics

- What composer is

- Using composer 

- Migrating libraries
What composer is
What composer is
• Created by Nils Adermann and Jordi Boggiano in 2012

• MIT license
What composer is
• https://getcomposer.org/

- Installation instructions

- Documentation
What composer is
• Dependency manager for PHP projects
What composer is
• Tool to manage libraries used by a project
What composer is
• Best practice for dependency management for PHP
projects
What composer is
• Manage libraries

- Add libraries to project

- Autoload libraries

- Versioning

- Library dependencies

- Remove libraries
What composer is
• Uses packagist for package information

- https://packagist.org/

- Submit packages to website

- Versions

- Dependencies

- Location
What composer is
• Handles autoloading

- Automatically includes package files when needed

- Use along with other project autoloaders

‣ require_once __DIR__ . ‘/../vendor/autoload.php’;

require_once __DIR__ . ‘/../src/Autoloader.php’;
What composer is
Using composer
Using composer
• Installing composer

• Adding packages

• Updating packages

• Removing package
Using composer
• Installing composer

- Download phar installer file

- Run installer with php

- Move to bin

- curl -s https://getcomposer.org/installer | php

sudo mv composer.phar /usr/local/bin/composer
Using composer
• Installing composer

- Windows download https://getcomposer.org/
Composer-Setup.exe
Using composer
• Installing composer

- php /path/to/composer.phar command

- composer command
Using composer
• Installing composer

- Command line tool

- Are some UI helpers
Using composer
• composer package versioning
Using composer
• composer package versioning

- * = wildcard

- ~ = up to but not including next version

- ^ = up to but not including next major version
Using composer
• composer package versioning

- 4.5.2 means only 4.5.2
Using composer
• composer package versioning

- 4.5.* means 4.5 and below 4.6
Using composer
• composer package versioning

- ~4.5 means >= 4.5 and <5.0

- ~4.5.6 means >= 4.5.6 and < 4.6
Using composer
• composer package versioning

- ^4.5 means >= 4.5.0 and < 5

- ^4.5.6 means >= 4.5.6 and < 5

- Default versioning format if not specified
Using composer
• composer commands
Using composer
• composer commands

- composer init

- composer require

- composer install

- composer update

- composer create-project

- composer remove
Using composer
Using composer
• composer init
Using composer
• composer init

- Initialize a project with composer

- Creates autoloader

- Define basic settings

- Interactively install packages

- Creates composer.json file
Using composer
• composer init

{

"name": “mniebergall/composer",

"description": "Leveraging Composer in Existing Projects",

"authors": [

{

"name": "Mark Niebergall",

"email": “myemail@example.com”

}

],

"require": {}

}
Using composer
• composer require
Using composer
• composer require

- Add packages to a project

- Install the package plus dependencies
Using composer
• composer require

- Adds package to composer.json file

- Creates or updates the composer.lock file
Using composer
• composer require

- Package files are saved into the /vendor/ directory

- Autoloader is updated to load the package files
automatically
Using composer
• composer require

- Only run in development environment

- Not to be used in other environments
Using composer
• composer require

- composer require --dev vendor/package

‣ Only installs in development with ‘install’ command

• Testing frameworks (PHPUnit, behat, etc)

• Code analysis and statistics
Using composer
• composer require

- composer require --dev phpunit/phpunit



"require-dev": {

"phpunit/phpunit": "^6.3"

}
Using composer
• composer require

- composer require --dev fzaninotto/faker
Using composer
• composer require

- composer require --dev h4cc/phpqatools

‣ PHPUnit, PHP-Invoker, DbUnit, PHPLOC, PHPCPD,
PHP_Depend, PHPMD, PHP_CodeSniffer, Fabien
Potencier/PHP Coding Standards Fixer, Sensiolabs/
Security-Checker, and Behat
Using composer
• composer require

- composer require group/package

‣ See packagist for group/package

‣ Find project on GitHub, read the instructions

• Most will have composer installation command

• If not there are options
Using composer
• composer require

- composer require group/package VERSION

- composer require ramsey/uuid

- composer require ramsey/uuid 3.7

- composer require ramsey/uuid=^2.9

- composer require ramsey/uuid ^3.7
Using composer
• composer require

{

"name": “mniebergall/composer",

"description": "Leveraging Composer in Existing Projects",

"authors": [

{

"name": "Mark Niebergall",

"email": “myemail@example.com”

}

],

"require": {

"ramsey/uuid": “^3.7"

}

}

Using composer
• composer install
Using composer
• composer install

- Installs packages as defined in composer.lock file

- If no lock file then as defined in composer.json

‣ Generates composer.lock file
Using composer
• composer install

- composer install --no-dev

‣ Skips require-dev packages

‣ Use this in non-development environments

• We’ll discuss deployment considerations at the
end
Using composer
• composer install{

- phpsp, add this to composer.json

‣ "require-dev": {

"phpspec/phpspec": "^4.0"

},

"config": {

"bin-dir": "bin"

},

"autoload": {"psr-0": {"": “src”}}

‣ Then run composer install
Using composer
• composer update
Using composer
• composer update

- Updates packages to latest based on composer.json
contents

- Also updates necessary dependencies

- Updates content of composer.json and composer.lock
files
Using composer
• composer update

- composer update

‣ Update all packages

‣ Not recommended

- composer update group/package

‣ Target specific packages
Using composer
• composer update

- composer update group/package version

‣ composer update --dev phpunit/phpunit ^6
Using composer
• composer create-project
Using composer
• composer create-project

- New project from existing package

- Clones down repo, checkout, installs dependencies
Using composer
• composer create-project

- Skeleton projects

- Often used with projects using a framework

- Zend, Laravel, and others
Using composer
• composer remove
Using composer
• composer remove

- Removing lines from composer.json will not work
without a composer update
Using composer
• composer remove

- composer remove vendor/package

- Removes entry from composer.json

- Removes entry from composer.lock

- Removes dependencies

- Removes files from vendor directory
Using composer
• composer.json
Using composer
• composer.json

- Project configuration

- Packages to be used

- Package versions

- Used to generate composer.lock file
Using composer
• composer.json

- Can be manually updated

- Can run commands up update it

‣ composer require group/package
Using composer
• composer.json

- Define internally hosted packages

- Environment properties

‣ PHP version for compatibility
Using composer
• composer.lock
Using composer
• composer.lock

- Generated based on contents of composer.json

- Should not be manually edited

- Let composer manage contents
Using composer
• composer.lock

- Defines packages and dependencies to be installed

- composer install reads the composer.lock file
Using composer
Migrating libraries
Migrating libraries
• Benefits of migrating

• How to migrate
Migrating libraries
• Benefits of migrating

- Cleans the codebase

- Project only includes project files
Migrating libraries
• Benefits of migrating

- Centralizes library (package) management

- Easier library management
Migrating libraries
• Benefits of migrating

- Keep libraries current

‣ Bug fixes

‣ Security patches

‣ Features

‣ Performance
Migrating libraries
• How to migrate libraries
Migrating libraries
• How to migrate libraries

- Use source control

‣ Git (preferred)

‣ Mercurial
Migrating libraries
• How to migrate libraries

- Create user stories/tickets to track the progress
Migrating libraries
• How to migrate libraries

- Transparency with everyone impacted

‣ Development

‣ QA

‣ Project management

‣ Release team
Migrating libraries
• How to migrate libraries

- Identify libraries currently included in project

‣ Frameworks

‣ Tools

‣ Helpful libraries
Migrating libraries
• How to migrate libraries

- Identify libraries currently included in project

‣ Search for ‘@license’

‣ Tribal knowledge
Migrating libraries
• How to migrate libraries

- Vet libraries found

‣ Consolidation? ex: can framework do that?

‣ Secure?

‣ Altered? Run a compare? If so why?
Migrating libraries
• How to migrate libraries

- Vet libraries found

‣ Still needed? ex: deprecated functionality,
paragonie/random_compat or PHP 7?

‣ Better library available now?

‣ Best practices?

‣ Built into PHP core? ex: NuSOAP vs PHP Soap
Migrating libraries
• How to migrate libraries

- Find the package on packagist

‣ Actively maintained

‣ Popularity

‣ Community acceptance

‣ Documentation
Migrating libraries
• How to migrate libraries

- Find the package on packagist

‣ Determine desired version

‣ Review dependencies

‣ Consider alternatives
Migrating libraries
• How to migrate libraries

- Review the library source

‣ Unit tests

‣ Coding standards

‣ Time to close open bugs and security issues

‣ Architecturally sound
Migrating libraries
• How to migrate libraries

- Steps

‣ Tests

‣ Include the library using composer

‣ Remove old library files from source control

‣ Tests
Migrating libraries
• How to migrate libraries

- Steps

‣ Make a pull request

• .gitignore or equivalent ignores /vendor/

• Add changed files, including composer.json and
composer.lock
Migrating libraries
• How to migrate libraries

- Steps

‣ Make a pull request

• commit

• push

• create PR
Migrating libraries
• How to migrate libraries

- Steps

‣ Code reviews

• Automated tests

• Functional tests

• Peer review
Migrating libraries
• How to migrate libraries

- Steps

‣ Raise awareness

• QA team

• Project management

• Release team
Migrating libraries
Considerations
Considerations
• Handling altered libraries

- Understand why

- Use pure versions

- Make PR to fix issues

- Document what is wrong
Considerations
• Testing when updating packages

- composer update vendor/package version

- Domino effect with dependencies
Considerations
• Deployment

- composer install —no-dev

- From files

‣ Azer Koçulu case of unpublishing 250+ NPM
modules
Considerations
• Open discussion
Considerations
Questions?
• Rate on joind.in

- https://joind.in/talk/774d7
Sources
• https://www.theregister.co.uk/2016/03/23/
npm_left_pad_chaos/

• https://getcomposer.org/

Leveraging Composer in Existing Projects