katello 3.9.1 → 3.10.0.rc1

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of katello might be problematic. Click here for more details.

Files changed (229) hide show
  1. checksums.yaml +4 -4
  2. data/app/assets/javascripts/katello/hosts/host_and_hostgroup_edit.js +28 -12
  3. data/app/controllers/katello/api/rhsm/candlepin_dynflow_proxy_controller.rb +12 -3
  4. data/app/controllers/katello/api/rhsm/candlepin_proxies_controller.rb +4 -13
  5. data/app/controllers/katello/api/v2/content_credentials_controller.rb +1 -1
  6. data/app/controllers/katello/api/v2/content_view_filter_rules_controller.rb +1 -1
  7. data/app/controllers/katello/api/v2/content_view_versions_controller.rb +6 -4
  8. data/app/controllers/katello/api/v2/content_views_controller.rb +8 -3
  9. data/app/controllers/katello/api/v2/gpg_keys_controller.rb +2 -1
  10. data/app/controllers/katello/api/v2/host_module_streams_controller.rb +39 -0
  11. data/app/controllers/katello/api/v2/hosts_bulk_actions_controller.rb +20 -11
  12. data/app/controllers/katello/api/v2/module_streams_controller.rb +2 -1
  13. data/app/controllers/katello/api/v2/repository_sets_controller.rb +17 -8
  14. data/app/controllers/katello/application_controller.rb +0 -2
  15. data/app/controllers/katello/concerns/hosts_controller_extensions.rb +5 -2
  16. data/app/lib/actions/candlepin/consumer/attach_subscription.rb +0 -2
  17. data/app/lib/actions/candlepin/consumer/remove_subscription.rb +0 -2
  18. data/app/lib/actions/katello/capsule_content/create_repos.rb +1 -25
  19. data/app/lib/actions/katello/capsule_content/sync.rb +1 -1
  20. data/app/lib/actions/katello/content_view/promote.rb +2 -5
  21. data/app/lib/actions/katello/content_view/promote_to_environment.rb +2 -5
  22. data/app/lib/actions/katello/content_view/publish.rb +1 -4
  23. data/app/lib/actions/katello/content_view_puppet_environment/create.rb +6 -10
  24. data/app/lib/actions/katello/content_view_version/export.rb +0 -2
  25. data/app/lib/actions/katello/content_view_version/incremental_update.rb +19 -1
  26. data/app/lib/actions/katello/environment/publish_repositories.rb +2 -1
  27. data/app/lib/actions/katello/gpg_key/update.rb +17 -0
  28. data/app/lib/actions/katello/host/attach_subscriptions.rb +0 -2
  29. data/app/lib/actions/katello/host/erratum/install.rb +6 -0
  30. data/app/lib/actions/katello/host/generate_applicability.rb +0 -2
  31. data/app/lib/actions/katello/host/hypervisors_update.rb +11 -6
  32. data/app/lib/actions/katello/host/package/install.rb +6 -0
  33. data/app/lib/actions/katello/host/package/remove.rb +6 -0
  34. data/app/lib/actions/katello/host/package/update.rb +7 -1
  35. data/app/lib/actions/katello/host/package_group/install.rb +6 -0
  36. data/app/lib/actions/katello/host/package_group/remove.rb +6 -0
  37. data/app/lib/actions/katello/host/recalculate_errata_status.rb +0 -2
  38. data/app/lib/actions/katello/host/remove_subscriptions.rb +0 -2
  39. data/app/lib/actions/katello/host/update.rb +1 -0
  40. data/app/lib/actions/katello/host/update_content_overrides.rb +0 -2
  41. data/app/lib/actions/katello/host/upload_package_profile.rb +13 -12
  42. data/app/lib/actions/katello/host/upload_profiles.rb +70 -0
  43. data/app/lib/actions/katello/product/reindex_subscriptions.rb +0 -2
  44. data/app/lib/actions/katello/product/repositories_certs_reset.rb +4 -4
  45. data/app/lib/actions/katello/product/repositories_gpg_reset.rb +2 -2
  46. data/app/lib/actions/katello/repository/check_matching_content.rb +18 -6
  47. data/app/lib/actions/katello/repository/clone_deb_content.rb +1 -1
  48. data/app/lib/actions/katello/repository/clone_to_environment.rb +3 -5
  49. data/app/lib/actions/katello/repository/clone_to_version.rb +2 -3
  50. data/app/lib/actions/katello/repository/clone_yum_content.rb +1 -2
  51. data/app/lib/actions/katello/repository/clone_yum_metadata.rb +2 -2
  52. data/app/lib/actions/katello/repository/create.rb +1 -31
  53. data/app/lib/actions/katello/repository/destroy.rb +1 -2
  54. data/app/lib/actions/katello/repository/export.rb +0 -2
  55. data/app/lib/actions/katello/repository/fetch_pxe_files.rb +0 -2
  56. data/app/lib/actions/katello/repository/filtered_index_content.rb +0 -2
  57. data/app/lib/actions/katello/repository/finish_upload.rb +0 -2
  58. data/app/lib/actions/katello/repository/import_upload.rb +0 -2
  59. data/app/lib/actions/katello/repository/index_content.rb +0 -1
  60. data/app/lib/actions/katello/repository/index_package_groups.rb +0 -2
  61. data/app/lib/actions/katello/repository/instance_update.rb +21 -0
  62. data/app/lib/actions/katello/repository/remove_content.rb +0 -2
  63. data/app/lib/actions/katello/repository/sync.rb +0 -1
  64. data/app/lib/actions/katello/repository/update.rb +0 -2
  65. data/app/lib/actions/katello/upstream_subscriptions/bind_entitlement.rb +0 -2
  66. data/app/lib/actions/katello/upstream_subscriptions/bind_entitlements.rb +0 -2
  67. data/app/lib/actions/katello/upstream_subscriptions/remove_entitlement.rb +0 -1
  68. data/app/lib/actions/katello/upstream_subscriptions/remove_entitlements.rb +0 -2
  69. data/app/lib/actions/katello/upstream_subscriptions/update_entitlement.rb +0 -1
  70. data/app/lib/actions/katello/upstream_subscriptions/update_entitlements.rb +0 -2
  71. data/app/lib/actions/pulp/abstract.rb +13 -14
  72. data/app/lib/actions/pulp/repository/create.rb +13 -211
  73. data/app/lib/actions/pulp/repository/create_in_plan.rb +4 -18
  74. data/app/lib/actions/pulp/repository/refresh.rb +7 -70
  75. data/app/lib/actions/pulp/repository/sync.rb +1 -2
  76. data/app/lib/katello/capsule_content.rb +3 -3
  77. data/app/lib/katello/resources/candlepin/consumer.rb +1 -1
  78. data/app/lib/katello/resources/candlepin/product.rb +1 -1
  79. data/app/lib/katello/validators/hostgroup_kickstart_repository_validator.rb +1 -1
  80. data/app/models/katello/available_module_stream.rb +11 -0
  81. data/app/models/katello/concerns/content_facet_host_extensions.rb +1 -0
  82. data/app/models/katello/concerns/host_managed_extensions.rb +56 -0
  83. data/app/models/katello/concerns/hostgroup_extensions.rb +17 -0
  84. data/app/models/katello/concerns/redhat_extensions.rb +20 -6
  85. data/app/models/katello/concerns/search_by_repository_name.rb +0 -1
  86. data/app/models/katello/concerns/smart_proxy_extensions.rb +26 -12
  87. data/app/models/katello/content_facet_applicable_module_stream.rb +7 -0
  88. data/app/models/katello/content_view_puppet_environment.rb +14 -35
  89. data/app/models/katello/erratum.rb +54 -24
  90. data/app/models/katello/erratum_package.rb +6 -0
  91. data/app/models/katello/glue/pulp/repo.rb +5 -228
  92. data/app/models/katello/gpg_key.rb +1 -0
  93. data/app/models/katello/host/content_facet.rb +38 -83
  94. data/app/models/katello/host_available_module_stream.rb +47 -0
  95. data/app/models/katello/module_stream.rb +18 -0
  96. data/app/models/katello/module_stream_erratum_package.rb +6 -0
  97. data/app/models/katello/product.rb +0 -2
  98. data/app/models/katello/product_content.rb +1 -0
  99. data/app/models/katello/repository.rb +15 -6
  100. data/app/models/katello/root_repository.rb +1 -1
  101. data/app/models/katello/rpm.rb +5 -17
  102. data/app/services/katello/applicable_content_helper.rb +111 -0
  103. data/app/services/katello/managed_content_medium_provider.rb +7 -0
  104. data/app/services/katello/pulp/consumer.rb +13 -7
  105. data/app/services/katello/pulp/repository.rb +157 -4
  106. data/app/services/katello/pulp/repository/deb.rb +47 -0
  107. data/app/services/katello/pulp/repository/docker.rb +43 -0
  108. data/app/services/katello/pulp/repository/file.rb +31 -0
  109. data/app/services/katello/pulp/repository/ostree.rb +40 -0
  110. data/app/services/katello/pulp/repository/puppet.rb +43 -0
  111. data/app/services/katello/pulp/repository/yum.rb +61 -0
  112. data/app/services/katello/repository_type.rb +1 -1
  113. data/app/views/katello/api/v2/content_facet/base.json.rabl +1 -0
  114. data/app/views/katello/api/v2/content_view_versions/base.json.rabl +0 -1
  115. data/app/views/katello/api/v2/errata/_counts.json.rabl +0 -1
  116. data/app/views/katello/api/v2/errata/show.json.rabl +9 -3
  117. data/app/views/katello/api/v2/host_collections/delta_activation_keys.rabl +0 -1
  118. data/app/views/katello/api/v2/host_module_streams/base.json.rabl +8 -0
  119. data/app/views/katello/api/v2/host_module_streams/index.json.rabl +7 -0
  120. data/app/views/katello/api/v2/packages/backend.json.rabl +0 -1
  121. data/app/views/katello/api/v2/repositories/show.json.rabl +6 -6
  122. data/app/views/katello/layouts/react.html.erb +2 -2
  123. data/app/views/overrides/activation_keys/_host_synced_content_select.html.erb +0 -1
  124. data/config/routes/api/rhsm.rb +1 -0
  125. data/config/routes/overrides.rb +4 -0
  126. data/db/migrate/20181008201422_add_modules_to_errata_packages.rb +29 -0
  127. data/db/migrate/20181017181806_available_module_streams.rb +34 -0
  128. data/db/migrate/20181027014323_add_applicable_modules.rb +24 -0
  129. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/common/module-stream-actions.service.js +2 -1
  130. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-credentials/details/views/content-credential-info.html +1 -1
  131. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-credentials/new/views/new-content-credential.html +1 -0
  132. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-hosts/bulk/views/content-host-bulk-module-streams-modal.html +2 -2
  133. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-hosts/bulk/views/content-hosts-bulk-errata-modal.html +37 -22
  134. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-hosts/content-hosts.controller.js +4 -1
  135. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-hosts/content/content-host-module-streams.controller.js +27 -7
  136. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-hosts/content/views/content-host-module-streams.html +29 -0
  137. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-hosts/content/views/errata-details.html +15 -1
  138. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-hosts/views/content-hosts.html +1 -1
  139. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-views/details/content-view-promotion.controller.js +0 -1
  140. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-views/details/content-view-publish.controller.js +1 -2
  141. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-views/details/content-view-versions.controller.js +3 -1
  142. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-views/details/histories/content-view-history.controller.js +1 -1
  143. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-views/details/views/content-view-promotion.html +0 -15
  144. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/content-views/details/views/content-view-publish.html +0 -14
  145. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/errata/details/erratum.controller.js +19 -0
  146. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/errata/details/views/erratum-info.html +0 -12
  147. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/errata/details/views/erratum-packages.html +36 -0
  148. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/errata/details/views/erratum.html +7 -0
  149. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/errata/errata.routes.js +9 -0
  150. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/hosts/host-module-streams.factory.js +18 -0
  151. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/products/details/repositories/details/views/repository-info.html +4 -2
  152. data/engines/bastion_katello/app/assets/javascripts/bastion_katello/products/details/repositories/new/views/new-repository.html +2 -2
  153. data/engines/bastion_katello/app/assets/stylesheets/bastion_katello/bastion_katello.scss +13 -0
  154. data/lib/katello/permissions/host_permissions.rb +3 -0
  155. data/lib/katello/repository_types/deb.rb +3 -1
  156. data/lib/katello/repository_types/docker.rb +3 -1
  157. data/lib/katello/repository_types/file.rb +1 -0
  158. data/lib/katello/repository_types/ostree.rb +3 -1
  159. data/lib/katello/repository_types/puppet.rb +3 -1
  160. data/lib/katello/repository_types/yum.rb +3 -1
  161. data/lib/katello/tasks/delete_orphaned_content.rake +1 -1
  162. data/lib/katello/tasks/reset.rake +1 -0
  163. data/lib/katello/tasks/test.rake +14 -0
  164. data/lib/katello/tasks/unify_hosts.rake +2 -0
  165. data/lib/katello/tasks/virt_who_report.rake +2 -1
  166. data/lib/katello/version.rb +1 -1
  167. data/locale/Makefile +52 -17
  168. data/locale/update-i18n +22 -0
  169. data/package.json +11 -1
  170. data/webpack/__mocks__/foremanReact/components/common/EmptyState.js +8 -0
  171. data/webpack/move_to_foreman/components/common/table/components/Table.js +2 -1
  172. data/webpack/move_to_pf/react-bootstrap-select/index.js +4 -2
  173. data/webpack/move_to_pf/test-utils/testHelpers.js +9 -0
  174. data/webpack/redux/OrganizationProducts/OrganizationProductsActions.js +24 -0
  175. data/webpack/redux/OrganizationProducts/OrganizationProductsConstants.js +5 -0
  176. data/webpack/redux/OrganizationProducts/OrganizationProductsReducer.js +38 -0
  177. data/webpack/redux/OrganizationProducts/OrganizationProductsSelectors.js +7 -0
  178. data/webpack/redux/OrganizationProducts/__tests__/OrganizationProductsActions.test.js +47 -0
  179. data/webpack/redux/OrganizationProducts/__tests__/OrganizationProductsReducer.test.js +33 -0
  180. data/webpack/redux/OrganizationProducts/__tests__/OrganizationProductsSelectors.test.js +19 -0
  181. data/webpack/redux/OrganizationProducts/__tests__/__snapshots__/OrganizationProductsActions.test.js.snap +49 -0
  182. data/webpack/redux/OrganizationProducts/__tests__/__snapshots__/OrganizationProductsReducer.test.js.snap +36 -0
  183. data/webpack/redux/OrganizationProducts/__tests__/__snapshots__/OrganizationProductsSelectors.test.js.snap +9 -0
  184. data/webpack/redux/OrganizationProducts/index.js +13 -0
  185. data/webpack/redux/actions/RedHatRepositories/enabled.js +7 -1
  186. data/webpack/redux/actions/RedHatRepositories/helpers.js +4 -0
  187. data/webpack/redux/actions/RedHatRepositories/sets.js +2 -0
  188. data/webpack/redux/reducers/RedHatRepositories/enabled.fixtures.js +8 -2
  189. data/webpack/redux/reducers/RedHatRepositories/enabled.js +1 -1
  190. data/webpack/redux/reducers/RedHatRepositories/sets.fixtures.js +12 -3
  191. data/webpack/redux/reducers/index.js +2 -0
  192. data/webpack/scenes/RedHatRepositories/components/SearchBar.js +68 -33
  193. data/webpack/scenes/RedHatRepositories/index.js +13 -2
  194. data/webpack/scenes/RedHatRepositories/index.scss +26 -0
  195. data/webpack/scenes/Subscriptions/Manifest/ManageManifestModal.js +1 -1
  196. data/webpack/scenes/Subscriptions/Manifest/__tests__/__snapshots__/ManageManifestModal.test.js.snap +1 -1
  197. data/webpack/scenes/Subscriptions/SubscriptionActions.js +18 -2
  198. data/webpack/scenes/Subscriptions/SubscriptionConstants.js +8 -0
  199. data/webpack/scenes/Subscriptions/SubscriptionHelpers.js +15 -0
  200. data/webpack/scenes/Subscriptions/SubscriptionReducer.js +22 -14
  201. data/webpack/scenes/Subscriptions/SubscriptionsPage.js +39 -90
  202. data/webpack/scenes/Subscriptions/SubscriptionsSelectors.js +14 -0
  203. data/webpack/scenes/Subscriptions/UpstreamSubscriptions/UpstreamSubscriptionsPage.js +1 -3
  204. data/webpack/scenes/Subscriptions/UpstreamSubscriptions/__tests__/__snapshots__/UpstreamSubscriptionsPage.test.js.snap +0 -1
  205. data/webpack/scenes/Subscriptions/__tests__/SubscriptionHelpers.test.js +84 -0
  206. data/webpack/scenes/Subscriptions/__tests__/SubscriptionsActions.test.js +26 -1
  207. data/webpack/scenes/Subscriptions/__tests__/SubscriptionsPage.test.js +5 -0
  208. data/webpack/scenes/Subscriptions/__tests__/SubscriptionsReducer.test.js +177 -75
  209. data/webpack/scenes/Subscriptions/__tests__/SubscriptionsSelectors.test.js +29 -0
  210. data/webpack/scenes/Subscriptions/__tests__/__snapshots__/SubscriptionHelpers.test.js.snap +31 -0
  211. data/webpack/scenes/Subscriptions/__tests__/__snapshots__/SubscriptionsActions.test.js.snap +32 -0
  212. data/webpack/scenes/Subscriptions/__tests__/__snapshots__/SubscriptionsPage.test.js.snap +18 -96
  213. data/webpack/scenes/Subscriptions/__tests__/__snapshots__/SubscriptionsReducer.test.js.snap +511 -0
  214. data/webpack/scenes/Subscriptions/__tests__/__snapshots__/SubscriptionsSelectors.test.js.snap +26 -0
  215. data/webpack/scenes/Subscriptions/__tests__/subscriptions.fixtures.js +6 -1
  216. data/webpack/scenes/Subscriptions/components/SubscriptionsTable/__tests__/__snapshots__/SubscriptionsTable.test.js.snap +3 -21
  217. data/webpack/scenes/Subscriptions/components/SubscriptionsToolbar/SubscriptionsToolbar.js +113 -0
  218. data/webpack/scenes/Subscriptions/components/SubscriptionsToolbar/SubscriptionsToolbar.test.js +47 -0
  219. data/webpack/scenes/Subscriptions/components/SubscriptionsToolbar/__snapshots__/SubscriptionsToolbar.test.js.snap +504 -0
  220. data/webpack/scenes/Subscriptions/components/SubscriptionsToolbar/index.js +1 -0
  221. data/webpack/scenes/Subscriptions/index.js +15 -4
  222. metadata +59 -14
  223. data/app/lib/actions/pulp/repository/associate_distributor.rb +0 -20
  224. data/app/lib/actions/pulp/repository/associate_importer.rb +0 -23
  225. data/app/lib/actions/pulp/repository/delete_distributor.rb +0 -18
  226. data/app/lib/actions/pulp/repository/refresh_distributor.rb +0 -19
  227. data/app/lib/actions/pulp/repository/update_importer.rb +0 -33
  228. data/app/lib/katello/bulk_actions.rb +0 -63
  229. data/webpack/move_to_foreman/components/common/EmptyState/index.js +0 -68
@@ -5,13 +5,19 @@ export const disabledIndex = 1;
5
5
  export const initialState = Immutable({
6
6
  loading: true,
7
7
  repositories: [],
8
- pagination: {},
8
+ pagination: {
9
+ page: 0,
10
+ },
11
+ itemCount: 0,
9
12
  });
10
13
 
11
14
  export const loadingState = Immutable({
12
15
  loading: true,
13
16
  repositories: [],
14
- pagination: {},
17
+ pagination: {
18
+ page: 0,
19
+ },
20
+ itemCount: 0,
15
21
  });
16
22
 
17
23
  export const requestSuccessResponse = Immutable({
@@ -74,7 +74,7 @@ export default (state = initialState, action) => {
74
74
  return Immutable({
75
75
  repositories: mapRepositories(results),
76
76
  pagination: {
77
- page: Number(page),
77
+ page: Number(page) || 0,
78
78
  // server can return per_page: null when there's error in the search query,
79
79
  // don't store it in such case
80
80
  // eslint-disable-next-line camelcase
@@ -4,21 +4,30 @@ export const initialState = Immutable({
4
4
  loading: true,
5
5
  recommended: false,
6
6
  results: [],
7
- pagination: {},
7
+ pagination: {
8
+ page: 0,
9
+ },
10
+ itemCount: 0,
8
11
  });
9
12
 
10
13
  export const recommendedState = Immutable({
11
14
  loading: true,
12
15
  recommended: true,
13
16
  results: [],
14
- pagination: {},
17
+ pagination: {
18
+ page: 0,
19
+ },
20
+ itemCount: 0,
15
21
  });
16
22
 
17
23
  export const loadingState = Immutable({
18
24
  loading: true,
19
25
  recommended: false,
20
26
  results: [],
21
- pagination: {},
27
+ pagination: {
28
+ page: 0,
29
+ },
30
+ itemCount: 0,
22
31
  });
23
32
 
24
33
  export const requestSuccessResponse = Immutable({
@@ -8,6 +8,7 @@ import settings from '../../scenes/Settings';
8
8
  import { subscriptionDetails } from '../../scenes/Subscriptions/Details';
9
9
  import { setOrganization } from '../../components/SelectOrg/SetOrganization';
10
10
  import { moduleStreams } from '../../scenes/ModuleStreams';
11
+ import { reducers as organizationProductsReducers } from '../OrganizationProducts';
11
12
  import { moduleStreamDetails } from '../../scenes/ModuleStreams/Details';
12
13
 
13
14
  export default combineReducers({
@@ -21,4 +22,5 @@ export default combineReducers({
21
22
  setOrganization,
22
23
  moduleStreams,
23
24
  moduleStreamDetails,
25
+ ...organizationProductsReducers,
24
26
  });
@@ -3,13 +3,16 @@ import React, { Component } from 'react';
3
3
  import { connect } from 'react-redux';
4
4
  import PropTypes from 'prop-types';
5
5
 
6
- import { Button } from 'patternfly-react';
7
6
  import { Form, FormGroup } from 'react-bootstrap';
8
7
 
8
+ import { selectOrganizationProducts }
9
+ from '../../../redux/OrganizationProducts/OrganizationProductsSelectors';
10
+ import { loadOrganizationProducts }
11
+ from '../../../redux/OrganizationProducts/OrganizationProductsActions';
12
+
9
13
  import { loadEnabledRepos } from '../../../redux/actions/RedHatRepositories/enabled';
10
14
  import { loadRepositorySets } from '../../../redux/actions/RedHatRepositories/sets';
11
15
 
12
- import api from '../../../services/api';
13
16
  import Search from './Search';
14
17
  import MultiSelect from '../../../components/MultiSelect/index';
15
18
 
@@ -37,6 +40,11 @@ class SearchBar extends Component {
37
40
  this.onSelectSearchList = this.onSelectSearchList.bind(this);
38
41
  }
39
42
 
43
+ componentDidMount() {
44
+ // load all products until we use filtering and pagination
45
+ this.props.loadOrganizationProducts({ per_page: 1000 });
46
+ }
47
+
40
48
  onSearch(query) {
41
49
  this.updateSearch({ query });
42
50
  }
@@ -49,6 +57,10 @@ class SearchBar extends Component {
49
57
  this.updateSearch({ filters });
50
58
  }
51
59
 
60
+ onSelectProduct(products) {
61
+ this.updateSearch({ products });
62
+ }
63
+
52
64
  updateSearch(stateUpdate = {}) {
53
65
  const newState = {
54
66
  ...this.state,
@@ -86,35 +98,48 @@ class SearchBar extends Component {
86
98
  }
87
99
 
88
100
  render() {
89
- const { repoParams } = this.props;
101
+ const { organizationProducts } = this.props;
102
+
103
+ const getMultiSelectValuesFromEvent = e => [...e.target.options]
104
+ .filter(({ selected }) => selected)
105
+ .map(({ value }) => value);
90
106
 
91
107
  return (
92
108
  <Form className="toolbar-pf-actions">
93
- <FormGroup className="toolbar-pf-filter">
94
- <Search onSearch={this.onSearch} onSelectSearchList={this.onSelectSearchList} />
95
- </FormGroup>
96
-
97
- <MultiSelect
98
- value={this.state.filters}
99
- options={filterOptions}
100
- defaultValues={['rpm']}
101
- noneSelectedText={__('Filter by type')}
102
- onChange={(e) => {
103
- const values = [...e.target.options]
104
- .filter(({ selected }) => selected)
105
- .map(({ value }) => value);
106
- this.onSelectFilterType(values);
107
- }}
108
- />
109
-
110
- <FormGroup>
111
- <Button
112
- className="export-csv-button"
113
- onClick={() => { api.open('/repositories.csv', repoParams); }}
114
- >
115
- {__('Export Enabled as CSV')}
116
- </Button>
117
- </FormGroup>
109
+ <div className="search-bar-row">
110
+ <FormGroup className="toolbar-pf-filter">
111
+ <Search onSearch={this.onSearch} onSelectSearchList={this.onSelectSearchList} />
112
+ </FormGroup>
113
+ </div>
114
+
115
+ <div className="search-bar-row search-bar-selects-row">
116
+ <MultiSelect
117
+ className="product-select"
118
+ value="product"
119
+ options={organizationProducts.map(product => ({
120
+ value: product.id, label: product.name,
121
+ }))}
122
+ defaultValues={[]}
123
+ noneSelectedText={__('Filter by Product')}
124
+ maxItemsCountForFullLabel={2}
125
+ onChange={(e) => {
126
+ const values = getMultiSelectValuesFromEvent(e);
127
+ this.onSelectProduct(values);
128
+ }}
129
+ />
130
+ <MultiSelect
131
+ value={this.state.filters}
132
+ options={filterOptions}
133
+ defaultValues={['rpm']}
134
+ noneSelectedText={__('Filter by type')}
135
+ onChange={(e) => {
136
+ const values = [...e.target.options]
137
+ .filter(({ selected }) => selected)
138
+ .map(({ value }) => value);
139
+ this.onSelectFilterType(values);
140
+ }}
141
+ />
142
+ </div>
118
143
  </Form>
119
144
  );
120
145
  }
@@ -123,7 +148,11 @@ class SearchBar extends Component {
123
148
  SearchBar.propTypes = {
124
149
  loadEnabledRepos: PropTypes.func.isRequired,
125
150
  loadRepositorySets: PropTypes.func.isRequired,
126
- repoParams: PropTypes.shape({}).isRequired,
151
+ loadOrganizationProducts: PropTypes.func.isRequired,
152
+ organizationProducts: PropTypes.arrayOf(PropTypes.shape({
153
+ id: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
154
+ name: PropTypes.string,
155
+ })).isRequired,
127
156
  enabledRepositories: PropTypes.shape({
128
157
  pagination: PropTypes.shape({
129
158
  perPage: PropTypes.number,
@@ -136,12 +165,18 @@ SearchBar.propTypes = {
136
165
  }).isRequired,
137
166
  };
138
167
 
139
- const mapStateToProps = ({ katello: { redHatRepositories: { enabled, sets } } }) => ({
140
- enabledRepositories: enabled,
141
- repositorySets: sets,
142
- });
168
+ const mapStateToProps = (state) => {
169
+ const { katello: { redHatRepositories: { enabled, sets } } } = state;
170
+
171
+ return {
172
+ enabledRepositories: enabled,
173
+ repositorySets: sets,
174
+ organizationProducts: selectOrganizationProducts(state),
175
+ };
176
+ };
143
177
 
144
178
  export default connect(mapStateToProps, {
145
179
  loadEnabledRepos,
146
180
  loadRepositorySets,
181
+ loadOrganizationProducts,
147
182
  })(SearchBar);
@@ -6,12 +6,14 @@ import React, { Component } from 'react';
6
6
  import PropTypes from 'prop-types';
7
7
  import { connect } from 'react-redux';
8
8
  import { Grid, Row, Col } from 'react-bootstrap';
9
+ import { Button } from 'patternfly-react';
9
10
  import { LoadingState } from '../../move_to_pf/LoadingState';
10
11
  import { createEnabledRepoParams, loadEnabledRepos } from '../../redux/actions/RedHatRepositories/enabled';
11
12
  import { loadRepositorySets, updateRecommendedRepositorySets } from '../../redux/actions/RedHatRepositories/sets';
12
13
  import SearchBar from './components/SearchBar';
13
14
  import RecommendedRepositorySetsToggler from './components/RecommendedRepositorySetsToggler';
14
15
  import { getSetsComponent, getEnabledComponent } from './helpers';
16
+ import api from '../../services/api';
15
17
 
16
18
  class RedHatRepositoriesPage extends Component {
17
19
  componentDidMount() {
@@ -32,7 +34,7 @@ class RedHatRepositoriesPage extends Component {
32
34
  <h1>{__('Red Hat Repositories')}</h1>
33
35
  <Row className="toolbar-pf">
34
36
  <Col sm={12}>
35
- <SearchBar repoParams={repoParams} />
37
+ <SearchBar />
36
38
  </Col>
37
39
  </Row>
38
40
 
@@ -60,7 +62,16 @@ class RedHatRepositoriesPage extends Component {
60
62
  </Col>
61
63
 
62
64
  <Col sm={6} className="enabled-repositories-container">
63
- <h2>{__('Enabled Repositories')}</h2>
65
+ <h2>
66
+ {__('Enabled Repositories')}
67
+ <Button
68
+ className="pull-right"
69
+ onClick={() => { api.open('/repositories.csv', repoParams); }}
70
+ >
71
+ {__('Export as CSV')}
72
+ </Button>
73
+ </h2>
74
+
64
75
  <LoadingState loading={enabledRepositories.loading} loadingText={__('Loading')}>
65
76
  {getEnabledComponent(
66
77
  enabledRepositories,
@@ -19,6 +19,32 @@
19
19
  .deemphasize {
20
20
  color: lightgray;
21
21
  }
22
+ .search-bar-row {
23
+ min-height: 26px;
24
+ margin-bottom: 10px;
25
+
26
+ .form-group {
27
+ box-sizing: border-box;
28
+
29
+ &:first-child {
30
+ padding-left: 0;
31
+ }
32
+ }
33
+ &.search-bar-selects-row {
34
+ .form-group {
35
+ border: none;
36
+
37
+ @media (min-width: 1280px) {
38
+ &:first-child {
39
+ min-width: 300px;
40
+ }
41
+ &:last-child {
42
+ min-width: 180px;
43
+ }
44
+ }
45
+ }
46
+ }
47
+ }
22
48
 
23
49
  .list-group-item-header .list-view-pf-description,
24
50
  .enabled-repositories-container .list-view-pf-description {
@@ -112,7 +112,7 @@ class ManageManifestModal extends Component {
112
112
  header: __('There is no Manifest History to display.'),
113
113
  description: __('Import a Manifest using the manifest tab above.'),
114
114
  documentation: {
115
- title: __('Learn more about adding Subscription Manifests'),
115
+ label: __('Learn more about adding Subscription Manifests'),
116
116
  url: 'http://redhat.com',
117
117
  },
118
118
  });
@@ -312,7 +312,7 @@ exports[`manage manifest modal should render 1`] = `
312
312
  Object {
313
313
  "description": "Import a Manifest using the manifest tab above.",
314
314
  "documentation": Object {
315
- "title": "Learn more about adding Subscription Manifests",
315
+ "label": "Learn more about adding Subscription Manifests",
316
316
  "url": "http://redhat.com",
317
317
  },
318
318
  "header": "There is no Manifest History to display.",
@@ -19,8 +19,13 @@ import {
19
19
  SUBSCRIPTION_TABLE_COLUMNS,
20
20
  SUBSCRIPTION_TABLE_DEFAULT_COLUMNS,
21
21
  SUBSCRIPTIONS_COLUMNS_REQUEST,
22
+ SUBSCRIPTIONS_UPDATE_SEARCH_QUERY,
23
+ SUBSCRIPTIONS_OPEN_MANIFEST_MODAL,
24
+ SUBSCRIPTIONS_CLOSE_MANIFEST_MODAL,
25
+ SUBSCRIPTIONS_OPEN_DELETE_MODAL,
26
+ SUBSCRIPTIONS_CLOSE_DELETE_MODAL,
22
27
  } from './SubscriptionConstants';
23
- import { filterRHSubscriptions } from './SubscriptionHelpers.js';
28
+ import { filterRHSubscriptions, selectSubscriptionsQuantitiesFromResponse } from './SubscriptionHelpers.js';
24
29
  import { apiError } from '../../move_to_foreman/common/helpers.js';
25
30
 
26
31
  export const createSubscriptionParams = (extendedParams = {}) => ({
@@ -37,7 +42,7 @@ export const loadAvailableQuantities = (extendedParams = {}) => (dispatch) => {
37
42
  .then(({ data }) => {
38
43
  dispatch({
39
44
  type: SUBSCRIPTIONS_QUANTITIES_SUCCESS,
40
- response: data,
45
+ payload: selectSubscriptionsQuantitiesFromResponse(data),
41
46
  });
42
47
  })
43
48
  .catch(result => dispatch(apiError(SUBSCRIPTIONS_QUANTITIES_FAILURE, result)));
@@ -120,4 +125,15 @@ export const deleteSubscriptions = poolIds => (dispatch) => {
120
125
  .catch(result => dispatch(apiError(DELETE_SUBSCRIPTIONS_FAILURE, result)));
121
126
  };
122
127
 
128
+ export const updateSearchQuery = query => ({
129
+ type: SUBSCRIPTIONS_UPDATE_SEARCH_QUERY,
130
+ payload: query,
131
+ });
132
+
133
+ export const openManageManifestModal = () => ({ type: SUBSCRIPTIONS_OPEN_MANIFEST_MODAL });
134
+ export const closeManageManifestModal = () => ({ type: SUBSCRIPTIONS_CLOSE_MANIFEST_MODAL });
135
+
136
+ export const openDeleteModal = () => ({ type: SUBSCRIPTIONS_OPEN_DELETE_MODAL });
137
+ export const closeDeleteModal = () => ({ type: SUBSCRIPTIONS_CLOSE_DELETE_MODAL });
138
+
123
139
  export default loadSubscriptions;
@@ -19,6 +19,14 @@ export const DELETE_SUBSCRIPTIONS_FAILURE = 'DELETE_SUBSCRIPTIONS_FAILURE';
19
19
  export const SUBSCRIPTIONS_COLUMNS_REQUEST = 'SUBSCRIPTIONS_COLUMNS_REQUEST';
20
20
  export const UPDATE_SUBSCRIPTION_COLUMNS = 'UPDATE_SUBSCRIPTION_COLUMNS';
21
21
 
22
+ export const SUBSCRIPTIONS_UPDATE_SEARCH_QUERY = 'SUBSCRIPTIONS_UPDATE_SEARCH_QUERY';
23
+
24
+ export const SUBSCRIPTIONS_OPEN_MANIFEST_MODAL = 'SUBSCRIPTIONS_OPEN_MANIFEST_MODAL';
25
+ export const SUBSCRIPTIONS_CLOSE_MANIFEST_MODAL = 'SUBSCRIPTIONS_CLOSE_MANIFEST_MODAL';
26
+
27
+ export const SUBSCRIPTIONS_OPEN_DELETE_MODAL = 'SUBSCRIPTIONS_OPEN_DELETE_MODAL';
28
+ export const SUBSCRIPTIONS_CLOSE_DELETE_MODAL = 'SUBSCRIPTIONS_CLOSE_DELETE_MODAL';
29
+
22
30
  export const BLOCKING_FOREMAN_TASK_TYPES = [
23
31
  'Actions::Katello::Organization::ManifestImport',
24
32
  'Actions::Katello::Organization::ManifestRefresh',
@@ -5,3 +5,18 @@ export const filterRHSubscriptions = subscriptions =>
5
5
 
6
6
  export const manifestExists = organization =>
7
7
  organization.owner_details && organization.owner_details.upstreamConsumer;
8
+
9
+ export const selectSubscriptionsQuantitiesFromResponse = ({ results }) => {
10
+ const quantityMap = {};
11
+
12
+ results.forEach(pool =>
13
+ pool.local_pool_ids &&
14
+ pool.local_pool_ids.forEach((localId) => {
15
+ if (quantityMap[localId]) {
16
+ quantityMap[localId] += pool.available;
17
+ } else {
18
+ quantityMap[localId] = pool.available;
19
+ }
20
+ }));
21
+ return quantityMap;
22
+ };
@@ -17,11 +17,19 @@ import {
17
17
  DELETE_SUBSCRIPTIONS_REQUEST,
18
18
  DELETE_SUBSCRIPTIONS_SUCCESS,
19
19
  DELETE_SUBSCRIPTIONS_FAILURE,
20
+ SUBSCRIPTIONS_UPDATE_SEARCH_QUERY,
21
+ SUBSCRIPTIONS_OPEN_MANIFEST_MODAL,
22
+ SUBSCRIPTIONS_CLOSE_MANIFEST_MODAL,
23
+ SUBSCRIPTIONS_OPEN_DELETE_MODAL,
24
+ SUBSCRIPTIONS_CLOSE_DELETE_MODAL,
20
25
  } from './SubscriptionConstants';
21
26
  import { GET_SETTING_SUCCESS } from '../../move_to_foreman/Settings/SettingsConstants';
22
27
 
23
28
  const initialState = Immutable({
24
29
  ...initialApiState,
30
+ searchQuery: '',
31
+ manifestModalOpened: false,
32
+ deleteModalOpened: false,
25
33
  quantitiesLoading: false,
26
34
  availableQuantities: null,
27
35
  tasks: [],
@@ -29,19 +37,6 @@ const initialState = Immutable({
29
37
  selectedTableColumns: [],
30
38
  });
31
39
 
32
- const mapQuantities = (pools) => {
33
- const quantityMap = {};
34
- pools.forEach(pool =>
35
- pool.local_pool_ids && pool.local_pool_ids.forEach((localId) => {
36
- if (quantityMap[localId]) {
37
- quantityMap[localId] += pool.available;
38
- } else {
39
- quantityMap[localId] = pool.available;
40
- }
41
- }));
42
- return quantityMap;
43
- };
44
-
45
40
  export default (state = initialState, action) => {
46
41
  switch (action.type) {
47
42
  case SUBSCRIPTIONS_REQUEST:
@@ -100,7 +95,7 @@ export default (state = initialState, action) => {
100
95
  case SUBSCRIPTIONS_QUANTITIES_SUCCESS: {
101
96
  return state.merge({
102
97
  quantitiesLoading: false,
103
- availableQuantities: mapQuantities(action.response.results),
98
+ availableQuantities: action.payload,
104
99
  });
105
100
  }
106
101
 
@@ -139,6 +134,19 @@ export default (state = initialState, action) => {
139
134
  return state;
140
135
  }
141
136
 
137
+ case SUBSCRIPTIONS_UPDATE_SEARCH_QUERY:
138
+ return state.set('searchQuery', action.payload);
139
+
140
+ case SUBSCRIPTIONS_OPEN_MANIFEST_MODAL:
141
+ return state.set('manifestModalOpened', true);
142
+ case SUBSCRIPTIONS_CLOSE_MANIFEST_MODAL:
143
+ return state.set('manifestModalOpened', false);
144
+
145
+ case SUBSCRIPTIONS_OPEN_DELETE_MODAL:
146
+ return state.set('deleteModalOpened', true);
147
+ case SUBSCRIPTIONS_CLOSE_DELETE_MODAL:
148
+ return state.set('deleteModalOpened', false);
149
+
142
150
  default:
143
151
  return state;
144
152
  }