提交 25b3ff5d 编写于 作者: P Piotr Bryk

Merge branch 'master' into description

......@@ -8,7 +8,6 @@ bower_components/
.tmp/
coverage/
dist/
kubernetes/
.tools/
## IDE specific files
......
......@@ -41,15 +41,5 @@ before_script:
- export DISPLAY=:99.0
- sh -e /etc/init.d/xvfb start
# Download etcd and make add it to PATH environment variable.
# Etcd is used to manage kubernetes cluster coordination and for state management.
- curl -fsSL https://github.com/coreos/etcd/releases/download/v2.2.1/etcd-v2.2.1-linux-amd64.tar.gz | tar xzf -
- ln -fns etcd-v2.2.1-linux-amd64 etcd
- export PATH=$PWD/etcd:$PATH
# Pull golang image to build local kubernetes cluster.
# Local cluster has build process that runs in a Docker container.
# This simplifies initial set up and provides a very consistent build and test environment.
- docker pull golang:1.4
script: ./node_modules/.bin/gulp check:create-cluster
script: ./node_modules/.bin/gulp check:local-cluster
after_script: ./node_modules/.bin/gulp coverage-codecov-upload
......@@ -20,7 +20,6 @@ Make sure the following software is installed and added to the `$PATH` variable:
* go (1.5+)
* nodejs (4.2.2+)
* npm (1.3+)
* etcd (2.2+)
* java (7+)
* gulp (3.9+)
......@@ -31,16 +30,17 @@ $ npm install
## Run a Kubernetes Cluster
For development it is recommended to run a local Kubernetes cluster. For your convenience, a task is provided that checks out the latest stable version, compiles and runs the script: `<kubernetes>/hack/local-up-cluster.sh`. Open a separate tab in your terminal and run the following command:
For development it is recommended to run a local Kubernetes cluster. For your convenience, a task is provided that checks out the latest stable version, and runs it inside a Docker container. Open a separate tab in your terminal and run the following command:
```
$ gulp local-up-cluster
```
Depending on your environment you might need to run the gulp task with sudo. Also, you might need to propagate the `$PATH` settings to the root user.
This will build and start a lightweight local cluster, consisting of a master and a single node. All processes run locally, in Docker container. The local cluster should behave like a real cluster, however, plugins like heapster are not installed. To shut it down, type the following command that kills all running Docker containers:
```
$ sudo env "PATH=$PATH" gulp local-up-cluster
$ docker kill $(docker ps -aq)
```
This will build and start a lightweight local cluster, consisting of a master and a single node. All processes run locally, without virtual machines. The local cluster should behave like a real cluster, however, plugins like heapster are not installed. Type Control-C to shut it down.
From time to time you might want to use to a real Kubernetes cluster (e.g. GCE, Vagrant) instead of the local one. The most convenient way is to create a proxy. Run the following command instead of the gulp task from above:
```
......
......@@ -19,7 +19,6 @@ import gulp from 'gulp';
import gulpClangFormat from 'gulp-clang-format';
import gulpEslint from 'gulp-eslint';
import gulpSassLint from 'gulp-sass-lint';
import runSequence from 'run-sequence';
import path from 'path';
import conf from './conf';
......@@ -39,13 +38,7 @@ gulp.task('check', ['lint', 'build', 'test', 'integration-test:prod']);
* Checks the code quality of Dashboard. In addition a local kubernetes cluster is spawned.
* NOTE: This is meant as an entry point for CI jobs.
*/
gulp.task('check:create-cluster', function() {
runSequence('local-up-cluster', ['check'], function(err) {
if (err) {
gulp.start('kill-all');
}
});
});
gulp.task('check:local-cluster', ['lint', 'build', 'test', 'local-cluster-integration-test:prod']);
/**
* Lints all projects code files.
......
......@@ -16,43 +16,16 @@
* @fileoverview Gulp tasks for kubernetes cluster management.
*/
import childProcess from 'child_process';
import del from 'del';
import gulp from 'gulp';
import chmod from 'gulp-chmod';
import gulpFilter from 'gulp-filter';
import git from 'gulp-git';
import gunzip from 'gulp-gunzip';
import untar from 'gulp-untar';
import gulpUtil from 'gulp-util';
import pathExists from 'path-exists';
import request from 'request';
import source from 'vinyl-source-stream';
import conf from './conf';
const kubernetesArchive = 'kubernetes.tar.gz';
const kubernetesUrl = 'https://github.com/kubernetes/kubernetes.git';
const stableVersion = 'v1.1.1';
const tarballUrl = 'https://storage.googleapis.com/kubernetes-release/release';
const upScript = `${conf.paths.kubernetes}/hack/local-up-cluster.sh`;
/**
* The healthz URL of the cluster to check that it is running.
*/
const clusterHealthzUrl = `http://${conf.backend.apiServerHost}/healthz`;
/**
* Currently running cluster process object. Null if the cluster is not running.
*
* @type {?child.ChildProcess}
*/
let clusterProcess = null;
/**
* @type {boolean} The variable is set when there is an error during cluster creation.
*/
let clusterSpawnFailure = null;
/**
* A Number, representing the ID value of the timer that is set for function which periodically
* checks if cluster is running. The null means that no timer is running.
......@@ -61,19 +34,6 @@ let clusterSpawnFailure = null;
*/
let isRunningSetIntervalHandler = null;
/**
* Checks if there was a failure during cluster creation.
* Produces an error in case there was one.
* @param {function(?Error=)} doneFn - callback for the error
*/
function checkForClusterFailure(doneFn) {
if (clusterSpawnFailure) {
clearTimeout(isRunningSetIntervalHandler);
isRunningSetIntervalHandler = null;
doneFn(new Error('There was an error during cluster creation. Aborting.'));
}
}
/**
* Checks if cluster health check return correct status.
* When custer is up and running then return 'ok'.
......@@ -88,18 +48,6 @@ function clusterHealthCheck(doneFn) {
});
}
/**
* Executes controls command using kubectl.
* @param {string} command
* @param {function(?Error=)} doneFn
*/
function executeKubectlCommand(command, doneFn) {
childProcess.exec(`${conf.paths.kubernetes}/cluster/kubectl.sh ${command}`, function(err) {
if (err) return doneFn(new Error(err));
doneFn();
});
}
/**
* Creates cluster from scratch.
* Downloads latest version of kubernetes from git repository.
......@@ -114,96 +62,19 @@ function executeKubectlCommand(command, doneFn) {
gulp.task('local-up-cluster', ['spawn-cluster', 'wait-for-cluster']);
/**
* Tears down a Kubernetes cluster.
* Spawns a local Kubernetes cluster running inside a Docker container.:
*/
gulp.task('kill-cluster', function(doneFn) {
if (clusterProcess) {
clusterProcess.on('exit', function() {
clusterProcess = null;
doneFn();
});
clusterProcess.kill();
} else {
doneFn();
}
});
/**
* Clones kubernetes from git repository. Task skip if kubernetes directory exist.
*/
gulp.task('clone-kubernetes', function(doneFn) {
pathExists(conf.paths.kubernetes).then(function(exists) {
if (!exists) {
git.clone(kubernetesUrl, {args: conf.paths.kubernetes}, function(err) {
if (err) return doneFn(new Error(err));
doneFn();
});
} else {
doneFn();
}
});
});
/**
* Checkouts kubernetes to latest stable version.
*/
gulp.task('checkout-kubernetes-version', ['clone-kubernetes'], function(doneFn) {
git.checkout(stableVersion, {cwd: conf.paths.kubernetes, quiet: true}, function(err) {
if (err) return doneFn(new Error(err));
doneFn();
});
});
/**
* Checks if kubectl is already downloaded.
* If not downloads kubectl for all platforms from tarball.
*/
gulp.task('download-kubectl', function(doneFn) {
let filter = gulpFilter('**/platforms/**');
pathExists(`${conf.paths.kubernetes}/platforms`).then(function(exists) {
if (!exists) {
request(`${tarballUrl}/${stableVersion}/${kubernetesArchive}`)
.pipe(source(`${kubernetesArchive}`))
.pipe(gunzip())
.pipe(untar())
.pipe(filter)
.pipe(chmod(755))
.pipe(gulp.dest(conf.paths.base))
.on('end', function() { doneFn(); });
} else {
doneFn();
gulp.task('spawn-cluster', function(doneFn) {
childProcess.execFile(conf.paths.hyperkube, function(err, stdout, stderr) {
if (err) {
console.log(stdout);
console.error(stderr);
return doneFn(new Error(err));
}
return doneFn();
});
});
/**
* Removes kubernetes before git clone command.
*/
gulp.task('clear-kubernetes', function() { return del(conf.paths.kubernetes); });
/**
* Spawns local-up-cluster.sh script.
*/
gulp.task(
'spawn-cluster',
[
'checkout-kubernetes-version',
'kubeconfig-set-cluster-local',
'kubeconfig-set-context-local',
'kubeconfig-use-context-local',
'kill-cluster',
],
function() {
clusterProcess = childProcess.spawn(upScript, {stdio: 'inherit'});
clusterProcess.on('exit', function(code) {
if (code !== 0) {
clusterSpawnFailure = code;
}
clusterProcess = null;
});
});
/**
* Checks periodically if cluster is up and running.
*/
......@@ -221,8 +92,6 @@ gulp.task('wait-for-cluster', function(doneFn) {
}
counter += 1;
checkForClusterFailure(doneFn);
// constantly query the cluster until it is properly running
clusterHealthCheck(function(result) {
if (result === 'ok') {
......@@ -234,32 +103,3 @@ gulp.task('wait-for-cluster', function(doneFn) {
});
}
});
/**
* Sets a cluster entry in kubeconfig.
* Configures kubernetes server for localhost.
*/
gulp.task(
'kubeconfig-set-cluster-local', ['download-kubectl', 'checkout-kubernetes-version'],
function(doneFn) {
executeKubectlCommand(
`config set-cluster local --server=http://${conf.backend.apiServerHost}` +
' --insecure-skip-tls-verify=true',
doneFn);
});
/**
* Sets a context entry in kubeconfig as local.
*/
gulp.task(
'kubeconfig-set-context-local', ['download-kubectl', 'checkout-kubernetes-version'],
function(doneFn) {
executeKubectlCommand('config set-context local --cluster=local', doneFn);
});
/**
* Sets the current-context in a kubeconfig file
*/
gulp.task(
'kubeconfig-use-context-local', ['download-kubectl', 'checkout-kubernetes-version'],
function(doneFn) { executeKubectlCommand('config use-context local', doneFn); });
......@@ -95,9 +95,9 @@ export default {
frontendTest: path.join(basePath, 'src/test/frontend'),
goTools: path.join(basePath, '.tools/go'),
goWorkspace: path.join(basePath, '.go_workspace'),
hyperkube: path.join(basePath, 'build/hyperkube.sh'),
integrationTest: path.join(basePath, 'src/test/integration'),
karmaConf: path.join(basePath, 'build/karma.conf.js'),
kubernetes: path.join(basePath, 'kubernetes'),
nodeModules: path.join(basePath, 'node_modules'),
partials: path.join(basePath, '.tmp/partials'),
prodTmp: path.join(basePath, '.tmp/prod'),
......
#!/bin/bash
# Copyright 2015 Google Inc. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
# Starts local hypercube cluster in a Docker container.
# Learn more at https://github.com/kubernetes/kubernetes/blob/master/docs/getting-started-guides/docker.md
# Version of kubernetes to use.
K8S_VERSION="1.1.2"
# Port of the apiserver to serve on.
PORT=8080
docker run --net=host -d gcr.io/google_containers/etcd:2.0.12 \
/usr/local/bin/etcd --addr=127.0.0.1:4001 --bind-addr=0.0.0.0:4001 --data-dir=/var/etcd/data
docker run \
--volume=/:/rootfs:ro \
--volume=/sys:/sys:ro \
--volume=/dev:/dev \
--volume=/var/lib/docker/:/var/lib/docker:ro \
--volume=/var/lib/kubelet/:/var/lib/kubelet:rw \
--volume=/var/run:/var/run:rw \
--net=host \
--pid=host \
--privileged=true \
-d \
gcr.io/google_containers/hyperkube:v${K8S_VERSION} \
/hyperkube kubelet --containerized --hostname-override="127.0.0.1" \
--address="0.0.0.0" --api-servers=http://localhost:${PORT} \
--config=/etc/kubernetes/manifests
docker run -d --net=host --privileged gcr.io/google_containers/hyperkube:v${K8S_VERSION} \
/hyperkube proxy --master=http://127.0.0.1:${PORT} --v=2
......@@ -55,14 +55,14 @@ function runProtractorTests(doneFn) {
// Close browser sync server to prevent the process from hanging.
browserSyncInstance.exit();
// Kill backend server and cluster, if running.
gulp.start('kill-all');
gulp.start('kill-backend');
doneFn(err);
})
.on('end', function() {
// Close browser sync server to prevent the process from hanging.
browserSyncInstance.exit();
// Kill backend server and cluster, if running.
gulp.start('kill-all');
gulp.start('kill-backend');
doneFn();
});
}
......@@ -135,11 +135,13 @@ gulp.task('integration-test', ['serve:nowatch', 'webdriver-update'], runProtract
gulp.task('integration-test:prod', ['serve:prod', 'webdriver-update'], runProtractorTests);
/**
* Downloads and updates webdriver. Required to keep it up to date.
* Runs application integration tests. Uses production version of the application.
*/
gulp.task('webdriver-update', gulpProtractor.webdriver_update);
gulp.task(
'local-cluster-integration-test:prod', ['serve:prod', 'webdriver-update', 'local-up-cluster'],
runProtractorTests);
/**
* Kills backend server and cluster, if running.
* Downloads and updates webdriver. Required to keep it up to date.
*/
gulp.task('kill-all', ['kill-backend', 'kill-cluster']);
gulp.task('webdriver-update', gulpProtractor.webdriver_update);
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册