Page MenuHomePhabricator

Discard futures after they resolve in phage
ClosedPublic

Authored by yelirekim on Jun 25 2016, 10:14 AM.
Tags
None
Referenced Files
Unknown Object (File)
Mon, Mar 11, 11:19 AM
Unknown Object (File)
Wed, Mar 6, 10:50 PM
Unknown Object (File)
Feb 3 2024, 11:03 AM
Unknown Object (File)
Feb 3 2024, 3:18 AM
Unknown Object (File)
Jan 27 2024, 11:03 AM
Unknown Object (File)
Jan 25 2024, 11:04 AM
Unknown Object (File)
Jan 23 2024, 3:34 PM
Unknown Object (File)
Jan 11 2024, 12:25 AM
Subscribers

Details

Summary

The list of futures that the PHP agent maintains is never emptied after futures resolve. On subsequent passes through the loop in execute, all past futures are executed repeatedly.

Test Plan

This didn't work previously.

<?php

final class CIAWSDrydockHostCommandWorkflow extends CIAWSManagementWorkflow {

  protected function didConstruct() {
    $this
      ->setName('drydock-command')
      ->setSynopsis(pht('Interact with a drydock host.'))
      ->setArguments([
          [
            'name'        => 'lease',
            'param'       => 'id',
            'help'        => pht('ID of drydock lease to command.'),
          ],
        ]);
  }

  public function execute(PhutilArgumentParser $args) {
    $resource_id = $this->requireArgument($args, 'lease');
    $viewer = PhabricatorUser::getOmnipotentUser();
    $lease = (new DrydockLeaseQuery())
      ->setViewer($viewer)
      ->withIDs([$resource_id])
      ->executeOne();

    $boot = new PhagePHPAgentBootloader();
    $ssh = $lease->getInterface(DrydockCommandInterface::INTERFACE_TYPE);
    $exec = $ssh->getExecFuture('%C', $boot->getBootCommand());
    $exec->write($boot->getBootSequence(), $keep_open = true);
    $exec_channel = new PhutilExecChannel($exec);
    $agent = new PhutilJSONProtocolChannel($exec_channel);

    $console = PhutilConsole::getConsole();
    $cmd = null;
    $key = 1;
    while ($cmd !== 'exit') {
      $console->writeOut('**>** ');
      $cmd = fgets(STDIN);
      $cmd = rtrim($cmd, "\r\n");
      $agent->write([
        'type' => 'EXEC',
        'key' => $key++,
        'command' => $cmd,
      ]);
      $message = $agent->waitForMessage();
      $console->writeOut('%s', $message['stdout']);
      $console->writeErr('%s', $message['stderr']);
    }
    $agent->write(['type' => 'EXIT']);
    return 0;
  }

}

Diff Detail

Repository
rPHU libphutil
Lint
Lint Not Applicable
Unit
Tests Not Applicable

Event Timeline

yelirekim retitled this revision from to Discard futures after they resolve in phage.
yelirekim updated this object.
yelirekim edited the test plan for this revision. (Show Details)

I'm not sure if I"m just abusing this class?

epriestley added a reviewer: epriestley.

This code is very proof-of-concept right now so I wouldn't be surprised if there's more stuff like this.

This use case is (using Phage as a fancier remote shell) is an interesting one. I didn't really think about having something like Drydock drive Phage clients, but I think it's legitimate / reasonable / non-abusive.

In the original Hypershell, the clients had a fair amount of logic in them, but I've tried to simplify them in Phage ("Hypershell 2"), so I expect the clients will remain as dumb as possible even when the command-and-control stuff for large tiers eventually gets built out. This should leave them well-aligned with use as a more flexible shell program that you don't need to deploy or configure.

I would expect to clean up the API at some point to support this use case, though.

This revision is now accepted and ready to land.Jun 25 2016, 1:17 PM
This revision was automatically updated to reflect the committed changes.