-
-
Notifications
You must be signed in to change notification settings - Fork 1.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Deprecate Annotated Commands in favor of native Symfony Console commands #6135
base: 13.x
Are you sure you want to change the base?
Conversation
sut/modules/unish/woot/src/Drush/EventListener/WootDefinitionListener.php
Outdated
Show resolved
Hide resolved
We had talked about moving FormatterTrait to consolidation/output-formatters. I would like to do that. I think this implies that src/Attributes/FieldLabels.php and the other format-related attributes would also need to move over. We can maintain compatibility with Drush 13 if we make Drush\Attributes\FieldLables & c. extend the consolidation/output-formatters attribute. Should I go ahead and do that, and update this PR to use the output-formatters copy? |
I'm undecided about moving FormatterTrait and the related Attributes. I do agree that both are coupled and probably should live together. When authoring a command, its helpful for all Attributes to be in same namespace so you can browse them in your IDE. If we move the Formatter attributes, we bifurcate them, or we thinly extend the ones provided by output-formatters. We do that thin extension today for those provided by annotated-command, but I always found that slightly awkward. Lets mull it. Update: the implementation now complete. Maybe @greg-1-anderson has a suggestion about how to implement --filter in the new paradigm. See DrushCommandAlterer and FilterHooks. In this PR I've added
|
public function remove(string $id): void | ||
{ | ||
$rf = new \ReflectionProperty(\Symfony\Component\Console\Application::class, 'commands'); | ||
$rf->setAccessible(true); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not super excited to do this outside of tests. Is this for some sort of "alter" hook? If we want to do this, maybe we should, during preflight, add commands to some other list and provide a specific hook to alter that before adding to the application. That might be complicated, since today we add in two steps (commands from modules being added later).
Alternately, instead of removing a command, maybe we could change its name, remove its aliases and hide it?
I'm not sure why I think that setAccissible is worse than that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
add commands to some other list and provide a specific hook to alter that before adding to the application
I think thats more more easily done once we use a container to store commands and maybe use a CommandLoader. Yes, this is just used by Woot today - we can remove it if it offends the eyes.
Yes, I was thinking that filter could happen in the format trait. I think that consolidation/output-formatters should have the trait and format attributes, so that they are available when that library is used outside of Drush. I'll probably duplicate the code there regardless, even if Drush doesn't use it. Perhaps thin extensions would be a workable solution, where necessary. |
OK, when this PR is ready to go in, lets move the FormatterTrait and format Attributes, and Drush may thinly extend the Attributes. |
… \Drush\Runtime\DependencyInjection::alterServicesForDrush
Resolves a PHPStan failure.
The formatter thing looks complex and too magic. Will it save much time for command developers? I think Something like this. private static function getOutputFormatter(): FormatterManager {
return \Drupal::service(FormatterManager::class);
} It seems quite easy to apply it manually. protected function configure(): void
{
$this
->addArgument('some-arg', InputArgument::REQUIRED, 'Description');
self::getOutputFormatter()->configureCommand($this);
}
public function execute(InputInterface $input, OutputInterface $output): int
{
$data = [];
self::getOutputFormatter()->write($output, $input->getOption('format'), new RowsOfFields($data));
return self::SUCCESS;
} I would actually inject the formatter through constructor rather than through trait. |
Given that Also curious if it is possible to integrate the formatter with |
public static function handle(\ReflectionAttribute $attribute, CommandInfo $commandInfo) | ||
{ | ||
$args = $attribute->getArguments(); | ||
$commandInfo->addAnnotation('filter-default-field', $args['field']); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here and elsewhere, KEY
is defined in the class but not used in handle()
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just pushed a fix with a couple tweaks. Depends on another PR in output-formatters consolidation/output-formatters#113
src/Commands/OptionSets.php
Outdated
|
||
class OptionSets | ||
{ | ||
public static function sql(Command $command) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe the static method technique of holding option sets would sit better if it lived in some "sql" namespace, rather than putting all option set domains in the same class. (This would be more obvious if there were more than one here.)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
True. The benefit of putting multiple methods on a single OptionSet class is that the optionsets are more discoverable. The class analogous to our existing https://github.com/drush-ops/drush/blob/13.x/src/Commands/OptionsCommands.php
src/Formatters/FormatterTrait.php
Outdated
*/ | ||
public function addFormatterOptions(string $dataType): void | ||
{ | ||
$inputOptions = $this->formatterManager->automaticOptions($this->getFormatterOptions(), $dataType); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this can be refactored to avoid the intermediate instances and private field access. This can wait until moving this code into output-formatter.
Use a web URL instead of the actual topic text.
494faef
to
5b55f98
Compare
Its OK to duplicate a few lines of code
|
||
#[Deprecated(replacement: 'Copy \Drush\Commands\core\ImageFlushCommand::validateEntityLoad into command and call during execute()')] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could we maybe use a command hook to find and dispatch validate hooks?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have experimented with that approach earlier in this PR and can't decide whats best. Currently the validation is done right in execute() and isn't not DRY. See ImageFlushCommand. Compare with https://github.com/drush-ops/drush/blob/f923a801dd50d4aa17fd2390790336bc962785a3/src/Listeners/ValidateModulesEnabledListener.php and its associated Attribute. IMO the current approach is less magical and I'm slightly valuing that these days.
Open issues
consolidation/filter-via-dot-access-data
, move that into output-formatters, or drop the feature. See \Drush\Formatters\FormatterTrait::alterResult#[ValidateModulesEnabled]
Attribute signals to ValidateModulesEnabledListener to do its validation workDescription
It is our hope that Drush commands will be consumed by a future CLI in Drupal core. To make our commands more consumable, this PR changes Drush commands to directly extend Symfony's Command class.
Converted commands are sql:dump, twig:unused and image:flush. Some highlights:
We have more plans for simplifying Drush's Preflight and removing the consolidation/annotated-command and consolidation/robo dependencies - this is just a start!