From e059239bc31992c70f3907dfe6c3066b10aae41e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micae=CC=88l?= Date: Sat, 23 Jul 2016 19:59:54 +0200 Subject: [PATCH] Move webui to FountainJS with Webpack --- Makefile | 2 +- webui/.bowerrc | 3 - webui/.gitattributes | 1 + webui/.gitignore | 9 +- webui/.yo-rc.json | 82 +--- webui/Dockerfile | 5 - webui/bower.json | 45 -- webui/conf/browsersync-dist.conf.js | 12 + webui/conf/browsersync.conf.js | 13 + webui/conf/gulp.conf.js | 47 +++ webui/conf/karma-auto.conf.js | 55 +++ webui/conf/karma.conf.js | 55 +++ webui/conf/webpack-dist.conf.js | 74 ++++ webui/conf/webpack-test.conf.js | 41 ++ webui/conf/webpack.conf.js | 61 +++ webui/e2e/.eslintrc | 9 - webui/gulp/.eslintrc | 5 - webui/gulp/build.js | 98 ----- webui/gulp/conf.js | 41 -- webui/gulp/e2e-tests.js | 38 -- webui/gulp/inject.js | 42 -- webui/gulp/scripts.js | 26 -- webui/gulp/server.js | 63 --- webui/gulp/styles.js | 54 --- webui/gulp/unit-tests.js | 52 --- webui/gulp/watch.js | 39 -- webui/gulp_tasks/browsersync.js | 21 + webui/gulp_tasks/karma.js | 25 ++ webui/gulp_tasks/misc.js | 25 ++ webui/gulp_tasks/webpack.js | 48 +++ webui/gulpfile.js | 48 +-- webui/karma.conf.js | 110 ----- webui/package.json | 143 ++++--- webui/protractor.conf.js | 27 -- webui/readme.md | 9 +- webui/{ => src}/.eslintrc | 0 webui/src/app/core/health.resource.js | 21 +- webui/src/app/core/providers.resource.js | 21 +- webui/src/app/index.config.js | 15 - webui/src/app/index.constants.js | 9 - webui/src/app/index.module.js | 7 - webui/src/app/index.run.js | 14 - webui/src/app/index.scss | 1 - .../app/sections/health/health.controller.js | 389 +++++++++--------- .../src/app/sections/health/health.module.js | 33 +- .../backend-monitor.directive.js | 39 +- .../backend-monitor/backend-monitor.module.js | 13 +- .../frontend-monitor.directive.js | 39 +- .../frontend-monitor.module.js | 12 +- .../providers/providers.controller.js | 41 +- .../sections/providers/providers.module.js | 44 +- webui/src/app/sections/sections.config.js | 13 - webui/src/app/sections/sections.js | 24 ++ webui/src/app/sections/sections.module.js | 13 - webui/src/app/traefik.scss | 6 +- webui/src/index.html | 35 +- webui/src/index.js | 46 +++ webui/src/index.scss | 3 + 58 files changed, 1027 insertions(+), 1239 deletions(-) delete mode 100644 webui/.bowerrc create mode 100644 webui/.gitattributes delete mode 100644 webui/bower.json create mode 100755 webui/conf/browsersync-dist.conf.js create mode 100755 webui/conf/browsersync.conf.js create mode 100644 webui/conf/gulp.conf.js create mode 100644 webui/conf/karma-auto.conf.js create mode 100644 webui/conf/karma.conf.js create mode 100644 webui/conf/webpack-dist.conf.js create mode 100644 webui/conf/webpack-test.conf.js create mode 100644 webui/conf/webpack.conf.js delete mode 100644 webui/e2e/.eslintrc delete mode 100644 webui/gulp/.eslintrc delete mode 100644 webui/gulp/build.js delete mode 100644 webui/gulp/conf.js delete mode 100644 webui/gulp/e2e-tests.js delete mode 100644 webui/gulp/inject.js delete mode 100644 webui/gulp/scripts.js delete mode 100644 webui/gulp/server.js delete mode 100644 webui/gulp/styles.js delete mode 100644 webui/gulp/unit-tests.js delete mode 100644 webui/gulp/watch.js create mode 100644 webui/gulp_tasks/browsersync.js create mode 100644 webui/gulp_tasks/karma.js create mode 100644 webui/gulp_tasks/misc.js create mode 100644 webui/gulp_tasks/webpack.js delete mode 100644 webui/karma.conf.js delete mode 100644 webui/protractor.conf.js rename webui/{ => src}/.eslintrc (100%) delete mode 100644 webui/src/app/index.config.js delete mode 100644 webui/src/app/index.constants.js delete mode 100644 webui/src/app/index.module.js delete mode 100644 webui/src/app/index.run.js delete mode 100644 webui/src/app/sections/sections.config.js create mode 100644 webui/src/app/sections/sections.js delete mode 100644 webui/src/app/sections/sections.module.js create mode 100644 webui/src/index.js create mode 100644 webui/src/index.scss diff --git a/Makefile b/Makefile index 7ddb7564d..0003cdb21 100644 --- a/Makefile +++ b/Makefile @@ -73,7 +73,7 @@ run-dev: generate-webui: build-webui if [ ! -d "static" ]; then \ mkdir -p static; \ - docker run --rm -v "$$PWD/static":'/src/static' traefik-webui gulp; \ + docker run --rm -v "$$PWD/static":'/src/static' traefik-webui npm run build; \ echo 'For more informations show `webui/readme.md`' > $$PWD/static/DONT-EDIT-FILES-IN-THIS-DIRECTORY.md; \ fi diff --git a/webui/.bowerrc b/webui/.bowerrc deleted file mode 100644 index 69fad3580..000000000 --- a/webui/.bowerrc +++ /dev/null @@ -1,3 +0,0 @@ -{ - "directory": "bower_components" -} diff --git a/webui/.gitattributes b/webui/.gitattributes new file mode 100644 index 000000000..176a458f9 --- /dev/null +++ b/webui/.gitattributes @@ -0,0 +1 @@ +* text=auto diff --git a/webui/.gitignore b/webui/.gitignore index 745107738..d217ca660 100644 --- a/webui/.gitignore +++ b/webui/.gitignore @@ -1,5 +1,6 @@ -node_modules/ -bower_components/ -coverage/ -.sass-cache/ .tmp/ +coverage/ +dist/ +node_modules/ +.sass-cache/ + diff --git a/webui/.yo-rc.json b/webui/.yo-rc.json index 95e0f9aad..c266b5373 100644 --- a/webui/.yo-rc.json +++ b/webui/.yo-rc.json @@ -1,74 +1,20 @@ { - "generator-gulp-angular": { - "version": "1.0.2", + "generator-fountain-angular1": { + "version": "0.6.0", "props": { - "angularVersion": "~1.4.2", - "angularModules": [ - { - "key": "animate", - "module": "ngAnimate" - }, - { - "key": "cookies", - "module": "ngCookies" - }, - { - "key": "sanitize", - "module": "ngSanitize" - }, - { - "key": "messages", - "module": "ngMessages" - }, - { - "key": "aria", - "module": "ngAria" - } - ], - "jQuery": { - "key": "jquery2" + "resolved": "/Users/micael/Documents/zenika/fountain/generator-fountain-angular1/generators/app/index.js", + "namespace": "fountain-angular1:app", + "argv": { + "remain": [], + "cooked": [], + "original": [] }, - "resource": { - "key": "angular-resource", - "module": "ngResource" - }, - "router": { - "key": "ui-router", - "module": "ui.router" - }, - "ui": { - "key": "bootstrap", - "module": null - }, - "bootstrapComponents": { - "key": "ui-bootstrap", - "module": "ui.bootstrap" - }, - "cssPreprocessor": { - "key": "node-sass", - "extension": "scss" - }, - "jsPreprocessor": { - "key": "noJsPrepro", - "extension": "js", - "srcExtension": "js" - }, - "htmlPreprocessor": { - "key": "noHtmlPrepro", - "extension": "html" - }, - "foundationComponents": { - "name": null, - "version": null, - "key": null, - "module": null - }, - "paths": { - "src": "src", - "dist": "../static", - "e2e": "e2e", - "tmp": ".tmp" - } + "framework": "angular1", + "modules": "webpack", + "css": "scss", + "js": "js", + "sample": "hello", + "router": "none" } } } \ No newline at end of file diff --git a/webui/Dockerfile b/webui/Dockerfile index 113926d8b..675d5b09d 100644 --- a/webui/Dockerfile +++ b/webui/Dockerfile @@ -3,16 +3,11 @@ FROM node:6.3.0 ENV WEBUI_DIR /src/webui RUN mkdir -p $WEBUI_DIR -RUN npm install -g gulp bower - COPY package.json $WEBUI_DIR/ -COPY .bowerrc $WEBUI_DIR/ -COPY bower.json $WEBUI_DIR/ WORKDIR $WEBUI_DIR RUN npm set progress=false RUN npm install --quiet -RUN bower install --allow-root --quiet COPY . $WEBUI_DIR/ diff --git a/webui/bower.json b/webui/bower.json deleted file mode 100644 index 0dc46332e..000000000 --- a/webui/bower.json +++ /dev/null @@ -1,45 +0,0 @@ -{ - "name": "traefik", - "version": "2.0.0", - "homepage": "http://traefik.io", - "authors": [ - "Fernandez Ludovic " - ], - "description": "Front end for Træfɪk", - "license": "MIT", - "dependencies": { - "angular-animate": "~1.4.2", - "angular-cookies": "~1.4.2", - "angular-sanitize": "~1.4.2", - "angular-messages": "~1.4.2", - "angular-aria": "~1.4.2", - "jquery": "~2.1.4", - "angular-resource": "~1.4.2", - "angular-ui-router": "~0.2.15", - "bootstrap-sass": "~3.3.5", - "angular-bootstrap": "~0.13.4", - "moment": "~2.10.6", - "animate.css": "~3.4.0", - "angular": "~1.4.2", - "angular-nvd3": "~1.0.5" - }, - "devDependencies": { - "angular-mocks": "~1.4.2" - }, - "overrides": { - "bootstrap-sass": { - "main": [ - "assets/stylesheets/_bootstrap.scss", - "assets/fonts/bootstrap/glyphicons-halflings-regular.eot", - "assets/fonts/bootstrap/glyphicons-halflings-regular.svg", - "assets/fonts/bootstrap/glyphicons-halflings-regular.ttf", - "assets/fonts/bootstrap/glyphicons-halflings-regular.woff", - "assets/fonts/bootstrap/glyphicons-halflings-regular.woff2" - ] - } - }, - "resolutions": { - "jquery": "~2.1.4", - "angular": "~1.4.2" - } -} diff --git a/webui/conf/browsersync-dist.conf.js b/webui/conf/browsersync-dist.conf.js new file mode 100755 index 000000000..fa4584553 --- /dev/null +++ b/webui/conf/browsersync-dist.conf.js @@ -0,0 +1,12 @@ +const conf = require('./gulp.conf'); + +module.exports = function () { + return { + server: { + baseDir: [ + conf.paths.dist + ] + }, + open: false + }; +}; diff --git a/webui/conf/browsersync.conf.js b/webui/conf/browsersync.conf.js new file mode 100755 index 000000000..49936d48c --- /dev/null +++ b/webui/conf/browsersync.conf.js @@ -0,0 +1,13 @@ +const conf = require('./gulp.conf'); + +module.exports = function () { + return { + server: { + baseDir: [ + conf.paths.tmp, + conf.paths.src + ] + }, + open: false + }; +}; diff --git a/webui/conf/gulp.conf.js b/webui/conf/gulp.conf.js new file mode 100644 index 000000000..c56dda75c --- /dev/null +++ b/webui/conf/gulp.conf.js @@ -0,0 +1,47 @@ +'use strict'; + +/** + * This file contains the variables used in other gulp files + * which defines tasks + * By design, we only put there very generic config values + * which are used in several places to keep good readability + * of the tasks + */ + +const path = require('path'); +const gutil = require('gulp-util'); + +exports.ngModule = 'traefik'; + +/** + * The main paths of your project handle these with care + */ +exports.paths = { + src: 'src', + dist: '../static', + tmp: '.tmp', + e2e: 'e2e', + tasks: 'gulp_tasks' +}; + +exports.path = {}; +for (const pathName in exports.paths) { + if (exports.paths.hasOwnProperty(pathName)) { + exports.path[pathName] = function pathJoin() { + const pathValue = exports.paths[pathName]; + const funcArgs = Array.prototype.slice.call(arguments); + const joinArgs = [pathValue].concat(funcArgs); + return path.join.apply(this, joinArgs); + }; + } +} + +/** + * Common implementation for an error handler of a Gulp plugin + */ +exports.errorHandler = function (title) { + return function (err) { + gutil.log(gutil.colors.red(`[${title}]`), err.toString()); + this.emit('end'); + }; +}; diff --git a/webui/conf/karma-auto.conf.js b/webui/conf/karma-auto.conf.js new file mode 100644 index 000000000..4fdf45c9e --- /dev/null +++ b/webui/conf/karma-auto.conf.js @@ -0,0 +1,55 @@ +const conf = require('./gulp.conf'); + +module.exports = function (config) { + const configuration = { + basePath: '../', + singleRun: false, + autoWatch: true, + logLevel: 'INFO', + junitReporter: { + outputDir: 'test-reports' + }, + browsers: [ + 'PhantomJS' + ], + frameworks: [ + 'jasmine' + ], + files: [ + 'node_modules/es6-shim/es6-shim.js', + conf.path.src('index.spec.js'), + conf.path.src('**/*.html') + ], + preprocessors: { + [conf.path.src('index.spec.js')]: [ + 'webpack' + ], + [conf.path.src('**/*.html')]: [ + 'ng-html2js' + ] + }, + ngHtml2JsPreprocessor: { + stripPrefix: `${conf.paths.src}/` + }, + reporters: ['progress', 'coverage'], + coverageReporter: { + type: 'html', + dir: 'coverage/' + }, + webpack: require('./webpack-test.conf'), + webpackMiddleware: { + noInfo: true + }, + plugins: [ + require('karma-jasmine'), + require('karma-junit-reporter'), + require('karma-coverage'), + require('karma-phantomjs-launcher'), + require('karma-phantomjs-shim'), + require('karma-ng-html2js-preprocessor'), + require('karma-webpack') + ] + }; + + config.set(configuration); +}; diff --git a/webui/conf/karma.conf.js b/webui/conf/karma.conf.js new file mode 100644 index 000000000..b4303595b --- /dev/null +++ b/webui/conf/karma.conf.js @@ -0,0 +1,55 @@ +const conf = require('./gulp.conf'); + +module.exports = function (config) { + const configuration = { + basePath: '../', + singleRun: true, + autoWatch: false, + logLevel: 'INFO', + junitReporter: { + outputDir: 'test-reports' + }, + browsers: [ + 'PhantomJS' + ], + frameworks: [ + 'jasmine' + ], + files: [ + 'node_modules/es6-shim/es6-shim.js', + conf.path.src('index.spec.js'), + conf.path.src('**/*.html') + ], + preprocessors: { + [conf.path.src('index.spec.js')]: [ + 'webpack' + ], + [conf.path.src('**/*.html')]: [ + 'ng-html2js' + ] + }, + ngHtml2JsPreprocessor: { + stripPrefix: `${conf.paths.src}/` + }, + reporters: ['progress', 'coverage'], + coverageReporter: { + type: 'html', + dir: 'coverage/' + }, + webpack: require('./webpack-test.conf'), + webpackMiddleware: { + noInfo: true + }, + plugins: [ + require('karma-jasmine'), + require('karma-junit-reporter'), + require('karma-coverage'), + require('karma-phantomjs-launcher'), + require('karma-phantomjs-shim'), + require('karma-ng-html2js-preprocessor'), + require('karma-webpack') + ] + }; + + config.set(configuration); +}; diff --git a/webui/conf/webpack-dist.conf.js b/webui/conf/webpack-dist.conf.js new file mode 100644 index 000000000..90ddcc1f1 --- /dev/null +++ b/webui/conf/webpack-dist.conf.js @@ -0,0 +1,74 @@ +const webpack = require('webpack'); +const conf = require('./gulp.conf'); +const path = require('path'); + +const HtmlWebpackPlugin = require('html-webpack-plugin'); +const SplitByPathPlugin = require('webpack-split-by-path'); +const ExtractTextPlugin = require("extract-text-webpack-plugin"); +const autoprefixer = require('autoprefixer'); + +module.exports = { + module: { + preLoaders: [ + { + test: /\.js$/, + exclude: /node_modules/, + loader: 'eslint' + } + ], + + loaders: [ + { + test: /.json$/, + loaders: [ + 'json' + ] + }, + { + test: /\.(css|scss)$/, + loaders: ExtractTextPlugin.extract('style', 'css?minimize!sass', 'postcss') + }, + { + test: /\.js$/, + exclude: /node_modules/, + loaders: [ + 'ng-annotate' + ] + }, + { + test: /.html$/, + loaders: [ + 'html' + ] + }, + { + test: /\.(png|woff|woff2|eot|ttf|svg)$/, + loader: 'url-loader?limit=100000' + } + ] + }, + plugins: [ + new webpack.optimize.OccurrenceOrderPlugin(), + new webpack.NoErrorsPlugin(), + new HtmlWebpackPlugin({ + template: conf.path.src('index.html'), + inject: true + }), + new webpack.optimize.UglifyJsPlugin({ + compress: {unused: true, dead_code: true} // eslint-disable-line camelcase + }), + new SplitByPathPlugin([{ + name: 'vendor', + path: path.join(__dirname, '../node_modules') + }]), + new ExtractTextPlugin('./index-[contenthash].css') + ], + postcss: () => [autoprefixer], + output: { + path: path.join(process.cwd(), conf.paths.dist), + filename: './[name]-[hash].js' + }, + entry: { + app: `./${conf.path.src('index')}` + } +}; diff --git a/webui/conf/webpack-test.conf.js b/webui/conf/webpack-test.conf.js new file mode 100644 index 000000000..512a39e67 --- /dev/null +++ b/webui/conf/webpack-test.conf.js @@ -0,0 +1,41 @@ +module.exports = { + module: { + preLoaders: [ + { + test: /\.js$/, + exclude: /node_modules/, + loader: 'eslint' + } + ], + + loaders: [ + { + test: /.json$/, + loaders: [ + 'json' + ] + }, + { + test: /\.js$/, + exclude: /node_modules/, + loaders: [ + 'ng-annotate' + ] + }, + { + test: /.html$/, + loaders: [ + 'html' + ] + }, + { + test: /\.js$/, + exclude: /(node_modules|.*\.spec\.js)/, + loader: 'isparta' + } + ] + }, + plugins: [], + debug: true, + devtool: 'cheap-module-eval-source-map' +}; diff --git a/webui/conf/webpack.conf.js b/webui/conf/webpack.conf.js new file mode 100644 index 000000000..92ce2e155 --- /dev/null +++ b/webui/conf/webpack.conf.js @@ -0,0 +1,61 @@ +const webpack = require('webpack'); +const conf = require('./gulp.conf'); +const path = require('path'); + +const HtmlWebpackPlugin = require('html-webpack-plugin'); +const autoprefixer = require('autoprefixer'); + +module.exports = { + module: { + loaders: [ + { + test: /.json$/, + loaders: [ + 'json' + ] + }, + { + test: /\.(css|scss)$/, + loaders: [ + 'style', + 'css', + 'sass', + 'postcss' + ] + }, + { + test: /\.js$/, + exclude: /node_modules/, + loaders: [ + 'ng-annotate' + ] + }, + { + test: /.html$/, + loaders: [ + 'html' + ] + }, + { + test: /\.(png|woff|woff2|eot|ttf|svg)$/, + loader: 'url-loader?limit=100000' + } + ] + }, + plugins: [ + new webpack.optimize.OccurrenceOrderPlugin(), + new webpack.NoErrorsPlugin(), + new HtmlWebpackPlugin({ + template: conf.path.src('index.html'), + inject: true + }) + ], + postcss: () => [autoprefixer], + debug: true, + devtool: 'cheap-module-eval-source-map', + output: { + path: path.join(process.cwd(), conf.paths.tmp), + filename: 'index.js' + }, + entry: `./${conf.path.src('index')}` +}; diff --git a/webui/e2e/.eslintrc b/webui/e2e/.eslintrc deleted file mode 100644 index d2c6f97f7..000000000 --- a/webui/e2e/.eslintrc +++ /dev/null @@ -1,9 +0,0 @@ -{ - "globals": { - "browser": false, - "element": false, - "by": false, - "$": false, - "$$": false - } -} diff --git a/webui/gulp/.eslintrc b/webui/gulp/.eslintrc deleted file mode 100644 index 10d223883..000000000 --- a/webui/gulp/.eslintrc +++ /dev/null @@ -1,5 +0,0 @@ -{ - "env": { - "node": true - } -} diff --git a/webui/gulp/build.js b/webui/gulp/build.js deleted file mode 100644 index ed75a4832..000000000 --- a/webui/gulp/build.js +++ /dev/null @@ -1,98 +0,0 @@ -'use strict'; - -var path = require('path'); -var gulp = require('gulp'); -var conf = require('./conf'); - -var $ = require('gulp-load-plugins')({ - pattern: ['gulp-*', 'main-bower-files', 'uglify-save-license', 'del'] -}); - -gulp.task('partials', function () { - return gulp.src([ - path.join(conf.paths.src, '/app/**/*.html'), - path.join(conf.paths.tmp, '/serve/app/**/*.html') - ]) - .pipe($.minifyHtml({ - empty: true, - spare: true, - quotes: true - })) - .pipe($.angularTemplatecache('templateCacheHtml.js', { - module: 'traefik', - root: 'app' - })) - .pipe(gulp.dest(conf.paths.tmp + '/partials/')); -}); - -gulp.task('html', ['inject', 'partials'], function () { - var partialsInjectFile = gulp.src(path.join(conf.paths.tmp, '/partials/templateCacheHtml.js'), { read: false }); - var partialsInjectOptions = { - starttag: '', - ignorePath: path.join(conf.paths.tmp, '/partials'), - addRootSlash: false - }; - - var htmlFilter = $.filter('*.html', { restore: true }); - var jsFilter = $.filter('**/*.js', { restore: true }); - var cssFilter = $.filter('**/*.css', { restore: true }); - var assets; - - return gulp.src(path.join(conf.paths.tmp, '/serve/*.html')) - .pipe($.inject(partialsInjectFile, partialsInjectOptions)) - .pipe(assets = $.useref.assets()) - .pipe($.rev()) - .pipe(jsFilter) - .pipe($.sourcemaps.init()) - .pipe($.ngAnnotate()) - .pipe($.uglify({ preserveComments: $.uglifySaveLicense })).on('error', conf.errorHandler('Uglify')) - .pipe($.sourcemaps.write('maps')) - .pipe(jsFilter.restore) - .pipe(cssFilter) - .pipe($.sourcemaps.init()) - .pipe($.replace('../../bower_components/bootstrap-sass/assets/fonts/bootstrap/', '../fonts/')) - .pipe($.minifyCss({ processImport: false })) - .pipe($.sourcemaps.write('maps')) - .pipe(cssFilter.restore) - .pipe(assets.restore()) - .pipe($.useref()) - .pipe($.revReplace()) - .pipe(htmlFilter) - .pipe($.minifyHtml({ - empty: true, - spare: true, - quotes: true, - conditionals: true - })) - .pipe(htmlFilter.restore) - .pipe(gulp.dest(path.join(conf.paths.dist, '/'))) - .pipe($.size({ title: path.join(conf.paths.dist, '/'), showFiles: true })); - }); - -// Only applies for fonts from bower dependencies -// Custom fonts are handled by the "other" task -gulp.task('fonts', function () { - return gulp.src($.mainBowerFiles()) - .pipe($.filter('**/*.{eot,svg,ttf,woff,woff2}')) - .pipe($.flatten()) - .pipe(gulp.dest(path.join(conf.paths.dist, '/fonts/'))); -}); - -gulp.task('other', function () { - var fileFilter = $.filter(function (file) { - return file.stat.isFile(); - }); - - return gulp.src([ - path.join(conf.paths.src, '/**/*'), - path.join('!' + conf.paths.src, '/**/*.{html,css,js,scss}') - ]) - .pipe(fileFilter) - .pipe(gulp.dest(path.join(conf.paths.dist, '/'))); -}); - -gulp.task('clean', function () { - return $.del([path.join(conf.paths.dist, '/**'), '!' + conf.paths.dist, path.join(conf.paths.tmp, '/')], {force: true}); -}); - -gulp.task('build', ['html', 'fonts', 'other']); diff --git a/webui/gulp/conf.js b/webui/gulp/conf.js deleted file mode 100644 index cbbed6fb6..000000000 --- a/webui/gulp/conf.js +++ /dev/null @@ -1,41 +0,0 @@ -/** - * This file contains the variables used in other gulp files - * which defines tasks - * By design, we only put there very generic config values - * which are used in several places to keep good readability - * of the tasks - */ - -var gutil = require('gulp-util'); - -/** - * The main paths of your project handle these with care - */ -exports.paths = { - src: 'src', - dist: '../static', - tmp: '.tmp', - e2e: 'e2e' -}; - -/** - * Wiredep is the lib which inject bower dependencies in your project - * Mainly used to inject script tags in the index.html but also used - * to inject css preprocessor deps and js files in karma - */ -exports.wiredep = { - exclude: [/\/bootstrap\.js$/, /\/bootstrap-sass\/.*\.js/, /\/bootstrap\.css/], - directory: 'bower_components' -}; - -/** - * Common implementation for an error handler of a Gulp plugin - */ -exports.errorHandler = function(title) { - 'use strict'; - - return function(err) { - gutil.log(gutil.colors.red('[' + title + ']'), err.toString()); - this.emit('end'); - }; -}; diff --git a/webui/gulp/e2e-tests.js b/webui/gulp/e2e-tests.js deleted file mode 100644 index 3a66702a4..000000000 --- a/webui/gulp/e2e-tests.js +++ /dev/null @@ -1,38 +0,0 @@ -'use strict'; - -var path = require('path'); -var gulp = require('gulp'); -var conf = require('./conf'); - -var browserSync = require('browser-sync'); - -var $ = require('gulp-load-plugins')(); - -// Downloads the selenium webdriver -gulp.task('webdriver-update', $.protractor.webdriver_update); - -gulp.task('webdriver-standalone', $.protractor.webdriver_standalone); - -function runProtractor (done) { - var params = process.argv; - var args = params.length > 3 ? [params[3], params[4]] : []; - - gulp.src(path.join(conf.paths.e2e, '/**/*.js')) - .pipe($.protractor.protractor({ - configFile: 'protractor.conf.js', - args: args - })) - .on('error', function (err) { - // Make sure failed tests cause gulp to exit non-zero - throw err; - }) - .on('end', function () { - // Close browser sync server - browserSync.exit(); - done(); - }); -} - -gulp.task('protractor', ['protractor:src']); -gulp.task('protractor:src', ['serve:e2e', 'webdriver-update'], runProtractor); -gulp.task('protractor:dist', ['serve:e2e-dist', 'webdriver-update'], runProtractor); diff --git a/webui/gulp/inject.js b/webui/gulp/inject.js deleted file mode 100644 index 2a5804b56..000000000 --- a/webui/gulp/inject.js +++ /dev/null @@ -1,42 +0,0 @@ -'use strict'; - -var path = require('path'); -var gulp = require('gulp'); -var conf = require('./conf'); - -var $ = require('gulp-load-plugins')(); - -var wiredep = require('wiredep').stream; -var _ = require('lodash'); - -var browserSync = require('browser-sync'); - -gulp.task('inject-reload', ['inject'], function() { - browserSync.reload(); -}); - -gulp.task('inject', ['scripts', 'styles'], function () { - var injectStyles = gulp.src([ - path.join(conf.paths.tmp, '/serve/app/**/*.css'), - path.join('!' + conf.paths.tmp, '/serve/app/vendor.css') - ], { read: false }); - - var injectScripts = gulp.src([ - path.join(conf.paths.src, '/app/**/*.module.js'), - path.join(conf.paths.src, '/app/**/*.js'), - path.join('!' + conf.paths.src, '/app/**/*.spec.js'), - path.join('!' + conf.paths.src, '/app/**/*.mock.js'), - ]) - .pipe($.angularFilesort()).on('error', conf.errorHandler('AngularFilesort')); - - var injectOptions = { - ignorePath: [conf.paths.src, path.join(conf.paths.tmp, '/serve')], - addRootSlash: false - }; - - return gulp.src(path.join(conf.paths.src, '/*.html')) - .pipe($.inject(injectStyles, injectOptions)) - .pipe($.inject(injectScripts, injectOptions)) - .pipe(wiredep(_.extend({}, conf.wiredep))) - .pipe(gulp.dest(path.join(conf.paths.tmp, '/serve'))); -}); diff --git a/webui/gulp/scripts.js b/webui/gulp/scripts.js deleted file mode 100644 index 585e4fc8a..000000000 --- a/webui/gulp/scripts.js +++ /dev/null @@ -1,26 +0,0 @@ -'use strict'; - -var path = require('path'); -var gulp = require('gulp'); -var conf = require('./conf'); - -var browserSync = require('browser-sync'); - -var $ = require('gulp-load-plugins')(); - - -gulp.task('scripts-reload', function() { - return buildScripts() - .pipe(browserSync.stream()); -}); - -gulp.task('scripts', function() { - return buildScripts(); -}); - -function buildScripts() { - return gulp.src(path.join(conf.paths.src, '/app/**/*.js')) - .pipe($.eslint()) - .pipe($.eslint.format()) - .pipe($.size()) -}; diff --git a/webui/gulp/server.js b/webui/gulp/server.js deleted file mode 100644 index 500b0c0d0..000000000 --- a/webui/gulp/server.js +++ /dev/null @@ -1,63 +0,0 @@ -'use strict'; - -var path = require('path'); -var gulp = require('gulp'); -var conf = require('./conf'); - -var browserSync = require('browser-sync'); -var browserSyncSpa = require('browser-sync-spa'); - -var util = require('util'); - -var proxyMiddleware = require('http-proxy-middleware'); - -function browserSyncInit(baseDir, browser) { - browser = browser === undefined ? 'default' : browser; - - var routes = null; - if(baseDir === conf.paths.src || (util.isArray(baseDir) && baseDir.indexOf(conf.paths.src) !== -1)) { - routes = { - '/bower_components': 'bower_components' - }; - } - - var server = { - baseDir: baseDir, - routes: routes - }; - - /* - * You can add a proxy to your backend by uncommenting the line below. - * You just have to configure a context which will we redirected and the target url. - * Example: $http.get('/users') requests will be automatically proxified. - * - * For more details and option, https://github.com/chimurai/http-proxy-middleware/blob/v0.9.0/README.md - */ - // server.middleware = proxyMiddleware('/users', {target: 'http://jsonplaceholder.typicode.com', changeOrigin: true}); - - browserSync.instance = browserSync.init({ - startPath: '/', - server: server, - browser: browser - }); -} - -browserSync.use(browserSyncSpa({ - selector: '[ng-app]'// Only needed for angular apps -})); - -gulp.task('serve', ['watch'], function () { - browserSyncInit([path.join(conf.paths.tmp, '/serve'), conf.paths.src]); -}); - -gulp.task('serve:dist', ['build'], function () { - browserSyncInit(conf.paths.dist); -}); - -gulp.task('serve:e2e', ['inject'], function () { - browserSyncInit([conf.paths.tmp + '/serve', conf.paths.src], []); -}); - -gulp.task('serve:e2e-dist', ['build'], function () { - browserSyncInit(conf.paths.dist, []); -}); diff --git a/webui/gulp/styles.js b/webui/gulp/styles.js deleted file mode 100644 index 9eada3f90..000000000 --- a/webui/gulp/styles.js +++ /dev/null @@ -1,54 +0,0 @@ -'use strict'; - -var path = require('path'); -var gulp = require('gulp'); -var conf = require('./conf'); - -var browserSync = require('browser-sync'); - -var $ = require('gulp-load-plugins')(); - -var wiredep = require('wiredep').stream; -var _ = require('lodash'); - -gulp.task('styles-reload', ['styles'], function() { - return buildStyles() - .pipe(browserSync.stream()); -}); - -gulp.task('styles', function() { - return buildStyles(); -}); - -var buildStyles = function() { - var sassOptions = { - style: 'expanded' - }; - - var injectFiles = gulp.src([ - path.join(conf.paths.src, '/app/**/*.scss'), - path.join('!' + conf.paths.src, '/app/index.scss') - ], { read: false }); - - var injectOptions = { - transform: function(filePath) { - filePath = filePath.replace(conf.paths.src + '/app/', ''); - return '@import "' + filePath + '";'; - }, - starttag: '// injector', - endtag: '// endinjector', - addRootSlash: false - }; - - - return gulp.src([ - path.join(conf.paths.src, '/app/index.scss') - ]) - .pipe($.inject(injectFiles, injectOptions)) - .pipe(wiredep(_.extend({}, conf.wiredep))) - .pipe($.sourcemaps.init()) - .pipe($.sass(sassOptions)).on('error', conf.errorHandler('Sass')) - .pipe($.autoprefixer()).on('error', conf.errorHandler('Autoprefixer')) - .pipe($.sourcemaps.write()) - .pipe(gulp.dest(path.join(conf.paths.tmp, '/serve/app/'))); -}; diff --git a/webui/gulp/unit-tests.js b/webui/gulp/unit-tests.js deleted file mode 100644 index 576887aef..000000000 --- a/webui/gulp/unit-tests.js +++ /dev/null @@ -1,52 +0,0 @@ -'use strict'; - -var path = require('path'); -var gulp = require('gulp'); -var conf = require('./conf'); - -var karma = require('karma'); - -var pathSrcHtml = [ - path.join(conf.paths.src, '/**/*.html') -]; - -var pathSrcJs = [ - path.join(conf.paths.src, '/**/!(*.spec).js') -]; - -function runTests (singleRun, done) { - var reporters = ['progress']; - var preprocessors = {}; - - pathSrcHtml.forEach(function(path) { - preprocessors[path] = ['ng-html2js']; - }); - - if (singleRun) { - pathSrcJs.forEach(function(path) { - preprocessors[path] = ['coverage']; - }); - reporters.push('coverage') - } - - var localConfig = { - configFile: path.join(__dirname, '/../karma.conf.js'), - singleRun: singleRun, - autoWatch: !singleRun, - reporters: reporters, - preprocessors: preprocessors - }; - - var server = new karma.Server(localConfig, function(failCount) { - done(failCount ? new Error("Failed " + failCount + " tests.") : null); - }) - server.start(); -} - -gulp.task('test', ['scripts'], function(done) { - runTests(true, done); -}); - -gulp.task('test:auto', ['watch'], function(done) { - runTests(false, done); -}); diff --git a/webui/gulp/watch.js b/webui/gulp/watch.js deleted file mode 100644 index f748ccbbf..000000000 --- a/webui/gulp/watch.js +++ /dev/null @@ -1,39 +0,0 @@ -'use strict'; - -var path = require('path'); -var gulp = require('gulp'); -var conf = require('./conf'); - -var browserSync = require('browser-sync'); - -function isOnlyChange(event) { - return event.type === 'changed'; -} - -gulp.task('watch', ['inject'], function () { - - gulp.watch([path.join(conf.paths.src, '/*.html'), 'bower.json'], ['inject-reload']); - - gulp.watch([ - path.join(conf.paths.src, '/app/**/*.css'), - path.join(conf.paths.src, '/app/**/*.scss') - ], function(event) { - if(isOnlyChange(event)) { - gulp.start('styles-reload'); - } else { - gulp.start('inject-reload'); - } - }); - - gulp.watch(path.join(conf.paths.src, '/app/**/*.js'), function(event) { - if(isOnlyChange(event)) { - gulp.start('scripts-reload'); - } else { - gulp.start('inject-reload'); - } - }); - - gulp.watch(path.join(conf.paths.src, '/app/**/*.html'), function(event) { - browserSync.reload(event.path); - }); -}); diff --git a/webui/gulp_tasks/browsersync.js b/webui/gulp_tasks/browsersync.js new file mode 100644 index 000000000..945a88da7 --- /dev/null +++ b/webui/gulp_tasks/browsersync.js @@ -0,0 +1,21 @@ +const gulp = require('gulp'); +const browserSync = require('browser-sync'); +const spa = require('browser-sync-spa'); + +const browserSyncConf = require('../conf/browsersync.conf'); +const browserSyncDistConf = require('../conf/browsersync-dist.conf'); + +browserSync.use(spa()); + +gulp.task('browsersync', browserSyncServe); +gulp.task('browsersync:dist', browserSyncDist); + +function browserSyncServe(done) { + browserSync.init(browserSyncConf()); + done(); +} + +function browserSyncDist(done) { + browserSync.init(browserSyncDistConf()); + done(); +} diff --git a/webui/gulp_tasks/karma.js b/webui/gulp_tasks/karma.js new file mode 100644 index 000000000..c7ab0cf64 --- /dev/null +++ b/webui/gulp_tasks/karma.js @@ -0,0 +1,25 @@ +const path = require('path'); + +const gulp = require('gulp'); +const karma = require('karma'); + +gulp.task('karma:single-run', karmaSingleRun); +gulp.task('karma:auto-run', karmaAutoRun); + +function karmaFinishHandler(done) { + return failCount => { + done(failCount ? new Error(`Failed ${failCount} tests.`) : null); + }; +} + +function karmaSingleRun(done) { + const configFile = path.join(process.cwd(), 'conf', 'karma.conf.js'); + const karmaServer = new karma.Server({configFile}, karmaFinishHandler(done)); + karmaServer.start(); +} + +function karmaAutoRun(done) { + const configFile = path.join(process.cwd(), 'conf', 'karma-auto.conf.js'); + const karmaServer = new karma.Server({configFile}, karmaFinishHandler(done)); + karmaServer.start(); +} diff --git a/webui/gulp_tasks/misc.js b/webui/gulp_tasks/misc.js new file mode 100644 index 000000000..7510b0116 --- /dev/null +++ b/webui/gulp_tasks/misc.js @@ -0,0 +1,25 @@ +const path = require('path'); + +const gulp = require('gulp'); +const del = require('del'); +const filter = require('gulp-filter'); + +const conf = require('../conf/gulp.conf'); + +gulp.task('clean', clean); +gulp.task('other', other); + +function clean() { + return del([conf.paths.tmp]); +} + +function other() { + const fileFilter = filter(file => file.stat.isFile()); + + return gulp.src([ + path.join(conf.paths.src, '/**/*'), + path.join(`!${conf.paths.src}`, '/**/*.{scss,js,html}') + ]) + .pipe(fileFilter) + .pipe(gulp.dest(conf.paths.dist)); +} diff --git a/webui/gulp_tasks/webpack.js b/webui/gulp_tasks/webpack.js new file mode 100644 index 000000000..895edb750 --- /dev/null +++ b/webui/gulp_tasks/webpack.js @@ -0,0 +1,48 @@ +/* eslint angular/module-getter:0 */ +const gulp = require('gulp'); +const gutil = require('gulp-util'); + +const webpack = require('webpack'); +const webpackConf = require('../conf/webpack.conf'); +const webpackDistConf = require('../conf/webpack-dist.conf'); +const browsersync = require('browser-sync'); + +gulp.task('webpack:dev', done => { + webpackWrapper(false, webpackConf, done); +}); + +gulp.task('webpack:watch', done => { + webpackWrapper(true, webpackConf, done); +}); + +gulp.task('webpack:dist', done => { + webpackWrapper(false, webpackDistConf, done); +}); + +function webpackWrapper(watch, conf, done) { + const webpackBundler = webpack(conf); + + const webpackChangeHandler = (err, stats) => { + if (err) { + conf.errorHandler('Webpack')(err); + } + gutil.log(stats.toString({ + colors: true, + chunks: false, + hash: false, + version: false + })); + if (done) { + done(); + done = null; + } else { + browsersync.reload(); + } + }; + + if (watch) { + webpackBundler.watch(200, webpackChangeHandler); + } else { + webpackBundler.run(webpackChangeHandler); + } +} diff --git a/webui/gulpfile.js b/webui/gulpfile.js index 5669b5d96..3acaffbf3 100644 --- a/webui/gulpfile.js +++ b/webui/gulpfile.js @@ -1,29 +1,29 @@ -/** - * Welcome to your gulpfile! - * The gulp tasks are splitted in several files in the gulp directory - * because putting all here was really too long - */ +const gulp = require('gulp'); +const HubRegistry = require('gulp-hub'); +const browserSync = require('browser-sync'); -'use strict'; +const conf = require('./conf/gulp.conf'); -var gulp = require('gulp'); -var wrench = require('wrench'); +// Load some files into the registry +const hub = new HubRegistry([conf.path.tasks('*.js')]); -/** - * This will load all js or coffee files in the gulp directory - * in order to load all gulp tasks - */ -wrench.readdirSyncRecursive('./gulp').filter(function(file) { - return (/\.(js|coffee)$/i).test(file); -}).map(function(file) { - require('./gulp/' + file); -}); +// Tell gulp to use the tasks just loaded +gulp.registry(hub); +gulp.task('build', gulp.series(gulp.parallel('other', 'webpack:dist'))); +gulp.task('test', gulp.series('karma:single-run')); +gulp.task('test:auto', gulp.series('karma:auto-run')); +gulp.task('serve', gulp.series('webpack:watch', 'watch', 'browsersync')); +gulp.task('serve:dist', gulp.series('default', 'browsersync:dist')); +gulp.task('default', gulp.series('clean', 'build')); +gulp.task('watch', watch); -/** - * Default task clean temporaries directories and launch the - * main optimization build task - */ -gulp.task('default', ['clean'], function () { - gulp.start('build'); -}); +function reloadBrowserSync(cb) { + browserSync.reload(); + cb(); +} + +function watch(done) { + gulp.watch(conf.path.src('app/**/*.html'), reloadBrowserSync); + done(); +} diff --git a/webui/karma.conf.js b/webui/karma.conf.js deleted file mode 100644 index 1af45f284..000000000 --- a/webui/karma.conf.js +++ /dev/null @@ -1,110 +0,0 @@ -'use strict'; - -var path = require('path'); -var conf = require('./gulp/conf'); - -var _ = require('lodash'); -var wiredep = require('wiredep'); - -var pathSrcHtml = [ - path.join(conf.paths.src, '/**/*.html') -]; - -function listFiles() { - var wiredepOptions = _.extend({}, conf.wiredep, { - dependencies: true, - devDependencies: true - }); - - var patterns = wiredep(wiredepOptions).js - .concat([ - path.join(conf.paths.src, '/app/**/*.module.js'), - path.join(conf.paths.src, '/app/**/*.js'), - path.join(conf.paths.src, '/**/*.spec.js'), - path.join(conf.paths.src, '/**/*.mock.js'), - ]) - .concat(pathSrcHtml); - - var files = patterns.map(function(pattern) { - return { - pattern: pattern - }; - }); - files.push({ - pattern: path.join(conf.paths.src, '/assets/**/*'), - included: false, - served: true, - watched: false - }); - return files; -} - -module.exports = function(config) { - - var configuration = { - files: listFiles(), - - singleRun: true, - - autoWatch: false, - - ngHtml2JsPreprocessor: { - stripPrefix: conf.paths.src + '/', - moduleName: 'traefik' - }, - - logLevel: 'WARN', - - frameworks: ['jasmine', 'angular-filesort'], - - angularFilesort: { - whitelist: [path.join(conf.paths.src, '/**/!(*.html|*.spec|*.mock).js')] - }, - - browsers : ['PhantomJS'], - - plugins : [ - 'karma-phantomjs-launcher', - 'karma-angular-filesort', - 'karma-coverage', - 'karma-jasmine', - 'karma-ng-html2js-preprocessor' - ], - - coverageReporter: { - type : 'html', - dir : 'coverage/' - }, - - reporters: ['progress'], - - proxies: { - '/assets/': path.join('/base/', conf.paths.src, '/assets/') - } - }; - - // This is the default preprocessors configuration for a usage with Karma cli - // The coverage preprocessor is added in gulp/unit-test.js only for single tests - // It was not possible to do it there because karma doesn't let us now if we are - // running a single test or not - configuration.preprocessors = {}; - pathSrcHtml.forEach(function(path) { - configuration.preprocessors[path] = ['ng-html2js']; - }); - - // This block is needed to execute Chrome on Travis - // If you ever plan to use Chrome and Travis, you can keep it - // If not, you can safely remove it - // https://github.com/karma-runner/karma/issues/1144#issuecomment-53633076 - if(configuration.browsers[0] === 'Chrome' && process.env.TRAVIS) { - configuration.customLaunchers = { - 'chrome-travis-ci': { - base: 'Chrome', - flags: ['--no-sandbox'] - } - }; - configuration.browsers = ['chrome-travis-ci']; - } - - config.set(configuration); -}; diff --git a/webui/package.json b/webui/package.json index 868a9f0f1..92f25402e 100644 --- a/webui/package.json +++ b/webui/package.json @@ -1,55 +1,102 @@ { "name": "traefik", - "version": "0.0.0", - "dependencies": {}, - "scripts": { - "test": "gulp test" + "version": "2.0.0", + "homepage": "http://traefik.io", + "authors": [ + "Fernandez Ludovic ", + "Micaël Mbagira " + ], + "description": "Front end for Træfɪk", + "license": "MIT", + "dependencies": { + "angular": "^1.4.2", + "angular-animate": "^1.5.8", + "animate.css": "^3.4.0", + "angular-aria": "^1.5.8", + "angular-cookies": "^1.5.8", + "angular-messages": "^1.5.8", + "angular-nvd3": "^1.0.8", + "angular-resource": "^1.5.8", + "angular-sanitize": "^1.5.8", + "angular-ui-bootstrap": "^2.0.0", + "angular-ui-router": "^0.3.1", + "bootstrap": "^3.3.6", + "moment": "^2.14.1" }, "devDependencies": { - "estraverse": "~4.1.0", - "gulp": "~3.9.0", - "gulp-autoprefixer": "~3.0.2", - "gulp-angular-templatecache": "~1.8.0", - "del": "~2.0.2", - "lodash": "~3.10.1", - "gulp-minify-css": "~1.2.1", - "gulp-filter": "~3.0.1", - "gulp-flatten": "~0.2.0", - "gulp-eslint": "~1.0.0", - "eslint-plugin-angular": "~0.12.0", - "gulp-load-plugins": "~0.10.0", - "gulp-size": "~2.0.0", - "gulp-uglify": "~1.4.1", - "gulp-useref": "~1.3.0", - "gulp-util": "~3.0.6", - "gulp-ng-annotate": "~1.1.0", - "gulp-replace": "~0.5.4", - "gulp-rename": "~1.2.2", - "gulp-rev": "~6.0.1", - "gulp-rev-replace": "~0.4.2", - "gulp-minify-html": "~1.0.4", - "gulp-inject": "~3.0.0", - "gulp-protractor": "~1.0.0", - "gulp-sourcemaps": "~1.6.0", - "gulp-sass": "~2.0.4", - "gulp-angular-filesort": "~1.1.1", - "main-bower-files": "~2.9.0", - "wiredep": "~2.2.2", - "karma": "~0.13.10", - "karma-jasmine": "~0.3.6", - "karma-phantomjs-launcher": "~0.2.1", - "phantomjs": "~1.9.18", - "karma-angular-filesort": "~1.0.0", - "karma-coverage": "~0.5.2", - "karma-ng-html2js-preprocessor": "~0.2.0", - "browser-sync": "~2.9.11", - "browser-sync-spa": "~1.0.3", - "http-proxy-middleware": "~0.9.0", - "chalk": "~1.1.1", - "uglify-save-license": "~0.4.1", - "wrench": "~1.5.8" + "angular-mocks": "^1.4.2", + "autoprefixer": "^6.2.2", + "babel-loader": "^6.2.0", + "browser-sync": "^2.9.11", + "browser-sync-spa": "^1.0.3", + "css-loader": "^0.23.1", + "del": "^2.0.2", + "es6-shim": "^0.35.0", + "eslint": "^2.11.0", + "eslint-config-angular": "^0.5.0", + "eslint-config-xo-space": "^0.12.0", + "eslint-loader": "^1.3.0", + "eslint-plugin-angular": "^1.3.0", + "extract-text-webpack-plugin": "^1.0.1", + "file-loader": "^0.9.0", + "gulp": "gulpjs/gulp#4ed9a4a3275559c73a396eff7e1fde3824951ebb", + "gulp-angular-filesort": "^1.1.1", + "gulp-angular-templatecache": "^1.8.0", + "gulp-filter": "^4.0.0", + "gulp-htmlmin": "^1.3.0", + "gulp-hub": "frankwallis/gulp-hub#d461b9c700df9010d0a8694e4af1fb96d9f38bf4", + "gulp-insert": "^0.5.0", + "gulp-ng-annotate": "^1.1.0", + "gulp-sass": "^2.1.1", + "gulp-util": "^3.0.7", + "html-loader": "^0.4.3", + "html-webpack-plugin": "^2.9.0", + "isparta-loader": "^2.0.0", + "jasmine": "^2.4.1", + "json-loader": "^0.5.4", + "karma": "^0.13.14", + "karma-angular-filesort": "^1.0.0", + "karma-coverage": "^0.5.3", + "karma-jasmine": "^0.3.8", + "karma-junit-reporter": "^0.4.2", + "karma-ng-html2js-preprocessor": "^0.2.0", + "karma-phantomjs-launcher": "^1.0.0", + "karma-phantomjs-shim": "^1.1.2", + "karma-webpack": "^1.7.0", + "ng-annotate-loader": "^0.0.10", + "node-sass": "^3.4.2", + "phantomjs-prebuilt": "^2.1.6", + "postcss-loader": "^0.8.0", + "sass-loader": "^3.1.2", + "style-loader": "^0.13.0", + "url-loader": "^0.5.7", + "webpack": "2.1.0-beta.15", + "webpack-split-by-path": "^0.0.10" }, - "engines": { - "node": ">=0.10.0" + "scripts": { + "build": "gulp", + "serve": "gulp serve", + "serve:dist": "gulp serve:dist", + "test": "gulp test", + "test:auto": "gulp test:auto" + }, + "overrides": { + "angular-nvd3": { + "main": "dist/angular-nvd3.js" + } + }, + "eslintConfig": { + "globals": { + "expect": true + }, + "root": true, + "env": { + "browser": true, + "jasmine": true + }, + "extends": [ + "angular", + "xo-space" + ] } } diff --git a/webui/protractor.conf.js b/webui/protractor.conf.js deleted file mode 100644 index 862d068e4..000000000 --- a/webui/protractor.conf.js +++ /dev/null @@ -1,27 +0,0 @@ -'use strict'; - -var paths = require('./.yo-rc.json')['generator-gulp-angular'].props.paths; - -// An example configuration file. -exports.config = { - // The address of a running selenium server. - //seleniumAddress: 'http://localhost:4444/wd/hub', - //seleniumServerJar: deprecated, this should be set on node_modules/protractor/config.json - - // Capabilities to be passed to the webdriver instance. - capabilities: { - 'browserName': 'chrome' - }, - - baseUrl: 'http://localhost:3000', - - // Spec patterns are relative to the current working directory when - // protractor is called. - specs: [paths.e2e + '/**/*.js'], - - // Options to be passed to Jasmine-node. - jasmineNodeOpts: { - showColors: true, - defaultTimeoutInterval: 30000 - } -}; diff --git a/webui/readme.md b/webui/readme.md index 5ffe3c3b8..6054e58bd 100644 --- a/webui/readme.md +++ b/webui/readme.md @@ -19,13 +19,12 @@ make generate-webui # Generate static contents in `traefik/static/` folder. ## How to build (only for frontends developer) -- prerequisite: [Node](https://nodejs.org) +- prerequisite: [Node 4+ and NPM 3+](https://nodejs.org) - Go to the directory `webui` - To install dependencies, execute the following commands: - `npm install` - - `bower install` - Build static Web UI, execute the following command: - `gulp` @@ -40,6 +39,7 @@ make generate-webui # Generate static contents in `traefik/static/` folder. - add vendor prefixes to CSS (cross-bowser support) - add a hash in the file names to prevent browser cache problems - all images will be optimized at build + - bundle JavaScript in one file ## How to edit (only for frontends developer) @@ -62,7 +62,8 @@ make generate-webui # Generate static contents in `traefik/static/` folder. ## Libraries - [Node](https://nodejs.org) -- [Generator Gulp-Angular](https://github.com/Swiip/generator-gulp-angular) +- [Generator FountainJS](https://github.com/FountainJS/generator-fountain-webapp) +- [Webpack](https://github.com/webpack/webpack) - [AngularJS](https://docs.angularjs.org/api) - [UI Router](https://github.com/angular-ui/ui-router) - [UI Router - Documentation](https://github.com/angular-ui/ui-router/wiki) @@ -71,4 +72,4 @@ make generate-webui # Generate static contents in `traefik/static/` folder. - [D3](http://d3js.org) - [D3 - Documentation](https://github.com/mbostock/d3/wiki) - [NVD3](http://nvd3.org) -- [Angular nvD3](http://krispo.github.io/angular-nvd3) +- [Angular nvD3](http://krispo.github.io/angular-nvd3) \ No newline at end of file diff --git a/webui/.eslintrc b/webui/src/.eslintrc similarity index 100% rename from webui/.eslintrc rename to webui/src/.eslintrc diff --git a/webui/src/app/core/health.resource.js b/webui/src/app/core/health.resource.js index f31b6a55c..0e759ac5e 100644 --- a/webui/src/app/core/health.resource.js +++ b/webui/src/app/core/health.resource.js @@ -1,13 +1,14 @@ -(function () { - 'use strict'; +'use strict'; +var angular = require('angular'); - angular - .module('traefik.core.health', ['ngResource']) - .factory('Health', Health); +var traefikCoreHealth = 'traefik.core.health'; +module.exports = traefikCoreHealth; - /** @ngInject */ - function Health($resource) { - return $resource('../health'); - } +angular + .module(traefikCoreHealth, ['ngResource']) + .factory('Health', Health); -})(); + /** @ngInject */ + function Health($resource) { + return $resource('../health'); + } \ No newline at end of file diff --git a/webui/src/app/core/providers.resource.js b/webui/src/app/core/providers.resource.js index 41746a802..e785290ba 100644 --- a/webui/src/app/core/providers.resource.js +++ b/webui/src/app/core/providers.resource.js @@ -1,13 +1,14 @@ -(function () { - 'use strict'; +'use strict'; +var angular = require('angular'); - angular - .module('traefik.core.provider', ['ngResource']) - .factory('Providers', Providers); +var traefikCoreProvider = 'traefik.core.provider'; +module.exports = traefikCoreProvider; - /** @ngInject */ - function Providers($resource) { - return $resource('../api/providers'); - } +angular + .module(traefikCoreProvider, ['ngResource']) + .factory('Providers', Providers); -})(); + /** @ngInject */ + function Providers($resource) { + return $resource('../api/providers'); + } \ No newline at end of file diff --git a/webui/src/app/index.config.js b/webui/src/app/index.config.js deleted file mode 100644 index 5259aa207..000000000 --- a/webui/src/app/index.config.js +++ /dev/null @@ -1,15 +0,0 @@ -(function() { - 'use strict'; - - angular - .module('traefik') - .config(config); - - /** @ngInject */ - function config($logProvider) { - // Enable log - $logProvider.debugEnabled(true); - - } - -})(); diff --git a/webui/src/app/index.constants.js b/webui/src/app/index.constants.js deleted file mode 100644 index 9ed0c8e40..000000000 --- a/webui/src/app/index.constants.js +++ /dev/null @@ -1,9 +0,0 @@ -/* global moment:false */ -(function() { - 'use strict'; - - angular - .module('traefik') - .constant('moment', moment); - -})(); diff --git a/webui/src/app/index.module.js b/webui/src/app/index.module.js deleted file mode 100644 index 8c6b9c4f1..000000000 --- a/webui/src/app/index.module.js +++ /dev/null @@ -1,7 +0,0 @@ -(function() { - 'use strict'; - - angular - .module('traefik', ['ngAnimate', 'ngCookies', 'ngSanitize', 'ngMessages', 'ngAria', 'ngResource', 'ui.router', 'ui.bootstrap', 'traefik.section']); - -})(); diff --git a/webui/src/app/index.run.js b/webui/src/app/index.run.js deleted file mode 100644 index 75f8bf0bf..000000000 --- a/webui/src/app/index.run.js +++ /dev/null @@ -1,14 +0,0 @@ -(function() { - 'use strict'; - - angular - .module('traefik') - .run(runBlock); - - /** @ngInject */ - function runBlock($log) { - - $log.debug('runBlock end'); - } - -})(); diff --git a/webui/src/app/index.scss b/webui/src/app/index.scss index e7f0dc4d4..eeba970f1 100644 --- a/webui/src/app/index.scss +++ b/webui/src/app/index.scss @@ -3,7 +3,6 @@ * The list of variables are listed here bower_components/bootstrap-sass/assets/stylesheets/bootstrap/_variables.scss */ $navbar-inverse-link-color: #5AADBB; -$icon-font-path: "../../bower_components/bootstrap-sass/assets/fonts/bootstrap/"; /** * Do not remove the comments below. It's the markers used by wiredep to inject diff --git a/webui/src/app/sections/health/health.controller.js b/webui/src/app/sections/health/health.controller.js index 825e5db5a..ded809b16 100644 --- a/webui/src/app/sections/health/health.controller.js +++ b/webui/src/app/sections/health/health.controller.js @@ -1,209 +1,204 @@ -/* global d3:false */ -(function (d3) { - 'use strict'; +'use strict'; +var d3 = require('d3'); - angular - .module('traefik.section.health') - .controller('HealthController', HealthController); +/** @ngInject */ +function HealthController($scope, $interval, $log, Health) { - /** @ngInject */ - function HealthController($scope, $interval, $log, Health) { + var vm = this; - var vm = this; + vm.graph = { + averageResponseTime: {}, + totalStatusCodeCount: {} + }; - vm.graph = { - averageResponseTime: {}, - totalStatusCodeCount: {} - }; + vm.graph.totalStatusCodeCount.options = { + "chart": { + type: 'discreteBarChart', + height: 200, + margin: { + top: 20, + right: 20, + bottom: 40, + left: 55 + }, + x: function (d) { + return d.label; + }, + y: function (d) { + return d.value; + }, + showValues: true, + valueFormat: function (d) { + return d3.format('d')(d); + }, + transitionDuration: 50, + yAxis: { + axisLabelDistance: 30 + } + }, + "title": { + "enable": true, + "text": "Total Status Code Count", + "css": { + "textAlign": "center" + } + } + }; - vm.graph.totalStatusCodeCount.options = { - "chart": { - type: 'discreteBarChart', - height: 200, - margin: { - top: 20, - right: 20, - bottom: 40, - left: 55 - }, - x: function (d) { - return d.label; - }, - y: function (d) { - return d.value; - }, - showValues: true, - valueFormat: function (d) { - return d3.format('d')(d); - }, - transitionDuration: 50, - yAxis: { - axisLabelDistance: 30 - } - }, - "title": { - "enable": true, - "text": "Total Status Code Count", - "css": { - "textAlign": "center" - } - } - }; - - vm.graph.totalStatusCodeCount.data = [ + vm.graph.totalStatusCodeCount.data = [ + { + key: "Total Status Code Count", + values: [ { - key: "Total Status Code Count", - values: [ - { - "label": "200", - "value": 0 - } - ] + "label": "200", + "value": 0 } - ]; + ] + } + ]; - /** - * Update Total Status Code Count graph - * - * @param {Object} totalStatusCodeCount Object from API - */ - function updateTotalStatusCodeCount(totalStatusCodeCount) { - - // extract values - vm.graph.totalStatusCodeCount.data[0].values = []; - for (var code in totalStatusCodeCount) { - if (totalStatusCodeCount.hasOwnProperty(code)) { - vm.graph.totalStatusCodeCount.data[0].values.push({ - label: code, - value: totalStatusCodeCount[code] - }); - } - } - - // Update Total Status Code Count graph render - if (vm.graph.totalStatusCodeCount.api) { - vm.graph.totalStatusCodeCount.api.update(); - } else { - $log.error('fail'); - } + /** + * Update Total Status Code Count graph + * + * @param {Object} totalStatusCodeCount Object from API + */ + function updateTotalStatusCodeCount(totalStatusCodeCount) { + // extract values + vm.graph.totalStatusCodeCount.data[0].values = []; + for (var code in totalStatusCodeCount) { + if (totalStatusCodeCount.hasOwnProperty(code)) { + vm.graph.totalStatusCodeCount.data[0].values.push({ + label: code, + value: totalStatusCodeCount[code] + }); } - - vm.graph.averageResponseTime.options = { - chart: { - type: 'lineChart', - height: 200, - margin: { - top: 20, - right: 40, - bottom: 40, - left: 55 - }, - transitionDuration: 50, - x: function (d) { - return d.x; - }, - y: function (d) { - return d.y; - }, - useInteractiveGuideline: true, - xAxis: { - tickFormat: function (d) { - return d3.time.format('%X')(new Date(d)); - } - }, - yAxis: { - tickFormat: function (d) { - return d3.format(',.1f')(d); - } - } - }, - "title": { - "enable": true, - "text": "Average response time", - "css": { - "textAlign": "center" - } - } - }; - - var initialPoint = { - x: Date.now() - 3000, - y: 0 - }; - vm.graph.averageResponseTime.data = [ - { - values: [initialPoint], - key: 'Average response time (ms)', - type: 'line', - color: '#2ca02c' - } - ]; - - /** - * Update average response time graph - * - * @param {Number} x Coordinate X - * @param {Number} y Coordinate Y - */ - function updateAverageResponseTimeGraph(x, y) { - - // x multiply 1000 by because unix time is in seconds and JS Date are in milliseconds - var data = { - x: x * 1000, - y: y * 1000 - }; - vm.graph.averageResponseTime.data[0].values.push(data); - // limit graph entries - if (vm.graph.averageResponseTime.data[0].values.length > 100) { - vm.graph.averageResponseTime.data[0].values.shift(); - } - - // Update Average Response Time graph render - if (vm.graph.averageResponseTime.api) { - vm.graph.averageResponseTime.api.update(); - } - } - - /** - * Load all graph's datas - * - * @param {Object} health Health data from server - */ - function loadData(health) { - // Load datas and update Average Response Time graph render - updateAverageResponseTimeGraph(health.unixtime, health.average_response_time_sec); - - // Load datas and update Total Status Code Count graph render - updateTotalStatusCodeCount(health.total_status_code_count); - - // set data's view - vm.health = health; - } - - /** - * Action when load datas failed - * - * @param {Object} error Error state object - */ - function erroData(error) { - vm.health = {}; - $log.error(error); - } - - // first load - Health.get(loadData, erroData); - - // Auto refresh data - var intervalId = $interval(function () { - Health.get(loadData, erroData); - }, 3000); - - // Stop auto refresh when page change - $scope.$on('$destroy', function () { - $interval.cancel(intervalId); - }); - } -})(d3); + // Update Total Status Code Count graph render + if (vm.graph.totalStatusCodeCount.api) { + vm.graph.totalStatusCodeCount.api.update(); + } else { + $log.error('fail'); + } + + } + + vm.graph.averageResponseTime.options = { + chart: { + type: 'lineChart', + height: 200, + margin: { + top: 20, + right: 40, + bottom: 40, + left: 55 + }, + transitionDuration: 50, + x: function (d) { + return d.x; + }, + y: function (d) { + return d.y; + }, + useInteractiveGuideline: true, + xAxis: { + tickFormat: function (d) { + return d3.time.format('%X')(new Date(d)); + } + }, + yAxis: { + tickFormat: function (d) { + return d3.format(',.1f')(d); + } + } + }, + "title": { + "enable": true, + "text": "Average response time", + "css": { + "textAlign": "center" + } + } + }; + + var initialPoint = { + x: Date.now() - 3000, + y: 0 + }; + vm.graph.averageResponseTime.data = [ + { + values: [initialPoint], + key: 'Average response time (ms)', + type: 'line', + color: '#2ca02c' + } + ]; + + /** + * Update average response time graph + * + * @param {Number} x Coordinate X + * @param {Number} y Coordinate Y + */ + function updateAverageResponseTimeGraph(x, y) { + + // x multiply 1000 by because unix time is in seconds and JS Date are in milliseconds + var data = { + x: x * 1000, + y: y * 1000 + }; + vm.graph.averageResponseTime.data[0].values.push(data); + // limit graph entries + if (vm.graph.averageResponseTime.data[0].values.length > 100) { + vm.graph.averageResponseTime.data[0].values.shift(); + } + + // Update Average Response Time graph render + if (vm.graph.averageResponseTime.api) { + vm.graph.averageResponseTime.api.update(); + } + } + + /** + * Load all graph's datas + * + * @param {Object} health Health data from server + */ + function loadData(health) { + // Load datas and update Average Response Time graph render + updateAverageResponseTimeGraph(health.unixtime, health.average_response_time_sec); + + // Load datas and update Total Status Code Count graph render + updateTotalStatusCodeCount(health.total_status_code_count); + + // set data's view + vm.health = health; + } + + /** + * Action when load datas failed + * + * @param {Object} error Error state object + */ + function erroData(error) { + vm.health = {}; + $log.error(error); + } + + // first load + Health.get(loadData, erroData); + + // Auto refresh data + var intervalId = $interval(function () { + Health.get(loadData, erroData); + }, 3000); + + // Stop auto refresh when page change + $scope.$on('$destroy', function () { + $interval.cancel(intervalId); + }); + +} + +module.exports = HealthController; diff --git a/webui/src/app/sections/health/health.module.js b/webui/src/app/sections/health/health.module.js index 403e5b10f..38d1beaac 100644 --- a/webui/src/app/sections/health/health.module.js +++ b/webui/src/app/sections/health/health.module.js @@ -1,19 +1,24 @@ -(function () { - 'use strict'; +'use strict'; +var angular = require('angular'); +var traefikCoreHealth = require('../../core/health.resource'); +var HealthController = require('./health.controller'); - angular.module('traefik.section.health', ['traefik.core.health']) - .config(config); +var traefikSectionHealth = 'traefik.section.health'; +module.exports = traefikSectionHealth; - /** @ngInject */ - function config($stateProvider) { +angular + .module(traefikSectionHealth, [traefikCoreHealth]) + .controller('HealthController', HealthController) + .config(config); - $stateProvider.state('health', { - url: '/health', - templateUrl: 'app/sections/health/health.html', - controller: 'HealthController', - controllerAs: 'healthCtrl' - }); + /** @ngInject */ + function config($stateProvider) { - } + $stateProvider.state('health', { + url: '/health', + template: require('./health.html'), + controller: 'HealthController', + controllerAs: 'healthCtrl' + }); -})(); + } \ No newline at end of file diff --git a/webui/src/app/sections/providers/backend-monitor/backend-monitor.directive.js b/webui/src/app/sections/providers/backend-monitor/backend-monitor.directive.js index f993101ac..b05740726 100644 --- a/webui/src/app/sections/providers/backend-monitor/backend-monitor.directive.js +++ b/webui/src/app/sections/providers/backend-monitor/backend-monitor.directive.js @@ -1,26 +1,21 @@ -(function () { - 'use strict'; +'use strict'; - angular - .module('traefik.section.providers.backend-monitor') - .directive('backendMonitor', backendMonitor); - - function backendMonitor() { - return { - restrict: 'EA', - templateUrl: 'app/sections/providers/backend-monitor/backend-monitor.html', - controller: BackendMonitorController, - controllerAs: 'backendCtrl', - bindToController: true, - scope: { - backend: '=', - backendId: '=' - } - }; +function backendMonitor() { + return { + restrict: 'EA', + template: require('./backend-monitor.html'), + controller: BackendMonitorController, + controllerAs: 'backendCtrl', + bindToController: true, + scope: { + backend: '=', + backendId: '=' } + }; +} - function BackendMonitorController() { - // Nothing - } +function BackendMonitorController() { + // Nothing +} -})(); +module.exports = backendMonitor; \ No newline at end of file diff --git a/webui/src/app/sections/providers/backend-monitor/backend-monitor.module.js b/webui/src/app/sections/providers/backend-monitor/backend-monitor.module.js index ccee5d681..0fc55270a 100644 --- a/webui/src/app/sections/providers/backend-monitor/backend-monitor.module.js +++ b/webui/src/app/sections/providers/backend-monitor/backend-monitor.module.js @@ -1,7 +1,10 @@ -(function () { - 'use strict'; +'use strict'; +var angular = require('angular'); +var backendMonitor = require('./backend-monitor.directive'); - angular - .module('traefik.section.providers.backend-monitor', []); +var traefikBackendMonitor = 'traefik.section.providers.backend-monitor'; +module.exports = traefikBackendMonitor; -})(); +angular + .module(traefikBackendMonitor, []) + .directive('backendMonitor', backendMonitor); diff --git a/webui/src/app/sections/providers/frontend-monitor/frontend-monitor.directive.js b/webui/src/app/sections/providers/frontend-monitor/frontend-monitor.directive.js index b2c9ba767..7b6107202 100644 --- a/webui/src/app/sections/providers/frontend-monitor/frontend-monitor.directive.js +++ b/webui/src/app/sections/providers/frontend-monitor/frontend-monitor.directive.js @@ -1,26 +1,21 @@ -(function () { - 'use strict'; +'use strict'; - angular - .module('traefik.section.providers.frontend-monitor') - .directive('frontendMonitor', frontendMonitor); - - function frontendMonitor() { - return { - restrict: 'EA', - templateUrl: 'app/sections/providers/frontend-monitor/frontend-monitor.html', - controller: FrontendMonitorController, - controllerAs: 'frontendCtrl', - bindToController: true, - scope: { - frontend: '=', - frontendId: '=' - } - }; +function frontendMonitor() { + return { + restrict: 'EA', + template: require('./frontend-monitor.html'), + controller: FrontendMonitorController, + controllerAs: 'frontendCtrl', + bindToController: true, + scope: { + frontend: '=', + frontendId: '=' } + }; +} - function FrontendMonitorController() { - // Nothing - } +function FrontendMonitorController() { + // Nothing +} -})(); +module.exports = frontendMonitor; diff --git a/webui/src/app/sections/providers/frontend-monitor/frontend-monitor.module.js b/webui/src/app/sections/providers/frontend-monitor/frontend-monitor.module.js index 6257a7768..b4b06a372 100644 --- a/webui/src/app/sections/providers/frontend-monitor/frontend-monitor.module.js +++ b/webui/src/app/sections/providers/frontend-monitor/frontend-monitor.module.js @@ -1,6 +1,10 @@ -(function () { - 'use strict'; +'use strict'; +var angular = require('angular'); +var frontendMonitor = require('./frontend-monitor.directive'); - angular.module('traefik.section.providers.frontend-monitor', []); +var traefikFrontendMonitor = 'traefik.section.providers.frontend-monitor'; +module.exports = traefikFrontendMonitor; -})(); +angular + .module(traefikFrontendMonitor, []) + .directive('frontendMonitor', frontendMonitor); diff --git a/webui/src/app/sections/providers/providers.controller.js b/webui/src/app/sections/providers/providers.controller.js index 2f9bb4e74..7898d8a86 100644 --- a/webui/src/app/sections/providers/providers.controller.js +++ b/webui/src/app/sections/providers/providers.controller.js @@ -1,28 +1,23 @@ -(function () { - 'use strict'; +'use strict'; - angular - .module('traefik.section.providers') - .controller('ProvidersController', ProvidersController); +/** @ngInject */ +function ProvidersController($scope, $interval, $log, Providers) { + var vm = this; - /** @ngInject */ - function ProvidersController($scope, $interval, $log, Providers) { - var vm = this; + vm.providers = Providers.get(); - vm.providers = Providers.get(); + var intervalId = $interval(function () { + Providers.get(function (providers) { + vm.providers = providers; + }, function (error) { + vm.providers = {}; + $log.error(error); + }); + }, 2000); - var intervalId = $interval(function () { - Providers.get(function (providers) { - vm.providers = providers; - }, function (error) { - vm.providers = {}; - $log.error(error); - }); - }, 2000); + $scope.$on('$destroy', function () { + $interval.cancel(intervalId); + }); +} - $scope.$on('$destroy', function () { - $interval.cancel(intervalId); - }); - } - -})(); +module.exports = ProvidersController; \ No newline at end of file diff --git a/webui/src/app/sections/providers/providers.module.js b/webui/src/app/sections/providers/providers.module.js index 6467b246d..fadbec16b 100644 --- a/webui/src/app/sections/providers/providers.module.js +++ b/webui/src/app/sections/providers/providers.module.js @@ -1,24 +1,30 @@ -(function () { - 'use strict'; +'use strict'; +var angular = require('angular'); +var traefikCoreProvider = require('../../core/providers.resource'); +var ProvidersController = require('./providers.controller'); +var traefikBackendMonitor = require('./backend-monitor/backend-monitor.module'); +var traefikFrontendMonitor = require('./frontend-monitor/frontend-monitor.module'); - angular - .module('traefik.section.providers', [ - 'traefik.core.provider', - 'traefik.section.providers.backend-monitor', - 'traefik.section.providers.frontend-monitor' - ]) - .config(config); +var traefikSectionProviders = 'traefik.section.providers'; +module.exports = traefikSectionProviders; - /** @ngInject */ - function config($stateProvider) { +angular + .module(traefikSectionProviders, [ + traefikCoreProvider, + traefikBackendMonitor, + traefikFrontendMonitor + ]) + .config(config) + .controller('ProvidersController', ProvidersController); - $stateProvider.state('provider', { - url: '/', - templateUrl: 'app/sections/providers/providers.html', - controller: 'ProvidersController', - controllerAs: 'providersCtrl' - }); + /** @ngInject */ + function config($stateProvider) { - } + $stateProvider.state('provider', { + url: '/', + template: require('./providers.html'), + controller: 'ProvidersController', + controllerAs: 'providersCtrl' + }); -})(); + } \ No newline at end of file diff --git a/webui/src/app/sections/sections.config.js b/webui/src/app/sections/sections.config.js deleted file mode 100644 index 2700590f8..000000000 --- a/webui/src/app/sections/sections.config.js +++ /dev/null @@ -1,13 +0,0 @@ -(function () { - 'use strict'; - - angular - .module('traefik.section') - .config(config); - - /** @ngInject */ - function config($urlRouterProvider) { - $urlRouterProvider.otherwise('/'); - } - -})(); diff --git a/webui/src/app/sections/sections.js b/webui/src/app/sections/sections.js new file mode 100644 index 000000000..1dd926ff0 --- /dev/null +++ b/webui/src/app/sections/sections.js @@ -0,0 +1,24 @@ +'use strict'; +var angular = require('angular'); +require('nvd3'); +var ndv3 = require('angular-nvd3'); +var traefikSectionHealth = require('./health/health.module'); +var traefikSectionProviders = require('./providers/providers.module'); + +var traefikSection = 'traefik.section'; +module.exports = traefikSection; + +angular + .module(traefikSection, [ + 'ui.router', + 'ui.bootstrap', + ndv3, + traefikSectionProviders, + traefikSectionHealth + ]) + .config(config); + + /** @ngInject */ + function config($urlRouterProvider) { + $urlRouterProvider.otherwise('/'); + } \ No newline at end of file diff --git a/webui/src/app/sections/sections.module.js b/webui/src/app/sections/sections.module.js deleted file mode 100644 index 3fc85daaa..000000000 --- a/webui/src/app/sections/sections.module.js +++ /dev/null @@ -1,13 +0,0 @@ -(function () { - 'use strict'; - - angular - .module('traefik.section', [ - 'ui.router', - 'ui.bootstrap', - 'nvd3', - 'traefik.section.providers', - 'traefik.section.health' - ]); - -})(); diff --git a/webui/src/app/traefik.scss b/webui/src/app/traefik.scss index ead479076..9aa01ff24 100644 --- a/webui/src/app/traefik.scss +++ b/webui/src/app/traefik.scss @@ -1,9 +1,9 @@ @font-face { font-family: 'charterregular'; - src: url('../assets/fonts/charter_regular-webfont.eot'); - src: url('../assets/fonts/charter_regular-webfont.eot?#iefix') format('embedded-opentype'), - url('../assets/fonts/charter_regular-webfont.woff') format('woff'); + src: url('./assets/fonts/charter_regular-webfont.eot'); + src: url('./assets/fonts/charter_regular-webfont.eot?#iefix') format('embedded-opentype'), + url('./assets/fonts/charter_regular-webfont.woff') format('woff'); font-weight: normal; font-style: normal; } diff --git a/webui/src/index.html b/webui/src/index.html index 0edd91a06..468431563 100644 --- a/webui/src/index.html +++ b/webui/src/index.html @@ -2,29 +2,17 @@ - Træfɪk + Træfɪk - - - - - - - - - - - - - + + -
- - - - - - - - - - - - - - - - - diff --git a/webui/src/index.js b/webui/src/index.js new file mode 100644 index 000000000..388fbe865 --- /dev/null +++ b/webui/src/index.js @@ -0,0 +1,46 @@ +'use strict'; +var angular = require('angular'); +var ngAnimate = require('angular-animate'); +var ngCookies = require('angular-cookies'); +var ngSanitize = require('angular-sanitize'); +var ngMessages = require('angular-messages'); +var ngAria = require('angular-aria'); +var ngResource = require('angular-resource'); +var uiRouter = require('angular-ui-router'); +var uiBootstrap = require('angular-ui-bootstrap'); +var moment = require('moment'); +var traefikSection = require('./app/sections/sections'); +require('./index.scss'); +require('animate.css/animate.css'); +require('nvd3/build/nv.d3.css'); +require('bootstrap/dist/css/bootstrap.css'); + +var app = 'traefik'; +module.exports = app; + +angular + .module(app, [ + ngAnimate, + ngCookies, + ngSanitize, + ngMessages, + ngAria, + ngResource, + uiRouter, + uiBootstrap, + traefikSection + ]) + .run(runBlock) + .constant('moment', moment) + .config(config); + +/** @ngInject */ +function config($logProvider) { + // Enable log + $logProvider.debugEnabled(true); +} + +/** @ngInject */ +function runBlock($log) { + $log.debug('runBlock end'); +} diff --git a/webui/src/index.scss b/webui/src/index.scss new file mode 100644 index 000000000..ace77b97d --- /dev/null +++ b/webui/src/index.scss @@ -0,0 +1,3 @@ +$icon-font-path: "../bower_components/bootstrap-sass/assets/fonts/bootstrap/"; +@import 'app/index.scss'; +@import 'app/traefik.scss'; \ No newline at end of file