Codementor Events

Using and extending the Magento 2 command line

Published Aug 03, 2018
Using and extending the Magento 2 command line

In the days of Magento 1, using the command line was optional. Actually, it was not even possible to do much without the n98-magerun package.

While this was a good thing for smaller shops, doing daily operations via the web interface, with no automation capabilities and small memory limits, was not feasable.

In Magento 2, the command line is a first class citizen and, even more than that, basic knowledge is required to administer the site as some operations, like compiling and reindexing, can only be done via command line. In the guide below, I am listing the most common tasks one can do via CLI.

The basics

To use the Magento command line, you have to SSH into the server, go to your Magento's root directory, and run:

php bin/magento

The above will list all available commands:

Usage:
 command [options] [arguments]

Options:
 --help (-h)           Display this help message
 --quiet (-q)          Do not output any message
 --verbose (-v|vv|vvv) Increase the verbosity of messages: 1 for normal output, 2 for more verbose output and 3 for debug
 --version (-V)        Display this application version
 --ansi                Force ANSI output
 --no-ansi             Disable ANSI output
 --no-interaction (-n) Do not ask any interactive question

Available commands:
 help                                      Displays help for a command
 list                                      Lists commands
admin
 admin:user:create                         Creates an administrator
 admin:user:unlock                         Unlock Admin Account
......

To find out more about a command, simply run it with the --help option:

php bin/magento admin:user:create  --help

This will list all of the parameters for the specific command. A nice surprise is that you will get suggestions for typos and are also able to use short codes.

Deployments

Magento 2 comes with more deployment modes — developer, default, and production. The first thing you want to do in production is to turn on the production mode:

php bin/magento deploy:mode:set production

When pulling new code, you need to run a few commands...

First, start maintenance to make sure the site is not used while you deploy:

php bin/magento maintenance:enable

Then, if you added new modules, you will need to upgrade the database:

php bin/magento setup:upgrade

Compile the files:

php bin/magento setup:di:compile

Compile static assets:

php bin/magento setup:static-content:deploy -j1

And finally disable maintenance:

php bin/magento maintenance:enable

Of course, you can put them all in one line (which probably should go in a deploy script):

php bin/magento maintenance:enable && php bin/magento setup:upgrade && php bin/magento setup:di:compile && php bin/magento cache:clean && php bin/magento setup:static-content:deploy -j1  && php bin/magento maintenance:disable

Getting information

A list with all modules can be obtained with:

php bin/magento module:status

Then you can enable a module with:

php bin/magento module:enable Foo_Bar

See if indexers are up to date:

php bin/magento indexer:status

Administrative tasks

Cleaning the cache is way easier with CLI:

php bin/magento cache:clean

So is reindexing (which cannot be done via the web UI anymore, since it can be a very long process):

php bin/magento indexer:reindex

Run the cron:

php bin/magento cron:run

Or even create an admin user:

php bin/magento admin:user:create

Short Codes

As I was mentioning earlier, you can use short codes for every command, as long as there is no confusion in parsing them. So instead of writing:

php bin/magento cache:clean

You can get away with:

php bin/magento c:c

Try using whatever is shorter and mnemonic.

Creating your own command

You can easily extend the command line with your own command. For this you will need to write a Magento module. Start by creating a new folder structure in app/code/MyCompany/MyCommand . Here, add a new file, etc/module.xml to register the module:

<?xml version="1.0"?>
 
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Module/etc/module.xsd">
    <module name="MyCompany_MyCommand" setup_version="1.0.0">
    </module>
</config>

The only relevenat part above is that MyCompany_MyCommand matches the folder structure of MyCompany/MyCommand (vendor/module_name). Yet another file is needed for registration, app/code/MyCompany/MyCommand/registration.php:

<?php
 
\Magento\Framework\Component\ComponentRegistrar::register(
    \Magento\Framework\Component\ComponentRegistrar::MODULE,
    'MyCompany_MyCommand',
    __DIR__
);

If all went well, you should be able to see your module by running:

php bin/magento module:status

Go ahead and enable it:

php bin/magento module:enable MyCompany_MyCommand && php bin/magento setup:upgrade

As you can see, the module can only be enabled via the command line. It will not enable automatically when cleaning the cache, as was the case with Magento 1.

We now need to expose the new command. Create a new file, MyCompany/MyCommand/etc/di.xml:

<?xml version="1.0"?>
  <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
    <type name="Magento\Framework\Console\CommandList">
      <arguments>
        <argument name="commands" xsi:type="array">
          <item name="hello_world" xsi:type="object">MyCompany\MyCommand\Console\Command\HelloWorldCommand</item>
        </argument>
      </arguments>
    </type>
  </config>

In here, we simply tell Magento about the new command that is to be implemented in the MyCompany\MyCommand\Console\Command\HelloWorldCommand class. The next step is to create this class, in app/code/MyCompany/MyCommand/Console/Command/HelloWorldCommand.php:

namespace MyCompany\MyCommand\Console\Command;

use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Console\Input\InputOption;

class HelloWorldCommand extends Command
{
 
    protected function configure()
    {
        $this->setName('mycompany:hello_world')->setDescription('So much hello world.');
    }
 
    protected function execute(InputInterface $input, OutputInterface $output)
    {
        $output->writeln('Hello World!');
    }
 
}

The structure is pretty simple. The configure method is responsible for defining the command name and the description, while the execute method will do the logic.

Once this is done, start by clearning the Magento cache:

php bin/magento cache:clean

Then you should be able to see your command in the command list:

php bin/magento

And execute it:

php bin/magento mycompany:hello_world

Conclusion

The Magento 2 CLI interface is a pretty well built feature that allows you to script common operations. It's also extensible (you can write your own commands) which makes it even better. Make sure you know the existing commands, as they will certanly help you with your day-to-day Magento administration tasks.

Discover and read more posts from Paul Grigoruta
get started
post commentsBe the first to share your opinion
Show more replies