I am developing a package - myvendor/mylib - that I plan to distribute using Composer, probably via Packagist. This package contains - among other things - a commandline PHP script bin/console.php that I would like to make available to projects - say myvendor/mymain - that import the mylib package.
I am aware that I can specify in the mylib package a config setting in composer.json with an array of bins to import:
{
"name": "myvendor/mylib",
"config" : {
"bin" : ["bin/console.php"]
}
}
When the mymain project does a composer install/update, then this mylib/bin/console.php is symlinked as mymain/bin/console.php Further, I am aware that the mymain project can specify - in his own composer.json - where he wants dependency bins to be symlinked:
{
"name": "myvendor/mymain",
"config": {
"bin-dir": "scripts"
}
}
In this case, the console script is then symlinked as scripts/console.php.
This works fine - and is cool as as all get out, by the way. ;-)
However, the script bin/console.php itself needs to include the Composer-generated vendor/autoloader.php. When developing mylib in isolation, the script bin/console.php knows his own location relative to vendor/autoloader.php, so he can include it easily. But once it is imported as a dependency into another project - myvendor/mymain, in this case - then there is only the mymain/vendor/autoloader.php script. In principle, the console script cannot know where he resides relative to that autoloader script.
Does Composer provide some environment variable - accessible to the console script - that allows the script to locate the right vendor/autoloader.php script?
BTW: I am aware of the Composer CLI environment variable, so I imagine I could make it a requirement that the importing project - mymain - define (and export!) the var COMPOSER_VENDOR_DIR. Then my console script can use that to find the project's autoloader. But that seems potentially problematic in that:
We want the setting to apply only to this project, but a shell var (and an export) would apply to all projects accessed from that shell session. Seems presumptuous of my little dependency - myvendor/mylib - to impose that on an importing project.
In principle, the dependency itself - myvendor/mylib - should be able to find what he needs. Doesn't seem right to put the onus on the importer.
WDYT? Thanks in advance. Ideas welcome.
One approach (that came out of discussions with #igorw on IRC freenode #composer that I am paraphrasing and on which I am somewhat expanding) is to let the bin script console.php iterate up the filesystem, starting from __DIR__, looking for the presence of autoload.php.
Related
I want to install html-to-markdown without composer but I can't figure it out, with other libraries like Parsedown it worked just by using file location, but with html-to-markdown I don't know what I should use
This is the link for html-to-markdown
In your link there is a chapter How to use it with step by step instructions for installation.
Make sure to add require 'vendor/autoload.php'; to the top of your script, where you want to use the package.
First, use GitHub's "Code/ Download ZIP" option to get the code:
To figure out the requirements of an application meant to be installed with Composer, you need to inspect the composer.json file in the root directory:
The require key tells us the PHP extensions and third-party libraries needed:
"require": {
"php": "^7.2.5 || ^8.0",
"ext-dom": "*",
"ext-xml": "*"
},
In this case, the library is standalone, so you just need to verify your PHP installation meets the requirements. If it happened to need other packages, you'd have to repeat this for every package involved.
The autoload key tells us how the library locates and opens the files with class definitions:
"autoload": {
"psr-4": {
"League\\HTMLToMarkdown\\": "src/"
}
},
This library depends on Composer's PSR-4 autoloader implementation. We'll get back to this.
There may be other important information in the file, but in this particular case this is pretty much everything.
Regarding the autoloader... If your codebase already implements PSR-4, you just need to configure a new League\HTMLToMarkdown namespace and download the source code in the location expected by your autoloader, keeping the folder structure intact. Otherwise, I can think of a number of options, none of them particularly attractive:
Write your own autoloader.
Find a third-party PSR-4 autoloader.
Get a list of all relevant source PHP files and load them all manually:
$ find . -name '*.php'
./src/Environment.php
./src/Configuration.php
./src/Element.php
./src/ElementInterface.php
./src/PreConverterInterface.php
./src/HtmlConverterInterface.php
./src/ConfigurationAwareInterface.php
./src/Converter/TextConverter.php
./src/Converter/TableConverter.php
./src/Converter/ListItemConverter.php
./src/Converter/ListBlockConverter.php
./src/Converter/PreformattedConverter.php
./src/Converter/ConverterInterface.php
./src/Converter/DivConverter.php
./src/Converter/BlockquoteConverter.php
./src/Converter/HorizontalRuleConverter.php
./src/Converter/DefaultConverter.php
./src/Converter/CodeConverter.php
./src/Converter/ImageConverter.php
./src/Converter/HardBreakConverter.php
./src/Converter/ParagraphConverter.php
./src/Converter/EmphasisConverter.php
./src/Converter/CommentConverter.php
./src/Converter/HeaderConverter.php
./src/Converter/LinkConverter.php
./src/HtmlConverter.php
Make this into a list of require '...'; commands and play around with file order until you don't get errors.
(I know others have written about this, but the answers don't seem to help in this instance)
I have a WordPress PHP plugin (https://github.com/LiquidChurch/lqd-messages/) which uses WDS-Shortcodes which in turn uses TGM-Plugin-Activation. When I run composer install from within the lqd-messages plugin I get the following error:
In ClassMapGenerator.php line 69:
Could not scan for classes inside "/lqd-messages/vendor/webdevstudios/wds-shortcodes/vendor/tgmpa/tgm-plugin-activation/class-tgm-plugin-activation.php" which does not appear to be a file or folder"
I can then go into /lqd-messages/vendor/webdevstudios/wds-shortcodes/vendor and see that there is no tgmpa folder.
If I then go back to /wds-shortcodes and run composer install, the tgmpa folder will be successfully created.
Obviously, this is less than ideal. Is there a way to get around these extra steps?
This is bug in webdevstudios/wds-shortcodes package - their autoloadig settings are incorrect. Dependencies should not declare loading files from other dependencies inside of vendor directory - this is not their concern (and these files will not exist in some scenarios, like yours).
I can only recommend forking this package and fixing autoloading settings:
"autoload": {
"classmap": ["includes/"]
},
BTW: You've made the same mistake in your package.
I'm developing an app that will consist of multiple Composer packages.
First I have the "main" app (it will be a "project" in Composer) that will contain all the necessary files and folders:
app/
public/
index.php
logs/
config.php
..etc..
This is not an issue. I just set the type as "project" in the composer file so it can be install with composer create-project foo/bar.
I will also build a few optional extensions for the main app. They will be their own Composer packages. This isn't either an issue. I just make them into type "library" and install them with composer install foo/the-extension.
The issue
The extensions will have their own namespaces and some of them will have their own dependencies. A couple of them will even have the same dependencies.
This is needed since all of them will are optional. You can install one or the other or all.
Currently, I've created a new folder called "/dev" in the main app where I have all my extensions while developing. Then, in the main app, I'm loading all the extensions auto loaders:
# Main apps autoloader
require_once __DIR__ . '/vendor/autoload.php';
# Extensions
require_once __DIR__ . '/dev/foo/vendor/autoload.php';
require_once __DIR__ . '/dev/bar/vendor/autoload.php';
...etc...
This works, but it comes with a few drawbacks:
I need to change the code in the main app every time I'm going to make a commit to the main apps repo. This is a hassle and it's easy to miss something
Potential versioning clashes. If two packages depends on the same package that gets a new update. If I miss to update both, there might be a version clash. (This have happened)
It's never good to have more than one auto loader since that can mess things up royally.
So, does anyone know of a proper way of handling this, or is it one of those "well, if it works for you, do it like that"-type of situations?
Been searching for a good solution for this a while now but haven't found any. If I missed some answer here on SO, please mark it as a duplicate and I'll remove this post.
Edit
As #sammitch points out in the answer below, I could add the extensions using Composers "repositories" key. This would remove the multiple auto loader problem. However, that will make the development flow pretty awkward:
You make a change to an extension
You commit and push that change to a git repo
You do a composer update in the main app (to get the new commit)
Now you can test if your changes work
I rather not need to go through all that every single time I make a change the extensions code just to see if the change worked or not.
Whoa whoa whoa, you should only ever have one composer autoloader, and it's a bad idea to just cram in external dependencies like that as it will complicate your dev and/or deployment pipelines later.
What you want to do is have the main project include the subpackages as actual packages. You can do this either by:
1. Pushing them to a git host
https://getcomposer.org/doc/05-repositories.md#loading-a-package-from-a-vcs-repository
{
"repositories": [{
"type": "vcs",
"url": "https://github.com/youruser/yourrepo"}],
"require": {
"youruser/yourpackage": "^1.0.0"
}
}
2. Specifying a local repo
Composer require local package
{
"repositories": [{
"type": "vcs",
"url": "/home/youruser/src/yourrepo"
}],
"require": {
"youruser/yourpackage": "^1.0.0"
}
}
Now you can simply run composer install or composer update youruser/yourpackage and composer will pull in all the necessaries and build the relevant autoloader.
Note: Repository specifications are only effective in the root composer.json, so if your dependencies have specific repo config you'll need to either put that config into the root composer.json, or into your global composer config.
I have an existing PHP project with jquery and bootstrap, not using any front-end framework.
I am trying to use webpack module bundler in order to create a single entry point for my project resources, manage js dependencies with node js package manager, run tasks as minify js css, image re-size...etc. And improve the browser loading time required to load a single page.
I came across the webpack tutorials and got to install it and install its dev-server, but the problem is that I am not able to understand how I will convert all my current js scripts and css links in the project (where I have a lot of jquery and CSS libraries used to provide multiple features in the project) to use webpack.
Do I have to rewrite all my JS and CSS files in a way that suits webpack? How do I make a successful migration?
Besides, I am not able to run my current php application on the webpack dev-server, is it meant to run there in the first place? It is only listing the directories of the project in the meantime.
I have created a test index.js file and used the following webpack configuration:
var path = require('path');
var webpack = require('webpack');
module.exports =
{
entry: [
'./public/js/index.js',
'webpack/hot/dev-server',
'webpack-dev-server/client?http://localhost:8080'
],
plugins: [
new webpack.HotModuleReplacementPlugin()
],
output: {
path: path.join(__dirname, "public/dist/js"),
publicPath : "http://localhost:8080/my_proj/public/dist/js",
filename: "bundle.js"
}
};
I added the bundle.js to my script loads just for testing as follows hoping that the application will run on the webpack dev-server:
<script type="text/javascript" src="public/dist/js/bundle.js"></script>
<script type="text/javascript" src="public/js/jquery.min.js"></script>
<script type="text/javascript" src="public/js/jquery.migrate.js"></script>
<script type="text/javascript" src="public/js/jquery.bxslider.min.js"></script>
<script type="text/javascript" src="public/js/jquery.appear.js"></script>
<script type="text/javascript" src="public/js/jquery.countTo.js"></script>
<script type="text/javascript" src="public/js/bootstrap.js"></script>
Please help me understand the concept here and how can I make this migration successfully?
First, to answer your smaller questions:
No, you're not supposed to run your PHP application through a webpack dev server. Explained in the Live Reloading section below.
No, you won't have to rewrite your assets. Probably. See the CSS and Edge Cases sections below.
Disclaimer: I'll only take on a small fraction of your question. Its scope is just way too broad to be packed into just one StackOverflow answer.
I will only get in touch with
setting up a development and a production environment for webpack
bundling your first JavaScript
which should give you a foundation to build on.
I'll also mention some things you may want to add and link according resources to read through.
So, let's go.
Requirements
I assume you have Node.js and npm installed on your machine and roughly know how to use them.
I also assume you have webpack and webpack-cli installed as (dev) dependencies of your project (not just globally):
npm install --save-dev webpack webpack-cli
Update: Earlier versions of this answer did not require installing webpack-cli. As of version 4 (February 2018), webpack's CLI resides in its own package, hence the additional required package.
Set up development and a production workflow
You usually want to do stuff differently in development than in production (minifying in production, live-reloading in development, ...)
To achieve that, we'll want to split up our configuration files.
Prepare the directory structure
Let's agree to ignore the webpack config from your question. We'll start all over, we'd have to change almost everything anyway.
First, create a build folder inside your project root. Build-related stuff will go there, since we don't want to pollute your project's root folder with config files. (You're free to name this folder differently, but keep track of that during this tutorial.)
Create a config.base.js, a config.production.js and a config.development.js file inside that folder.
Great, we have config files for two build chains now. The configurations are still empty though, so let's now fill them with some basic logic.
Install webpack-merge
But first, we'll need to install webpack-merge.
npm install --save-dev webpack-merge
This package allows us to deeply merge multiple webpack configurations. We want to use it to create webpack configurations depending on our current environment.
Adjust your configuration
Now adjust your build/config.base.js:
module.exports = {
// We'll place webpack configuration for all environments here
}
The file does obviously just export an empty object right now, but we'll need that for the following steps.
Put this code in your build/config.production.js:
const { merge } = require('webpack-merge')
module.exports = merge(require('./config.base.js'), {
mode: 'production'
// We'll place webpack configuration for production environment here
})
And almost the same code goes into your build/config.development.js:
const { merge } = require('webpack-merge')
module.exports = merge(require('./config.base.js'), {
mode: 'development',
watch: true
// All webpack configuration for development environment will go here
})
I guess it's pretty intuitive what this does:
Using webpack with the config.development.js configuration will fetch the common configuration and merge its own config declaration in.
Update: The mode option in the above config files was added in webpack 4 (released February 2018). It sets a bunch of sensible defaults for development and production bundles.
Now running the process would look like this from the command line:
npx webpack --config build/config.development.js
# If the above doesn't work, you probably have an older version of npm (< 5.1) installed
# While npx is a really great tool, you can of course still call the path of the webpack executable manually:
node_modules/.bin/webpack --config build/config.development.js
...and vice versa for the production environment.
That command is rather clunky to use, but no worries, we'll address that later.
Make some helper files
There are information we'll be wanting to centralize to make them easily exchangeable. File paths are such a thing. So let's extract them.
Create a paths.js in your build folder and have it export some paths we'll want to use later:
const path = require('path')
// I'm really just guessing your project's folder structure from reading your question,
// you might want to adjust this whole section
module.exports = {
// The base path of your source files, especially of your index.js
SRC: path.resolve(__dirname, '..', 'public'),
// The path to put the generated bundle(s)
DIST: path.resolve(__dirname, '..', 'public', 'dist'),
/*
This is your public path.
If you're running your app at http://example.com and I got your DIST folder right,
it'll simply be "/dist".
But if you're running it locally at http://localhost/my/app, it will be "/my/app/dist".
That means you should probably *not* hardcode that path here but write it to a
machine-related config file. (If you don't already have something like that,
google for "dotenv" or something similar.)
*/
ASSETS: '/dist'
}
Create aliases
As mentioned above, we could technically run our build chain in development mode like this:
npx webpack --config build/config.development.js
That's an uncomfortably verbose command though, so let's change that.
It's way more convenient to run your build process via npm scripts. Add one script per environment to your package.json like this:
{
"scripts": {
"dev": "webpack --config build/config.development.js",
"prod": "webpack --config build/config.production.js"
}
}
Now you can run your build chains with npm run dev resp. npm run prod – which is much easier to memorize and faster to type.
...as soon as there'es anything to build, of course.
Bundle JavaScript
Okay, that was actually a fair amount of work without achieving too much so far.
So let's start with something more exciting: We'll define a JavaScript entry point.
Define an entry point
Put the following code into your build/config.base.js (replacing the existing code entirely):
const path = require('path')
const { SRC, DIST, ASSETS } = require('./paths')
module.exports = {
entry: {
scripts: path.resolve(SRC, 'js', 'index.js')
},
output: {
// Put all the bundled stuff in your dist folder
path: DIST,
// Our single entry point from above will be named "scripts.js"
filename: '[name].js',
// The output path as seen from the domain we're visiting in the browser
publicPath: ASSETS
}
}
Create the JavaScript file
The above configuration expects an index.js to live in your SRC/js folder (as defined in the build/paths.js).
Let's create that file with the following content:
import './jquery.min.js'
import './jquery.migrate.js'
import './jquery.bxslider.min.js'
import './jquery.appear.js'
import './jquery.countTo.js'
import './bootstrap.js'
As you can see, the index.js just imports all of the files you want to use.
If you now run
npm run prod
from your terminal, a scripts.js file will be created in your DIST folder. You can include that into your markup with a plain ol' <script> tag.
Congratulations, you've got a working webpack setup!
Dive deeper
This mini-tutorial really just scraped the surface of what you can do with webpack. It gives you a pretty solid foundation for your configuration which you now can fill with whatever you need. And that will actually be quite a lot of stuff.
I'll list a few more things you may want to enhance, with some links to read through.
webpack Concepts
If you want to use webpack, it can be hard to do so if you don't know about its underlying concepts. Juho Vepsäläinen created a great guide on getting started with webpack which helped me a whole lot. He's also a webpack core contributor so you can be sure he knows what he's talking about.
Especially loaders are a concept you'll really need to know.
Many of the hints on this list are also explained there.
Read more: SurviveJS – webpack tutorial
Code Splitting
It does what the name's saying: You might not want to pack all your JavaScript into one bulky output file.
It's a job webpack does for you to split off parts of your bundle which you only need on certain pages of your application.
Also, depending on how frequently you're working on your project's JavaScript, it might be a good idea to split off third party code from your bundle for caching purposes.
Read more: webpack Documentation – Code Splitting
Caching
You may want to enhance your site's caching behaviour by adding a hash to your bundled file names which depends on their content. This will create (for example) a script.31aa1d3cad014475a618.js instead of a scripts.js.
That file can then be cached indefinitely because as soon as its contents change, the file name will change as well.
Your PHP code might then use the webpack-manifest-plugin to gain access to the generated file names.
Read more:
Immutable Caching on how to cache your bundles forever
webpack Documentation – chunkhash on how to enrich your bundle file names with hashes
webpack-manifest-plugin on how to generate a manifest.json containing the file names of your current bundle
Transpiling
In case you want to use modern ES2015 code in your site's JavaScript (and are targeting non-evergreen browsers), you'll want to transpile them down to regular ES5. (If the term "ES2015" does not make any sense to you, you're most likely not using it and can ignore this paragraph.)
Read more: babel-loader – A loader that runs Babel on your scripts
CSS
There are webpack loaders for CSS. And Sass. And PostCSS. Whatever you need.
And since you're probably not planning to include your CSS via <script> tags, get to know the Extract Text Plugin to generate actual .css files.
Update: The Extract Text Plugin is very established. However, it's actually a kind of hack: It generates .css files even though webpack only knows JavaScript as its target language.
However, this is no longer true as of webpack 4. There's now a system to define arbitrary module types, including CSS.
Long story short: Expect native CSS support in webpack to replace Extract Text Plugin some time soon.
Hint: Paths
I'll mention this because this was a real pain point for me until I realized how webpack works here:
Be aware that webpack will recognize your url(...) statements and try to resolve them relative to your source files.
This means, your source file public/css/main.css:
body {
background: url('../img/bg.jpg');
}
if your output path is public/dist/css/bundle.css, will be transformed to:
body {
background: url('../../img/bg.jpg');
}
Read more:
style-loader and css-loader – you'll hands down need those.
extract-text-webpack-plugin
Minifying
Update: Since webpack 4 was released in February 2018, this section is rather obsolete. Setting the new mode option to "production" now automatically applies JavaScript minification.
There is a Terser plugin for webpack to minify your JavaScript. Minifying CSS is a feature already builtin to the css-loader plugin mentioned above.
Read more: Terser webpack Plugin
Image Optimization
webpack is a bundler, not a task runner. Thus, image optimization is not a genuine webpack task. You'd probably be better off using an actual task runner or just defining some npm scripts for this.
This does not mean webpack is not capable of doing this. There are plugins for pretty much everything.
Read more:
imagemin can minify images pretty nicely on its own.
imagemin-webpack-plugin will integrate that process into your webpack build chain.
Live Reloading
Your problems with live reloading have a pretty simple cause: a webpack dev server is just a simple Node.js server serving only static files.
For you're case, webpack-dev-server probably is the wrong tool at all. Try webpack-livereload-plugin instead for a live reloader that you can just include via <script> tag.
Read more: webpack-livereload-plugin
Source Maps
Update: As of webpack 4 (released in February 2018), source maps are automatically generated when the new mode option is set to "development".
By all means, use source maps. They'll make your work with bundles so much easier you'll want to cry.
Read more: webpack Documentation – Source Maps
Edge Cases
Usually, all your existing scripts you'll process with webpack should be running just fine.
The only exception that comes to my mind right now would be regarding global entities.
Look at the following code:
function myFunc () {
console.log('I exist!')
}
This code in a plain JavaScript file would make myFunc available everywhere in your JS code. But since webpack bundle code is wrapped inside callback functions (and thus leaving the global scope), there won't be any access to that function anymore.
Third party libraries should not be a problem there, they usually assign their globals to the window object directly, but if you've already written JS code in your project, you should be aware of that.
Automate!
You'll want to automate as much of your workflow as possible.
Consider running npm run prod via a git hook before pushing / after pulling.
Based on the existing vue-templates and and the answer from #Loilo I made a vue template you can install with vue-cli. This template jumpstarts you for a vue application you can extend with or integrate in you existing environment.
npm install -g vue-cli
vue init delcon/webpack-simple my-project
cd my-project
npm install
devwatch:
This template has an additional run devwatch option that watches for filechanges instead of using the webpack-dev-server. This makes it usable for any existing webserver enviroment.
npm run devwatch
dev:
to run it with the default webpack-dev-server, remove <script src="http://localhost:35729/livereload.js"></script> in index.html:
npm run dev
build:
to build your project for production:
npm run build
I have a local project with loaded with Composer libs. I uploaded this project to my FTP and received errors, connected with not found classes from some libs.
Can I simply copy vendor/ folder to FTP or I missed something?
Error received:
Fatal error: Class 'AAA\Core\Tools' not found in /home/aaa/public_html/api.php on line 11
api.php:
<?php
use AAA\Core\Tools;
require_once("./vendor/autoload.php");
require_once("./api/" . Tools::getFieldValue('controller') . ".php");
All works fine on localhost!
Linux has a case sensitive file system. That means that files Alex.txt and alex.txt are the same thing in Windows, but not in Linux. Actually on Linux both can happily live in the same directory:
$ tree .
.
├── alex.txt
└── Alex.txt
0 directories, 2 files
Taking this into consideration, I would try to double check that the paths you are using in your namespace are actually identical to what is found at the file system level. (i.e: AAA directory with only uppercase letters ; Core directory capitalized and Tools.php file capitalized)
If you want to keep your existing file system layout, you can use PSR-4 to explicitly tell Composer how to map the namespace to the file system:
Change autoload section from your composer.json:
{
"autoload": {
"psr-4": {"AAA\\DB\\": "db/"}
}
}
where db/ is the actual path from the file system
Update the autoloader:
$ composer dump-autoload
This will take care of directory names, but doesn't apply for files. Meaning that any file inside db/ must be named exactly as used in namespace (for a usage as use AAA\DB\DBCore the file must be db/DBCore.php).
If your file is named dbcore.php and you want to reference it in your namespace as DBCore, you can use classmap feature from Composer:
"autoload": {
"classmap": [
"db/dbcore.php"
]
}
dbcore.php:
<?php
namespace AAA\DB;
class DBCore
{
}
And you can use it as usual:
<?php
require_once("./vendor/autoload.php");
$dbCore = new \AAA\DB\DBCore();
Firstly I would check the autoloader files composer has generated to make sure the paths are valid on your linux server.
Another simple but common issue is that on windows the folder and file names are not case sensitive however they are on Linux. Double check that the folders and files have the correct case as if not it won't find them to auto load.
Rather than trying to upload via FTP which I think is going to be tricky if not impossible to get right, I would suggest you explore getting composer working on your hosting environment.
Composer is entirely PHP based, so should run anywhere that PHP is running.
If you don't have command line access, you can use something like PHPShell which gives you a PHP based command line on which you can then run Composer.
See this other SO answer to get some tips on how to use PHPShell.
Another option is to build a little PHP wrapper that you actually run by visiting it in your browser, in the classic PHP way. See this other SO answer for some tips on how to do that.
Bottom line, you should really look at getting Composer running on your server rather than trying to bodge it another way.
Once you have done your composer process on the server, you must remove the PHPShell or composer wrapper you created so that you don't leave any security holes.
Did you tell the composer where your Class 'AAA\Core\Tools' is?
You can even add your own code to the autoloader by adding an autoload field > to composer.json.
{
"autoload": {
"psr-4": {"Acme\\": "src/"}
}
}
Composer is not meant to be used that way (i.e. you shouldn't be manually transferring vendor directories from one environment to another).
As you add dependencies to your project, the composer.json file will contain those dependencies. When you run composer install or update on your localhost, it "locks" the current version of those dependencies for your project and stores them in the composer.lock file. You should be transferring the composer.json and composer.lock files from your development environment to your production environment and then running composer install on your production environment as part of your deployment process. When you run composer install on your production environment, Composer will look at your composer.lock file and install the specified versions of the dependencies in the vendor directory of the production environment.
You may want to review the composer documentation regarding basic usage (https://getcomposer.org/doc/01-basic-usage.md) and command line options (https://getcomposer.org/doc/03-cli.md) for more details.