diff --git a/app/graphql/mutations/update_event.rb b/app/graphql/mutations/update_event.rb index 44303883832..a66672af6bd 100644 --- a/app/graphql/mutations/update_event.rb +++ b/app/graphql/mutations/update_event.rb @@ -39,16 +39,16 @@ def apply_registration_policy(event, registration_policy_attributes, bucket_key_ end # EventChangeRegistrationPolicyService still works entirely in terms of from_key/to_key (see the - # comment on that service). This resolves incoming from_bucket_id/to_bucket_id args (only usable - # when the destination bucket already exists, since a bucket being newly created in this same - # edit has no id yet) down to that shape. + # comment on that service). This resolves incoming from_bucket_id/to_bucket_id args down to that + # shape -- to_bucket_id is only usable when the destination bucket already exists, since a + # bucket being newly created in this same edit has no id yet, so to_key is still accepted too. def resolve_bucket_key_mappings(event, bucket_key_mappings) (bucket_key_mappings || []).map { |mapping| resolve_bucket_key_mapping(event, mapping.to_h) } end def resolve_bucket_key_mapping(event, mapping) { - from_key: mapping[:from_key] || bucket_key_for_id(event, mapping[:from_bucket_id]), + from_key: bucket_key_for_id(event, mapping[:from_bucket_id]), to_key: mapping[:to_key] || bucket_key_for_id(event, mapping[:to_bucket_id]) } end diff --git a/app/graphql/types/bucket_key_mapping_input_type.rb b/app/graphql/types/bucket_key_mapping_input_type.rb index fa5690b21b3..02da6024059 100644 --- a/app/graphql/types/bucket_key_mapping_input_type.rb +++ b/app/graphql/types/bucket_key_mapping_input_type.rb @@ -7,12 +7,6 @@ class Types::BucketKeyMappingInputType < Types::BaseInputObject required: false, camelize: true, description: "The id of the old bucket being removed or changed" - argument :from_key, - String, - required: false, - camelize: false, - deprecation_reason: "Use from_bucket_id instead", - description: "The old bucket key being removed or changed" argument :to_bucket_id, ID, required: false, camelize: true, description: <<~MARKDOWN The id of the new bucket to map to (nil means no preference). Only usable when mapping to a bucket that already exists -- mapping to a bucket being newly created in the same diff --git a/app/graphql/types/registration_policy_bucket_input_type.rb b/app/graphql/types/registration_policy_bucket_input_type.rb deleted file mode 100644 index e91077a4ee1..00000000000 --- a/app/graphql/types/registration_policy_bucket_input_type.rb +++ /dev/null @@ -1,13 +0,0 @@ -# frozen_string_literal: true -class Types::RegistrationPolicyBucketInputType < Types::BaseInputObject - argument :anything, Boolean, required: false - argument :description, String, required: false - argument :expose_attendees, Boolean, required: false, camelize: false - argument :key, String, required: true - argument :minimum_slots, Integer, required: false, camelize: false - argument :name, String, required: false - argument :not_counted, Boolean, required: false, camelize: false - argument :preferred_slots, Integer, required: false, camelize: false - argument :slots_limited, Boolean, required: false, camelize: false - argument :total_slots, Integer, required: false, camelize: false -end diff --git a/app/graphql/types/registration_policy_bucket_type.rb b/app/graphql/types/registration_policy_bucket_type.rb index c65f4584ee9..2493a761315 100644 --- a/app/graphql/types/registration_policy_bucket_type.rb +++ b/app/graphql/types/registration_policy_bucket_type.rb @@ -4,7 +4,11 @@ class Types::RegistrationPolicyBucketType < Types::BaseObject field :description, String, null: true, description: "A long-form description for the bucket" field :id, ID, null: false, description: "The ID of this bucket" - field :key, String, null: false, description: "The unique string identifier for this bucket" + field :key, + String, + null: false, + deprecation_reason: "Use id instead", + description: "The unique string identifier for this bucket" field :minimum_slots, Integer, null: true, description: "The minimum number of attendees needed for this bucket" field :name, String, null: false, description: "The name of this bucket" field :preferred_slots, Integer, null: true, description: "The preferred number of attendees for this bucket" diff --git a/app/graphql/types/registration_policy_input_type.rb b/app/graphql/types/registration_policy_input_type.rb deleted file mode 100644 index 6ac3864d5ba..00000000000 --- a/app/graphql/types/registration_policy_input_type.rb +++ /dev/null @@ -1,5 +0,0 @@ -# frozen_string_literal: true -class Types::RegistrationPolicyInputType < Types::BaseInputObject - argument :buckets, [Types::RegistrationPolicyBucketInputType], required: false - argument :prevent_no_preference_signups, Boolean, required: false, camelize: false -end diff --git a/app/javascript/EventAdmin/BucketKeyRemappingModal.tsx b/app/javascript/EventAdmin/BucketKeyRemappingModal.tsx index 27b40623cf3..2c5aeecae2c 100644 --- a/app/javascript/EventAdmin/BucketKeyRemappingModal.tsx +++ b/app/javascript/EventAdmin/BucketKeyRemappingModal.tsx @@ -10,9 +10,13 @@ type BucketOption = { name?: string | null; }; +// A removed bucket is always a persisted row, so it always has a real id -- unlike a bucket in +// newPolicyBuckets, which might have been added in the current, not-yet-saved edit. +type RemovedBucketOption = BucketOption & { id: string }; + export type BucketKeyRemappingModalProps = { visible: boolean; - removedBuckets: BucketOption[]; + removedBuckets: RemovedBucketOption[]; newPolicyBuckets: BucketOption[]; preventNoPreferenceSignups: boolean; onConfirm: (mappings: BucketKeyMappingInput[]) => Promise; @@ -42,22 +46,22 @@ function BucketKeyRemappingModal({ const [prevRemovedBuckets, setPrevRemovedBuckets] = useState(removedBuckets); if (prevRemovedBuckets !== removedBuckets) { setPrevRemovedBuckets(removedBuckets); - setMappings(Object.fromEntries(removedBuckets.map((bucket) => [bucket.key, null]))); + setMappings(Object.fromEntries(removedBuckets.map((bucket) => [bucket.id, null]))); } - const setMapping = (fromKey: string, toKey: string | null) => { - setMappings((prev) => ({ ...prev, [fromKey]: toKey })); + const setMapping = (fromBucketId: string, toKey: string | null) => { + setMappings((prev) => ({ ...prev, [fromBucketId]: toKey })); }; // When the new policy disallows no-preference signups, mapping a removed bucket to "no // preference" would leave affected signups/requests with a null requested_bucket_id that the // policy no longer permits new signups to have -- so every row needs an explicit bucket chosen // before this can be confirmed. - const canConfirm = !preventNoPreferenceSignups || removedBuckets.every((bucket) => mappings[bucket.key]); + const canConfirm = !preventNoPreferenceSignups || removedBuckets.every((bucket) => mappings[bucket.id]); const handleConfirm = async () => { - const bucketKeyMappings: BucketKeyMappingInput[] = Object.entries(mappings).map(([fromKey, toKey]) => ({ - from_key: fromKey, + const bucketKeyMappings: BucketKeyMappingInput[] = Object.entries(mappings).map(([fromBucketId, toKey]) => ({ + from_bucket_id: fromBucketId, to_key: toKey ?? undefined, })); setIsSubmitting(true); @@ -90,13 +94,13 @@ function BucketKeyRemappingModal({ {removedBuckets.map((bucket) => ( - + {bucket.name}