diff --git a/static/js/quay.config.ts b/static/js/quay-config.module.ts similarity index 96% rename from static/js/quay.config.ts rename to static/js/quay-config.module.ts index 164c98692..21bfbed09 100644 --- a/static/js/quay.config.ts +++ b/static/js/quay-config.module.ts @@ -108,6 +108,7 @@ export class QuayConfig { } +// TODO: Make injected values into services and move to NgModule.providers, as constants are not supported in Angular 2 angular .module(QuayConfig.name) .constant('NAME_PATTERNS', NAME_PATTERNS) diff --git a/static/js/quay-run.module.ts b/static/js/quay-run.module.ts new file mode 100644 index 000000000..710235c7b --- /dev/null +++ b/static/js/quay-run.module.ts @@ -0,0 +1,179 @@ +import { NgModule } from 'angular-ts-decorators'; +import { INJECTED_CONFIG, INJECTED_FEATURES, INJECTED_ENDPOINTS } from "./constants/injected-values.constant"; +import { NAME_PATTERNS } from "./constants/name-patterns.constant"; +import * as angular from 'angular'; + + +var quayDependencies: any[] = [ + 'chieffancypants.loadingBar', + 'cfp.hotkeys', + 'angular-tour', + 'restangular', + 'angularMoment', + 'mgcrea.ngStrap', + 'ngCookies', + 'ngSanitize', + 'angular-md5', + 'pasvaz.bindonce', + 'ansiToHtml', + 'core-ui', + 'core-config-setup', + 'infinite-scroll', + 'react' +]; + +if (INJECTED_CONFIG && (INJECTED_CONFIG.MIXPANEL_KEY || + INJECTED_CONFIG.MUNCHKIN_KEY || + INJECTED_CONFIG.GOOGLE_ANALYTICS_KEY)) { + quayDependencies.push('angulartics'); +} +if (INJECTED_CONFIG && INJECTED_CONFIG.MIXPANEL_KEY) { + quayDependencies.push('angulartics.mixpanel'); +} +if (INJECTED_CONFIG && INJECTED_CONFIG.MUNCHKIN_KEY) { + quayDependencies.push('angulartics.marketo'); +} +if (INJECTED_CONFIG && INJECTED_CONFIG.GOOGLE_ANALYTICS_KEY) { + quayDependencies.push('angulartics.google.analytics'); +} +if (INJECTED_CONFIG && INJECTED_CONFIG.RECAPTCHA_SITE_KEY) { + quayDependencies.push('vcRecaptcha'); +} + + +/** + * Module for application-wide configuration. + */ +@NgModule({ + imports: quayDependencies, + declarations: [], + providers: [] +}) +export class QuayRun { + + public run($rootScope: QuayRunScope, + Restangular: any, + PlanService: any, + $http: ng.IHttpService, + CookieService: any, + Features: any, + $anchorScroll: ng.IAnchorScrollService, + MetaService: any, + INJECTED_CONFIG: any): void { + var defaultTitle = INJECTED_CONFIG['REGISTRY_TITLE'] || 'Quay Container Registry'; + + // Handle session security. + Restangular.setDefaultRequestParams(['post', 'put', 'remove', 'delete'], + {'_csrf_token': (window).__token || ''}); + + // Handle session expiration. + Restangular.setErrorInterceptor(function(response) { + if (response !== undefined && response.status == 503) { + ($('#cannotContactService')).modal({}); + return false; + } + + if (response !== undefined && response.status == 500) { + window.location.href = '/500'; + return false; + } + + if (response !== undefined && !response.data) { + return true; + } + + var invalid_token = response.data['title'] == 'invalid_token' || response.data['error_type'] == 'invalid_token'; + if (response !== undefined && response.status == 401 && + invalid_token && + response.data['session_required'] !== false) { + ($('#sessionexpiredModal')).modal({}); + return false; + } + + return true; + }); + + // Check if we need to redirect based on a previously chosen plan. + var result = PlanService.handleNotedPlan(); + + // Check to see if we need to show a redirection page. + var redirectUrl = CookieService.get('quay.redirectAfterLoad'); + CookieService.clear('quay.redirectAfterLoad'); + + if (!result && redirectUrl && redirectUrl.indexOf((window).location.href) == 0) { + (window).location = redirectUrl; + return; + } + + $rootScope.$watch('description', function(description: string) { + if (!description) { + description = `Hosted private docker repositories. Includes full user management and history. + Free for public repositories.`; + } + + // Note: We set the content of the description tag manually here rather than using Angular binding + // because we need the tag to have a default description that is not of the form "{{ description }}", + // we read by tools that do not properly invoke the Angular code. + $('#descriptionTag').attr('content', description); + }); + + // Listen for scope changes and update the title and description accordingly. + $rootScope.$watch(function() { + var title = MetaService.getTitle($rootScope.currentPage) || defaultTitle; + $rootScope.title = title; + + var description = MetaService.getDescription($rootScope.currentPage) || ''; + if ($rootScope.description != description) { + $rootScope.description = description; + } + }); + + $rootScope.$on('$routeChangeSuccess', function (event, current, previous) { + $rootScope.current = current.$$route; + $rootScope.currentPage = current; + $rootScope.pageClass = ''; + + if (!current.$$route) { return; } + + var pageClass = current.$$route.pageClass || ''; + if (typeof pageClass != 'string') { + pageClass = pageClass(Features); + } + + $rootScope.pageClass = pageClass; + $rootScope.newLayout = !!current.$$route.newLayout; + $rootScope.fixFooter = !!current.$$route.fixFooter; + + $anchorScroll(); + }); + + var initallyChecked: boolean = false; + (window).__isLoading = function() { + if (!initallyChecked) { + initallyChecked = true; + return true; + } + return $http.pendingRequests.length > 0; + }; + } +} + + +interface QuayRunScope extends ng.IRootScopeService { + currentPage: any; + current: any; + title: any; + description: string, + pageClass: any; + newLayout: any; + fixFooter: any; +} + + +// TODO: Make injected values into services and move to NgModule.providers, as constants are not supported in Angular 2 +angular + .module(QuayRun.name) + .constant('NAME_PATTERNS', NAME_PATTERNS) + .constant('INJECTED_CONFIG', INJECTED_CONFIG) + .constant('INJECTED_FEATURES', INJECTED_FEATURES) + .constant('INJECTED_ENDPOINTS', INJECTED_ENDPOINTS); \ No newline at end of file diff --git a/static/js/quay.module.ts b/static/js/quay.module.ts index e4c6099bf..60dbe5933 100644 --- a/static/js/quay.module.ts +++ b/static/js/quay.module.ts @@ -9,7 +9,8 @@ import { DockerfilePathSelectComponent } from './directives/ui/dockerfile-path-s import { ManageTriggerCustomGitComponent } from './directives/ui/manage-trigger-custom-git/manage-trigger-custom-git.component'; import { ManageTriggerGithostComponent } from './directives/ui/manage-trigger-githost/manage-trigger-githost.component'; import { LinearWorkflowComponent } from './directives/ui/linear-workflow/linear-workflow.component'; -import { QuayConfig } from './quay.config'; +import { QuayConfig } from './quay-config.module'; +import { QuayRun } from './quay-run.module'; /** @@ -19,6 +20,7 @@ import { QuayConfig } from './quay.config'; imports: [ QuayRoutes, QuayConfig, + QuayRun, ], declarations: [ RegexMatchViewComponent, @@ -33,129 +35,8 @@ import { QuayConfig } from './quay.config'; }) export class quay { - constructor() { - - } - - public run($rootScope: QuayRunScope, - Restangular: any, - PlanService: any, - $http: ng.IHttpService, - CookieService: any, - Features: any, - $anchorScroll: ng.IAnchorScrollService, - MetaService: any, - INJECTED_CONFIG: any): void { - var defaultTitle = INJECTED_CONFIG['REGISTRY_TITLE'] || 'Quay Container Registry'; - - // Handle session security. - Restangular.setDefaultRequestParams(['post', 'put', 'remove', 'delete'], - {'_csrf_token': (window).__token || ''}); - - // Handle session expiration. - Restangular.setErrorInterceptor(function(response) { - if (response !== undefined && response.status == 503) { - ($('#cannotContactService')).modal({}); - return false; - } - - if (response !== undefined && response.status == 500) { - window.location.href = '/500'; - return false; - } - - if (response !== undefined && !response.data) { - return true; - } - - var invalid_token = response.data['title'] == 'invalid_token' || response.data['error_type'] == 'invalid_token'; - if (response !== undefined && response.status == 401 && - invalid_token && - response.data['session_required'] !== false) { - ($('#sessionexpiredModal')).modal({}); - return false; - } - - return true; - }); - - // Check if we need to redirect based on a previously chosen plan. - var result = PlanService.handleNotedPlan(); - - // Check to see if we need to show a redirection page. - var redirectUrl = CookieService.get('quay.redirectAfterLoad'); - CookieService.clear('quay.redirectAfterLoad'); - - if (!result && redirectUrl && redirectUrl.indexOf((window).location.href) == 0) { - (window).location = redirectUrl; - return; - } - - $rootScope.$watch('description', function(description: string) { - if (!description) { - description = `Hosted private docker repositories. Includes full user management and history. - Free for public repositories.`; - } - - // Note: We set the content of the description tag manually here rather than using Angular binding - // because we need the tag to have a default description that is not of the form "{{ description }}", - // we read by tools that do not properly invoke the Angular code. - $('#descriptionTag').attr('content', description); - }); - - // Listen for scope changes and update the title and description accordingly. - $rootScope.$watch(function() { - var title = MetaService.getTitle($rootScope.currentPage) || defaultTitle; - $rootScope.title = title; - - var description = MetaService.getDescription($rootScope.currentPage) || ''; - if ($rootScope.description != description) { - $rootScope.description = description; - } - }); - - $rootScope.$on('$routeChangeSuccess', function (event, current, previous) { - $rootScope.current = current.$$route; - $rootScope.currentPage = current; - $rootScope.pageClass = ''; - - if (!current.$$route) { return; } - - var pageClass = current.$$route.pageClass || ''; - if (typeof pageClass != 'string') { - pageClass = pageClass(Features); - } - - $rootScope.pageClass = pageClass; - $rootScope.newLayout = !!current.$$route.newLayout; - $rootScope.fixFooter = !!current.$$route.fixFooter; - - $anchorScroll(); - }); - - var initallyChecked: boolean = false; - (window).__isLoading = function() { - if (!initallyChecked) { - initallyChecked = true; - return true; - } - return $http.pendingRequests.length > 0; - }; - } } - -interface QuayRunScope extends ng.IRootScopeService { - currentPage: any; - current: any; - title: any; - description: string, - pageClass: any; - newLayout: any; - fixFooter: any; -} - - // TODO: Make injected values into services and move to NgModule.providers, as constants are not supported in Angular 2 angular .module(quay.name)