Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 22 additions & 15 deletions packages/bazel/src/protractor/utils/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -71,24 +71,31 @@ export interface ServerSpec {
port: number;
}

export function runServer(
workspace: string, binary: string, portFlag: string, args: string[],
/**
* Runs the specified server binary from a given workspace and waits for the server
* being ready. The server binary will be resolved from the Bazel runfiles. Note that
* the server will be launched with a random free port in order to support test concurrency
* with Bazel.
*/
export async function runServer(
workspace: string, serverTarget: string, portFlag: string, serverArgs: string[],
timeout = 5000): Promise<ServerSpec> {
return findFreeTcpPort().then(function(port) {
const runfiles_path = process.env.TEST_SRCDIR;
const cmd = path.join(runfiles_path, workspace, binary);
const serverPath = require.resolve(`${workspace}/${serverTarget}`);
const port = await findFreeTcpPort();

args = args.concat([portFlag, port.toString()]);
// Start the Bazel server binary with a random free TCP port.
const serverProcess = child_process.spawn(
serverPath, serverArgs.concat([portFlag, port.toString()]), {stdio: 'inherit'});

const child = child_process.spawn(
cmd, args, {cwd: path.join(runfiles_path, workspace), stdio: 'inherit'});
// In case the process exited with an error, we want to propagate the error.
serverProcess.on('exit', exitCode => {
if (exitCode !== 0) {
throw new Error(`Server exited with error code: ${exitCode}`);
Comment thread
devversion marked this conversation as resolved.
Resolved
}
});

child.on('exit', function(code) {
if (code != 0) {
throw new Error(`non-zero exit code ${code} from server`);
}
});
// Wait for the server to be bound to the given port.
await waitForServer(port, timeout);

return waitForServer(port, timeout).then(() => { return {port}; });
});
return {port};
}
29 changes: 29 additions & 0 deletions packages/bazel/test/protractor-utils/BUILD.bazel
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
load("//tools:defaults.bzl", "jasmine_node_test", "nodejs_binary", "ts_library")

ts_library(
name = "protractor_utils_tests_lib",
testonly = True,
srcs = ["index_test.ts"],
deps = [
"//packages/bazel/src/protractor/utils",
],
)

nodejs_binary(
name = "fake-devserver",
testonly = True,
data = [
"fake-devserver.js",
"@ngdeps//minimist",
],
entry_point = "angular/packages/bazel/test/protractor-utils/fake-devserver.js",
)

jasmine_node_test(
name = "protractor_utils_tests",
size = "small",
srcs = [":protractor_utils_tests_lib"],
data = [
":fake-devserver",
],
)
23 changes: 23 additions & 0 deletions packages/bazel/test/protractor-utils/fake-devserver.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/

const http = require('http');
const minimist = require('minimist');

const {port} = minimist(process.argv);
const server = new http.Server();

// Basic request handler so that it could respond to fake requests.
server.on('request', (req, res) => {
res.writeHead(200, {'Content-Type': 'text/plain'});
res.end('Running');
});

server.listen(port);

console.info('Server running on port:', port);
17 changes: 17 additions & 0 deletions packages/bazel/test/protractor-utils/index_test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/

import {runServer} from '../../src/protractor/utils';

describe('Bazel protractor utils', () => {

it('should be able to start devserver', async() => {
// Test will automatically time out if the server couldn't be launched as expected.
await runServer('angular', 'packages/bazel/test/protractor-utils/fake-devserver', '--port', []);
});
});