2

I have a Symfony Console app and I want to use it with autocomplete but autocoplite doesn't work. When I click tab nothing happens.

My app works successfully from the command line if I type like this:

./myapp generate-constants nomenclature

Then it prints

Hello World!, nomenclature

This is my script named myapp

#!/usr/bin/env php
<?php
require 'bootstrap.php';

use MyApp\Core\Console\GenerateConstantsCommand;
use Symfony\Component\Console\Application;

$app = new Application();
$app->add(new GenerateConstantsCommand());
$app->run();

And this is GenerateConstantsCommand.php

<?php
namespace MyApp\Core\Console;
use LogicException;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Completion\CompletionInput;
use Symfony\Component\Console\Completion\CompletionSuggestions;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Console\Input\InputArgument;

class GenerateConstantsCommand extends Command
{
    protected function configure()
    {
        $this->setName('generate-constants')
            ->setDescription('Generate constsants')
            ->setHelp('Demonstration of custom commands created by Symfony Console component.')
            ->addArgument('nomenclature', InputArgument::REQUIRED, 'Pass the nomenclature');
    }


    protected function execute(InputInterface $input, OutputInterface $output)
    {
        $output->writeln(sprintf('Hello World!, %s', $input->getArgument('nomenclature')));
        return 0;
    }

    public function complete(CompletionInput $input, CompletionSuggestions $suggestions): void
    {
        if ($input->mustSuggestOptionValuesFor('nomenclature')) {
            $suggestions->suggestValues(['json', 'xml']);
        }
    }
}

What I am doing wrong? Why autocomplete doesn't work?

Also I have tried with stecman/symfony-console-completion but when I run eval $(./myapp _completion --generate-hook) the cursor goes to new line and stays there forever.

I use Bash 5.0.17(1)-release, Ubuntu 20.04.4 LTS, Symfony Console 5.4.7, and PHP 7.3.26.

1 Answer 1

5

As per the documentation:

Make sure to install the bash-completion package: sudo apt-get install -y bash-completion.

Then run the following command ONCE (installing Symfony's bash completion script): php bin/console completion bash | sudo tee /etc/bash_completion.d/console-events-terminate.

Restart your terminal and it should work.

This is the example command that I used for testing and shell auto-completion works as expected:

<?php declare(strict_types = 1);

namespace App\Command;

use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Completion\CompletionInput;
use Symfony\Component\Console\Completion\CompletionSuggestions;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use function is_string;
use function sprintf;

class TestCommand extends Command
{
    protected function configure(): void
    {
        $this->setName('app:test')
            ->setDescription('Test command')
            ->setHidden(false)
            ->addArgument('format', InputArgument::REQUIRED, 'The format');
    }

    public function complete(CompletionInput $input, CompletionSuggestions $suggestions): void
    {
        if (true === $input->mustSuggestArgumentValuesFor('format')) {
            $suggestions->suggestValues(['json', 'xml']);
        }
    }

    protected function execute(InputInterface $input, OutputInterface $output): int
    {
        $format = $input->getArgument('format');
        if (false === is_string($format)) {
            $output->writeln('Given format is not a string');
            return Command::FAILURE;
        }
        $output->writeln(sprintf('Format: %s', $format));
        return Command::SUCCESS;
    }
}

enter image description here

Sign up to request clarification or add additional context in comments.

1 Comment

Also readline PHP extension needs to be installed.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.