From 34d81ef9b27b6be99e89ceba75a5aac62c18c405 Mon Sep 17 00:00:00 2001
From: Kasra Bigdeli
Date: Tue, 27 Nov 2018 20:01:32 -0800
Subject: [PATCH 1/2] rebuilt front end
---
app-backend/app.js | 4 +-
app-backend/dist/js/dashboard.min.js | 238 +++++++++---------
app-backend/dist/oneclick-apps/vsts-agent.js | 201 +++++++++++++++
app-backend/dist/oneclick-apps/wordpress.js | 6 +-
app-backend/dist/templates/app-details.html | 10 +-
app-backend/dist/templates/apps.html | 2 +-
app-backend/dist/templates/login.html | 2 +-
.../dist/templates/modals/delete-app.html | 2 +-
.../src/datastore/DataStoreProvider.js | 12 +-
app-backend/src/user/Authenticator.js | 6 +-
app-frontend/package-lock.json | 6 +-
11 files changed, 349 insertions(+), 140 deletions(-)
create mode 100644 app-backend/dist/oneclick-apps/vsts-agent.js
diff --git a/app-backend/app.js b/app-backend/app.js
index b6f68d4..7287407 100644
--- a/app-backend/app.js
+++ b/app-backend/app.js
@@ -174,14 +174,12 @@ app.use(function (req, res, next) {
// error handler
app.use(function (err, req, res, next) {
// set locals, only providing error in development
- res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
Logger.e(err);
// render the error page
- res.status(err.status || 500);
- res.render('error');
+ res.sendStatus(err.status || 500);
});
// Initializing with delay helps with debugging. Many times, docker didn't see the CAPTAIN service
diff --git a/app-backend/dist/js/dashboard.min.js b/app-backend/dist/js/dashboard.min.js
index 1479875..1ccf786 100644
--- a/app-backend/dist/js/dashboard.min.js
+++ b/app-backend/dist/js/dashboard.min.js
@@ -725,6 +725,124 @@ angular.module('RDash')
}
});
+/**
+ * File Upload Read Directive
+ */
+
+angular
+ .module('RDash')
+ .directive("fileread", [function () {
+ return {
+ scope: {
+ fileread: "="
+ },
+ link: function (scope, element, attributes) {
+ element.bind("change", function (changeEvent) {
+ scope.$apply(function () {
+ scope.fileread = changeEvent.target.files[0];
+ // or all selected files:
+ // scope.fileread = changeEvent.target.files;
+ });
+ });
+ }
+ }
+ }]);
+/**
+ * Loading Directive
+ * @see http://tobiasahlin.com/spinkit/
+ */
+
+angular
+ .module('RDash')
+ .directive('rdLoading', rdLoading);
+
+function rdLoading() {
+ var directive = {
+ restrict: 'AE',
+ template: ''
+ };
+ return directive;
+};
+/**
+ * Widget Body Directive
+ */
+
+angular
+ .module('RDash')
+ .directive('rdWidgetBody', rdWidgetBody);
+
+function rdWidgetBody() {
+ var directive = {
+ requires: '^rdWidget',
+ scope: {
+ loading: '=?',
+ classes: '@?'
+ },
+ transclude: true,
+ template: '',
+ restrict: 'E'
+ };
+ return directive;
+};
+
+/**
+ * Widget Footer Directive
+ */
+
+angular
+ .module('RDash')
+ .directive('rdWidgetFooter', rdWidgetFooter);
+
+function rdWidgetFooter() {
+ var directive = {
+ requires: '^rdWidget',
+ transclude: true,
+ template: '',
+ restrict: 'E'
+ };
+ return directive;
+};
+/**
+ * Widget Header Directive
+ */
+
+angular
+ .module('RDash')
+ .directive('rdWidgetHeader', rdWidgetTitle);
+
+function rdWidgetTitle() {
+ var directive = {
+ requires: '^rdWidget',
+ scope: {
+ title: '@',
+ icon: '@'
+ },
+ transclude: true,
+ template: '',
+ restrict: 'E'
+ };
+ return directive;
+};
+/**
+ * Widget Directive
+ */
+
+angular
+ .module('RDash')
+ .directive('rdWidget', rdWidget);
+
+function rdWidget() {
+ var directive = {
+ transclude: true,
+ template: '',
+ restrict: 'EA'
+ };
+ return directive;
+
+ function link(scope, element, attrs) {
+ /* */
+ }
+};
/**
* Alerts Controller
*/
@@ -1886,122 +2004,4 @@ function SettingsCtrl($scope, $cookieStore, $rootScope, pageDefinitions,
}());
-}
-/**
- * File Upload Read Directive
- */
-
-angular
- .module('RDash')
- .directive("fileread", [function () {
- return {
- scope: {
- fileread: "="
- },
- link: function (scope, element, attributes) {
- element.bind("change", function (changeEvent) {
- scope.$apply(function () {
- scope.fileread = changeEvent.target.files[0];
- // or all selected files:
- // scope.fileread = changeEvent.target.files;
- });
- });
- }
- }
- }]);
-/**
- * Loading Directive
- * @see http://tobiasahlin.com/spinkit/
- */
-
-angular
- .module('RDash')
- .directive('rdLoading', rdLoading);
-
-function rdLoading() {
- var directive = {
- restrict: 'AE',
- template: ''
- };
- return directive;
-};
-/**
- * Widget Body Directive
- */
-
-angular
- .module('RDash')
- .directive('rdWidgetBody', rdWidgetBody);
-
-function rdWidgetBody() {
- var directive = {
- requires: '^rdWidget',
- scope: {
- loading: '=?',
- classes: '@?'
- },
- transclude: true,
- template: '',
- restrict: 'E'
- };
- return directive;
-};
-
-/**
- * Widget Footer Directive
- */
-
-angular
- .module('RDash')
- .directive('rdWidgetFooter', rdWidgetFooter);
-
-function rdWidgetFooter() {
- var directive = {
- requires: '^rdWidget',
- transclude: true,
- template: '',
- restrict: 'E'
- };
- return directive;
-};
-/**
- * Widget Header Directive
- */
-
-angular
- .module('RDash')
- .directive('rdWidgetHeader', rdWidgetTitle);
-
-function rdWidgetTitle() {
- var directive = {
- requires: '^rdWidget',
- scope: {
- title: '@',
- icon: '@'
- },
- transclude: true,
- template: '',
- restrict: 'E'
- };
- return directive;
-};
-/**
- * Widget Directive
- */
-
-angular
- .module('RDash')
- .directive('rdWidget', rdWidget);
-
-function rdWidget() {
- var directive = {
- transclude: true,
- template: '',
- restrict: 'EA'
- };
- return directive;
-
- function link(scope, element, attrs) {
- /* */
- }
-};
\ No newline at end of file
+}
\ No newline at end of file
diff --git a/app-backend/dist/oneclick-apps/vsts-agent.js b/app-backend/dist/oneclick-apps/vsts-agent.js
new file mode 100644
index 0000000..849df9c
--- /dev/null
+++ b/app-backend/dist/oneclick-apps/vsts-agent.js
@@ -0,0 +1,201 @@
+
+(function () {
+
+ var SUCCESS = 'success';
+ var ERROR = 'danger';
+ var INFO = 'info';
+
+ oneClickAppsRepository["vsts-agent"] = function (apiManager) {
+
+ var getErrorMessageIfExists = apiManager.getErrorMessageIfExists;
+
+ var VSTS_ACCOUNT = 'VSTS_ACCOUNT';
+ var VSTS_TOKEN = 'VSTS_TOKEN';
+ var VSTS_AGENT = 'VSTS_AGENT';
+ var VSTS_POOL = 'VSTS_POOL';
+ var DOCKER_TAG = 'DOCKER_TAG';
+ var VSTS_AGENT_CONTAINER_NAME = 'VSTS_AGENT_CONTAINER_NAME';
+
+ var step1next = {};
+
+ step1next.data = [];
+ step1next.data.push({
+ label: 'VSTS Agent Container Name',
+ id: VSTS_AGENT_CONTAINER_NAME,
+ type: 'text'
+ });
+
+ step1next.data.push({
+ label: 'OPTIONAL: Docker Tag (default "latest")',
+ labelDesc: 'https://hub.docker.com/r/microsoft/vsts-agent/tags/',
+ id: DOCKER_TAG,
+ type: 'text'
+ });
+
+ step1next.data.push({
+ label: 'VSTS Account',
+ labelDesc: 'The name of the Visual Studio account. Take only the account part from your address, e.g. http://{account}.visualstudio.com',
+ id: VSTS_ACCOUNT,
+ type: 'text'
+ });
+ step1next.data.push({
+ label: 'VSTS Token',
+ labelDesc: 'A personal access token (PAT) for the Visual Studio account that has been given at least the Agent Pools (read, manage) scope.',
+ id: VSTS_TOKEN,
+ type: 'text'
+ });
+
+ step1next.data.push({
+ label: 'VSTS Agent',
+ labelDesc: 'The name of the agent.',
+ id: VSTS_AGENT,
+ type: 'text'
+ });
+
+ step1next.data.push({
+ label: 'VSTS Pool',
+ labelDesc: 'The name of the agent pool.',
+ id: VSTS_POOL,
+ type: 'text'
+ });
+
+ step1next.process = function (data, step1Callback) {
+
+ // create container and set persistent
+ // set env vars and volumes
+ // deploy image via dockerfile
+
+ function endWithSuccess() {
+ step1Callback({
+ message: {
+ text: 'VSTS Agent is deployed and published as ' + data[VSTS_AGENT] +'.',
+ type: SUCCESS
+ },
+ next: null // this can be similar to step1next, in that case the flow continues...
+ });
+ }
+
+ function endWithError(errorMessage) {
+ step1Callback({
+ message: {
+ text: errorMessage,
+ type: ERROR
+ },
+ next: step1next
+ });
+ }
+
+ // process the inputs:
+
+ var errorMessage = null;
+
+ if (!data[VSTS_AGENT_CONTAINER_NAME]) {
+ errorMessage = 'Container name is required!';
+ } else if (!data[VSTS_ACCOUNT]) {
+ errorMessage = 'Account is required!';
+ } else if (!data[VSTS_TOKEN]) {
+ errorMessage = 'Acess token is required!';
+ } else if (!data[VSTS_AGENT]) {
+ errorMessage = 'Agent name is required!';
+ } else if (!data[VSTS_POOL]) {
+ errorMessage = 'Pool name is required!';
+ }
+
+ if (errorMessage) {
+ endWithError(errorMessage);
+ return;
+ }
+
+ var appName = data[VSTS_AGENT_CONTAINER_NAME];
+ var dockerTag = data[DOCKER_TAG] || 'latest';
+ var envVars = [{
+ key: VSTS_ACCOUNT,
+ value: data[VSTS_ACCOUNT]
+ }, {
+ key: VSTS_TOKEN,
+ value: data[VSTS_TOKEN]
+ },
+ {
+ key: VSTS_AGENT,
+ value: data[VSTS_AGENT]
+ },
+ {
+ key: VSTS_POOL,
+ value: data[VSTS_POOL]
+ }];
+ var volumes = [{
+ volumeName: appName + '-vsts-agent-vol',
+ containerPath: '/data/db'
+ }, {
+ volumeName: appName + '-vsts-agent-vol',
+ containerPath: '/data/configdb'
+ }];
+
+ function createContainer() {
+
+ var hasPersistentData = true;
+
+ apiManager.registerNewApp(appName, hasPersistentData, function (data) {
+ if (getErrorMessageIfExists(data)) {
+ endWithError(getErrorMessageIfExists(data));
+ return;
+ }
+
+ setupAppDefinition();
+ });
+ }
+
+ function setupAppDefinition() {
+
+ var appDefinition = {
+ instanceCount: 1,
+ envVars: envVars,
+ notExposeAsWebApp: true,
+ volumes: volumes
+ };
+
+ apiManager.updateConfigAndSave(appName, appDefinition, function (data) {
+ if (getErrorMessageIfExists(data)) {
+ endWithError(getErrorMessageIfExists(data));
+ return;
+ }
+
+ deployDockerfile();
+ });
+ }
+
+ function deployDockerfile() {
+
+ var captainDefinitionContent = {
+ schemaVersion: 1,
+ dockerfileLines: [
+ "FROM microsoft/vsts-agent:" + dockerTag
+ ]
+ }
+
+ apiManager.uploadCaptainDefinitionContent(appName,
+ JSON.stringify(captainDefinitionContent), function (data) {
+ if (getErrorMessageIfExists(data)) {
+ endWithError(getErrorMessageIfExists(data));
+ return;
+ }
+
+ endWithSuccess();
+ });
+ }
+
+ createContainer();
+
+ }
+
+ var step1 = {};
+ step1.message = {
+ type: INFO,
+ text: 'Official image for the Visual Studio Team Services (VSTS) agent.'
+ }
+ step1.next = step1next;
+ return step1;
+
+ }
+
+})();
diff --git a/app-backend/dist/oneclick-apps/wordpress.js b/app-backend/dist/oneclick-apps/wordpress.js
index 1bf5be6..be0d33d 100644
--- a/app-backend/dist/oneclick-apps/wordpress.js
+++ b/app-backend/dist/oneclick-apps/wordpress.js
@@ -34,7 +34,7 @@
type: 'text'
});
step1next.data.push({
- label: 'OPTIONAL: Docker Tag for MySQL (default "5.5")',
+ label: 'OPTIONAL: Docker Tag for MySQL (default "5.7")',
labelDesc: 'https://hub.docker.com/r/library/mysql/tags/',
id: DOCKER_TAG_MYSQL,
type: 'text'
@@ -83,7 +83,7 @@
}
var dockerTagWordPress = data[DOCKER_TAG_WORDPRESS] || '4.9';
- var dockerTagMySql = data[DOCKER_TAG_MYSQL] || '5.5';
+ var dockerTagMySql = data[DOCKER_TAG_MYSQL] || '5.7';
var mySqlAppName = data[WORDPRESS_NAME] + '-mysql';
var envVarsMySql = [{
key: MYSQL_ROOT_PASSWORD,
@@ -231,4 +231,4 @@
}
-})();
\ No newline at end of file
+})();
diff --git a/app-backend/dist/templates/app-details.html b/app-backend/dist/templates/app-details.html
index 92e0414..00561df 100644
--- a/app-backend/dist/templates/app-details.html
+++ b/app-backend/dist/templates/app-details.html
@@ -182,13 +182,13 @@
Make sure that you have a 'captain-definition' file in your project. See
- docs for more details.
+ docs for more details.
Method 1 (RECOMMENDED)
Use CLI deploy command. This is the best method as it's the only method that reports potential build
failures to you.
- Read here
+ Read here