hyrax 3.0.2 → 3.1.0

Sign up to get free protection for your applications and to get access to all the features.
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]