test('run dockerSave, then check contents', async () => {
    let result = await worker.postToQueue({
      payload: {
        image: 'busybox',
        command: ['/bin/sh', '-c', 'echo testString > /tmp/test.log'],
        features: {
          dockerSave: true
        },
        maxRunTime: 5 * 60
      }
    });

    assert(result.run.state === 'completed', 'task should be successful');
    assert(result.run.reasonResolved === 'completed',
                 'task should be successful');

    let taskId = result.taskId;
    let runId = result.runId;

    let url = `https://queue.taskcluster.net/v1/task/${taskId}/runs/${runId}/artifacts/public/dockerImage.tar`;

    //superagent means no zlib required
    let res = await request.get(url).end();
    res.pipe(fs.createWriteStream('/tmp/dockerload.tar'));
    await waitForEvent(res, 'end');
    //make sure it finishes unzipping
    await base.testing.sleep(2000);

    let docker = new Docker(dockerOpts());
    let imageName = createImageName(taskId, runId);
    await docker.loadImage('/tmp/dockerload.tar');
    let opts = {
      AttachStdin: true,
      AttachStdout: true,
      AttachStderr: true,
      Cmd: ['cat', '/tmp/test.log'],
      Image: imageName
    };
    let streamOpts = {
      logs: true,
      stdout: true,
    };
    let container = await docker.createContainer(opts);
    await container.start();
    let stream = await container.attach(streamOpts);

    await new Promise((accept, reject) => {
      stream.on('data', (data) => {
        assert(data.compare(new Buffer(0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x0b, //header
          0x74,0x65,0x73,0x74,0x53,0x74,0x72,0x69,0x6e,0x67,0x0a))); //testString\n
        accept();
      });
      stream.on('error', reject);
      // stream.on('end', () => {reject(new Error('stream ended too early'))});
      setTimeout(reject, 15000, new Error('timed out waiting for docker container'));
    });
    await base.testing.sleep(100);
    await Promise.all([container.remove(), fs.unlink('/tmp/dockerload.tar')]);
    await removeImage(docker, imageName);
  });
Beispiel #2
0
suiteSetup(async function() {
  // Since we may be operating docker over vagrant/remote/etc.. It is required
  // to figure out where docker is hosted then
  let dockerConfig = dockerOpts();

  // In the case where docker is over a unix socket we fallback to 'localhost'
  let dockerHost = (dockerConfig.host || 'localhost').replace('http://', '');

  // Turn on fig (service names are hardcoded!)
  await figUp();

  // Fetch the ports we need to pass in...
  let [
    thapiPort,
    redisPort,
    rabbitmqPort
  ] = await Promise.all([
    // If your confused see test/fig.yml
    figPort('thapi', 8000),
    figPort('redis', 6379),
    figPort('rabbitmq', 5672)
  ]);

  // We use a custom config file based on src/config/test.js
  let config = await loadConfig('test', { noRaise: true });
  config.treeherder.apiUrl = `http://${dockerHost}:${thapiPort}/api/`;
  config.redis.host = dockerHost;
  config.redis.port = redisPort;
  config.commitPublisher.connectionString =
    `amqp://${dockerHost}:${rabbitmqPort}`;

  // write out the custom config...
  await fs.writeFile(GENERATED_CONFIG, yaml.safeDump(config));

  this.config = await loadConfig('test');
  this.runtime = await loadRuntime(this.config);

  // Note listener is for messages/exchanges we generate...
  this.listener = new taskcluster.AMQPListener({
    connectionString: this.config.commitPublisher.connectionString
  });

  // Pulse is for things external components generate...
  this.pulse = new taskcluster.PulseListener({
    credentials: this.config.pulse
  });

  this.queue = new taskcluster.Queue({
    credentials: this.config.taskcluster.credentials
  });

  this.scheduler = new taskcluster.Scheduler({
    credentials: this.config.taskcluster.credentials
  });

  let commitPublisher = await publisher(this.config.commitPublisher);
  await commitPublisher.assertExchanges(PushExchange);

  // We only need the connection to assert the exchanges after that we can
  // shut it down...
  await commitPublisher.close();

  let Client = taskcluster.createClient(commitPublisher.toSchema(
    PushExchange
  ));

  this.pushEvents = new Client();
  this.treeherder = new THProject('try', {
    consumerKey: 'try',
    consumerSecret: 'try',
    baseUrl: this.config.treeherder.apiUrl
  });

  this.runtime.jobs.on('failed attempt', function(result) {
    console.error('Failed job', result);
  });
});