From 4ad39a5c96dd99acf819ce189b13fec946d7506b Mon Sep 17 00:00:00 2001 From: talasila Date: Tue, 7 Feb 2017 15:03:57 -0500 Subject: Initial OpenECOMP Portal commit Change-Id: I804b80e0830c092e307da1599bd9fbb5c3e2da77 Signed-off-by: talasila --- ecomp-portal-FE/client/app/app.js | 120 ++++ ecomp-portal-FE/client/app/app.less | 78 +++ ecomp-portal-FE/client/app/configurations.js | 5 + .../directives/auto-focus/auto-focus.directive.js | 46 ++ .../image-upload/image-upload.directive.js | 222 ++++++ .../directives/left-menu/left-menu.directive.js | 96 +++ .../client/app/directives/left-menu/left-menu.less | 133 ++++ .../app/directives/left-menu/left-menu.tpl.html | 57 ++ .../multiple-select/multiple-select.directive.js | 111 +++ .../multiple-select/multiple-select.less | 81 +++ .../multiple-select/multiple-select.tpl.html | 38 + .../right-click-menu/right-click-menu.directive.js | 38 + .../right-click/ng-right-click-directive.js | 32 + .../directives/right-menu/right-menu.directive.js | 140 ++++ .../app/directives/right-menu/right-menu.less | 178 +++++ .../app/directives/right-menu/right-menu.tpl.html | 40 ++ .../directives/scroll-top/scroll-top.directive.js | 35 + .../search-users/search-users.controller.js | 161 +++++ .../search-users/search-users.controller.spec.js | 176 +++++ .../search-users/search-users.directive.js | 34 + .../app/directives/search-users/search-users.less | 154 +++++ .../directives/search-users/search-users.tpl.html | 144 ++++ .../client/app/filters/elipsis/elipsis.filter.js | 38 + .../app/filters/elipsis/elipsis.filter.spec.js | 58 ++ .../app/filters/trusted-url/trusted-url.filter.js | 26 + ecomp-portal-FE/client/app/router.js | 528 ++++++++++++++ .../client/app/services/admins/admins.service.js | 176 +++++ .../services/applications/applications.service.js | 346 ++++++++++ .../client/app/services/catalog/catalog.service.js | 95 +++ .../services/confirm-box/confirm-box.service.js | 153 ++++ .../app/services/contact-us/contact-us.service.js | 247 +++++++ .../app/services/dashboard/dashboard.service.js | 185 +++++ .../error-messages/error-messages.service.js | 23 + .../functionalMenu/functionalMenu.service.js | 253 +++++++ .../services/global-constants/global-constants.js | 21 + .../kpi-dashboard/kpi-dashboard.service.js | 185 +++++ .../app/services/manifest/manifest.service.js | 64 ++ .../client/app/services/menus/menus.service.js | 145 ++++ .../portal-admins/portal-admins.service.js | 107 +++ .../support/getAccess/get-access.service.js | 61 ++ .../services/support/session/session.service.js | 56 ++ .../services/userProfile/userProfile.service.js | 240 +++++++ .../app/services/userbar/userbar.update.service.js | 97 +++ .../client/app/services/users/users.service.js | 161 +++++ .../client/app/services/utils/utils.service.js | 57 ++ .../client/app/services/widgets/widgets.service.js | 178 +++++ ecomp-portal-FE/client/app/styles/att-abs.less | 86 +++ ecomp-portal-FE/client/app/styles/buttons.less | 72 ++ .../client/app/styles/ecomp-general.less | 76 ++ ecomp-portal-FE/client/app/styles/fonts.less | 81 +++ ecomp-portal-FE/client/app/styles/form.less | 189 +++++ .../client/app/styles/kpi-dashboard.less | 111 +++ ecomp-portal-FE/client/app/styles/mixins.less | 296 ++++++++ ecomp-portal-FE/client/app/styles/ng-dialog.less | 88 +++ ecomp-portal-FE/client/app/styles/reset.less | 79 +++ ecomp-portal-FE/client/app/styles/select2.less | 102 +++ ecomp-portal-FE/client/app/styles/spinner.less | 56 ++ ecomp-portal-FE/client/app/styles/sprites.less | 118 ++++ ecomp-portal-FE/client/app/styles/variables.less | 86 +++ .../add-admin-dialogs/new-admin.controller.js | 214 ++++++ .../add-admin-dialogs/new-admin.controller.spec.js | 130 ++++ .../admins/add-admin-dialogs/new-admin.modal.html | 66 ++ .../admins/add-admin-dialogs/new-admin.modal.less | 99 +++ .../client/app/views/admins/admins.controller.js | 151 ++++ .../app/views/admins/admins.controller.spec.js | 19 + .../client/app/views/admins/admins.less | 47 ++ .../client/app/views/admins/admins.tpl.html | 82 +++ .../application-details.controller.js | 244 +++++++ .../application-details.controller.spec.js | 19 + .../application-details.modal.html | 183 +++++ .../application-details.modal.less | 122 ++++ .../views/applications/applications.controller.js | 111 +++ .../applications/applications.controller.spec.js | 19 + .../app/views/applications/applications.less | 45 ++ .../app/views/applications/applications.tpl.html | 100 +++ .../client/app/views/catalog/catalog.controller.js | 166 +++++ .../client/app/views/catalog/catalog.less | 439 ++++++++++++ .../client/app/views/catalog/catalog.tpl.html | 91 +++ .../catalog/catalogconfirmation.controller.js | 62 ++ .../app/views/catalog/information-box.tpl.html | 42 ++ .../admin-confirmation-box.tpl.html | 31 + .../confirmation-box.controller.js | 41 ++ .../views/confirmation-box/confirmation-box.less | 53 ++ .../confirmation-box/confirmation-box.tpl.html | 28 + .../dragdrop-confirmation-box.tpl.html | 31 + .../confirmation-box/information-box.tpl.html | 27 + .../views/dashboard/dashboard-widget-manage.html | 152 ++++ .../views/dashboard/dashboard-widget.controller.js | 422 ++++++++++++ .../dashboard/dashboard-widget.controller.less | 101 +++ .../app/views/dashboard/dashboard.controller.js | 312 +++++++++ .../views/dashboard/dashboard.controller.spec.js | 78 +++ .../client/app/views/dashboard/dashboard.less | 766 +++++++++++++++++++++ .../client/app/views/dashboard/dashboard.tpl.html | 346 ++++++++++ .../app/views/dashboard/newsticker.controller.js | 47 ++ .../client/app/views/errors/error.404.tpl.html | 31 + .../client/app/views/errors/error.controller.js | 36 + .../client/app/views/errors/error.tpl.html | 26 + .../client/app/views/footer/footer.controller.js | 49 ++ .../app/views/footer/footer.controller.spec.js | 19 + .../client/app/views/footer/footer.less | 53 ++ .../client/app/views/footer/footer.tpl.html | 36 + .../menu-details.controller.js | 384 +++++++++++ .../menu-details.delete.modal.html | 35 + .../functionalMenu-dialog/menu-details.modal.html | 106 +++ .../functionalMenu-dialog/modal-details.modal.less | 103 +++ .../functionalMenu/functionalMenu.controller.js | 331 +++++++++ .../app/views/functionalMenu/functionalMenu.less | 70 ++ .../views/functionalMenu/functionalMenu.tpl.html | 48 ++ .../app/views/functionalMenu/jqTreeContextMenu.js | 192 ++++++ .../client/app/views/header/header.controller.js | 419 +++++++++++ .../app/views/header/header.controller.spec.js | 19 + .../client/app/views/header/header.less | 380 ++++++++++ .../client/app/views/header/header.tpl.html | 277 ++++++++ .../views/header/user-edit/edit-user.controller.js | 134 ++++ .../app/views/header/user-edit/edit-user.less | 61 ++ .../app/views/header/user-edit/edit-user.tpl.html | 69 ++ .../applications-home.controller.js | 244 +++++++ .../applications-home.controller.spec.js | 77 +++ .../home/applications-home/applications-home.less | 164 +++++ .../applications-home/applications-home.tpl.html | 59 ++ .../home/widgets-home/widgets-home.controller.js | 284 ++++++++ .../widgets-home/widgets-home.controller.spec.js | 1 + .../app/views/home/widgets-home/widgets-home.less | 137 ++++ .../views/home/widgets-home/widgets-home.tpl.html | 123 ++++ .../new-portal-admin.controller.js | 85 +++ .../new-portal-admin.controller.spec.js | 19 + .../new-portal-admin/new-portal-admin.modal.html | 32 + .../new-portal-admin/new-portal-admin.modal.less | 99 +++ .../views/portal-admin/portal-admin-controller.js | 127 ++++ .../app/views/portal-admin/portal-admin.tpl.html | 73 ++ .../app/views/portal-admin/portal-admins.less | 56 ++ .../client/app/views/search/search.controller.js | 184 +++++ .../app/views/search/search.controller.spec.js | 19 + .../client/app/views/search/search.less | 55 ++ .../client/app/views/search/search.tpl.html | 82 +++ .../client/app/views/sidebar/sidebar.controller.js | 143 ++++ .../client/app/views/sidebar/sidebar.less | 37 + .../client/app/views/sidebar/sidebar.tpl.html | 20 + .../contact-us-manage.controller.js | 194 ++++++ .../contact-us-manage.controller.less | 159 +++++ .../contact-us-manage/contact-us-manage.html | 136 ++++ .../support/contact-us/contact-us.controller.js | 166 +++++ .../contact-us/contact-us.controller.spec.js | 19 + .../app/views/support/contact-us/contact-us.less | 104 +++ .../views/support/contact-us/contact-us.tpl.html | 125 ++++ .../support/get-access/get-access.controller.js | 70 ++ .../get-access/get-access.controller.spec.js | 19 + .../app/views/support/get-access/get-access.less | 67 ++ .../views/support/get-access/get-access.tpl.html | 88 +++ .../client/app/views/tabs/tabframe.html | 22 + .../client/app/views/tabs/tabs.controller.js | 231 +++++++ .../client/app/views/tabs/tabs.controller.spec.js | 80 +++ ecomp-portal-FE/client/app/views/tabs/tabs.less | 658 ++++++++++++++++++ .../client/app/views/tabs/tabs.tpl.html | 46 ++ .../client/app/views/userbar/userbar.controller.js | 262 +++++++ .../client/app/views/userbar/userbar.less | 41 ++ .../client/app/views/userbar/userbar.tpl.html | 20 + .../users/new-user-dialogs/new-user.controller.js | 211 ++++++ .../new-user-dialogs/new-user.controller.spec.js | 222 ++++++ .../users/new-user-dialogs/new-user.modal.html | 70 ++ .../users/new-user-dialogs/new-user.modal.less | 126 ++++ .../client/app/views/users/users.controller.js | 187 +++++ .../app/views/users/users.controller.spec.js | 19 + ecomp-portal-FE/client/app/views/users/users.less | 59 ++ .../client/app/views/users/users.tpl.html | 105 +++ .../widget-details.controller.js | 202 ++++++ .../widget-details.controller.spec.js | 19 + .../widget-details.modal.html | 132 ++++ .../widget-details.modal.less | 94 +++ .../client/app/views/widgets/widgets.controller.js | 151 ++++ .../app/views/widgets/widgets.controller.spec.js | 19 + .../client/app/views/widgets/widgets.less | 60 ++ .../client/app/views/widgets/widgets.tpl.html | 77 +++ 173 files changed, 21203 insertions(+) create mode 100644 ecomp-portal-FE/client/app/app.js create mode 100644 ecomp-portal-FE/client/app/app.less create mode 100644 ecomp-portal-FE/client/app/configurations.js create mode 100644 ecomp-portal-FE/client/app/directives/auto-focus/auto-focus.directive.js create mode 100644 ecomp-portal-FE/client/app/directives/image-upload/image-upload.directive.js create mode 100644 ecomp-portal-FE/client/app/directives/left-menu/left-menu.directive.js create mode 100644 ecomp-portal-FE/client/app/directives/left-menu/left-menu.less create mode 100644 ecomp-portal-FE/client/app/directives/left-menu/left-menu.tpl.html create mode 100644 ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.directive.js create mode 100644 ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.less create mode 100644 ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.tpl.html create mode 100644 ecomp-portal-FE/client/app/directives/right-click-menu/right-click-menu.directive.js create mode 100644 ecomp-portal-FE/client/app/directives/right-click/ng-right-click-directive.js create mode 100644 ecomp-portal-FE/client/app/directives/right-menu/right-menu.directive.js create mode 100644 ecomp-portal-FE/client/app/directives/right-menu/right-menu.less create mode 100644 ecomp-portal-FE/client/app/directives/right-menu/right-menu.tpl.html create mode 100644 ecomp-portal-FE/client/app/directives/scroll-top/scroll-top.directive.js create mode 100644 ecomp-portal-FE/client/app/directives/search-users/search-users.controller.js create mode 100644 ecomp-portal-FE/client/app/directives/search-users/search-users.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/directives/search-users/search-users.directive.js create mode 100644 ecomp-portal-FE/client/app/directives/search-users/search-users.less create mode 100644 ecomp-portal-FE/client/app/directives/search-users/search-users.tpl.html create mode 100644 ecomp-portal-FE/client/app/filters/elipsis/elipsis.filter.js create mode 100644 ecomp-portal-FE/client/app/filters/elipsis/elipsis.filter.spec.js create mode 100644 ecomp-portal-FE/client/app/filters/trusted-url/trusted-url.filter.js create mode 100644 ecomp-portal-FE/client/app/router.js create mode 100644 ecomp-portal-FE/client/app/services/admins/admins.service.js create mode 100644 ecomp-portal-FE/client/app/services/applications/applications.service.js create mode 100644 ecomp-portal-FE/client/app/services/catalog/catalog.service.js create mode 100644 ecomp-portal-FE/client/app/services/confirm-box/confirm-box.service.js create mode 100644 ecomp-portal-FE/client/app/services/contact-us/contact-us.service.js create mode 100644 ecomp-portal-FE/client/app/services/dashboard/dashboard.service.js create mode 100644 ecomp-portal-FE/client/app/services/error-messages/error-messages.service.js create mode 100644 ecomp-portal-FE/client/app/services/functionalMenu/functionalMenu.service.js create mode 100644 ecomp-portal-FE/client/app/services/global-constants/global-constants.js create mode 100644 ecomp-portal-FE/client/app/services/kpi-dashboard/kpi-dashboard.service.js create mode 100644 ecomp-portal-FE/client/app/services/manifest/manifest.service.js create mode 100644 ecomp-portal-FE/client/app/services/menus/menus.service.js create mode 100644 ecomp-portal-FE/client/app/services/portal-admins/portal-admins.service.js create mode 100644 ecomp-portal-FE/client/app/services/support/getAccess/get-access.service.js create mode 100644 ecomp-portal-FE/client/app/services/support/session/session.service.js create mode 100644 ecomp-portal-FE/client/app/services/userProfile/userProfile.service.js create mode 100644 ecomp-portal-FE/client/app/services/userbar/userbar.update.service.js create mode 100644 ecomp-portal-FE/client/app/services/users/users.service.js create mode 100644 ecomp-portal-FE/client/app/services/utils/utils.service.js create mode 100644 ecomp-portal-FE/client/app/services/widgets/widgets.service.js create mode 100644 ecomp-portal-FE/client/app/styles/att-abs.less create mode 100644 ecomp-portal-FE/client/app/styles/buttons.less create mode 100644 ecomp-portal-FE/client/app/styles/ecomp-general.less create mode 100644 ecomp-portal-FE/client/app/styles/fonts.less create mode 100644 ecomp-portal-FE/client/app/styles/form.less create mode 100644 ecomp-portal-FE/client/app/styles/kpi-dashboard.less create mode 100644 ecomp-portal-FE/client/app/styles/mixins.less create mode 100644 ecomp-portal-FE/client/app/styles/ng-dialog.less create mode 100644 ecomp-portal-FE/client/app/styles/reset.less create mode 100644 ecomp-portal-FE/client/app/styles/select2.less create mode 100644 ecomp-portal-FE/client/app/styles/spinner.less create mode 100644 ecomp-portal-FE/client/app/styles/sprites.less create mode 100644 ecomp-portal-FE/client/app/styles/variables.less create mode 100644 ecomp-portal-FE/client/app/views/admins/add-admin-dialogs/new-admin.controller.js create mode 100644 ecomp-portal-FE/client/app/views/admins/add-admin-dialogs/new-admin.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/admins/add-admin-dialogs/new-admin.modal.html create mode 100644 ecomp-portal-FE/client/app/views/admins/add-admin-dialogs/new-admin.modal.less create mode 100644 ecomp-portal-FE/client/app/views/admins/admins.controller.js create mode 100644 ecomp-portal-FE/client/app/views/admins/admins.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/admins/admins.less create mode 100644 ecomp-portal-FE/client/app/views/admins/admins.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/applications/application-details-dialog/application-details.controller.js create mode 100644 ecomp-portal-FE/client/app/views/applications/application-details-dialog/application-details.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/applications/application-details-dialog/application-details.modal.html create mode 100644 ecomp-portal-FE/client/app/views/applications/application-details-dialog/application-details.modal.less create mode 100644 ecomp-portal-FE/client/app/views/applications/applications.controller.js create mode 100644 ecomp-portal-FE/client/app/views/applications/applications.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/applications/applications.less create mode 100644 ecomp-portal-FE/client/app/views/applications/applications.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/catalog/catalog.controller.js create mode 100644 ecomp-portal-FE/client/app/views/catalog/catalog.less create mode 100644 ecomp-portal-FE/client/app/views/catalog/catalog.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/catalog/catalogconfirmation.controller.js create mode 100644 ecomp-portal-FE/client/app/views/catalog/information-box.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/confirmation-box/admin-confirmation-box.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/confirmation-box/confirmation-box.controller.js create mode 100644 ecomp-portal-FE/client/app/views/confirmation-box/confirmation-box.less create mode 100644 ecomp-portal-FE/client/app/views/confirmation-box/confirmation-box.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/confirmation-box/dragdrop-confirmation-box.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/confirmation-box/information-box.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/dashboard/dashboard-widget-manage.html create mode 100644 ecomp-portal-FE/client/app/views/dashboard/dashboard-widget.controller.js create mode 100644 ecomp-portal-FE/client/app/views/dashboard/dashboard-widget.controller.less create mode 100644 ecomp-portal-FE/client/app/views/dashboard/dashboard.controller.js create mode 100644 ecomp-portal-FE/client/app/views/dashboard/dashboard.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/dashboard/dashboard.less create mode 100644 ecomp-portal-FE/client/app/views/dashboard/dashboard.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/dashboard/newsticker.controller.js create mode 100644 ecomp-portal-FE/client/app/views/errors/error.404.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/errors/error.controller.js create mode 100644 ecomp-portal-FE/client/app/views/errors/error.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/footer/footer.controller.js create mode 100644 ecomp-portal-FE/client/app/views/footer/footer.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/footer/footer.less create mode 100644 ecomp-portal-FE/client/app/views/footer/footer.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/functionalMenu/functionalMenu-dialog/menu-details.controller.js create mode 100644 ecomp-portal-FE/client/app/views/functionalMenu/functionalMenu-dialog/menu-details.delete.modal.html create mode 100644 ecomp-portal-FE/client/app/views/functionalMenu/functionalMenu-dialog/menu-details.modal.html create mode 100644 ecomp-portal-FE/client/app/views/functionalMenu/functionalMenu-dialog/modal-details.modal.less create mode 100644 ecomp-portal-FE/client/app/views/functionalMenu/functionalMenu.controller.js create mode 100644 ecomp-portal-FE/client/app/views/functionalMenu/functionalMenu.less create mode 100644 ecomp-portal-FE/client/app/views/functionalMenu/functionalMenu.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/functionalMenu/jqTreeContextMenu.js create mode 100644 ecomp-portal-FE/client/app/views/header/header.controller.js create mode 100644 ecomp-portal-FE/client/app/views/header/header.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/header/header.less create mode 100644 ecomp-portal-FE/client/app/views/header/header.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/header/user-edit/edit-user.controller.js create mode 100644 ecomp-portal-FE/client/app/views/header/user-edit/edit-user.less create mode 100644 ecomp-portal-FE/client/app/views/header/user-edit/edit-user.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/home/applications-home/applications-home.controller.js create mode 100644 ecomp-portal-FE/client/app/views/home/applications-home/applications-home.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/home/applications-home/applications-home.less create mode 100644 ecomp-portal-FE/client/app/views/home/applications-home/applications-home.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/home/widgets-home/widgets-home.controller.js create mode 100644 ecomp-portal-FE/client/app/views/home/widgets-home/widgets-home.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/home/widgets-home/widgets-home.less create mode 100644 ecomp-portal-FE/client/app/views/home/widgets-home/widgets-home.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.controller.js create mode 100644 ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.modal.html create mode 100644 ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.modal.less create mode 100644 ecomp-portal-FE/client/app/views/portal-admin/portal-admin-controller.js create mode 100644 ecomp-portal-FE/client/app/views/portal-admin/portal-admin.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/portal-admin/portal-admins.less create mode 100644 ecomp-portal-FE/client/app/views/search/search.controller.js create mode 100644 ecomp-portal-FE/client/app/views/search/search.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/search/search.less create mode 100644 ecomp-portal-FE/client/app/views/search/search.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/sidebar/sidebar.controller.js create mode 100644 ecomp-portal-FE/client/app/views/sidebar/sidebar.less create mode 100644 ecomp-portal-FE/client/app/views/sidebar/sidebar.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.controller.js create mode 100644 ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.controller.less create mode 100644 ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.html create mode 100644 ecomp-portal-FE/client/app/views/support/contact-us/contact-us.controller.js create mode 100644 ecomp-portal-FE/client/app/views/support/contact-us/contact-us.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/support/contact-us/contact-us.less create mode 100644 ecomp-portal-FE/client/app/views/support/contact-us/contact-us.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/support/get-access/get-access.controller.js create mode 100644 ecomp-portal-FE/client/app/views/support/get-access/get-access.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/support/get-access/get-access.less create mode 100644 ecomp-portal-FE/client/app/views/support/get-access/get-access.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/tabs/tabframe.html create mode 100644 ecomp-portal-FE/client/app/views/tabs/tabs.controller.js create mode 100644 ecomp-portal-FE/client/app/views/tabs/tabs.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/tabs/tabs.less create mode 100644 ecomp-portal-FE/client/app/views/tabs/tabs.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/userbar/userbar.controller.js create mode 100644 ecomp-portal-FE/client/app/views/userbar/userbar.less create mode 100644 ecomp-portal-FE/client/app/views/userbar/userbar.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.controller.js create mode 100644 ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.modal.html create mode 100644 ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.modal.less create mode 100644 ecomp-portal-FE/client/app/views/users/users.controller.js create mode 100644 ecomp-portal-FE/client/app/views/users/users.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/users/users.less create mode 100644 ecomp-portal-FE/client/app/views/users/users.tpl.html create mode 100644 ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.controller.js create mode 100644 ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.modal.html create mode 100644 ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.modal.less create mode 100644 ecomp-portal-FE/client/app/views/widgets/widgets.controller.js create mode 100644 ecomp-portal-FE/client/app/views/widgets/widgets.controller.spec.js create mode 100644 ecomp-portal-FE/client/app/views/widgets/widgets.less create mode 100644 ecomp-portal-FE/client/app/views/widgets/widgets.tpl.html (limited to 'ecomp-portal-FE/client/app') diff --git a/ecomp-portal-FE/client/app/app.js b/ecomp-portal-FE/client/app/app.js new file mode 100644 index 00000000..ea06d9aa --- /dev/null +++ b/ecomp-portal-FE/client/app/app.js @@ -0,0 +1,120 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +var app = angular.module('ecompApp', [ + 'ngCookies', + 'ngResource', + 'ngSanitize', + 'ui.router', + 'ecomp.conf', + 'ngMessages', + 'ui.select', + 'angular-cache', + 'ngDialog', + 'att.abs', + 'att.gridster', + 'uuid', + 'ui.bootstrap', + 'ngMaterial' + ]) + .config(($stateProvider, $urlRouterProvider, $locationProvider, $httpProvider, ngDialogProvider) => { + $urlRouterProvider.otherwise('/error404'); + $locationProvider.html5Mode(true); + + //initialize get if not there + if (!$httpProvider.defaults.headers.get) { + $httpProvider.defaults.headers.get = {}; + } + + //withCredentials flag on the XHR object - add cookie to XHR requests + $httpProvider.defaults.withCredentials = true; + $httpProvider.defaults.useXDoain = true; + $httpProvider.defaults.timeout = 30000; + + //default configuration for ngDialog modal + ngDialogProvider.setDefaults({ + className: 'ngdialog-theme-default', + showClose: true, + closeByDocument: false, + closeByEscape: false + }); + + + var myHostName; + myHostName = location.host; + + if (!(myHostName.includes("localhost"))) { + $httpProvider.defaults.headers.get['If-Modified-Since'] = 'Mon, 26 Jul 1997 05:00:00 GMT'; + $httpProvider.defaults.headers.get['Cache-Control'] = 'no-cache'; + $httpProvider.defaults.headers.get['Pragma'] = 'no-cache'; + } + + + //interceptor here: + var interceptor = function ($q, $injector, $log) { + return { + 'responseError': function (rejection) { + $log.error('Interceptor rejection: ' + JSON.stringify(rejection)); + var $state = $injector.get('$state'); + switch (rejection.status) { + case 401: + var globalLoginUrl = rejection.headers()['global-login-url']; + if (globalLoginUrl) { + window.location = globalLoginUrl + + (globalLoginUrl.indexOf('?') === -1 ? '?' : '') + + '&retUrl=' + encodeURI(window.location); + return; + } + break; + case 403: + // $state.go('root.applicationsHome'); + //handle forbidden error + break; + // case 404: + // $state.go('/login.htm'); + // //handle forbidden error + // break; + default: + //handle internal server error + } + return $q.reject(rejection); + } + }; + }; + $httpProvider.interceptors.push(interceptor); + + }).run(($http, CacheFactory) => { + //default configuration for cache factory + $http.defaults.cache = CacheFactory('defaultCache', { + maxAge: 15 * 60 * 1000, // Items added to this cache expire after 15 minutes + cacheFlushInterval: 60 * 60 * 1000, // This cache will clear itself every hour + deleteOnExpire: 'aggressive' // Items will be deleted from this cache when they expire + }); + }); + + +angular.module( 'ecompApp' ).config( [ +'$compileProvider', +function( $compileProvider ) +{ + $compileProvider.aHrefSanitizationWhitelist(/^\s*(https?|ftp|mailto|chrome-extension):/); +} +]); diff --git a/ecomp-portal-FE/client/app/app.less b/ecomp-portal-FE/client/app/app.less new file mode 100644 index 00000000..4c8ac018 --- /dev/null +++ b/ecomp-portal-FE/client/app/app.less @@ -0,0 +1,78 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +// injector +@import 'directives/left-menu/left-menu.less'; +@import 'directives/multiple-select/multiple-select.less'; +@import 'directives/right-menu/right-menu.less'; +@import 'directives/search-users/search-users.less'; +@import 'styles/att-abs.less'; +@import 'styles/buttons.less'; +@import 'styles/ecomp-general.less'; +@import 'styles/fonts.less'; +@import 'styles/form.less'; +@import 'styles/kpi-dashboard.less'; +@import 'styles/mixins.less'; +@import 'styles/ng-dialog.less'; +@import 'styles/reset.less'; +@import 'styles/select2.less'; +@import 'styles/spinner.less'; +@import 'styles/sprites.less'; +@import 'styles/variables.less'; +@import 'views/admins/add-admin-dialogs/new-admin.modal.less'; +@import 'views/admins/admins.less'; +@import 'views/applications/application-details-dialog/application-details.modal.less'; +@import 'views/applications/applications.less'; +@import 'views/catalog/catalog.less'; +@import 'views/confirmation-box/confirmation-box.less'; +@import 'views/dashboard/dashboard-widget.controller.less'; +@import 'views/dashboard/dashboard.less'; +@import 'views/footer/footer.less'; +@import 'views/functionalMenu/functionalMenu-dialog/modal-details.modal.less'; +@import 'views/functionalMenu/functionalMenu.less'; +@import 'views/header/header.less'; +@import 'views/home/applications-home/applications-home.less'; +@import 'views/home/widgets-home/widgets-home.less'; +@import 'views/portal-admin/new-portal-admin/new-portal-admin.modal.less'; +@import 'views/portal-admin/portal-admins.less'; +@import 'views/search/search.less'; +@import 'views/sidebar/sidebar.less'; +@import 'views/support/contact-us/contact-us-manage/contact-us-manage.controller.less'; +@import 'views/support/contact-us/contact-us.less'; +@import 'views/support/get-access/get-access.less'; +@import 'views/tabs/tabs.less'; +@import 'views/userbar/userbar.less'; +@import 'views/users/new-user-dialogs/new-user.modal.less'; +@import 'views/users/users.less'; +@import 'views/widgets/widget-details-dialog/widget-details.modal.less'; +@import 'views/widgets/widgets.less'; +// endinjector + +html { height: 100%; overflow-y: hidden;} +* { box-sizing: border-box; } +body { + font: normal 12px arial; +} + +/* Responsive: Portrait tablets and up */ +@media screen and (min-width: 768px) { + .container { + //max-width: 730px; + } +} diff --git a/ecomp-portal-FE/client/app/configurations.js b/ecomp-portal-FE/client/app/configurations.js new file mode 100644 index 00000000..0c417914 --- /dev/null +++ b/ecomp-portal-FE/client/app/configurations.js @@ -0,0 +1,5 @@ +angular.module('ecomp.conf', []) + +.constant('conf', {api:{userApps:'http://www.ecomp.att.com:8080/ecompportal/portalApi/userApps',persUserApps:'http://www.ecomp.att.com:8080/ecompportal/portalApi/persUserApps',appCatalog:'http://www.ecomp.att.com:8080/ecompportal/portalApi/appCatalog',accountAdmins:'http://www.ecomp.att.com:8080/ecompportal/portalApi/accountAdmins',availableApps:'http://www.ecomp.att.com:8080/ecompportal/portalApi/availableApps',allAvailableApps:'http://www.ecomp.att.com:8080/ecompportal/portalApi/allAvailableApps',userProfile:'http://www.ecomp.att.com:8080/ecompportal/portalApi/userProfile',currentUserProfile:'http://www.ecomp.att.com:8080/ecompportal/portalApi/currentUserProfile',queryUsers:'http://www.ecomp.att.com:8080/ecompportal/portalApi/queryUsers',adminAppsRoles:'http://www.ecomp.att.com:8080/ecompportal/portalApi/adminAppsRoles',adminApps:'http://www.ecomp.att.com:8080/ecompportal/portalApi/adminApps',appsForSuperAdminAndAccountAdmin:'http://www.ecomp.att.com:8080/ecompportal/portalApi/appsForSuperAdminAndAccountAdmin',accountUsers:'http://www.ecomp.att.com:8080/ecompportal/portalApi/app/:appId/users',saveNewUser:'http://www.ecomp.att.com:8080/ecompportal/portalApi/saveNewUser',userAppRoles:'http://www.ecomp.att.com:8080/ecompportal/portalApi/userAppRoles',updateRemoteUserProfile:'http://www.ecomp.att.com:8080/ecompportal/portalApi/updateRemoteUserProfile',onboardingApps:'http://www.ecomp.att.com:8080/ecompportal/portalApi/onboardingApps',widgets:'http://www.ecomp.att.com:8080/ecompportal/portalApi/widgets',widgetsValidation:'http://www.ecomp.att.com:8080/ecompportal/portalApi/widgets/validation',functionalMenuForAuthUser:'http://www.ecomp.att.com:8080/ecompportal/portalApi/functionalMenuForAuthUser',functionalMenuForEditing:'http://www.ecomp.att.com:8080/ecompportal/portalApi/functionalMenuForEditing',functionalMenu:'http://www.ecomp.att.com:8080/ecompportal/portalApi/functionalMenu',functionalMenuItemDetails:'http://www.ecomp.att.com:8080/ecompportal/portalApi/functionalMenuItemDetails/:menuId',appRoles:'http://www.ecomp.att.com:8080/ecompportal/portalApi/appRoles/:appId',functionalMenuItem:'http://www.ecomp.att.com:8080/ecompportal/portalApi/functionalMenuItem',regenerateFunctionalMenuAncestors:'http://www.ecomp.att.com:8080/ecompportal/portalApi/regenerateFunctionalMenuAncestors',listOfApp:'http://www.ecomp.att.com:8080/ecompportal/portalApi/getAppList',setFavoriteItem:'http://www.ecomp.att.com:8080/ecompportal/portalApi/setFavoriteItem',getFavoriteItems:'http://www.ecomp.att.com:8080/ecompportal/portalApi/getFavoriteItems',removeFavoriteItem:'http://www.ecomp.att.com:8080/ecompportal/portalApi/removeFavoriteItem/:menuId',ping:'http://www.ecomp.att.com:8080/ecompportal/portalApi/ping',functionalMenuStaticInfo:'http://www.ecomp.att.com:8080/ecompportal/portalApi/functionalMenuStaticInfo',resetFunctionalMenuStaticInfo:'http://www.ecomp.att.com:8080/ecompportal/portalApi/resetFunctionalMenuStaticInfo',portalAdmins:'http://www.ecomp.att.com:8080/ecompportal/portalApi/portalAdmins',portalAdmin:'http://www.ecomp.att.com:8080/ecompportal/portalApi/portalAdmin',getKpiDashUserStoriesStats:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_user_stories_stats',getKpiDashUserApiStats:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_user_api_stats',getKpiDashLocStats:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_loc_stats',getKpiDashLocStatsCat:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_loc_stats_cat',getKpiDashServiceSupported:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_kpi_service_supported',getKpiDashPublishedDelivered:'http://www.ecomp.att.com:8080/ecompportal/portalApi/execute_get_published_delivered',getKpiDashFeedStats:'http://www.ecomp.att.com:8080/ecompportal/portalApi/execute_get_feed_stats',getKpiDashUserApis:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_user_api_stats',getKpiDashGeoMapUrl:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_geo_map_url',getKpiDashRCloudAUrl:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_rcloud_a_url',getKpiDashGeoMapApiUrl:'http://www.ecomp.att.com:8080/ecompportal/portalApi/get_geo_map_api_url',getManifest:'http://www.ecomp.att.com:8080/ecompportal/portalApi/manifest',getActiveUser:'http://www.ecomp.att.com:8080/ecompportal/portalApi/dashboard/activeUsers',getSearchAllByStringResults:'http://www.ecomp.att.com:8080/ecompportal/portalApi/dashboard/search',commonWidget:'http://www.ecomp.att.com:8080/ecompportal/portalApi/dashboard/widgetData',deleteCommonWidget:'http://www.ecomp.att.com:8080/ecompportal/portalApi/dashboard/deleteData',getContactUS:'http://www.ecomp.att.com:8080/ecompportal/portalApi/contactus/list',getAppsAndContacts:'http://www.ecomp.att.com:8080/ecompportal/portalApi/contactus/allapps',saveContactUS:'http://www.ecomp.att.com:8080/ecompportal/portalApi/contactus/save',deleteContactUS:'http://www.ecomp.att.com:8080/ecompportal/portalApi/contactus/delete',getContactUSPortalDetails:'http://www.ecomp.att.com:8080/ecompportal/portalApi/contactus/feedback',getAppCategoryFunctions:'http://www.ecomp.att.com:8080/ecompportal/portalApi/contactus/functions',onlineUserUpdateRate:'http://www.ecomp.att.com:8080/ecompportal/portalApi/dashboard/onlineUserUpdateRate',getWidthThresholdLeftMenu:'http://www.ecomp.att.com:8080/ecompportal/portalApi/dashboard/windowWidthThresholdLeftMenu',getWidthThresholdRightMenu:'http://www.ecomp.att.com:8080/ecompportal/portalApi/dashboard/windowWidthThresholdRightMenu'},cookieDomain:'att.com'}) + +; \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/directives/auto-focus/auto-focus.directive.js b/ecomp-portal-FE/client/app/directives/auto-focus/auto-focus.directive.js new file mode 100644 index 00000000..73964115 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/auto-focus/auto-focus.directive.js @@ -0,0 +1,46 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + + + +//angular.module('ecompApp') +// .directive('autoFocus', function () { +// return { +// restrict: 'A', +// scope: {}, +// link: function (scope, element) { +// element[0].focus(); +// } +// }; +// }); + +/* istanbul ignore next */ +(function(){ + class AutoFocusDirective{ + constructor(){ + this.restrict = 'A'; + this.link = this._link.bind(this); + } + _link(scope, element){ + element[0].focus(); + } + } + angular.module('ecompApp').directive('autoFocus', () => new AutoFocusDirective()); +})(); diff --git a/ecomp-portal-FE/client/app/directives/image-upload/image-upload.directive.js b/ecomp-portal-FE/client/app/directives/image-upload/image-upload.directive.js new file mode 100644 index 00000000..90c88c50 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/image-upload/image-upload.directive.js @@ -0,0 +1,222 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +angular.module('ecompApp').directive('imageUpload', function factory($q) { + var imageMimeRgx = /^image\/[a-zA-Z0-9]*$/; + + var URL = window.URL || window.webkitURL; + + var getResizeArea = function () { + var resizeAreaId = 'fileupload-resize-area'; + + var resizeArea = document.getElementById(resizeAreaId); + + if (!resizeArea) { + resizeArea = document.createElement('canvas'); + resizeArea.id = resizeAreaId; + resizeArea.style.visibility = 'hidden'; + document.body.appendChild(resizeArea); + } + + return resizeArea; + }; + + var resizeImage = function (origImage, options) { + var maxHeight = options.resizeMaxHeight || 300; + var maxWidth = options.resizeMaxWidth || 250; + var quality = options.resizeQuality || 0.7; + var type = options.resizeType || 'image/jpg'; + + var canvas = getResizeArea(); + + var height = origImage.height; + var width = origImage.width; + + //image redraw starting points + var x0, y0; + + // calculate the width and height, constraining the proportions + if (width > height) { + if (width > maxWidth) { + height = Math.round(height *= maxWidth / width); + width = maxWidth; + + x0 = 0; + y0 = Math.round((maxHeight - height)/2); + }else{ + maxHeight = height; + maxWidth = width; + x0 = 0; + y0 = 0; + } + } else { + if (height > maxHeight) { + width = Math.round(width *= maxHeight / height); + height = maxHeight; + + x0 = Math.round((maxWidth - width)/2); + y0 = 0; + }else{ + maxHeight = height; + maxWidth = width; + x0 = 0; + y0 = 0; + } + } + + canvas.width = maxWidth; + canvas.height = maxHeight; + + //draw image on canvas + var ctx = canvas.getContext("2d"); + + //set background color + if(options.backgroundColor){ + ctx.fillStyle = options.backgroundColor; + ctx.fillRect(0,0,maxWidth,maxHeight); + } + + + ctx.drawImage(origImage, x0, y0, width, height); + + // get the data from canvas as 70% jpg (or specified type). + return canvas.toDataURL(type, quality); + }; + + var createImage = function(url, callback) { + var image = new Image(); + image.onload = function() { + callback(image); + }; + image.src = url; + }; + + var fileToDataURL = function (file) { + var deferred = $q.defer(); + var reader = new FileReader(); + reader.onload = function (e) { + deferred.resolve(e.target.result); + }; + reader.readAsDataURL(file); + return deferred.promise; + }; + + return { + restrict: 'A', + require: '^form', + scope: { + image: '=imageUpload', + resizeMaxHeight: '@?imageUploadResizeMaxHeight', + resizeMaxWidth: '@?imageUploadResizeMaxWidth', + resizeQuality: '@?imageUploadResizeQuality', + resizeType: '@?imageUploadResizeType', + imageApi: '=?imageUploadApi', + backgroundColor: '@?imageUploadBackgroundColor' + }, + compile: function compile(tElement, tAttrs, transclude) { + return function postLink(scope, iElement, iAttrs, formCtrl) { + var doResizing = function(imageResult, callback) { + createImage(imageResult.url, function(image) { + var dataURL = resizeImage(image, scope); + imageResult.resized = { + dataURL: dataURL, + type: dataURL.match(/:(.+\/.+);/)[1] + }; + callback(imageResult); + }); + }; + + var applyScope = function(imageResult) { + scope.$apply(function() { + //console.log(imageResult); + if(iAttrs.multiple) + scope.image.push(imageResult); + else + scope.image = imageResult; + }); + }; + + iElement.bind('change', function (evt) { + //when multiple always return an array of images + if(iAttrs.multiple) + scope.image = []; + + var files = evt.target.files; + for(var i = 0; i < files.length; i++) { + setInputValidity(files[i]); + + //create a result object for each file in files + var imageResult = { + file: files[i], + url: URL.createObjectURL(files[i]) + }; + + fileToDataURL(files[i]).then(function (dataURL) { + imageResult.dataURL = dataURL; + }); + + if(scope.resizeMaxHeight || scope.resizeMaxWidth) { //resize image + doResizing(imageResult, function(imageResult) { + applyScope(imageResult); + }); + } + else { //no resizing + applyScope(imageResult); + } + } + }); + + //API for otter actions + scope.imageApi = scope.imageApi || {}; + scope.imageApi.clearFile = () => { + iElement[0].value = ""; + setInputValidity(); + }; + + + let setInputValidity = file => { + //if form validation supported + + if(formCtrl && iAttrs.name && formCtrl[iAttrs.name]){ + formCtrl[iAttrs.name].$setDirty(); + if(file && file.type && !imageMimeRgx.test(file.type)){ + //set form invalid + formCtrl[iAttrs.name].$setValidity('mimeType', false); + applyScope(); + return; + } + if(file && file.size && file.size > 1000000){ + //set form invalid + formCtrl[iAttrs.name].$setValidity('imageSize', false); + applyScope(); + return; + } + //set valid + formCtrl[iAttrs.name].$setValidity('mimeType', true); + formCtrl[iAttrs.name].$setValidity('imageSize', true); + } + + } + } + } + } +}); diff --git a/ecomp-portal-FE/client/app/directives/left-menu/left-menu.directive.js b/ecomp-portal-FE/client/app/directives/left-menu/left-menu.directive.js new file mode 100644 index 00000000..363485fe --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/left-menu/left-menu.directive.js @@ -0,0 +1,96 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +(function () { + class LeftMenu { + constructor($rootScope, $log, userbarUpdateService) { + this.templateUrl = 'app/directives/left-menu/left-menu.tpl.html'; + this.restrict = 'AE'; + this.$rootScope = $rootScope; + this.$log = $log; + this.userbarUpdateService = userbarUpdateService; + this.link = this._link.bind(this); + this.scope = { + sidebarModel: '=' + } + } + + _link(scope) { + let init = () => { + scope.isOpen = true; + }; + + init(); + + scope.refreshOnlineUsers = () => { + this.userbarUpdateService.setRefreshCount(this.userbarUpdateService.maxCount); + }; + + scope.toggleSidebar = () => { + scope.isOpen = !scope.isOpen; + if(scope.isOpen) + setContentPos(1); + else + setContentPos(0); + + }; + + scope.isBrowserInternetExplorer = false; + scope.browserName = bowser.name; + + if (bowser.msie || bowser.msedge) { + scope.isBrowserInternetExplorer = true; + } else { + scope.isBrowserInternetExplorer = false; + } + + let log = this.$log; + + this.userbarUpdateService.getWidthThresholdLeftMenu().then(function (res) { + if (res == null || res.response == null) { + log.error('userbarUpdateService: failed to get window width threshold for collapsing left menu; please make sure "window_width_threshold_left_menu" is specified in system.properties file.'); + } else { + var leftMenuCollapseWidthThreshold = parseInt(res.response.windowWidth); + if ($(window).width() { + scope.isOpen = true; + }); + } + } + angular.module('ecompApp').directive('leftMenu', ($rootScope,$log,userbarUpdateService) => new LeftMenu($rootScope,$log,userbarUpdateService)); +})(); + +function setContentPos(open) { + if(open==1){ + $("#contentId" ).css( "padding-left", "210px" ); + }else{ + $("#contentId" ).css( "padding-left", "50px" ); + } + +} diff --git a/ecomp-portal-FE/client/app/directives/left-menu/left-menu.less b/ecomp-portal-FE/client/app/directives/left-menu/left-menu.less new file mode 100644 index 00000000..276fb409 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/left-menu/left-menu.less @@ -0,0 +1,133 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +@sidebar-width: 200px; +@transition-duration: 0.25s; +@overlayer-opacity: 0.65; + + +.close-button { + .a24r; + font-size: 3em; + line-height: 18px; + position: absolute; + cursor: pointer; + vertical-align: middle; + top: @second-level-top; + left: 0; + -webkit-font-smoothing: antialiased; + height: 53px; + z-index: 101; +} +.ecomp-sidebar-container { + position: absolute; + display: block; + left: 0; + z-index: 100; + transition: left @transition-duration; + margin-top: -15px; + + .ecomp-sidebar-main { + position: absolute; + margin-top: 65px; + width: @sidebar-width; + height: 100vh; + .bg_u; + box-shadow: 0 4px 5px rgba(0, 0, 0, .2); + + padding-right: 10px; + padding-left: 10px; + + .accordion-container{ + margin-top: 45px; + overflow-y:auto; + overflow-x:hidden; + } + .att-accordion-font{ + font-size: .875rem; + color: #666; + display: inline-block; + font-family: arial; + + } + + .att-accordion-active{ + color: #199DDF !important; + } + + .sub-item{ + .att-accordion-font; + cursor: pointer; + height: 37px; + line-height: 37px; + padding-left: 20px; + padding-bottom: 10px; + vertical-align: middle; + width: 100%; + } + .sub-item:hover{ + .att-accordion-active; + } + + .parent-item{ + .att-accordion-font; + border-bottom: 1px solid #bbb; + cursor: pointer; + height: 37px; + line-height: 37px; + padding-bottom: 10px; + vertical-align: middle; + width: 100%; + } + .parent-item:hover{ + .att-accordion-active; + } + + } +} + +.open-sidebar { + left: 0; +} + +.close-sidebar { + left: -@sidebar-width; +} + +.content-overlayed { + position: fixed; + top: 110px; + right: 0; + bottom: 0; + left: 0; + background: none repeat scroll 0 0 rgb(242, 242, 242); + z-index: 9999; +} +.fade-animation{ + opacity: @overlayer-opacity; + transition: opacity @transition-duration ease-in-out; +} +.fade-animation.ng-hide { + opacity:0; + transition: opacity @transition-duration ease-in-out; +} + +#contentId{ + padding-left:210px +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/directives/left-menu/left-menu.tpl.html b/ecomp-portal-FE/client/app/directives/left-menu/left-menu.tpl.html new file mode 100644 index 00000000..0059d6a4 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/left-menu/left-menu.tpl.html @@ -0,0 +1,57 @@ + +
+ +
+
+
+
+ +
+
+ +   {{parent.name}} +
+ + +
+   {{child.name}} +
+
+ +
+
+ +
+
+
diff --git a/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.directive.js b/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.directive.js new file mode 100644 index 00000000..e8f6ed94 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.directive.js @@ -0,0 +1,111 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +angular.module('ecompApp') + .directive('multipleSelect', function ($window) { + return { + restrict: 'E', + templateUrl: 'app/directives/multiple-select/multiple-select.tpl.html', + scope: { + onChange: '&', + nameAttr: '@', + valueAttr: '@', + ngModel: '=', + placeholder: '@', + uniqueData: '@?', + onDropdownClose: '&?' + }, + link: function(scope, elm, attrs){ + scope.isExpanded = false; + + scope.isDisabled = !scope.ngModel || !scope.ngModel.length; + scope.$watch('ngModel', function(newVal){ + scope.isDisabled = !newVal || !newVal.length; + }); + + + let startListening = () => { + console.log('listening on $window!'); + angular.element($window).on('click', function () { + stopListening(); + }); + + angular.element('multiple-select').on('click', function(e) { + if($(e.target).closest('multiple-select')[0].attributes['unique-data'].value === attrs.uniqueData){ + console.log('ignored that..:', attrs.uniqueData); + e.stopPropagation(); + }else{ + console.log('shouldnt ignore, close expanded!:', attrs.uniqueData); + scope.isExpanded = false; + scope.$applyAsync(); + } + }); + }; + + let stopListening = function() { + if(scope.onDropdownClose){ + scope.onDropdownClose(); + } + scope.isExpanded = false; + scope.$applyAsync(); + console.log('stop listening on $window and multiple-element!'); + angular.element($window).off('click'); + angular.element('multiple-select').off('click'); + }; + + scope.showCheckboxes = function(){ + scope.isExpanded = !scope.isExpanded; + if(scope.isExpanded){ + startListening(); + }else{ + stopListening(); + if(scope.onDropdownClose){ + scope.onDropdownClose(); + } + } + }; + + scope.onCheckboxClicked = function() { + console.log('checkbox clicked; unique data: ',attrs.uniqueData); + if(scope.onChange) { + scope.onChange(); + } + } + + scope.getTitle = function(){ + var disp = ""; + if(!scope.ngModel || !scope.ngModel.length) { + return disp; + } + scope.ngModel.forEach(function(item){ + if(item[scope.valueAttr]){ + disp+=item[scope.nameAttr] + ","; + } + }); + if(disp!==""){ + disp = disp.slice(0,disp.length-1); + }else{ + disp = scope.placeholder; + } + return disp; + }; + } + }; + }); diff --git a/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.less b/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.less new file mode 100644 index 00000000..6e54c8b6 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.less @@ -0,0 +1,81 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .multiple-select{ + position: relative; + width: 100%; + + .selectBox{ + cursor: pointer; + position: relative; + border: 1px solid @o; + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; + line-height: 30px; + height: 30px; + padding-left: 10px; + padding-right: 10px; + + &.open::after{ + content: ''; + .arrow_up; + display: block; + position: absolute; + top: 12px; + right: 4px; + } + &.closed::after{ + content: ''; + .arrow_down; + display: block; + position: absolute; + top: 12px; + right: 4px; + } + &.disabled{ + cursor: default; + background: #CCCCCC; + } + + } + + .checkboxes{ + z-index: 99999; + padding-left: 8px; + padding-right: 8px; + position: absolute; + top: 30px; + width: 100%; + background: white; + + display: block; + border: 1px #dadada solid; + + label{ + cursor: pointer; + display: block; + } + input{ + cursor: pointer; + } + + + } +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.tpl.html b/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.tpl.html new file mode 100644 index 00000000..e55e844c --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/multiple-select/multiple-select.tpl.html @@ -0,0 +1,38 @@ + + diff --git a/ecomp-portal-FE/client/app/directives/right-click-menu/right-click-menu.directive.js b/ecomp-portal-FE/client/app/directives/right-click-menu/right-click-menu.directive.js new file mode 100644 index 00000000..358cc56f --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/right-click-menu/right-click-menu.directive.js @@ -0,0 +1,38 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +angular.module('ecompApp').directive( "contextMenu", function($compile){ + contextMenu = {}; + contextMenu.restrict = "AE"; + contextMenu.link = function( lScope, lElem, lAttr ){ + lElem.on("contextmenu", function (e) { + e.preventDefault(); + lElem.append( $compile( lScope[ lAttr.contextMenu ])(lScope) ); + $("#contextmenu-node").css("left", e.clientX); + $("#contextmenu-node").css("top", e.clientY); + }); + lElem.on("mouseleave", function(e){ + console.log("Leaved the div"); + if($("#contextmenu-node") ) + $("#contextmenu-node").remove(); + }); + }; + return contextMenu; +}); diff --git a/ecomp-portal-FE/client/app/directives/right-click/ng-right-click-directive.js b/ecomp-portal-FE/client/app/directives/right-click/ng-right-click-directive.js new file mode 100644 index 00000000..075ea3ac --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/right-click/ng-right-click-directive.js @@ -0,0 +1,32 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +angular.module('ecompApp'). + directive('ngRightClick', function($parse) { + return function(scope, element, attrs) + { + var fn = $parse(attrs.ngRightClick); + element.bind('contextmenu', function(event) { + scope.$apply(function() { + event.preventDefault(); + fn(scope, {$event:event}); + }); + }); + }; + }); diff --git a/ecomp-portal-FE/client/app/directives/right-menu/right-menu.directive.js b/ecomp-portal-FE/client/app/directives/right-menu/right-menu.directive.js new file mode 100644 index 00000000..b778ce7b --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/right-menu/right-menu.directive.js @@ -0,0 +1,140 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +/** + * Created by nnaffar on 1/28/16. + */ +(function () { + class RightMenu { + constructor($rootScope,$window,$log,userbarUpdateService) { + this.templateUrl = 'app/directives/right-menu/right-menu.tpl.html'; + this.restrict = 'AE'; + this.$rootScope = $rootScope; + this.userbarUpdateService = userbarUpdateService; + this.$window = $window; + this.$log = $log; + this.link = this._link.bind(this); + this.scope = { + userList :'=' + } + } + + + + _link(scope) { + let init = () => { + scope.isOpen = true; + scope.rightSideToggleBtn = 'Collapse'; + + scope.openInNewTab = (url) => { + if(url == "self") { + alert("Cannot chat with self!"); + } else { + var win = window.open(url, '_blank'); + setCookie(url.split("chat_id=")[1], 'source', 1); + //window.localStorage.setItem(url.split("chat_id=")[1],'source'); + win.focus(); + } + }; + + }; + + function setCookie(cname,cvalue,exdays) { + var d = new Date(); + d.setTime(d.getTime() + (exdays*24*60*60*1000)); + var expires = "expires=" + d.toGMTString(); + document.cookie = cname + "=" + cvalue + ";" + expires + ";path=/"; + } + + function getCookie(cname) { + var name = cname + "="; + var decodedCookie = decodeURIComponent(document.cookie); + var ca = decodedCookie.split(';'); + for(var i = 0; i < ca.length; i++) { + var c = ca[i]; + while (c.charAt(0) == ' ') { + c = c.substring(1); + } + if (c.indexOf(name) == 0) { + return c.substring(name.length, c.length); + } + } + return ""; + } + + + + init(); + + /***Getting the list of the users***/ + scope.toggleSidebar = () => { + scope.isOpen = !scope.isOpen; + if(scope.isOpen){ + scope.rightSideToggleBtn = 'Collapse'; + }else{ + scope.rightSideToggleBtn = 'Expand'; + } + }; + + scope.isBrowserInternetExplorer = false; + scope.browserName = bowser.name; + + if (bowser.msie || bowser.msedge) { + scope.isBrowserInternetExplorer = true; + } else { + scope.isBrowserInternetExplorer = false; + } + + + + + scope.calculateUserBarHeight = () => { + var footerOff = $('#online-userbar').offset().top; + var headOff = $('#footer').offset().top; + var userbarHeight= parseInt($(".online-user-container").css('height'),10); + var defaultOffSet = 45; + // console.log(headOff - footerOff-defaultOffSet); + $(".online-user-container").css({ + "height" : headOff - footerOff-defaultOffSet + }); + }; + + let log = this.$log; + + this.userbarUpdateService.getWidthThresholdRightMenu().then(function (res) { + if (res.status=="ERROR") { + log.error('userbarUpdateService: failed to get window width threshold for collapsing right menu; please make sure "window_width_threshold_right_menu" is specified in system.properties file.'); + } else { + var rightMenuCollapseWidthThreshold = parseInt(res.response.windowWidth); + if ($(window).width() new RightMenu($rootScope,$window,$log,userbarUpdateService)); +})(); diff --git a/ecomp-portal-FE/client/app/directives/right-menu/right-menu.less b/ecomp-portal-FE/client/app/directives/right-menu/right-menu.less new file mode 100644 index 00000000..bc23b614 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/right-menu/right-menu.less @@ -0,0 +1,178 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + /** + * Created by nnaffar on 1/28/16. + */ +@sidebar-width: 200px; +@transition-duration: 0.25s; +@overlayer-opacity: 0.65; + + +.close-button { + //width: @sidebar-width; + .a24r; + //.bg_u; + font-size: 3em; + line-height: 18px; + position: absolute; + cursor: pointer; + vertical-align: middle; + top: @second-level-top; + left: 0; + -webkit-font-smoothing: antialiased; + height: 53px; + z-index: 101; + //box-shadow: 0 4px 5px rgba(0, 0, 0, .2); + +} +.ecomp-right-sidebar-container{ + position: absolute; + display: block; + left: 0; + z-index: 100; + transition: left @transition-duration; + margin-top: -15px; + + .ecomp-sidebar-main { + //background-color: ; + position: absolute; + margin-top: 65px; + width: @sidebar-width; + height: 100vh; + .bg_u;//white for 1610 + //.bg_w; // gray for 1702 + box-shadow: 0 4px 5px rgba(0, 0, 0, .2); + + padding-right: 10px; + padding-left: 10px; + + .accordion-container{ + margin-top: 45px; + } + .att-accordion-font{ + font-size: .875rem; + color: #666; + display: inline-block; + font-family: arial; + + } + + .att-accordion-active{ + color: #199DDF !important; + } + + .sub-item{ + .att-accordion-font; + cursor: pointer; + height: 37px; + line-height: 37px; + padding-left: 20px; + padding-bottom: 10px; + vertical-align: middle; + width: 100%; + } + .sub-item:hover{ + .att-accordion-active; + } + + .parent-item{ + .att-accordion-font; + border-bottom: 1px solid #bbb; + cursor: pointer; + height: 37px; + line-height: 37px; + padding-bottom: 10px; + vertical-align: middle; + width: 100%; + } + .parent-item:hover{ + .att-accordion-active; + } + + } +} + +.open-sidebar { + right: 0; + transition: right .25s ease-in-out; + -moz-transition: right .25s ease-in-out; + -webkit-transition: right .25s ease-in-out; +} + +.close-sidebar { + right: -@sidebar-width; + transition: right .25s ease-in-out; + -moz-transition: right .25s ease-in-out; + -webkit-transition: right .25s ease-in-out; +} + +.content-overlayed { + position: fixed; + top: 110px; + right: 0; + bottom: 0; + left: 0; + background: none repeat scroll 0 0 rgb(242, 242, 242); + z-index: 9999; +} +.fade-animation{ + opacity: @overlayer-opacity; + transition: opacity @transition-duration ease-in-out; +} +.fade-animation.ng-hide { + opacity:0; + transition: opacity @transition-duration ease-in-out; +} + +.activeUserIcon { + transition: all .2s ease-in-out; + display: block; + margin-left: auto; margin-right: auto; height:55px; width:55px; border-radius: 50%; + +} +.activeUserIcon:hover { transform: scale(1.5); } + +.ecomp-right-sidebar-toggle{ + position: absolute; + top: 400px; + right: 35px; +} + +.open-sidebar-toggle { + // right: 0; + transition: right .25s ease-in-out; + -moz-transition: right .25s ease-in-out; + -webkit-transition: right .25s ease-in-out; +} + +.close-sidebar-toggle { + right: -36px; + transition: right .25s ease-in-out; + -moz-transition: right .25s ease-in-out; + -webkit-transition: right .25s ease-in-out; +} + +.ecomp-right-sidebar-title{ + font-family: arial; + font-size: 14px; + color: #ef6f00; + margin-bottom:20px; + text-align: center; +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/directives/right-menu/right-menu.tpl.html b/ecomp-portal-FE/client/app/directives/right-menu/right-menu.tpl.html new file mode 100644 index 00000000..39eb7087 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/right-menu/right-menu.tpl.html @@ -0,0 +1,40 @@ + +
+
+
+
Online Users
+
+
+
+ User Link +
{{user.userId}}
+
+
+
+
+
+
+ diff --git a/ecomp-portal-FE/client/app/directives/scroll-top/scroll-top.directive.js b/ecomp-portal-FE/client/app/directives/scroll-top/scroll-top.directive.js new file mode 100644 index 00000000..148660b5 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/scroll-top/scroll-top.directive.js @@ -0,0 +1,35 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +angular.module('ecompApp') + .directive('scrollTop', function () { + return { + restrict: 'A', + scope: {api: '=scrollTop'}, + link: function (scope, element) { + scope.api = scope.api || {}; + scope.api.scrollTop = function() { + element.animate({ + scrollTop : 0 + }, 500); + }; + } + }; + }); diff --git a/ecomp-portal-FE/client/app/directives/search-users/search-users.controller.js b/ecomp-portal-FE/client/app/directives/search-users/search-users.controller.js new file mode 100644 index 00000000..649b3ab2 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/search-users/search-users.controller.js @@ -0,0 +1,161 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; +(function () { + class SearchUsersCtrl { + + constructor($log, usersService,adminsService, $scope,confirmBoxService) { + + $scope.UserSearchsIsNull=false; + $scope.userExist = false; + this.scrollApi = {};//scrollTop directive + + this.showAddUser = false; + this.showSearch = true; + this.newUser ={ + firstName:'', + lastName:'', + emailAddress:'', + + middleName:'', + loginId:'', + loginPwd:'', + loginPwdCheck:'' + }; + + let activeRequests = []; + let clearReq = (req) => { + activeRequests.splice(activeRequests.indexOf(req), 1); + }; + + this.showAddUserSection = () => { + this.showAddUser = true; + this.showSearch = false; + } + + this.addNewUserFun = () => { + if (this.newUser.loginId =='' || this.newUser.loginPwd == '' || this.newUser.firstName == '' || this.newUser.lastName =='' || this.newUser.emailAddress ==''||this.newUser.loginPwd ==''){ + var warningMsg = "Please enter a value for all fields marked with *."; + confirmBoxService.showInformation(warningMsg).then(isConfirmed => {return;}); + return; + } else if (this.newUser.loginPwd != this.newUser.loginPwdCheck) { + var warningMsg = "Passwords do not match, please try again."; + confirmBoxService.showInformation(warningMsg).then(isConfirmed => {return;}); + return; + } + else { + // check password length complexity. + var warningMsg = adminsService.isComplexPassword(this.newUser.loginPwd); + if (warningMsg != null) { + confirmBoxService.showInformation(warningMsg).then(isConfirmed => {return;}); + return; + } + } // password + + adminsService.addNewUser(this.newUser,'Yes').then(res=> { + + if(res.message == 'Record already exist'){ + + this.showAddUser = true; + this.showSearch = false; + $scope.userExist = true; + + }else{ + + $scope.userExist = false; + this.selectedUser = this.newUser; + this.selectedUser.orgUserId = this.newUser.loginId; + this.searchUsersResults = []; + this.searchUsersResults.push(this.newUser); + this.showAddUser = false; + this.showSearch = true; + this.newUser ={ + firstName:'', + lastName:'', + emailAdress:'', + middleName:'', + loginId:'', + loginPwd:'', + loginPwdCheck:'' + }; + this.searchUserString =''; + $scope.UserSearchsIsNull = false; + } + + + }).catch(err=> { + $log.error('adminsService: addNewUser error:: ', err); + // $scope.errMsg=err; + confirmBoxService.showInformation('Add New User failed: ' + err); + + }).finally(() => { + //this.isLoadingTable = false; + + }); + } + + this.searchUsers = () => { + this.isLoading = true; + if(this.searchUsersInProgress){ + return; + } + this.selectedUser = null; + this.searchUsersInProgress = true; + this.searchUsersResults = null; + + let searchUsersReq = usersService.searchUsers(this.searchUserString); + activeRequests.push(searchUsersReq); + searchUsersReq.promise().then(usersList => { + $log.debug('searchUsers found the following users: ', JSON.stringify(usersList)); + this.searchUsersResults = usersList; + $scope.UserSearchsIsNull=false; + }).catch(err => { + $log.error('SearchUsersCtrl.searchUsers: ' + err); + $scope.UserSearchsIsNull=true; + }).finally(() => { + this.scrollApi.scrollTop(); + this.searchUsersInProgress = false; + clearReq(searchUsersReq); + this.isLoading = false; + }); + }; + + let init = () => { + this.isLoading = false; + this.searchUsersInProgress = false; + }; + + this.setSelectedUser = user => { + this.selectedUser = user; + }; + + init(); + + $scope.$on('$destroy', () => { + activeRequests.forEach(req => { + req.cancel(); + }); + }); + } + } + SearchUsersCtrl.$inject = ['$log', 'usersService','adminsService', '$scope','confirmBoxService']; + angular.module('ecompApp').controller('SearchUsersCtrl', SearchUsersCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/directives/search-users/search-users.controller.spec.js b/ecomp-portal-FE/client/app/directives/search-users/search-users.controller.spec.js new file mode 100644 index 00000000..96f5b0df --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/search-users/search-users.controller.spec.js @@ -0,0 +1,176 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +//'use strict'; +// +//describe('Controller: NewAdminCtrl ', () => { +// beforeEach(module('ecompApp')); +// +// //destroy $http default cache before starting to prevent the error 'default cache already exists' +// beforeEach(inject((_CacheFactory_)=> { +// _CacheFactory_.destroyAll(); +// })); +// +// +// let newCtrl, $controller, $q, $rootScope, $log; +// +// beforeEach(inject((_$controller_, _$q_, _$rootScope_, _$log_)=> { +// [$controller, $q, $rootScope, $log] = [_$controller_, _$q_, _$rootScope_, _$log_]; +// })); +// +// let deferredUsersList, deferredAdminAppsRoles, deferredUpdateRolesRes; +// let usersServiceMock, adminsServiceMock; +// beforeEach(()=> { +// [deferredUsersList, deferredAdminAppsRoles, deferredUpdateRolesRes] = [$q.defer(), $q.defer(), $q.defer()]; +// +// //usersServiceMock = jasmine.createSpyObj('usersServiceMock', ['searchUsers']); +// usersServiceMock = { +// searchUsers: () => { +// var promise = () => {return deferredUsersList.promise}; +// var cancel = jasmine.createSpy(); +// return { +// promise: promise, +// cancel: cancel +// } +// } +// }; +// +// adminsServiceMock = jasmine.createSpyObj('adminsServiceMock', ['getAdminAppsRoles', 'updateAdminAppsRoles']); +// +// //usersServiceMock.searchUsers.and.returnValue(deferredUsersList.promise); +// adminsServiceMock.getAdminAppsRoles.and.returnValue(deferredAdminAppsRoles.promise); +// adminsServiceMock.updateAdminAppsRoles.and.returnValue(deferredUpdateRolesRes.promise); +// +// newCtrl = $controller('NewAdminModalCtrl', { +// $log: $log, +// usersService: usersServiceMock, +// adminsService: adminsServiceMock, +// $scope: $rootScope +// }); +// }); +// +// it('should init default values when loading the controller', ()=> { +// //expect(newCtrl.searchUsersInProgress).toBe(false); +// expect(newCtrl.dialogState).toBe(1); +// expect(newCtrl.selectedUser).toBe(null); +// }); +// +// it('should populate retrieved users when search users service returns a list ', ()=> { +// //spyOn(usersServiceMock, 'searchUsers'); +// let usersListRes = [{user: 1}, {user: 2}]; +// newCtrl.searchUserString = 'some user name'; +// deferredUsersList.resolve(usersListRes); +// newCtrl.searchUsers(); +// $rootScope.$apply(); +// +// //expect(usersServiceMock.searchUsers).toHaveBeenCalledWith(newCtrl.searchUserString); +// expect(newCtrl.searchUsersResults).toEqual(usersListRes); +// expect(newCtrl.searchUsersInProgress).toBe(false); +// }); +// +// it('should log the error when search users fails', ()=> { +// spyOn($log, 'error'); +// deferredUsersList.reject('oh snap!'); +// newCtrl.searchUsers(); +// $rootScope.$apply(); +// expect($log.error).toHaveBeenCalled(); +// }); +// +// it('should populate admin apps roles and move to the next screen when adminsService.getAdminAppsRoles succeeded', ()=> { +// let userApps = {appsRoles: [{id: 1, isAdmin: false}, {id: 2, isAdmin: true}]}; +// deferredAdminAppsRoles.resolve(userApps); +// +// newCtrl.searchUsersInProgress = false; +// newCtrl.selectedUser = {userId: 'userId'}; +// +// newCtrl.getAdminAppsRoles(); +// $rootScope.$apply(); +// +// expect(adminsServiceMock.getAdminAppsRoles).toHaveBeenCalledWith(newCtrl.selectedUser.userId); +// expect(newCtrl.adminAppsRoles).toEqual(userApps.appsRoles); +// expect(newCtrl.dialogState).toBe(2); +// }); +// +// it('should log the error when adminsService.getAdminAppsRoles fails', ()=> { +// spyOn($log, 'error'); +// deferredAdminAppsRoles.reject('some error'); +// +// newCtrl.searchUsersInProgress = false; +// newCtrl.selectedUser = {userId: 'userId'}; +// +// newCtrl.getAdminAppsRoles(); +// $rootScope.$apply(); +// +// expect($log.error).toHaveBeenCalled(); +// }); +// it('should log the error when trying to getAdminAppsRoles without selecting user ', ()=> { +// spyOn($log, 'error'); +// +// newCtrl.searchUsersInProgress = false; +// newCtrl.selectedUser = null; +// +// newCtrl.getAdminAppsRoles(); +// $rootScope.$apply(); +// +// expect($log.error).toHaveBeenCalled(); +// }); +// //it('should setSelectedUser when choosing user', ()=> { +// // +// //}); +// //it('should set isAdmin as false when removing app from the administrated apps list', ()=> { +// //}); +// it('should set isAdmin as true when adding app via the dropdown menu', ()=> { +// newCtrl.adminAppsRoles = [{id: 1, isAdmin: false},{id: 2, isAdmin: true}]; +// //simulate UI change +// $rootScope.$apply('newAdmin.selectedNewApp = null'); +// $rootScope.$apply('newAdmin.selectedNewApp = {id: 1, isAdmin: true}'); +// +// expect(newCtrl.adminAppsRoles[0].isAdmin).toBe(true); +// expect(newCtrl.selectedNewApp).toBe(null); +// }); +// +// it('should close the modal when updating apps roles succeeded', ()=> { +// $rootScope.closeThisDialog = () => {}; +// spyOn($rootScope,'closeThisDialog'); +// +// newCtrl.selectedUser = {userId: 'userId'}; +// newCtrl.adminAppsRoles = [{id: 1}]; +// +// deferredUpdateRolesRes.resolve(); +// newCtrl.updateAdminAppsRoles(); +// $rootScope.$apply(); +// +// expect(adminsServiceMock.updateAdminAppsRoles).toHaveBeenCalledWith({userId: newCtrl.selectedUser.userId, appsRoles: newCtrl.adminAppsRoles}); +// expect($rootScope.closeThisDialog).toHaveBeenCalled(); +// }); +// it('should log the error when updating apps roles fails', ()=> { +// newCtrl.selectedUser = {userId: 'userId'}; +// newCtrl.adminAppsRoles = [{id: 1}]; +// +// spyOn($log,'error'); +// deferredUpdateRolesRes.reject(); +// newCtrl.updateAdminAppsRoles(); +// $rootScope.$apply(); +// expect($log.error).toHaveBeenCalled(); +// }); +// //it('should display the add admin dropdown when clicking the add button', ()=> { +// //}); +// +//}); diff --git a/ecomp-portal-FE/client/app/directives/search-users/search-users.directive.js b/ecomp-portal-FE/client/app/directives/search-users/search-users.directive.js new file mode 100644 index 00000000..4e5809f9 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/search-users/search-users.directive.js @@ -0,0 +1,34 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +angular.module('ecompApp') + .directive('searchUsers', function () { + return { + restrict: 'E', + templateUrl: 'app/directives/search-users/search-users.tpl.html', + controller: 'SearchUsersCtrl', + controllerAs: 'searchUsers', + bindToController: true, + scope: { + selectedUser: '=', + searchTitle: '@' + } + }; + }); diff --git a/ecomp-portal-FE/client/app/directives/search-users/search-users.less b/ecomp-portal-FE/client/app/directives/search-users/search-users.less new file mode 100644 index 00000000..9c6de2b4 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/search-users/search-users.less @@ -0,0 +1,154 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .search-users-directive{ + .title { + .n18r; + border-bottom: @a 3px solid; + + } + + .add-user-section{ + margin-top:0px; + margin-left:10px; + } + + .input-text-new-user { + font-style: italic; + padding: 7px 10px; + width: 200px !important; + display: inline-block; + position: relative; + margin-bottom: 10px; + border-radius: 6px; + border: 1px solid #d8d8d8; + height: 32px; + border-color: slategrey !important; + } + + .input-new-user-div{ + + margin-left:10px; + } + + .add-user-button { + cursor: pointer; + float:right; + width: 120px; + + margin-left : 5px; + + .btn-blue; + + line-height: 32px; + height: 29px; + text-align: center; + vertical-align: middle; + line-height: 28px; + + &::before { + .ico_add_user; + content: '\f211'; + font-family: "Ionicons"; + vertical-align: middle; + display: inline-block; + margin-right: 8px; + line-height: 16px; + } + } + + .main { + margin: 16px; + .search-instructions { + .n14r; + margin-bottom: 8px; + } + .search { + .input-field { + display: inline-block; + width: 250px; + height: 30px; + } + .search-button { + .btn-blue; + width: 90px; + display: inline-block; + float: right; + } + } + + .search-results { + margin-top: 10px; + .results-title { + .n14r; + margin-bottom: 8px; + } + + .results-container { + height: 208px; + overflow-y: auto; + .user { + padding-left: 10px; + padding-top: 6px; + height: 48px; + + border-top: 1px solid @p; + border-right: 1px solid @p; + border-left: 1px solid @p; + + &:last-child { + border-bottom: 1px solid @p; + } + + cursor: pointer; + &:hover { + background-color: @v; + } + + &.selected { + background-color: @v; + } + + .main-name { + .n14r; + + } + .sub-job-title { + .p13r; + + } + } + + } + + } + .error-text { + margin-top: 25px; + font-weight: 400; + font-size: 16px; + text-align: left; + color: @err; + } + + .no-user-found { + margin-top: 16px; + .n14r; + } + } +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/directives/search-users/search-users.tpl.html b/ecomp-portal-FE/client/app/directives/search-users/search-users.tpl.html new file mode 100644 index 00000000..6c275693 --- /dev/null +++ b/ecomp-portal-FE/client/app/directives/search-users/search-users.tpl.html @@ -0,0 +1,144 @@ + +
+
+
+
+
+
Enter first name, last name or User ID
+ + + +
+
+
+
+
+
+ + +
+
+
+
+
+
+
+ +
+ No match found. +
+ +
+ No users found +
+
+ + +
+
+
+
*First Name
+ +
+
+
Middle Name
+ +
+
+
*Last Name
+ +
+
+
*Email Address ID
+ +
+
+
*Login ID
+ +
+
+
*Login Password
+ +
+
+
*Confirm Login Password
+ +
+
+ The passwords do not match. Try again. + +
+
+ User with same loginId already exists. Try again. + +
+
+ +
+ + +
+ +
+ + + diff --git a/ecomp-portal-FE/client/app/filters/elipsis/elipsis.filter.js b/ecomp-portal-FE/client/app/filters/elipsis/elipsis.filter.js new file mode 100644 index 00000000..310649b3 --- /dev/null +++ b/ecomp-portal-FE/client/app/filters/elipsis/elipsis.filter.js @@ -0,0 +1,38 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +angular.module('ecompApp') + .filter('elipsis', () => { + return (val, limit) => { + if (!val) { + return val; + } + limit = parseInt(limit); + + if (!limit || val.length <= limit) { + return val; + } + + val = val.substr(0, limit); + + return val + '...'; + } + }); diff --git a/ecomp-portal-FE/client/app/filters/elipsis/elipsis.filter.spec.js b/ecomp-portal-FE/client/app/filters/elipsis/elipsis.filter.spec.js new file mode 100644 index 00000000..a9dc7836 --- /dev/null +++ b/ecomp-portal-FE/client/app/filters/elipsis/elipsis.filter.spec.js @@ -0,0 +1,58 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +describe('Filter: elipsis', function () { + 'use strict'; + let filter; + + beforeEach(function () { + module('ecompApp'); + }); + + beforeEach(inject((_CacheFactory_)=> { + _CacheFactory_.destroyAll(); + + })); + + it('should trim the text and return it with ... when the text length is greater than the limit"', inject(function (_$filter_) { + filter = _$filter_; + // given + let text = `Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore + et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex + ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat + nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim + id est laborum`; + let limit = 50; + + var result = filter('elipsis')(text, limit); + + expect(result).toBe(text.substr(0, 50) + '...'); + })); + + it("should return the exact string where there's no limit", inject(function (_$filter_) { + filter = _$filter_; + + let text = 'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore'; + + let result = filter('elipsis')(text); + + expect(result).toEqual(text); + })); + +}); diff --git a/ecomp-portal-FE/client/app/filters/trusted-url/trusted-url.filter.js b/ecomp-portal-FE/client/app/filters/trusted-url/trusted-url.filter.js new file mode 100644 index 00000000..a6e70d69 --- /dev/null +++ b/ecomp-portal-FE/client/app/filters/trusted-url/trusted-url.filter.js @@ -0,0 +1,26 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +angular.module('ecompApp') + .filter('trusted', function($sce){ + return function(url) { + return $sce.trustAsResourceUrl(url); + }; + }); diff --git a/ecomp-portal-FE/client/app/router.js b/ecomp-portal-FE/client/app/router.js new file mode 100644 index 00000000..8af5f171 --- /dev/null +++ b/ecomp-portal-FE/client/app/router.js @@ -0,0 +1,528 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +angular.module('ecompApp') + .config($stateProvider => { + $stateProvider + .state('root', { + abstract: true, + views: { + 'header@': { + templateUrl: 'app/views/header/header.tpl.html', + controller: 'HeaderCtrl', + controllerAs: 'header' + }, + 'tabbar@': { + templateUrl: 'app/views/tabs/tabs.tpl.html', + controller: 'TabsCtrl', + controllerAs: 'tabsHome' + }, + 'sidebar@':{ + templateUrl: 'app/views/sidebar/sidebar.tpl.html', + controller: 'SidebarCtrl', + controllerAs: 'sidebar' + }, + 'userbar@':{ + templateUrl: 'app/views/userbar/userbar.tpl.html', + controller: 'UserbarCtrl', + controllerAs: 'userbar' + }, + 'footer@': { + templateUrl: 'app/views/footer/footer.tpl.html', + controller: 'FooterCtrl', + controllerAs: 'footer' } + } +// }).state('root.applicationsHome', { +// url: '/applicationsHome', +// views: { +// 'content@': { +// templateUrl: 'app/views/home/applications-home/applications-home.tpl.html', +// controller: 'ApplicationsHomeCtrl', +// controllerAs: 'applicationsHome' +// } +// } + }).state('root.applicationsHome', { + url: '/applicationsHome', + views: { + 'content@': { + templateUrl: 'app/views/dashboard/dashboard.tpl.html', + controller: 'DashboardCtrl', + controllerAs: 'dashboard' + } + } + }).state('root.appCatalog', { + url: '/appCatalog', + views: { + 'content@': { + templateUrl: 'app/views/catalog/catalog.tpl.html', + controller: 'CatalogCtrl', + controllerAs: 'catalog' + } + } + }).state('root.widgetsHome', { + url: '/widgetsHome', + views: { + 'content@': { + templateUrl: 'app/views/home/widgets-home/widgets-home.tpl.html', + controller: 'WidgetsHomeCtrl', + controllerAs: 'widgetsHome' + } + } + }).state('root.admins', { + url: '/admins', + views: { + 'content@': { + templateUrl: 'app/views/admins/admins.tpl.html', + controller: 'AdminsCtrl', + controllerAs: 'admins' + } + } + }).state('root.users', { + url: '/users', + views: { + 'content@': { + templateUrl: 'app/views/users/users.tpl.html', + controller: 'UsersCtrl', + controllerAs: 'users' + } + } + }).state('root.applications', { + url: '/applications', + views: { + 'content@': { + templateUrl: 'app/views/applications/applications.tpl.html', + controller: 'ApplicationsCtrl', + controllerAs: 'apps' + } + } + }).state('root.functionalMenu', { + url: '/functionalMenu', + views: { + 'content@': { + templateUrl: 'app/views/functionalMenu/functionalMenu.tpl.html', + controller: 'FunctionalMenuCtrl', + controllerAs: 'functionalMenu' + } + } + }).state('root.getAccess', { + url: '/getAccess', + params: { + appName: null, + }, + views: { + 'content@': { + templateUrl: 'app/views/support/get-access/get-access.tpl.html', + controller: 'GetAccessCtrl', + controllerAs: 'access' + } + } + }).state('root.contactUs', { + url: '/contactUs', + views: { + 'content@': { + templateUrl: 'app/views/support/contact-us/contact-us.tpl.html', + controller: 'ContactUsCtrl', + controllerAs: 'contact' + } + } + }).state('root.widgets', { + url: '/widgets', + views: { + 'content@': { + templateUrl: 'app/views/widgets/widgets.tpl.html', + controller: 'WidgetsCtrl', + controllerAs: 'widgets' + } + } + }).state('root.portalAdmins', { + url: '/portalAdmins', + views: { + 'content@': { + templateUrl: 'app/views/portal-admin/portal-admin.tpl.html', + controller: 'PortalAdminsCtrl', + controllerAs: 'portalAdmin' + } + } + }).state('root.error404', { + url: '/error404', + views: { + 'content@': { + templateUrl: 'app/views/errors/error.404.tpl.html', + controller: 'Error404Ctrl', + controllerAs: 'error404' + } + } + }).state('noUserError', { + url: '/noUserError', + views: { + 'error@': { + templateUrl: 'app/views/errors/error.tpl.html', + controller: 'ErrorCtrl', + controllerAs: 'error' + } + } + }).state('unKnownError', { + url: '/unKnownError', + views: { + 'error@': { + templateUrl: 'app/views/errors/error.tpl.html', + controller: 'ErrorCtrl', + controllerAs: 'error' + } + } + }).state('root.kpidash', { + url: '/kpidash', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DCAE/DCAE_KPI.html', + controller: 'DCAE_Ctrl_KPI' + } + } + }).state('root.kpidash_DCAE', { + //url: '/kpidash_DCAE', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DCAE/DCAE_KPI.html', + controller: 'DCAE_Ctrl_KPI' + } + } + }).state('root.kpidash_DCAE_KPI', { + //url: '/kpidash_DCAE_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DCAE/DCAE_KPI.html', + controller: 'DCAE_Ctrl_KPI' + } + } + }).state('root.kpidash_DCAE_UserDefinedKPI', { + //url: '/kpidash_DCAE_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DCAE/DCAE_UserDefinedKPI.html', + controller: 'DCAE_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_DCAE_Metrics', { + //url: '/kpidash_DCAE_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DCAE/DCAE_Metrics.html', + controller: 'DCAE_Ctrl_Metrics' + } + } + }).state('root.kpidash_ECOMP', { + //url: '/kpidash_ECOMP', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ECOMP.html', + controller: 'ECOMP_Ctrl' + } + } + }).state('root.kpidash_AAI', { + //url: '/kpidash_AAI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/AAI/AAI_KPI.html', + controller: 'AAI_Ctrl_KPI' + } + } + }).state('root.kpidash_AAI_KPI', { + //url: '/kpidash_AAI_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/AAI/AAI_KPI.html', + controller: 'AAI_Ctrl_KPI' + } + } + }).state('root.kpidash_AAI_UserDefinedKPI', { + //url: '/kpidash_AAI_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/AAI/AAI_UserDefinedKPI.html', + controller: 'AAI_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_AAI_Metrics', { + //url: '/kpidash_AAI_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/AAI/AAI_Metrics.html', + controller: 'AAI_Ctrl_Metrics' + } + } + }).state('root.kpidash_APPC', { + //url: '/kpidash_APPC', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/APPC/APPC_KPI.html', + controller: 'APPC_Ctrl_KPI' + } + } + }).state('root.kpidash_APPC_KPI', { + //url: '/kpidash_APPC_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/APPC/APPC_KPI.html', + controller: 'APPC_Ctrl_KPI' + } + } + }).state('root.kpidash_APPC_UserDefinedKPI', { + //url: '/kpidash_APPC_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/APPC/APPC_UserDefinedKPI.html', + controller: 'APPC_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_APPC_Metrics', { + //url: '/kpidash_APPC_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/APPC/APPC_Metrics.html', + controller: 'APPC_Ctrl_Metrics' + } + } + }).state('root.kpidash_ASDC', { + //url: '/kpidash_ASDC', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ASDC/ASDC_KPI.html', + controller: 'ASDC_Ctrl_KPI' + } + } + }).state('root.kpidash_ASDC_KPI', { + //url: '/kpidash_ASDC_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ASDC/ASDC_KPI.html', + controller: 'ASDC_Ctrl_KPI' + } + } + }).state('root.kpidash_ASDC_UserDefinedKPI', { + //url: '/kpidash_ASDC_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ASDC/ASDC_UserDefinedKPI.html', + controller: 'ASDC_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_ASDC_Metrics', { + //url: '/kpidash_ASDC_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ASDC/ASDC_Metrics.html', + controller: 'ASDC_Ctrl_Metrics' + } + } + }).state('root.kpidash_Closedloop', { + //url: '/kpidash_Closedloop', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/Closedloop/Closedloop_KPI.html', + controller: 'Closedloop_Ctrl_KPI' + } + } + }).state('root.kpidash_Closedloop_KPI', { + //url: '/kpidash_Closedloop_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/Closedloop/Closedloop_KPI.html', + controller: 'Closedloop_Ctrl_KPI' + } + } + }).state('root.kpidash_Closedloop_UserDefinedKPI', { + //url: '/kpidash_Closedloop_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/Closedloop/Closedloop_UserDefinedKPI.html', + controller: 'Closedloop_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_Closedloop_Metrics', { + //url: '/kpidash_Closedloop_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/Closedloop/Closedloop_Metrics.html', + controller: 'Closedloop_Ctrl_Metrics' + } + } + }).state('root.kpidash_DMaaP', { + //url: '/kpidash_DMaaP', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DMaaP/DMaaP_KPI.html', + controller: 'DMaaP_Ctrl_KPI' + } + } + }).state('root.kpidash_DMaaP_KPI', { + //url: '/kpidash_DMaaP_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DMaaP/DMaaP_KPI.html', + controller: 'DMaaP_Ctrl_KPI' + } + } + }).state('root.kpidash_DMaaP_UserDefinedKPI', { + //url: '/kpidash_DMaaP_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DMaaP/DMaaP_UserDefinedKPI.html', + controller: 'DMaaP_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_DMaaP_Metrics', { + //url: '/kpidash_DMaaP_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/DMaaP/DMaaP_Metrics.html', + controller: 'DMaaP_Ctrl_Metrics' + } + } + }).state('root.kpidash_ECOMP_Portal', { + //url: '/kpidash_ECOMP_Portal', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ECOMP_Portal/ECOMP_Portal_KPI.html', + controller: 'ECOMP_Portal_Ctrl_KPI' + } + } + }).state('root.kpidash_ECOMP_Portal_KPI', { + //url: '/kpidash_ECOMP_Portal_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ECOMP_Portal/ECOMP_Portal_KPI.html', + controller: 'ECOMP_Portal_Ctrl_KPI' + } + } + }).state('root.kpidash_ECOMP_Portal_UserDefinedKPI', { + //url: '/kpidash_ECOMP_Portal_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ECOMP_Portal/ECOMP_Portal_UserDefinedKPI.html', + controller: 'ECOMP_Portal_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_ECOMP_Portal_Metrics', { + //url: '/kpidash_ECOMP_Portal_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/ECOMP_Portal/ECOMP_Portal_Metrics.html', + controller: 'ECOMP_Portal_Ctrl_Metrics' + } + } + }).state('root.kpidash_InfrastructurePortal', { + //url: '/kpidash_InfrastructurePortal', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/InfrastructurePortal/InfrastructurePortal_KPI.html', + controller: 'InfrastructurePortal_Ctrl_KPI' + } + } + }).state('root.kpidash_InfrastructurePortal_KPI', { + //url: '/kpidash_InfrastructurePortal_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/InfrastructurePortal/InfrastructurePortal_KPI.html', + controller: 'InfrastructurePortal_Ctrl_KPI' + } + } + }).state('root.kpidash_InfrastructurePortal_UserDefinedKPI', { + //url: '/kpidash_InfrastructurePortal_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/InfrastructurePortal/InfrastructurePortal_UserDefinedKPI.html', + controller: 'InfrastructurePortal_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_InfrastructurePortal_Metrics', { + //url: '/kpidash_InfrastructurePortal_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/InfrastructurePortal/InfrastructurePortal_Metrics.html', + controller: 'InfrastructurePortal_Ctrl_Metrics' + } + } + }).state('root.kpidash_MSO', { + //url: '/kpidash_MSO', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/MSO/MSO_KPI.html', + controller: 'MSO_Ctrl_KPI' + } + } + }).state('root.kpidash_MSO_KPI', { + //url: '/kpidash_MSO_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/MSO/MSO_KPI.html', + controller: 'MSO_Ctrl_KPI' + } + } + }).state('root.kpidash_MSO_UserDefinedKPI', { + //url: '/kpidash_MSO_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/MSO/MSO_UserDefinedKPI.html', + controller: 'MSO_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_MSO_Metrics', { + //url: '/kpidash_MSO_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/MSO/MSO_Metrics.html', + controller: 'MSO_Ctrl_Metrics' + } + } + }).state('root.kpidash_Policy', { + //url: '/kpidash_Policy', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/Policy/Policy_KPI.html', + controller: 'Policy_Ctrl_KPI' + } + } + }).state('root.kpidash_Policy_KPI', { + //url: '/kpidash_Policy_KPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/Policy/Policy_KPI.html', + controller: 'Policy_Ctrl_KPI' + } + } + }).state('root.kpidash_Policy_UserDefinedKPI', { + //url: '/kpidash_Policy_UserDefinedKPI', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/Policy/Policy_UserDefinedKPI.html', + controller: 'Policy_Ctrl_UserDefinedKPI' + } + } + }).state('root.kpidash_Policy_Metrics', { + //url: '/kpidash_Policy_Metrics', + views: { + 'content@': { + templateUrl: 'kpi-dashboard/views/Policy/Policy_Metrics.html', + controller: 'Policy_Ctrl_Metrics' + } + } + }); + }); diff --git a/ecomp-portal-FE/client/app/services/admins/admins.service.js b/ecomp-portal-FE/client/app/services/admins/admins.service.js new file mode 100644 index 00000000..ee742af8 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/admins/admins.service.js @@ -0,0 +1,176 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +(function () { + class AdminsService { + constructor($q, $log, $http, conf,uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + } + + getAccountAdmins() { + let deferred = this.$q.defer(); + this.$log.info('AdminsService::get all applications admins list'); + this.$http({ + method: "GET", + cache: false, + url: this.conf.api.accountAdmins, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }) + .then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("AdminsService::getAccountAdmins Failed"); + } else { + this.$log.info('AdminsService::getAccountAdmins Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + + return deferred.promise; + } + + getAdminAppsRoles(orgUserId) { + let deferred = this.$q.defer(); + this.$log.info('AdminsService::getAdminAppsRoles.adminAppsRoles'); + + this.$http({ + method: "GET", + url: this.conf.api.adminAppsRoles, + params: {orgUserId: orgUserId}, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("AdminsService::getAdminAppsRoles.adminAppsRoles Failed"); + } else { + this.$log.info('AdminsService::getAdminAppsRoles.adminAppsRoles Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + + return deferred.promise; + } + + updateAdminAppsRoles(newAdminAppRoles) { + let deferred = this.$q.defer(); + this.$log.info('AdminsService::updateAdminAppsRoles'); + this.$http({ + method: "PUT", + url: this.conf.api.adminAppsRoles, + data: newAdminAppRoles, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + deferred.resolve(res.data); + }) + .catch( status => { + deferred.reject(status); + }); + + return deferred.promise; + } + + addNewUser(newUser,checkDuplicate) { + // this.$log.info(newContactUs) + let deferred = this.$q.defer(); + // this.$log.info('ContactUsService:: add Contact Us' + JSON.stringify(newContactUs)); + + var newUserObj={ + firstName:newUser.firstName, + middleInitial:newUser.middleName, + lastName:newUser.lastName, + email:newUser.emailAddress, + loginId:newUser.loginId, + loginPwd:newUser.loginPwd, + }; + this.$http({ + url: this.conf.api.saveNewUser + "?isCheck=" + checkDuplicate, + method: 'POST', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + }, + data: newUserObj + }).then(res => { + // this.$log.info('ContactUsService:: add Contact Us res' ,res); + // If response comes back as a redirected HTML page which IS NOT a success + if (res==null || Object.keys(res.data).length == 0 || res.data.message == 'failure') { + deferred.reject("Add new User failed"); + this.$log.error('adminService:: add New User failed'); + } else { + deferred.resolve(res.data); + } + }).catch(errRes => { + deferred.reject(errRes); + }); + return deferred.promise; + } + + /** + * Tests the specified password against complexity requirements. + * Returns an explanation message if the test fails; null if it passes. + */ + isComplexPassword(str) { + let minLength = 8; + let message = 'Password is too simple. Minimum length is '+ minLength + ', ' + + 'and it must use letters, digits and special characters.'; + if (str == null) + return message; + + let hasLetter = false; + let hasDigit = false; + let hasSpecial = false; + var code, i, len; + for (i = 0, len = str.length; i < len; i++) { + code = str.charCodeAt(i); + if (code > 47 && code < 58) // numeric (0-9) + hasDigit = true; + else if ((code > 64 && code < 91) || (code > 96 && code < 123)) // A-Z, a-z + hasLetter = true; + else + hasSpecial = true; + } // for + + if (str.length < minLength || !hasLetter || !hasDigit || !hasSpecial) + return message; + + // All is well. + return null; + } + + } + AdminsService.$inject = ['$q', '$log', '$http', 'conf','uuid4']; + angular.module('ecompApp').service('adminsService', AdminsService) +})(); diff --git a/ecomp-portal-FE/client/app/services/applications/applications.service.js b/ecomp-portal-FE/client/app/services/applications/applications.service.js new file mode 100644 index 00000000..38cfd650 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/applications/applications.service.js @@ -0,0 +1,346 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +(function () { + class ApplicationsService { + constructor($q, $log, $http, conf, uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + } + + getPersUserApps() { + let deferred = this.$q.defer(); + // this.$log.info('ApplicationsService::getPersUserApps'); + this.$http.get(this.conf.api.persUserApps, + { + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }) + .then( res => { + // If response comes back as a redirected HTML page which IS NOT a success + // But don't declare an empty list to be an error. + if (res == null || res.data == null) { + deferred.reject("ApplicationsService::getPersUserApps Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getUserApps(){ + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService::getUserApps'); + this.$http.get(this.conf.api.userApps, + { + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }) + .then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("ApplicationsService::getUserApps Failed"); + } else { + this.$log.info('ApplicationsService::getUserApps Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + + return deferred.promise; + } + + getAvailableApps() { + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService::getAvailableApps'); + this.$http( + { + method: "GET", + url: this.conf.api.availableApps, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }) + .then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("ApplicationsService::getAvailableApps Failed"); + } else { + this.$log.info('ApplicationsService::getAvailableApps Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + + return deferred.promise; + } + + getAdminApps(){ + let canceller = this.$q.defer(); + let isActive = false; + + let cancel = () => { + if(isActive){ + this.$log.debug('ApplicationsService::getAdminApps: canceling the request'); + canceller.resolve(); + } + }; + + let promise = () => { + isActive = true; + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService::getAdminApps: starting'); + this.$http({method: "GET", + url: this.conf.api.adminApps, + cache: false, + timeout: canceller.promise, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + isActive = false; + if (Object.keys(res.data).length == 0) { + deferred.reject("ApplicationsService::adminApps Failed"); + } else { + this.$log.info('ApplicationsService::adminApps Succeeded'); + deferred.resolve(res.data); + } + }) + .catch(status => { + isActive = false; + deferred.reject(status); + }); + return deferred.promise; + }; + + return { + cancel: cancel, + promise: promise + }; + } + + getAppsForSuperAdminAndAccountAdmin(){ + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService::getAppsForSuperAdminAndAccountAdmin'); + this.$http({method: "GET", + url: this.conf.api.appsForSuperAdminAndAccountAdmin, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("ApplicationsService::getAppsForSuperAdminAndAccountAdmin Failed"); + } else { + this.$log.info('ApplicationsService::getAppsForSuperAdminAndAccountAdmin Succeeded'); + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getAdminAppsSimpler(){ + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService::getAdminApps'); + this.$http({method: "GET", + url: this.conf.api.adminApps, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("ApplicationsService::getAdminApps Failed"); + } else { + this.$log.info('ApplicationsService::getAdminApps Succeeded'); + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getOnboardingApps(){ + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService::getOnboardingApps'); + + this.$http.get(this.conf.api.onboardingApps, + { + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }) + .then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("ApplicationsService::getOnboardingApps Failed"); + } else { + this.$log.info('ApplicationsService::getOnboardingApps Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + + return deferred.promise; + } + + addOnboardingApp(newApp){ + let deferred = this.$q.defer(); + this.$log.info('applications-service::addOnboardingApp'); + this.$log.debug('applications-service::addOnboardingApp with:', newApp); + + this.$http({ + method: "POST", + url: this.conf.api.onboardingApps, + data: newApp, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("ApplicationsService::addOnboardingApp Failed"); + } else { + this.$log.info('ApplicationsService::addOnboardingApp Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + return deferred.promise; + } + + updateOnboardingApp(appData){ + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService::addOnboardingApp'); + if(!appData.id){ + this.$log.error('ApplicationsService::addOnboardingApp: App id not found!'); + return deferred.reject('App id not found'); + } + + this.$http({ + method: "PUT", + url: this.conf.api.onboardingApps, + data: appData, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("ApplicationsService::updateOnboardingApp Failed"); + } else { + this.$log.info('ApplicationsService::updateOnboardingApp Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + return deferred.promise; + } + + deleteOnboardingApp(appId) { + let deferred = this.$q.defer(); + let url = this.conf.api.onboardingApps + '/' + appId; + + this.$log.info('applications.service::deleteOnboardingApp' +appId); + + this.$http({ + method: "DELETE", + url: url, + cache: false, + data:'', + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("applications.service::deleteOnboardingApp Failed"); + } else { + this.$log.info('applications.service::deleteOnboardingApp succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(errRes => { + deferred.reject(errRes); + }); + return deferred.promise; + } + + getTopMenuData(selectedApp) { + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService:getTopMenuData'); + this.$log.debug('ApplicationsService:getTopMenuData with:', selectedApp); + + } + + ping(){ + let deferred = this.$q.defer(); + this.$log.info('ApplicationsService::ping: '); + + this.$http.get(this.conf.api.ping, + { + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }) + .success( res => { + if (Object.keys(res).length == 0) { + deferred.reject("ApplicationsService::ping: Failed"); + } else { + this.$log.info('ApplicationsService::ping: Succeeded'); + deferred.resolve(res); + } + }) + .error( status => { + deferred.reject(status); + }); + + return deferred.promise; + } + } + ApplicationsService.$inject = ['$q', '$log', '$http', 'conf','uuid4']; + angular.module('ecompApp').service('applicationsService', ApplicationsService) +})(); diff --git a/ecomp-portal-FE/client/app/services/catalog/catalog.service.js b/ecomp-portal-FE/client/app/services/catalog/catalog.service.js new file mode 100644 index 00000000..2ad594a2 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/catalog/catalog.service.js @@ -0,0 +1,95 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +(function () { + class CatalogService { + + constructor($q, $log, $http, conf, uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + } + + getAppCatalog() { + let deferred = this.$q.defer(); + this.$http( + { + method: "GET", + url: this.conf.api.appCatalog, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }) + .then( res => { + // Detect non-JSON + if (res == null || res.data == null) { + deferred.reject("CatalogService::getAppCatalog Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch( status => { + this.$log.error('CatalogService:getAppCatalog failed: ' + status); + deferred.reject(status); + }); + return deferred.promise; + } + + // Expects an object with fields matching model class AppCatalogSelection: + // appId (number), select (boolean), pending (boolean). + updateAppCatalog(appData) { + let deferred = this.$q.defer(); + // Validate the request, maybe this is overkill + if (appData == null || appData.appId == null || appData.select == null) { + var msg = 'CatalogService::updateAppCatalog: field appId and/or select not found'; + this.$log.error(msg); + return deferred.reject(msg); + } + this.$http({ + method: "PUT", + url: this.conf.api.appCatalog, + data: appData, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + // Detect non-JSON + if (res == null || res.data == null) { + deferred.reject("CatalogService::updateAppCatalog Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch( status => { + this.$log.error('CatalogService:updateAppCatalog failed: ' + status); + deferred.reject(status); + }); + return deferred.promise; + } + + } + + CatalogService.$inject = ['$q', '$log', '$http', 'conf','uuid4']; + angular.module('ecompApp').service('catalogService', CatalogService) +})(); diff --git a/ecomp-portal-FE/client/app/services/confirm-box/confirm-box.service.js b/ecomp-portal-FE/client/app/services/confirm-box/confirm-box.service.js new file mode 100644 index 00000000..affc6d3f --- /dev/null +++ b/ecomp-portal-FE/client/app/services/confirm-box/confirm-box.service.js @@ -0,0 +1,153 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +(function () { + class ConfirmBoxService { + constructor($q, $log, ngDialog) { + this.$q = $q; + this.$log = $log; + this.ngDialog = ngDialog; + } + + showInformation(message) { + let deferred = this.$q.defer(); + this.ngDialog.open({ + templateUrl: 'app/views/confirmation-box/information-box.tpl.html', + controller: 'ConfirmationBoxCtrl', + controllerAs: 'confirmBox', + className: 'confirm-box ngdialog-theme-default', + showClose: false, + data: { + message: message + } + }).closePromise.then(confirmed => { + deferred.resolve(confirmed.value); + }).catch(err => { + deferred.reject(err); + }); + return deferred.promise; + }; + + confirm(message) { + let deferred = this.$q.defer(); + this.ngDialog.open({ + templateUrl: 'app/views/confirmation-box/confirmation-box.tpl.html', + controller: 'ConfirmationBoxCtrl', + controllerAs: 'confirmBox', + className: 'confirm-box ngdialog-theme-default', + showClose: false, + data: { + message: message + } + }).closePromise.then(confirmed => { + deferred.resolve(confirmed.value); + }).catch(err => { + deferred.reject(err); + }); + return deferred.promise; + }; + + + showDynamicInformation(message, templatePath, controller) { + let deferred = this.$q.defer(); + this.ngDialog.open({ + templateUrl: templatePath, + controller: controller, + controllerAs: 'confirmBox', + className: 'confirm-box ngdialog-theme-default', + showClose: false, + data: { + message: message + } + }).closePromise.then(confirmed => { + deferred.resolve(confirmed.value); + }).catch(err => { + deferred.reject(err); + }); + return deferred.promise; + }; + + deleteItem(item) { + let deferred = this.$q.defer(); + this.ngDialog.open({ + templateUrl: 'app/views/confirmation-box/confirmation-box.tpl.html', + controller: 'ConfirmationBoxCtrl', + controllerAs: 'confirmBox', + className: 'confirm-box ngdialog-theme-default', + showClose: false, + data: { + item: item, + title: 'Functional Menu - Delete' + } + }).closePromise.then(confirmed => { + deferred.resolve(confirmed.value); + }).catch(err => { + deferred.reject(err); + }); + return deferred.promise; + }; + + moveMenuItem(message) { + let deferred = this.$q.defer(); + this.ngDialog.open({ + templateUrl: 'app/views/confirmation-box/dragdrop-confirmation-box.tpl.html', + controller: 'ConfirmationBoxCtrl', + controllerAs: 'confirmBox', + className: 'confirm-box ngdialog-theme-default', + showClose: false, + data: { + message: message, + title:'Functional Menu - Move' + } + }).closePromise.then(confirmed => { + deferred.resolve(confirmed.value); + }).catch(err => { + deferred.reject(err); + }); + return deferred.promise; + }; + + makeAdminChanges(message) { + let deferred = this.$q.defer(); + this.ngDialog.open({ + templateUrl: 'app/views/confirmation-box/admin-confirmation-box.tpl.html', + controller: 'ConfirmationBoxCtrl', + controllerAs: 'confirmBox', + className: 'confirm-box ngdialog-theme-default', + showClose: false, + data: { + message: message, + title: 'Admin Update' + } + }).closePromise.then(confirmed => { + deferred.resolve(confirmed.value); + }).catch(err => { + deferred.reject(err); + }); + return deferred.promise; + }; + + + } + ConfirmBoxService.$inject = ['$q', '$log', 'ngDialog']; + angular.module('ecompApp').service('confirmBoxService', ConfirmBoxService) +})(); diff --git a/ecomp-portal-FE/client/app/services/contact-us/contact-us.service.js b/ecomp-portal-FE/client/app/services/contact-us/contact-us.service.js new file mode 100644 index 00000000..241a12ab --- /dev/null +++ b/ecomp-portal-FE/client/app/services/contact-us/contact-us.service.js @@ -0,0 +1,247 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +/** + * Created by robertlo on 10/10/2016. + */ +'use strict'; + +(function () { + class ContactUsService { + constructor($q, $log, $http, conf, uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + } + getListOfApp() { + // this.$log.info('ContactUsService::getListOfavailableApps: get all app list'); + let deferred = this.$q.defer(); + // this.$log.info('ContactUsService::getListOfavailableApps: ', this.conf.api.listOfApp); + this.$http({ + method: "GET", + url: this.conf.api.availableApps, + cache: false + }).then( res => { + // If response comes back as a redirected HTML page which IS NOT a success + // this.$log.info('ContactUsService::getListOfavailableApps availableApps response: ', res); + if (Object.keys(res).length == 0) { + deferred.reject("ContactUsService::getListOfavailableApps: Failed"); + } else { + // this.$log.debug('ContactUsService::getListOfavailableApps: Succeeded results: ', res); + deferred.resolve(res); + } + }).catch( status => { + this.$log.error('ContactUsService::getListOfavailableApps: query error: ',status); + deferred.reject(status); + }); + return deferred.promise; + } + + getContactUs() { + let deferred = this.$q.defer(); + // this.$log.info('ContactUsService::get all Contact Us list'); + this.$http({ + url: this.conf.api.getContactUS, + method: 'GET', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + // If response comes back as a redirected HTML page which IS NOT a success + if (Object.keys(res.data).length == 0) { + deferred.reject("ContactUsService::getContactUs Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getAppsAndContacts() { + let deferred = this.$q.defer(); + // this.$log.info('ContactUsService::getAppsAndContacts'); + this.$http({ + url: this.conf.api.getAppsAndContacts, + method: 'GET', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + // If response comes back as a redirected HTML page which IS NOT a success + if (Object.keys(res.data).length == 0) { + deferred.reject("ContactUsService::getAppsAndContacts Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getContactUSPortalDetails(){ + let deferred = this.$q.defer(); + // this.$log.info('ContactUsService::get all Contact Us Portal Details'); + this.$http({ + url: this.conf.api.getContactUSPortalDetails, + method: 'GET', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + // If response comes back as a redirected HTML page which IS NOT a success + if (Object.keys(res.data).length == 0) { + deferred.reject("ContactUsService::getContactUSPortalDetails Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getAppCategoryFunctions(){ + let deferred = this.$q.defer(); + // this.$log.info('ContactUsService::get all App Category Functions'); + this.$http({ + url: this.conf.api.getAppCategoryFunctions, + method: 'GET', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + // If response comes back as a redirected HTML page which IS NOT a success + if (Object.keys(res.data).length == 0) { + deferred.reject("ContactUsService::getAppCategoryFunctions Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + addContactUs(newContactUs) { + // this.$log.info('ContactUsService::add a new Contact Us'); + // this.$log.info(newContactUs) + let deferred = this.$q.defer(); + // this.$log.info('ContactUsService:: add Contact Us' + JSON.stringify(newContactUs)); + + var contactUsObj={ + appId:newContactUs.app.value, + appName:newContactUs.app.title, + description:newContactUs.desc, + contactName:newContactUs.name, + contactEmail:newContactUs.email, + url:newContactUs.url, + }; + this.$http({ + url: this.conf.api.saveContactUS, + method: 'POST', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + }, + data: contactUsObj + }).then(res => { + // this.$log.info('ContactUsService:: add Contact Us res' ,res); + // If response comes back as a redirected HTML page which IS NOT a success + if (res==null || Object.keys(res.data).length == 0 || res.data.message == 'failure') { + deferred.reject("Add Contact Us failed"); + this.$log.error('ContactUsService:: add Contact Us failed'); + } else { + deferred.resolve(res.data); + } + }).catch(errRes => { + deferred.reject(errRes); + }); + return deferred.promise; + } + + modifyContactUs(contactUsObj) { + // this.$log.info('ContactUsService::edit Contact Us',contactUsObj); + let deferred = this.$q.defer(); + this.$http({ + url: this.conf.api.saveContactUS, + method: 'POST', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + }, + data: contactUsObj + }).then(res => { + // this.$log.info('ContactUsService:: edit Contact Us res' ,res); + // If response comes back as a redirected HTML page which IS NOT a success + if (res==null || Object.keys(res.data).length == 0 || res.data.message == 'failure') { + deferred.reject("Edit Contact Us failed"); + this.$log.error('ContactUsService:: edit Contact Us failed'); + } else { + deferred.resolve(res.data); + } + }).catch(errRes => { + deferred.reject(errRes); + }); + return deferred.promise; + } + + removeContactUs(id) { + let deferred = this.$q.defer(); + let url = this.conf.api.deleteContactUS + '/' + id; + // this.$log.info('ContactUsService:: remove Contact Us'); + this.$http({ + url: url, + method: 'POST', + cache: false, + data: '', + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + // If response comes back as a redirected HTML page which IS NOT a success + // this.$log.info("ContactUsService::removeContactUs res",res); + deferred.resolve(res.data); + if (Object.keys(res.data).length == 0) { + deferred.reject("ContactUsService::removeContactUs Failed"); + } else { + deferred.resolve(res.data); + } + }).catch(errRes => { + deferred.reject(errRes); + }); + + return deferred.promise; + } + } + ContactUsService.$inject = ['$q', '$log', '$http', 'conf', 'uuid4']; + angular.module('ecompApp').service('contactUsService', ContactUsService) +})(); \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/services/dashboard/dashboard.service.js b/ecomp-portal-FE/client/app/services/dashboard/dashboard.service.js new file mode 100644 index 00000000..bc9c9cee --- /dev/null +++ b/ecomp-portal-FE/client/app/services/dashboard/dashboard.service.js @@ -0,0 +1,185 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +/** + * Created by robertlo on 09/26/2016. + */ +'use strict'; + +(function () { + class DashboardService { + constructor($q, $log, $http, conf, uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.dashboardService = null; + this.uuid = uuid; + } + + getCommonWidgetData(widgetType) { + // this.$log.info('ecomp::dashboard-service::getting news data'); + let deferred = this.$q.defer(); + let url = this.conf.api.commonWidget + '?resourceType=' + widgetType; + + this.$http({ + method: "GET", + url: url, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }) + .then( res => { + // this.$log.info('ecomp::dashboard-service::getting news data',res); + // If response comes back as a redirected HTML page which IS NOT a success + if (Object.keys(res.data).length == 0 || Object.keys(res.data.response) ==null || Object.keys(res.data.response.items) ==null) { + deferred.reject("ecomp::dashboard-service::getNewsData Failed"); + } else { + this.userProfile = res.data; + // this.$log.info('ecomp::dashboard-service::getNewsData Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + return deferred.promise; + } + + saveCommonWidgetData(newData){ + let deferred = this.$q.defer(); + //this.$log.info('ecomp::dashboard-service::saveCommonWidgetData'); + //this.$log.debug('ecomp::dashboard-service::saveCommonWidgetData with:', newData); + + this.$http({ + method: "POST", + url: this.conf.api.commonWidget, + data: newData, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + // If response comes back as a redirected HTML page which IS NOT a success + // this.$log.info(res.data); + if (Object.keys(res.data).length == 0) { + deferred.reject("ecomp::dashboard-service::saveCommonWidgetData Failed"); + } else { + // this.$log.info('ecomp::dashboard-service::saveCommonWidgetData Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + return deferred.promise; + } + + + + removeCommonWidgetData(widgetToRemove){ + let deferred = this.$q.defer(); + // this.$log.info('ecomp::dashboard-service::removeCommonWidgetData'); + // this.$log.debug('ecomp::dashboard-service::removeCommonWidgetData with:', widgetToRemove); + this.$http({ + method: "POST", + url: this.conf.api.deleteCommonWidget, + data: widgetToRemove, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + // If response comes back as a redirected HTML page which IS NOT a success + // this.$log.info(res.data); + if (Object.keys(res.data).length == 0) { + deferred.reject("ecomp::dashboard-service::saveCommonWidgetData Failed"); + } else { + // this.$log.info('ecomp::dashboard-service::saveCommonWidgetData Succeeded'); + deferred.resolve(res.data); + } + }) + .catch( status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getSearchAllByStringResults(searchStr) { + // this.$log.info('ecomp::getSearchAllByStringResults::getting search by string results'); + let deferred = this.$q.defer(); + let url = this.conf.api.getSearchAllByStringResults; + + this.$http({ + method: "GET", + url : url, + params : { + 'searchString' : searchStr + }, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + // If response comes back as a redirected HTML page which IS NOT a success + if (Object.keys(res.data).length == 0) { + deferred.reject("ecomp::dashboard-service::getSearchAllByStringResults Failed"); + } else { + //this.searchResults = res.data; + // this.$log.info('ecomp::dashboard-service::getSearchAllByStringResults Succeeded'); + deferred.resolve(res.data.response); + } + }).catch( status => { + this.$log.error('ecomp::getSearchAllByStringResults error'); + deferred.reject(status); + }); + return deferred.promise; + + } + + getOnlineUserUpdateRate() { + let deferred = this.$q.defer(); + let url = this.conf.api.onlineUserUpdateRate; + this.$http({ + method: "GET", + url: url, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + // If response comes back as a redirected HTML page which IS NOT a success + if (Object.keys(res.data).length == 0) { + deferred.reject("ecomp::dashboard-service::getOnlineUserUpdateRate Failed"); + } else { + this.$log.info('ecomp::dashboard-service::getOnlineUserUpdateRate Succeeded',res); + deferred.resolve(res.data); + } + }).catch( status => { + deferred.reject(status); + }); + return deferred.promise; + } + + } + + DashboardService.$inject = ['$q', '$log', '$http', 'conf', 'uuid4']; + angular.module('ecompApp').service('dashboardService', DashboardService) +})(); diff --git a/ecomp-portal-FE/client/app/services/error-messages/error-messages.service.js b/ecomp-portal-FE/client/app/services/error-messages/error-messages.service.js new file mode 100644 index 00000000..032fb803 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/error-messages/error-messages.service.js @@ -0,0 +1,23 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; +let errorMessageByCode = {1201: 'Value already exists'}; +angular.module('ecompApp').constant('errorMessageByCode', errorMessageByCode); diff --git a/ecomp-portal-FE/client/app/services/functionalMenu/functionalMenu.service.js b/ecomp-portal-FE/client/app/services/functionalMenu/functionalMenu.service.js new file mode 100644 index 00000000..ec3bd387 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/functionalMenu/functionalMenu.service.js @@ -0,0 +1,253 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +(function () { + class FunctionalMenuService { + constructor($q, $log, $http, conf,uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + } + + + getManagedRolesMenu( appId ) + { + let deferred = this.$q.defer(); + this.$log.info('FunctionalMenuService::getManagedRolesMenu'); + let url = this.conf.api.appRoles.replace(':appId', appId); + this.$log.info("FunctionalMenuService::getManagedRolesMenu url: "+url); + + this.$http({ + method: "GET", + url: url, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("functionalMenu.service::getManagedRolesMenu Failed"); + } else { + this.$log.info('functionalMenu.service::getManagedRolesMenu succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getAvailableApplications() + { + let deferred = this.$q.defer(); + this.$log.info('FunctionalMenuService::getManagedRolesMenu:getAvailableApplications'); + + this.$http({ + method: "GET", +// url: this.conf.api.availableApps, + url: this.conf.api.allAvailableApps, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("FunctionalMenuService::getManagedRolesMenu:getAvailableApplications Failed"); + } else { + this.$log.info('FunctionalMenuService::getManagedRolesMenu:getAvailableApplications succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + getMenuDetails( menuId ) + { + let deferred = this.$q.defer(); + this.$log.info('FunctionalMenuService::getMenuDetails:getMenuDetails'); + let url = this.conf.api.functionalMenuItemDetails.replace(':menuId',menuId); + this.$log.info("FunctionalMenuService::getMenuDetails url: "+url); + + this.$http({ + method: "GET", + url: url, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("FunctionalMenuService::getMenuDetails:getMenuDetails Failed"); + } else { + this.$log.info('FunctionalMenuService::getMenuDetails:getMenuDetails succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + + getManagedFunctionalMenu() { + let deferred = this.$q.defer(); + this.$log.info('FunctionalMenuService::getMenuDetails:getManagedFunctionalMenu'); + + this.$http({ + method: "GET", + url: this.conf.api.functionalMenuForEditing, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("FunctionalMenuService::getManagedFunctionalMenu Failed"); + } else { + this.$log.info('FunctionalMenuService::getManagedFunctionalMenu succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + regenerateFunctionalMenuAncestors() { + let deferred = this.$q.defer(); + this.$log.info('FunctionalMenuService::regenerateFunctionalMenuAncestors'); + + this.$http({ + method: "GET", + url: this.conf.api.regenerateFunctionalMenuAncestors, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("FunctionalMenuService::regenerateFunctionalMenuAncestors Failed"); + } else { + this.$log.info('FunctionalMenuService::regenerateFunctionalMenuAncestors succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + saveEditedMenuItem(menuData) { + let deferred = this.$q.defer(); + this.$log.info('FunctionalMenuService::saveEditedMenuItem: ' + menuData); + + let url = this.conf.api.functionalMenuItem; + this.$http({ + method: "PUT", + url: url, + cache: false, + data: menuData, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("FunctionalMenuService::saveEditedMenuItem Failed"); + } else { + this.$log.info('FunctionalMenuService::saveEditedMenuItem succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(errRes => { + deferred.reject(errRes); + }); + return deferred.promise; + } + + saveMenuItem(menuData) { + let deferred = this.$q.defer(); + this.$log.info('FunctionalMenuService::saveMenuItem: ' + JSON.stringify(menuData)); + + let url = this.conf.api.functionalMenuItem; + this.$http({ + method: "POST", + url: url, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + }, + data: menuData + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("FunctionalMenuService::saveMenuItem: Failed"); + } else { + this.$log.info('FunctionalMenuService::saveMenuItem: succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(errRes => { + deferred.reject(errRes); + }); + return deferred.promise; + } + + + deleteMenuItem(menuId) { + let deferred = this.$q.defer(); + let url = this.conf.api.functionalMenuItem + '/' + menuId; + + this.$log.info('FunctionalMenuService::deleteMenuItem: ' +menuId); + + this.$http({ + method: "DELETE", + url: url, + cache: false, + data:'', + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("FunctionalMenuService::deleteMenuItem Failed"); + } else { + this.$log.info('FunctionalMenuService::deleteMenuItem succeeded: '); + deferred.resolve(res.data); + } + }) + .catch(errRes => { + deferred.reject(errRes); + }); + return deferred.promise; + } + +} + FunctionalMenuService.$inject = ['$q', '$log', '$http', 'conf','uuid4']; + angular.module('ecompApp').service('functionalMenuService', FunctionalMenuService) +})(); diff --git a/ecomp-portal-FE/client/app/services/global-constants/global-constants.js b/ecomp-portal-FE/client/app/services/global-constants/global-constants.js new file mode 100644 index 00000000..fa13dae4 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/global-constants/global-constants.js @@ -0,0 +1,21 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +angular.module('ecompApp').value('ECOMP_URL_REGEX', /^((?:https?\:\/\/|ftp?\:\/\/)?(w{3}.)?(?:[-a-z0-9]+\.)*[-a-z0-9]+.*)[^-_.]$/i); diff --git a/ecomp-portal-FE/client/app/services/kpi-dashboard/kpi-dashboard.service.js b/ecomp-portal-FE/client/app/services/kpi-dashboard/kpi-dashboard.service.js new file mode 100644 index 00000000..ff9b66b8 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/kpi-dashboard/kpi-dashboard.service.js @@ -0,0 +1,185 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +(function () { + class KpiDashboardService { + constructor($q, $log, $http, conf, uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + this.applicationsHomeUrl = 'kpidash'; + } + + kpiApiCall(ApiName) { + let deferred = this.$q.defer(); + this.$log.info('KpiDashboardService::kpiApiCall: '+ApiName); + this.$http({ + method: 'GET', + url: this.conf.api[ApiName], + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + this.$log.debug("KpiDashboardService::kpiApiCall: response successfully retrieved"); + if (Object.keys(res.data).length == 0) { + deferred.reject("KpiDashboardService::kpiApiCall: "+ ApiName+ " Failed"); + } else { + deferred.resolve(res); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + getKpiUserStoriesStats(){ + return this.kpiApiCall("getKpiDashUserStoriesStats"); + } + getKpiUserApiStats(){ + return this.kpiApiCall("getKpiDashUserApiStats"); + } + getKpiLocStats(){ + return this.kpiApiCall("getKpiDashLocStats"); + } + getKpiLocStatsCat(){ + return this.kpiApiCall("getKpiDashLocStatsCat"); + } + getKpiServiceSupported(){ + return this.kpiApiCall("getKpiDashServiceSupported"); + } + getKpiPublishedDelivered(){ + return this.kpiApiCall("getKpiDashPublishedDelivered"); + } + getKpiFeedStats(){ + return this.kpiApiCall("getKpiDashFeedStats"); + } + getKpiUserApis(){ + return this.kpiApiCall("getKpiDashUserApis"); + } + getKpiGeoMapUrl(){ + return this.kpiApiCall("getKpiDashGeoMapUrl"); + } + getKpiRCloudAUrl(){ + return this.kpiApiCall("getKpiDashRCloudAUrl"); + } + getKpiGeoMapApiUrl(){ + return this.kpiApiCall("getKpiDashGeoMapApiUrl"); + } + + getToplevelgTabs1() { + var toplevelgTabs1=[{ + title : 'eCOMP', + id : 'ECOMP', + url : this.applicationsHomeUrl, + state : 'root.kpidash_ECOMP' + }] + return toplevelgTabs1; + } + + getToplevelgTabs2() { + var toplevelgTabs2 = [ { + title : 'A&AI', + id : 'A&AI', + url : this.applicationsHomeUrl, + state : 'root.kpidash_AAI' + }, { + title : 'APP-C', + id : 'APP-C', + url : this.applicationsHomeUrl, + state : 'root.kpidash_APPC' + }, { + title : 'ASDC', + id : 'ASDC', + url : this.applicationsHomeUrl, + state : 'root.kpidash_ASDC' + }, { + title : 'DCAE', + id : 'DCAE', + url : this.applicationsHomeUrl, + state : 'root.kpidash_DCAE' + }, { + title : 'OpenECOMP Portal', + id : 'OpenECOMP Portal', + url : this.applicationsHomeUrl, + state : 'root.kpidash_ECOMP_Portal' + }, { + title : 'i-Portal', + id : 'i-Portal', + url : this.applicationsHomeUrl, + state : 'root.kpidash_InfrastructurePortal' + }, { + title : 'MSO', + id : 'MSO', + url : this.applicationsHomeUrl, + state : 'root.kpidash_MSO' + }, { + title : 'Policy', + id : 'Policy', + url : this.applicationsHomeUrl, + state : 'root.kpidash_Policy' + }]; + return toplevelgTabs2; + } + + getToplevelgTabs3() { + var toplevelgTabs3 = [ { + title : 'Closed Loop', + id : 'Closedloop', + url : this.applicationsHomeUrl, + state : 'root.kpidash_Closedloop' + }, { + title : 'eDMaaP', + id : 'DMaaP', + url : this.applicationsHomeUrl, + state : 'root.kpidash_DMaaP' + } ]; + return toplevelgTabs3; + } + + getGenericTabs(activeTab) { + var gTabs = [ { + title : 'KPI', + id : 'KPI', + url : this.applicationsHomeUrl, + state : 'root.kpidash_'+activeTab+'_KPI' + }, { + title : 'User Defined KPI', + id : 'User Defined KPI', + url : this.applicationsHomeUrl, + state : 'root.kpidash_'+activeTab+'_UserDefinedKPI' + }, { + title : 'Metrics', + id : 'Metrics', + url : this.applicationsHomeUrl, + state : 'root.kpidash_'+activeTab+'_Metrics' + } ]; + return gTabs; + } + } + + KpiDashboardService.$inject = ['$q', '$log', '$http', 'conf', 'uuid4']; + angular.module('ecompApp').service('KpiDashboardService', KpiDashboardService) +})(); diff --git a/ecomp-portal-FE/client/app/services/manifest/manifest.service.js b/ecomp-portal-FE/client/app/services/manifest/manifest.service.js new file mode 100644 index 00000000..4341a138 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/manifest/manifest.service.js @@ -0,0 +1,64 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +/** + * Created by mlittle on 9/9/2016. + */ +'use strict'; + +(function () { + class ManifestService { + constructor($q, $log, $http, conf, uuid, utilsService) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + this.utilsService = utilsService; + } + + getManifest() { + let deferred = this.$q.defer(); + this.$http({ + method: "GET", + url: this.conf.api.getManifest, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + if (this.utilsService.isValidJSON(res)== false) { + this.$log.error('ManifestService.getManifest failed: '); + deferred.reject('ManifestService.getManifest: response.data null or not object'); + } else { + // this.$log.info('ManifestService.getManifest Succeeded'); + // this.$log.debug('ManifestService.getManifest: ', JSON.stringify(res)) + deferred.resolve(res.data); + } + }).catch( status => { + this.$log.error('ManifestService.getManifest failed: ' + status.data); + deferred.reject(status); + }); + return deferred.promise; + } + + } + ManifestService.$inject = ['$q', '$log', '$http', 'conf', 'uuid4', 'utilsService']; + angular.module('ecompApp').service('manifestService', ManifestService) +})(); diff --git a/ecomp-portal-FE/client/app/services/menus/menus.service.js b/ecomp-portal-FE/client/app/services/menus/menus.service.js new file mode 100644 index 00000000..19bb385b --- /dev/null +++ b/ecomp-portal-FE/client/app/services/menus/menus.service.js @@ -0,0 +1,145 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +(function () { + class MenusService { + constructor($q, $log, $http, conf, uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + } + + GetFunctionalMenuForUser() { + let deferred = this.$q.defer(); + // this.$log.info('MenusService::GetFunctionalMenuForUser via REST API'); + this.$http({ + method: "GET", + url: this.conf.api.functionalMenuForAuthUser, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("MenusService::GetFunctionalMenuForUser Failed"); + } else { + this.$log.info('MenusService::GetFunctionalMenuForUser success:'); + deferred.resolve(res.data); + } + }) + .catch( status => { + this.$log.info('MenusService::rejection:' + status); + deferred.reject(status); + }); + + + return deferred.promise; + } + + getFavoriteItems() { + let deferred = this.$q.defer(); + // this.$log.info('MenusService::getFavoriteItems via REST API'); + this.$http({ + method: "GET", + url: this.conf.api.getFavoriteItems +"?date="+new Date().getTime(), + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then( res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("MenusService::getFavoriteItems Failed"); + } else { + this.$log.info('MenusService::getFavoriteItems success:'); + deferred.resolve(res.data); + } + }) + .catch( status => { + this.$log.error('MenusService::getFavoriteItems rejection:' + status); + deferred.reject(status); + }); + + + return deferred.promise; + } + + setFavoriteItem(menuId) { + let deferred = this.$q.defer(); + // this.$log.info('menus-service.service::setFavoriteItem via REST API' + menuId); + let url = this.conf.api.setFavoriteItem; + this.$http({ + method: "POST", + url: url, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate(), + 'Content-Type': 'application/json' + }, + data: menuId + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("MenusService::setFavoriteItem Failed"); + } else { + this.$log.info('MenusService::setFavoriteItem success:'); + deferred.resolve(res.data); + } + }) + .catch(errRes => { + this.$log.error('MenusService::setFavoriteItem rejection:' + JSON.stringify(errRes)); + deferred.reject(errRes); + }); + + return deferred.promise; + } + + removeFavoriteItem(menuId) { + let deferred = this.$q.defer(); + // this.$log.info('menus-service.service::removeFavoriteItem via REST API'); + let url = this.conf.api.removeFavoriteItem.replace(':menuId', menuId); + this.$http({ + method: "DELETE", + url: url, + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("MenusService::removeFavoriteItem Failed"); + } else { + // this.$log.info('MenusService::removeFavoriteItem success:'); + deferred.resolve(res.data); + } + }) + .catch(errRes => { + this.$log.error('MenusService::removeFavoriteItem rejection:' + status); + deferred.reject(errRes); + }); + return deferred.promise; + } + + } + MenusService.$inject = ['$q', '$log', '$http', 'conf', 'uuid4']; + angular.module('ecompApp').service('menusService', MenusService) +})(); diff --git a/ecomp-portal-FE/client/app/services/portal-admins/portal-admins.service.js b/ecomp-portal-FE/client/app/services/portal-admins/portal-admins.service.js new file mode 100644 index 00000000..683c0f02 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/portal-admins/portal-admins.service.js @@ -0,0 +1,107 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +(function () { + class PortalAdminsService { + constructor($q, $log, $http, conf, uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + } + + getPortalAdmins() { + let deferred = this.$q.defer(); + this.$log.info('PortalAdminsService::get all portal admins list'); + this.$http({ + url: this.conf.api.portalAdmins, + method: 'GET', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("PortalAdminsService::getPortalAdmins Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch(status => { + deferred.reject(status); + }); + return deferred.promise; + } + + addPortalAdmin(userData) { + let deferred = this.$q.defer(); + this.$log.info('PortalAdminsService:: add Portal Admin' + JSON.stringify(userData)); + this.$http({ + url: this.conf.api.portalAdmin, + method: 'POST', + cache: false, + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + }, + data: userData + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("PortalAdminsService::addPortalAdmin Failed"); + } else { + deferred.resolve(res.data); + } + }) + .catch(errRes => { + deferred.reject(errRes); + }); + return deferred.promise; + } + + removePortalAdmin(userId) { + let deferred = this.$q.defer(); + let url = this.conf.api.portalAdmin + '/' + userId; + this.$log.info('PortalAdminsService:: remove Portal Admin'); + this.$http({ + url: url, + method: 'DELETE', + cache: false, + data: '', + headers: { + 'X-ECOMP-RequestID':this.uuid.generate() + } + }).then(res => { + if (Object.keys(res.data).length == 0) { + deferred.reject("PortalAdminsService::removePortalAdmin Failed"); + } else { + deferred.resolve(res.data); + } + }).catch(errRes => { + deferred.reject(errRes); + }); + + return deferred.promise; + } + } + PortalAdminsService.$inject = ['$q', '$log', '$http', 'conf', 'uuid4']; + angular.module('ecompApp').service('portalAdminsService', PortalAdminsService) +})(); diff --git a/ecomp-portal-FE/client/app/services/support/getAccess/get-access.service.js b/ecomp-portal-FE/client/app/services/support/getAccess/get-access.service.js new file mode 100644 index 00000000..24b6945d --- /dev/null +++ b/ecomp-portal-FE/client/app/services/support/getAccess/get-access.service.js @@ -0,0 +1,61 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +(function () { + class GetAccessService { + constructor($q, $log, $http, conf,uuid) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + } + getListOfApp(searchStr) { + //this.$log.info('GetAccessService::getListOfApp: get all app list'); + let deferred = this.$q.defer(); + //this.$log.info('GetAccessService::getListOfApp: searchStr', searchStr); + //this.$log.info('GetAccessService::getListOfApp: ', this.conf.api.listOfApp); + this.$http({ + method: "GET", + url: this.conf.api.listOfApp, + params: {search:searchStr}, + cache: false + }).then( res => { + // this.$log.info('GetAccessService::getListOfApp response: ', res); + if (Object.keys(res).length == 0) { + deferred.reject("GetAccessService::getListOfApp: Failed"); + } else { + // this.$log.debug('GetAccessService::getListOfApp: query results: ', res); + // this.$log.info('GetAccessService::getListOfApp Succeeded'); + deferred.resolve(res); + } + }).catch( status => { + this.$log.error('GetAccessService::getListOfApp: query error: ',status); + deferred.reject(status); + }); + return deferred.promise; + } + + } + GetAccessService.$inject = ['$q', '$log', '$http', 'conf','uuid4']; + angular.module('ecompApp').service('getAccessService', GetAccessService) +})(); diff --git a/ecomp-portal-FE/client/app/services/support/session/session.service.js b/ecomp-portal-FE/client/app/services/support/session/session.service.js new file mode 100644 index 00000000..d18c42a4 --- /dev/null +++ b/ecomp-portal-FE/client/app/services/support/session/session.service.js @@ -0,0 +1,56 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +(function () { + class SessionService { + constructor($q, $log, $http, conf,uuid,$sce) { + this.$q = $q; + this.$log = $log; + this.$http = $http; + this.conf = conf; + this.uuid = uuid; + this.$sce = $sce; + } + + logout(appStr) { + this.$log.info('SessionService::logout from App'); + let deferred = this.$q.defer(); + this.$log.info('SessionService appStr: ', appStr); + + var eaccessPattern = '\https?\:\/\/[^/]+/[^/]+/[^/]+'; + var standardPattern = '\https?\:\/\/[^/]+/[^/]+'; + + if(appStr.includes("e-access")) { + standardPattern = eaccessPattern; + } + + var contextUrl = appStr.match(new RegExp(standardPattern)); + var logoutUrl = contextUrl + "/logout.htm" ; + this.$sce.trustAsResourceUrl(logoutUrl); + console.log('logoutUrl ' + logoutUrl); + jQuery('#reg-logout-div').append(" + + + + + +
+
X
+ +
+ + + +
+ To request access to an application, please visit the Get Access page. +
+ + diff --git a/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.controller.js b/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.controller.js new file mode 100644 index 00000000..b5216101 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.controller.js @@ -0,0 +1,85 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +(function () { + class NewPortalAdminModalCtrl { + constructor($log, portalAdminsService, $scope, confirmBoxService) { + + let init = () => { + this.isSaving = false; + if($scope.ngDialogData && $scope.ngDialogData.selectedUser && $scope.ngDialogData.dialogState){ + this.selectedUser = $scope.ngDialogData.selectedUser; + this.dialogState = $scope.ngDialogData.dialogState; + }else{ + this.selectedUser = null; + this.dialogState = 1; + } + $log.info('NewPortalAdminModalCtrl:: initiated'); + }; + + this.addNewPortalAdmin = () => { + portalAdminsService.getPortalAdmins().then(result=> { + var dupNameCheck = JSON.stringify(result).search(this.selectedUser.orgUserId); + if (dupNameCheck != -1) { + $log.error("NewPortalAdminModalCtrl::addNewPortalAdmin: userId already exists as a portal admin! dupNameCheck=",dupNameCheck); + confirmBoxService.showInformation('This user already exists as a portal admin!').then(function (isConfirmed) { + $scope.closeThisDialog(true); + }); + } else { + confirmBoxService.makeAdminChanges('Are you sure you want to add "' + this.selectedUser.firstName + ' ' + this.selectedUser.lastName + '" as a Portal Admin?') + .then(isConfirmed => { + if(isConfirmed) { + if (!this.selectedUser || !this.selectedUser.orgUserId) { + $log.error('NewPortalAdminModalCtrl::makeAdminChanges: No portal admin or ID... cannot add'); + return; + } + portalAdminsService.addPortalAdmin(this.selectedUser.orgUserId) + .then(() => { + $log.debug("NewPortalAdminModalCtrl::addNewPortalAdmin: portal admin added successfully"); + $scope.closeThisDialog(true); + }).catch(err => { + $log.error('NewPortalAdminModalCtrl::addNewPortalAdmin error status: ' + err.status); + confirmBoxService.showInformation('There was a unknown problem adding the portal admin. ' + 'Please try again later. Error Status: '+ err.status).then(function (isConfirmed) {}); + }); + } + }).catch(err => { + $log.error('portalAdminsService.addPortalAdmin error status: '+ err.status); + }); + } + }).catch(err=> { + $log.error('NewPortalAdminModalCtrl::addNewPortalAdmin error getting portal admins list:',err); + }); + }; + + this.setSelectedUser = (user) => { + $log.debug('NewPortalAdminModalCtrl::setSelectedUser: selected user: ', user); + this.selectedUser = user; + }; + + init(); + + $scope.$on('$stateChangeStart', e => { + e.preventDefault(); + }); + } + } + NewPortalAdminModalCtrl.$inject = ['$log', 'portalAdminsService', '$scope', 'confirmBoxService']; + angular.module('ecompApp').controller('NewPortalAdminModalCtrl', NewPortalAdminModalCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.controller.spec.js b/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.controller.spec.js new file mode 100644 index 00000000..34042c14 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.controller.spec.js @@ -0,0 +1,19 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ diff --git a/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.modal.html b/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.modal.html new file mode 100644 index 00000000..f235b391 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.modal.html @@ -0,0 +1,32 @@ + +
+
+ +
+
Save +
+
Cancel
+
+
+
diff --git a/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.modal.less b/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.modal.less new file mode 100644 index 00000000..dcc4fc52 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/portal-admin/new-portal-admin/new-portal-admin.modal.less @@ -0,0 +1,99 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .new-portal-admin-modal { + display:block; + overflow:auto; + min-height: 450px; + + .search-users { + } + + .admin-app-roles { + .title { + .n18r; + border-bottom: @a 3px solid; + + } + + .app-roles-main { + margin-top: 16px; + .app-roles-main-title { + .n14r; + margin-bottom: 8px; + .left { + display: inline-block; + } + .right { + display: inline-block; + color: @a; + float: right; + cursor: pointer; + } + } + + .select-input{ + width: 460px; + } + + .new-administrated-app { + height: 30px; + line-height: 30px; + + border: 1px solid @p; + margin-bottom: 8px; + border-radius: 2px; + padding-left: 6px; + padding-top: 0; + .o14r; + } + + .admin-roles-list { + height: 240px; + overflow-y: auto; + } + + .administrated-application { + width: 460px; + height: 30px; + border: 1px solid @p; + margin-bottom: 8px; + border-radius: 2px; + padding: 6px; + .o14r; + display: inline-block; + + } + + .delete-application { + .ico_trash_default; + display: inline-block; + vertical-align: 4px; + cursor: pointer; + position: relative; + top: 6px; + color: transparent; + margin-left: 8px; + } + + } + + } +} + diff --git a/ecomp-portal-FE/client/app/views/portal-admin/portal-admin-controller.js b/ecomp-portal-FE/client/app/views/portal-admin/portal-admin-controller.js new file mode 100644 index 00000000..10043005 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/portal-admin/portal-admin-controller.js @@ -0,0 +1,127 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +(function () { + class PortalAdminsCtrl { + constructor($log, portalAdminsService, ngDialog, confirmBoxService) { + + let updateTableData = () => { + this.isLoadingTable = true; + portalAdminsService.getPortalAdmins().then(result=> { + $log.debug('PortalAdminsCtrl::updateTableData: result: ' + JSON.stringify(result)); + if (!result || !result.length) { + $log.info('PortalAdminsCtrl::updateTableData: no Portal Admins err handling'); + this.portalAdminsTableData = []; + return; + } + this.portalAdminsTableData = result; + }).catch(err=> { + $log.error('PortalAdminsCtrl::updateTableData error :',err); + }).finally(() => { + this.isLoadingTable = false; + }); + }; + + let init = () => { + $log.info('portalAdminsService.getPortalAdmins::initializing...'); + this.isLoadingTable = false; + + this.searchString= ''; + this.portalAdminsTableHeaders = ['First Name', 'Last Name', 'User ID', 'Delete']; + this.portalAdminsTableData = []; + updateTableData(); + }; + + init(); + + this.removePortalAdmin = pAdmin => { + $log.debug('pAdmin = ' + JSON.stringify(pAdmin)); + confirmBoxService.deleteItem(pAdmin.firstName + ' ' + pAdmin.lastName ) + .then(isConfirmed => { + if(isConfirmed){ + if(!pAdmin || !pAdmin.userId){ + $log.error('PortalAdminsCtrl::removePortalAdmin No portal admin or ID... cannot delete'); + return; + } + portalAdminsService.removePortalAdmin(pAdmin.userId).then(() => { + $log.info("PortalAdminsCtrl::removePortalAdmin removed admin"); + init(); + }).catch(err => { + $log.error('PortalAdminsCtrl::removePortalAdmin.deleteItem error: '+ err); + }); + } + }).catch(err => { + $log.error('PortalAdminsCtrl::removePortalAdmin.deleteItem error: '+ err); + }); + }; + + this.openAddNewPortalAdminModal = (user) => { + let data = null; + if(user){ + data = { + dialogState: 2, + selectedUser:{ + userId: user.orgUserId, + firstName: user.firstName, + lastName: user.lastName + } + } + } + ngDialog.open({ + templateUrl: 'app/views/portal-admin/new-portal-admin/new-portal-admin.modal.html', + controller: 'NewPortalAdminModalCtrl', + controllerAs: 'newPortalAdmin', + data: data + }).closePromise.then(needUpdate => { + if(needUpdate.value === true){ + $log.debug('PortalAdminsCtrl::openAddNewPortalAdminModal: updating Portal Admin table data...'); + updateTableData(); + } + }); + }; + + this.openEditUserModal = (loginId) => { + var data = { + loginId : loginId, + updateRemoteApp : false, + appId : this.selectedApp!=null?this.selectedApp.id:'' + } + var modalInstance = ngDialog.open({ + templateUrl: 'app/views/header/user-edit/edit-user.tpl.html', + controller: 'editUserController', + data: data, + resolve: { + message: function message() { + var message = { + type: 'Contact', + }; + return message; + } + } + }).closePromise.then(needUpdate => { + updateTableData(); + }); + } + + } + } + PortalAdminsCtrl.$inject = ['$log', 'portalAdminsService', 'ngDialog', 'confirmBoxService']; + angular.module('ecompApp').controller('PortalAdminsCtrl', PortalAdminsCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/portal-admin/portal-admin.tpl.html b/ecomp-portal-FE/client/app/views/portal-admin/portal-admin.tpl.html new file mode 100644 index 00000000..05216f34 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/portal-admin/portal-admin.tpl.html @@ -0,0 +1,73 @@ + +
+
+
+
Portal Admins
+
+
+ +
Add Portal Admin
+
+ +
+ + + + + + + + + + + + + + + + + +
{{portalAdmin.portalAdminsTableHeaders[0]}}{{portalAdmin.portalAdminsTableHeaders[1]}}{{portalAdmin.portalAdminsTableHeaders[2]}}{{portalAdmin.portalAdminsTableHeaders[3]}}
+
+
+
+
+
+
+ +
+
+
+
+
+
+
+
+
diff --git a/ecomp-portal-FE/client/app/views/portal-admin/portal-admins.less b/ecomp-portal-FE/client/app/views/portal-admin/portal-admins.less new file mode 100644 index 00000000..29fd9e32 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/portal-admin/portal-admins.less @@ -0,0 +1,56 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .portal-admins-page-main { + .bg_w; + position: @page-main-position; + top: @page-main-top; + left: @page-main-left; + right: @page-main-right; + bottom: @page-main-bottom; + padding-top: @padding-top; + overflow-y: @page-main-overflow-y; + padding-left: @padding-left-side; + + + .portal-admins-table { + width: @table-width; + margin: @table-margin; + + .table-control { + .table-dropdown-filter{ + width: @table-dropdown-filter-width; + display: @table-dropdown-filter-display; + } + } + + .table-body { + cursor: pointer; + } + } + + .delete-user{ + .ico_trash_default; + } + + .portal-add-button { + width: 160px; + } +} + diff --git a/ecomp-portal-FE/client/app/views/search/search.controller.js b/ecomp-portal-FE/client/app/views/search/search.controller.js new file mode 100644 index 00000000..60e27593 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/search/search.controller.js @@ -0,0 +1,184 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +(function () { + + class SearchCtrl { + constructor($log, $scope, $cookies, $timeout, userProfileService, sessionService, dashboardService) { + $scope.firstName=""; + $scope.lastName=""; + + function showHideSearchSnippet() { + + setTimeout(function() { + jQuery("#mainSearchSnippet").click(); + },500); + + setTimeout(function() { + jQuery("#mainSearchText").focus(); + },1000); + } + + jQuery("#mainSearchDiv").keyup(function(event){ + if(event.keyCode == 13){ + // there is a watch on this variable which will trigger the database pull + dashboardService.searchString = jQuery("#mainSearchText").val(); + + // opens the popup + var popupDomObj = jQuery("[content='searchSnippet.html']"); + if(popupDomObj.length == 0) { + showHideSearchSnippet(); + } else { + jQuery("#mainSearchSnippet").click(); + showHideSearchSnippet(); + } + + + + } + }); + + + + } + + + } + + + class SearchSnippetCtrl { + constructor($log, $scope, $cookies, $timeout, userProfileService, sessionService, dashboardService,applicationsService, $window, $state) { + $scope.firstName=""; + $scope.lastName=""; + $scope.goToUrl = goToUrl; + $scope.dService = dashboardService; + + + + function goToUrl (item, type) { + $log.info("goToUrl called") + $log.info(item + "/" + type); + + + if(type == 'intra') { + + var intraSearcLink = "http://to_do_link.com"; + var intraSpecSearcLink = intraSearcLink + encodeURIComponent(dashboardService.searchString); + $window.open(intraSpecSearcLink, '_blank'); + + } else if (type == 'extra') { + var extraSearcLink = "https://to_do_link.com"; + var extraSpecSearcLink = extraSearcLink + encodeURIComponent(dashboardService.searchString); + $window.open(extraSpecSearcLink, '_blank'); + } + + let url = item.target; + let restrictedApp = item.uuid; + let getAccessState = "root.getAccess" + if (!url) { + + applicationsService.goGetAccessAppName = item.name; + if($state.current.name == getAccessState) + $state.reload(); + else + $state.go(getAccessState); + //$log.info('No url found for this application, doing nothing..'); + return; + } + + if (restrictedApp != "true") { + $window.open(url, '_blank'); + } else { + if(item.url=="root.access"){ + $state.go(url); + var tabContent = { id: new Date(), title: 'Home', url: url }; + $cookies.putObject('addTab', tabContent ); + } else { + var tabContent = { id: new Date(), title: item.name, url: url }; + $cookies.putObject('addTab', tabContent ); + } + } + + } + + function getItems(searchString) { + + var items; + var itemMap = dashboardService.getSearchAllByStringResults(searchString) + .then(res => { + $scope.items = res; + + + }).catch(err => { + $scope.items = []; + $log.error('Couldnt get search results...', err) + }); + + } + + $scope.$watch('dService.searchString', function(searchString) { + if(searchString != undefined ) + getItems(searchString); + + }); + + + + } + + + + } + + + + SearchCtrl.$inject = ['$log', '$scope', '$cookies', '$timeout','userProfileService', 'sessionService', 'dashboardService']; + SearchSnippetCtrl.$inject = ['$log', '$scope', '$cookies', '$timeout','userProfileService', 'sessionService', 'dashboardService','applicationsService', '$window','$state']; + angular.module('ecompApp').controller('searchCtrl', SearchCtrl); + angular.module('ecompApp').controller('searchSnippetCtrl', SearchSnippetCtrl); + angular.module('ecompApp').directive('searchBox', function() { + return { + restrict: "E", + templateUrl: 'app/views/search/search.tpl.html', + link: function(scope, element) { + + //var iframeId = "#tabframe-" + scope.$parent.tab.title.split(' ').join('-'); + // jQuery(iframeId).load(function() { + // alert("hello"); + // }); //.attr("src",'{{tab.content | trusted}}' ); //src='{{tab.content | trusted}}' + // jQuery(iframeId).attr('src', '{{tab.content | trusted}}'); + + //element.childNodes[0].on('load', function() { + // alert('hello'); + //}); + } + } + }); + angular.module( 'ecompApp' ).config( [ + '$compileProvider', + function( $compileProvider ) + { + $compileProvider.aHrefSanitizationWhitelist(/^\s*(https?|ftp|mailto|chrome-extension|qto):/); + } + ]); + +})(); + + diff --git a/ecomp-portal-FE/client/app/views/search/search.controller.spec.js b/ecomp-portal-FE/client/app/views/search/search.controller.spec.js new file mode 100644 index 00000000..34042c14 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/search/search.controller.spec.js @@ -0,0 +1,19 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ diff --git a/ecomp-portal-FE/client/app/views/search/search.less b/ecomp-portal-FE/client/app/views/search/search.less new file mode 100644 index 00000000..a21559ec --- /dev/null +++ b/ecomp-portal-FE/client/app/views/search/search.less @@ -0,0 +1,55 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .searchLiHeader { +font-weight: bold; +color: #0574ac; +font-size: 16px; +padding-bottom: 10px; +line-height: 1.5; +font-family: arial; + +} + +.searchLiItems{ +cursor: pointer; +font-weight: normal; +font-size: 12px; +color: #444444; +font-family: arial; +} + +.searchUl { +list-style: none; +border-bottom: 1px solid #bbb; +padding-bottom: 20px; +} + +#contentVertical { + height: 300px; + width: 250px; + } + +#contentVertical .scroll-viewport { + height: 300px; + width: 250px; + } +#mainSearchText::-ms-clear{ + display:none; +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/views/search/search.tpl.html b/ecomp-portal-FE/client/app/views/search/search.tpl.html new file mode 100644 index 00000000..bd37f772 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/search/search.tpl.html @@ -0,0 +1,82 @@ + + +
+
+ +   + +
+
+
+ +
+ + + + + diff --git a/ecomp-portal-FE/client/app/views/sidebar/sidebar.controller.js b/ecomp-portal-FE/client/app/views/sidebar/sidebar.controller.js new file mode 100644 index 00000000..76d5301c --- /dev/null +++ b/ecomp-portal-FE/client/app/views/sidebar/sidebar.controller.js @@ -0,0 +1,143 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +(function () { + class SidebarCtrl { + constructor(userProfileService, $log, $rootScope) { + this.$log = $log; + this.userProfileService = userProfileService; + this.$rootScope = $rootScope; + $rootScope.isAdminPortalAdmin = false; + + //if (bowser.msie || bowser.msedge) + // $log.debug('SidebarCtrl::init: Browser is: Internet Explorer or Edge'); + // else + // $log.debug('SidebarCtrl::init: Browser is: ' + bowser.name + ': ' + bowser.version); + + userProfileService.getUserProfile() + .then(profile=> { + // $log.debug('SidebarCtrl::getUserProfile: profile.roles.indexOf(superAdmin) = ' + profile.roles.indexOf('superAdmin')); + // $log.debug('SidebarCtrl::getUserProfile: profile.roles.indexOf(admin) = ' + profile.roles.indexOf('admin')); + if (profile.roles.indexOf('superAdmin') > -1) { + $rootScope.isAdminPortalAdmin = true; + // this.$log.debug('SidebarCtrl::getUserProfile: user has the superAdmin role'); + this.sidebarModel = { + label: 'ECOMP portal', + navItems: [ + { + name: 'Home', + state: 'root.applicationsHome', + imageSrc : 'ion-home' + }, { + name: 'Application Catalog', + state: 'root.appCatalog', + imageSrc : 'ion-grid' + }, { + name: 'Widgets', + state: 'root.widgetsHome', + imageSrc : 'ion-android-apps' + }, { + name: 'Admins', + state: 'root.admins', + imageSrc : 'ion-android-star' + }, { + name: 'Users', + state: 'root.users', + imageSrc : 'ion-person' + },{ + name: 'Portal Admins', + state: 'root.portalAdmins', + imageSrc : 'ion-gear-a' + }, { + name: 'Application Onboarding', + state: 'root.applications', + imageSrc : 'ion-ios-upload-outline' + }, { + name: 'Widget Onboarding', + state: 'root.widgets', + imageSrc : 'ion-ios-upload-outline' + },{ + name: 'Edit Functional Menu', + state: 'root.functionalMenu', + imageSrc : 'ion-compose' + } + ] + }; + } + else if (profile.roles.indexOf('admin') > -1) { + // this.$log.debug('SidebarCtrl::getUserProfile: user has the admin role'); + this.sidebarModel = { + label: 'ECOMP portal', + navItems: [ + { + name: 'Home', + state: 'root.applicationsHome', + imageSrc : 'ion-home' + }, { + name: 'Application Catalog', + state: 'root.appCatalog', + imageSrc : 'ion-grid' + }, { + name: 'Widgets', + state: 'root.widgetsHome', + imageSrc : 'ion-grid' + }, { + name: 'Users', + state: 'root.users', + imageSrc : 'ion-person' + }, { + name: 'Widget Onboarding', + state: 'root.widgets', + imageSrc : 'ion-grid' + } + ] + }; + } + else { + $rootScope.isAdminPortalAdmin = false; + // this.$log.debug('SidebarCtrl::getUserProfile: user is not superAdmin nor admin'); + this.sidebarModel = { + label: 'ECOMP portal', + navItems: [ + { + name: 'Home', + state: 'root.applicationsHome', + imageSrc : 'ion-home' + }, { + name: 'Application Catalog', + state: 'root.appCatalog', + imageSrc : 'ion-grid' + }, { + name: 'Widgets', + state: 'root.widgetsHome', + imageSrc : 'ion-grid' + } + ] + }; + } + }).catch(err=> { + $log.error('SidebarCtrl: failed to get user profile: ' + err); + }); + + } + } + SidebarCtrl.$inject = ['userProfileService', '$log', '$rootScope']; + angular.module('ecompApp').controller('SidebarCtrl', SidebarCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/sidebar/sidebar.less b/ecomp-portal-FE/client/app/views/sidebar/sidebar.less new file mode 100644 index 00000000..97650fed --- /dev/null +++ b/ecomp-portal-FE/client/app/views/sidebar/sidebar.less @@ -0,0 +1,37 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .w-ecomp-sidebar { + position: relative; + left: 0; + right: 0; + top: 5px; + padding-left: 0; +} + + @media screen and (-webkit-min-device-pixel-ratio:0) +{ + .w-ecomp-sidebar { + position: relative; + left: 0; + right: 0; + top: -5px; + padding-left: 0; + } +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/views/sidebar/sidebar.tpl.html b/ecomp-portal-FE/client/app/views/sidebar/sidebar.tpl.html new file mode 100644 index 00000000..a5cbf8ff --- /dev/null +++ b/ecomp-portal-FE/client/app/views/sidebar/sidebar.tpl.html @@ -0,0 +1,20 @@ + + diff --git a/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.controller.js b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.controller.js new file mode 100644 index 00000000..368f2fe3 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.controller.js @@ -0,0 +1,194 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +(function () { + class ContactUsManageController { + constructor($scope,$log, message, $q, $http, conf,contactUsService,confirmBoxService) { + $scope.contactUsList=[]; + $scope.contactUsAllAppList=[]; + $scope.errMsg=''; + $scope.newContactUs ={ + app:'', + name:'', + email:'', + url:'', + desc:'' + }; + /*Get the existing contact us first, then based on the existing, filter from all apps*/ + $scope.getContactUsList = function(){ + contactUsService.getContactUs().then(res=> { + // $log.info('getting getContactUs',res.response); + if(res!=null && res.response!=null){ + for(var i=0; i { + var tableData=[]; + $scope.contactUsAllAppListTemp=[]; + // $log.info('contactUsService::getListOfApp: getting res'); + var result = (typeof(res.data) != "undefined" && res.data!=null)?res.data:null; + // $log.info('contactUsService::getListOfApp: result',result); + var res1 = result; + var realAppIndex = 0; + $scope.contactUsAllAppList.length=0; + for (var i = 1; i <= res1.length; i++) { + if (!res1[i - 1].restrictedApp) { + var okToAdd = true; + for(var j =0; j<$scope.contactUsList.length;j++){ + if(res1[i - 1].title==$scope.contactUsList[j].appName) + okToAdd=false; + } + // not allowed to add(duplicate) another entry if the app is already available in the table + if(okToAdd){ + if(res1[i - 1].title){ + $scope.contactUsAllAppList.push({ + index: realAppIndex, + title: res1[i - 1].title, + value: res1[i - 1].index + }); + } + realAppIndex = realAppIndex + 1; + } + } else { + // $log.debug('contactUsService:getAvailableApps:: Restricted/URL only App will not be used = ' + res1[i - 1].title); + } + } + }).catch(err=> { + $log.error('contactUsService:error:: ', err); + + + }).finally(() => { + //this.isLoadingTable = false; + }); + }); + } + + $scope.getContactUsList(); + + $scope.closeDialog = function(){ + $scope.closeThisDialog( $scope.widgetData); + } + + /*Add new Contact Us*/ + $scope.newContactUsFun = function(){ + if($scope.newContactUs.app.title==null || $scope.newContactUs.app.title=='' ){ + confirmBoxService.showInformation('Please select an App to add').then(isConfirmed => { + return; + }); + } + + if($scope.newContactUs.url !=null && $scope.newContactUs.url != '' && !validateUrl($scope.newContactUs.url)){ + var warningMsg = "Please enter a valid URL"; + confirmBoxService.showInformation(warningMsg).then(isConfirmed => {return;}); + return; + } + + contactUsService.addContactUs($scope.newContactUs).then(res=> { + // $log.info('contactUsService: add ContactUs successfully'); + $scope.contactUsList.length=0; + // $log.info('contactUsService: refreshing the Contact US table'); + $scope.getContactUsList(); + $scope.errMsg=''; + /* confirmBoxService.showInformation('You have added a new Contact Us item').then(isConfirmed => { });*/ + var defaultSel={ + index: 0, + title: '', + value: '' + } + $scope.newContactUs ={ + app:defaultSel, + name:'', + email:'', + url:'', + desc:'' + }; + + }).catch(err=> { + $log.error('contactUsService: addContactUs error:: ', err); + // $scope.errMsg=err; + confirmBoxService.showInformation('Add Contact Us list failed: ' + err); + + }).finally(() => { + //this.isLoadingTable = false; + }); + } + /* Edit Contact Us*/ + $scope.editContactUsFun = function(contactObj){ + // $log.info('contactUsService: edit ContactUs save successfully', contactObj); + var contactUsObj={ + appId:contactObj.appId, + appName:contactObj.appName, + description:contactObj.description, + contactName:contactObj.contactName, + contactEmail:contactObj.contactEmail, + url:contactObj.url, + }; + + contactUsService.modifyContactUs(contactUsObj).then(res=> { + // $log.info('contactUsService: edit ContactUs successfully'); + // confirmBoxService.showInformation('You have saved the changes').then(isConfirmed => {}); + $scope.errMsg=''; + + }).catch(err=> { + $log.error('contactUsService: editContactUs error:: ', err); + confirmBoxService.showInformation('Edit Contact Us list failed: ' + err); + // $scope.errMsg=err; + }).finally(() => { + //this.isLoadingTable = false; + }); + + } + /*del Contact Us*/ + $scope.delContactUsFun = function(appObj){ + var confirmMsg = 'Are you sure you want to delete '+appObj.appName +' from the list?' + ' Press OK to delete.'; + confirmBoxService.confirm(confirmMsg).then(function (confirmed) { + if (confirmed == true) { + contactUsService.removeContactUs(appObj.appId).then(res=> { + // $log.info('delContactUsFun: delete ContactUs successfully',res); + $scope.errMsg=''; + $scope.contactUsList.length=0; + $scope.getContactUsList(); + confirmBoxService.showInformation('Item has been deleted').then(isConfirmed => {}); + }).catch(err=> { + $log.error('contactUsService: addContactUs error:: ', err); + confirmBoxService.showInformation('Deletion failed: ' + err); + // $scope.errMsg=err; + }).finally(() => { + //this.isLoadingTable = false; + }); + } + }); + + } + + } + } + ContactUsManageController.$inject = ['$scope','$log', 'message', '$q', '$http', 'conf','contactUsService','confirmBoxService']; + angular.module('ecompApp').controller('ContactUsManageController', ContactUsManageController); + + +})(); +function validateUrl(value){ + return /^(https?|ftp):\/\/(((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:)*@)?(((\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5]))|((([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)+(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.?)(:\d*)?)(\/((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)+(\/(([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)*)*)?)?(\?((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|[\uE000-\uF8FF]|\/|\?)*)?(\#((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|\/|\?)*)?$/i.test(value); + } diff --git a/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.controller.less b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.controller.less new file mode 100644 index 00000000..ef8c88df --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.controller.less @@ -0,0 +1,159 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .searchLiHeader { +font-weight: bold; +color: #0574ac; +font-size: 16px; +padding-bottom: 10px; +line-height: 1.5; +font-family: arial; + +} + +.searchLiItems{ +cursor: pointer; +font-weight: normal; +font-size: 12px; +color: #444444; +font-family: arial; +} + +.searchUl { +list-style: none; +border-bottom: 1px solid #bbb; +padding-bottom: 20px; +} + +.manage-contactUs-home-title{ + color: #067ab4; + font-family: arial; + font-size: 24px; + margin-left: 78px; + width: 1170px; + } + +.manage-contactUs-home-manageWidgets-title{ + color: #067ab4; + font-family: arial; + font-size: 24px; + margin-left: 30px; + width: 1170px; + } + +#editWidgetsContent { + height: 300px; + width: 1250px; + } + +#editWidgetsContent .scroll-viewport { + height: 300px; + width: 1250px; + } + + .add-contact-us-field{ + width:250px; + display: inline-block; + margin:10px; + } + .add-contact-us-field-des{ + width:800px; + margin:10px; + } + +.errMsg{ + color:red; +} +.sucessMsg{ + color:green; +} +.contact-us-margin{ + margin-left: 80px; + margin-right: 120px; +} +.contact-us-manage-table { + + + .delete-contact-us{ + font-size:20px; + } + + .portal-add-button { + width: 160px; + } +} + +.select2-container .select2-chosen, .select2-container .select2-container input{ + line-height:39px; +} +.select2-container .select2-choice{ + -webkit-transition: border-color .2s ease-out; + -moz-transition: border-color .2s ease-out; + transition: border-color .2s ease-out; + background: #fff; + border-radius: 6px; + display: block; + border: 1px solid #888; + box-shadow: none; + filter: none; + height: 32px !important; + padding: 0; + position: relative; + z-index: 5; + cursor: pointer; +} + +.c-ecomp-att-abs-table .contactUs{ + + height:300px; + +} + +.ngdialog-overlay { + pointer-events: none !important; +} + +.input-text-area { + font-style: italic; + padding: 7px 10px; + width: 250px; + display: inline-block; + position: relative; + margin-bottom: 10px; + border-radius: 6px; + border: 1px solid #d8d8d8; + height: 32px !important; + border-color: slategrey !important; +} +.input-inline-edit-text { + font-style: italic; + padding: 7px 10px; + display: inline-block; + position: relative; + margin-bottom: 10px; + border-radius: 6px; + border: 1px solid #d8d8d8; + height: 32px; + border-color: slategrey !important; + width:100%; + } +.glyphicon { + position: relative !important; + line-height: 0 !important; +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.html b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.html new file mode 100644 index 00000000..257226a0 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us-manage/contact-us-manage.html @@ -0,0 +1,136 @@ + +
+ +
+
+ +
+
Manage Contact Us
+
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + +
App NameContact NameContact EmailContact URLDescriptionEditDelete
+
+
+
+ +
+
+ +
+
+ +
+
+ +
+
+ +
+ + Save + +
+
+ +
+
+
+ +
+
+
+

Add Application Contact Information

+ +
+
+
+
+
App Name
+
+
+
+
+
Contact Name
+ +
+
+
Contact Email
+ +
+
+
Contact URL
+ +
+
+
Description
+ +
+
+
+ Add New +
+ +
+ +
+ Close +
+ +
+ +
+ +
+
+
+
+ + \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.controller.js b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.controller.js new file mode 100644 index 00000000..63e38a48 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.controller.js @@ -0,0 +1,166 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +(function () { + + class ContactUsCtrl { + constructor($log, contactUsService, applicationsService, $modal, ngDialog, $state) { + + contactUsService.getContactUSPortalDetails().then(res => { + // $log.info('ContactUsCtrl:: contactUsService getContactUSPortalDetails res',res); + // $log.info('getting res',res); + var result = (typeof(res.response) != "undefined" && res.response!=null)?res.response:null; + // $log.info('result',result); + // $log.info('done'); + var source = JSON.parse(result); + // $log.info(source); + this.ush_TicketInfoUrl = source.ush_ticket_url; + this.portalInfo_Address = source.feedback_email_address; + this.feedback_Url = source.portal_info_url; + }).catch(err=> { + $log.error('ContactUsCtrl:error:: ', err); + }).finally(() => { + }); + + let init = () => { + // $log.info('ecomp app::contact-us-controller::initializing...'); + this.appTable=[]; + this.functionalTableData=[]; + }; + init(); + + let updateContactUsTable = () => { + contactUsService.getAppsAndContacts().then(res=> { + // $log.info('ContactUsCtrl:: contactUsService getAppsAndContacts res',res); + var tableData=[]; + // $log.info('getting res',res); + var result = (typeof(res.response) != "undefined" && res.response!=null)?res.response:null; + // $log.info('result',result); + // $log.info('done'); + var source = result; + // $log.info(source); + // Drop Portal app, empty name entries + for(var i=0;i { + $log.error('ContactUsCtrl.updateContactUsTable:error:: ', err); + }) + }; + + contactUsService.getAppCategoryFunctions().then(res=> { + // $log.info('ContactUsCtrl:: contactUsService getAppCategoryFunctionsthen res',res); + var tablefunctionalData=[]; + // $log.info('getting res',res); + var result = (typeof(res.response) != "undefined" && res.response!=null)?res.response:null; + // $log.info('result',result); + // $log.info('done'); + var source = result; + // $log.info(source); + for(var i=0;i { + $log.error('ContactUsCtrl:error:: ', err); + }) + + updateContactUsTable(); + this.editContactUsModalPopup = () => { + // $log.debug('ContactUsCtrl::editContactUsModalPopup updating table data...'); + var modalInstance = ngDialog.open({ + templateUrl: 'app/views/support/contact-us/contact-us-manage/contact-us-manage.html', + controller: 'ContactUsManageController', + resolve: { + message: function message() { + var message = { + type: 'Contact', + }; + return message; + } + } + }).closePromise.then(needUpdate => { + updateContactUsTable(); + }); + }; + + this.goToSection = (id) => { + var targetDiv = document.getElementById(id); + var offSetHeight = 0; + for(var i=0;i d.showFlag = false); + // let index = this.appTable.findIndex(a => a.app_Id == id); + var index =-1; + for(var i=0; i -1) { + // setting the showFlag to true based on index comparing with the app_Id + this.appTable[index].showFlag = true; + $('#contentId').animate({ + scrollTop: targetDiv.offsetTop-offSetHeight + 'px' + }, 'fast'); + } + + }; + + // Take the user to the application on the get access page. + this.goGetAccess = (appName) => { + // $log.debug('ContactUsCtrl::goGetAccess received name ' + appName); + applicationsService.goGetAccessAppName = appName; + $state.go('root.getAccess'); + }; + + } + } + ContactUsCtrl.$inject = ['$log','contactUsService', 'applicationsService', '$modal', 'ngDialog', '$state']; + angular.module('ecompApp').controller('ContactUsCtrl', ContactUsCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.controller.spec.js b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.controller.spec.js new file mode 100644 index 00000000..34042c14 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.controller.spec.js @@ -0,0 +1,19 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ diff --git a/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.less b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.less new file mode 100644 index 00000000..b0c0af4f --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.less @@ -0,0 +1,104 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .w-ecomp-contactUs-home { + .bg_w; + position: @page-main-position; + top: @page-main-top; + left: @page-main-left; + right: @page-main-right; + bottom: @page-main-bottom; + padding-top: @padding-top; + padding-left: @padding-left-side; + + .contactUs-home-container { + .content_justify; + position: relative; + //padding-top: 15px; + padding-right: 0; + padding-left: 0; + padding-bottom: 32px; + width: 100%; + + .contactUs-home-title { + .a24r; + margin: auto; + .content_justify; + } + + .contactUs-general-div { + margin: auto; + padding-top: 15px; + padding-bottom: 15px; + .content_justify; + } + } + +.collapsibleArrow { + width: 30px; + height: 30px; + margin-left: 10px; + } + +.contactUs-collapsible-panel { + margin: auto; + width: 1170px; + + } + + .contactUs-collapsible-table { + margin: auto; + width: 1170px; + } + + .contactUs-txt { + font-weight: normal; + color: #666666; + font-size: 15px; + font-family: arial; + margin:10px; + } + +.contactUs-panel-header { + font-weight: normal; + color: #666666; + font-size: 18px; + font-family: sans-serif; + border-top: 1px solid #ccc; + outline : none; + height: 35px; + width: 1050px; + } + + .contactUs-panel-header:hover{ + color: #428bca; + background: #eae8e8; + cursor: pointer; cursor: hand; + } + +.contactUs-panel-labels { + font-weight: normal; + color: #666666; + font-size: 15px; + font-family: sans-serif; + padding-top: 5px; + padding-bottom: 5px; +} + +} diff --git a/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.tpl.html b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.tpl.html new file mode 100644 index 00000000..0b403ece --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/contact-us/contact-us.tpl.html @@ -0,0 +1,125 @@ + +
+
+
+
Contact Us + +
+ +
+ To give feedback or report an issue to the OpenECOMP Portal team, send email to {{contact.portalInfo_Address}}. +
+ +
+ +
Application Functions +
+
+ + + + + + + + + + + + + + + + + +
CategoryECOMP FunctionsECOMP Application
+
+
+
+
+
+ {{rowData.app_Name}} +
+
+
+
+
+ +
+
All Applications +
+
+
+ + + + + + +
+ +
+
+ No application information is available. Please use the links above to contact the OpenECOMP Portal team. +
+
+ + + + + + + + + + + + + + + + + + + + + +
Contact:{{rowData.contact_name}}
Email:{{rowData.contact_email}}
Info URL:{{rowData.url_Info}}
Description:{{rowData.desc}}
Get access:Click for application and role information
+
+
+ +
+
+ +
+
+
\ No newline at end of file diff --git a/ecomp-portal-FE/client/app/views/support/get-access/get-access.controller.js b/ecomp-portal-FE/client/app/views/support/get-access/get-access.controller.js new file mode 100644 index 00000000..b9b254ac --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/get-access/get-access.controller.js @@ -0,0 +1,70 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +(function () { + class GetAccessCtrl { + constructor($log, $stateParams, getAccessService,applicationsService, ngDialog) { + // $log.debug('GetAccessCtrl: appService param is: ' + applicationsService.goGetAccessAppName); + + this.updateAppsList = () => { + getAccessService.getListOfApp().then(res=> { + var tableData=[]; + // $log.info('GetAccessCtrl::updateAppsList: getting res'); + var result = (typeof(res.data) != "undefined" && res.data!=null)?res.data:null; + // $log.info('GetAccessCtrl::updateAppsList: result',result); + // $log.info('GetAccessCtrl::updateAppsList: done'); + var source = result; + // $log.info('GetAccessCtrl::updateAppsList source: ', source); + for(var i=0;i { + $log.error('GetAccessCtrl:error:: ', err); + }).finally(() => { + this.isLoadingTable = false; + }); + }; + let init = () => { + // $log.info('GetAccessCtrl:: initializing...'); + this.searchString = ''; + this.getAccessTableHeaders = ['ECOMP Function', 'Application Name', 'Role Name']; + this.appTable=[]; + this.updateAppsList(); + }; + init(); + } + } + GetAccessCtrl.$inject = ['$log', '$stateParams', 'getAccessService', 'applicationsService', 'ngDialog']; + angular.module('ecompApp').controller('GetAccessCtrl', GetAccessCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/support/get-access/get-access.controller.spec.js b/ecomp-portal-FE/client/app/views/support/get-access/get-access.controller.spec.js new file mode 100644 index 00000000..34042c14 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/get-access/get-access.controller.spec.js @@ -0,0 +1,19 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ diff --git a/ecomp-portal-FE/client/app/views/support/get-access/get-access.less b/ecomp-portal-FE/client/app/views/support/get-access/get-access.less new file mode 100644 index 00000000..20b406e9 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/get-access/get-access.less @@ -0,0 +1,67 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .w-ecomp-get-access-home { + .bg_w; + position: @page-main-position; + top: @page-main-top; + left: @page-main-left; + right: @page-main-right; + bottom: @page-main-bottom; + padding-top: @padding-top; + padding-left: @padding-left-side; + + .get-access-home-container { + .content_justify; + position: relative; + padding-right: 0; + padding-left: 0; + padding-bottom: 32px; + width: 100%; + + .get-access-home-title { + .a24r; + margin: auto; + .content_justify; + } + + .get-access-general-div { + margin: auto; + padding-top: 15px; + padding-bottom: 15px; + .content_justify; + } + } + + .get-access-table { + width: @table-width; + margin: @table-margin; + + .table-control { + .table-dropdown-filter { + width: @table-dropdown-filter-width; + display: @table-dropdown-filter-display; + } + } + + .table-body { + cursor: pointer; + } + } +} diff --git a/ecomp-portal-FE/client/app/views/support/get-access/get-access.tpl.html b/ecomp-portal-FE/client/app/views/support/get-access/get-access.tpl.html new file mode 100644 index 00000000..3ed92f14 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/support/get-access/get-access.tpl.html @@ -0,0 +1,88 @@ + +
+
+
+
Get Access
+
+ + Request access for following functions by sending email to the Application's Admin. For Admin contact details, please click here. + +
+
+
+ + +
+ + + + + + + + + + + + + + + + + +
{{access.getAccessTableHeaders[0]}}{{access.getAccessTableHeaders[1]}}{{access.getAccessTableHeaders[2]}}
+
+
+
+
+
+
+
+
+
+
+
+
+
+ diff --git a/ecomp-portal-FE/client/app/views/tabs/tabframe.html b/ecomp-portal-FE/client/app/views/tabs/tabframe.html new file mode 100644 index 00000000..bc428832 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/tabs/tabframe.html @@ -0,0 +1,22 @@ + + diff --git a/ecomp-portal-FE/client/app/views/tabs/tabs.controller.js b/ecomp-portal-FE/client/app/views/tabs/tabs.controller.js new file mode 100644 index 00000000..0c970f0e --- /dev/null +++ b/ecomp-portal-FE/client/app/views/tabs/tabs.controller.js @@ -0,0 +1,231 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +(function () { + const HTTP_PROTOCOL_RGX = /https?:\/\//; + class TabsCtrl { + constructor(applicationsService, $log, $window, conf, userProfileService, $scope,$cookies,$rootScope,confirmBoxService) { + + var counter = 1; + var tabLimit = 6; + this.conf = conf; + var cookieDomain = this.conf.cookieDomain; + $scope.tabs = []; + $scope.notificationShow=true; + $rootScope.showFooter = ""; + console.log("****************** get cookie domain from config json file " + this.conf.cookieDomain); + $cookies.putObject('show_app_header', false,{domain: cookieDomain, path : '/'}); + + + let noRefresh = function () { + window.onbeforeunload = function(e) { + + var isQtoHref = false; + try{ + isQtoHref = e.srcElement.activeElement.href.includes("mailto"); + } catch(err) { + + } + + if ($scope.tabs.length > 1 && isQtoHref == false) { + return "Changes you made may not be saved. Are you sure you want to refresh?"; + } else { + return null; + } + } + } + var addTab = function (title, content) { + if($scope.tabs.length==tabLimit){ + confirmBoxService.showInformation('You have reached your maximum limit of tabs allowed.').then(isConfirmed => {}); + } else { + if(title!=='Home' && content.indexOf('https') == -1){ + console.log('App URL: '+content+'. The application URL you are trying to open is not HTTPS. We recommend to use secured HTTPS URL while on-boarding the application.'); + } + + $scope.tabs.push({ title: title, content: content }); + counter++; + $scope.selectedIndex = $scope.tabs.length - 1; + if ($scope.tabs.length > 1) { + noRefresh(); + } + $cookies.putObject('cookieTabs', $scope.tabs,{domain: cookieDomain, path : '/'}); + $cookies.putObject('visInVisCookieTabs', $scope.tabs,{domain: cookieDomain, path : '/'}); + } + }; + + var adjustTitle = function (title) { + var index = 15; + var nonEmptyCharPattern = /(\s|\w)/; + var adjustedTitle = title.substring(0,index); + var ext = title.charAt(index).replace(nonEmptyCharPattern,'...'); + return adjustedTitle.concat(ext); + + + }; + + var removeTab = function (event, index) { + event.preventDefault(); + event.stopPropagation(); + $scope.tabs.splice(index, 1); + $cookies.putObject('cookieTabs', $scope.tabs,{domain: cookieDomain, path : '/'}); + }; + + var selectTab = function (title) { + if(title=='Home') { + $rootScope.ContentModel.IsVisible=true; + $rootScope.showFooter = true; + $rootScope.tabBottom = 75; + } + else { + $rootScope.ContentModel.IsVisible=false; + $rootScope.showFooter = false; + $rootScope.tabBottom = 0; + } + }; + + $scope.addTab = addTab; + $scope.removeTab = removeTab; + $scope.selectTab = selectTab; + $scope.adjustTitle = adjustTitle; + + + $rootScope.ContentModel = { + IsVisible : false, + ViewUrl : null, + }; + + + var sessionActive = applicationsService.ping() + .then(sessionActive => { + $log.debug('TabsCtrl::addTab: applicationsService.ping() = ' + JSON.stringify(sessionActive)); + + var cookieTabs = $cookies.getObject('cookieTabs'); + if(cookieTabs!=null){ + for(var t in cookieTabs){ + console.log('TabsCtrl::addTab: cookieTabs title: '+cookieTabs[t].title); + if(cookieTabs[t].title!=null && cookieTabs[t].title==='Home'){ + cookieTabs[t].content = ""; + $rootScope.ContentModel.IsVisible=true; + } + + addTab( cookieTabs[t].title, cookieTabs[t].content) ; + } + } else { + for (var i = 0; i < 1; i++) { + var content=""; + var title=""; + if(i==0){ + title="Home"; + $rootScope.ContentModel.IsVisible=true; + } + addTab(title, content); + } + } + + $scope.selectedIndex = 0; + }); + + $scope.$watchCollection(function() { return $cookies.getObject('addTab'); }, function(newValue) { + var tabContent = $cookies.getObject('addTab'); + if(tabContent!=null && tabContent.url!=null){ + var tabExists = false; + for(var x in $scope.tabs){ + console.log($scope.tabs[x].content); + if($scope.tabs[x].title==tabContent.title){ + tabExists = true; + $scope.selectedIndex = x; + } + } + if(!tabExists){ + addTab( tabContent.title, tabContent.url) ; + } + $cookies.remove('addTab'); + } + }); + + + } + + + } + + TabsCtrl.$inject = ['applicationsService', '$log', '$window', 'conf','userProfileService', '$scope','$cookies','$rootScope','confirmBoxService']; + angular.module('ecompApp').controller('TabsCtrl', TabsCtrl); + + angular.module('ecompApp').directive('mainArea', function() { + return { + restrict: "E", + templateUrl: 'app/views/tabs/tabframe.html', + link: function(scope, element) { + + } + } + }); + + + + angular.module('ecompApp').directive('tabHighlight', [function () { + return { + restrict: 'A', + link: function (scope, element) { + var x, y, initial_background = '#c3d5e6'; + + element + .removeAttr('style') + .mousemove(function (e) { + if(!element.hasClass('md-active')) + { + x = e.pageX - this.offsetLeft; + y = e.pageY - this.offsetTop; + + element + .css({ background: '-moz-radial-gradient(circle at ' + x + 'px ' + y + 'px, rgba(255,255,255,0.4) 0px, rgba(255,255,255,0.0) 45px), ' + initial_background }) + .css({ background: '-webkit-radial-gradient(circle at ' + x + 'px ' + y + 'px, rgba(255,255,255,0.4) 0px, rgba(255,255,255,0.0) 45px), ' + initial_background }) + .css({ background: 'radial-gradient(circle at ' + x + 'px ' + y + 'px, rgba(255,255,255,0.4) 0px, rgba(255,255,255,0.0) 45px), ' + initial_background }); + } + }) + .mouseout(function () { + element.removeAttr('style'); + }); + } + }; + }]); + + + +})(); + +function getParameterByName(name, url) { + if (!url) url = window.location.href; + name = name.replace(/[\[\]]/g, "\\$&"); + var regex = new RegExp("[?&]" + name + "(=([^&#]*)|&|#|$)"), + results = regex.exec(url); + if (!results) return ''; + if (!results[2]) return ''; + return (results[2].replace(/\+/g, " ")); +} + +function isCascadeFrame(ref) { + if (self != top) { + var e = document.body; + e.parentNode.removeChild(e); + window.location = "unKnownError"; + } +} diff --git a/ecomp-portal-FE/client/app/views/tabs/tabs.controller.spec.js b/ecomp-portal-FE/client/app/views/tabs/tabs.controller.spec.js new file mode 100644 index 00000000..44aea239 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/tabs/tabs.controller.spec.js @@ -0,0 +1,80 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +describe('Controller: TabsCtrl ',() => { + beforeEach(module('ecompApp')); + + beforeEach(inject((_CacheFactory_)=>{ + _CacheFactory_.destroyAll(); + })); + + let TabsCtrl, $controller, $q, $rootScope, $log, $window, $cookies,$scope; + + beforeEach(inject((_$controller_, _$q_, _$rootScope_, _$log_, _$window_, _$cookies_)=>{ + [$controller, $q, $rootScope, $log, $window, $cookies] = [_$controller_, _$q_, _$rootScope_, _$log_, _$window_, _$cookies_]; + })); + + var deferredApps, deferredUserProfile; + beforeEach(()=>{ + deferredApps = $q.defer(); + deferredUserProfile = $q.defer(); + let applicationsServiceMock = jasmine.createSpyObj('applicationsServiceMock', ['getUserApps']); + applicationsServiceMock.getUserApps.and.returnValue(deferredApps.promise); + + let userProfileServiceMock = jasmine.createSpyObj('userProfileServiceMock',['getUserProfile']); + userProfileServiceMock.getUserProfile.and.returnValue(deferredUserProfile.promise); + + $scope = $rootScope.$new(); + TabsCtrl = $controller('TabsCtrl', { + applicationsService: applicationsServiceMock, + $log: $log, + $window: $window, + userProfileService: userProfileServiceMock, + $scope: $scope, + $cookies: $cookies, + $rootScope: $rootScope + }); + }); + + it('should populate this.apps with data from portals service getUserApps', ()=>{ + var profile = {roles:'superAdmin',userId:'userid'}; + deferredUserProfile.resolve(profile); + deferredApps.resolve([{name: 'portal1'},{name: 'portal2'},{name: 'portal3'}]); + $rootScope.$apply(); + expect($scope.appsViewData.length).toBe(3); + }); + + it('should call $log error when getAllPortals fail', ()=>{ + spyOn($log, 'error'); + deferredUserProfile.reject('something happened!'); + $rootScope.$apply(); + expect($log.error).toHaveBeenCalled(); + }); + + it('should open link in a new window when clicking app thumbnail', () => { + spyOn($window, 'open'); + let someUrl = 'http://some/url/'; + TabsCtrl.goToPortal(someUrl); + expect($window.open).toHaveBeenCalledWith(someUrl, '_self'); + }); + + +}); diff --git a/ecomp-portal-FE/client/app/views/tabs/tabs.less b/ecomp-portal-FE/client/app/views/tabs/tabs.less new file mode 100644 index 00000000..0247e3d0 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/tabs/tabs.less @@ -0,0 +1,658 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .w-ecomp-tabs { + .bg_s; + + position: fixed; + left: 0; + right: 0; + bottom: @footer-height; + overflow-y: hidden; + top: @header-height; + padding-left: 0; + + .go-button { + .btn-green; + width: 96px; + position: absolute; + border-radius: 0px; + } + + .tabs-container { + .content_justify; + position: relative; + padding: 15px 0 32px 0; + width: 100%; + + .tabs-title { + .a24r; + margin: auto; + .content_justify; + } + .portals-list { + min-height: 70vh; + justify-content: center; + flex-flow: row wrap; + width: 1170px; + + margin: auto; + margin-bottom: 63px; + + .app-gridster-header { + background-color: @u; + } + + .app-gridster-footer { + background-color: @u; + } + + .portals-list-item { + background-color: @u; + border-radius: 2px; + box-shadow: 0px -1px 2px 0px rgba(0, 0, 0, 0.1); + display: inline-block; + width: 360px; + height: 300px; + background-size: cover; + cursor: pointer; + margin: 15px; + overflow: hidden; + + .portals-item-info { + background-color: @u; + height: 120px; + top: 180px; + position: relative; + box-shadow: 0px -1px 2px 0px rgba(0, 0, 0, 0.1); + padding: 16px; + + .info-title { + .a24r; + margin-bottom: 4px; + + text-overflow: ellipsis; + overflow: hidden; + } + .info-description { + .c16r; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + } + .info-button { + .btn-green; + width: 96px; + position: absolute; + bottom: 16px; + left: 16px; + } + + &:hover { + opacity: .93; + z-index: 3; + } + } + } + } + } +} + + +.build-number { + .o12i; +} + +@keyframes fadein { + from { + opacity: 0; + } + to { + opacity: 1; + } +} + + + +.tab-container { + background: #8dc8fb; + margin: 0; + padding: 0; + max-height: 40px; +} +.tab-container ul.nav-tabs { + margin: 0; + list-style-type: none; + line-height: 40px; + max-height: 40px; + overflow: hidden; + display: inline-block; + display: -webkit-flex; + display: flex; + padding-right: 20px; + border-bottom: 5px solid #f7f7f7; +} +.tab-container ul.nav-tabs > li { + margin: 5px -14px 0; + -moz-border-radius-topleft: 28px 145px; + -webkit-border-top-left-radius: 28px 145px; + border-top-left-radius: 28px 145px; + -moz-border-radius-topright: 28px 145px; + -webkit-border-top-right-radius: 28px 145px; + border-top-right-radius: 28px 145px; + padding: 0 30px 0 25px; + height: 170px; + background: #c3d5e6; + position: relative; + -moz-box-shadow: 0 4px 6px rgba(0, 0, 0, 0.5); + -webkit-box-shadow: 0 4px 6px rgba(0, 0, 0, 0.5); + box-shadow: 0 4px 6px rgba(0, 0, 0, 0.5); + width: 200px; + max-width: 200px; + min-width: 20px; + border: 1px solid #aaa; +} +.tab-container ul.nav-tabs > li:first-child { + margin-left: 0; +} +.tab-container ul.nav-tabs > li:last-of-type { + margin-right: 0; +} +.tab-container ul.nav-tabs > li > a { + display: block; + max-width: 100%; + text-decoration: none; + color: #222; + padding: 3px 7px; +} +.tab-container ul.nav-tabs > li > a span { + overflow: hidden; + white-space: nowrap; + display: block; +} +.tab-container ul.nav-tabs > li > a:focus, .tab-container ul.nav-tabs > li > a:hover { + background-color: transparent; + border-color: transparent; +} +.tab-container ul.nav-tabs > li > a .glyphicon-remove { + color: #777; + display: inline-block; + padding: 3px; + font-size: 10px; + position: absolute; + z-index: 10; + top: 7px; + right: -10px; + -moz-border-radius: 50%; + -webkit-border-radius: 50%; + border-radius: 50%; +} +.tab-container ul.nav-tabs > li > a .glyphicon-remove:hover { + background: #d39ea3; + color: white; + -moz-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.25); + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.25); + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.25); + text-shadow: 0 1px 1px rgba(0, 0, 0, 0.25); +} +.tab-container ul.nav-tabs > li.active { + z-index: 4; + background-image: url('data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0idXRmLTgiPz4gPHN2ZyB2ZXJzaW9uPSIxLjEiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJncmFkIiBncmFkaWVudFVuaXRzPSJvYmplY3RCb3VuZGluZ0JveCIgeDE9IjAuNSIgeTE9IjAuMCIgeDI9IjAuNSIgeTI9IjEuMCI+PHN0b3Agb2Zmc2V0PSIwJSIgc3RvcC1jb2xvcj0iI2ZmZmZmZiIvPjxzdG9wIG9mZnNldD0iMTAwJSIgc3RvcC1jb2xvcj0iI2Y3ZjdmNyIvPjwvbGluZWFyR3JhZGllbnQ+PC9kZWZzPjxyZWN0IHg9IjAiIHk9IjAiIHdpZHRoPSIxMDAlIiBoZWlnaHQ9IjEwMCUiIGZpbGw9InVybCgjZ3JhZCkiIC8+PC9zdmc+IA=='); + background-size: 100%; + background-image: -webkit-gradient(linear, 50% 0%, 50% 30, color-stop(0%, #ffffff), color-stop(100%, #f7f7f7)); + background-image: -moz-linear-gradient(#ffffff, #f7f7f7 30px); + background-image: -webkit-linear-gradient(#ffffff, #f7f7f7 30px); + background-image: linear-gradient(#ffffff, #f7f7f7 30px); +} +.tab-container ul.nav-tabs > li.active > a { + background-color: transparent; + border-color: transparent; + border-bottom-color: transparent; +} +.tab-container ul.nav-tabs > li.active > a:focus, .tab-container ul.nav-tabs > li.active > a:hover { + background-color: transparent; + border-color: transparent; + border-bottom-color: transparent; +} +.tab-container ul.nav-tabs .btn { + float: left; + height: 20px; + width: 35px; + min-width: 35px; + max-width: 35px; + margin: 10px 0 0 0; + border-color: #71a0c9; + outline: none; + -moz-transform: skew(30deg); + -ms-transform: skew(30deg); + -webkit-transform: skew(30deg); + transform: skew(30deg); +} +.tab-container ul.nav-tabs .btn.btn-default { + background: #c3d5e6; +} +.tab-container ul.nav-tabs .btn.btn-default:hover { + background: #d2deeb; +} +.tab-container ul.nav-tabs .btn.btn-default:active { + background: #9cb5cc; +} +.tab-container .tab-pane { + padding: 0px 0px; + text-align: center; +} +.tab-container .tab-pane.active { + border-top: 1px solid #ddd; +} + +.tab-container md-content { + background-color: transparent !important; } + .tab-container md-content md-tabs { + border: 1px solid #e1e1e1; } + .tab-container md-content md-tabs md-tab-content { + background: #f6f6f6; } + .tab-container md-content md-tabs md-tabs-canvas { + background: white; } + .tab-container md-content h1:first-child { + margin-top: 0; } +.tab-container md-input-container { + padding-bottom: 0; } +.tab-container .remove-tab { + margin-bottom: 40px; } +.tab-container .demo-tab > div > div { + padding: 25px; + box-sizing: border-box; } +.tab-container .edit-form input { + width: 100%; } +.tab-container md-tabs { + border-bottom: 1px solid rgba(0, 0, 0, 0.12); } +.tab-container md-tab[disabled] { + opacity: 0.5; } +.tab-container label { + text-align: left; } +.tab-container .long > input { + width: 264px; } +.tab-container .md-button.add-tab { + transform: translateY(5px); } + +.md-tab{ + font-size: 13px; + line-height: 30px; + margin: 5px -3px 0; + border-top-left-radius: 88px 205px; + border-top-right-radius: 88px 205px; + padding: 0 30px 0 25px; + height: 40px; + background: #c3d5e6; + position: relative; + box-shadow: 0 4px 6px rgba(0,0,0,.5); + width: 180px; + max-width: 200px; + min-width: 20px; + border: 1px solid #aaa; + text-transform: capitalize; + text-align: left; +} + +md-tabs .md-tab { + color: #222; +} + +md-tabs-canvas { + border-bottom: 5px solid #f7f7f7; + height: 40px; +} +.md-tab.md-active { + z-index: 4; + background-color: #f5f5f5 !important; +} +.md-tab:first-child{ + margin-left: 10px; +} +md-ink-bar{ + z-index: 5 !important; +} + +.glyphicon { + position: fixed; + line-height: 4; +} +.close_button { + font-size: x-small;width: 10px;margin-left: 130px; +} +@media all and (-ms-high-contrast: none), (-ms-high-contrast: active) { + .close_button { + font-size: x-small;width: 10px;margin-left: 130px;margin-top: 55px; + } +} + +*, +*:after, +*:before +{ + -moz-box-sizing: border-box; + -webkit-box-sizing: border-box; + box-sizing: border-box; +} + + +.button-default +{ + .transition(@transitionDefault color); + background: transparent; + border: none; + cursor: pointer; + margin: 0; + outline: none; + position: relative; +} + +.show-notifications +{ + position: relative; + + &:hover, + &:focus, + &.active + { + #icon-bell + { + fill: @colorWetAsphalt; + } + } + + #icon-bell + { + fill: @colorAsbestos; + } + + + + &.active ~ .notifications + { + opacity: 1; + top: 35px; + } +} +.notifications_li{ + border-top: 1px solid #bdc3c7; + color: #7f8c8d; + cursor: default; + display: block; + padding: 10px; + position: relative; + white-space: nowrap; + width: 350px; +} +.notifications_li:hover{ + background:#eee; +} +.notifications_detail{ + margin-left: 10px; + white-space: normal; + width: 280px; + display: inline-block; + vertical-align: middle; +} + +.notifications_empty{ + display: none; + text-align: center; +} +.notifications_title{ + display: block; +} + +.notifications_date{ + color: #95a5a6; + font-size: .85em; + margin-top: 3px; +} +.notifications +{ + .border-radius(@borderRadius); + .transition(@transitionDefault opacity); + background: @colorClouds; + border: 1px solid @colorSilver; + left: 10px; + opacity: 0; + + &:after + { + border: 10px solid transparent; + border-bottom-color: @colorPeterRiver; + content: ''; + display: block; + height: 0; + left: 10px; + position: absolute; + top: -20px; + width: 0; + } + + h3, + .show-all + { + background: @colorPeterRiver; + color: @colorWhite; + margin: 0; + padding: 10px; + width: 350px; + } + + h3 + { + cursor: default; + font-size: 1.05em; + font-weight: normal; + } + + .show-all + { + display: block; + text-align: center; + text-decoration: none; + + &:hover, + &:focus + { + text-decoration: underline; + } + } + + .notifications-list + { + list-style: none; + margin: 0; + overflow: hidden; + padding: 0; + + .item + { + .transition-transform(@transitionDefault); + border-top: 1px solid @colorSilver; + color: @colorAsbestos; + cursor: default; + display: block; + padding: 10px; + position: relative; + white-space: nowrap; + width: 350px; + + &:before, + .details, + .button-dismiss + { + display: inline-block; + vertical-align: middle; + } + + &:before + { + .border-radius(50%); + background: @colorPeterRiver; + content: ''; + height: 8px; + width: 8px; + } + + .details + { + margin-left: 10px; + white-space: normal; + width: 280px; + + .title, + .date + { + display: block; + } + + .date + { + color: @colorConcrete; + font-size: .85em; + margin-top: 3px; + } + } + + .button-dismiss + { + color: @colorSilver; + font-size: 2.25em; + + &:hover, + &:focus + { + color: @colorConcrete; + } + } + + &.no-data + { + display: none; + text-align: center; + + &:before + { + display: none; + } + } + + &.expired + { + color: @colorSilver; + + &:before + { + background: @colorSilver; + } + + .details + { + .date + { + color: @colorSilver; + } + } + } + + &.dismissed + { + .transform(translateX(100%)); + } + } + } + + &.empty + { + .notifications-list + { + .no-data + { + display: block; + padding: 10px; + } + } + } +} + +/* variables */ +@colorClouds: #ecf0f1; +@colorSilver: #bdc3c7; +@colorWhite: #fefefe; +@colorPeterRiver: #3498db; +@colorConcrete: #95a5a6; +@colorAsbestos: #7f8c8d; +@colorWetAsphalt: #34495e; + +@borderRadius: 2px; + +@transitionDefault: 0.25s ease-out 0.10s; + +/* mixins */ +.background-clip(@value: border-box) +{ + -moz-background-clip: @value; + -webkit-background-clip: @value; + background-clip: @value; +} + +.border-radius(@value: 5px) +{ + -moz-border-radius: @value; + -webkit-border-radius: @value; + border-radius: @value; + .background-clip(padding-box); +} + +.transform(@value) +{ + -webkit-transform: @value; + -moz-transform: @value; + -ms-transform: @value; + -o-transform: @value; + transform: @value; +} + +.transition(@value: all 0.25s ease-out) +{ + -webkit-transition: @value; + -moz-transition: @value; + -o-transition: @value; + transition: @value; +} + +.transition-transform(@transition: 0.25s ease-out) +{ + -webkit-transition: -webkit-transform @transition; + -moz-transition: -moz-transform @transition; + -o-transition: -o-transform @transition; + transition: transform @transition; +} + +.tab-cross-sign{ + position:relative; + margin-left:130px; + font-size:9px; + top:-30px; + @media screen and (-ms-high-contrast: active), (-ms-high-contrast: none) { + top:-70px; + } +} diff --git a/ecomp-portal-FE/client/app/views/tabs/tabs.tpl.html b/ecomp-portal-FE/client/app/views/tabs/tabs.tpl.html new file mode 100644 index 00000000..62af73e9 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/tabs/tabs.tpl.html @@ -0,0 +1,46 @@ + +
+
+ + + + + {{adjustTitle(tab.title)}} + + + + + + + + + + +
+
+ +
+
+ +
+
diff --git a/ecomp-portal-FE/client/app/views/userbar/userbar.controller.js b/ecomp-portal-FE/client/app/views/userbar/userbar.controller.js new file mode 100644 index 00000000..5dae2f86 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/userbar/userbar.controller.js @@ -0,0 +1,262 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; + +(function () { + + class UserbarCtrl { + constructor(userProfileService,userbarUpdateService, $log, $rootScope , $interval,$scope,$timeout,dashboardService) { + this.$log = $log; + this.userProfileService = userProfileService; + this.$rootScope = $rootScope; + $rootScope.isAdminPortalAdmin = false; + $scope.updateRate = 10000; //default online user bar refreshing rate + var intervalPromise = null; + $scope.myservice = userbarUpdateService; + $scope.userList=this.userLists; + var websocket = ''; + var currentUser = ''; + var remoteUser = ''; + var f = ''; + + + function socketSetup(initialPageVisit,_currentUser, _remoteUser, _f) { + + + + if( true) { + + var href = window.location.href; + var hostPatt = new RegExp(window.location.host +"/[^/]*"); + var res = hostPatt.exec(href); + var protocol = window.location.protocol.replace("http","ws"); + var signalingServerPath = protocol + "//" + res + "/opencontact"; + var wsUri = signalingServerPath; + console.log("Connecting to " + wsUri); + websocket = new WebSocket(wsUri); + //localStorage.notifySocket = JSON.stringify(websocket); + //window.top.notifySocket = websocket; + + currentUser = _currentUser; + remoteUser = _remoteUser; + f = socketSend; + + + } + + //var websocket = JSON.parse(localStorage.notifySocket || "{}") ; + if( websocket != null) { + websocket.onopen = function(evt) { onOpen(evt); }; + websocket.onmessage = function(evt) { onMessage(evt); }; + websocket.onerror = function(evt) { onError(evt); }; + + } + + //if(f != undefined) + // f(); + + //window.top.notifySocket.send(""); + } + + function socketSend(currentUser, remoteUser) { + + + + websocket.send(JSON.stringify({ + from: currentUser, + to: remoteUser + })); + + //window.top.notifySocket.send(""); + } + + + + + function onOpen(evt) { + console.log("onOpen"); + //writeToScreen("CONNECTED"); + + if(f != undefined) + f(currentUser, remoteUser); + + } + + function onMessage(evt) { + if (typeof evt.data == "string") { + writeToScreen("RECEIVED (text): " + evt.data); + var chatObject = JSON.parse(evt.data); + if(confirm("User " + chatObject.from + " is requesting a chat session with you. Please click ok to accept")== true) { + + var url = userProfileService.getSortedUserIdCombination(chatObject.from, chatObject.to); + var win = window.open(url, '_blank'); + win.focus(); + } else { + // + } + + + } else { + writeToScreen("RECEIVED (binary): " + evt.data); + } + } + + function onError(evt) { + writeToScreen('ERROR: ' + evt.data); + } + + function writeToScreen(message) { + console.log(message); + } + + function callAtInterval() { + userProfileService.getActiveUser() + .then(res=> { + $log.info('sasasasasa getting userinfo from shared context.. '); + if(res==null){ + $log.info('failed getting userinfo from shared context.. '); + $log.info('getting userinfo from session '); + }else{ + $log.info('getting ActiveUser successfully',res); + $scope.userList = []; + for(var i=0;i { + var footerOff = $('#online-userbar').offset().top; + var headOff = $('#footer').offset().top; + var userbarHeight= parseInt($(".online-user-container").css('height'),10); + var defaultOffSet = 45; + $(".online-user-container").css({ + "height" : headOff - footerOff-defaultOffSet + }); + }); + } + + + var intervalPromise; + dashboardService.getOnlineUserUpdateRate().then(res=> { + // $log.info('getting Online User Update Rate init***********************', res); + if (res == null || res.response == null) { + $log.error('UserbarCtlr: failed to get online user update rate!'); + } else { + // $log.debug('UserbarCtlr: got online User Update Rate ' + res.response); + var rate = parseInt(res.response.onlineUserUpdateRate); + // var updateRate = parseInt(res.response.onlineUserUpdateRate); + var duration = parseInt(res.response.onlineUserUpdateDuration); + userbarUpdateService.setMaxRefreshCount(parseInt(duration/rate)+1); + userbarUpdateService.setRefreshCount(userbarUpdateService.maxCount); + // $scope.refreshCount = userbarUpdateService.getRefreshCount(); + + if (rate != NaN && duration != NaN) { + // $log.debug('UserbarCtlr: scheduling function at interval ' + millis); + $scope.updateRate=rate; + $scope.start($scope.updateRate); + } + } + }).catch(err=> { + $log.error('Header Controller:: getOnlineUserUpdateRate() failed: ' + err); + }); + + $scope.start = function(rate) { + // stops any running interval to avoid two intervals running at the same time + $scope.stop(); + // store the interval promise + intervalPromise = $interval(updateActiveUsers, rate); + }; + + $scope.stop = function() { + $interval.cancel(intervalPromise); + }; + + $scope.$watch('myservice.getRefreshCount()', function (newVal,oldVal) { + //$log.info("refresh "+$scope.myservice.refreshCount + " more time(s)"); + if (newVal<=0) { + // $log.info("UserbarCtrl: stopped refreshing online users"); + $scope.stop(); + } else if (newVal== $scope.myservice.maxCount){ + // $log.info("UserbarCtrl: start refreshing online users at every "+($scope.updateRate/1000)+" sec"); + // initial update of activate users + userProfileService.getUserProfile().then(res=> { + if (res == null || res.orgUserId == null) { + $log.error('UserbarCtlr: failed to get profile of the user!'); + } + else { + updateActiveUsers(); + $scope.start($scope.updateRate); + socketSetup(null, res.orgUserId, null, "socketSend"); + } + }); + + + } + }); + function updateActiveUsers() { + userProfileService.getActiveUser() + .then(res=> { + $log.info('getting Active User init***********************'); + // decrement the counter every time updateActiveUser is called; + userbarUpdateService.decrementRefreshCount(); + + if(res==null ||res.status!='OK'){ + $log.error('failed updateActiveUsers res is null.. '); + + }else{ + $log.info('getting ActiveUser successfully',res); + $scope.userList = []; + var maxItems = 10; + var users = res.response; + if (users.length < maxItems) + maxItems = users.length; + for(var i=0;i { + var footerOff = $('#online-userbar').offset().top; + var headOff = $('#footer').offset().top; + var userbarHeight= parseInt($(".online-user-container").css('height'),10); + var defaultOffSet = 45; + $(".online-user-container").css({ + "height" : headOff - footerOff-defaultOffSet + }); + }); + } + } + } + UserbarCtrl.$inject = ['userProfileService', 'userbarUpdateService', '$log', '$rootScope','$interval','$scope','$timeout','dashboardService']; + angular.module('ecompApp').controller('UserbarCtrl', UserbarCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/userbar/userbar.less b/ecomp-portal-FE/client/app/views/userbar/userbar.less new file mode 100644 index 00000000..489185f7 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/userbar/userbar.less @@ -0,0 +1,41 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .w-ecomp-sidebar { + + position: relative; + left: 0; + right: 0; + top: 5px; + padding-left: 0; + + } + + @media screen and (-webkit-min-device-pixel-ratio:0) +{ + .w-ecomp-sidebar { + + position: relative; + left: 0; + right: 0; + top: -5px; + padding-left: 0; + + } +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/views/userbar/userbar.tpl.html b/ecomp-portal-FE/client/app/views/userbar/userbar.tpl.html new file mode 100644 index 00000000..dab62910 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/userbar/userbar.tpl.html @@ -0,0 +1,20 @@ + + diff --git a/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.controller.js b/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.controller.js new file mode 100644 index 00000000..182ffe8f --- /dev/null +++ b/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.controller.js @@ -0,0 +1,211 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; +(function () { + class NewUserModalCtrl { + constructor($scope, $log, usersService, applicationsService, confirmBoxService) { + let init = () => { + $log.info('NewUserModalCtrl::init'); + this.isSaving = false; + this.anyChanges = false; + this.isGettingAdminApps = false; + if($scope.ngDialogData && $scope.ngDialogData.selectedUser && $scope.ngDialogData.dialogState){ + this.selectedUser = $scope.ngDialogData.selectedUser; + this.dialogState = $scope.ngDialogData.dialogState; + this.isShowBack = false; + if(this.dialogState === 3){ + this.getUserAppsRoles(); + } + }else{ + this.isShowBack = true; + this.selectedUser = null; + this.dialogState = 1; + } + }; + + this.appChanged = (index) => { + let myApp = this.adminApps[index]; + $log.debug('NewUserModalCtrl::appChanged: index: ', index, '; app id: ', myApp.id, 'app name: ',myApp.name); + myApp.isChanged = true; + this.anyChanges = true; + } + + this.deleteApp = (app) => { + let appMessage = this.selectedUser.firstName + ' ' + this.selectedUser.lastName; + confirmBoxService.deleteItem(appMessage).then(isConfirmed => { + if(isConfirmed){ + app.isChanged = true; + this.anyChanges = true; + app.isDeleted = true; + app.appRoles.forEach(function(role){ + role.isApplied = false; + }); + } + }).catch(err => { + $log.error('NewUserModalCtrl::deleteApp error: ',err); + }); + }; + + this.getUserAppsRoles = () => { + if (!this.selectedUser || !this.selectedUser.orgUserId) { + $log.error('NewUserModalCtrl::getUserAppsRoles error: No user is selected'); + this.dialogState = 1; + return; + } + $log.debug('NewUserModalCtrl::getUserAppsRoles: about to call getAdminAppsSimpler'); + this.isGettingAdminApps = true; + applicationsService.getAdminAppsSimpler().then((apps) => { + $log.debug('NewUserModalCtrl::getUserAppsRoles: beginning of then for getAdminAppsSimpler'); + this.isGettingAdminApps = false; + if (!apps || !apps.length) { + $log.error('NewUserModalCtrl::getUserAppsRoles error: no apps found'); + return null; + } + $log.debug('NewUserModalCtrl::getUserAppsRoles: then for getAdminAppsSimpler: step 2'); + $log.debug('NewUserModalCtrl::getUserAppsRoles: admin apps: ', apps); + this.adminApps = apps; + this.dialogState = 3; + this.userAppRoles = {}; + this.numberAppsProcessed = 0; + this.isLoading = true; + apps.forEach(app => { + $log.debug('NewUserModalCtrl::getUserAppsRoles: app: id: ', app.id, 'name: ',app.name); + app.isChanged = false; + app.isLoading = true; + app.isError = false; + app.isDeleted = false; + app.printNoChanges = false; + app.isUpdating = false; + app.isErrorUpdating = false; + app.isDoneUpdating = false; + app.errorMessage = ""; + usersService.getUserAppRoles(app.id, this.selectedUser.orgUserId).then((userAppRolesResult) => { + $log.debug('NewUserModalCtrl::getUserAppsRoles: got a result for app: ',app.id,': ',app.name,': ',userAppRolesResult); + app.appRoles = userAppRolesResult; + app.isLoading = false; + + }).catch(err => { + $log.error(err); + app.isError = true; + app.isLoading = false; + app.errorMessage = err.headers('FEErrorString'); + $log.debug('NewUserModalCtrl::getUserAppsRoles: in new-user.controller: response header: '+err.headers('FEErrorString')); + }).finally(()=>{ + this.numberAppsProcessed++; + if (this.numberAppsProcessed == this.adminApps.length) { + this.isLoading = false; + } + }); + }) + return; + }).catch(err => { + $log.error(err); + }) + + } + + this.getAdminApps = () => { + if (!this.selectedUser || !this.selectedUserorgUserId) { + $log.error('NewUserModalCtrl::getAdminApps: No user is selected'); + this.dialogState = 1; + return; + } + applicationsService.getAdminApps().promise().then(apps => { + if (!apps || !apps.length) { + $log.error('NewUserModalCtrl::getAdminApps: no apps found'); + return null; + } + $log.debug('NewUserModalCtrl::getAdminApps: admin apps: ', apps); + this.adminApps = apps; + this.dialogState = 3; + return; + }).catch(err => { + $log.error('NewUserModalCtrl::getAdminApps: ', err); + }) + + } + + this.updateUserAppsRoles = () => { + $log.debug('NewUserModalCtrl::updateUserAppsRoles: entering updateUserAppsRoles'); + if(!this.selectedUser || !this.selectedUser.orgUserId || !this.adminApps){ + $log.debug('NewUserModalCtrl::updateUserAppsRoles: returning early'); + return; + } + this.isSaving = true; + $log.debug('NewUserModalCtrl::updateUserAppsRoles: going to update user: ' + this.selectedUser.orgUserId); + this.numberAppsProcessed = 0; + this.numberAppsSucceeded = 0; + this.adminApps.forEach(app => { + if (app.isChanged) { + $log.debug('NewUserModalCtrl::updateUserAppsRoles: app roles have changed; going to update: id: ', app.id, '; name: ', app.name); + app.isUpdating = true; + usersService.updateUserAppRoles({orgUserId: this.selectedUser.orgUserId, appId: app.id, appRoles: app.appRoles}) + .then(res => { + $log.debug('NewUserModalCtrl::updateUserAppsRoles: User app roles updated successfully on app: ',app.id); + app.isUpdating = false; + app.isDoneUpdating = true; + this.numberAppsSucceeded++; + }).catch(err => { + $log.error(err); + app.isErrorUpdating = true; + }).finally(()=>{ + this.numberAppsProcessed++; + if (this.numberAppsProcessed == this.adminApps.length) { + this.isSaving = false; + } + if (this.numberAppsSucceeded == this.adminApps.length) { + $scope.closeThisDialog(true); + } + }) + } else { + $log.debug('NewUserModalCtrl::updateUserAppsRoles: app roles have NOT changed; NOT going to update: id: ', app.id, '; name: ', app.name); + app.noChanges = true; + app.isError = false; + this.numberAppsProcessed++; + this.numberAppsSucceeded++; + if (this.numberAppsProcessed == this.adminApps.length) { + this.isSaving = false; + } + if (this.numberAppsSucceeded == this.adminApps.length) { + $scope.closeThisDialog(true); + } + } + }); + }; + + this.navigateBack = () => { + if (this.dialogState === 1) { + } + if (this.dialogState === 3) { + this.dialogState = 1; + } + }; + + init(); + + $scope.$on('$stateChangeStart', e => { + e.preventDefault(); + }); + } + } + NewUserModalCtrl.$inject = ['$scope', '$log', 'usersService', 'applicationsService', 'confirmBoxService']; + angular.module('ecompApp').controller('NewUserModalCtrl', NewUserModalCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.controller.spec.js b/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.controller.spec.js new file mode 100644 index 00000000..54c564b7 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.controller.spec.js @@ -0,0 +1,222 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; + +describe('Controller: NewUserModalCtrl ', () => { + beforeEach(module('testUtils')); + beforeEach(module('ecompApp')); + + let promisesTestUtils; + beforeEach(inject((_CacheFactory_, _promisesTestUtils_)=> { + _CacheFactory_.destroyAll(); + promisesTestUtils = _promisesTestUtils_; + })); + + let newUser, $controller, $q, $rootScope, $log, $scope; + + let applicationsServiceMock, usersServiceMock, confirmBoxServiceMock; + let deferredAdminApps, deferredUsersAccounts, deferredUsersAppRoles, deferredUsersAppRoleUpdate; + + beforeEach(inject((_$controller_, _$q_, _$rootScope_, _$log_)=> { + $rootScope = _$rootScope_; + $q = _$q_; + $controller = _$controller_; + $log = _$log_; + })); + + beforeEach(()=> { + [deferredAdminApps, deferredUsersAccounts, deferredUsersAppRoles, deferredUsersAppRoleUpdate] = [$q.defer(),$q.defer(), $q.defer(), $q.defer()]; + + /*applicationsServiceMock = { + getAdminApps: () => { + var promise = () => {return deferredAdminApps.promise}; + var cancel = jasmine.createSpy(); + return { + promise: promise, + cancel: cancel + } + } + };*/ + + confirmBoxServiceMock = { + deleteItem: () => { + var promise = () => {return deferredAdminApps.promise}; + var cancel = jasmine.createSpy(); + return { + promise: promise, + cancel: cancel + } + } + }; + + applicationsServiceMock = jasmine.createSpyObj('applicationsServiceMock', ['getAdminAppsSimpler']); + applicationsServiceMock.getAdminAppsSimpler.and.returnValue(deferredAdminApps.promise); + + usersServiceMock = jasmine.createSpyObj('usersServiceMock', ['getAccountUsers','getUserAppRoles','updateUserAppsRoles']); + + usersServiceMock.getAccountUsers.and.returnValue(deferredUsersAccounts.promise); + usersServiceMock.getUserAppRoles.and.returnValue(deferredUsersAppRoles.promise); + usersServiceMock.updateUserAppsRoles.and.returnValue(deferredUsersAppRoleUpdate.promise); + + $scope = $rootScope.$new(); + newUser = $controller('NewUserModalCtrl', { + $scope: $scope, + $log: $log, + usersService: usersServiceMock, + applicationsService: applicationsServiceMock, + confirmBoxService: confirmBoxServiceMock + }); + }); + + it('should open modal window without user when no user is selected', ()=> { + expect(newUser.selectedUser).toBe(null); + }); + + it('should open modal window with selectedUser apps roles when user is selected', ()=> { + let roles = {apps: [{id: 1, appRoles: [{id: 3, isApplied: true}]}]}; + let someUser = {userId: 'asdfjl'}; + + deferredUsersAppRoles.resolve(roles); + deferredAdminApps.resolve(roles.apps); + + $scope.ngDialogData = { + selectedUser: someUser, + dialogState: 2 + }; + + newUser = $controller('NewUserModalCtrl', { + $scope: $scope, + $log: $log, + usersService: usersServiceMock, + applicationsService: applicationsServiceMock, + confirmBoxService: confirmBoxServiceMock + }); + + newUser.getUserAppsRoles(); + $scope.$apply(); + + expect(newUser.selectedUser).toBe(someUser); + expect(newUser.adminApps).toEqual(roles.apps); + }); + + it('should push to apps order list only apps that has applied roles when initializing', () => { + let roles = {apps: [{appId: 13, appRoles: [{id: 3, isApplied: true}]},{appId: 20, appRoles: [{id: 3, isApplied: false}]}]}; + let someUser = {userId: 'asdfjl'}; + + deferredUsersAppRoles.resolve(roles); + + $scope.ngDialogData = { + selectedUser: someUser, + dialogState: 2 + }; + + newUser = $controller('NewUserModalCtrl', { + $scope: $scope, + $log: $log, + usersService: usersServiceMock, + applicationsService: applicationsServiceMock, + confirmBoxService: confirmBoxServiceMock + }); + + $scope.$apply(); + + }); + + it('should push app to apps order list when applying at least one role to user from app', () => { + let roles = {apps: [{appId: 13, appRoles: [{id: 3, isApplied: true}]},{appId: 20, appRoles: [{id: 3, isApplied: false}]}]}; + let someUser = {userId: 'asdfjl'}; + + deferredUsersAppRoles.resolve(roles); + + $scope.ngDialogData = { + selectedUser: someUser, + dialogState: 2 + }; + + newUser = $controller('NewUserModalCtrl', { + $scope: $scope, + $log: $log, + usersService: usersServiceMock, + applicationsService: applicationsServiceMock, + confirmBoxService: confirmBoxServiceMock + }); + + $scope.$apply(); + + }); + + + it('should remove app from list when removing all user roles in it', () => { + let roles = {apps: [{appName: 'aaa', appId: 13, appRoles: [{id: 3, isApplied: true}]},{appName: 'vvv', appId: 20, appRoles: [{id: 3, isApplied: true}]}]}; + let someUser = {userId: 'asdfjl'}; + + promisesTestUtils.resolvePromise(confirmBoxServiceMock, 'deleteItem', true); + + deferredUsersAppRoles.resolve(roles); + + $scope.ngDialogData = { + selectedUser: someUser, + dialogState: 2 + }; + + newUser = $controller('NewUserModalCtrl', { + $scope: $scope, + $log: $log, + usersService: usersServiceMock, + applicationsService: applicationsServiceMock, + confirmBoxService: confirmBoxServiceMock + }); + + $scope.$apply(); + newUser.deleteApp(roles.apps[0]); + $scope.$apply(); + + }); + + it('should close the modal when update changes succeeded', () => { + let roles = {apps: [{appName: 'aaa', appId: 13, appRoles: [{id: 3, isApplied: true}]},{appName: 'vvv', appId: 20, appRoles: [{id: 3, isApplied: true}]}]}; + let someUser = {userId: 'asdfjl'}; + deferredUsersAppRoles.resolve(roles); + deferredUsersAppRoleUpdate.resolve(); + deferredAdminApps.resolve(roles.apps); + + $scope.ngDialogData = { + selectedUser: someUser, + dialogState: 2 + }; + + newUser = $controller('NewUserModalCtrl', { + $scope: $scope, + $log: $log, + usersService: usersServiceMock, + applicationsService: applicationsServiceMock, + confirmBoxService: confirmBoxServiceMock + }); + $scope.closeThisDialog = function(){}; + spyOn($scope, 'closeThisDialog'); + + newUser.getUserAppsRoles(); + $scope.$apply(); + newUser.updateUserAppsRoles(); + $scope.$apply(); + expect($scope.closeThisDialog).toHaveBeenCalledWith(true); + }); + }); diff --git a/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.modal.html b/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.modal.html new file mode 100644 index 00000000..e50c9d4a --- /dev/null +++ b/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.modal.html @@ -0,0 +1,70 @@ + +
+
+ +
+
Next +
+
Cancel
+
+
+
+
+
+
+ Access and roles: +
+
+
+
{{app.name | elipsis: 27}}
+
+ +
+
{{app.errorMessage}}
+
Contacting application...
+
No changes
+
Updating application...
+
Finished updating application
+
Could not update application...
+ +
+
+
+
+ +
Back
+
Save +
+
Cancel
+
+
+
+
diff --git a/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.modal.less b/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.modal.less new file mode 100644 index 00000000..9f86b022 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/users/new-user-dialogs/new-user.modal.less @@ -0,0 +1,126 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .new-user-modal { + display:block; + overflow:auto; + min-height: 450px; + + .user-apps-roles{ + .title{ + .n18r; + border-bottom: @a 3px solid; + } + + .app-roles-list{ + height: 286px; + overflow-y: auto; + + .app-item{ + border: 1px solid #d8d8d8; + border-radius: 2px; + background-color: #f8f8f8; + + padding: 10px; + margin-top: 8px; + + .app-item-left{ + padding-top: 0; + line-height: 30px; + height: 30px; + vertical-align: middle; + display:inline-block; + width: 45%; + border-radius: 2px; + border: 1px solid #d8d8d8; + margin-right: 10px; + padding-left: 4px; + background: #fff; + white-space: nowrap; + + } + .app-item-right{ + display:inline-block; + width: 45%; + border-radius: 2px; + border: 1px solid #d8d8d8; + background: #fff; + vertical-align: middle; + } + + .app-item-right-error{ + .k; + padding: 7px 7px 7px 7px; + display:inline-block; + width: 45%; + border-radius: 2px; + border: 1px solid #d8d8d8; + background: #fff; + vertical-align: middle; + } + + .app-item-right-contacting{ + .e; + padding: 7px 7px 7px 7px; + display:inline-block; + width: 45%; + border-radius: 2px; + border: 1px solid #d8d8d8; + background: #fff; + vertical-align: middle; + } + + .app-select-left{ + width: 45%; + margin-right: 10px; + vertical-align: middle; + + + .select-field{ + padding-top: 0; + line-height: 30px; + height: 30px; + vertical-align: middle; + border-radius: 2px; + border: 1px solid #d8d8d8; + margin-right: 10px; + padding-left: 4px; + background: #fff; + display:inline-block; + } + } + + + .app-item-delete{ + .ico_trash_default; + display: inline-block; + vertical-align: 2px; + cursor: pointer; + position: relative; + top: 6px; + color: transparent; + margin-left: 8px; + + } + + } + } + + } +} diff --git a/ecomp-portal-FE/client/app/views/users/users.controller.js b/ecomp-portal-FE/client/app/views/users/users.controller.js new file mode 100644 index 00000000..433b24e4 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/users/users.controller.js @@ -0,0 +1,187 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +(function () { + class UsersCtrl { + constructor($log, applicationsService, usersService, $scope, ngDialog,$timeout) { + this.$log = $log; + $scope.adminAppsIsNull = false; + $scope.appsIsDown = false; + + $log.info('UsersCtrl:: initializing...'); + let activeRequests = []; + let clearReq = (req) => { + activeRequests.splice(activeRequests.indexOf(req), 1); + }; + + let getAdminApps = () => { + $log.debug('UsersCtrl::getAdminApps: - Starting getAdminApps'); + try { + this.isLoadingTable = true; + var adminAppsReq = applicationsService.getAdminApps(); + + activeRequests.push(adminAppsReq); + adminAppsReq.promise().then(apps => { + $log.debug('UsersCtrl::getAdminApps: Apps for this user are: ' + JSON.stringify(apps)); + $log.debug('UsersCtrl::getAdminApps: Apps length: ' + apps.length); + var res1 = apps.sort(getSortOrder("name")); + if (!res1 || !res1.length) { + $log.error('UsersCtrl::getAdminApps: - no apps found'); + return null; + } + for (let i = 0; i < apps.length; i++) { + res1[i].index = i; + res1[i].value = apps[i].name; + res1[i].title = apps[i].name; + } + + this.adminApps = apps; + this.selectedApp = apps[0]; + clearReq(adminAppsReq); + $scope.adminAppsIsNull = false; + }).catch(e => { + $scope.adminAppsIsNull = true; + $log.error('UsersCtrl::getAdminApps: - getAdminApps() failed = '+ e.message); + clearReq(adminAppsReq); + }).finally(() => { + this.isLoadingTable = false; + }); + } catch (e) { + $scope.adminAppsIsNull = true; + $log.error('UsersCtrl::getAdminApps: - getAdminApps() failed!'); + this.isLoadingTable = false; + } + }; + + let getSortOrder = (prop) => { + return function(a, b) { + if (a[prop] > b[prop]) { + return 1; + } else if (a[prop] < b[prop]) { + return -1; + } + return 0; + } + } + + this.updateUsersList = () => { + $scope.appsIsDown = false; + $log.debug('UsersCtrl::updateUsersList: Starting updateUsersList'); + this.searchString = ''; + this.isAppSelectDisabled = true; + this.isLoadingTable = true; + usersService.getAccountUsers(this.selectedApp.id) + .then(accountUsers => { + $log.debug('UsersCtrl::updateUsersList length: '+ Object.keys(accountUsers).length); + this.isAppSelectDisabled = false; + this.accountUsers = accountUsers; + }).catch(err => { + this.isAppSelectDisabled = false; + $log.error('UsersCtrl::updateUsersList: ' + err); + $scope.appsIsDown = true; + }).finally(() => { + this.isLoadingTable = false; + }); + }; + + + let init = () => { + this.isLoadingTable = false; + this.selectedApp = null; + this.isAppSelectDisabled = false; + getAdminApps(); + + this.searchString = ''; + this.usersTableHeaders = ['First Name', 'Last Name', 'User ID', 'Roles']; + this.accountUsers = []; + }; + + this.openAddNewUserModal = (user) => { + let data = null; + if (user) { + data = { + dialogState: 3, + selectedUser: { + orgUserId: user.orgUserId, + firstName: user.firstName, + lastName: user.lastName + } + } + } + ngDialog.open({ + templateUrl: 'app/views/users/new-user-dialogs/new-user.modal.html', + controller: 'NewUserModalCtrl', + controllerAs: 'newUser', + data: data + }).closePromise.then(needUpdate => { + if (needUpdate.value === true) { + $log.debug('UsersCtrl::openAddNewUserModal updating table data...'); + this.updateUsersList(); + } + }); + }; + + this.openEditUserModal = (loginId) => { + var data = { + loginId : loginId, + updateRemoteApp : true, + appId : this.selectedApp!=null?this.selectedApp.id:'' + } + var modalInstance = ngDialog.open({ + templateUrl: 'app/views/header/user-edit/edit-user.tpl.html', + controller: 'editUserController', + data: data, + resolve: { + message: function message() { + var message = { + type: 'Contact', + }; + return message; + } + } + }).closePromise.then(needUpdate => { + //update selected app's database for this user. + console.log("'''''''''''''''''' now updating user list after update remote server"); + $timeout(this.updateUsersList, 1500); + }); + } + + + $scope.$watch('users.selectedApp', (newVal, oldVal) => { + if (!newVal || _.isEqual(newVal, oldVal)) { + return; + } + $log.debug('UsersCtrl::openAddNewUserModal:$watch selectedApp -> Fire with: ', newVal); + this.accountUsers = []; + this.updateUsersList(); + }); + + $scope.$on('$destroy', () => { + activeRequests.forEach(req => { + req.cancel(); + }); + }); + + init(); + } + } + UsersCtrl.$inject = ['$log', 'applicationsService', 'usersService', '$scope', 'ngDialog','$timeout']; + angular.module('ecompApp').controller('UsersCtrl', UsersCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/users/users.controller.spec.js b/ecomp-portal-FE/client/app/views/users/users.controller.spec.js new file mode 100644 index 00000000..34042c14 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/users/users.controller.spec.js @@ -0,0 +1,19 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ diff --git a/ecomp-portal-FE/client/app/views/users/users.less b/ecomp-portal-FE/client/app/views/users/users.less new file mode 100644 index 00000000..ff2d815f --- /dev/null +++ b/ecomp-portal-FE/client/app/views/users/users.less @@ -0,0 +1,59 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .users-page-main{ + .bg_w; + position: @page-main-position; + top: @page-main-top; + left: @page-main-left; + right: @page-main-right; + bottom: @page-main-bottom; + padding-top: @padding-top; + overflow-y: @page-main-overflow-y; + padding-left: @padding-left-side; + + .users-table { + width: @table-width; + margin: @table-margin; + + } + + .error-text { + width: 1170px; + margin: auto; + padding: 20px; + left: 20px; + font-weight: bold; + font-size: 16px; + text-align: left; + color: @err; + background-color: @u; + + .error-help { + color: @o; + font-weight: normal; + } + + .error-help-bold { + color: @o; + font-weight: bold; + } + + } +} diff --git a/ecomp-portal-FE/client/app/views/users/users.tpl.html b/ecomp-portal-FE/client/app/views/users/users.tpl.html new file mode 100644 index 00000000..88a3b62d --- /dev/null +++ b/ecomp-portal-FE/client/app/views/users/users.tpl.html @@ -0,0 +1,105 @@ + +
+
+
+
Users
+
+ + +
+
+
+
+ + +
Add User
+
+
+
+

Attention:

+

 

+

Select "Add User" in order to add User and Roles to the '{{users.selectedApp.name}}' Application.

+
+
+ +
+ + + + + + + + + + + + + + + + + +
{{users.usersTableHeaders[0]}}{{users.usersTableHeaders[1]}}{{users.usersTableHeaders[2]}}{{users.usersTableHeaders[3]}}
+
+
+
+
+
+
+ +
+
+
+
+
+ +
+
+

Attention:

+

 

+

It appears that you have not been added as an admin yet to an application.

+

 

+

Click on the Admins link to the left and check and see if you are listed as an admin for an application. + If not, you can add yourself to the appropriate application.

+
+
+
+ +
diff --git a/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.controller.js b/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.controller.js new file mode 100644 index 00000000..f50e4683 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.controller.js @@ -0,0 +1,202 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + +'use strict'; +(function () { + class WidgetDetailsModalCtrl { + constructor($scope, $log, applicationsService, widgetsService, errorMessageByCode, ECOMP_URL_REGEX, $window,userProfileService,$cookies) { + + let newWidgetModel = { + name: null, + appId: null, + appName: null, + width: 360, + height: 300, + url: null + }; + + let getAvailableApps = () => { + applicationsService.getAppsForSuperAdminAndAccountAdmin().then(apps => { + this.availableApps=[]; + for(var i=0;i { + $log.error(err); + }); + }; + /**/ + + let init = () => { + $log.info('AppDetailsModalCtrl::init'); + this.isSaving = false; + if ($scope.ngDialogData && $scope.ngDialogData.widget) { + $log.debug('WidgetDetailsModalCtrl::getAvailableApps: Edit widget mode for', $scope.ngDialogData.widget); + this.isEditMode = true; + this.widget = _.clone($scope.ngDialogData.widget); + } else { + $log.debug('WidgetDetailsModalCtrl::init: New app mode'); + this.isEditMode = false; + this.widget = _.clone(newWidgetModel); + } + getAvailableApps(); + }; + + this.ECOMP_URL_REGEX = ECOMP_URL_REGEX; + + this.conflictMessages = {}; + this.scrollApi = {}; + let handleConflictErrors = err => { + if(!err.data){ + return; + } + if(!err.data.length){ + err.data = [err.data] + } + _.forEach(err.data, item => { + _.forEach(item.fields, field => { + this.conflictMessages[field.name] = errorMessageByCode[item.errorCode]; + $scope.widgetForm[field.name].$setValidity('conflict', false); + watchOnce[field.name](); + }); + }); + this.scrollApi.scrollTop(); + }; + + let resetConflict = fieldName => { + delete this.conflictMessages[fieldName]; + if($scope.widgetForm[fieldName]){ + $scope.widgetForm[fieldName].$setValidity('conflict', true); + } + }; + + let watchOnce = { + name: () => { + let unregisterName = $scope.$watchGroup(['widgetDetails.selectedApp','widgetDetails.widget.name'], (newVal, oldVal) => { + if(newVal.toLowerCase() !== oldVal.toLowerCase()){ + resetConflict('name'); + unregisterName(); + } + }); + }, + url: () => { + let unregisterUrl = $scope.$watch('widgetDetails.widget.url', (newVal, oldVal) => { + if(newVal.toLowerCase() !== oldVal.toLowerCase()) { + resetConflict('url'); + unregisterUrl(); + } + }); + } + }; + + this.updateSelectedApp = () => { + if (!this.selectedApp) { + return; + } + this.widget.appId = this.selectedApp.id; + this.widget.appName = this.selectedApp.name; + }; + + let emptyCookies = () => { + userProfileService.getUserProfile() + .then(profile=> { + $log.info('AppDetailsModalCtrl::emptyCookies profile: ', profile); + $scope.userId = profile.orgUserId; + $log.info('user has the following userId: ' + profile.userId); + if ($cookies.getObject($scope.userId + '_widget') != undefined && $cookies.getObject($scope.userId + '_widget') != null) { + $cookies.remove($scope.userId + '_widget'); + } + }); + }; + + this.saveChanges = () => { + if($scope.widgetForm.$invalid){ + return; + } + this.isSaving = true; + if(this.isEditMode){ + widgetsService.updateWidget(this.widget.id, this.widget) + .then(() => { + $log.debug('WidgetDetailsModalCtrl::saveChanges: Widget update succeeded!'); + $scope.closeThisDialog(true); + emptyCookies(); + }).catch(err => { + if(err.status === 409){ + handleConflictErrors(err); + } + $log.error(err); + }).finally(()=>{ + this.isSaving = false; + var objOffsetVersion = objAgent.indexOf("MSIE"); + if (objOffsetVersion != -1) { + $log.debug('WidgetDetailsModalCtrl::saveChanges: Browser is IE, forcing Refresh'); + $window.location.reload(); + } + }); + }else{ + widgetsService.createWidget(this.widget) + .then(() => { + $log.debug('WidgetDetailsModalCtrl::createWidget: Widget creation succeeded!'); + $scope.closeThisDialog(true); + emptyCookies(); + }).catch(err => { + if(err.status === 409){ + handleConflictErrors('WidgetDetailsModalCtrl::createWidget error: ',err); + } + $log.error('WidgetDetailsModalCtrl::createWidget error: ',err); + }).finally(()=>{ + this.isSaving = false; + var objOffsetVersion = objAgent.indexOf("MSIE"); + if (objOffsetVersion != -1) { + $log.debug('WidgetDetailsModalCtrl::createWidget: Browser is IE, forcing Refresh'); + $window.location.reload(); + } + }); + } + }; + + init(); + + $scope.$on('$stateChangeStart', e => { + e.preventDefault(); + }); + } + } + WidgetDetailsModalCtrl.$inject = ['$scope', '$log', 'applicationsService', 'widgetsService', 'errorMessageByCode', 'ECOMP_URL_REGEX', '$window','userProfileService','$cookies']; + angular.module('ecompApp').controller('WidgetDetailsModalCtrl', WidgetDetailsModalCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.controller.spec.js b/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.controller.spec.js new file mode 100644 index 00000000..34042c14 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.controller.spec.js @@ -0,0 +1,19 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ diff --git a/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.modal.html b/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.modal.html new file mode 100644 index 00000000..87be6f15 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.modal.html @@ -0,0 +1,132 @@ + +
+
Widget Details
+
+
+ +
+
Application Name
+
+ +
+
+
+ Application is required +
+
+
+
+
Widget Name
+ +
+ +
+
+
+ Widget Name is required + Widget Name must be letters, numbers, or underscore +
+
+
+
+
+
Width
+ +
+
+ Widget width is required + Minimum width is 300 +
+
+
+
+
Height
+ +
+
+ Widget height is required + Minimum height is 200 +
+
+
+
+
+
URL
+ +
+ +
+
+
+ Widget URL is required + Incorrect URL pattern +
+
+ +
+
+
+
+ +
Save
+
Cancel
+
+
diff --git a/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.modal.less b/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.modal.less new file mode 100644 index 00000000..6e031b1d --- /dev/null +++ b/ecomp-portal-FE/client/app/views/widgets/widget-details-dialog/widget-details.modal.less @@ -0,0 +1,94 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .widget-details-modal { + height: 430px; + + .title { + .n18r; + border-bottom: @a 3px solid; + + } + + .widget-properties-main { + padding: 16px; + height: 306px; + overflow-y: auto; + + .item{ + position: relative; + margin-bottom: 18px; + + .input-field{ + .custom-input-field; + width: 100%; + &.url{ + width: 78%; + display: inline-block; + } + } + + .select-field { + .custom-select-field; + } + + .item-label{ + .o14r; + } + + .right-item{ + position: relative; + display: inline-block; + width: 48%; + float: right; + } + .left-item{ + display: inline-block; + width: 48%; + } + + .url-validation-button{ + .btn-blue; + width: 20%; + display: inline-block; + float: right; + } + + .error-container{ + position: absolute; + width: 280px; + display: block; + height: 12px; + line-height: 12px; + + .err-message{ + color: red; + font-size: 9px; + } + .valid-message{ + color: green; + font-size: 9px; + } + } + + } + + } + +} diff --git a/ecomp-portal-FE/client/app/views/widgets/widgets.controller.js b/ecomp-portal-FE/client/app/views/widgets/widgets.controller.js new file mode 100644 index 00000000..c24f49cd --- /dev/null +++ b/ecomp-portal-FE/client/app/views/widgets/widgets.controller.js @@ -0,0 +1,151 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ +'use strict'; +(function () { + class WidgetsCtrl { + constructor($log, applicationsService, widgetsService, ngDialog, confirmBoxService, + userProfileService, $cookies, $scope) { + $log.info('WidgetsCtrl::init: Starting Up'); + $scope.infoMessage = true; + + let populateAvailableApps = widgets => { + let allPortalsFilterObject = {index: 0, title: 'All applications', value: ''}; + this.availableApps = [allPortalsFilterObject]; + this.filterByApp = this.availableApps[0]; + applicationsService.getAppsForSuperAdminAndAccountAdmin().then(myApps => { + var reSortedApp = myApps.sort(getSortOrder("name")); + var realAppIndex = 1; + for (let i = 1; i <= reSortedApp.length; i++) { + if (!reSortedApp[i-1].restrictedApp) { + $log.debug('WidgetsCtrl::populateAvailableApps: pushing {index: ', realAppIndex, 'title: ', reSortedApp[i - 1].name, + 'value: ', reSortedApp[i - 1].name, '}'); + this.availableApps.push({ + index: realAppIndex, + title: reSortedApp[i - 1].name, + value: reSortedApp[i - 1].name + }) + realAppIndex = realAppIndex + 1; + } + } + }).catch(err => { + $log.error(err); + }); + }; + + let getOnboardingWidgets = () => { + this.isLoadingTable = true; + widgetsService.getManagedWidgets().then(res => { + var reSortedWidget = res.sort(getSortOrder("name")); + this.widgetsList = reSortedWidget; + populateAvailableApps(reSortedWidget); + }).catch(err => { + $log.error('WidgetsCtrl::getOnboardingWidgets error: ' + err); + }).finally(()=> { + this.isLoadingTable = false; + }); + }; + + let getSortOrder = (prop) => { + return function(a, b) { + if (a[prop].toLowerCase() > b[prop].toLowerCase()) { + return 1; + } else if (a[prop].toLowerCase() < b[prop].toLowerCase()) { + return -1; + } + return 0; + } + } + + $scope.hideMe = function () { + $scope.infoMessage = false; + } + + let init = () => { + this.isLoadingTable = false; + getOnboardingWidgets(); + + + this.searchString = ''; + + this.widgetsTableHeaders = [ + {name: 'Widget Name', value: 'name', isSortable: false}, + {name: 'Application', value: 'appName', isSortable: true}, + {name: 'Width', value: 'width', isSortable: false}, + {name: 'Height', value: 'height', isSortable: false} + ]; + this.widgetsList = []; + }; + + this.filterByDropdownValue = item => { + if(this.filterByApp.value === ''){ + return true; + } + return item.appName === this.filterByApp.value; + }; + + this.openWidgetDetailsModal = (selectedWidget) => { + let data = null; + if(selectedWidget){ + if(!selectedWidget.id){ + $log.error('Widget id not found'); + return; + } + data = { + widget: selectedWidget + } + } + ngDialog.open({ + templateUrl: 'app/views/widgets/widget-details-dialog/widget-details.modal.html', + controller: 'WidgetDetailsModalCtrl', + controllerAs: 'widgetDetails', + data: data + }).closePromise.then(needUpdate => { + if(needUpdate.value === true){ + $log.debug('WidgetsCtrl::openWidgetDetailsModal: updating table data...'); + getOnboardingWidgets(); + } + }); + }; + + this.deleteWidget = widget => { + confirmBoxService.deleteItem(widget.name).then(isConfirmed => { + if(isConfirmed){ + if(!widget || !widget.id){ + $log.error('WidgetsCtrl::deleteWidget: No widget or ID... cannot delete'); + return; + } + widgetsService.deleteWidget(widget.id).then(() => { + this.widgetsList.splice(this.widgetsList.indexOf(widget), 1); + }).catch(err => { + $log.error('WidgetsCtrl::deleteWidget error:',err); + }); + } + }).catch(err => { + $log.error('WidgetsCtrl::deleteWidget error:',err); + }); + }; + + init(); + } + } + WidgetsCtrl.$inject = ['$log', 'applicationsService', 'widgetsService', 'ngDialog', 'confirmBoxService', + 'userProfileService','$cookies', '$scope']; + angular.module('ecompApp').controller('WidgetsCtrl', WidgetsCtrl); +})(); diff --git a/ecomp-portal-FE/client/app/views/widgets/widgets.controller.spec.js b/ecomp-portal-FE/client/app/views/widgets/widgets.controller.spec.js new file mode 100644 index 00000000..34042c14 --- /dev/null +++ b/ecomp-portal-FE/client/app/views/widgets/widgets.controller.spec.js @@ -0,0 +1,19 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ diff --git a/ecomp-portal-FE/client/app/views/widgets/widgets.less b/ecomp-portal-FE/client/app/views/widgets/widgets.less new file mode 100644 index 00000000..4b83b66f --- /dev/null +++ b/ecomp-portal-FE/client/app/views/widgets/widgets.less @@ -0,0 +1,60 @@ +/*- + * ================================================================================ + * eCOMP Portal + * ================================================================================ + * Copyright (C) 2017 AT&T Intellectual Property + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * ================================================================================ + */ + .widgets-page-main{ + .bg_w; + position: @page-main-position; + top: @page-main-top; + left: @page-main-left; + right: @page-main-right; + bottom: @page-main-bottom; + padding-top: @padding-top; + overflow-y: @page-main-overflow-y; + padding-left: @padding-left-side; + + .widgets-table{ + width: @table-width; + margin: @table-margin; + + .table-control{ + + } + + .delete-widget{ + .ico_trash_default; + } + } + .error-text { + width: 1170px; + margin: auto; + padding: 20px; + left: 20px; + font-weight: bold; + font-size: 16px; + text-align: left; + color: @err; + background-color: @u; + + .error-help { + color: @o; + font-weight: normal; + } + } + +} \ No newline at end of file diff --git a/ecomp-portal-FE/client/app/views/widgets/widgets.tpl.html b/ecomp-portal-FE/client/app/views/widgets/widgets.tpl.html new file mode 100644 index 00000000..d255174f --- /dev/null +++ b/ecomp-portal-FE/client/app/views/widgets/widgets.tpl.html @@ -0,0 +1,77 @@ + +
+
+
+
Widget Onboarding
+
+
+
+
+
+ + +
Add Widget
+
+
+ Only widgets for active applications are displayed. + +
+ + +
+ + + + + + + + + + + + + + + +
{{header.name}}URLDelete
+
+
+
+
+
+
+
+
+
+
+
-- cgit 1.2.3-korg