hyrax 3.0.2 → 3.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (162) hide show
  1. checksums.yaml +4 -4
  2. data/.circleci/config.yml +22 -0
  3. data/.dassie/Gemfile +10 -5
  4. data/.dassie/config/initializers/hyrax.rb +5 -0
  5. data/.dockerignore +3 -0
  6. data/.env +0 -1
  7. data/.rubocop.yml +4 -0
  8. data/CONTAINERS.md +1 -1
  9. data/Dockerfile +12 -6
  10. data/Gemfile +21 -27
  11. data/app/actors/hyrax/actors/base_actor.rb +1 -1
  12. data/app/actors/hyrax/actors/create_with_remote_files_actor.rb +85 -63
  13. data/app/actors/hyrax/actors/create_with_remote_files_ordered_members_actor.rb +7 -42
  14. data/app/controllers/concerns/hyrax/collections_controller_behavior.rb +20 -8
  15. data/app/controllers/concerns/hyrax/embargoes_controller_behavior.rb +21 -9
  16. data/app/controllers/concerns/hyrax/leases_controller_behavior.rb +14 -5
  17. data/app/controllers/concerns/hyrax/works_controller_behavior.rb +22 -3
  18. data/app/controllers/hyrax/admin/workflows_controller.rb +8 -2
  19. data/app/controllers/hyrax/dashboard/collection_members_controller.rb +13 -9
  20. data/app/controllers/hyrax/dashboard/collections_controller.rb +12 -10
  21. data/app/controllers/hyrax/file_sets_controller.rb +49 -13
  22. data/app/controllers/hyrax/permissions_controller.rb +3 -4
  23. data/app/controllers/hyrax/workflow_actions_controller.rb +3 -1
  24. data/app/forms/hyrax/forms/collection_form.rb +7 -3
  25. data/app/forms/hyrax/forms/dashboard/nest_collection_form.rb +24 -2
  26. data/app/forms/hyrax/forms/file_set_form.rb +46 -0
  27. data/app/forms/hyrax/forms/permission.rb +23 -0
  28. data/app/forms/hyrax/forms/permission_template_form.rb +8 -2
  29. data/app/forms/hyrax/forms/resource_form.rb +10 -17
  30. data/app/forms/hyrax/forms/work_form.rb +5 -2
  31. data/app/helpers/hyrax/batch_edits_helper.rb +3 -1
  32. data/app/helpers/hyrax/collections_helper.rb +88 -2
  33. data/app/helpers/hyrax/dashboard_helper_behavior.rb +3 -7
  34. data/app/helpers/hyrax/file_set_helper.rb +25 -6
  35. data/app/helpers/hyrax/work_form_helper.rb +53 -0
  36. data/app/indexers/hyrax/administrative_set_indexer.rb +18 -0
  37. data/app/indexers/hyrax/valkyrie_indexer.rb +3 -3
  38. data/app/inputs/controlled_vocabulary_input.rb +2 -5
  39. data/app/jobs/attach_files_to_work_job.rb +19 -10
  40. data/app/jobs/attach_files_to_work_with_ordered_members_job.rb +6 -5
  41. data/app/jobs/inherit_permissions_job.rb +9 -5
  42. data/app/models/admin_set.rb +6 -25
  43. data/app/models/concerns/hyrax/ability.rb +3 -1
  44. data/app/models/concerns/hyrax/collection_behavior.rb +17 -44
  45. data/app/models/concerns/hyrax/file_set/characterization.rb +18 -12
  46. data/app/models/concerns/hyrax/solr_document_behavior.rb +9 -52
  47. data/app/models/concerns/hyrax/suppressible.rb +5 -0
  48. data/app/models/concerns/hyrax/user.rb +9 -3
  49. data/app/models/hyrax/file_set.rb +6 -0
  50. data/app/models/hyrax/pcdm_collection.rb +1 -0
  51. data/app/models/hyrax/permission_template.rb +98 -12
  52. data/app/models/hyrax/virus_scanner.rb +27 -18
  53. data/app/models/sipity/agent.rb +1 -0
  54. data/app/models/sipity/entity.rb +30 -8
  55. data/app/models/sipity/workflow.rb +1 -0
  56. data/app/models/sipity.rb +42 -0
  57. data/app/presenters/hyrax/admin_set_options_presenter.rb +2 -10
  58. data/app/presenters/hyrax/admin_set_presenter.rb +5 -1
  59. data/app/presenters/hyrax/admin_set_selection_presenter.rb +116 -0
  60. data/app/presenters/hyrax/collection_presenter.rb +31 -6
  61. data/app/presenters/hyrax/file_set_presenter.rb +6 -1
  62. data/app/presenters/hyrax/file_usage.rb +3 -2
  63. data/app/presenters/hyrax/stats_usage_presenter.rb +2 -1
  64. data/app/presenters/hyrax/trophy_presenter.rb +33 -4
  65. data/app/presenters/hyrax/user_profile_presenter.rb +11 -1
  66. data/app/presenters/hyrax/version_list_presenter.rb +19 -0
  67. data/app/presenters/hyrax/version_presenter.rb +3 -2
  68. data/app/presenters/hyrax/work_show_presenter.rb +25 -4
  69. data/app/presenters/hyrax/work_usage.rb +5 -3
  70. data/app/renderers/hyrax/renderers/attribute_renderer.rb +10 -2
  71. data/app/search_builders/hyrax/admin_set_search_builder.rb +1 -1
  72. data/app/search_builders/hyrax/my/collections_search_builder.rb +1 -1
  73. data/app/services/hyrax/admin_set_create_service.rb +3 -1
  74. data/app/services/hyrax/collections/collection_member_search_service.rb +72 -0
  75. data/app/services/hyrax/collections/collection_member_service.rb +112 -27
  76. data/app/services/hyrax/collections/migration_service.rb +4 -2
  77. data/app/services/hyrax/collections/nested_collection_persistence_service.rb +12 -13
  78. data/app/services/hyrax/collections/nested_collection_query_service.rb +2 -0
  79. data/app/services/hyrax/collections/permissions_create_service.rb +6 -4
  80. data/app/services/hyrax/contextual_path.rb +23 -0
  81. data/app/services/hyrax/custom_queries/find_file_metadata.rb +7 -5
  82. data/app/services/hyrax/custom_queries/navigators/parent_collections_navigator.rb +46 -0
  83. data/app/services/hyrax/edit_permissions_service.rb +27 -20
  84. data/app/services/hyrax/find_objects_via_solr_service.rb +11 -7
  85. data/app/services/hyrax/multiple_membership_checker.rb +51 -31
  86. data/app/services/hyrax/resource_status.rb +7 -0
  87. data/app/services/hyrax/search_service.rb +4 -2
  88. data/app/services/hyrax/solr_query_builder_service.rb +29 -6
  89. data/app/services/hyrax/solr_query_service.rb +224 -0
  90. data/app/services/hyrax/solr_service.rb +8 -1
  91. data/app/services/hyrax/statistics/depositors/summary.rb +2 -1
  92. data/app/services/hyrax/work_uploads_handler.rb +17 -2
  93. data/app/services/hyrax/workflow/actionable_objects.rb +70 -0
  94. data/app/services/hyrax/workflow/object_in_workflow_decorator.rb +31 -0
  95. data/app/services/hyrax/workflow/status_list_service.rb +43 -13
  96. data/app/views/hyrax/base/_form_relationships.html.erb +1 -2
  97. data/app/views/hyrax/base/_form_rendering.html.erb +1 -1
  98. data/app/views/hyrax/base/_form_representative.html.erb +1 -1
  99. data/app/views/hyrax/base/_form_thumbnail.html.erb +1 -1
  100. data/app/views/hyrax/base/_guts4form.html.erb +2 -2
  101. data/app/views/hyrax/base/_representative_media.html.erb +1 -1
  102. data/app/views/hyrax/base/_show_actions.html.erb +1 -1
  103. data/app/views/hyrax/dashboard/collections/_form.html.erb +3 -3
  104. data/app/views/hyrax/dashboard/collections/_list_collections.html.erb +1 -1
  105. data/app/views/hyrax/dashboard/collections/edit.html.erb +4 -2
  106. data/app/views/hyrax/dashboard/collections/new.html.erb +4 -2
  107. data/app/views/hyrax/dashboard/collections/show.html.erb +1 -1
  108. data/app/views/hyrax/file_sets/edit.html.erb +1 -1
  109. data/app/views/hyrax/file_sets/media_display/_audio.html.erb +1 -1
  110. data/app/views/hyrax/file_sets/media_display/_default.html.erb +1 -1
  111. data/app/views/hyrax/file_sets/media_display/_image.html.erb +1 -1
  112. data/app/views/hyrax/file_sets/media_display/_office_document.html.erb +1 -1
  113. data/app/views/hyrax/file_sets/media_display/_pdf.html.erb +1 -1
  114. data/app/views/hyrax/file_sets/media_display/_video.html.erb +1 -1
  115. data/app/views/hyrax/file_sets/show.html.erb +1 -1
  116. data/app/views/hyrax/my/_admin_set_action_menu.html.erb +0 -11
  117. data/app/views/hyrax/my/_collection_action_menu.html.erb +1 -2
  118. data/app/views/hyrax/my/collections/_list_collections.html.erb +1 -1
  119. data/app/views/hyrax/my/collections/_modal_add_subcollection.html.erb +3 -5
  120. data/bin/solrcloud-assign-configset.sh +8 -5
  121. data/bin/solrcloud-upload-configset.sh +4 -2
  122. data/chart/hyrax/Chart.yaml +3 -3
  123. data/chart/hyrax/README.md +47 -1
  124. data/chart/hyrax/templates/_helpers.tpl +1 -1
  125. data/chart/hyrax/templates/configmap-env.yaml +1 -3
  126. data/chart/hyrax/templates/deployment-worker.yaml +6 -3
  127. data/chart/hyrax/templates/deployment.yaml +8 -3
  128. data/chart/hyrax/values.yaml +12 -0
  129. data/config/brakeman.ignore +2 -2
  130. data/config/locales/hyrax.de.yml +1 -1
  131. data/config/locales/hyrax.en.yml +1 -1
  132. data/config/locales/hyrax.es.yml +1 -1
  133. data/config/locales/hyrax.fr.yml +1 -1
  134. data/config/locales/hyrax.it.yml +1 -1
  135. data/config/locales/hyrax.pt-BR.yml +1 -1
  136. data/config/locales/hyrax.zh.yml +1 -1
  137. data/docker-compose.yml +1 -0
  138. data/documentation/developing-your-hyrax-based-app.md +1 -1
  139. data/documentation/legacyREADME.md +1 -1
  140. data/lib/generators/hyrax/templates/config/initializers/hyrax.rb +5 -0
  141. data/lib/hyrax/active_fedora_dummy_model.rb +62 -0
  142. data/lib/hyrax/configuration.rb +8 -0
  143. data/lib/hyrax/engine.rb +1 -0
  144. data/lib/hyrax/errors.rb +2 -0
  145. data/lib/hyrax/specs/capybara.rb +3 -1
  146. data/lib/hyrax/specs/shared_specs/valkyrie_storage_versions.rb +9 -0
  147. data/lib/hyrax/transactions/container.rb +21 -0
  148. data/lib/hyrax/transactions/file_set_destroy.rb +21 -0
  149. data/lib/hyrax/transactions/steps/add_file_sets.rb +3 -2
  150. data/lib/hyrax/transactions/steps/add_to_parent.rb +36 -0
  151. data/lib/hyrax/transactions/steps/remove_file_set_from_work.rb +47 -0
  152. data/lib/hyrax/transactions/work_create.rb +2 -1
  153. data/lib/hyrax/valkyrie_can_can_adapter.rb +1 -0
  154. data/lib/hyrax/version.rb +1 -1
  155. data/lib/hyrax.rb +9 -0
  156. data/lib/tasks/collection_type_global_id.rake +1 -1
  157. data/lib/tasks/regenerate_derivatives.rake +12 -0
  158. data/lib/wings/orm_converter.rb +18 -2
  159. data/lib/wings/setup.rb +1 -0
  160. data/lib/wings/valkyrie/storage.rb +56 -1
  161. data/template.rb +1 -1
  162. metadata +17 -2
@@ -3,7 +3,7 @@ module Hyrax
3
3
  module Collections
4
4
  ##
5
5
  # Retrieves collection members
6
- class CollectionMemberService < Hyrax::SearchService
6
+ class CollectionMemberService
7
7
  ##
8
8
  # @param scope [#repository] Typically a controller object which responds to :repository
9
9
  # @param [::Collection] collection
@@ -12,14 +12,14 @@ module Hyrax
12
12
  # @param [::Ability] current_ability
13
13
  # @param [Class] search_builder_class a {::SearchBuilder}
14
14
  def initialize(scope:, collection:, params:, user_params: nil, current_ability: nil, search_builder_class: Hyrax::CollectionMemberSearchBuilder) # rubocop:disable Metrics/ParameterLists
15
- super(
16
- config: scope.blacklight_config,
17
- user_params: user_params || params,
18
- collection: collection,
19
- scope: scope,
20
- current_ability: current_ability || scope.current_ability,
21
- search_builder_class: search_builder_class
22
- )
15
+ Deprecation.warn("'##{__method__}' will be removed in Hyrax 4.0. " \
16
+ "Instead, use the same method in 'Hyrax::Collections::CollectionMemberSearchService'.")
17
+ @member_search_service = Hyrax::Collections::CollectionMemberSearchService(scope: scope,
18
+ collection: collection,
19
+ params: params,
20
+ user_params: user_params,
21
+ current_ability: current_ability,
22
+ search_builder_class: search_builder_class)
23
23
  end
24
24
 
25
25
  ##
@@ -29,14 +29,9 @@ module Hyrax
29
29
  #
30
30
  # @return [Blacklight::Solr::Response] (up to 50 solr documents)
31
31
  def available_member_subcollections
32
- response, _docs = search_results do |builder|
33
- # To differentiate current page for works vs subcollections, we have to use a sub_collection_page
34
- # param. Map this to the page param before querying for subcollections, if it's present
35
- builder.page(user_params[:sub_collection_page])
36
- builder.search_includes_models = :collections
37
- builder
38
- end
39
- response
32
+ Deprecation.warn("'##{__method__}' will be removed in Hyrax 4.0. " \
33
+ "Instead, use the same method in 'Hyrax::Collections::CollectionMemberSearchService'.")
34
+ @member_search_service.available_member_subcollections
40
35
  end
41
36
 
42
37
  ##
@@ -46,11 +41,9 @@ module Hyrax
46
41
  #
47
42
  # @return [Blacklight::Solr::Response]
48
43
  def available_member_works
49
- response, _docs = search_results do |builder|
50
- builder.search_includes_models = :works
51
- builder
52
- end
53
- response
44
+ Deprecation.warn("'##{__method__}' will be removed in Hyrax 4.0. " \
45
+ "Instead, use the same method in 'Hyrax::Collections::CollectionMemberSearchService'.")
46
+ @member_search_service.available_member_works
54
47
  end
55
48
 
56
49
  ##
@@ -60,12 +53,104 @@ module Hyrax
60
53
  #
61
54
  # @return [Blacklight::Solr::Response]
62
55
  def available_member_work_ids
63
- response, _docs = search_results do |builder|
64
- builder.search_includes_models = :works
65
- builder.merge(fl: 'id')
66
- builder
56
+ Deprecation.warn("'##{__method__}' will be removed in Hyrax 4.0. " \
57
+ "Instead, use the same method in 'Hyrax::Collections::CollectionMemberSearchService'.")
58
+ @member_search_service.available_member_work_ids
59
+ end
60
+
61
+ class << self
62
+ # Check if a work or collection is already a member of a collection
63
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
64
+ # @param member [Hyrax::Resource] the child collection and/or child work to check
65
+ # @return [Boolean] true if already in the member set; otherwise, false
66
+ def member?(collection_id:, member:)
67
+ member.member_of_collection_ids.include? collection_id
68
+ end
69
+
70
+ # Add works and/or collections as members of a collection
71
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
72
+ # @param new_member_ids [Enumerable<Valkyrie::ID>] the ids of the new child collections and/or child works
73
+ # @return [Enumerable<Hyrax::Resource>] updated member resources
74
+ def add_members_by_ids(collection_id:, new_member_ids:, user:)
75
+ new_members = Hyrax.query_service.find_many_by_ids(ids: new_member_ids)
76
+ add_members(collection_id: collection_id, new_members: new_members, user: user)
77
+ end
78
+
79
+ # Add works and/or collections as members of a collection
80
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
81
+ # @param new_members [Enumerable<Hyrax::Resource>] the new child collections and/or child works
82
+ # @return [Enumerable<Hyrax::Resource>] updated member resources
83
+ def add_members(collection_id:, new_members:, user:)
84
+ messages = []
85
+ new_members.map do |new_member|
86
+ begin
87
+ add_member(collection_id: collection_id, new_member: new_member, user: user)
88
+ rescue Hyrax::SingleMembershipError => err
89
+ messages += [err.message]
90
+ end
91
+ end
92
+ raise Hyrax::SingleMembershipError, messages if messages.present?
93
+ end
94
+
95
+ # Add a work or collection as a member of a collection
96
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
97
+ # @param new_member_id [Valkyrie::ID] the id of the new child collection or child work
98
+ # @return [Hyrax::Resource] updated member resource
99
+ def add_member_by_id(collection_id:, new_member_id:, user:)
100
+ new_member = Hyrax.query_service.find_by(id: new_member_id)
101
+ add_member(collection_id: collection_id, new_member: new_member, user: user)
102
+ end
103
+
104
+ # Add a work or collection as a member of a collection
105
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
106
+ # @param new_member [Hyrax::Resource] the new child collection or child work
107
+ # @return [Hyrax::Resource] updated member resource
108
+ def add_member(collection_id:, new_member:, user:)
109
+ message = Hyrax::MultipleMembershipChecker.new(item: new_member).check(collection_ids: [collection_id], include_current_members: true)
110
+ raise Hyrax::SingleMembershipError, message if message.present?
111
+ new_member.member_of_collection_ids << collection_id # only populate this direction
112
+ new_member = Hyrax.persister.save(resource: new_member)
113
+ Hyrax.publisher.publish('object.metadata.updated', object: new_member, user: user)
114
+ new_member
115
+ end
116
+
117
+ # Remove collections and/or works from the members set of a collection
118
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
119
+ # @param member_ids [Enumerable<Valkyrie::ID>] the ids of the child collections and/or child works to be removed
120
+ # @return [Enumerable<Hyrax::Resource>] updated member resources
121
+ def remove_members_by_ids(collection_id:, member_ids:, user:)
122
+ members = Hyrax.query_service.find_many_by_ids(ids: member_ids)
123
+ remove_members(collection_id: collection_id, members: members, user: user)
124
+ end
125
+
126
+ # Remove collections and/or works from the members set of a collection
127
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
128
+ # @param members [Enumerable<Valkyrie::Resource>] the child collections and/or child works to be removed
129
+ # @return [Enumerable<Hyrax::Resource>] updated member resources
130
+ def remove_members(collection_id:, members:, user:)
131
+ members.map { |member| remove_member(collection_id: collection_id, member: member, user: user) }
132
+ end
133
+
134
+ # Remove collections and/or works from the members set of a collection
135
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
136
+ # @param member_id [Valkyrie::ID] the id of the child collection or child work to be removed
137
+ # @return [Hyrax::Resource] updated member resource
138
+ def remove_member_by_id(collection_id:, member_id:, user:)
139
+ member = Hyrax.query_service.find_by(id: member_id)
140
+ remove_member(collection_id: collection_id, member: member, user: user)
141
+ end
142
+
143
+ # Remove a collection or work from the members set of a collection, also removing the inverse relationship
144
+ # @param collection_id [Valkyrie::ID] the id of the parent collection
145
+ # @param member [Hyrax::Resource] the child collection or child work to be removed
146
+ # @return [Hyrax::Resource] updated member resource
147
+ def remove_member(collection_id:, member:, user:)
148
+ return member unless member?(collection_id: collection_id, member: member)
149
+ member.member_of_collection_ids.delete(collection_id)
150
+ member = Hyrax.persister.save(resource: member)
151
+ Hyrax.publisher.publish('object.metadata.updated', object: member, user: user)
152
+ member
67
153
  end
68
- response
69
154
  end
70
155
  end
71
156
  end
@@ -40,6 +40,7 @@ module Hyrax
40
40
  end
41
41
  private_class_method :migrate_collection
42
42
 
43
+ ##
43
44
  # @api private
44
45
  #
45
46
  # Migrate a single adminset to grant depositors and viewers read access to the admin set unless the grant is for
@@ -50,7 +51,8 @@ module Hyrax
50
51
  def self.migrate_adminset(adminset)
51
52
  Hyrax::PermissionTemplateAccess.find_or_create_by(permission_template_id: adminset.permission_template.id,
52
53
  agent_type: "group", agent_id: "admin", access: "manage")
53
- adminset.reset_access_controls!
54
+
55
+ adminset.permission_template.reset_access_controls_for(collection: adminset)
54
56
  end
55
57
  private_class_method :migrate_adminset
56
58
 
@@ -84,7 +86,7 @@ module Hyrax
84
86
  collection.collection_type_gid = Hyrax::CollectionType.find_or_create_default_collection_type.to_global_id
85
87
  permission_template = Hyrax::PermissionTemplate.find_by(source_id: collection.id)
86
88
  if permission_template.present?
87
- collection.reset_access_controls!
89
+ permission_template.reset_access_controls_for(collection: collection, interpret_visibility: true)
88
90
  else
89
91
  create_permissions(collection)
90
92
  end
@@ -7,24 +7,23 @@ module Hyrax
7
7
  # Responsible for persisting the relationship between the parent and the child.
8
8
  # @see Hyrax::Collections::NestedCollectionQueryService
9
9
  #
10
- # @param parent [::Collection]
11
- # @param child [::Collection]
10
+ # @param parent [Hyrax::PcdmCollection | ::Collection]
11
+ # @param child [Hyrax::PcdmCollection | ::Collection]
12
+ # @param user [::User] current logged in user (defaults=nil for backward compatibility)
12
13
  # @note There is odd permission arrangement based on the NestedCollectionQueryService:
13
14
  # You can nest the child within a parent if you can edit the parent and read the child.
14
15
  # See https://wiki.lyrasis.org/display/samvera/Samvera+Tech+Call+2017-08-23 for tech discussion.
15
- # @note Adding the member_of_collections method doesn't trigger reindexing of the child so we have to do it manually.
16
- # However it save and reindexes the parent unnecessarily!!
17
- def self.persist_nested_collection_for(parent:, child:)
18
- parent.reindex_extent = Hyrax::Adapters::NestingIndexAdapter::LIMITED_REINDEX
19
- child.member_of_collections.push(parent)
20
- child.update_nested_collection_relationship_indices
16
+ def self.persist_nested_collection_for(parent:, child:, user: nil)
17
+ child_resource = child.respond_to?(:valkyrie_resource) ? child.valkyrie_resource : child
18
+ Hyrax::Collections::CollectionMemberService.add_member(collection_id: parent.id, new_member: child_resource, user: user)
21
19
  end
22
20
 
23
- # @note Removing the member_of_collections method doesn't trigger reindexing of the child so we have to do it manually.
24
- # However it doesn't save and reindex the parent, as it does when a parent is added!!
25
- def self.remove_nested_relationship_for(parent:, child:)
26
- child.member_of_collections.delete(parent)
27
- child.update_nested_collection_relationship_indices
21
+ # @param parent [Hyrax::PcdmCollection | ::Collection]
22
+ # @param child [Hyrax::PcdmCollection | ::Collection]
23
+ # @param user [::User] current logged in user (defaults=nil for backward compatibility)
24
+ def self.remove_nested_relationship_for(parent:, child:, user: nil)
25
+ child_resource = child.respond_to?(:valkyrie_resource) ? child.valkyrie_resource : child
26
+ Hyrax::Collections::CollectionMemberService.remove_member(collection_id: parent.id, member: child_resource, user: user)
28
27
  true
29
28
  end
30
29
  end
@@ -1,6 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
  module Hyrax
3
3
  module Collections
4
+ ##
5
+ # A query service handling nested collection queries.
4
6
  module NestedCollectionQueryService
5
7
  ##
6
8
  # @api private
@@ -13,9 +13,10 @@ module Hyrax
13
13
  def self.create_default(collection:, creating_user:, grants: [])
14
14
  collection_type = Hyrax::CollectionType.find_by_gid!(collection.collection_type_gid)
15
15
  access_grants = access_grants_attributes(collection_type: collection_type, creating_user: creating_user, grants: grants)
16
- PermissionTemplate.create!(source_id: collection.id,
17
- access_grants_attributes: access_grants.uniq)
18
- collection.reset_access_controls!
16
+ template = PermissionTemplate.create!(source_id: collection.id,
17
+ access_grants_attributes: access_grants.uniq)
18
+
19
+ template.reset_access_controls_for(collection: collection, interpret_visibility: true)
19
20
  end
20
21
 
21
22
  # @api public
@@ -38,7 +39,8 @@ module Hyrax
38
39
  agent_id: grant[:agent_id],
39
40
  access: grant[:access])
40
41
  end
41
- collection.reset_access_controls!
42
+
43
+ template.reset_access_controls_for(collection: collection, interpret_visibility: true)
42
44
  end
43
45
 
44
46
  # @api private
@@ -1,14 +1,37 @@
1
1
  # frozen_string_literal: true
2
2
  module Hyrax
3
+ ##
4
+ # @api public
5
+ #
6
+ # Provides a polymorphic path for a target object (presenter) nested under the
7
+ # path of the parent, if given.
8
+ #
9
+ # @see WorkShowPresenter#contextual_path
10
+ #
11
+ # @example
12
+ # Hyrax::ContextualPath.new(my_file_set, parent_object).show
13
+ # # => "/concerns/parent/id4parent/file_sets/id4file_set"
14
+ #
15
+ # @example with a nil parent
16
+ # Hyrax::ContextualPath.new(my_file_set, nil).show
17
+ # # => "/concerns/file_sets/id4file_set"
18
+ #
3
19
  class ContextualPath
4
20
  include Rails.application.routes.url_helpers
5
21
  include ActionDispatch::Routing::PolymorphicRoutes
6
22
  attr_reader :presenter, :parent_presenter
23
+
24
+ ##
25
+ # @param presenter [#model_name] an ActiveModel-like target object
26
+ # @param parent_presenter [#id, nil] an ActiveModel-like presenter for the
27
+ # target's parent
7
28
  def initialize(presenter, parent_presenter)
8
29
  @presenter = presenter
9
30
  @parent_presenter = parent_presenter
10
31
  end
11
32
 
33
+ ##
34
+ # @return [String]
12
35
  def show
13
36
  if parent_presenter
14
37
  polymorphic_path([:hyrax, :parent, presenter.model_name.singular.to_sym],
@@ -1,11 +1,13 @@
1
1
  # frozen_string_literal: true
2
- # Provide custom queries for finding Hyrax::FileMetadata
3
- # @example
4
- # Hyrax.custom_queries.find_file_metadata_by(id: valkyrie_id)
5
- # Hyrax.custom_queries.find_file_metadata_by_alternate_identifier(alternate_identifier: alt_id)
6
- # Hyrax.custom_queries.find_many_file_metadata_by_ids(ids: [valkyrie_id, valkyrie_id])
7
2
  module Hyrax
8
3
  module CustomQueries
4
+ ##
5
+ # Provide custom queries for finding Hyrax::FileMetadata
6
+ #
7
+ # @example
8
+ # Hyrax.custom_queries.find_file_metadata_by(id: valkyrie_id)
9
+ # Hyrax.custom_queries.find_file_metadata_by_alternate_identifier(alternate_identifier: alt_id)
10
+ # Hyrax.custom_queries.find_many_file_metadata_by_ids(ids: [valkyrie_id, valkyrie_id])
9
11
  class FindFileMetadata
10
12
  def self.queries
11
13
  [:find_file_metadata_by,
@@ -0,0 +1,46 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Hyrax
4
+ module CustomQueries
5
+ module Navigators
6
+ ##
7
+ # Navigate from a resource to the parent collections of the resource.
8
+ #
9
+ # @see https://github.com/samvera/valkyrie/wiki/Queries#custom-queries
10
+ # @since 3.0.0
11
+ class ParentCollectionsNavigator
12
+ # Define the queries that can be fulfilled by this navigator.
13
+ def self.queries
14
+ [:find_parent_collections, :find_parent_collection_ids]
15
+ end
16
+
17
+ attr_reader :query_service
18
+
19
+ def initialize(query_service:)
20
+ @query_service = query_service
21
+ end
22
+
23
+ ##
24
+ # Find parent collections of a given resource, and map to Valkyrie Resources
25
+ #
26
+ # @param [Valkyrie::Resource] resource
27
+ #
28
+ # @return [Array<Valkyrie::Resource>]
29
+ def find_parent_collections(resource:)
30
+ query_service
31
+ .find_many_by_ids(ids: find_parent_collection_ids(resource: resource))
32
+ end
33
+
34
+ ##
35
+ # Find the ids of parent collections of a given resource, and map to Valkyrie Resources IDs
36
+ #
37
+ # @param [Valkyrie::Resource] resource
38
+ #
39
+ # @return [Array<Valkyrie::ID>]
40
+ def find_parent_collection_ids(resource:)
41
+ resource.member_of_collection_ids
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
@@ -1,11 +1,15 @@
1
1
  # frozen_string_literal: true
2
2
  module Hyrax
3
+ ##
4
+ # @api public
5
+ #
3
6
  # Encapsulates the logic to determine which object permissions may be edited by a given user
4
- # - user is permitted to update any work permissions coming ONLY from collections they manage
5
- # - user is not permitted to update a work permission if it comes from a collection they do not manage, even if also from a managed collection
6
- # - user is permitted to update only non-manager permissions from any Collections
7
- # - user is permitted to update any non-collection permissions
7
+ # * user is permitted to update any work permissions coming ONLY from collections they manage
8
+ # * user is not permitted to update a work permission if it comes from a collection they do not manage, even if also from a managed collection
9
+ # * user is permitted to update only non-manager permissions from any Collections
10
+ # * user is permitted to update any non-collection permissions
8
11
  class EditPermissionsService
12
+ ##
9
13
  # @api public
10
14
  # @since v3.0.0
11
15
  #
@@ -14,15 +18,15 @@ module Hyrax
14
18
  # @return [Hyrax::EditPermissionService]
15
19
  #
16
20
  # @note
17
- # form object.class = SimpleForm::FormBuilder
18
- # For works (i.e. GenericWork):
19
- # - form object.object = Hyrax::GenericWorkForm
20
- # - form object.object.model = GenericWork
21
- # - use the work itself
22
- # For file_sets:
23
- # - form object.object.class = FileSet
24
- # - use work the file_set is in
25
- # No other object types are supported by this view. %>
21
+ # +form object.class = SimpleForm::FormBuilder+
22
+ # For works (i.e. GenericWork):
23
+ # * form object.object = Hyrax::GenericWorkForm
24
+ # * form object.object.model = GenericWork
25
+ # * use the work itself
26
+ # For file_sets:
27
+ # * form object.object.class = FileSet
28
+ # * use work the file_set is in
29
+ # No other object types are supported by this view.
26
30
  def self.build_service_object_from(form:, ability:)
27
31
  if form.object.respond_to?(:model) && form.object.model.work?
28
32
  new(object: form.object, ability: ability)
@@ -33,7 +37,9 @@ module Hyrax
33
37
 
34
38
  attr_reader :depositor, :unauthorized_collection_managers
35
39
 
36
- # @param object [#depositor, #admin_set_id, #member_of_collection_ids] GenericWorkForm (if called for object) or GenericWork (if called for file set)
40
+ ##
41
+ # @param object [#depositor, #admin_set_id, #member_of_collection_ids]
42
+ # +GenericWorkForm+ (if called for object) or +GenericWork+ (if called for file set)
37
43
  # @param ability [Ability] user's current_ability
38
44
  def initialize(object:, ability:)
39
45
  @object = object
@@ -47,7 +53,7 @@ module Hyrax
47
53
  # @api private
48
54
  # @todo refactor this code to use "can_edit?"; Thinking in negations can be challenging.
49
55
  #
50
- # @param permission_hash [Hash] one set of permission fields for object {:name, :access}
56
+ # @param permission_hash [Hash] one set of permission fields for object +:name+, :access}
51
57
  # @return [Boolean] true if user cannot edit the given permissions
52
58
  def cannot_edit_permissions?(permission_hash)
53
59
  permission_hash.fetch(:access) == "edit" && @unauthorized_managers.include?(permission_hash.fetch(:name))
@@ -55,7 +61,7 @@ module Hyrax
55
61
 
56
62
  # @api private
57
63
  #
58
- # @param permission_hash [Hash] one set of permission fields for object {:name, :access}
64
+ # @param permission_hash [Hash] one set of permission fields for object +:name+, +:access+
59
65
  # @return [Boolean] true if given permissions are one of fixed exclusions
60
66
  def excluded_permission?(permission_hash)
61
67
  exclude_from_display.include? permission_hash.fetch(:name).downcase
@@ -68,9 +74,10 @@ module Hyrax
68
74
  # * returns false if the given permission_hash is part of the fixed exclusions.
69
75
  # * yields a PermissionPresenter to provide additional logic and text for rendering
70
76
  #
71
- # @param permission_hash [Hash<:name, :access>]
72
- # @return false if the given permission_hash is a fixed exclusion
73
- # @yield PermissionPresenter
77
+ # @param permission_hash [Hash{Symbol => Object}]
78
+ #
79
+ # @return [Boolean] +false+ if the given +permission_hash+ is a fixed exclusion
80
+ # @yield [PermissionPresenter]
74
81
  #
75
82
  # @see #excluded_permission?
76
83
  def with_applicable_permission(permission_hash:)
@@ -81,7 +88,7 @@ module Hyrax
81
88
  # @api private
82
89
  #
83
90
  # A helper class to contain specific presentation logic related to
84
- # the EditPermissionsService
91
+ # the {EditPermissionsService}
85
92
  class PermissionPresenter
86
93
  # @param service [Hyrax::EditPermissionsService]
87
94
  # @param permission_hash [Hash]