From 12e0c4190f793dc43ecc2c326230e73fcfb6b60d Mon Sep 17 00:00:00 2001 From: Larry Feigen Date: Tue, 27 Apr 2021 21:01:04 -0400 Subject: [PATCH] Release 1.1.0 --- .gitignore | 7 + CONTRIBUTING.md | 4 +- README.md | 18 +- THIRD_PARTY_LICENSES.txt | 1381 ++++++++++++++ common/pom.xml | 4 +- .../pagedesc/WeblogicCreateFormSource.java | 9 + .../pagedesc/WeblogicSectionSource.java | 34 + .../pagedesc/WeblogicSliceFormSource.java | 19 + .../backend/typedesc/WeblogicBeanTypes.java | 4 +- .../console/backend/utils/StringUtils.java | 22 +- ...nPageWeblogicSearchResponseRestMapper.java | 5 +- .../backend/driver/PageRestMappings.java | 6 +- .../driver/UnlocalizedWeblogicPages.java | 16 +- .../driver/WeblogicPageRepresenter.java | 3 + .../backend/driver/WeblogicSliceForm.java | 16 + frontend/.eslintignore | 3 +- frontend/.eslintrc.js | 13 +- frontend/.eslintrc.json | 51 +- frontend/.jsdocrc.json | 3 + frontend/eslint-html.template | 116 -- frontend/eslint-rules/README.md | 136 ++ .../{src/js => }/eslint-rules/js-copyright.js | 85 +- frontend/jsconfig.json | 24 +- frontend/package.json | 7 +- frontend/pom.xml | 40 +- frontend/scripts/config/oraclejet-serve.js | 4 +- frontend/src/config/console-frontend-jet.yaml | 49 +- frontend/src/config/console-preferences.yaml | 7 +- frontend/src/config/perspectives.yaml | 18 +- frontend/src/css/app.css | 369 ++-- .../WOFF/OracleSans_W_BdIt.woff | Bin 0 -> 55256 bytes frontend/src/images/close-icon-blk_24x24.png | Bin 0 -> 156 bytes frontend/src/images/close-icon-wht_24x24.png | Bin 0 -> 156 bytes .../monitoring-icon-navstrip-blk_48x48.png | Bin 4125 -> 0 bytes .../monitoring-icon-navstrip-gry_48x48.png | Bin 10140 -> 0 bytes .../monitoring-icon-navstrip-wht_48x48.png | Bin 14525 -> 0 bytes .../src/images/more-vertical-blk-8x24.png | Bin 609 -> 2318 bytes .../navstrip-icon-monitoring-blk_48x48.png | Bin 0 -> 2289 bytes .../navstrip-icon-monitoring-gry_48x48.png | Bin 0 -> 475 bytes .../navstrip-icon-monitoring-wht_48x48.png | Bin 0 -> 742 bytes ...-icon-readonly-configuration-blk_48x48.png | Bin 0 -> 1017 bytes ...-icon-readonly-configuration-gry_48x48.png | Bin 0 -> 812 bytes ...-icon-readonly-configuration-wht_48x48.png | Bin 0 -> 625 bytes ...icon-readwrite-configuration-blk_48x48.png | Bin 0 -> 299 bytes ...icon-readwrite-configuration-gry_48x48.png | Bin 0 -> 335 bytes ...icon-readwrite-configuration-wht_48x48.png | Bin 0 -> 325 bytes .../src/images/navtree-icon2-blk_24x24.png | Bin 0 -> 202 bytes .../src/images/navtree-icon2-wht_24x24.png | Bin 0 -> 259 bytes .../src/images/oracle-logo-red_109x16.png | Bin 2225 -> 8111 bytes .../images/overlay-detach-icon-blk_24x24.png | Bin 0 -> 299 bytes .../src/images/overlay-pin-icon-blk_24x24.png | Bin 0 -> 160 bytes .../overlay-reattach-icon-blk_24x24.png | Bin 0 -> 297 bytes frontend/src/images/search-icon-blk_24x24.png | Bin 718 -> 373 bytes frontend/src/images/search-icon-wht_24x24.png | Bin 738 -> 409 bytes .../src/images/toggle-help-icon-blk_16x16.png | Bin 0 -> 565 bytes frontend/src/index.html | 11 +- frontend/src/js/apis/data-operations.js | 311 ++++ frontend/src/js/apis/message-displaying.js | 165 ++ frontend/src/js/appController.js | 136 +- frontend/src/js/cfe/binding/Attribute.js | 43 - frontend/src/js/cfe/binding/Column.js | 33 - frontend/src/js/cfe/binding/Form.js | 98 - frontend/src/js/cfe/binding/PDJResource.js | 103 -- frontend/src/js/cfe/binding/Property.js | 39 - frontend/src/js/cfe/binding/RDJResource.js | 42 - frontend/src/js/cfe/binding/Resource.js | 32 - frontend/src/js/cfe/binding/Slice.js | 39 - frontend/src/js/cfe/binding/Table.js | 98 - frontend/src/js/cfe/cbe-types.js | 38 - frontend/src/js/cfe/cbe-wrapper.js | 77 - frontend/src/js/cfe/common/types.js | 73 - frontend/src/js/cfe/http/adapter.js | 153 -- frontend/src/js/cfe/model/Model.js | 60 - .../domain/domain-connection-manager.js | 313 ---- .../perspective/perspective-memory-manager.js | 44 - .../cfe/services/preferences/preferences.js | 64 - .../adapters/file-adapter.js} | 25 +- frontend/src/js/core/adapters/http-adapter.js | 177 ++ frontend/src/js/core/cbe-types.js | 71 + frontend/src/js/core/cbe-utils.js | 21 + frontend/src/js/core/cfe-errors.js | 58 + frontend/src/js/core/data-storage.js | 78 + frontend/src/js/{cfe/common => core}/mutex.js | 0 .../src/js/{cfe/common => core}/runtime.js | 27 +- frontend/src/js/core/types.js | 49 + frontend/src/js/core/utils.js | 82 + frontend/src/js/{cfe => core}/utils/Path.js | 2 +- .../js/{cfe => core}/utils/keyset-utils.js | 2 +- .../src/js/eslint-rules/css-copyright.jsx | 301 ---- .../src/js/eslint-rules/html-copyright.jsx | 315 ---- frontend/src/js/main.js | 16 +- .../ataglance}/ataglance-manager.js | 44 +- .../beanpath}/beanpath-manager.js | 8 +- .../breadcrumb}/breadcrumbs-manager.js | 10 +- .../change-management/change-manager.js | 204 +++ .../domain-connection-manager.js | 255 +++ .../domain-connection-verifier.js | 64 + .../domain-connection.js | 7 +- .../data-management/cbe-data-manager.js | 811 +++++++++ .../data-management/cbe-data-storage.js | 89 + .../navtree}/navtree-manager.js | 573 +++--- .../page-definition/actions.js} | 139 +- .../page-definition/crosslinks.js} | 17 +- .../page-definition/fields.js} | 93 +- .../page-definition/form-layouts.js | 273 +++ .../page-definition/options-sources.js | 80 + .../page-definition/pages.js} | 2 +- .../page-definition/types.js} | 35 +- .../page-definition/usedifs.js} | 4 +- .../page-definition}/utils.js | 62 +- .../perspective/perspective-manager.js | 59 +- .../perspective/perspective-memory-manager.js | 75 + .../perspective/perspective-memory.js | 69 +- .../perspective/perspective.js | 32 +- .../microservices/preferences/preferences.js | 131 ++ frontend/src/js/resources/nls/frontend.js | 310 ++++ frontend/src/js/system-tests/sanityTest.js | 3 - .../src/js/system-tests/tests/login_test.js | 113 -- frontend/src/js/unit-tests/cfe/cbe_test.js | 48 - .../branding-area/domain-connection.js | 319 ++++ .../src/js/viewModels/branding-area/header.js | 236 +++ .../branding-area/navtree-toggler.js | 96 + frontend/src/js/viewModels/configuration.js | 219 ++- .../ancillary-content.js} | 98 +- .../ancillary}/ataglance.js | 46 +- .../ancillary}/shoppingcart.js | 51 +- .../content-area/body/container-resizer.js | 97 + .../body}/create-form.js | 143 +- .../content-area/body/form-tabstrip.js | 289 +++ .../body}/form-toolbar.js | 133 +- .../content-area/body/form-variables-stack.js | 54 + .../content-area/body/form-variables.js | 55 + .../body}/form.js | 1325 +++++++------- .../body}/help-form.js | 4 +- .../body}/table-toolbar.js | 217 ++- .../body}/table.js | 285 +-- .../content-area/header/buttons-toolbar.js | 61 + .../header/content-area-header.js | 99 + .../content-area/header/icons-tabstrip.js | 244 +++ frontend/src/js/viewModels/footer/footer.js | 71 + .../js/viewModels/{template => }/gallery.js | 30 +- frontend/src/js/viewModels/home.js | 18 +- frontend/src/js/viewModels/landing.js | 91 +- .../js/viewModels/modules/change-manager.js | 204 --- .../src/js/viewModels/modules/pdj-messages.js | 90 - .../js/viewModels/modules/tooltip-helper.js | 191 -- frontend/src/js/viewModels/monitoring.js | 196 +- .../src/js/viewModels/monitoring/navtree.js | 159 -- .../{template => navigation-area}/navstrip.js | 59 +- .../navtree.js | 27 +- .../ancillary-content/notifications.js | 22 - .../template/content-area-header.js | 86 - .../src/js/viewModels/template/desktop.js | 256 --- .../src/js/viewModels/template/domains.js | 327 ---- frontend/src/js/viewModels/template/header.js | 237 --- frontend/src/js/viewModels/utils.js | 113 ++ .../domain-connection.html} | 44 +- .../src/js/views/branding-area/header.html | 108 ++ .../views/branding-area/navtree-toggler.html | 20 + frontend/src/js/views/configuration.html | 14 +- .../ancillary-content.html} | 2 +- .../ancillary}/ataglance.html | 0 .../ancillary}/shoppingcart.html | 2 +- .../content-area/body/form-tabstrip.html | 28 + .../body}/form-toolbar.html | 16 +- .../body}/form.html | 75 +- .../body}/table-toolbar.html | 14 +- .../body}/table.html | 35 +- .../content-area/header/buttons-toolbar.html | 44 + .../header}/content-area-header.html | 17 +- .../content-area/header/icons-tabstrip.html | 71 + frontend/src/js/views/footer/footer.html | 15 + .../src/js/views/{template => }/gallery.html | 4 +- frontend/src/js/views/landing.html | 7 +- frontend/src/js/views/monitoring.html | 14 +- frontend/src/js/views/monitoring/navtree.html | 28 - .../navstrip.html | 8 +- .../navtree.html | 0 .../ancillary-content/notifications.html | 6 - frontend/src/js/views/template/desktop.html | 6 - frontend/src/js/views/template/header.html | 95 - .../src/resources/nls/frontend.properties | 319 ++-- frontend/{src/js => }/system-tests/README.md | 38 +- frontend/{src/js => }/system-tests/index.js | 26 +- .../{src/js => }/system-tests/lib/admin.js | 94 +- .../{src/js => }/system-tests/lib/browser.js | 144 +- .../system-tests/lib/domainProperty.js | 16 +- .../lib/machineAndClusterProps.js | 170 +- frontend/system-tests/lib/securityProps.js | 105 ++ .../lib/serverAndTemplateProperty.js | 0 .../js => }/system-tests/lib/servicesProps.js | 288 +-- .../js => }/system-tests/tests/basic_test.js | 0 .../system-tests/tests/configPanel_test.js | 0 .../system-tests/tests/domainProps_test.js | 2 +- frontend/system-tests/tests/interop_test.js | 131 ++ .../tests/machineAndCluster_test.js | 214 +-- .../tests/monitoringPanel_test.js | 0 .../system-tests/tests/monitoring_test.js | 0 .../system-tests/tests/navtree_test.js | 0 frontend/system-tests/tests/security_test.js | 140 ++ .../tests/serverAndTemplate_test.js | 0 .../system-tests/tests/services_test.js | 447 +++-- .../system-tests/tests/utilities_test.js | 0 frontend/test/specs/navtree.json | 7 - frontend/unit-tests/README.md | 60 + frontend/{test => unit-tests}/karma.conf.js | 25 +- .../fixtures/monitoring-navtree-rdj.json | 1594 +++++++++++++++++ .../navtree/navtree-manager.spec.js} | 21 +- .../page-definition}/pdj-types.spec.js | 2 +- frontend/{test => unit-tests}/test-main.js | 0 .../console/backend/index/PageIndexer.java | 6 +- installer/assembly/zip.xml | 87 + pom.xml | 12 +- resource-bundles/pom.xml | 14 +- .../build/EnglishResourceBundleCreator.java | 28 +- .../backend/build/MergeHtmlAndProperties.java | 143 ++ .../backend/build/PropertiesSorter.java | 142 ++ .../backend/build/PropertiesToHtml.java | 115 ++ .../slices/OnlySlice/form.yaml | 6 +- .../AppDeploymentRuntimeMBean/table.yaml | 5 + .../ClusterMBean/slices/Messaging/form.yaml | 5 +- .../ClusterMBean/slices/Migration/form.yaml | 3 +- .../ClusterMBean/slices/Overload/form.yaml | 6 +- .../src/main/resources/ClusterMBean/type.yaml | 90 +- .../resources/ComponentRuntimeMBean/type.yaml | 13 +- .../DataSourceLogFileMBean/type.yaml | 34 + .../DefaultDeliveryParamsBean/type.yaml | 12 + .../DomainMBean/slices/General/form.yaml | 2 +- .../slices/Security/General/form.yaml | 2 +- .../src/main/resources/DomainMBean/type.yaml | 12 + .../DynamicDeploymentMBean/type.yaml | 15 + .../resources/DynamicServersMBean/type.yaml | 5 +- .../FileStoreMBean/slices/General/form.yaml | 4 +- .../main/resources/FileStoreMBean/type.yaml | 23 +- .../slices/Transaction/form.yaml | 2 +- .../resources/JDBCStoreMBean/createForm.yaml | 40 +- .../main/resources/JDBCStoreMBean/slices.yaml | 5 +- .../JDBCStoreMBean/slices/General/form.yaml | 26 +- .../JDBCStoreMBean/slices/HA/form.yaml | 21 +- .../JDBCStoreMBean/slices/Target/form.yaml | 30 +- .../JDBCStoreMBean/slices/Tuning/form.yaml | 34 + .../main/resources/JDBCStoreMBean/table.yaml | 18 +- .../main/resources/JDBCStoreMBean/type.yaml | 14 +- .../JDBCSystemResourceMBean/type.yaml | 2 +- .../slices/DefaultDelivery/form.yaml | 4 +- .../JMSServerMBean/slices/General/form.yaml | 4 +- .../src/main/resources/JMXMBean/type.yaml | 9 + .../src/main/resources/LogFileMBean/type.yaml | 60 +- .../src/main/resources/LogMBean/type.yaml | 36 +- .../main/resources/MachineMBean/slices.yaml | 4 +- .../{Nodemanager => NodeManager}/form.yaml | 2 +- .../src/main/resources/MachineMBean/type.yaml | 6 + .../resources/MessagingBridgeMBean/type.yaml | 16 +- .../MigratableTargetMBean/slices.yaml | 3 +- .../slices/General/form.yaml | 23 +- .../slices/Migration/form.yaml | 42 - .../slices/ChannelGeneral/form.yaml | 6 +- .../slices/ChannelSecurity/form.yaml | 7 +- .../NetworkAccessPointMBean/type.yaml | 18 + .../src/main/resources/RealmMBean/slices.yaml | 3 +- .../slices/CertPathBuilder/form.yaml | 9 + .../src/main/resources/RealmMBean/type.yaml | 4 + .../main/resources/SAFAgentMBean/slices.yaml | 4 +- .../SAFAgentMBean/slices/Logging/form.yaml | 33 + .../SAFAgentMBean/slices/Quotas/form.yaml | 25 + .../SAFAgentMBean/slices/Thresholds/form.yaml | 11 +- .../SNMPAgentMBean/slices/General/form.yaml | 4 +- .../main/resources/SNMPAgentMBean/type.yaml | 9 +- .../SecurityConfigurationMBean/type.yaml | 4 + .../main/resources/ServerMBean/slices.yaml | 13 +- .../ServerMBean/slices/Cluster/form.yaml | 4 +- .../{HealthMonitoring => Health}/form.yaml | 6 +- .../ServerMBean/slices/Overload/form.yaml | 6 +- .../slices/Protocols/General/form.yaml | 3 +- .../slices/WebServices/Buffering/form.yaml | 34 + .../WebServices/ReliableMessage/form.yaml | 33 + .../resources/ServerTemplateMBean/slices.yaml | 13 +- .../resources/ServerTemplateMBean/table.yaml | 8 +- .../resources/ServerTemplateMBean/type.yaml | 39 +- .../resources/ShutdownClassMBean/table.yaml | 4 +- .../slices/Configuration/form.yaml | 1 + .../resources/SubDeploymentMBean/type.yaml | 9 +- .../type.yaml | 10 +- .../resources/UnixMachineMBean/slices.yaml | 4 +- .../resources/WebServerLogMBean/type.yaml | 34 + .../type.yaml | 15 + .../type.yaml | 15 + .../slices/General/form.yaml | 5 +- server/pom.xml | 4 +- .../weblogic/console/backend/server/Main.java | 82 +- services/pom.xml | 6 +- site/console_uidesign.md | 16 +- site/developer_guide.md | 6 +- site/install_config.md | 114 +- site/known_issues.md | 4 +- site/troubleshoot.md | 2 +- site/tuning.md | 64 +- 297 files changed, 14516 insertions(+), 7403 deletions(-) create mode 100644 core/src/main/java/weblogic/console/backend/pagedesc/WeblogicSectionSource.java create mode 100644 frontend/.jsdocrc.json delete mode 100644 frontend/eslint-html.template create mode 100644 frontend/eslint-rules/README.md rename frontend/{src/js => }/eslint-rules/js-copyright.js (62%) create mode 100644 frontend/src/css/fonts/2010.1.0/OracleFont/OracleSans_Web/WOFF/OracleSans_W_BdIt.woff create mode 100644 frontend/src/images/close-icon-blk_24x24.png create mode 100644 frontend/src/images/close-icon-wht_24x24.png delete mode 100644 frontend/src/images/monitoring-icon-navstrip-blk_48x48.png delete mode 100644 frontend/src/images/monitoring-icon-navstrip-gry_48x48.png delete mode 100644 frontend/src/images/monitoring-icon-navstrip-wht_48x48.png create mode 100644 frontend/src/images/navstrip-icon-monitoring-blk_48x48.png create mode 100644 frontend/src/images/navstrip-icon-monitoring-gry_48x48.png create mode 100644 frontend/src/images/navstrip-icon-monitoring-wht_48x48.png create mode 100644 frontend/src/images/navstrip-icon-readonly-configuration-blk_48x48.png create mode 100644 frontend/src/images/navstrip-icon-readonly-configuration-gry_48x48.png create mode 100644 frontend/src/images/navstrip-icon-readonly-configuration-wht_48x48.png create mode 100644 frontend/src/images/navstrip-icon-readwrite-configuration-blk_48x48.png create mode 100644 frontend/src/images/navstrip-icon-readwrite-configuration-gry_48x48.png create mode 100644 frontend/src/images/navstrip-icon-readwrite-configuration-wht_48x48.png create mode 100644 frontend/src/images/navtree-icon2-blk_24x24.png create mode 100644 frontend/src/images/navtree-icon2-wht_24x24.png create mode 100644 frontend/src/images/overlay-detach-icon-blk_24x24.png create mode 100644 frontend/src/images/overlay-pin-icon-blk_24x24.png create mode 100644 frontend/src/images/overlay-reattach-icon-blk_24x24.png create mode 100644 frontend/src/images/toggle-help-icon-blk_16x16.png create mode 100644 frontend/src/js/apis/data-operations.js create mode 100644 frontend/src/js/apis/message-displaying.js delete mode 100644 frontend/src/js/cfe/binding/Attribute.js delete mode 100644 frontend/src/js/cfe/binding/Column.js delete mode 100644 frontend/src/js/cfe/binding/Form.js delete mode 100644 frontend/src/js/cfe/binding/PDJResource.js delete mode 100644 frontend/src/js/cfe/binding/Property.js delete mode 100644 frontend/src/js/cfe/binding/RDJResource.js delete mode 100644 frontend/src/js/cfe/binding/Resource.js delete mode 100644 frontend/src/js/cfe/binding/Slice.js delete mode 100644 frontend/src/js/cfe/binding/Table.js delete mode 100644 frontend/src/js/cfe/cbe-types.js delete mode 100644 frontend/src/js/cfe/cbe-wrapper.js delete mode 100644 frontend/src/js/cfe/common/types.js delete mode 100644 frontend/src/js/cfe/http/adapter.js delete mode 100644 frontend/src/js/cfe/model/Model.js delete mode 100644 frontend/src/js/cfe/services/domain/domain-connection-manager.js delete mode 100644 frontend/src/js/cfe/services/perspective/perspective-memory-manager.js delete mode 100644 frontend/src/js/cfe/services/preferences/preferences.js rename frontend/src/js/{cfe/io/adapter.js => core/adapters/file-adapter.js} (73%) create mode 100644 frontend/src/js/core/adapters/http-adapter.js create mode 100644 frontend/src/js/core/cbe-types.js create mode 100644 frontend/src/js/core/cbe-utils.js create mode 100644 frontend/src/js/core/cfe-errors.js create mode 100644 frontend/src/js/core/data-storage.js rename frontend/src/js/{cfe/common => core}/mutex.js (100%) rename frontend/src/js/{cfe/common => core}/runtime.js (81%) create mode 100644 frontend/src/js/core/types.js create mode 100644 frontend/src/js/core/utils.js rename frontend/src/js/{cfe => core}/utils/Path.js (98%) rename frontend/src/js/{cfe => core}/utils/keyset-utils.js (83%) delete mode 100644 frontend/src/js/eslint-rules/css-copyright.jsx delete mode 100644 frontend/src/js/eslint-rules/html-copyright.jsx rename frontend/src/js/{viewModels/modules => microservices/ataglance}/ataglance-manager.js (66%) rename frontend/src/js/{viewModels/modules => microservices/beanpath}/beanpath-manager.js (93%) rename frontend/src/js/{viewModels/modules => microservices/breadcrumb}/breadcrumbs-manager.js (91%) create mode 100644 frontend/src/js/microservices/change-management/change-manager.js create mode 100644 frontend/src/js/microservices/connection-management/domain-connection-manager.js create mode 100644 frontend/src/js/microservices/connection-management/domain-connection-verifier.js rename frontend/src/js/{cfe/services/domain => microservices/connection-management}/domain-connection.js (92%) create mode 100644 frontend/src/js/microservices/data-management/cbe-data-manager.js create mode 100644 frontend/src/js/microservices/data-management/cbe-data-storage.js rename frontend/src/js/{viewModels/modules => microservices/navtree}/navtree-manager.js (50%) rename frontend/src/js/{viewModels/modules/pdj-actions.js => microservices/page-definition/actions.js} (65%) rename frontend/src/js/{viewModels/modules/pdj-crosslinks.js => microservices/page-definition/crosslinks.js} (68%) rename frontend/src/js/{viewModels/modules/pdj-fields.js => microservices/page-definition/fields.js} (81%) create mode 100644 frontend/src/js/microservices/page-definition/form-layouts.js create mode 100644 frontend/src/js/microservices/page-definition/options-sources.js rename frontend/src/js/{viewModels/modules/pdj-pages.js => microservices/page-definition/pages.js} (99%) rename frontend/src/js/{viewModels/modules/pdj-types.js => microservices/page-definition/types.js} (90%) rename frontend/src/js/{viewModels/modules/pdj-usedifs.js => microservices/page-definition/usedifs.js} (98%) rename frontend/src/js/{cfe/common => microservices/page-definition}/utils.js (82%) rename frontend/src/js/{cfe/services => microservices}/perspective/perspective-manager.js (70%) create mode 100644 frontend/src/js/microservices/perspective/perspective-memory-manager.js rename frontend/src/js/{cfe/services => microservices}/perspective/perspective-memory.js (68%) rename frontend/src/js/{cfe/services => microservices}/perspective/perspective.js (52%) create mode 100644 frontend/src/js/microservices/preferences/preferences.js create mode 100644 frontend/src/js/resources/nls/frontend.js delete mode 100644 frontend/src/js/system-tests/sanityTest.js delete mode 100644 frontend/src/js/system-tests/tests/login_test.js delete mode 100644 frontend/src/js/unit-tests/cfe/cbe_test.js create mode 100644 frontend/src/js/viewModels/branding-area/domain-connection.js create mode 100644 frontend/src/js/viewModels/branding-area/header.js create mode 100644 frontend/src/js/viewModels/branding-area/navtree-toggler.js rename frontend/src/js/viewModels/{template/ancillary-content-area.js => content-area/ancillary-content.js} (60%) rename frontend/src/js/viewModels/{template/ancillary-content => content-area/ancillary}/ataglance.js (78%) rename frontend/src/js/viewModels/{template/ancillary-content => content-area/ancillary}/shoppingcart.js (89%) create mode 100644 frontend/src/js/viewModels/content-area/body/container-resizer.js rename frontend/src/js/viewModels/{weblogic-page => content-area/body}/create-form.js (88%) create mode 100644 frontend/src/js/viewModels/content-area/body/form-tabstrip.js rename frontend/src/js/viewModels/{weblogic-page => content-area/body}/form-toolbar.js (78%) create mode 100644 frontend/src/js/viewModels/content-area/body/form-variables-stack.js create mode 100644 frontend/src/js/viewModels/content-area/body/form-variables.js rename frontend/src/js/viewModels/{weblogic-page => content-area/body}/form.js (61%) rename frontend/src/js/viewModels/{weblogic-page => content-area/body}/help-form.js (93%) rename frontend/src/js/viewModels/{weblogic-page => content-area/body}/table-toolbar.js (59%) rename frontend/src/js/viewModels/{weblogic-page => content-area/body}/table.js (70%) create mode 100644 frontend/src/js/viewModels/content-area/header/buttons-toolbar.js create mode 100644 frontend/src/js/viewModels/content-area/header/content-area-header.js create mode 100644 frontend/src/js/viewModels/content-area/header/icons-tabstrip.js create mode 100644 frontend/src/js/viewModels/footer/footer.js rename frontend/src/js/viewModels/{template => }/gallery.js (50%) delete mode 100644 frontend/src/js/viewModels/modules/change-manager.js delete mode 100644 frontend/src/js/viewModels/modules/pdj-messages.js delete mode 100644 frontend/src/js/viewModels/modules/tooltip-helper.js delete mode 100644 frontend/src/js/viewModels/monitoring/navtree.js rename frontend/src/js/viewModels/{template => navigation-area}/navstrip.js (71%) rename frontend/src/js/viewModels/{configuration => navigation-area}/navtree.js (88%) delete mode 100644 frontend/src/js/viewModels/template/ancillary-content/notifications.js delete mode 100644 frontend/src/js/viewModels/template/content-area-header.js delete mode 100644 frontend/src/js/viewModels/template/desktop.js delete mode 100644 frontend/src/js/viewModels/template/domains.js delete mode 100644 frontend/src/js/viewModels/template/header.js create mode 100644 frontend/src/js/viewModels/utils.js rename frontend/src/js/views/{template/domains.html => branding-area/domain-connection.html} (53%) create mode 100644 frontend/src/js/views/branding-area/header.html create mode 100644 frontend/src/js/views/branding-area/navtree-toggler.html rename frontend/src/js/views/{template/ancillary-content-area.html => content-area/ancillary-content.html} (96%) rename frontend/src/js/views/{template/ancillary-content => content-area/ancillary}/ataglance.html (100%) rename frontend/src/js/views/{template/ancillary-content => content-area/ancillary}/shoppingcart.html (97%) create mode 100644 frontend/src/js/views/content-area/body/form-tabstrip.html rename frontend/src/js/views/{weblogic-page => content-area/body}/form-toolbar.html (92%) rename frontend/src/js/views/{weblogic-page => content-area/body}/form.html (62%) rename frontend/src/js/views/{weblogic-page => content-area/body}/table-toolbar.html (92%) rename frontend/src/js/views/{weblogic-page => content-area/body}/table.html (87%) create mode 100644 frontend/src/js/views/content-area/header/buttons-toolbar.html rename frontend/src/js/views/{template => content-area/header}/content-area-header.html (73%) create mode 100644 frontend/src/js/views/content-area/header/icons-tabstrip.html create mode 100644 frontend/src/js/views/footer/footer.html rename frontend/src/js/views/{template => }/gallery.html (90%) delete mode 100644 frontend/src/js/views/monitoring/navtree.html rename frontend/src/js/views/{template => navigation-area}/navstrip.html (89%) rename frontend/src/js/views/{configuration => navigation-area}/navtree.html (100%) delete mode 100644 frontend/src/js/views/template/ancillary-content/notifications.html delete mode 100644 frontend/src/js/views/template/desktop.html delete mode 100644 frontend/src/js/views/template/header.html rename frontend/{src/js => }/system-tests/README.md (63%) rename frontend/{src/js => }/system-tests/index.js (85%) rename frontend/{src/js => }/system-tests/lib/admin.js (91%) rename frontend/{src/js => }/system-tests/lib/browser.js (97%) rename frontend/{src/js => }/system-tests/lib/domainProperty.js (97%) rename frontend/{src/js => }/system-tests/lib/machineAndClusterProps.js (96%) create mode 100644 frontend/system-tests/lib/securityProps.js rename frontend/{src/js => }/system-tests/lib/serverAndTemplateProperty.js (100%) rename frontend/{src/js => }/system-tests/lib/servicesProps.js (97%) rename frontend/{src/js => }/system-tests/tests/basic_test.js (100%) rename frontend/{src/js => }/system-tests/tests/configPanel_test.js (100%) rename frontend/{src/js => }/system-tests/tests/domainProps_test.js (99%) create mode 100644 frontend/system-tests/tests/interop_test.js rename frontend/{src/js => }/system-tests/tests/machineAndCluster_test.js (96%) rename frontend/{src/js => }/system-tests/tests/monitoringPanel_test.js (100%) rename frontend/{src/js => }/system-tests/tests/monitoring_test.js (100%) rename frontend/{src/js => }/system-tests/tests/navtree_test.js (100%) create mode 100644 frontend/system-tests/tests/security_test.js rename frontend/{src/js => }/system-tests/tests/serverAndTemplate_test.js (100%) rename frontend/{src/js => }/system-tests/tests/services_test.js (56%) rename frontend/{src/js => }/system-tests/tests/utilities_test.js (100%) delete mode 100644 frontend/test/specs/navtree.json create mode 100644 frontend/unit-tests/README.md rename frontend/{test => unit-tests}/karma.conf.js (83%) create mode 100644 frontend/unit-tests/specs/microservices/navtree/fixtures/monitoring-navtree-rdj.json rename frontend/{test/specs/navtree-viewmodel.spec.js => unit-tests/specs/microservices/navtree/navtree-manager.spec.js} (96%) rename frontend/{test/specs => unit-tests/specs/microservices/page-definition}/pdj-types.spec.js (91%) rename frontend/{test => unit-tests}/test-main.js (100%) create mode 100644 resource-bundles/src/main/java/weblogic/console/backend/build/MergeHtmlAndProperties.java create mode 100644 resource-bundles/src/main/java/weblogic/console/backend/build/PropertiesSorter.java create mode 100644 resource-bundles/src/main/java/weblogic/console/backend/build/PropertiesToHtml.java create mode 100644 resources/src/main/resources/DefaultDeliveryParamsBean/type.yaml create mode 100644 resources/src/main/resources/DynamicDeploymentMBean/type.yaml create mode 100644 resources/src/main/resources/JDBCStoreMBean/slices/Tuning/form.yaml create mode 100644 resources/src/main/resources/JMXMBean/type.yaml rename resources/src/main/resources/MachineMBean/slices/{Nodemanager => NodeManager}/form.yaml (94%) delete mode 100644 resources/src/main/resources/MigratableTargetMBean/slices/Migration/form.yaml create mode 100644 resources/src/main/resources/RealmMBean/slices/CertPathBuilder/form.yaml create mode 100644 resources/src/main/resources/SAFAgentMBean/slices/Logging/form.yaml create mode 100644 resources/src/main/resources/SAFAgentMBean/slices/Quotas/form.yaml rename resources/src/main/resources/ServerMBean/slices/{HealthMonitoring => Health}/form.yaml (89%) create mode 100644 resources/src/main/resources/ServerMBean/slices/WebServices/Buffering/form.yaml create mode 100644 resources/src/main/resources/ServerMBean/slices/WebServices/ReliableMessage/form.yaml create mode 100644 resources/src/main/resources/WebServiceRequestBufferingQueueMBean/type.yaml create mode 100644 resources/src/main/resources/WebServiceResponseBufferingQueueMBean/type.yaml diff --git a/.gitignore b/.gitignore index 7cf45557..449667fe 100644 --- a/.gitignore +++ b/.gitignore @@ -43,3 +43,10 @@ weblogic-bean-info-harvester/build-* run/work fortify-output/** owasp-output/** +frontend/seleniumTest.log + +electron/build/** +electron/dist/** +electron/extraFiles/** +electron/node_modules/** +electron/package-lock.json diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 785d4d41..97c58804 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -1,6 +1,6 @@ # Contributing -Oracle welcomes contributions to this repository from anyone. +We welcome contributions to this repository from anyone. If you want to submit a pull request to fix a bug or enhance an existing feature, please first open an issue and link to that issue when you @@ -9,7 +9,7 @@ submit your pull request. If you have any questions about a possible submission, feel free to open an issue too. -## Contributing to the WebLogic Server Remote Console repository +## Contributing to the WebLogic Remote Console repository Pull requests can be made under [The Oracle Contributor Agreement](https://www.oracle.com/technetwork/community/oca-486395.html) (OCA). diff --git a/README.md b/README.md index 1f40e4db..75995bf1 100644 --- a/README.md +++ b/README.md @@ -1,14 +1,16 @@ -# Oracle WebLogic Server Remote Console +# WebLogic Remote Console -The Oracle WebLogic Server Remote Console is a lightweight, open source console that you can use to manage your WebLogic Server domain running anywhere, such as on a physical or virtual machine, in a container, Kubernetes, or in the Oracle Cloud. The Remote Console does not need to be colocated with the WebLogic Server domain. You can install and run the Remote Console anywhere. You simply start the console server, display the console in your browser, and connect to the Administration Server of the domain using WebLogic REST APIs. +The WebLogic Remote Console is a lightweight, open source console that you can use to manage your WebLogic Server domain running anywhere, such as on a physical or virtual machine, in a container, Kubernetes, or in the Oracle Cloud. The Remote Console does not need to be colocated with the WebLogic Server domain. + +You can install and run the Remote Console anywhere, and connect to your domain using WebLogic REST APIs. You simply launch the desktop application and connect to the Administration Server of your domain. Or, you can start the console server, launch the console in a browser and then connect to the Administration Server. The Remote Console is fully supported with WebLogic Server 12.2.1.3, 12.2.1.4, and 14.1.1. Ready to download and use the Remote Console? See [Get Started](#start). -## Key Features of the WebLogic Server Remote Console -The WebLogic Server Remote Console provides an alternative WebLogic Server administration GUI that enables REST-based access to WebLogic management information, in alignment with current cloud-native trends. When connected to a WebLogic domain using the Remote Console, you can: +## Key Features of the WebLogic Remote Console +The WebLogic Remote Console provides an alternative WebLogic Server administration GUI that enables REST-based access to WebLogic management information, in alignment with current cloud-native trends. When connected to a WebLogic domain using the Remote Console, you can: * Configure WebLogic Server instances * Configure WebLogic Server clusters * Configure WebLogic Server services, such as database connectivity (JDBC), and messaging (JMS) @@ -21,18 +23,18 @@ The WebLogic Server Remote Console provides an alternative WebLogic Server admin ## Differences With the WebLogic Server Administration Console -If you are already familiar with the WebLogic Server Administration Console deployed as part of your WebLogic domain, you'll notice these key differences in the WebLogic Server Remote Console: +If you are already familiar with the WebLogic Server Administration Console deployed as part of your WebLogic domain, you'll notice these key differences in the WebLogic Remote Console: * The user interface has been completely redesigned to conform to the Oracle Alta UI Design system and the Oracle Redwood theme included with Oracle JET. * The configuration and monitoring content is separated into separate pages in the Remote Console. In the WebLogic Server Administration Console, the configuration and runtime information is presented on one page. See [Separation of Configuration and Runtime Data](site/console_uidesign.md#separation). * The Change Center is now expressed as a shopping cart. See [Use the Shopping Cart](site/console_uidesign.md#cart). * Instead of logging directly into the Administration Console deployed in a WebLogic domain, the Remote Console connects to the Administration Server in a WebLogic domain, with the credentials supplied by the user, using WebLogic REST APIs. ## Get Started -You can download a `console.zip` installer from [https://github.com/oracle/weblogic-remote-console/releases](https://github.com/oracle/weblogic-remote-console/releases), or build the console from source. In this version, the console consists of the Remote Console JAR file, associated libraries necessary to use the console, and a web application that provides an extension that you can configure in your WebLogic Server domain. The extension provides additional functionality that is not available with the console only. Although installing the extension is optional, we recommend that you install it to get the optimum functionality from the Remote Console. +You can access the Remote Console through your browser or by running a desktop application. Both versions are available to download from [https://github.com/oracle/weblogic-remote-console/releases](https://github.com/oracle/weblogic-remote-console/releases). The browser installer, `console.zip`, consists of the Remote Console JAR file and associated libraries necessary to use the console. For the desktop application, simply run the appropriate installer for your operating system. -To install the software, simply unzip the `console.zip` installer on a machine that has JDK 11 installed. After unzipping the archive, the console is ready to use. You simply start the console application, enter the console URL in a browser, and provide the Administration credentials and URL for the domain of your choice. +You should also download and install the Remote Console extension for your WebLogic Server domain. The extension provides additional functionality that is not available with the console alone. Although installing the extension is optional, we recommend that you install it to get the optimum functionality from the Remote Console. -For details about installing and running the Remote Console using the ZIP installer, see [Install and Configure the WebLogic Server Remote Console](site/install_config.md). +For details about installing and running the Remote Console, see [Install and Configure the WebLogic Remote Console](site/install_config.md). To build the Remote Console from source, see the [Developer Guide](site/developer_guide.md). diff --git a/THIRD_PARTY_LICENSES.txt b/THIRD_PARTY_LICENSES.txt index 564270ff..e0b6fd97 100644 --- a/THIRD_PARTY_LICENSES.txt +++ b/THIRD_PARTY_LICENSES.txt @@ -2282,6 +2282,1387 @@ The project maintains the following source code repositories: =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-= =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-= +electron + +Copyright (c) Electron contributors +Copyright (c) 2013-2020 GitHub Inc. + +Permission is hereby granted, free of charge, to any person obtaining +a copy of this software and associated documentation files (the +"Software"), to deal in the Software without restriction, including +without limitation the rights to use, copy, modify, merge, publish, +distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to +the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE +LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +---------------------------- Fourth-party information ---------------------- +@electron/get + +MIT License + +Copyright (c) Contributors to the Electron project + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + +@types/node + +This project is licensed under the MIT license. +Copyrights are respective of each contributor listed at the beginning of each definition file. + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +extract-zip + +Copyright (c) 2014 Max Ogden and other contributors +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + +========================== Dependencies of 4th party modules ================================================= + +------------------------ LICENSE INFO ------------------------- + +@sindresorhus/is + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +@szmarczak/http-timer + +MIT License + +Copyright (c) 2018 Szymon Marczak + +------------------------ LICENSE INFO ------------------------- + +boolean + +The MIT License (MIT) + +Copyright (c) 2014-2021 the native web. + +------------------------ LICENSE INFO ------------------------- + +buffer-crc32 + +The MIT License + +Copyright (c) 2013 Brian J. Brennan + +------------------------ LICENSE INFO ------------------------- + +buffer-from + +MIT License + +Copyright (c) 2016, 2018 Linus Unnebäck + +------------------------ LICENSE INFO ------------------------- + +cacheable-request + +MIT License + +Copyright (c) 2017 Luke Childs + +------------------------ LICENSE INFO ------------------------- + +clone-response + +MIT License + +Copyright (c) 2017 Luke Childs + +------------------------ LICENSE INFO ------------------------- + +concat-stream + +The MIT License + +Copyright (c) 2013 Max Ogden + +------------------------ LICENSE INFO ------------------------- + +config-chain + +Copyright (c) 2011 Dominic Tarr + +Permission is hereby granted, free of charge, +to any person obtaining a copy of this software and +associated documentation files (the "Software"), to +deal in the Software without restriction, including +without limitation the rights to use, copy, modify, +merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom +the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice +shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR +ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +------------------------ LICENSE INFO ------------------------- + +core-js + +Copyright (c) 2014-2021 Denis Pushkarev + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. + + +------------------------ LICENSE INFO ------------------------- + +core-util-is + +Copyright Node.js contributors. All rights reserved. + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to +deal in the Software without restriction, including without limitation the +rights to use, copy, modify, merge, publish, distribute, sublicense, and/or +sell copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS +IN THE SOFTWARE. + + +------------------------ LICENSE INFO ------------------------- + +debug + +MIT License + +Copyright (c) 2014 TJ Holowaychuk + +------------------------ LICENSE INFO ------------------------- + +debug + +MIT License + +Copyright (c) 2014 TJ Holowaychuk + +------------------------ LICENSE INFO ------------------------- + +decompress-response + +MIT License (MIT) + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +defer-to-connect + +MIT License + +Copyright (c) 2018 Szymon Marczak + +------------------------ LICENSE INFO ------------------------- + +define-properties + +The MIT License (MIT) + +Copyright (C) 2015 Jordan Harband + +------------------------ LICENSE INFO ------------------------- + +detect-node + +MIT License + +Copyright (c) 2017 Ilya Kantor + +------------------------ LICENSE INFO ------------------------- + +duplexer3 + +Copyright (c) 2013, Deoxxa Development +====================================== +All rights reserved. +-------------------- + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: +1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. +2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. +3. Neither the name of Deoxxa Development nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY DEOXXA DEVELOPMENT ''AS IS'' AND ANY +EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL DEOXXA DEVELOPMENT BE LIABLE FOR ANY +DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + +------------------------ LICENSE INFO ------------------------- + +encodeurl + +MIT License + +Copyright (c) 2016 Douglas Christopher Wilson + +------------------------ LICENSE INFO ------------------------- + +end-of-stream + +The MIT License (MIT) + +Copyright (c) 2014 Mathias Buus + +------------------------ LICENSE INFO ------------------------- + +env-paths + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +es6-error + +The MIT License (MIT) + +Copyright (c) 2015 Ben Youngblood + +------------------------ LICENSE INFO ------------------------- + +escape-string-regexp + +MIT License + +Copyright (c) Sindre Sorhus (https://sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +fd-slicer + +Copyright (c) 2014 Andrew Kelley + +Permission is hereby granted, free of charge, to any person +obtaining a copy of this software and associated documentation files +(the "Software"), to deal in the Software without restriction, +including without limitation the rights to use, copy, modify, merge, +publish, distribute, sublicense, and/or sell copies of the Software, +and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS +BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN +ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + + +------------------------ LICENSE INFO ------------------------- + +fs-extra + +MIT License + +Copyright (c) 2011-2017 JP Richardson + +------------------------ LICENSE INFO ------------------------- + +get-stream + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +get-stream + +MIT License + +Copyright (c) Sindre Sorhus (https://sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +global-agent + +Copyright (c) 2019, Gajus Kuizinas (http://gajus.com/) +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + * Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + * Neither the name of the Gajus Kuizinas (http://gajus.com/) nor the + names of its contributors may be used to endorse or promote products + derived from this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL ANUARY BE LIABLE FOR ANY +DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + +------------------------ LICENSE INFO ------------------------- + +global-tunnel-ng + +Copyright (c) 2013, GoInstant Inc., a salesforce.com company +All rights reserved. + +Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. + +* Neither the name of salesforce.com, nor GoInstant, nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + +------------------------ LICENSE INFO ------------------------- + +globalthis + +The MIT License (MIT) + +Copyright (c) 2016 Jordan Harband + +------------------------ LICENSE INFO ------------------------- + +got + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +graceful-fs + +The ISC License + +Copyright (c) Isaac Z. Schlueter, Ben Noordhuis, and Contributors + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR +IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + + +------------------------ LICENSE INFO ------------------------- + +http-cache-semantics + +Copyright 2016-2018 Kornel Lesiński + +Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: + +1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. + +2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + +------------------------ LICENSE INFO ------------------------- + +inherits + +The ISC License + +Copyright (c) Isaac Z. Schlueter + +------------------------ LICENSE INFO ------------------------- + +ini + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +------------------------ LICENSE INFO ------------------------- + +isarray + +The MIT License + +Copyright (c) 2013 Julian Gruber <julian@juliangruber.com> + +------------------------ LICENSE INFO ------------------------- + +json-buffer + +Copyright (c) 2013 Dominic Tarr + +Permission is hereby granted, free of charge, +to any person obtaining a copy of this software and +associated documentation files (the "Software"), to +deal in the Software without restriction, including +without limitation the rights to use, copy, modify, +merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom +the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice +shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR +ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + + +------------------------ LICENSE INFO ------------------------- + +json-stringify-safe + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +------------------------ LICENSE INFO ------------------------- + +jsonfile + +MIT License + +Copyright (c) 2012-2015, JP Richardson + +------------------------ LICENSE INFO ------------------------- + +keyv + +MIT License + +Copyright (c) 2017 Luke Childs + +------------------------ LICENSE INFO ------------------------- + +lodash + +Copyright OpenJS Foundation and other contributors + +Based on Underscore.js, copyright Jeremy Ashkenas, +DocumentCloud and Investigative Reporters & Editors + +This software consists of voluntary contributions made by many +individuals. For exact contribution history, see the revision history +available at https://github.com/lodash/lodash + +The following license applies to all parts of this software except as +documented below: + +==== + +Permission is hereby granted, free of charge, to any person obtaining +a copy of this software and associated documentation files (the +"Software"), to deal in the Software without restriction, including +without limitation the rights to use, copy, modify, merge, publish, +distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to +the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE +LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +==== + +Copyright and related rights for sample code are waived via CC0. Sample +code is defined as all source code displayed within the prose of the +documentation. + +CC0: http://creativecommons.org/publicdomain/zero/1.0/ + +==== + +Files located in the node_modules and vendor directories are externally +maintained libraries used by this software which have their own +licenses; we recommend you read them, as their terms may differ from the +terms above. + + +------------------------ LICENSE INFO ------------------------- + +lowercase-keys + +The MIT License (MIT) + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +lowercase-keys + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +lru-cache + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +------------------------ LICENSE INFO ------------------------- + +matcher + +MIT License + +Copyright (c) Sindre Sorhus (https://sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +mimic-response + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +minimist + +This software is released under the MIT license: + +------------------------ LICENSE INFO ------------------------- + +mkdirp + +Copyright 2010 James Halliday (mail@substack.net) + +This project is free software released under the MIT/X11 license: + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. + + +------------------------ LICENSE INFO ------------------------- + +ms + +The MIT License (MIT) + +Copyright (c) 2016 Zeit, Inc. + +------------------------ LICENSE INFO ------------------------- + +normalize-url + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +npm-conf + +MIT License + +Copyright (c) Kevin Mårtensson (github.com/kevva) + +------------------------ LICENSE INFO ------------------------- + +object-keys + +The MIT License (MIT) + +Copyright (C) 2013 Jordan Harband + +------------------------ LICENSE INFO ------------------------- + +once + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +------------------------ LICENSE INFO ------------------------- + +p-cancelable + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +pend + +The MIT License (Expat) + +Copyright (c) 2014 Andrew Kelley + +------------------------ LICENSE INFO ------------------------- + +pify + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +prepend-http + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +process-nextick-args + +# Copyright (c) 2015 Calvin Metcalf + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +**THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE.** + + +------------------------ LICENSE INFO ------------------------- + +progress + +(The MIT License) + +Copyright (c) 2017 TJ Holowaychuk + +------------------------ LICENSE INFO ------------------------- + +proto-list + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +------------------------ LICENSE INFO ------------------------- + +pump + +The MIT License (MIT) + +Copyright (c) 2014 Mathias Buus + +------------------------ LICENSE INFO ------------------------- + +readable-stream + +Node.js is licensed for use as follows: + +""" +Copyright Node.js contributors. All rights reserved. + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to +deal in the Software without restriction, including without limitation the +rights to use, copy, modify, merge, publish, distribute, sublicense, and/or +sell copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS +IN THE SOFTWARE. +""" + +This license applies to parts of Node.js originating from the +https://github.com/joyent/node repository: + +""" +Copyright Joyent, Inc. and other Node contributors. All rights reserved. +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to +deal in the Software without restriction, including without limitation the +rights to use, copy, modify, merge, publish, distribute, sublicense, and/or +sell copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS +IN THE SOFTWARE. +""" + + +------------------------ LICENSE INFO ------------------------- + +responselike + +Copyright (c) 2017 Luke Childs + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. + + +------------------------ LICENSE INFO ------------------------- + +roarr + +Copyright (c) 2019, Gajus Kuizinas (http://gajus.com/) +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + * Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + * Neither the name of the Gajus Kuizinas (http://gajus.com/) nor the + names of its contributors may be used to endorse or promote products + derived from this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL ANUARY BE LIABLE FOR ANY +DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + +------------------------ LICENSE INFO ------------------------- + +safe-buffer + +The MIT License (MIT) + +Copyright (c) Feross Aboukhadijeh + +------------------------ LICENSE INFO ------------------------- + +semver-compare + +This software is released under the MIT license: + +------------------------ LICENSE INFO ------------------------- + +semver + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR +IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + + +------------------------ LICENSE INFO ------------------------- + +semver + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +------------------------ LICENSE INFO ------------------------- + +serialize-error + +MIT License + +Copyright (c) Sindre Sorhus (https://sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +sprintf-js + +Copyright (c) 2007-present, Alexandru Mărășteanu +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: +* Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. +* Neither the name of this software nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + +------------------------ LICENSE INFO ------------------------- + +string_decoder + +Node.js is licensed for use as follows: + +""" +Copyright Node.js contributors. All rights reserved. + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to +deal in the Software without restriction, including without limitation the +rights to use, copy, modify, merge, publish, distribute, sublicense, and/or +sell copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS +IN THE SOFTWARE. +""" + +This license applies to parts of Node.js originating from the +https://github.com/joyent/node repository: + +""" +Copyright Joyent, Inc. and other Node contributors. All rights reserved. +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to +deal in the Software without restriction, including without limitation the +rights to use, copy, modify, merge, publish, distribute, sublicense, and/or +sell copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS +IN THE SOFTWARE. +""" +------------------------ LICENSE INFO ------------------------- + +sumchecker + +Apache License Version 2.0, January 2004 http://www.apache.org/licenses/ + +------------------------ LICENSE INFO ------------------------- + +to-readable-stream + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +tunnel + +The MIT License (MIT) + +Copyright (c) 2012 Koichi Kobayashi + +------------------------ LICENSE INFO ------------------------- + +type-fest + +MIT License + +Copyright (c) Sindre Sorhus (https:/sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +typedarray + +/* + Copyright (c) 2010, Linden Research, Inc. + Copyright (c) 2012, Joshua Bell + + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be included in + all copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + THE SOFTWARE. + $/LicenseInfo$ + */ + +// Original can be found at: +// https://bitbucket.org/lindenlab/llsd +// Modifications by Joshua Bell inexorabletash@gmail.com +// https://github.com/inexorabletash/polyfill + +// ES3/ES5 implementation of the Krhonos Typed Array Specification +// Ref: http://www.khronos.org/registry/typedarray/specs/latest/ +// Date: 2011-02-01 +// +// Variations: +// * Allows typed_array.get/set() as alias for subscripts (typed_array[]) + + +------------------------ LICENSE INFO ------------------------- + +universalify + +(The MIT License) + +Copyright (c) 2017, Ryan Zimmerman + +------------------------ LICENSE INFO ------------------------- + +url-parse-lax + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +------------------------ LICENSE INFO ------------------------- + +util-deprecate + +(The MIT License) + +Copyright (c) 2014 Nathan Rajlich + +------------------------ LICENSE INFO ------------------------- + +wrappy + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +------------------------ LICENSE INFO ------------------------- + +yallist + +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +------------------------ LICENSE INFO ------------------------- + +yauzl + +The MIT License (MIT) + +Copyright (c) 2014 Josh Wolfe + +=================================================================================== +=================================================================================== + +electron-builder + +The MIT License (MIT) + +Copyright (c) 2015 Loopline Systems + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + +--------------------------------------------------------------------------------------------- + +@types/yargs + +MIT License + +Copyright 2010 James Halliday (mail@substack.net); Modified work Copyright 2014 Contributors (ben@npmjs.com) + +--------------------------------------------------------------------------------------------- + +app-builder-lib + + +The MIT License (MIT) + +Copyright (c) 2015 Loopline Systems + +--------------------------------------------------------------------------------------------- + +bluebird-lst + +The MIT License (MIT) + +Copyright (c) 2017 Vladimir Krivosheev + +--------------------------------------------------------------------------------------------- + +builder-util + +The MIT License (MIT) + +Copyright (c) 2015 Loopline Systems + +--------------------------------------------------------------------------------------------- + +builder-util-runtime + +The MIT License (MIT) + +Copyright (c) 2015 Loopline Systems + +--------------------------------------------------------------------------------------------- + +chalk + +MIT License + +Copyright (c) Sindre Sorhus (sindresorhus.com) + +--------------------------------------------------------------------------------------------- + +dmg-builder + +The MIT License (MIT) + +Copyright (c) 2015 Loopline Systems + +--------------------------------------------------------------------------------------------- + +fs-extra + +(The MIT License) + +Copyright (c) 2011-2017 JP Richardson + +--------------------------------------------------------------------------------------------- + +is-ci + +The MIT License (MIT) + +Copyright (c) 2016-2021 Thomas Watson Steen + +--------------------------------------------------------------------------------------------- + +lazy-val + +MIT +https://github.com/develar/lazy-val + +--------------------------------------------------------------------------------------------- + +read-config-file + +MIT License + +Copyright (c) 2020 Vladimir Krivosheev + +--------------------------------------------------------------------------------------------- + +sanitize-filename + +This project is licensed under the [WTFPL][] and [ISC][] licenses. + +[WTFPL]: https://en.wikipedia.org/wiki/WTFPL +[ISC]: https://opensource.org/licenses/ISC + +## WTFPL + +DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE +Version 2, December 2004 + +Copyright (C) 2004 Sam Hocevar \ + +Everyone is permitted to copy and distribute verbatim or modified copies +of this license document, and changing it is allowed as long as the name +is changed. + +DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE TERMS AND CONDITIONS FOR +COPYING, DISTRIBUTION AND MODIFICATION + +0. You just DO WHAT THE FUCK YOU WANT TO. + +## ISC + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + +--------------------------------------------------------------------------------------------- + +update-notifier + +Copyright Google + +Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: + +1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. + +2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +--------------------------------------------------------------------------------------------- + +yargs + +Copyright 2010 James Halliday (mail@substack.net) +Modified work Copyright 2014 Contributors (ben@npmjs.com) + +This project is free software released under the MIT/X11 license: + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. + +=================================================================================== +=================================================================================== + Jersey Client =============== jersey-core-client (org.glassfish.jersey.core:jersey-client) diff --git a/common/pom.xml b/common/pom.xml index 1c5de7a9..0895ae37 100644 --- a/common/pom.xml +++ b/common/pom.xml @@ -36,12 +36,12 @@ org.glassfish.jersey.media jersey-media-sse - 2.31 + 2.33 org.glassfish.jersey.media jersey-media-multipart - 2.31 + 2.33 org.junit.jupiter diff --git a/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicCreateFormSource.java b/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicCreateFormSource.java index 0f95b959..a79eca13 100644 --- a/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicCreateFormSource.java +++ b/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicCreateFormSource.java @@ -14,6 +14,15 @@ */ public class WeblogicCreateFormSource extends BaseWeblogicPageSource { private List properties = new ArrayList<>(); + private List sections = new ArrayList<>(); + + public List getSections() { + return sections; + } + + public void setSections(List sections) { + this.sections = ListUtils.nonNull(sections); + } public List getProperties() { return properties; diff --git a/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicSectionSource.java b/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicSectionSource.java new file mode 100644 index 00000000..ad53b672 --- /dev/null +++ b/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicSectionSource.java @@ -0,0 +1,34 @@ +// Copyright (c) 2021, Oracle and/or its affiliates. +// Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. + +package weblogic.console.backend.pagedesc; + +import java.util.ArrayList; +import java.util.List; + +import weblogic.console.backend.utils.ListUtils; + +/** + * This POJO mirrors the yaml source file format for configuring information + * about a section on a weblogic bean's form page + */ +public class WeblogicSectionSource { + private String title; + private List properties = new ArrayList<>(); + + public String getTitle() { + return title; + } + + public void setTitle(String title) { + this.title = title; + } + + public List getProperties() { + return properties; + } + + public void setProperties(List properties) { + this.properties = ListUtils.nonNull(properties); + } +} diff --git a/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicSliceFormSource.java b/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicSliceFormSource.java index cbd4e3f6..67a33ebe 100644 --- a/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicSliceFormSource.java +++ b/core/src/main/java/weblogic/console/backend/pagedesc/WeblogicSliceFormSource.java @@ -14,11 +14,30 @@ */ public class WeblogicSliceFormSource extends BaseWeblogicPageSource { private List properties = new ArrayList<>(); + private List sections = new ArrayList<>(); + + public List getSections() { + return sections; + } + + public void setSections(List sections) { + this.sections = ListUtils.nonNull(sections); + } public List getProperties() { return properties; } + public List getAllProperties() { + List ret = new ArrayList<>(); + for (WeblogicSectionSource section : getSections()) { + ret.addAll(section.getProperties()); + } + ret.addAll(getProperties()); + ret.addAll(getAdvancedProperties()); + return ret; + } + public void setProperties(List properties) { this.properties = ListUtils.nonNull(properties); } diff --git a/core/src/main/java/weblogic/console/backend/typedesc/WeblogicBeanTypes.java b/core/src/main/java/weblogic/console/backend/typedesc/WeblogicBeanTypes.java index 205df001..0c0271f2 100644 --- a/core/src/main/java/weblogic/console/backend/typedesc/WeblogicBeanTypes.java +++ b/core/src/main/java/weblogic/console/backend/typedesc/WeblogicBeanTypes.java @@ -1112,12 +1112,12 @@ private void mergeConsolePropertyInfo( // Same rational for 'dateAsLong' (boolean that defaults to false) if (prop.isDateAsLong()) { - merged.setReference(prop.isDateAsLong()); + merged.setDateAsLong(prop.isDateAsLong()); } // Same rational for 'allowNullReference' (boolean that defaults to true) if (!prop.isAllowNullReference()) { - merged.setReference(prop.isAllowNullReference()); + merged.setAllowNullReference(prop.isAllowNullReference()); } } diff --git a/core/src/main/java/weblogic/console/backend/utils/StringUtils.java b/core/src/main/java/weblogic/console/backend/utils/StringUtils.java index 451efbc1..2cc099f1 100644 --- a/core/src/main/java/weblogic/console/backend/utils/StringUtils.java +++ b/core/src/main/java/weblogic/console/backend/utils/StringUtils.java @@ -90,6 +90,16 @@ public static String getSingular(String plural) { return singular; } + /** + * Determines whether a single letter is a vowel + * + * @param letter + * @return true if letter is a vowel + */ + private static boolean isVowel(String letter) { + return "aeiou".contains(letter); + } + /** * Converts a singular string to a plural string * @@ -99,9 +109,15 @@ public static String getSingular(String plural) { public static String getPlural(String singular) { String plural = replaceEnding(singular, "ss", "sses"); if (plural == null) { - plural = replaceEnding(singular, "y", "ies"); + int len = singular.length(); + // Check whether the letter before a 'y' is a vowel or not + if (singular.endsWith("y") && !isVowel(singular.substring(len - 2, len - 1))) { + // not a vowel, so replace 'y' with 'ies' + plural = replaceEnding(singular, "y", "ies"); + } } if (plural == null) { + // includes case where singular ends in 'y' and preceding letter is a vowel plural = singular + "s"; } return plural; @@ -205,7 +221,7 @@ public static String camelCaseToLowerCaseWords(String camelCase) { } else { // in a normal word - continue // e.g. ...1b..., ...#b... - } + } } else { if (wasUpperCase) { // in an acronym - continue @@ -216,7 +232,7 @@ public static String camelCaseToLowerCaseWords(String camelCase) { } else { // in an acronym or normal word - continue // e.g. ...11..., ...#1..., ...##..., ...1#... - } + } } } } diff --git a/driver/src/main/java/weblogic/console/backend/driver/ConfigurationPageWeblogicSearchResponseRestMapper.java b/driver/src/main/java/weblogic/console/backend/driver/ConfigurationPageWeblogicSearchResponseRestMapper.java index f2b253a7..8565a8d8 100644 --- a/driver/src/main/java/weblogic/console/backend/driver/ConfigurationPageWeblogicSearchResponseRestMapper.java +++ b/driver/src/main/java/weblogic/console/backend/driver/ConfigurationPageWeblogicSearchResponseRestMapper.java @@ -336,7 +336,7 @@ private JsonValue harvestedValueToJsonValue( // Gets the default value to use based solely on the property's type. // Used when the bean info doesn't have a default value for the property. private JsonValue getPropertyTypeDefaultJsonValue(WeblogicBeanProperty beanProp) throws Exception { - if (beanProp.isArray()) { + if (beanProp.isArray() && !beanProp.isReferenceAsReferences()) { return JsonValue.EMPTY_JSON_ARRAY; } String type = beanProp.getPropertyType(); @@ -396,7 +396,8 @@ private void addCreateFormPropertyOptions( JsonArray rdjOptions = getRDJIdentitiesFromWeblogicIdentities(weblogicOptions); // See if we need to add a None option - boolean allowNullReference = beanProp.isReference() && beanProp.isAllowNullReference(); + boolean allowNullReference = (beanProp.isReferenceAsReferences() || beanProp.isReference()) + && beanProp.isAllowNullReference(); // Sort the references and add a None options if needed JsonArray sortedRDJOptions = sortRDJReferences(rdjOptions, allowNullReference); diff --git a/driver/src/main/java/weblogic/console/backend/driver/PageRestMappings.java b/driver/src/main/java/weblogic/console/backend/driver/PageRestMappings.java index 4d8fe429..85fe3603 100644 --- a/driver/src/main/java/weblogic/console/backend/driver/PageRestMappings.java +++ b/driver/src/main/java/weblogic/console/backend/driver/PageRestMappings.java @@ -132,11 +132,7 @@ private void getSliceFormPropertyNames( Set propertyNames, WeblogicSliceFormPageSource pageSource ) throws Exception { - for (WeblogicPropertySource propertySource : pageSource.getSliceFormSource().getProperties()) { - propertyNames.add(propertySource.getName()); - } - for (WeblogicPropertySource propertySource : - pageSource.getSliceFormSource().getAdvancedProperties()) { + for (WeblogicPropertySource propertySource : pageSource.getSliceFormSource().getAllProperties()) { propertyNames.add(propertySource.getName()); } } diff --git a/driver/src/main/java/weblogic/console/backend/driver/UnlocalizedWeblogicPages.java b/driver/src/main/java/weblogic/console/backend/driver/UnlocalizedWeblogicPages.java index 0be0a05e..dfb5897c 100644 --- a/driver/src/main/java/weblogic/console/backend/driver/UnlocalizedWeblogicPages.java +++ b/driver/src/main/java/weblogic/console/backend/driver/UnlocalizedWeblogicPages.java @@ -24,6 +24,7 @@ import weblogic.console.backend.pagedesc.WeblogicPageSources; import weblogic.console.backend.pagedesc.WeblogicPropertyPresentationSource; import weblogic.console.backend.pagedesc.WeblogicPropertySource; +import weblogic.console.backend.pagedesc.WeblogicSectionSource; import weblogic.console.backend.pagedesc.WeblogicSliceFormPageSource; import weblogic.console.backend.pagedesc.WeblogicSliceFormPresentationSource; import weblogic.console.backend.pagedesc.WeblogicSliceFormSource; @@ -134,6 +135,19 @@ private void createSliceForm( sliceForm.setProperties( createProperties(pageSource, sliceFormSource.getProperties(), isCreate) ); + // I'm gonna do this for now to get things back working while waiting + // for the CFE to catch up: + List tempAllNormalProperties = new ArrayList<>(); + tempAllNormalProperties.addAll(createProperties(pageSource, sliceFormSource.getProperties(), isCreate)); + for (WeblogicSectionSource section : sliceFormSource.getSections()) { + FormSection formSection = sliceForm.addSection(); + if (StringUtils.notEmpty(section.getTitle())) { + formSection.setTitle(LocalizationUtils.sectionTitleKey(pageSource, section.getTitle())); + } + formSection.setProperties(createProperties(pageSource, section.getProperties(), isCreate)); + tempAllNormalProperties.addAll(createProperties(pageSource, section.getProperties(), isCreate)); + } + sliceForm.setProperties(tempAllNormalProperties); sliceForm.setAdvancedProperties( createProperties(pageSource, sliceFormSource.getAdvancedProperties(), isCreate) ); @@ -199,7 +213,7 @@ private WeblogicSliceFormPresentation createSliceFormPresentation( // Force the form to be single column if it doesn't have many properties: if (!singleColumn) { WeblogicSliceFormSource sliceFormSource = pageSource.getSliceFormSource(); - int propCount = sliceFormSource.getProperties().size() + sliceFormSource.getAdvancedProperties().size(); + int propCount = sliceFormSource.getAllProperties().size(); if (propCount <= MAX_SINGLE_COLUMN_PROPERTY_COUNT) { singleColumn = true; } diff --git a/driver/src/main/java/weblogic/console/backend/driver/WeblogicPageRepresenter.java b/driver/src/main/java/weblogic/console/backend/driver/WeblogicPageRepresenter.java index 6ffc68f7..92188a1d 100644 --- a/driver/src/main/java/weblogic/console/backend/driver/WeblogicPageRepresenter.java +++ b/driver/src/main/java/weblogic/console/backend/driver/WeblogicPageRepresenter.java @@ -99,6 +99,9 @@ protected boolean isIgnore(WeblogicSliceForm prop, Property p) { if ("slices".equals(name) && ListUtils.isEmpty(prop.getSlices())) { return true; } + if ("sections".equals(name) && ListUtils.isEmpty(prop.getSections())) { + return true; + } if ("advancedProperties".equals(name) && ListUtils.isEmpty(prop.getAdvancedProperties())) { return true; } diff --git a/driver/src/main/java/weblogic/console/backend/driver/WeblogicSliceForm.java b/driver/src/main/java/weblogic/console/backend/driver/WeblogicSliceForm.java index edc37797..89f39ced 100644 --- a/driver/src/main/java/weblogic/console/backend/driver/WeblogicSliceForm.java +++ b/driver/src/main/java/weblogic/console/backend/driver/WeblogicSliceForm.java @@ -50,4 +50,20 @@ public WeblogicSliceFormPresentation getPresentation() { public void setPresentation(WeblogicSliceFormPresentation presentation) { this.presentation = presentation; } + + private List sections = new ArrayList<>(); + + public List getSections() { + return sections; + } + + public void setSections(List sections) { + this.sections = sections; + } + + public FormSection addSection() { + FormSection section = new FormSection(); + sections.add(section); + return section; + } } diff --git a/frontend/.eslintignore b/frontend/.eslintignore index 63645567..36500cad 100644 --- a/frontend/.eslintignore +++ b/frontend/.eslintignore @@ -1,2 +1 @@ -src/js/system-tests -src/js/unit-tests \ No newline at end of file +src/js/resources/nls \ No newline at end of file diff --git a/frontend/.eslintrc.js b/frontend/.eslintrc.js index ce464e2e..8fcadb75 100644 --- a/frontend/.eslintrc.js +++ b/frontend/.eslintrc.js @@ -31,17 +31,6 @@ module.exports = { "no-unused-vars": "off", "no-console": "off", "no-fallthrough": "off", - "no-prototype-builtins": "off", - "js-copyright": ["error",{ - regexPatterns: { - startLine: "^\\/\\*\\*\\s*", - licenseTag: "\\s*\\*\\s*@license", - copyrightLine: "\\s*\\*\\s*Copyright\\s*\\(c\\)\\s*[\\s*\\d{4}$|\\d{4}$\\-\\d{4}$|\\d{4}$,]+[ ,|]\\s*Oracle[ |Corporation|Corp|Corp\\.]+and\\/or its affiliates.", - uplLine: "\\s*\\*\\s*The Universal Permissive License \\(UPL\\), Version 1\\.0", - ignoreTag: "\\s*\\*\\s*@ignore", - endLine: "\\s*\\*\\/" - }, - validCopyright: "/**\n * @license\n * Copyright (c) 2020 Oracle Corporation and/or its affiliates.\n * The Universal Permissive License (UPL), Version 1.0\n * @ignore\n */\n" - }] + "no-prototype-builtins": "off" } }; \ No newline at end of file diff --git a/frontend/.eslintrc.json b/frontend/.eslintrc.json index 9ecd23e5..4e972375 100644 --- a/frontend/.eslintrc.json +++ b/frontend/.eslintrc.json @@ -1,33 +1,22 @@ { - "env": { - "browser": true, - "amd": true, - "node": true, - "es6": true, - "mocha": true - }, - "extends": "eslint:recommended", - "parserOptions": { - "ecmaVersion": 12 - }, - "globals": { - "requirejs": "off" - }, - "overrides": [ - { - "files": ["src/js/viewModels/configuration.js", "src/js/viewModels/monitoring.js"], - "env": { - "node": true - }, - "rules": { - "strict": "off", - "no-undef": "off", - "no-unused-vars": "off" - } - } - ], - "rules": { - "strict": "off", - "no-console": "off" - } + "env": { + "browser": true, + "amd": true, + "node": true, + "es6": true, + "mocha": true + }, + "extends": "eslint:recommended", + "parserOptions": { + "ecmaVersion": 2016 + }, + "globals": { + "requirejs": false + }, + "overrides": [ + ], + "rules": { + "strict": "off", + "no-console": "off" + } } diff --git a/frontend/.jsdocrc.json b/frontend/.jsdocrc.json new file mode 100644 index 00000000..533a731d --- /dev/null +++ b/frontend/.jsdocrc.json @@ -0,0 +1,3 @@ +{ + "plugins": ["plugins/markdown"] +} \ No newline at end of file diff --git a/frontend/eslint-html.template b/frontend/eslint-html.template deleted file mode 100644 index 17a68bed..00000000 --- a/frontend/eslint-html.template +++ /dev/null @@ -1,116 +0,0 @@ - - - - - ESLint Report - - - - - -

ESLint Report

-
- -
- - - - - -
- - - \ No newline at end of file diff --git a/frontend/eslint-rules/README.md b/frontend/eslint-rules/README.md new file mode 100644 index 00000000..30efbde6 --- /dev/null +++ b/frontend/eslint-rules/README.md @@ -0,0 +1,136 @@ +# Oracle WebLogic Server Remote Console Project + +## ESLint Integration + +### Overview +[ESLint](https://eslint.org/) is an open source JavaScript linting utility that help you overcome developer errors, as JavaScript is a loosely-typed language. It consist of a CLI and a set of pluggable linting "rules" that the JavaScript code either pass or fail. + +A report is generated stating which "rules" (and which ``.js`` files) failed, along with what line number the offending code is on. + +The ESLint CLI (and the "rules") are configurable, but it can only evaluate ``.js`` files or ``.html`` files that have a ```` tag in them. + +A `.js` file can "work" at runtime, but still have ESLint warnings/errors reported against it. This is why we run ESLint as part of the make or build process, and treat ESLint rule failures as a failure of that process. + +Finally, ESLint rule evaluation is what the product is primarily used for, so it is well worth it to spend some time perusing the ESLint documentation on ["Working with Rules"](https://eslint.org/docs/developer-guide/working-with-rules). + +### Installing ESLint in the `frontend` Maven Module +ESLint is available as a npm package that has already been added as a devDependency in our `package.json` file. This means that it will automatically be added to your `frontend` project, if you (or the make) runs the `ojet restore` command. + +### Configuring ESLint in the `frontend` Maven Module +We use the `frontend/.eslintrc.js` and `frontend/.eslintignore` files to configure ESLint. + +* __.eslintrc.js__ The file used to specify the rules used when running the `node_module/.bin/eslint` CLI command. +* __.eslintignore__ The file used to specify the directories that will be excluded when running the `node_module/.bin/eslint` CLI command. Current this includes the system tests, CFE unit tests and any custom eslint rules we write. + +#### Core Rule Overrides +The `overrides` array in the `/frontend/.eslintrc.js` file, is used to specify which `files` and `rules` are not subjected to the core rules: +
+    overrides: [
+      {
+        files: [
+          "main.js"
+        ],
+        rules: {
+          "strict": "off",
+          "no-undef": "off"
+        }
+      }
+    ]
+
+ +The `main.js` file is provided with the JET install, so we don't try to make it adhere to the same ESLint rules as our own ``.js`` files. + +### Running ESLint CLI with ``Maven`` +ESLint CLI is a standalone executable (`eslint`) located under the `/frontend/node_modules/.bin` directory. The `exec-maven-plugin` is used to allow it to be called when a `mvn test` command is issued. + +Enter the following at a prompt to run ESLint on the `.js` files of the CFE: +``` +$ cd /frontend +$ mvn test +``` + +`node_modules/.bin/eslint` returns a non-zero value if the `--fix` option is not specified on the command line, and: + + 1. The copyright is not located at the top of the ``.html``, or + 2. An existing copyright is at the top of the ``.html``, but something is incorrect in it. + +The ``/frontend/pom.xml`` file uses the ``compact`` as the ESLint report format: +``` +compact +``` + +That format write ASCII text to ``stdout``. + +### Running ESLint CLI with ``Node`` +Type the following in a terminal, to run ESLint CLI with ``node``: +``` +cd /frontend +node_modules/.bin/eslint --rulesdir eslint-rules/ -f html -o eslint-js.html src/js +``` +Here, the ``src/js`` argument determines which files will be linted. It can be a directory or a single file, but it must be under the ``src/js`` folder. + +Use the following table to find out what the command-line options mean and do: + + + + + + + + + + + + + + + + + + +
OptionComment
---rulesdirDirectory path to custom rule implementations (e.g. Javascript files).
-fReport format (or formatter).
-oPath/name of file for the report
+ +When the prompt returns, you can load the `/frontend/eslint-js.html` file into a web browser and use the ``[+]`` on each line to see report details on problems. + +### The ESLint Report +The ESLint report identifies which ``.js`` files had rule violations, and where they occurred in the file. + +This report is generated to ``stdout`` when the ESLint CLI is run as part of a ``mvn test`` command. The other formats available can be found [here](https://eslint.org/docs/user-guide/command-line-interface#options). + +#### Fixing Errors Appearing in the ESLint Report +The ESLint report contains the line and column location of each error, to aid in fixing errors. It may also include a message stating how to fix something. + +If you elect to use ``html`` as the format for the output report, you can load it into a web browser and use the ``[+]`` on each line to see report details on problems. + +### GitLab CI Pipeline Integration +ESLint CLI return a zero or non-zero exit code, so you should be able to use it directly in shell scripts or CI pipeline rules. + +### Custom ESLint Rules +ESLint provides a way for developers to write "custom rules" (in the JavaScript language) that can be used in concert with the ones that come with the product. We took advantage of this to create a "custom rule" that checks for Oracle copyright notices, at the very top of ``.js`` files: + +``` +/** + * @license + * Copyright (c) [\s*\d{4}$|\d{4}$\-\d{4}$|\d{4}$,]+[ ,|] Oracle and/or its affiliates. + * The Universal Permissive License (UPL), Version 1.0 + */ +``` + +RegEx matching is the principle technology used in ``js-copyright.js``, but most of it's code is associated with what's required to be a custom rule. The ``regex`` matching is used to do the following: + +1. To ensure the pieces of the Oracle copyright notice are present in a multi-line JavaScript comment, at the very top of a ``.js`` file. "Very top" means the first line of the ``.js`` file, not the first non-whitespace line. +2. To ensure that the words in each line match, from both a case and whitespace perspective. It does not do "spell-checking", but misspelling of a word will be caught by the case and whitespace enforcement. +3. To ensure that the year range specified properly, and that the ones used are in the ``acceptableYears`` array field, that appears in the ``/frontend/.eslintrc.js`` file. + +There is no specific documentation on _how to write a custom rule_, but there is documentation on _working with rules_, in general. This means that you kind of have to examine the latter, to figure out how to write one. Click [here](https://eslint.org/docs/developer-guide/working-with-rules) to check out the _Working with Rules_ section of the ESLint documentation. + +The ESLint documentation talks about rules optionally being able to "fix" things. The ``js-copyright`` custom rule does not try to fix errors in the Oracle copyright notice. It simply reports that the expected regex match did not happen. The underlying reason could be a misspelled word, case-sensitivity or additional/missing whitespace. It does nt try to figure out which of those is true, but additional regex patterns (or code that performs the Levenshtein Distance algorithm) could be added to do that, if so desired. + +Care should be taken when modifying the ``/frontend/.eslintrc.js`` file because: + +1. The ESLint CLI will typically just generate a JavaScript stacktrace when it's not able to pass control to a custom rule. That stacktrace may or may not be useful for debugging purposes. +2. The ``js-copyright`` custom rule does not try to double as a "regex pattern validator". If there's something wrong with a regex pattern under the ``regexPatterns`` property in ``/frontend/.eslintrc.js``, a JavaScript Error will occur when it gets passed as an argument to the built-in ``RegExp(pattern)`` JavaScript function. When that happens, you will need to figure out how to correct the regex pattern using your own experience, or the Internet. + +Finally, the ESLint CLI can only process ``.html`` files that have a ```` tag in them. This restriction is passed down to custom rules that the ESLint CLI runs. None of the ``.html`` files under the ``/src/js/view`` folder have ```` tags in them, so the ``js-copyright`` custom rule cannot be used on them. + +We experimented with just writing a JavaScript module that would run on ``node``, and produce output that looked like the ``html`` format ESLint report, but it was too complex and would have required a lot more effort to make it "appear to be" an ESLint custom rule. \ No newline at end of file diff --git a/frontend/src/js/eslint-rules/js-copyright.js b/frontend/eslint-rules/js-copyright.js similarity index 62% rename from frontend/src/js/eslint-rules/js-copyright.js rename to frontend/eslint-rules/js-copyright.js index bf5137d2..51784f9a 100644 --- a/frontend/src/js/eslint-rules/js-copyright.js +++ b/frontend/eslint-rules/js-copyright.js @@ -1,6 +1,6 @@ /** * @license - * Copyright (c) 2020, Oracle and/or its affiliates. + * Copyright (c) 2020, 2021, Oracle and/or its affiliates. * The Universal Permissive License (UPL), Version 1.0 * @ignore */ @@ -51,12 +51,20 @@ module.exports = { endLine: { type: "string", default: "\\s*\\*\\/" + }, + licenseWord: { + type: "string", + default: "\\s*@license" + }, + copyrightWord: { + type: "string", + default: "\\s*Copyright" } } }, validCopyright: { type: "string", - default: "/**\n * @license\n * Copyright (c) 2020 Oracle Corporation and/or its affiliates.\n * The Universal Permissive License (UPL), Version 1.0\n * @ignore\n */\n" + default: "/**\n * @license\n * Copyright (c) 2020, 2021 Oracle Corporation and/or its affiliates.\n * The Universal Permissive License (UPL), Version 1.0\n * @ignore\n */\n" } } } @@ -65,7 +73,7 @@ module.exports = { "missingCopyright": "Oracle copyright missing from {{fileType}} file.", "startLineError": "First line of .js file does not begin with /**.", "licenseTagError": "@license tag missing or in the wrong location. Change second line to ' * @license'", - "copyrightLineError": "Copyright line is incorrect or in the wrong location. Change second line to ' * Copyright (c) ${0} ${1} and/or its affiliates.' ${0} must be in ('2020', '2020,'). ${1} must be in ('Oracle', 'Oracle Corp', 'Oracle Corp.', 'Oracle Corporation').", + "copyrightLineError": "Copyright line is incorrect or in the wrong location. Change second line to ' * Copyright (c) 2021 ${0} ${1} and/or its affiliates.' ${0} must be in ('2020', '2020,', '2021', '2021,'). ${1} must be in ('Oracle', 'Oracle Corp', 'Oracle Corp.', 'Oracle Corporation').", "uplLineError": "Universal Permissive License (UPL) line is incorrect or in the wrong location. Change fourth line to ' * The Universal Permissive License (UPL), Version 1.0'", "ignoreTagError": "@ignore tag missing or in the wrong location. Change fifth line to ' * @ignore'", "endLineError": "Last line of .js file is not */, or is in the wrong location. Change sixth line to '*/'" @@ -75,44 +83,49 @@ module.exports = { create(context) { const config = Object.assign({}, context.options[0]); const sourceCode = context.getSourceCode(); + const levenshtein = require('./js-levenshtein'); + const os = require('os'); + console.log(`platform=${os.platform()}`); + const eolChars = (os.platform() === "win32" ? "\r\n" : "\n"); + console.log(`eolChars=${eolChars}`); function computeFixRanges(text) { let ranges = [], solIndex, eolIndex = -1; solIndex = text.indexOf('/**'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "startLine", text: "/**\n", solIndex: solIndex, eolIndex: eolIndex} + {key: "startLine", text: `/**${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); solIndex = text.indexOf(' * @license'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "licenseTag", text: " * @license\n", solIndex: solIndex, eolIndex: eolIndex} + {key: "licenseTag", text: ` * @license${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); - solIndex = text.indexOf(' * Copyright (c) 2020 Oracle and/or its affiliates.'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + solIndex = text.indexOf(' * Copyright (c) 2020, 2021 Oracle and/or its affiliates.'); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "copyrightLine", text: " * Copyright (c) 2020 Oracle and/or its affiliates.\n", solIndex: solIndex, eolIndex: eolIndex} + {key: "copyrightLine", text: ` * Copyright (c) 2020, 2021 Oracle and/or its affiliates.${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); solIndex = text.indexOf(' * The Universal Permissive License (UPL), Version 1.0'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "uplLine", text: " * The Universal Permissive License (UPL), Version 1.0\n", solIndex: solIndex, eolIndex: eolIndex} + {key: "uplLine", text: ` * The Universal Permissive License (UPL), Version 1.0${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); solIndex = text.indexOf(' * @ignore'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "ignoreTag", text: " * @ignore\n", solIndex: solIndex, eolIndex: eolIndex} + {key: "ignoreTag", text: ` * @ignore${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); solIndex = text.indexOf(' */'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "endLine", text: " */\n", solIndex: solIndex, eolIndex: eolIndex} + {key: "endLine", text: ` */${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); return ranges; @@ -122,48 +135,48 @@ module.exports = { let ranges = [], solIndex, eolIndex = -1; solIndex = text.indexOf('/**'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "startLine", text: `${text.substring(solIndex, eolIndex)}\n`, solIndex: solIndex, eolIndex: eolIndex} + {key: "startLine", text: `${text.substring(solIndex, eolIndex)}${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); solIndex = text.indexOf(' * @license'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "licenseTag", text: `${text.substring(solIndex, eolIndex)}\n`, solIndex: solIndex, eolIndex: eolIndex} + {key: "licenseTag", text: `${text.substring(solIndex, eolIndex)}${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); solIndex = text.indexOf(' * Copyright'); if (solIndex !== -1 ) { - eolIndex = text.indexOf('\n', solIndex); + eolIndex = text.indexOf(eolChars, solIndex); if (eolIndex !== -1) { ranges.push( - {key: "copyrightLine", text: `${text.substring(solIndex, eolIndex)}\n`, solIndex: solIndex, eolIndex: eolIndex} + {key: "copyrightLine", text: `${text.substring(solIndex, eolIndex)}${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); } } else { ranges.push( - {key: "copyrightLine", text: " * Copyright (c) 2020 Oracle and/or its affiliates.\n", solIndex: -1, eolIndex: -1} + {key: "copyrightLine", text: ` * Copyright (c) 2020, 2021 Oracle and/or its affiliates.${eolChars}`, solIndex: -1, eolIndex: -1} ); } solIndex = text.indexOf(' * The Universal Permissive License (UPL), Version 1.0'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "uplLine", text: `${text.substring(solIndex, eolIndex)}\n`, solIndex: solIndex, eolIndex: eolIndex} + {key: "uplLine", text: `${text.substring(solIndex, eolIndex)}${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); solIndex = text.indexOf(' * @ignore'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "ignoreTag", text: `${text.substring(solIndex, eolIndex)}\n`, solIndex: solIndex, eolIndex: eolIndex} + {key: "ignoreTag", text: `${text.substring(solIndex, eolIndex)}${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); solIndex = text.indexOf(' */'); - if (solIndex !== -1 ) eolIndex = text.indexOf('\n', solIndex); + if (solIndex !== -1 ) eolIndex = text.indexOf(eolChars, solIndex); ranges.push( - {key: "endLine", text: `${text.substring(solIndex, eolIndex)}\n`, solIndex: solIndex, eolIndex: eolIndex} + {key: "endLine", text: `${text.substring(solIndex, eolIndex)}${eolChars}`, solIndex: solIndex, eolIndex: eolIndex} ); // console.log(`text=${text}\nrange=[0, ${eolIndex}]`); @@ -175,6 +188,11 @@ module.exports = { return regex.test(lineText); } + function isWordInLine(wordKey, lineText) { + const regex = new RegExp(config.regexPatterns[wordKey]); + return regex.test(lineText); + } + function reportError(range, messageId) { context.report({ loc: {start: range.solIndex, end: range.eolIndex}, @@ -195,16 +213,17 @@ module.exports = { messageId: "missingCopyright", data: { fileType: ".js", - }, - fix: fixer => fixer.insertTextBeforeRange([0, 0], config.validCopyright) + } }); } if (isLinePresent(fixRanges[0].key, lineText)) { // Any deviation from config.validCopyright after // the first line, is an error. Deviations are - // determined by a regex test, and consider - // mis-location to be an error. + // determined by a regex pattern testing, where + // any deviation (including not being on the + // correct line) results in an error being + // reported. const eolIndex = sourceCode.getText().indexOf(" */", 0); const actualRanges = computeActualRanges(sourceCode.getText().substring(0, eolIndex + ' */\n'.length)); diff --git a/frontend/jsconfig.json b/frontend/jsconfig.json index 4d069334..8238f958 100644 --- a/frontend/jsconfig.json +++ b/frontend/jsconfig.json @@ -2,14 +2,24 @@ "compileOnSave": true, "compilerOptions": { "rootDirs": [ - "src", - "tests/src" + "src" ], "outDir": "dist" }, "paths": { - "ojs/*":["./node_modules/@oracle/oraclejet/dist/types/*"], - "knockout": ["./node_modules/knockout"], - "dotenv": ["./node_modules/dotenv/types/*"] - } -} + "ojs/*": [ + "./node_modules/@oracle/oraclejet/dist/types/*" + ], + "knockout": [ + "./node_modules/knockout" + ], + "dotenv": [ + "./node_modules/dotenv/types/*" + ] + }, + "exclude": [ + "web", + "node_modules", + "**/node_modules/*" + ] +} \ No newline at end of file diff --git a/frontend/package.json b/frontend/package.json index 468e730d..24338198 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -15,10 +15,11 @@ "@types/node": "^12.11.7", "@types/sinon": "^9.0.0", "chai": "^4.2.0", - "chromedriver": "^85.0.0", + "chromedriver": "^85.0.1", "dotenv": "^8.2.0", "eslint": "^7.9.0", - "geckodriver": "^1.20.0", + "fixture": "^0.1.2", + "geckodriver": "^1.22.3", "jquery-ui": "^1.12.1", "js-yaml": "^3.13.1", "karma": "^4.3.0", @@ -43,7 +44,7 @@ "node": ">=0.10.0" }, "scripts": { - "test": "npx karma start test/karma.conf.js" + "test": "npx karma start unit-tests/karma.conf.js" }, "private": true } diff --git a/frontend/pom.xml b/frontend/pom.xml index fb324d57..8a2af732 100644 --- a/frontend/pom.xml +++ b/frontend/pom.xml @@ -18,17 +18,10 @@ console-backend-frontend - ./node_modules/mocha/bin/mocha - src/js/unit-tests - src/js/system-tests/index.js ./node_modules/.bin/eslint - src/js/eslint-rules/ - html - eslint-js.html + eslint-rules/ + compact src/js - node - src/js/eslint-rules/html-copyright.jsx - src/js/views @@ -45,7 +38,6 @@ . - staged-themes/** web/** @@ -81,18 +73,12 @@ - diff --git a/frontend/scripts/config/oraclejet-serve.js b/frontend/scripts/config/oraclejet-serve.js index 89569662..bc84a567 100644 --- a/frontend/scripts/config/oraclejet-serve.js +++ b/frontend/scripts/config/oraclejet-serve.js @@ -1,5 +1,5 @@ /** - Copyright (c) 2015, 2020, Oracle and/or its affiliates. + Copyright (c) 2015, 2020, 2021, Oracle and/or its affiliates. Licensed under The Universal Permissive License (UPL), Version 1.0 as shown at https://oss.oracle.com/licenses/upl/ @@ -32,7 +32,7 @@ module.exports = function () { watch: { sourceFiles: { - files: ['src/**','src/js/config/**'], + files: ['src/**'], options: { livereload: true } } }, diff --git a/frontend/src/config/console-frontend-jet.yaml b/frontend/src/config/console-frontend-jet.yaml index 469a0856..c2b19848 100644 --- a/frontend/src/config/console-frontend-jet.yaml +++ b/frontend/src/config/console-frontend-jet.yaml @@ -1,39 +1,50 @@ -# Copyright 2020, 2021, Oracle and/or its affiliates. All rights reserved. -# Licensed under the Universal Permissive License v 1.0 as shown at http://oss.oracle.com/licenses/upl. - -name: "WebLogic Server Remote Console" -version: "" +name: WebLogic Remote Console +version: '1.1.0' console-backend: - name: "Oracle WebLogic Console Backend Microprofile Server" - version: "1.0" - baseUrl: "http://localhost:8012" + name: Oracle WebLogic Console Backend Microprofile Server + version: '1.0' + baseUrl: 'http://localhost:8012' pollingMillis: 60000 + retryAttempts: 5 services: - - id: configuring - path: "/configuration" + - id: configuration + path: /configuration enabled: true components: + data: null + pages: null changeManager: - id: view - uri: "/changeManager" + uri: /changeManager - id: edit - uri: "/changeManager/changes" + uri: /changeManager/changes - id: commit - uri: "/changeManager/activate" + uri: /changeManager/activate - id: discard - uri: "/changeManager/cancelEdit" + uri: /changeManager/cancelEdit - id: monitoring - path: "/monitoring" + path: /monitoring enabled: true components: + data: null + pages: null lifecycle: - id: view - uri: "DomainRuntime/ServerStates" + prefix: /data + uri: /DomainRuntime/ServerStates + - id: information + path: /about + - id: connecting + path: /connection settings: logging: - defaultLevel: "INFO" + defaultLevel: INFO autoSync: minimumSecs: 30 themes: - dark: ["#413e3c", "#624f4f"] - light: ["#dcd6d1", "#b6a29a"] + dark: + - '#413e3c' + - '#624f4f' + light: + - '#dcd6d1' + - '#b6a29a' diff --git a/frontend/src/config/console-preferences.yaml b/frontend/src/config/console-preferences.yaml index 4ce02855..ee6e4398 100644 --- a/frontend/src/config/console-preferences.yaml +++ b/frontend/src/config/console-preferences.yaml @@ -1,7 +1,12 @@ -# Copyright 2020, Oracle Corporation and/or its affiliates. All rights reserved. +# Copyright 2020, 2021, Oracle Corporation and/or its affiliates. All rights reserved. # Licensed under the Universal Permissive License v 1.0 as shown at http://oss.oracle.com/licenses/upl. #startup: # perspective: landing/configuration general: theme: light +notifications: + showPopupForFailureResponses: true + autoCloseInterval: 5000 +logging: + logFailureResponses: true diff --git a/frontend/src/config/perspectives.yaml b/frontend/src/config/perspectives.yaml index 494f08ec..fd0e68dd 100644 --- a/frontend/src/config/perspectives.yaml +++ b/frontend/src/config/perspectives.yaml @@ -1,20 +1,16 @@ -# Copyright 2020, Oracle Corporation and/or its affiliates. All rights reserved. +# Copyright 2020, 2021, Oracle Corporation and/or its affiliates. All rights reserved. # Licensed under the Universal Permissive License v 1.0 as shown at http://oss.oracle.com/licenses/upl. perspectives: - id: configuration - label: Configuration - description: "

Maintain configuration of WebLogic domain you are currently working with.

" type: built-in iconFiles: - light: configuration-icon-navstrip-blk_48x48 - dark: configuration-icon-navstrip-wht_48x48 - greyed: configuration-icon-navstrip-gry_48x48 + light: navstrip-icon-readwrite-configuration-blk_48x48 + dark: navstrip-icon-readwrite-configuration-wht_48x48 + greyed: navstrip-icon-readwrite-configuration-gry_48x48 - id: monitoring - label: Monitoring - description: "

View runtime MBean information for select resources in WebLogic domain you are currently working with.

" type: built-in iconFiles: - light: monitoring-icon-navstrip-blk_48x48 - dark: monitoring-icon-navstrip-wht_48x48 - greyed: monitoring-icon-navstrip-gry_48x48 + light: navstrip-icon-monitoring-blk_48x48 + dark: navstrip-icon-monitoring-wht_48x48 + greyed: navstrip-icon-monitoring-gry_48x48 diff --git a/frontend/src/css/app.css b/frontend/src/css/app.css index 805cf8c2..65205cda 100644 --- a/frontend/src/css/app.css +++ b/frontend/src/css/app.css @@ -10,28 +10,28 @@ --domains-toolbar-right-margin-right: 0; --form-container-calc-max-width: 10px; --form-container-calc-min-width: 310px; - --form-container-calc-max-height: 395px; - --servers-glance-dom-calc-min-height: 448px; + --form-container-calc-max-height: 385px; + --servers-glance-dom-calc-min-height: 460px; + --form-input-min-width: 15em; + --form-input-min-switch-width: 7.25em; + --dialog1-calc-height: 345px; /* * END: CFE code will make adjustments to the - * following custom CSS variables, at runtime. + * above custom CSS variables, at runtime. */ --form-container-fixed-min-width: 1120px; --content-area-header-height: 70px; - --table-container-offset-height: 395px; - --form-container-offset-height: 405px; - --padding-30: 30px; - --padding-40: 40px; - --form-tabstrip-converyor-calc-max-width: 10px; + --form-tabstrip-converyor-calc-max-width: 275px; --form-table-container-min-width: 310px; --instructions-calc-max-width: 335px; --paging-bottom: 32px; - --form-input-min-width: 15em; --form-input-max-width: 15em; + --min-width-35em: 35em; + --min-width-15em: 15em; - --landing-page-cards-min-width: 1040px; + --landing-page-cards-min-width: 1095px; --landing-page-panel-subtree-max-height: 295px; --landing-page-panel-subtree-max-width: 55px; --landing-page-conveyor-calc-max-width: 55px; @@ -40,10 +40,10 @@ --landing-page-subtree-card-color: #70706c; --ancillary-content-area-width: 300px; - --instructions-max-height: 120px; + --instructions-max-height: 160px; --system-status-collapse-min-height: 340px; - --system-status-expand-min-height: 448px; - --servers-glance-dom-max-height: 448px; + --system-status-expand-min-height: 460px; + --servers-glance-dom-max-height: 460px; --table-dom-max-height: 500px; --navstrip-max-width: 45px; /* DON'T CHANGE THIS!! Needs to be 45px, or else left edge of control will be cut off and dnd feature on MyHome will go bonkers */ --navstrip-min-height: 60px; @@ -67,13 +67,14 @@ --slideup-popup-offset-top: 200px; --slideup-box-shadow-color: #dfdad7; + --app-info-label-color: #161513; --fixed-header-background-color: #f6f6f6; --table-gridline-color: #eceaec; --table-background-color: #f7f7f7; --navtree-label-color: #161513; --navtree-background-color: #c3b2ab; --navstrip-background-color: #b6a29a; - --panel-card-width: 215px; + --panel-card-min-width: 195px; --panel-card-label-color: #161513; --detail-popup-background-color: #cae4ef; --sideways-tabstrip-min-width: 24px; @@ -85,21 +86,33 @@ --breadcrumb-link-color: #0275d8; --breadcrumb-hover-color: #01447e; --dialog-background-color: #dbd5d0; + --dialog1-width: 360px; - --dialog1-height: 355px; - --dialog2-width: 330px; - --dialog2-height: 232px; - --dialog3-width: 300px; - --dialog3-height: 168px; - --dialog4-width: 475px; - --dialog4-height: 392px; + --dialog1-fixed-min-height: 345px; + --syncIntervalDialog-width: 330px; + --syncIntervalDialog-min-height: 236px; + --confirmDialog-width: 300px; + --confirmDialog-min-height: 168px; + --actionDialog-width: 475px; + --actionDialog-min-height: 390px; + --input-text-wide-width: 18rem; --single-select-one-wide-width: 630px; - --app-info-container-height: 35px; + --single-select-one-md-width: 250px; + --header-container-height: 34px; + --app-info-container-height: 34px; --scrollbar-thumb-color: #837670; --scrollbar-track-color: #faf8f7; --scrollbar-track-color1: #bba9a1; + + --form-input-integer-max-width: 110px; + + --form-layout-row-height: 2.4em; + --field-highlight-border-color: black; + --field-highlight-border-style: solid; + + --form-section-title-background-color: #dfdcda; /* #ede7e4 #dfdcda; */ } html, body { @@ -117,10 +130,18 @@ footer { padding: 5px; } +#footer-container { + min-height: 26px; +} + body { touch-action: manipulation; } +#header-container { + height: var(--header-container-height); +} + #oracle-jet-icon { height: 16px; width: 16px; @@ -147,6 +168,21 @@ a:focus { min-height: var(--app-info-container-height); } +div#header-title a:hover, +div#header-title a:active, +div#header-title a:focus +{ + text-decoration: none; +} + +#app-name { + color: var(--app-info-label-color); +} + +#app-version { + margin-left: 2px; +} + #navtreeToggle, #app-info-logo, #app-info-title { @@ -157,7 +193,7 @@ a:focus { width: 24px; height: 24px; cursor: pointer; - margin-left: 10px; + margin: 5px 10px 0 10px; } #oracleLogo { @@ -322,6 +358,7 @@ li.oj-navigationlist-focused-element.oj-navigationlist-item-element { #connection-type-image { width: 18px; height: 18px; + margin-left: 3px; } #not-connected-label @@ -340,6 +377,17 @@ li.oj-navigationlist-focused-element.oj-navigationlist-item-element { margin: 8px 5px 0 0; } +div#domain-menu-dropdown { + margin-top: 8px; +} + +div#domain-menu-dropdown a:hover, +div#domain-menu-dropdown a:active, +div#domain-menu-dropdown a:focus +{ + text-decoration: none; +} + #connected-to-variable { margin: 8px 5px 0 5px; @@ -438,10 +486,16 @@ canvas#console-state-bar { max-width: var(--ancillary-content-area-width); } +.tabstrip-tab-icon { + padding: 10px; + height: 24px; + width: 24px; + vertical-align: middle; +} + #ataglance-tab-container, #shoppingcart-tab-container { min-width: var(--ancillary-content-area-width); -/* overflow: auto; */ scrollbar-color: var(--scrollbar-thumb-color) var(--scrollbar-track-color); } @@ -660,20 +714,11 @@ a.oj-tabbar-focused-element.oj-tabbar-item-content.oj-tabbar-item-no-icon { margin: 5px 2px; } -#desktop-container { - min-width: calc(100vw - var(--form-container-calc-min-width)); - height: 720px; - background-image: url('../images/myhome-background_1080x720.png'); - background-repeat: no-repeat; - background-position: left; -} - #form-help-container { display: none; } #table-form-container { -/* min-width: calc(100vw - var(--form-container-calc-min-width)); */ max-width: calc(100vw - var(--form-container-calc-max-width)); overflow: auto; scrollbar-color: var(--scrollbar-thumb-color) var(--scrollbar-track-color); @@ -681,12 +726,6 @@ a.oj-tabbar-focused-element.oj-tabbar-item-content.oj-tabbar-item-no-icon { .cfe-table-form-container { margin: 5px 5px 0 0; - /* - DON'T THINK WE NEED THE SCROLLBARS HERE, BECAUSE THE TABLES - ALREADY HAVE THEM. KEEPING IT AROUND UNTIL ALL THE NEW ELASTIC - STUFF HAS BEEN VERIFIED TO WORK CORRECTLY !!! - */ - /* overflow: auto; */ scrollbar-color: var(--scrollbar-thumb-color) var(--scrollbar-track-color); } @@ -726,13 +765,12 @@ div#formMessages { max-width: calc(100vw - var(--instructions-calc-max-width)); overflow-wrap: break-word; /* Wraps really long instructions */ font-size: 11pt; - margin: 5px 0 10px 10px; + margin: 10px 0 10px 10px; overflow: auto; scrollbar-color: var(--scrollbar-thumb-color) var(--scrollbar-track-color); } .cfe-table-form-content { -/* min-width: calc(100vw - var(--form-container-calc-min-width)); */ min-width: var(--form-container-fixed-min-width); max-width: calc(100vw - var(--form-container-calc-max-width)); /* Any form, table or article wider than var(--content-area-max-width) will have a horizontal scroll bar */ max-height: calc(100vh - var(--form-container-calc-max-height)); @@ -751,10 +789,67 @@ oj-table.wlstable { padding-top: 3px; } -.cfe-form-field { - height: 54px; +#cfe-form > oj-form-layout > div > div:nth-child(+n+0) { + padding-left: 8px; + padding-top: 3px; +} + +#cfe-form > oj-form-layout > div > div:nth-child(+n+1) { + margin-bottom: 0px; +} + +#cfe-form > .oj-form-layout > .oj-form > .oj-flex > .oj-formlayout-nested-formlayout > .oj-form-layout > .oj-form, .oj-form-layout > .oj-form.oj-formlayout-form-across > .oj-flex > .oj-formlayout-no-label-flex-item.oj-formlayout-nested-formlayout.oj-flex-item { + height: 100%; +} + +.cfe-sections-form-layout-title { + width: 99%; + padding: 0 3px 3px 0; + background-color: var(--form-section-title-background-color); } +.cfe-sections-form-layout-title-arrow, +.cfe-sections-form-layout-title-arrow:hover, +.cfe-sections-form-layout-title-arrow:active, +.cfe-sections-form-layout-title-arrow:focus { + text-decoration: none; +} + +.cfe-sections-form-layout-title-arrow, +.cfe-sections-form-layout-title-text { + vertical-align: middle; +} + +.cfe-sections-form-layout-title-arrow { + font-size: 14pt; +} + +.cfe-sections-form-layout-title-text { + font-size: 12pt; +} + +/* Style for highlighting of form fields */ +.cfe-field-highlight +{ + border-color: var(--field-highlight-border-color); + border-style: var(--field-highlight-border-style); + border-width: 2px; + border-radius: 8px; +} + +/* Adjust the margin to allow for a cfe-field-highlight */ +.cfe-form-field > .oj-form-control.oj-component > .oj-text-field-container, +.cfe-form-field > .oj-form-control.oj-component > .oj-switch-container +{ + margin: 1px 1px 0 2px; + min-height: 2.65rem; +} + +.cfe-form-input-integer-sm { + max-width: var(--form-input-integer-max-width); +} + +.cfe-form-input-integer-sm, .cfe-form-input-text, .cfe-form-input-textarea, .cfe-form-input-password, @@ -781,12 +876,24 @@ oj-table.wlstable { .cfe-form-input-text, .cfe-form-input-textarea, .cfe-form-readonly-text, -.cfe-form-input-password, -.cfe-form-switch +.cfe-form-input-password { min-width: var(--form-input-min-width); } +.cfe-form-input-single-column { + min-width: var(--min-width-35em); +} + +.cfe-form-input-two-columns { + min-width: var(--min-width-15em); +} + +.cfe-form-switch +{ + min-width: var(--form-input-min-switch-width); +} + .cfe-form-input-text, .cfe-form-input-textarea, .cfe-form-readonly-text, @@ -858,11 +965,25 @@ oj-input-text.cfe-form-readonly-text > div > div > div.oj-text-field-readonly-di width: var(--single-select-one-wide-width); } +.cfe-form-select-one-md, +.cfe-form-readonly-select-one-md { + width: var(--single-select-one-md-width); +} + .cfe-form-checkboxset { margin-left: 10px; } -.cfe-form-checkboxset .oj-form.oj-enabled .oj-user-assistance-inline-container.oj-efficient, .oj-form-control:not(.oj-read-only):not(.oj-disabled) .oj-user-assistance-inline-container.oj-efficient { +/* Height for the user-assistance area in the form controls */ +.cfe-form-checkboxset.oj-form-control.oj-component > .oj-user-assistance-inline-container.oj-efficient, +.cfe-form-field > .oj-form-control.oj-component:not(.oj-switch) .oj-user-assistance-inline-container.oj-efficient +{ + min-height: 0rem; +} + +/* Height for the user-assistance area for a switch in the form to ensure uniform highlight */ +.cfe-form-field > .oj-form-control.oj-component.oj-switch .oj-user-assistance-inline-container.oj-efficient +{ min-height: .5rem; } @@ -887,7 +1008,7 @@ oj-option#show-advanced-fields { font-size: 11pt; } -.cfe-form-tabstrip > div > oj-conveyor-belt { +.cfe-form-tabstrip { margin: 5px 0 0 5px; max-width: calc(100vw - var(--form-tabstrip-converyor-calc-max-width)); } @@ -914,7 +1035,7 @@ oj-option#show-advanced-fields { } .restart-required-icon { - padding: 8px 6px 0 2px; + padding: 11px 6px 0 2px; width: 18px; } @@ -1053,27 +1174,81 @@ div#oj-combobox-choice-beanpath.oj-combobox-choice { oj-dialog[id="dialog1"] { width: var(--dialog1-width); - height: var(--dialog1-height); + height: var(--dialog1-calc-height); background-color: var(--dialog-background-color); } -oj-dialog#dialog1 > div.oj-dialog-content.oj-dialog-default-content { +oj-dialog[id="dialog1"] div.oj-dialog-content.oj-dialog-default-content { font-size: 11pt; background-color: white; } -oj-dialog#dialog1 div.oj-dialog-header.oj-dialog-header-close { +oj-dialog[id="dialog1"] div.oj-dialog-header.oj-dialog-header-close { padding: 0.5rem .75rem 0.5rem .75rem; } +#connection-dialog { + margin-top: 10px; + font-size: 13pt; +} + +#connection-dialog-instructions, +#connection-dialog-text { + margin-left: 15px; +} + +#connection-dialog-text { + min-height: 30px; +} + +#connection-dialog-body.oj-dialog-body { + padding: 10px 0 0 0; +} + +.connection-dialog-body-container { + margin: 15px; +} + +#connection-dialog-body img#username-icon, +#connection-dialog-body img#password-icon +{ + height: 24px; + width: 24px; + vertical-align: top; + padding: 0 15px 0 0; +} + +#url-field-label { + font-size: 10pt; + margin-right: 10px; +} + +oj-input-text#url-field .oj-user-assistance-inline-container.oj-efficient, .oj-form-control:not(.oj-read-only):not(.oj-disabled) .oj-user-assistance-inline-container.oj-efficient { + min-height: 5px; +} + +#connection-dialog-body oj-input-text#username-field, +#connection-dialog-body oj-input-password#password-field, +#connection-dialog-body oj-input-text#url-field +{ + font-size: 11pt; + width: 272px; +} + +#connection-dialog-button-image, +#connection-dialog-button-label { + vertical-align: middle; + padding: 0 5px 0 0; +} + html:not([dir="rtl"]) .oj-dialog-header-close-wrapper { margin-right: -1rem; /* to properly position "X" in header, which closes the */ } oj-dialog[id="syncIntervalDialog"] { display: none; - width: var(--dialog2-width); - height: var(--dialog2-height); + width: var(--syncIntervalDialog-width); + min-height: var(--syncIntervalDialog-min-height); background-color: var(--dialog-background-color); } @@ -1128,65 +1303,20 @@ oj-dialog#syncIntervalDialog div.oj-dialog-body oj-form-layout } oj-dialog[id="confirmDialog"] { - width: var(--dialog3-width); - height: var(--dialog3-height); + width: var(--confirmDialog-width); + min-height: var(--confirmDialog-min-height); + margin-bottom: 5px; background-color: var(--dialog-background-color); } oj-dialog[id="actionsDialog"] { - width: var(--dialog4-width); - height: var(--dialog4-height); + width: var(--actionDialog-width); + min-height: var(--actionDialog-min-height); background-color: var(--dialog-background-color); border: 1px none #f8f6f5; } -#connection-dialog { - margin-top: 10px; - font-size: 13pt; -} - -#connection-dialog-instructions, -#connection-dialog-text { - margin-left: 15px; -} - -#connection-dialog-body.oj-dialog-body { - padding: 10px 0 0 0; -} - -.connection-dialog-body-container { - margin: 15px; -} - -#connection-dialog-body img#username-icon, -#connection-dialog-body img#password-icon -{ - height: 24px; - width: 24px; - vertical-align: middle; - padding: 0 15px 0 0; -} - -#url-field-label { - font-size: 10pt; - margin-right: 10px; -} - -#connection-dialog-body oj-input-text#username-field, -#connection-dialog-body oj-input-password#password-field, -#connection-dialog-body oj-input-text#url-field -{ - font-size: 11pt; - width: 272px; -} - -#connection-dialog-button-image, -#connection-dialog-button-label { - vertical-align: middle; - padding: 0 5px 0 0; -} - .cfe-draggable { height: 60px; width: 60px; @@ -1272,6 +1402,7 @@ div#tab-module.oj-flex-bar-end { text-decoration: none; } +.site-sideways-tabstrip span img, .site-sideways-tabstrip span a img { margin-top: 3px; width: 18px; @@ -1279,6 +1410,7 @@ div#tab-module.oj-flex-bar-end { vertical-align: middle; } +.site-sideways-tabstrip span span, .site-sideways-tabstrip span a span { padding: 0 2px 8px 0; margin-bottom: 3px; @@ -1309,24 +1441,29 @@ div#tab-module.oj-flex-bar-end { } .landing-page-panel { + margin: 5px 0 5px 5px; + min-width: var(--panel-card-min-width); +} + +.landing-page-card { padding: 5px; border: 0; outline: none; display: block; font-size: 11pt; font-weight: 500; - width: var(--panel-card-width); + min-width: var(--panel-card-min-width); color: var(--panel-card-label-color); } -.landing-page-panel, -.landing-page-panel:hover, -.landing-page-panel:active, -.landing-page-panel:focus { +.landing-page-card, +.landing-page-card:hover, +.landing-page-card:active, +.landing-page-card:focus { text-decoration: none; } -.landing-page-panel:hover { +.landing-page-card:hover { background: var(--landing-page-hover-color); } @@ -1436,16 +1573,6 @@ for "slices". The workaround is to control it here. margin-right: .875rem; /* Set size of margin between tabbar items */ } -/* -Don't delete. We will need it to write code that changes background of -advanced fields, when/if that JIRA gets created/assigned to CFE team. - -#wlsform > div > div:nth-child(+n+4) { - padding-top: 3px; - background-color: #ebebeb; -} -*/ - /* Used to control layout for form labels */ .oj-formlayout-labels-inline > .oj-flex > .oj-flex-item:nth-child(odd) > .oj-label .oj-label-group { overflow: inherit; @@ -1460,7 +1587,7 @@ advanced fields, when/if that JIRA gets created/assigned to CFE team. text-align: left; font-size: 11pt; line-height: 1em; - height: 2.3em; /* Controls height of rows */ + height: var(--form-layout-row-height); /* Controls height of rows */ } html:not([dir="rtl"]) .oj-navigationlist-collapsible ul.oj-navigationlist-has-icons > .oj-navigationlist-item-element > ul, html:not([dir="rtl"]) .oj-navigationlist-expanded:not(.oj-navigationlist-icon-only).oj-navigationlist-vertical ul.oj-navigationlist-has-icons > .oj-navigationlist-item-element > ul { @@ -1677,4 +1804,4 @@ the text characters limited to the text box width along with scrolling. #slideup-toggle img { height: 24px; width: 24px; -} +} \ No newline at end of file diff --git a/frontend/src/css/fonts/2010.1.0/OracleFont/OracleSans_Web/WOFF/OracleSans_W_BdIt.woff b/frontend/src/css/fonts/2010.1.0/OracleFont/OracleSans_Web/WOFF/OracleSans_W_BdIt.woff new file mode 100644 index 0000000000000000000000000000000000000000..262acd99a2c25e0ce00a918a42e34abc1ec7008d GIT binary patch literal 55256 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¬2^4 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 FO#sfaI)(rM literal 0 HcmV?d00001 diff --git a/frontend/src/images/close-icon-wht_24x24.png b/frontend/src/images/close-icon-wht_24x24.png new file mode 100644 index 0000000000000000000000000000000000000000..7b8c6b46e201a969f493a85d599b64a7a20a7493 GIT binary patch literal 156 zcmeAS@N?(olHy`uVBq!ia0vp^5+KaM1|%Pp+x`Gj$(}BbAs)xyPC3YXK!Jxju>8ZZ zc^Z?R7ylPss?c%8{T;WZvPZ^RjY|rdp8syCpH$f^qi~WzMsWR6!9<2&c1f-(#l>6S zPDuVV@57EilAE;l*InGSGJMLf6DxCP*=4+pcMbF@W=^-C`f-=BVgb-P22WQ%mvv4F FO#sfaI)(rM literal 0 HcmV?d00001 diff --git a/frontend/src/images/monitoring-icon-navstrip-blk_48x48.png b/frontend/src/images/monitoring-icon-navstrip-blk_48x48.png deleted file mode 100644 index 7b7181305560dfda53454c2c0fc1b02861feda4f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4125 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 B>xKXT diff --git a/frontend/src/images/monitoring-icon-navstrip-gry_48x48.png b/frontend/src/images/monitoring-icon-navstrip-gry_48x48.png deleted file mode 100644 index 98e1d858874230c5d284d746be5242bae6d584fb..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 10140 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 diff --git a/frontend/src/images/more-vertical-blk-8x24.png b/frontend/src/images/more-vertical-blk-8x24.png index 38b9f0ad45ecf85d6346f475ccaa4073b8f46946..18efabffb9e0886d2471fa91cbb2c310516494b0 100644 GIT binary patch delta 2210 zcmV;T2wnH#1dbArBYy_0dQ@0+Qek%>aB^>EX>4U6ba`-PAZ2)IW&i+q+ND=fmfR=| z{O1&V1Oy1daRh?*_6B?WEn#GF=9u-4p3OQBJqza{WJU%e6Q8xP<#XUm`u1ieK;7YKFwdIEUocrnT2j3V#8C<~3 z{l<31Cz>zVJb&7s9N|05x+#C5oB34+;e#dmN(Ob^{rQc(`fN{scz;0rHQk5P4<1Q* z8cr`BZGPH_A8Ga9-q!YB*Xp!XEV|OO?!vi z7dm$Pu{RNa7L7185hf$N^4l|fXV9_He_Q^DBmd5!yGXd;or& zuY$aZ&7hDE%nb|FIIbxM(+_RsLv+SCMtj8=iCypeLGI^Z3lGd6L$`jI8U1m~Is+#obTRw)eqNNLcJa^}L! zm4zF3)|zVxh_G6vdb(A~QiP?7NRuwwax0BnZPHrnO?&DY*_b=RvA5p4Dr_od)*2M! z6+I)3Jj&ovhm1D*&GI`c1v&}x$l4V02TYojNX5Dnrf|OQS99CVj+UiR;w6^mu zn|Ix^+wNPRtkE5|@8=(|MmKBeFy-Uq$r^e^t~MOKU=rsHjHNB-#>=KhGcP|GiQOW$QKICX!?+~F-O{=nN8teJ1y z^M5dQMWJIFGolaASJTwgcTo+Go4;*;I?-w}$+Y^)hmJWSubEe!6??nHF`Di?kaGn= zh_wc(wl_+K)sQpt!X-wKSG-+G8@AMXPru4u33+*XKKAFjmA$pd8pgCWOogLm;K)3{ zXxf!F$meQ{M2Hvm|A*~b{beN1p;7kSO@H<(HT3M=O<{3gD?|Me-`cDL8RJKM$U;WJdlLurHFMaQ0756LIr~;jAzcN|heuRDc4{5K*iP zGFXIcp?2ucn<@wv8%G4#Ay>~1vNW~>IJWfHmW(%I_^2!*_3Yp!)>1gHluWdkv{8|X zy4mV1z}QepE-q~j6h;sQye*DvbX*OqKgvBG?Zeb1!A!STunK8@;6EGcW`8Sd?H}yb zolwDb$Rbq3?$Au95N25|jn;n~AdwosNiDo<53BPyLQ+crQfz^y1@9mE=@?;D?5Ah$ zff3s_K5C#>X6eHYgvbTz#MP|82s(i#u&mhD$X?QQ;wNwY@TQmC!cX+~$1NsO=n!_> z7$_kjoLENA4Z!KFSVW^W8h>_G*#o*b0@PS}dA*#Wm&RVz?*Kd?U1T!sNok_lN8Zun z<-$WuhsWvUE{XVVMD50v5|l7{r$=5sJL{0oHhB zVsXgHGhOH|WIT?0**L0gN$M4AD5g*l_||~*?dh{nzH-rwm!|!5vY{@4Qy2tPiwLrZ zpy-gP*f&QQ8+j7cOn+p4u>|VwAUNQ1^fIy^A*@-ko6ub91(+!6Y#09WWV=#8UV`!@ z>65ouhksQ4VM!AHzNSIU;=?-p52gw=D{HxK+W-IoglR)VP)S2WAaHVTW@&6?004NL zeUUv#!$2IxUq3|AiijOV95Pg0EJzh`)G8FALZ}s5buhW~3j&%nkzW>n=H{g6A|?JW zDYS_3;J6>}?mh0_0seZKsb+8jP&La)CE`LRyDD_PB8YzUU<@&dnfjb4CgC~0?&0I> zU6f~epZjz4Dmjw@K7n|a>4rtTK|H-_>74h8!>lMN#OK8023?T&k?XR{Z=4Gb`*~*A zNT=qB!^A?Njpa6GMMEWjo+6GYsz&+#jLQn=EzWAW%9{7&FAU|hm1VBe97Y0*Sb_)v zGO8${3=2_OHBwBZXg}`ZA9DO6xny#cz{s(H3RFmrAN&t~cWdS+V{TF?4s^WO_Qwd& zxeGLEw*7r<+l><-@C;mOEq|pB%zTnwYiW@qpl=(vxNd3k9&oun0}MXtk|8-#fTlm6 z2j0)w3au97#v!67hOpzL*zcXze-_V1Zye?OYLa<^5d@0gRY z0Wb>X1Q84;2|as74wLEuC_^quL_t(2&tqVqFDNM~`Cn2}@*i1@5m^#hqNk^ak%57M kfr(-(7)HH0>P=Dr027iZPN1TjEdT%j07*qoM6N<$fV!Z delta 506 zcmVEX>4Tx04R}tkv&MmKpe$i(@I5J9PA*{ zAwzYtAS&XhRVYG*P%E_RU~=gfG%+M8E{=k0!NHHks)LKOt`4q(Aou~|}?mh0_0YbCJG%GX)Xu54?(j znaj=*$B4yp7b{)NDyBv}Nt{qMo$`ge$13M7&RVU`+V|uyj1=|dC9czqBaH9sfoXnEoWa(a{n|K>s#yaoy3BJ>YT&7<@8hQ+A~wO`%i* z-p}Zp3c$cE(6{RK*51eI1CXPxGB?1%Auv*=>@}Zv_YijX_V1Z?e?Rkaa&(9csLPXS z2rvrd1QP`-1cCcj9+RU8C{H>`L_t(2&tqVqJNOU9aKMNri6O^Ct`+RG@c}13Np|{s w6Rw#Ni?J+F_HUBC$$`a0I1m^ZZ_*0@0M_^rF-Zbo8UO$Q07*qoM6N<$g8v8TivR!s diff --git a/frontend/src/images/navstrip-icon-monitoring-blk_48x48.png b/frontend/src/images/navstrip-icon-monitoring-blk_48x48.png new file mode 100644 index 0000000000000000000000000000000000000000..bc3d36f431c99ea475dbadfe60f8b3d20712b7da GIT binary patch literal 2289 zcmV%{DO@6zPhvMiWHPxH3Y}s^FmVLm5DZH#0EKy!USZ*cn1mVGuOh z_$Bv`$((oZ_nmw0Ip<#B9sd8}22co~8~}a6D39B?-z4G=tJQi?r_((IFbqH*M}Qo+ zc?jSj07tTmkm+VE2*UiHo}N7b@-s3r-WNrYvD@u1o6UW*XV31p*=$r01jJ%73=9mQ zv$KVzE4yBq`19c59a} zUyj_|++L&6Sf#3JRU{Irvs$gP)oMjF8byD9KOQ}L#F)+IpF|>&HIgK)ynFX<`h^P@ zaP#KPn8{>%BFpk;p-|{BfT7nRV8Cj%T9zzXLJJEE{SJqtlIQtzgpjjEMMc8^pwVcw zilRh49uMm3>QYoyjRC;5YuEI$EU$d@=+Vmd_V(2c4GkH!wY9|W_Xhxc450KyBBqUe zc6K)1x^=5kQBl!YU0pr@>eZ{3XFNuT&g1b=0F)4-8~cBKeZ8f!vU2|E)2AD^Y}uk@ zWMohP102Wgb~>H$k550p@M<}+TGoa<;$0=9*@UsG#b|}UAnYAPB>-f&YjGn zMT=tV)~!<*hCxnF4j6{HLI{DPC}?PCa0LQ^MJ|`C+2L?}4x(8zBz>l+rI%RlTSv z%7-UUo+NpBdAND=<`q>{3tcW30N|^yzVcL6Rh9Vt{=X)^%gf7a7e#ShadB~z$K#=r zB$@j9`hMedI<@1Gqe+Zr0I2{VisE*iPNx(U6wpJ54n3}}uAV=3LcLyph39#?XV0F; zCr+IBpsubi<ieaW2|v{div2|F!=tNGiNe%I^E$pbLQ-dMx)y_ z8VxpW+7tx|`WK@;IGN zhtKD0e^CgHjq$N#HvpK;=8NHQ_&uA=hODftUZc@?uBfOeknrS&4I3INDk_Rumc2M* z#*Cp`w{DU0@^Z1PtZa)UNyhc-*GChJ$g-@cs`@k>4%3p75=}`-$=aHlnqOySWo55k zy*gkvn`>+~TfZoZ2#3S(`Tc%jqC-4kiX9vr{0o4KZnqm&tF?+!dKLiAojaGgZ{NOc zR;zVZetv!rfPhA$`ChNruWD{?CcVAAi;o>Uww-0!zss_$jGgz$kt2$tD1`u!pP&CY zevbZau~=3)ozBfIEiDLzLP^E{L?{O!@7S@U=luEe#p4+|ozCCSoH=uB>+mrl#FT7~ zE-fwn<;IO0{qb+hli7iBq1Wrz4i67Q5QKrQuCA*SnD;OY<7XHqLseA(&;a-|r8Gte z`GQjVj7wWvTeXx@PE}RO<#H*ZP^jK&wLSrm9zXO`6EJJmEOd2sVfO6VG&3`k0{AI_ zd2x@^GgVlTvk>FolXZq5K09>_(WAzQAMmQWsFc<`-GzK6B0C(=(L4JPz*dFK!!!SpAp5HexFaQAHc^(|c z9b;Km8l71dFJ3&7Vk40V9z1w}?(S~*{eCElGCcwmMFFK0w{PFJGYs=>X=!PUkRPH$ ztNo$cn@lF;JN9Ioxe3wN*LR9ix~8hCO5fexy?_t`N@>E|NSuX&f`ZJs zbLTb#_}1t1g`7_3=kZ<&03@H!Hv|Cp@89?I^z{7p`t|EM2`4;#`ZUo`K~+^WH#dV2 z0<+nSKp-$R0nupmQvfTyUa!XM^}f(95D3@}2E(UKO-+TeEdQ&cqoZFCg#N6oEZWu8 z#p`rByDZD=8yg!xtf{HVId$sP2+6_0!4ap73dNXSuRo9wK*s5XCc5mn0h|ROj%Q>t znXqixGAvxUFlw{eIsx=+wc7nAlSxq&WmhN^%4}GazQtmBEC|9g7ba#JJku+R z;&(jH2NLP?6(AtX@@J{3scnC6h+!o4y0&4JJ%p)`-3>=f_X*i00000 LNkvXXu0mjfraxg~ literal 0 HcmV?d00001 diff --git a/frontend/src/images/navstrip-icon-monitoring-gry_48x48.png b/frontend/src/images/navstrip-icon-monitoring-gry_48x48.png new file mode 100644 index 0000000000000000000000000000000000000000..144c6cee3fdb33c0caf27ba34d77797f689eed3c GIT binary patch literal 475 zcmV<10VMv3P)ePEx8h3k_1A8a#yrwF2^Ll7ku?gjpro6G03M@EtNnC zrfey`71a0dZ?~sXqA~mw7Xe9r(wYy$@KuUA8}r!n@#BPi1cdCBs>q}@4~^Bt=QWe} zR=>3%_iR~~XJ_q42tz`5$8AzM=QvfkN~zD;n7kUOA@BRs}dS-{UyGLG=PjsTl9h-G2$Q(mN7L5w{c{ z)QiQR?*k-P2}~&#Sin?$L|_NN#uik8urLL6Kxiz9x#bj(yOOH#u%6e+I&lfXk{3PF zs{}@OzB=)hz?Hy%O#u3-9qao*Vt`T_KP%zf#>daN>dim8k4%E{3-2-r`vFasAhojP RL&X39002ovPDHLkV1m)M*LDB^ literal 0 HcmV?d00001 diff --git a/frontend/src/images/navstrip-icon-monitoring-wht_48x48.png b/frontend/src/images/navstrip-icon-monitoring-wht_48x48.png new file mode 100644 index 0000000000000000000000000000000000000000..b44be604de7701a0f5c84b5fb317b33d7fe177de GIT binary patch literal 742 zcmV7E09(o$8j7a5D4Mf z5%2>Y1sO;ixEmafE)@b^fP!X}#1_U0URBkvxm-?z5PlZ~VeQs?3~o3arfu84na}4p zl}hD4it~XD{vfg}Te_|nP1C$W>3Yre`~53LQHpM##9&b3r7w!2Wf;aa3aER0Fc`dS zwOVf{lgTR_vXO(AW!aJ>>Dp@!1?uqIG)>u!r`c>;fmg!85HA~D*NY?>L;+M3rHGn` zBsKeRs28u=yGQy!Wf>=Peq-%+`)5#}olfWZ z-)i>87Z)!0W7|X1G!8|;FNT+nq9|zq09dcr|JXs&r4F)vqUyG&n9QkflQ?H@yWQ^H zW1$J4GH9A+0(XUayHNh9smFU literal 0 HcmV?d00001 diff --git a/frontend/src/images/navstrip-icon-readonly-configuration-blk_48x48.png b/frontend/src/images/navstrip-icon-readonly-configuration-blk_48x48.png new file mode 100644 index 0000000000000000000000000000000000000000..d536599839aef43e04563295796af33b9094b150 GIT binary patch literal 1017 zcmVHIR4?s`V!KNp{YWF2K&g#bGh8ld_Mnh zetwSY>ucQH+@M@8Ll6Ww91e)02%pb~Y&Ofj)T(T3Y*08HCZo|v0EjV0j4=XGX|KPT z&1M=I8KKS1P5K&P{Y~yIX@kK)f*=sj^Ri+XV>CE8NU2n+VIiclRS*h=B!mHw%jKe# zl@(b+i;IiobUGzsc%G;6@p1Yz@@}_VLf+%?s9wp{)m3V1Ym>~;-``JvgnTFzA}t5L zudh!M4X@WrA4cBm^-9S5{eI1%&tx)Wx7#H?)kdNw*|!J=gA#j=<0u}FH*^3eCMIMT zPEAx*lUH)m+1dGCX;60lXf#R<3s_!WR@`2rqoa!Bwzjs&@As3mr+;e_;C8!f z9`N<`b=h&TSWLDOE7gbj`FTYjjIpY%%GI+m3x$GGB?{GP^limdTX2q!j(+Xz>`*S3`>7?31_A+k zmpX8EcJ`Oc<&rqCSS*xIryHsT3kwUf;AXz~0^-*=)ADLaYYA(`!|;+wF96 za7Z7lb&7X*O5I`V9sHT3T8liXytYy3o_pgJd#Ux6cm~@D_)MhyRpHCCk&(6HF!( z1VJdrNklQ!~|*+8=Ke!V|&qu=mYct8e){FAY{WL!5ac3ng}KS0PzlzUiSg| z60K>1jaN0rYEv($z*0?=>5WZWnPqo&hlKNQXd z0RV8P14gp%^?0CED!niypmTZIbA5Dl)I+lG?(XJD_HZ~%JnM6Fb3GeMTT$K^5}*Z} z%|^6WDwPP_Gl)IIOI!5F_gI`JSrW2}o}%rxKvmnF@shaeZ}l z6n8lSy>iXmr`9e7@&?zdy@jRN#0XBuPTl!yL^ll*weU=x`9% zzMY)F`ue)6FG-T{gRwEpfsb0L$kj?fy(JGC3AQpAHU8`S@~lL=`*% z7^7G$qN~db@9*!&o=i{cs)Y{5u)MrXopt5{{um#Ak;z@X6Mi(CO~=K>1=#I&aJgJ( zkw`@BbrkhvqHhAOLyfH28sgxV!xCT#umo5FECH5)|5E_V(YT+ZxbUy$`+flpDq+2E q0yKzGr+LtzK|4A||Cg|EQ}_uF#yT2W-Nd5+0000qUt=%(3VU-=BsmD3 zQy>Z5Jw0vtlhEI>r>pw=s;jDN05mi-G88FGgNAlGSPzM+hc)m4ZLY*Coln!t*@!n+R*fJIJyu zda6di+DqOVz57522|9%7Fu+b$0PovJ|BR^hn0AI?JcfB6^7*`UGl>8qVzC%=eZ5{k zu-5nc{U6qPG#ZsY6IH-wvth2cS}kUzQ>oMs&YK`?1k75K%}?1kBFHwA$^61-r8i-t zOb8*O8WDA($z<|(yWOUe$>jIdYV}{GjY=yP?OiMuKY0;yUH7PmtWYSZ-Ei1+==b~h zlcXSZX0urpRR92h>$=Rtvf1o!Oaa5;kfNs0TR4ux6k!;~BL;cj_bGY}d_=d~<)%}; zUKjeRR4QEC>2x{`Y$~e599s7X)9X+DkP$*isZ=`3hi%(x6D?*Z0RZUrdNiF**JOW` z27`gpnW!lw!gxG>+U<6?hrB_uYGvf&@Q<9_0REO$8clcY zJcTZqd9e}CABSE%Grcbb;Q#e$o*7aAo^~X-2)s3y-wJR-ky`8IQ6LNcRsXK*!1+Bt zPVnaZs4t*SwUe?E!{8$Xpzvq`I6P7y1Rf>e1+N(bq43@U;qaaUDeztbVFim2NQK`O zNQcij)VuF+C2;g17YNdIncOV+g+@EVGoIV&9B=>t002ovPDHLkV1l<7e4zjU literal 0 HcmV?d00001 diff --git a/frontend/src/images/navstrip-icon-readwrite-configuration-gry_48x48.png b/frontend/src/images/navstrip-icon-readwrite-configuration-gry_48x48.png new file mode 100644 index 0000000000000000000000000000000000000000..23578e2f6a04a3a46a586176e1f87df783e69e10 GIT binary patch literal 335 zcmV-V0kHmwP)bz7! zJiwQhy^@mF{TH=JOV>$OzzV*$ebqd$zxRg*d`)>(f#tb;*xNEZ6Su;fOd&QrRDb~w z6JWtZ1hn8yb|E&rs(=N&nt&C&iU4!LstZ`d-xBZuPk*ULJmF5P-bcXGMgRp*5kSJj z1<>$K0;Thx0UtsLbC10a5nzKi3s`}=NMu7`2n+$D0P<^^W_vTDQf7!(;OZY7o+N6L hrFfe<-ZK4&T%2DRyc&H{X3PKp002ovPDHLkV1nwtjEMjM literal 0 HcmV?d00001 diff --git a/frontend/src/images/navstrip-icon-readwrite-configuration-wht_48x48.png b/frontend/src/images/navstrip-icon-readwrite-configuration-wht_48x48.png new file mode 100644 index 0000000000000000000000000000000000000000..94f27623c0b998bba6ab9c9b7a07c7278bb371bd GIT binary patch literal 325 zcmV-L0lNN)P)fOkLCBX+pWtM?J`ZXun literal 0 HcmV?d00001 diff --git a/frontend/src/images/navtree-icon2-blk_24x24.png b/frontend/src/images/navtree-icon2-blk_24x24.png new file mode 100644 index 0000000000000000000000000000000000000000..4b9c43ab34c96d450e9e22955aa0d9c5f216cd59 GIT binary patch literal 202 zcmV;*05$)KP)|^i+KP$_0lWF+MlhSDS@cLg9ezKKwDspsQ@4%w9mVX ziBL+RUd^&kwAK)jUwpJ-t#vvWcc7F4Gv9OIoWqD@X8wwUma9&zwa7VB*FnqKyEr)D zOAeko+3J=n-HbZ%-Xo@~07*qoM6N<$ Ef+_h`J^%m! literal 0 HcmV?d00001 diff --git a/frontend/src/images/navtree-icon2-wht_24x24.png b/frontend/src/images/navtree-icon2-wht_24x24.png new file mode 100644 index 0000000000000000000000000000000000000000..e11b324a382b72bc6fb5cc132f0bea3737d7eb0f GIT binary patch literal 259 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 JPDHLkV1hz?WElVe delta 2214 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 literal 0 HcmV?d00001 diff --git a/frontend/src/images/overlay-pin-icon-blk_24x24.png b/frontend/src/images/overlay-pin-icon-blk_24x24.png new file mode 100644 index 0000000000000000000000000000000000000000..49c3b6c53be853bbe87c5ec07ebe164c6797d27b GIT binary patch literal 160 zcmeAS@N?(olHy`uVBq!ia0vp^5+KaM1|%Pp+x`Gj>7Fi*As)xyPI2U7P~>5L`^fZv zeTLkFIM=YXw_{qKg-z(}yc864oy&pwLfP{-`g`Vk`dRjC_39kt`Zo1Q$cLGpp$>=p z-?Q{KIZ@c literal 0 HcmV?d00001 diff --git a/frontend/src/images/overlay-reattach-icon-blk_24x24.png b/frontend/src/images/overlay-reattach-icon-blk_24x24.png new file mode 100644 index 0000000000000000000000000000000000000000..ba3007728f7c0dcb0c61956a5bb8380c628d19e1 GIT binary patch literal 297 zcmV+^0oMMBP)dH~H0-jWMt6*4$EdjW5vI6376xqzPFb!kCsstv7Bs6Pb43w(d_ zl0U$yBh+;ryXw|jw$}2;a3bQmt`{I<42NOJN~uNt`tI%kKnM{$=Hoan;CY@SNfKzS zgO>)z7*5mF>qK*S-}k}u`odtECIEm^$_dk2d%>M8n!$ptoe#r+q9``un+AJong&^x zp{gnXVAnmZ)V3`HSiOX25fR^^t5KFEe{A5R%h92{d?C@BZTamJ{D*-vXi`c@Df#OL vQ51oQAcXLO#Buy`%^7Q-pzZxxr*?G%1vYf#mukFf00000NkvXXu0mjf4;+DS literal 0 HcmV?d00001 diff --git a/frontend/src/images/search-icon-blk_24x24.png b/frontend/src/images/search-icon-blk_24x24.png index a3e8b0b6037279a6a28fa9dc94e043272cba385e..a88663853ade94e44d603cec762dc13edd85079d 100644 GIT binary patch delta 346 zcmV-g0j2)V1@!`uB!4_fL_t(Y$JLavN<%>qMbE|ZxB!lTeUU7I zQ=MI}iN6BwLQ^X500Us6{gad=vtuKBA|PmX%F4S2cq%2G--4FS-!m6rn<>6nNgNw7S4z7YA_yOYN=%nZ(CH^ld zw21NGxF7HCJ?`EC{ziqVX4g2NYL<~sCWLHmRS3Q!fGEP~L4R0cramW%DR_>rd-(Wz z7w1{t=l&f1O5S9EPavLUx?vG-5KnJfI_G`j2rEen@j3CBK^G)`h+~SXQNBOxvch?bvs$UK);;+PLwRjwnd>y8NMaF75FtQD z4P{hdAx^7CihqeT?I%3^!;W7hmrSlQ7&#VDg$l{>ga5(rZq35vgqsvf0NpRP{V@Ur zcY$Wzw!e>UyLkcxo`EZ^?XNa~nNQN|Z7p^L3~U1z*KJMS11@)fp(kB3Bu5I+^cM=i z`x$*x4j8-z`qtduTKhPC05a57>IOJC1V)RLz3%bu-ha;C{yo#`?*|*&a)be|&F}yK z00v@9M??Ss00000`9r&Z00009a7bBm000XU000XU0RWnu7ytkO2XskIMF->q9u)%* z7Z`?t0002XNkl=HUb-!Z(j)r{D0=P85A30h8r_6&|WL{W`Cn-M=v@j9uad39__{{581SII*3T1s(JCG c%nMB84eaV?pORYthyVZp07*qoM6N<$f_JGgTmS$7 diff --git a/frontend/src/images/search-icon-wht_24x24.png b/frontend/src/images/search-icon-wht_24x24.png index 89c102281374e1f8271189fdba0527b3293c96fc..da406ee7692f95e7dd5022c60c740b58597c1f1e 100644 GIT binary patch delta 382 zcmV-^0fGMF1(^eoB!6H@L_t(Y$JLa*N<%>qh0mB6LQExuG$s&ITUZHs0ZXy4u}zaM zrEOjzmG}Y{DHKAA*oaNQMtp%pQEp*l8h;R*&t|VImk{qwt`G;d*qNPkX3x%!v`PkS z0A*%d8z=&qMZv4Uy94_I#@?EGM2En7Qt)jcZ~!Bq7l}8W|9{0J$s{2dxy1f2=Z-y+ zVqEY&U=laUE2bTn;M^s2fn1F9&G1c<64Vn&It~fe{<^hSir@+;#E_>ashXrk^T5pl zT~uB~qE|N#3K7tp^Y>|zTL%Vf1DW!!S{Rf|B cHqn2wZ!Ffo-a|KzlK=n!07*qoM6N<$f~NPY5&!@I delta 714 zcmV;*0yX`a1L6gcB!7fyLqkwWLqi~Na&Km7Y-IodD3N`UJxIeq9K~N-wIUTMb`a^1 zp*mR*6>-!m6rn<>6nNgNw7S4z7YA_yOYN=%nZ(CH^ld zw21NGxF7HCJ?`EC{ziqVX4g2NYL<~sCWLHmRS3Q!fGEP~L4R0cramW%DR_>rd-(Wz z7w1{t=l&f1O5S9EPavLUx?vG-5KnJfI_G`j2rEen@j3CBK^G)`h+~SXQNBOxvch?bvs$UK);;+PLwRjwnd>y8NMaF75FtQD z4P{hdAx^7CihqeT?I%3^!;W7hmrSlQ7&#VDg$l{>ga5(rZq35vgqsvf0NpRP{V@Ur zcY$Wzw!e>UyLkcxo`EZ^?XNa~nNQN|Z7p^L3~U1z*KJMS11@)fp(kB3Bu5I+^cM=i z`x$*x4j8-z`qtduTKhPC05a57>IOJC1V)RLz3%bu-ha;C{yo#`?*|*&a)be|&F}yK z00v@9M??Ss00000`9r&Z00009a7bBm000XU000XU0RWnu7ytkO2XskIMF->q9u)!? z9d9p|0002rNkl`>0sO!bYVc z5kZH8GoLaqn$ZAdb{#6xkUcZ?SV4H}sCa%yNki6dklAh1+&+|uWROsu?8qobrh?2u wEC)6ZiCS7?>lHDs$lMP^mt`#+zf@O=7hQ&_DqM+K>Hq)$07*qoM6N<$f?TjXO#lD@ diff --git a/frontend/src/images/toggle-help-icon-blk_16x16.png b/frontend/src/images/toggle-help-icon-blk_16x16.png new file mode 100644 index 0000000000000000000000000000000000000000..404389245e7a267215f533a62d5aa658a80a16b3 GIT binary patch literal 565 zcmV-50?Pe~P)JedEY<`uX*C)V1fx<9B2`cfMTA;t4^0qhLB)Cy1TR(a4-oVq zf+rQLSZD>oLob3*sh3|e=mfg-Tycz3rIju#4t zw;jmm_X7RE1ktwr%Egi4%c+MC?(2TY3mpK;r6CLG177(>LH>F3JkS;5^^Oz@t2ahR zzntpn`57k3<#I=XufbiquKN_Y349Bj*RNfjPNjA}-)frYZ9Dlr+_7n@Dli5-l2XPb z&<}>2 za-D;U>2%6Vr_)z}43GnM0k?cXpKQ=6>L`~>Nl%jY& z>Tn!qaAxMC_hxGHLcLy}Q!17?SL~gVQsTPqhL(Q=HM)uMPdDU`00000NkvXXu0mjf DuiXII literal 0 HcmV?d00001 diff --git a/frontend/src/index.html b/frontend/src/index.html index 99f828fc..dfcf4cf1 100644 --- a/frontend/src/index.html +++ b/frontend/src/index.html @@ -1,6 +1,6 @@ @@ -63,14 +63,7 @@
-
- -
- - -
-
+
diff --git a/frontend/src/js/apis/data-operations.js b/frontend/src/js/apis/data-operations.js new file mode 100644 index 00000000..7da4c524 --- /dev/null +++ b/frontend/src/js/apis/data-operations.js @@ -0,0 +1,311 @@ +/** + * @license + * Copyright (c) 2021, Oracle and/or its affiliates. + * The Universal Permissive License (UPL), Version 1.0 + * @ignore + */ +"use strict"; + +/** + * UI API module for performing data CRUD operations via the `CbeDataManager` module. + *

That module uses the CBE REST API to perform the actual CRUD operation(s).

+ *

There are several architectural principles being adhered to here:

+ *
    + *
  • Data being returned is transport-agnostic.   Being a UI API means that the consumer is a UI (e.g. View/ViewModel combination), so it doesn't need to know "what" is providing the data, "how" it's providing it or "where" it's coming from. If the UI API returns things like "HTTP status code" or "HTTP response headers", then the consumer will end up having code in it that "knows how" the data is being obtained, and will 1) factor that into how responses are processed, and 2) not be a tier that focuses exclusively on UI layout, UI components and how to use them to offer the end-user the best UX.

    NOTE: If you have a scenario where the consumer needs/wants to use transport-related data, then use the CFE micro-services directly, instead of going through the CFE UI API.

  • + *
  • All successes result in Promise fulfillments, and all failures result in Promise rejections   There are no cases where an error is caught, and a Promise resolve is returned instead. The caught error (or response) is only being caught to determine if enhancements (e.g. then addition of more properties to it) can be done, before it is rethrown for handling by code in the API consumer. + *
+ * @module + */ +define(['ojs/ojcore', '../microservices/data-management/cbe-data-manager', '../core/runtime', '../core/types', '../core/utils' , '../core/cfe-errors', '../core/cbe-types'], + function (oj, CbeDataManager, Runtime, CoreTypes, CoreUtils, CfeErrors, CbeTypes) { + //public: + return { + mbean: { + messages: { + "cfeApi": { + "serviceNotDefined": {detail: "'{0}' service not defined in console-frontend-jet.yaml file."} + }, + "cbeRestApi": { + "requestUnsuccessful": { + "summary": oj.Translations.getTranslatedString("wrc-cbe-data-manager.messages.cbeRestApi.requestUnsuccessful.summary"), + "detail": oj.Translations.getTranslatedString("wrc-cbe-data-manager.messages.cbeRestApi.requestUnsuccessful.detail") + } + } + }, + + /** + * + * @param {string} url + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + test: function(url) { + return CbeDataManager.testUri({url: url}) + .then(reply => { + // Here, we show how to remove fields from reply when + // you need to adhere to SoC between the architectural + // tiers. That adherence means removing all the + // transport-related fields from the reply, before you + // return it to the consumer. + if (CoreUtils.isNotUndefinedNorNull(reply.transport)) { + delete reply.transport["status"]; + delete reply.transport["statusText"]; + delete reply.transport["headers"]; + } + return reply; + }); + }, + /** + * + * @param {ServiceType} serviceType + * @param {string} uri + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + get: function(serviceType, uri) { + return CbeDataManager.getAggregatedData(serviceType, uri); + }, + /** + * + * @param {string} url + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + reload: function(url) { + return CbeDataManager.reloadData({url: url}) + .catch(response =>{ + // Try to make FailureType more accurate, if + // it was a CBE_REST_API generated failure + if (response.transport.status === 404) { + // Switch it to FailureType.NOT_FOUND + response["failureType"] = CoreTypes.FailureType.NOT_FOUND; + } + // Rethrow updated (or not updated) reject + return Promise.reject(response); + }); + }, + /** + * + * @param {ServiceType} serviceType + * @param {string} uri + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + new: function(serviceType, uri) { + return CbeDataManager.putData(serviceType, uri); + }, + /** + * Use a ``multipart/form-data`` POST request to upload deployment-related files to a CBE REST endpoint + * @param {string} url - URL for resource at CBE REST endpoint + * @param {object} formData - Data to use in ``multipart/form-data`` POST request sent to CBE REST API endpoint + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + upload: function (url, formData) { + return CbeDataManager.postMultipartFormData(url, formData); + }, + /** + * + * @param {string} url + * @param {object} dataPayload + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + update: function(url, dataPayload) { + return CbeDataManager.postData({url: url}, dataPayload); + }, + /** + * + * @param {string} url + * @param {object} dataPayload + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + save: function(url, dataPayload) { + return CbeDataManager.postPayloadData({url: url}, dataPayload); + }, + /** + * + * @param {string} url + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + delete: function(url) { + return CbeDataManager.deleteData(url) + .catch(response =>{ + // Try to make FailureType more accurate, if + // it was a CBE_REST_API generated failure + if (response.transport.status === 404) { + // Switch it to FailureType.NOT_FOUND + response["failureType"] = CoreTypes.FailureType.NOT_FOUND; + } + // Rethrow updated (or not updated) reject + return Promise.reject(response); + }); + } + }, + + ataglance: { + /** + * + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + getServersGlance: function() { + return CbeDataManager.getData(CbeTypes.ServiceType.MONITORING, CbeTypes.ServiceComponentSubType.LIFECYCLE, {id: "view"}); + } + }, + + changeManager: { + SessionAction: Object.freeze({ + EDIT: {name: "edit"}, + COMMIT: {name: "commit"}, + DISCARD: {name: "discard"} + }), + /** + * Returns a Promise containing the lock state of the edit session the CBE has with WLS domain + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + getLockState: function() { + return CbeDataManager.getChangeManagerData("view"); + }, + /** + * + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + getData: function() { + return CbeDataManager.getChangeManagerData("edit"); + }, + /** + * + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + commitChanges: function() { + return CbeDataManager.postChangeManagerData("commit"); + }, + /** + * + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + discardChanges: function() { + return CbeDataManager.postChangeManagerData("discard"); + } + }, + + connection: { + messages: { + "connectionMessage": {summary: oj.Translations.getTranslatedString("wrc-data-operations.messages.connectionMessage.summary")}, + "backendNotReachable": {detail: oj.Translations.getTranslatedString("wrc-data-operations.messages.backendNotReachable.detail")}, + "connectFailed": {detail: oj.Translations.getTranslatedString("wrc-data-operations.messages.connectFailed.detail")}, + "badRequest": {detail: oj.Translations.getTranslatedString("wrc-data-operations.messages.badRequest.detail")}, + "invalidCredentials": {detail: oj.Translations.getTranslatedString("wrc-data-operations.messages.invalidCredentials.detail")}, + "invalidUrl": {detail: oj.Translations.getTranslatedString("wrc-data-operations.messages.invalidUrl.detail")}, + "notSupported": {detail: oj.Translations.getTranslatedString("wrc-data-operations.messages.notSupported.detail")}, + "unexpectedStatus": {detail: oj.Translations.getTranslatedString("wrc-data-operations.messages.unexpectedStatus.detail", "{0}")} + }, + + /** + * Gets about information from the CBE + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + getAboutInformation: function() { + return CbeDataManager.getConnectionData(CbeTypes.ServiceType.INFORMATION) + }, + + /** + * Try to establish a connection to the CBE. + *

It takes no parameters because the connectivity info is being (or has already been) gotten from elsewhere.

+ *

The possible choices for the state are:

+ *
    + *
  • CONNECTED>/li> + *
  • DISCONNECTED
  • + *
+ * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + getConnectivityMode: function () { + return CbeDataManager.getConnectionData(CbeTypes.ServiceType.CONNECTING); + }, + + // FortifyIssueSuppression Password Management: Password in Comment + // The comment below is not referencing a password + /** + * Ask CBE to make a connection to a WebLogic REST API endpoint, using the given WebLogic ``user``, WebLogic ``password`` and WebLogic admin ``url``. * + * @param {{username: string, password: string, adminUrl: string}} connectivityInfo user - Information to use when attempting to connect to the WebLogic REST API endpoint. + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + makeConnection: function (connectivityInfo) { + function getErrorMessage(status) { + let msg = this.messages.connectFailed.detail; + // Create message to display for connection error + switch (status) { + case 400: + msg = msg + this.messages.badRequest.detail; + break; + case 401: + case 403: + msg = msg + this.messages.invalidCredentials.detail; + break; + case 404: + msg = msg + this.messages.invalidUrl.detail; + break; + case 501: + msg = msg + this.messages.notSupported.detail; + break; + default: + msg = msg + this.messages.unexpectedStatus.detail.replace("{0}", status); + break; + } + return msg; + } + + async function createAuthorizationHeader(connectivityInfo) { + // Use built-in, global btoa() method to create + // an Authorization HTTP request header. + // + // If btoa() throws an error, control will pass + // to the ".catch(reason => {})" chain link below. + // Otherwise, we just return the base64 encoded + // value for the Authorization HTTP header. + return "Basic " + btoa(connectivityInfo.username + ":" + connectivityInfo.password); + } + + const dataPayload = {"domainUrl": connectivityInfo.adminUrl}; + + // Use Promise chain to do the work + return new Promise((resolve, reject) => { + createAuthorizationHeader(connectivityInfo) + .then(authorization => { + // Creation of Authorization header succeeded, so + // go ahead and make the call on the CbeDataManager + // micro-service. + CbeDataManager.postReplyConnectionData(dataPayload, authorization) + .then(reply => { + resolve(reply); + }) + .catch(response => { + // Don't assume that this is a CBE_REST_API + // failure type!! Check and see what failure + // type it actually is, before you alter the + // response :-) + if (response.failureType === CoreTypes.FailureType.UNEXPECTED && response.failureReason.message === "Failed to fetch") { + response["failureReason"] = this.messages.backendNotReachable.detail; + } + else if (response.failureType === CoreTypes.FailureType.CBE_REST_API) { + response["failureReason"] = getErrorMessage.call(this, response.transport.status); + } + reject(response); + }); + }) + .catch(reason => { + reject({ + failureType: CoreTypes.FailureType.UNEXPECTED, + failureReason: new CfeErrors.CfeError("Some of the characters used are outside of the Latin character set") + }); + }) + + }); + }, + + /** + * Ask CBE to disconnect from the WebLogic REST API endpoint it is currently connected to. + * @returns {Promise<{transport?: {status: number, statusText: string}, body: {data: any, messages?: any}}|{failureType: FailureType, failureReason?: any}|{Error}>} + */ + removeConnection: function() { + return CbeDataManager.deleteConnectionData(); + } + } + + } + } +); diff --git a/frontend/src/js/apis/message-displaying.js b/frontend/src/js/apis/message-displaying.js new file mode 100644 index 00000000..e72118b6 --- /dev/null +++ b/frontend/src/js/apis/message-displaying.js @@ -0,0 +1,165 @@ +/** + * @license + * Copyright (c) 2021, Oracle and/or its affiliates. + * The Universal Permissive License (UPL), Version 1.0 + * @ignore + */ +"use strict"; + +/** + * CFE UI API module for displaying popup messages of all severities and varieties + *

The CBE REST API does not currently have a standardizes contract for either the message structure, or the location. They are generally in the response body of the HTTP response, but the format varies from:

+ *
    + *
  • Plain-text that is not, and cannot be coerced to be JSON or YAML.   These need to be turned into a JSON array containing JSON objects for each message.
  • + *
  • JSON intertwined with HTML tags.   These need to be transformed into a JSON array containing JSON objects for each message, which get rendered as HTML

    tags.

  • + *
  • JSON array with the name , which contains message objects.
  • + *
  • Plain-text that is in JSON format, but the root may or maynot be a JSON array, and the root may or may not be named messages   Again, the CFE has to turn this into a JSON array that contains JSON objects for each message.

  • + *
+ *

This is, as you might guess, too involved to be done in the code of a ViewModels, so this module is dedicated to dealing with all of those nuances.

+ */ +define(['ojs/ojcore', 'knockout', 'ojs/ojhtmlutils', 'ojs/ojlogger'], + function (oj, ko, HtmlUtils, Logger) { + const i18n = { + messages: { + "seeJavascriptConsole": { + detail: oj.Translations.getTranslatedString("wrc-message-displaying.messages.seeJavascriptConsole.detail") + }, + "responseMessages": { + summary: oj.Translations.getTranslatedString("wrc-message-displaying.messages.responseMessages.summary") + } + } + }; + + var _popupMessageSentSignal; + + /** + * + * @param {{severity: string, summary: string, [detail]: string}} message + * @returns {string} + */ + function getMessageSeverity(message) { + // Default to the error severity + let severity = 'error'; + + // Check if the message defines a severity and map to the message box severity + if ((typeof message.severity !== 'undefined') && (message.severity !== "")) { + switch (message.severity) { + case "INFO": + severity = 'info'; + break; + case "WARNING": + severity = 'warning'; + break; + } + } + + // Return the mapped severity + return severity; + } + + function getPopupMessageSentSignal() { + return _popupMessageSentSignal; + } + + return { + setPopupMessageSentSignal: function(signal) { + _popupMessageSentSignal = signal; + }, + + /** + * Common message objects. + */ + messages: { + "seeJavascriptConsole": i18n.messages.seeJavascriptConsole + }, + + /** + * Displays `message` as a popup message. + *

The optional `autoCloseInterval` parameter is ignored if `message.severity !=== "confirmation"`

only

+ * @param {{severity: string, summary: string, [detail]: string}} message - The message object to display + * @param {number} [autoCloseInterval] - Optionally, the number of milliseconds to leave message up, before auto-closing it. 1500 milliseconds (1.5 seconds) will be used, if the parameter is missing. + */ + displayMessage: function(message, autoCloseInterval) { + if (typeof message.severity === "undefined") message["severity"] = "confirmation"; + if (autoCloseInterval && ["confirmation", "info"].includes(message.severity) ) { + getPopupMessageSentSignal().dispatch(message, autoCloseInterval || 1500); + } + else { + getPopupMessageSentSignal().dispatch(message); + } + }, + + /** + * + * @param {{severity: string, summary: string, detail?: string}[]} messages + */ + displayMessages: function(messages) { + messages.forEach((message) => { + message["severity"] = getMessageSeverity(message); + getPopupMessageSentSignal().dispatch(message); + }); + }, + + /** + * + * @param {{severity: string, summary: string, detail?: string}[]} responseMessages + * @param {number} [autoCloseInterval] - Optionally, the number of milliseconds to leave message up, before auto-closing it. 1500 milliseconds (1.5 seconds) will be used, if the parameter is missing. + * @returns {Array} + */ + displayResponseMessages: function(responseMessages, autoCloseInterval) { + let rtnval = []; + + if (typeof responseMessages !== 'undefined') { + let errorMessagesHTML = "
    ", errorSummary = i18n.messages.responseMessages.summary; + responseMessages.forEach((message) => { + if (typeof message === "object") { + errorMessagesHTML += "
  • " + message.message + "
  • "; + } + else { + errorMessagesHTML += "
  • " + message + "
  • "; + } + }); + if (errorMessagesHTML.indexOf("
  • ") !== -1) { + errorMessagesHTML += "
"; + const errorMessage = { + html: { view: HtmlUtils.stringToNodeArray(errorMessagesHTML) }, + severity: "error", + summary: errorSummary + }; + getPopupMessageSentSignal().dispatch(errorMessage, autoCloseInterval || 5000); + } + } + + return rtnval; + }, + + displayFieldMessages: function(fieldMessages) { + + }, + + /** + * Display a given array of messages with detail fields that contain HTML tags. + *

All of the messages are displayed in a single popup, using ``summary`` as the message summary field.

+ * @param {{severity: string, summary?: string, detail?: string}[]} messages - Array of messages to display + * @param {string} summary + * @param {number} [autoCloseInterval] - Optionally, the number of milliseconds to leave message up, before auto-closing it. 1500 milliseconds (1.5 seconds) will be used, if the parameter is missing. + */ + displayErrorMessagesHTML: function (messages, summary, autoCloseInterval) { + let errorMessagesHTML = "
    ", errorSummary = summary || i18n.messages.incompleteRequiredField.summary; + messages.forEach((message) => { + errorMessagesHTML += "
  • " + message.detail + "
  • "; + }); + if (errorMessagesHTML.indexOf("
  • ") !== -1) { + errorMessagesHTML += "
"; + const errorMessage = { + html: { view: HtmlUtils.stringToNodeArray(errorMessagesHTML) }, + severity: "info", + summary: errorSummary + }; + getPopupMessageSentSignal().dispatch(errorMessage, autoCloseInterval); + } + } + }; + + } +); \ No newline at end of file diff --git a/frontend/src/js/appController.js b/frontend/src/js/appController.js index d1ca9156..9a243ebb 100644 --- a/frontend/src/js/appController.js +++ b/frontend/src/js/appController.js @@ -6,17 +6,17 @@ */ "use strict"; -define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'signals', 'ojs/ojresponsiveutils', 'ojs/ojresponsiveknockoututils', './cfe/common/runtime', 'ojs/ojcontext', './cfe/services/perspective/perspective-manager', './cfe/services/preferences/preferences', 'ojs/ojlogger', './panel_resizer', 'ojs/ojarraydataprovider', 'ojs/ojknockout', 'ojs/ojmodule-element', 'ojs/ojmessages'], - function ($, ko, ModuleElementUtils, Router, signals, ResponsiveUtils, ResponsiveKnockoutUtils, Runtime, Context, PerspectiveManager, Preferences, Logger) { +define(['jquery', 'ojs/ojcore', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'signals', 'ojs/ojresponsiveutils', 'ojs/ojresponsiveknockoututils', './apis/message-displaying', './core/runtime', 'ojs/ojcontext', './microservices/perspective/perspective-manager', './microservices/perspective/perspective-memory-manager', './microservices/preferences/preferences', './viewModels/utils', 'ojs/ojlogger', './panel_resizer', 'ojs/ojarraydataprovider', 'ojs/ojknockout', 'ojs/ojmodule-element', 'ojs/ojmessages'], + function ($, oj, ko, ModuleElementUtils, Router, signals, ResponsiveUtils, ResponsiveKnockoutUtils, MessageDisplaying, Runtime, Context, PerspectiveManager, PerspectiveMemoryManager, Preferences, ViewModelUtils, Logger) { function ControllerViewModel() { const PANEL_RESIZER_WIDTH = parseInt(getComputedStyle(document.documentElement).getPropertyValue("--panel-resizer-width"), 10); const NAVSTRIP_WIDTH = parseInt(getComputedStyle(document.documentElement).getPropertyValue("--navstrip-max-width"), 10); const NAVTREE_MIN_WIDTH = parseInt(getComputedStyle(document.documentElement).getPropertyValue("--resizer-left-panel-min-width"), 10); const NAVTREE_MAX_WIDTH = parseInt(getComputedStyle(document.documentElement).getPropertyValue("--navtree-max-width"), 10); - var self = this; + const self = this; - var signaling = { + const signaling = { modeChanged: new signals.Signal(), domainChanged: new signals.Signal(), perspectiveChanged: new signals.Signal(), @@ -36,7 +36,11 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig readonlyChanged: new signals.Signal() }; - if (Preferences.hasThemePreference()) Runtime.setProperty(Runtime.PropertyName.CFE_CURRENT_THEME, Preferences.themePreference()); + MessageDisplaying.setPopupMessageSentSignal(signaling["popupMessageSent"]); + + Runtime.setProperty(Runtime.PropertyName.CFE_NAME, oj.Translations.getTranslatedString("wrc-header.text.appName")); + + if (Preferences.general.hasThemePreference()) Runtime.setProperty(Runtime.PropertyName.CFE_CURRENT_THEME, Preferences.general.themePreference()); // Media queries for responsive layouts const smQuery = ResponsiveUtils.getFrameworkQuery(ResponsiveUtils.FRAMEWORK_QUERY_KEY.SM_ONLY); @@ -44,18 +48,9 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig const mdQuery = ResponsiveUtils.getFrameworkQuery(ResponsiveUtils.FRAMEWORK_QUERY_KEY.MD_UP); this.mdScreen = ResponsiveKnockoutUtils.createMediaQueryObservable(mdQuery); - this.i18n = { - footer: { - text: { - copyrightLegal: "Copyright © 2020, 2021, Oracle and/or its affiliates.
Oracle is a registered trademark of Oracle Corporation and/or its affiliates. Other names may be trademarks of their respective owners.
", - builtWith: "Built with Oracle JET" - } - } - }; - this.navTreeModuleConfig = ko.observable({ view: [], viewModel: null }); - var router = Router.rootInstance; + const router = Router.rootInstance; this.router = router; Router.defaults['urlAdapter'] = new Router.urlParamAdapter(); @@ -69,6 +64,10 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig "monitoring/{path}": { label: "Monitoring", value: "monitoring", title: Runtime.getName() } }); + this.getSignal = function (key) { + return (key in signaling ? signaling[key] : undefined); + }; + this.loadModule = function () { self.moduleConfig = ko.pureComputed(function () { var name = self.router.moduleConfig.name(); @@ -96,9 +95,9 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig this.loadHeaderTemplate = function () { self.headerModuleConfig = ko.pureComputed(function () { - var name = 'header'; - var viewPath = 'views/template/' + name + '.html'; - var modelPath = 'viewModels/template/' + name; + const name = 'header'; + const viewPath = 'views/branding-area/' + name + '.html'; + const modelPath = 'viewModels/branding-area/' + name; return ModuleElementUtils.createConfig({ viewPath: viewPath, viewModelPath: modelPath, @@ -117,8 +116,8 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig this.loadNavStripTemplate = function () { self.navStripModuleConfig = ko.pureComputed(function () { var name = 'navstrip'; - var viewPath = 'views/template/' + name + '.html'; - var modelPath = 'viewModels/template/' + name; + var viewPath = 'views/navigation-area/' + name + '.html'; + var modelPath = 'viewModels/navigation-area/' + name; return ModuleElementUtils.createConfig({ viewPath: viewPath, viewModelPath: modelPath, @@ -132,13 +131,32 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig }; this.loadNavStripTemplate(); + this.loadFooterTemplate = function () { + self.footerModuleConfig = ko.pureComputed(function () { + var name = 'footer'; + var viewPath = 'views/footer/' + name + '.html'; + var modelPath = 'viewModels/footer/' + name; + return ModuleElementUtils.createConfig({ + viewPath: viewPath, + viewModelPath: modelPath, + params: { + parentRouter: self.router, + smQuery: smQuery, + mdQuery: mdQuery, + signaling: signaling + } + }); + }); + }; + this.loadFooterTemplate(); + this.loadNavTree = function (perspectiveId) { - let name = perspectiveId + "/navtree"; - let perspective = PerspectiveManager.getById(perspectiveId); + const name = "navtree"; + const perspective = PerspectiveManager.getById(perspectiveId); ModuleElementUtils.createConfig({ - viewPath: 'views/' + name + '.html', - viewModelPath: 'viewModels/' + name, + viewPath: 'views/navigation-area/' + name + '.html', + viewModelPath: 'viewModels/navigation-area/' + name, params: { parentRouter: self.router, signaling: signaling, @@ -154,9 +172,9 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig this.loadContentAreaHeaderTemplate = function () { self.contentAreaHeaderModuleConfig = ko.pureComputed(function () { - var name = "content-area-header"; - var viewPath = 'views/template/' + name + '.html'; - var modelPath = 'viewModels/template/' + name; + const name = "content-area-header"; + const viewPath = 'views/content-area/header/' + name + '.html'; + const modelPath = 'viewModels/content-area/header/' + name; return ModuleElementUtils.createConfig({ viewPath: viewPath, viewModelPath: modelPath, @@ -171,17 +189,16 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig this.loadAncillaryContentAreaTemplate = function () { self.ancillaryContentAreaModuleConfig = ko.pureComputed(function () { - var name = "ancillary-content-area"; - var viewPath = 'views/template/' + name + '.html'; - var modelPath = 'viewModels/template/' + name; + var name = "ancillary-content"; + var viewPath = 'views/content-area/' + name + '.html'; + var modelPath = 'viewModels/content-area/' + name; return ModuleElementUtils.createConfig({ viewPath: viewPath, viewModelPath: modelPath, params: { parentRouter: self.router, signaling: signaling, - onAncillaryContentAreaToggled: toggledAncillaryContentArea, - onResized: resizeTriggered + onAncillaryContentAreaToggled: toggledAncillaryContentArea } }); }); @@ -189,36 +206,9 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig this.loadAncillaryContentAreaTemplate(); function setThemePreference(theme) { - setFooter(theme); signaling.themeChanged.dispatch(theme); } - function setFooter(theme) { - let ele = document.querySelector("footer"); - if (ele !== null) { - ele.style.backgroundColor = Runtime.getConfig().settings.themes[theme][0]; - - let ele1 = document.getElementById("copyright-legal"); - if (ele1 !== null) ele1.innerHTML = self.i18n.footer.text.copyrightLegal; - - ele1 = document.getElementById("oracle-jet-label"); - if (ele1 !== null) ele1.innerHTML = self.i18n.footer.text.builtWith; - - ele1 = document.getElementById("oracle-jet-icon"); - - switch (theme) { - case "light": - ele.style.color = "black"; - if (ele1 !== null) ele1.src = "../../images/oracle-jet-logo-blk_16x16.png" - break; - case "dark": - ele.style.color = "white"; - if (ele1 !== null) ele1.src = "../../images/oracle-jet-logo-wht_16x16.png" - break; - } - } - } - function toggledAncillaryContentArea(visible) { signaling.ancillaryContentAreaToggled.dispatch(visible); } @@ -247,7 +237,7 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig } } else { - Logger.info(`[APPCONTROLLER] newOffsetWidth=0`); + Logger.info(`newOffsetWidth=0`); } resizeContentAreaElements(source, newOffsetLeft, newOffsetWidth); @@ -255,7 +245,7 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig function resizeContentAreaElements(source, newOffsetLeft, newOffsetWidth) { const viewPortValues = getBrowserViewPortValues(); - Logger.info(`[APPCONTROLLER] window.width=${viewPortValues.width}, window.height=${viewPortValues.height}`); + Logger.info(`window.width=${viewPortValues.width}, window.height=${viewPortValues.height}`); if (newOffsetWidth !== viewPortValues.width) resizeDomainsToolbarRight(source, newOffsetLeft, newOffsetWidth); resizeTableFormContainer(source); } @@ -273,12 +263,12 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig } else if (source === "navtree") { marginRightVariable = 0; } - document.documentElement.style.setProperty("--domains-toolbar-right-margin-right", `${marginRightVariable}px`); + document.documentElement.style.setProperty("--content-area-header-toolbar-right-margin-right", `${marginRightVariable}px`); } function resizeTableFormContainer(source) { if (source === "opener") { - let maxWidthVariable = parseInt(getComputedStyle(document.documentElement).getPropertyValue("--domains-toolbar-right-margin-right"), 10); + let maxWidthVariable = parseInt(getComputedStyle(document.documentElement).getPropertyValue("--content-area-header-toolbar-right-margin-right"), 10); maxWidthVariable += (NAVSTRIP_WIDTH + PANEL_RESIZER_WIDTH); document.documentElement.style.setProperty("--form-container-calc-max-width", `${maxWidthVariable}px`); } @@ -290,7 +280,7 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig signaling.perspectiveSelected.add((newPerspective) => { if (typeof newPerspective === "undefined") { - Logger.info(`[APPCONTROLLER] newPerspective is undefined`); + Logger.info(`newPerspective is undefined`); newPerspective = PerspectiveManager.getDefault(); } let active = PerspectiveManager.current(); @@ -355,7 +345,7 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig case "ONLINE": ele.style.display = "inline-flex"; break; - case "OFFLINE": + case "DETACHED": ele.style.display = "none"; router.go("home"); break; @@ -364,13 +354,15 @@ define(['jquery', 'knockout', 'ojs/ojmodule-element-utils', 'ojs/ojrouter', 'sig }); Context.getPageContext().getBusyContext().whenReady() - .then(function () { - setThemePreference(Preferences.themePreference()); - $('#spa-resizer').split({limit: 10}); - }) - .catch((err) => { - Logger.error(err); - }); + .then(function () { + setThemePreference(Preferences.general.themePreference()); + $('#spa-resizer').split({limit: 10}); + // Pass the mode changed signal so that memory can be cleared + PerspectiveMemoryManager.setModeChangedSignal(signaling.modeChanged); + }) + .catch((err) => { + Logger.error(err); + }); } return new ControllerViewModel(); diff --git a/frontend/src/js/cfe/binding/Attribute.js b/frontend/src/js/cfe/binding/Attribute.js deleted file mode 100644 index 616ab250..00000000 --- a/frontend/src/js/cfe/binding/Attribute.js +++ /dev/null @@ -1,43 +0,0 @@ -/** - * @license - * Copyright (c) 2020, 2021, Oracle and/or its affiliates. - * The Universal Permissive License (UPL), Version 1.0 - * @ignore - */ -'use strict'; - -define( - function() { - function Attribute(data){ - if (data['name'] !== undefined) this.name = data['name']; - if (data['label'] !== undefined) this.label = data['label']; - if (data['fullHelpHTML'] !== undefined) this.fullHelpHTML = data['fullHelpHTML']; - if (data['helpSummaryHTML'] !== undefined) this.helpSummaryHTML = data['helpSummaryHTML']; - if (data['type'] !== undefined) this.dataType = data['type']; - } - - Attribute.prototype = { - getDataType: function() { - return (this.dataType ? this.dataType : 'string'); - }, - - getName: function() { - return (this.name ? this.name : undefined); - }, - - getLabel: function() { - return (this.label ? this.label : undefined); - }, - - getFullHelpHTML: function() { - return (this.fullHelpHTML ? this.fullHelpHTML : undefined); - }, - - getHelpSummaryHTML: function() { - return (this.helpSummaryHTML ? this.helpSummaryHTML : undefined); - } - }; - - return Attribute; - } -); \ No newline at end of file diff --git a/frontend/src/js/cfe/binding/Column.js b/frontend/src/js/cfe/binding/Column.js deleted file mode 100644 index 4c531835..00000000 --- a/frontend/src/js/cfe/binding/Column.js +++ /dev/null @@ -1,33 +0,0 @@ -/** - * @license - * Copyright (c) 2020 Oracle and/or its affiliates. - * The Universal Permissive License (UPL), Version 1.0 - * @ignore - */ -'use strict'; - -define(['cfe/binding/Attribute'], - function(Attribute) { - function Column(data){ - // equivalent to super(data), in Java - Attribute.call(this, data); - if (data['array'] != undefined) this.array = data['array']; - if (data['usedIf'] != undefined) this.usedIf = data['usedIf']; - } - - // Allow properties of Attribute 'superclass' to be access - // by Column object 'subclass' - Column.prototype = Object.create(Attribute.prototype); - - Column.prototype.isArray = function() { - return (this.array ? this.array : undefined); - }; - - Column.prototype.getUsedIf = function() { - return (this.usedIf ? this.usedIf : undefined); - }; - - // Return RDJResource constructor function - return Column; - } -); \ No newline at end of file diff --git a/frontend/src/js/cfe/binding/Form.js b/frontend/src/js/cfe/binding/Form.js deleted file mode 100644 index d94d9827..00000000 --- a/frontend/src/js/cfe/binding/Form.js +++ /dev/null @@ -1,98 +0,0 @@ -/** - * @license - * Copyright (c) 2020 Oracle and/or its affiliates. - * The Universal Permissive License (UPL), Version 1.0 - * @ignore - */ -'use strict'; - -define(['cfe/binding/Property'], - function (Property) { - function Form(data) { - if (data['properties'] !== undefined) { - this.properties = []; - data['properties'].forEach(element => { - this.properties.push(new Property(element)); - }); - } - - if (data['advancedProperties'] !== undefined) { - this.advancedProperties = []; - data['advancedProperties'].forEach(element => { - this.advancedProperties.push(new Property(element)); - }); - } - } - - Form.prototype = { - /** - * Returns an array of Property objects - * @return {Property[]} - */ - getProperties: function(){ - return (this.properties ? this.properties : undefined); - }, - - /** - * Returns the value of a given Form property, or undefined. - *

undefined will be returned if any of the following are true: - *