spree_core 6.0.0.beta4 → 6.0.0.rc2
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.
- checksums.yaml +4 -4
- data/README.md +5 -5
- data/app/helpers/spree/images_helper.rb +0 -57
- data/app/jobs/spree/base_job.rb +21 -0
- data/app/jobs/spree/carts/reap_expired_job.rb +2 -2
- data/app/jobs/spree/collections/regenerate_time_based_job.rb +6 -3
- data/app/jobs/spree/orders/finalize_stale_drafts_job.rb +8 -5
- data/app/jobs/spree/payments/cancel_unused_sessions_job.rb +61 -0
- data/app/jobs/spree/search_provider/index_job.rb +4 -0
- data/app/jobs/spree/seller_payouts/sweep_seller_job.rb +2 -0
- data/app/jobs/spree/uploads/purge_unattached_job.rb +49 -0
- data/app/mailers/spree/admin_user_mailer.rb +4 -19
- data/app/mailers/spree/base_mailer.rb +97 -13
- data/app/mailers/spree/email_template_mailer.rb +27 -0
- data/app/mailers/spree/export_mailer.rb +3 -4
- data/app/mailers/spree/import_mailer.rb +3 -4
- data/app/mailers/spree/invitation_mailer.rb +24 -7
- data/app/mailers/spree/seller_user_mailer.rb +4 -16
- data/app/mailers/spree/webhook_mailer.rb +2 -2
- data/app/models/concerns/spree/acted_by.rb +1 -1
- data/app/models/concerns/spree/admin_user_methods.rb +15 -1
- data/app/models/concerns/spree/api_typed.rb +91 -0
- data/app/models/concerns/spree/calculated_adjustments.rb +41 -13
- data/app/models/concerns/spree/calculator/currency_amounts.rb +1 -1
- data/app/models/concerns/spree/calculator/tiers.rb +63 -0
- data/app/models/concerns/spree/canonical_decimals.rb +61 -0
- data/app/models/concerns/spree/customer_methods.rb +23 -18
- data/app/models/concerns/spree/derived_number.rb +11 -13
- data/app/models/concerns/spree/email_template_identity.rb +52 -0
- data/app/models/concerns/spree/parameterizable_name.rb +2 -0
- data/app/models/concerns/spree/payment_session_transitions.rb +8 -2
- data/app/models/concerns/spree/post_sale/taxation.rb +54 -0
- data/app/models/concerns/spree/post_sale/taxed_line.rb +51 -0
- data/app/models/concerns/spree/preference_schema/json_schema.rb +139 -0
- data/app/models/concerns/spree/preference_schema.rb +62 -32
- data/app/models/concerns/spree/product_scopes.rb +16 -2
- data/app/models/concerns/spree/provider_listing.rb +41 -0
- data/app/models/concerns/spree/publishable.rb +82 -14
- data/app/models/concerns/spree/purchase/addresses.rb +23 -10
- data/app/models/concerns/spree/purchase/currency.rb +1 -1
- data/app/models/concerns/spree/purchase/deprecated_aliases.rb +87 -0
- data/app/models/concerns/spree/purchase/gift_cards.rb +10 -4
- data/app/models/concerns/spree/purchase/locale.rb +1 -1
- data/app/models/concerns/spree/purchase/payment_processing.rb +8 -4
- data/app/models/concerns/spree/purchase/purchase_order.rb +9 -4
- data/app/models/concerns/spree/purchase/store_credits.rb +36 -1
- data/app/models/concerns/spree/purchase/totals.rb +49 -8
- data/app/models/concerns/spree/ransackable_attributes.rb +46 -0
- data/app/models/concerns/spree/receivable.rb +1 -1
- data/app/models/concerns/spree/searchable.rb +0 -4
- data/app/models/concerns/spree/secret_preferences.rb +59 -0
- data/app/models/concerns/spree/signed_id_attachments.rb +54 -0
- data/app/models/concerns/spree/single_store_resource.rb +1 -1
- data/app/models/concerns/spree/stores/email_branding.rb +32 -0
- data/app/models/concerns/spree/stores/markets.rb +5 -2
- data/app/models/concerns/spree/type_labels.rb +38 -0
- data/app/models/concerns/spree/typed_adjustment_line.rb +5 -6
- data/app/models/concerns/spree/typed_associations.rb +12 -18
- data/app/models/concerns/spree/vat_price_calculation.rb +5 -6
- data/app/models/spree/address.rb +12 -2
- data/app/models/spree/adjusters/largest_remainder.rb +14 -1
- data/app/models/spree/adjusters/promotion.rb +4 -19
- data/app/models/spree/allowed_origin.rb +3 -1
- data/app/models/spree/api_key.rb +5 -6
- data/app/models/spree/authentication/strategies/oidc_strategy.rb +5 -5
- data/app/models/spree/base.rb +99 -22
- data/app/models/spree/calculator/flat_percent_item_total.rb +2 -4
- data/app/models/spree/calculator/flat_rate.rb +3 -5
- data/app/models/spree/calculator/flexi_rate.rb +4 -6
- data/app/models/spree/calculator/percent_on_line_item.rb +2 -2
- data/app/models/spree/calculator/price_sack.rb +5 -7
- data/app/models/spree/calculator/shipping/digital_delivery.rb +3 -5
- data/app/models/spree/calculator/shipping/flat_percent_item_total.rb +7 -7
- data/app/models/spree/calculator/shipping/flat_rate.rb +5 -7
- data/app/models/spree/calculator/shipping/flexi_rate.rb +4 -6
- data/app/models/spree/calculator/shipping/per_item.rb +3 -5
- data/app/models/spree/calculator/shipping/price_sack.rb +5 -7
- data/app/models/spree/calculator/tiered_flat_rate.rb +7 -24
- data/app/models/spree/calculator/tiered_percent.rb +7 -25
- data/app/models/spree/cart.rb +78 -18
- data/app/models/spree/catalog.rb +1 -0
- data/app/models/spree/catalog_price.rb +0 -7
- data/app/models/spree/catalog_price_tier.rb +0 -8
- data/app/models/spree/category.rb +3 -1
- data/app/models/spree/channel/gating.rb +3 -2
- data/app/models/spree/channel.rb +6 -4
- data/app/models/spree/claim.rb +22 -1
- data/app/models/spree/claim_line_item.rb +41 -6
- data/app/models/spree/collection.rb +2 -1
- data/app/models/spree/collection_rule.rb +5 -21
- data/app/models/spree/commission_line.rb +1 -1
- data/app/models/spree/commission_rate.rb +7 -4
- data/app/models/spree/commission_rate_value.rb +1 -1
- data/app/models/spree/commission_rule.rb +4 -11
- data/app/models/spree/commission_rules/category_rule.rb +2 -5
- data/app/models/spree/commission_rules/item_total_rule.rb +2 -2
- data/app/models/spree/commission_rules/product_rule.rb +1 -1
- data/app/models/spree/commission_rules/seller_rule.rb +2 -5
- data/app/models/spree/company.rb +1 -0
- data/app/models/spree/company_invitation.rb +1 -0
- data/app/models/spree/consent_record.rb +0 -1
- data/app/models/spree/credit_card.rb +1 -1
- data/app/models/spree/current.rb +23 -0
- data/app/models/spree/custom_field.rb +2 -2
- data/app/models/spree/custom_field_definition.rb +20 -35
- data/app/models/spree/custom_fields/boolean.rb +1 -1
- data/app/models/spree/custom_fields/json.rb +1 -1
- data/app/models/spree/customer_group.rb +1 -0
- data/app/models/spree/data_feed/google.rb +0 -2
- data/app/models/spree/data_request.rb +2 -1
- data/app/models/spree/delivery_method.rb +36 -14
- data/app/models/spree/delivery_method_rule.rb +4 -11
- data/app/models/spree/delivery_method_rules/channel_rule.rb +2 -5
- data/app/models/spree/delivery_method_rules/item_total_rule.rb +2 -2
- data/app/models/spree/delivery_profile.rb +1 -0
- data/app/models/spree/delivery_rate.rb +7 -8
- data/app/models/spree/delivery_rate_provider/base.rb +1 -0
- data/app/models/spree/delivery_zone.rb +1 -2
- data/app/models/spree/delivery_zone_member.rb +4 -4
- data/app/models/spree/digital_asset.rb +7 -0
- data/app/models/spree/digital_asset_provider/base.rb +2 -0
- data/app/models/spree/digital_link.rb +2 -5
- data/app/models/spree/discount.rb +1 -1
- data/app/models/spree/email_template.rb +25 -0
- data/app/models/spree/email_template_draft.rb +13 -0
- data/app/models/spree/email_template_revision.rb +17 -0
- data/app/models/spree/email_templates/entry.rb +118 -0
- data/app/models/spree/email_templates/sample_record.rb +16 -0
- data/app/models/spree/emails/branding.rb +80 -0
- data/app/models/spree/exchange.rb +16 -1
- data/app/models/spree/exchange_line_item.rb +121 -5
- data/app/models/spree/export.rb +0 -1
- data/app/models/spree/exports/products.rb +10 -1
- data/app/models/spree/exports/report.rb +3 -3
- data/app/models/spree/fee.rb +4 -2
- data/app/models/spree/file_upload.rb +155 -0
- data/app/models/spree/fulfillment.rb +66 -30
- data/app/models/spree/fulfillment_changer.rb +2 -2
- data/app/models/spree/fulfillment_group.rb +6 -1
- data/app/models/spree/fulfillment_item.rb +0 -4
- data/app/models/spree/fulfillment_provider/base.rb +1 -0
- data/app/models/spree/gateway/bogus.rb +6 -0
- data/app/models/spree/gateway/custom_payment_source_method.rb +5 -0
- data/app/models/spree/gateway.rb +6 -2
- data/app/models/spree/gift_card.rb +18 -8
- data/app/models/spree/gift_card_batch.rb +3 -5
- data/app/models/spree/import.rb +5 -7
- data/app/models/spree/import_mapping.rb +1 -2
- data/app/models/spree/import_row.rb +2 -2
- data/app/models/spree/import_schemas/products.rb +1 -0
- data/app/models/spree/integration.rb +9 -19
- data/app/models/spree/invitation.rb +5 -5
- data/app/models/spree/line_item.rb +15 -4
- data/app/models/spree/locale.rb +11 -8
- data/app/models/spree/market.rb +8 -2
- data/app/models/spree/media.rb +1 -9
- data/app/models/spree/newsletter_subscriber.rb +4 -0
- data/app/models/spree/option_type.rb +2 -1
- data/app/models/spree/option_value.rb +2 -1
- data/app/models/spree/order.rb +60 -142
- data/app/models/spree/order_group.rb +18 -4
- data/app/models/spree/order_inventory.rb +10 -5
- data/app/models/spree/order_promotion.rb +1 -1
- data/app/models/spree/order_routing/has_strategy_preference.rb +1 -1
- data/app/models/spree/order_routing/strategy/base.rb +4 -2
- data/app/models/spree/order_routing/strategy/rules.rb +1 -1
- data/app/models/spree/order_routing_rule.rb +6 -22
- data/app/models/spree/package_type.rb +2 -2
- data/app/models/spree/payment/gateway_options.rb +15 -53
- data/app/models/spree/payment/processing.rb +2 -4
- data/app/models/spree/payment.rb +21 -13
- data/app/models/spree/payment_method/check.rb +2 -0
- data/app/models/spree/payment_method/session_instrumentation.rb +1 -0
- data/app/models/spree/payment_method/store_credit.rb +15 -13
- data/app/models/spree/payment_method.rb +78 -6
- data/app/models/spree/payment_session.rb +5 -1
- data/app/models/spree/payment_setup_session.rb +1 -0
- data/app/models/spree/payout_provider/base.rb +3 -1
- data/app/models/spree/pickup_point_provider/base.rb +2 -0
- data/app/models/spree/policy.rb +1 -0
- data/app/models/spree/price.rb +17 -14
- data/app/models/spree/price_adjustment_tier.rb +4 -0
- data/app/models/spree/price_list.rb +14 -9
- data/app/models/spree/price_rules/channel_rule.rb +3 -6
- data/app/models/spree/price_rules/customer_group_rule.rb +3 -6
- data/app/models/spree/price_rules/market_rule.rb +2 -5
- data/app/models/spree/price_rules/user_rule.rb +1 -3
- data/app/models/spree/product/channels.rb +9 -2
- data/app/models/spree/product.rb +54 -30
- data/app/models/spree/product_submission.rb +0 -12
- data/app/models/spree/product_type.rb +1 -1
- data/app/models/spree/promotion/actions/create_line_items.rb +28 -18
- data/app/models/spree/promotion/rules/category.rb +1 -5
- data/app/models/spree/promotion/rules/channel.rb +2 -9
- data/app/models/spree/promotion/rules/country.rb +3 -8
- data/app/models/spree/promotion/rules/currency.rb +1 -5
- data/app/models/spree/promotion/rules/customer_group.rb +2 -9
- data/app/models/spree/promotion/rules/first_order.rb +0 -4
- data/app/models/spree/promotion/rules/item_total.rb +6 -10
- data/app/models/spree/promotion/rules/market.rb +2 -9
- data/app/models/spree/promotion/rules/one_use_per_user.rb +0 -4
- data/app/models/spree/promotion/rules/option_value.rb +2 -6
- data/app/models/spree/promotion/rules/product.rb +1 -5
- data/app/models/spree/promotion/rules/user.rb +0 -4
- data/app/models/spree/promotion/rules/user_logged_in.rb +0 -4
- data/app/models/spree/promotion.rb +36 -6
- data/app/models/spree/promotion_action.rb +7 -14
- data/app/models/spree/promotion_action_line_item.rb +1 -1
- data/app/models/spree/promotion_handler/coupon.rb +59 -27
- data/app/models/spree/promotion_rule.rb +7 -14
- data/app/models/spree/purchase_order.rb +3 -0
- data/app/models/spree/quantity_rule.rb +1 -1
- data/app/models/spree/refund.rb +41 -18
- data/app/models/spree/return.rb +31 -2
- data/app/models/spree/return_line_item.rb +65 -14
- data/app/models/spree/role.rb +7 -7
- data/app/models/spree/saved_report.rb +2 -1
- data/app/models/spree/search_provider/base.rb +4 -0
- data/app/models/spree/seller.rb +10 -2
- data/app/models/spree/seller_payout.rb +8 -0
- data/app/models/spree/seller_requirement.rb +5 -12
- data/app/models/spree/seller_requirement_custom_field.rb +1 -2
- data/app/models/spree/seller_requirement_submission.rb +3 -2
- data/app/models/spree/seller_requirements/accept_terms.rb +2 -3
- data/app/models/spree/seller_transfer.rb +6 -0
- data/app/models/spree/shipping_label.rb +2 -0
- data/app/models/spree/stock/availability_validator.rb +2 -2
- data/app/models/spree/stock/estimator.rb +1 -1
- data/app/models/spree/stock/inventory_unit_builder.rb +1 -1
- data/app/models/spree/stock/packer.rb +2 -2
- data/app/models/spree/stock/splitter/weight.rb +1 -1
- data/app/models/spree/stock_level/custom_events.rb +6 -0
- data/app/models/spree/stock_level.rb +3 -1
- data/app/models/spree/stock_location.rb +1 -0
- data/app/models/spree/stock_movement.rb +1 -1
- data/app/models/spree/stock_receipt_item.rb +1 -1
- data/app/models/spree/stock_reservation.rb +2 -2
- data/app/models/spree/stock_transfer.rb +6 -2
- data/app/models/spree/store.rb +70 -19
- data/app/models/spree/store_credit.rb +13 -13
- data/app/models/spree/store_credit_event.rb +5 -5
- data/app/models/spree/supplier.rb +1 -0
- data/app/models/spree/tax_category.rb +1 -0
- data/app/models/spree/tax_exemption_certificate.rb +3 -0
- data/app/models/spree/tax_identifier.rb +3 -1
- data/app/models/spree/tax_line.rb +53 -3
- data/app/models/spree/tax_provider/base.rb +71 -14
- data/app/models/spree/tax_provider/internal.rb +70 -41
- data/app/models/spree/tax_provider/recorded_share.rb +114 -0
- data/app/models/spree/tax_rate.rb +30 -8
- data/app/models/spree/taxon.rb +1 -1
- data/app/models/spree/taxonomy.rb +0 -1
- data/app/models/spree/update_status.rb +25 -0
- data/app/models/spree/variant.rb +10 -12
- data/app/models/spree/variant_media.rb +1 -1
- data/app/models/spree/webhook_delivery.rb +1 -0
- data/app/models/spree/webhook_endpoint.rb +46 -13
- data/app/models/spree/wishlist.rb +1 -6
- data/app/models/spree/wishlist_item/custom_events.rb +6 -0
- data/app/presenters/spree/csv/customer_presenter.rb +1 -1
- data/app/presenters/spree/csv/newsletter_subscriber_presenter.rb +1 -1
- data/app/presenters/spree/csv/order_line_item_presenter.rb +10 -6
- data/app/presenters/spree/csv/price_list_price_presenter.rb +3 -8
- data/app/presenters/spree/csv/product_variant_presenter.rb +59 -20
- data/app/presenters/spree/csv/purchase_order_item_presenter.rb +1 -3
- data/app/serializers/spree/emails/base_serializer.rb +14 -0
- data/app/serializers/spree/emails/export_serializer.rb +13 -0
- data/app/serializers/spree/emails/import_serializer.rb +19 -0
- data/app/serializers/spree/emails/invitation_serializer.rb +28 -0
- data/app/serializers/spree/emails/store_serializer.rb +31 -0
- data/app/serializers/spree/emails/user_serializer.rb +12 -0
- data/app/serializers/spree/emails/webhook_endpoint_serializer.rb +16 -0
- data/app/services/spree/carts/create.rb +8 -2
- data/app/services/spree/carts/destroy.rb +2 -2
- data/app/services/spree/carts/remove_out_of_stock_items.rb +2 -2
- data/app/services/spree/carts/split_by_seller.rb +1 -1
- data/app/services/spree/carts/update.rb +22 -8
- data/app/services/spree/catalogs/set_product_terms.rb +1 -1
- data/app/services/spree/categories/add_products.rb +13 -31
- data/app/services/spree/categories/remove_products.rb +12 -51
- data/app/services/spree/checkout/advance.rb +1 -4
- data/app/services/spree/collections/add_products.rb +10 -23
- data/app/services/spree/collections/remove_products.rb +7 -43
- data/app/services/spree/coupon_codes/bulk_generate.rb +8 -14
- data/app/services/spree/data_requests/create.rb +1 -1
- data/app/services/spree/deliveries/destroy.rb +2 -2
- data/app/services/spree/email_templates/check.rb +58 -0
- data/app/services/spree/email_templates/no_sample_record.rb +7 -0
- data/app/services/spree/email_templates/preview.rb +99 -0
- data/app/services/spree/emails/file_system.rb +23 -0
- data/app/services/spree/emails/filters.rb +84 -0
- data/app/services/spree/emails/liquid_context.rb +48 -0
- data/app/services/spree/emails/rendered_email.rb +14 -0
- data/app/services/spree/emails/renderer.rb +125 -0
- data/app/services/spree/emails/template.rb +51 -0
- data/app/services/spree/emails/template_data.rb +23 -0
- data/app/services/spree/emails/template_resolver.rb +109 -0
- data/app/services/spree/emails/text_converter.rb +72 -0
- data/app/services/spree/emails/translation_inliner.rb +134 -0
- data/app/services/spree/imports/row_processors/price_list_price.rb +10 -10
- data/app/services/spree/imports/row_processors/product_variant.rb +77 -34
- data/app/services/spree/imports/row_processors/purchase_order.rb +13 -13
- data/app/services/spree/locales.rb +43 -10
- data/app/services/spree/newsletter/subscribe.rb +8 -12
- data/app/services/spree/orders/build_fulfillments.rb +3 -2
- data/app/services/spree/orders/create.rb +5 -4
- data/app/services/spree/orders/discounts/create.rb +14 -11
- data/app/services/spree/orders/discounts/destroy.rb +1 -0
- data/app/services/spree/orders/discounts/update.rb +1 -0
- data/app/services/spree/orders/fees/create.rb +1 -0
- data/app/services/spree/orders/fees/destroy.rb +1 -0
- data/app/services/spree/orders/fees/update.rb +1 -0
- data/app/services/spree/orders/remove_line_item.rb +13 -3
- data/app/services/spree/orders/update.rb +10 -6
- data/app/services/spree/orders/update_item.rb +6 -3
- data/app/services/spree/orders/update_statuses.rb +3 -1
- data/app/services/spree/prices/bulk_upsert.rb +32 -25
- data/app/services/spree/product_memberships.rb +61 -0
- data/app/services/spree/returns/eligibility_validator.rb +1 -1
- data/app/services/spree/search_provider/custom_field_schema.rb +2 -2
- data/app/services/spree/seeds/commission_rates.rb +1 -1
- data/app/services/spree/seeds/digital_delivery.rb +1 -1
- data/app/services/spree/seeds/payment_methods.rb +2 -2
- data/app/services/spree/seeds/saved_reports.rb +3 -3
- data/app/services/spree/seeds/stores.rb +1 -1
- data/app/services/spree/sellers/requirements.rb +1 -2
- data/app/services/spree/shipping_labels/confirm_refund.rb +1 -1
- data/app/services/spree/shipping_labels/store_file.rb +3 -3
- data/app/services/spree/stock_levels/correct.rb +3 -3
- data/app/services/spree/stock_reservations/reserve.rb +2 -3
- data/app/services/spree/store_credits/apply.rb +15 -13
- data/app/services/spree/stores/provision_defaults.rb +23 -25
- data/app/services/spree/update_check.rb +160 -0
- data/app/services/spree/uploads/assign_stores.rb +92 -0
- data/app/subscribers/spree/seller_onboarding_subscriber.rb +1 -1
- data/app/validators/spree/attachment_content_type_validator.rb +19 -2
- data/app/validators/spree/locale_codes_validator.rb +22 -0
- data/app/views/layouts/spree/base_mailer.html.erb +2 -43
- data/app/views/layouts/spree/base_mailer.liquid +79 -0
- data/app/views/spree/admin_user_mailer/password_reset_email.liquid +14 -0
- data/app/views/spree/export_mailer/export_done.liquid +12 -0
- data/app/views/spree/import_mailer/import_done.liquid +15 -0
- data/app/views/spree/invitation_mailer/invitation_accepted.liquid +9 -0
- data/app/views/spree/invitation_mailer/invitation_email.liquid +13 -0
- data/app/views/spree/seller_user_mailer/password_reset_email.liquid +14 -0
- data/app/views/spree/shared/_mailer_button.html.erb +4 -5
- data/app/views/spree/shared/_mailer_hero.html.erb +6 -5
- data/app/views/spree/shared/_summary_row.liquid +8 -0
- data/app/views/spree/webhook_mailer/endpoint_disabled.liquid +21 -0
- data/app/workflows/spree/carts/add_item.rb +4 -4
- data/app/workflows/spree/carts/complete.rb +13 -3
- data/app/workflows/spree/carts/merge.rb +1 -1
- data/app/workflows/spree/carts/recalculate_totals.rb +5 -0
- data/app/workflows/spree/carts/upsert_items.rb +18 -9
- data/app/workflows/spree/claims/approve.rb +5 -22
- data/app/workflows/spree/claims/cancel.rb +5 -21
- data/app/workflows/spree/claims/create.rb +15 -0
- data/app/workflows/spree/claims/deny.rb +7 -0
- data/app/workflows/spree/claims/resolve.rb +34 -31
- data/app/workflows/spree/customers/anonymize.rb +3 -4
- data/app/workflows/spree/customers/create.rb +1 -1
- data/app/workflows/spree/data_requests/fulfill.rb +2 -2
- data/app/workflows/spree/deliveries/update_tracking.rb +1 -1
- data/app/workflows/spree/email_templates/discard_draft.rb +20 -0
- data/app/workflows/spree/email_templates/publish.rb +70 -0
- data/app/workflows/spree/email_templates/restore_revision.rb +33 -0
- data/app/workflows/spree/email_templates/revert.rb +29 -0
- data/app/workflows/spree/email_templates/save_draft.rb +85 -0
- data/app/workflows/spree/exchanges/approve.rb +5 -22
- data/app/workflows/spree/exchanges/cancel.rb +5 -21
- data/app/workflows/spree/exchanges/create.rb +6 -0
- data/app/workflows/spree/exchanges/fulfill.rb +75 -51
- data/app/workflows/spree/exchanges/receive.rb +6 -65
- data/app/workflows/spree/fulfillments/cancel.rb +1 -1
- data/app/workflows/spree/fulfillments/create.rb +53 -49
- data/app/workflows/spree/fulfillments/fulfill.rb +23 -27
- data/app/workflows/spree/fulfillments/mark_delivered.rb +1 -1
- data/app/workflows/spree/fulfillments/replacements.rb +59 -0
- data/app/workflows/spree/gift_cards/apply.rb +2 -2
- data/app/workflows/spree/orders/add_item.rb +5 -1
- data/app/workflows/spree/orders/cancel.rb +3 -3
- data/app/workflows/spree/orders/complete.rb +16 -8
- data/app/workflows/spree/payments/capture.rb +20 -5
- data/app/workflows/spree/payments/process.rb +5 -3
- data/app/workflows/spree/post_sale/approval.rb +35 -0
- data/app/workflows/spree/post_sale/cancellation.rb +44 -0
- data/app/workflows/spree/post_sale/receipt.rb +92 -0
- data/app/workflows/spree/price_lists/update.rb +4 -4
- data/app/workflows/spree/products/nested_attributes.rb +1 -1
- data/app/workflows/spree/purchase_orders/cancel.rb +1 -1
- data/app/workflows/spree/purchase_orders/close.rb +3 -31
- data/app/workflows/spree/purchase_orders/create.rb +3 -1
- data/app/workflows/spree/purchase_orders/mark_draft.rb +2 -2
- data/app/workflows/spree/purchase_orders/mark_ordered.rb +2 -2
- data/app/workflows/spree/purchase_orders/receive.rb +1 -1
- data/app/workflows/spree/purchase_orders/update.rb +5 -34
- data/app/workflows/spree/receivables/closing_short.rb +46 -0
- data/app/workflows/spree/receivables/draft_editing.rb +48 -0
- data/app/workflows/spree/refunds/create.rb +5 -2
- data/app/workflows/spree/refunds/order_payments.rb +14 -2
- data/app/workflows/spree/refunds/tax_credit.rb +67 -0
- data/app/workflows/spree/returns/approve.rb +5 -22
- data/app/workflows/spree/returns/cancel.rb +5 -22
- data/app/workflows/spree/returns/create.rb +8 -0
- data/app/workflows/spree/returns/receive.rb +5 -76
- data/app/workflows/spree/returns/refund.rb +31 -8
- data/app/workflows/spree/seller_requirement_submissions/create.rb +1 -2
- data/app/workflows/spree/seller_transfers/reverse.rb +28 -1
- data/app/workflows/spree/shipping_labels/purchase.rb +8 -8
- data/app/workflows/spree/shipping_labels/record.rb +7 -7
- data/app/workflows/spree/shipping_labels/refund.rb +2 -2
- data/app/workflows/spree/stock_receipts/recording.rb +4 -4
- data/app/workflows/spree/stock_transfers/cancel.rb +2 -2
- data/app/workflows/spree/stock_transfers/close.rb +3 -30
- data/app/workflows/spree/stock_transfers/create.rb +3 -1
- data/app/workflows/spree/stock_transfers/mark_draft.rb +1 -1
- data/app/workflows/spree/stock_transfers/mark_in_transit.rb +3 -3
- data/app/workflows/spree/stock_transfers/mark_ready.rb +2 -2
- data/app/workflows/spree/stock_transfers/receive.rb +1 -1
- data/app/workflows/spree/stock_transfers/update.rb +5 -33
- data/config/currency_exponents.json +180 -0
- data/config/i18n-tasks.yml +32 -18
- data/config/initializers/alba.rb +7 -0
- data/config/language_names.csv +264 -0
- data/config/locales/ar.yml +811 -0
- data/config/locales/be.yml +855 -0
- data/config/locales/bg.yml +723 -0
- data/config/locales/ca.yml +689 -0
- data/config/locales/content_locales.rb +9 -0
- data/config/locales/cs.yml +855 -0
- data/config/locales/da.yml +771 -0
- data/config/locales/de-CH.yml +248 -0
- data/config/locales/de.yml +835 -0
- data/config/locales/el.yml +769 -0
- data/config/locales/en.yml +47 -505
- data/config/locales/es-CL.yml +301 -0
- data/config/locales/es-EC.yml +186 -0
- data/config/locales/es-MX.yml +334 -0
- data/config/locales/es.yml +831 -0
- data/config/locales/et.yml +644 -0
- data/config/locales/fa.yml +709 -0
- data/config/locales/fi.yml +771 -0
- data/config/locales/fr.yml +830 -0
- data/config/locales/hu.yml +751 -0
- data/config/locales/id.yml +756 -0
- data/config/locales/it.yml +833 -0
- data/config/locales/ja.yml +726 -0
- data/config/locales/km.yml +759 -0
- data/config/locales/ko.yml +575 -0
- data/config/locales/ku.yml +753 -0
- data/config/locales/lt.yml +821 -0
- data/config/locales/lv.yml +685 -0
- data/config/locales/nb.yml +824 -0
- data/config/locales/ne.yml +823 -0
- data/config/locales/nl.yml +826 -0
- data/config/locales/pl.yml +835 -0
- data/config/locales/pt-BR.yml +547 -0
- data/config/locales/pt.yml +636 -0
- data/config/locales/ro.yml +750 -0
- data/config/locales/ru.yml +834 -0
- data/config/locales/sk.yml +680 -0
- data/config/locales/sl-SI.yml +600 -0
- data/config/locales/sv.yml +827 -0
- data/config/locales/th.yml +745 -0
- data/config/locales/tr.yml +777 -0
- data/config/locales/uk.yml +836 -0
- data/config/locales/vi.yml +768 -0
- data/config/locales/zh-CN.yml +786 -0
- data/config/locales/zh-TW.yml +834 -0
- data/db/migrate/20260925000001_add_replacement_to_spree_fulfillment_items.rb +5 -0
- data/db/migrate/20261001000001_add_post_sale_tax.rb +30 -0
- data/db/migrate/20261001000001_convert_preferences_to_json.rb +166 -0
- data/db/migrate/20261001000001_create_spree_email_templates.rb +52 -0
- data/db/migrate/20261009000001_change_money_columns_to_decimal_19_4.rb +116 -0
- data/db/migrate/20261010000001_add_store_id_to_active_storage_blobs.rb +12 -0
- data/lib/generators/spree/dummy/dummy_generator.rb +0 -9
- data/lib/generators/spree/dummy/templates/rails/test.rb +26 -0
- data/lib/spree/checkout/default_requirements.rb +37 -13
- data/lib/spree/core/configuration.rb +19 -1
- data/lib/spree/core/controller_helpers/store.rb +1 -1
- data/lib/spree/core/dependencies.rb +5 -4
- data/lib/spree/core/emails/escaped_output.rb +60 -0
- data/lib/spree/core/engine.rb +72 -165
- data/lib/spree/core/permissions/default_catalog.rb +5 -0
- data/lib/spree/core/preferences/invalid_preferences.rb +18 -0
- data/lib/spree/core/preferences/json_conversion.rb +186 -0
- data/lib/spree/core/preferences/masking.rb +55 -2
- data/lib/spree/core/preferences/preferable.rb +343 -103
- data/lib/spree/core/preferences/preferable_class_methods.rb +188 -136
- data/lib/spree/core/previews/import_preview.rb +10 -0
- data/lib/spree/core/ransack_configuration.rb +13 -2
- data/lib/spree/core/tax/provider_error.rb +37 -0
- data/lib/spree/core/version.rb +1 -1
- data/lib/spree/core.rb +91 -373
- data/lib/spree/emails/editable_templates.rb +82 -0
- data/lib/spree/events/catalog.rb +189 -0
- data/lib/spree/events.rb +21 -1
- data/lib/spree/hooks.rb +0 -17
- data/lib/spree/i18n.rb +32 -15
- data/lib/spree/iso_data.rb +7 -0
- data/lib/spree/localized_number.rb +6 -0
- data/lib/spree/migrations.rb +4 -1
- data/lib/spree/money.rb +196 -15
- data/lib/spree/reporting/adapters/base.rb +7 -6
- data/lib/spree/reporting/adapters/live.rb +6 -6
- data/lib/spree/reporting/default_vocabulary.rb +22 -10
- data/lib/spree/reporting/hydration.rb +1 -1
- data/lib/spree/reporting/query.rb +8 -0
- data/lib/spree/reporting/registry.rb +13 -0
- data/lib/spree/reporting/schema.rb +10 -10
- data/lib/spree/testing_support/editable_email_templates.rb +61 -0
- data/lib/spree/testing_support/emails.rb +22 -0
- data/lib/spree/testing_support/factories/cart_factory.rb +1 -1
- data/lib/spree/testing_support/factories/email_template_factory.rb +28 -0
- data/lib/spree/testing_support/factories/order_factory.rb +2 -2
- data/lib/spree/testing_support/factories/product_factory.rb +9 -0
- data/lib/spree/testing_support/factories/refund_factory.rb +1 -1
- data/lib/spree/testing_support/factories/stock_factory.rb +1 -1
- data/lib/spree/testing_support/factories/variant_factory.rb +1 -1
- data/lib/spree/testing_support/i18n.rb +3 -94
- data/lib/spree/testing_support/lifecycle_events.rb +1 -1
- data/lib/spree/testing_support/order_walkthrough.rb +1 -1
- data/lib/spree/testing_support/preferences.rb +0 -5
- data/lib/spree/testing_support/store.rb +9 -1
- data/lib/spree/upgrades/5_6_to_6_0/manifest.yml +67 -1
- data/lib/spree/uploads.rb +101 -0
- data/lib/tasks/categories_and_collections.rake +3 -3
- data/lib/tasks/core.rake +6 -4
- data/lib/tasks/markets.rake +2 -1
- data/lib/tasks/media.rake +3 -3
- data/lib/tasks/migrate_users_to_customers.rake +23 -18
- data/lib/tasks/money.rake +46 -0
- data/lib/tasks/package_types.rake +1 -1
- data/lib/tasks/preferences_json.rake +101 -0
- data/lib/tasks/seller_sample_data.rake +2 -2
- data/lib/tasks/store_settings.rake +13 -6
- data/lib/tasks/typed_adjustments_migration.rake +1 -1
- data/lib/tasks/uploads.rake +19 -0
- data/spec/fixtures/mailer_views/custom_views_probe_mailer/welcome_email.html.erb +4 -0
- metadata +219 -46
- data/app/jobs/spree/products/touch_categories_job.rb +0 -15
- data/app/jobs/spree/products/touch_taxons_job.rb +0 -13
- data/app/models/acts_as_taggable_on/tag_decorator.rb +0 -10
- data/app/models/concerns/spree/has_image_alt_text.rb +0 -18
- data/app/models/spree/base_analytics_event_handler.rb +0 -54
- data/app/models/spree/invitations/store.rb +0 -6
- data/app/models/spree/preference.rb +0 -14
- data/app/models/spree/promotion_handler/page.rb +0 -25
- data/app/models/spree/promotion_handler/promotion_duplicator.rb +0 -60
- data/app/models/spree/stock/differentiator.rb +0 -45
- data/app/presenters/spree/filters/options_presenter.rb +0 -47
- data/app/services/spree/carts/empty.rb +0 -42
- data/app/services/spree/country_to_timezone.rb +0 -273
- data/app/services/spree/payments/create.rb +0 -92
- data/app/validators/spree/url_validator.rb +0 -23
- data/app/views/active_storage/blobs/_blob.html.erb +0 -14
- data/app/views/spree/admin_user_mailer/password_reset_email.html.erb +0 -8
- data/app/views/spree/export_mailer/export_done.html.erb +0 -7
- data/app/views/spree/import_mailer/import_done.html.erb +0 -12
- data/app/views/spree/invitation_mailer/invitation_accepted.html.erb +0 -4
- data/app/views/spree/invitation_mailer/invitation_email.html.erb +0 -12
- data/app/views/spree/seller_user_mailer/password_reset_email.html.erb +0 -8
- data/app/views/spree/shared/_base_mailer_footer.html.erb +0 -19
- data/app/views/spree/shared/_base_mailer_header.html.erb +0 -8
- data/app/views/spree/shared/_base_mailer_stylesheets.html.erb +0 -399
- data/app/views/spree/shared/_mailer_logo.html.erb +0 -41
- data/app/views/spree/shared/_purchased_items_styles.html.erb +0 -119
- data/app/views/spree/webhook_mailer/endpoint_disabled.html.erb +0 -51
- data/app/views/spree/webhook_mailer/endpoint_disabled.text.erb +0 -10
- data/app/workflows/spree/fulfillments/purchase_label.rb +0 -40
- data/app/workflows/spree/returns/purchase_label.rb +0 -32
- data/lib/spree/analytics.rb +0 -11
- data/lib/spree/core/preferences/scoped_store.rb +0 -34
- data/lib/spree/core/preferences/store.rb +0 -105
- data/lib/spree/translation_migrations.rb +0 -52
|
@@ -1,24 +1,22 @@
|
|
|
1
|
-
require_dependency 'spree/shipping_calculator'
|
|
2
|
-
|
|
3
1
|
module Spree
|
|
4
2
|
module Calculator::Shipping
|
|
5
3
|
class FlatRate < ShippingCalculator
|
|
6
4
|
include Spree::Calculator::CurrencyAmounts
|
|
7
5
|
|
|
8
|
-
preference :amount, :
|
|
6
|
+
preference :amount, :money, default: 0
|
|
9
7
|
# @deprecated Together with the single `amount`, superseded by the
|
|
10
8
|
# per-currency `amounts` hash; kept as the fallback for its own
|
|
11
9
|
# currency so upgraded stores quote unchanged.
|
|
12
|
-
preference :currency, :string, default: -> { Spree::Store.default.default_currency }
|
|
10
|
+
preference :currency, :string, format: :currency, default: -> { Spree::Store.default.default_currency }
|
|
13
11
|
|
|
14
|
-
preference :minimum_item_total, :
|
|
15
|
-
preference :maximum_item_total, :
|
|
12
|
+
preference :minimum_item_total, :money, default: nil, nullable: true, deprecated: 'Use a Spree::DeliveryMethodRules rule on the delivery method instead; removed in Spree 6.1.'
|
|
13
|
+
preference :maximum_item_total, :money, default: nil, nullable: true, deprecated: 'Use a Spree::DeliveryMethodRules rule on the delivery method instead; removed in Spree 6.1.'
|
|
16
14
|
|
|
17
15
|
preference :minimum_weight, :decimal, default: nil, nullable: true, deprecated: 'Use a Spree::DeliveryMethodRules rule on the delivery method instead; removed in Spree 6.1.'
|
|
18
16
|
preference :maximum_weight, :decimal, default: nil, nullable: true, deprecated: 'Use a Spree::DeliveryMethodRules rule on the delivery method instead; removed in Spree 6.1.'
|
|
19
17
|
|
|
20
18
|
def self.description
|
|
21
|
-
|
|
19
|
+
I18n.t('spree.shipping_flat_rate_per_order')
|
|
22
20
|
end
|
|
23
21
|
|
|
24
22
|
def compute_package(package)
|
|
@@ -1,12 +1,10 @@
|
|
|
1
|
-
require_dependency 'spree/shipping_calculator'
|
|
2
|
-
|
|
3
1
|
module Spree
|
|
4
2
|
module Calculator::Shipping
|
|
5
3
|
class FlexiRate < ShippingCalculator
|
|
6
|
-
preference :first_item, :
|
|
7
|
-
preference :additional_item, :
|
|
4
|
+
preference :first_item, :money, default: 0.0
|
|
5
|
+
preference :additional_item, :money, default: 0.0
|
|
8
6
|
preference :max_items, :integer, default: 0
|
|
9
|
-
preference :currency, :string, default: -> { Spree::Store.default.default_currency }
|
|
7
|
+
preference :currency, :string, format: :currency, default: -> { Spree::Store.default.default_currency }
|
|
10
8
|
|
|
11
9
|
# Single-currency amounts: quoting another currency would mislabel
|
|
12
10
|
# the configured numbers, so the method stays hidden there.
|
|
@@ -15,7 +13,7 @@ module Spree
|
|
|
15
13
|
end
|
|
16
14
|
|
|
17
15
|
def self.description
|
|
18
|
-
|
|
16
|
+
I18n.t('spree.shipping_flexible_rate')
|
|
19
17
|
end
|
|
20
18
|
|
|
21
19
|
def compute_package(package)
|
|
@@ -1,15 +1,13 @@
|
|
|
1
|
-
require_dependency 'spree/shipping_calculator'
|
|
2
|
-
|
|
3
1
|
module Spree
|
|
4
2
|
module Calculator::Shipping
|
|
5
3
|
class PerItem < ShippingCalculator
|
|
6
4
|
include Spree::Calculator::CurrencyAmounts
|
|
7
5
|
|
|
8
|
-
preference :amount, :
|
|
9
|
-
preference :currency, :string, default: -> { Spree::Store.default.default_currency }
|
|
6
|
+
preference :amount, :money, default: 0
|
|
7
|
+
preference :currency, :string, format: :currency, default: -> { Spree::Store.default.default_currency }
|
|
10
8
|
|
|
11
9
|
def self.description
|
|
12
|
-
|
|
10
|
+
I18n.t('spree.shipping_flat_rate_per_item')
|
|
13
11
|
end
|
|
14
12
|
|
|
15
13
|
def compute_package(package)
|
|
@@ -1,12 +1,10 @@
|
|
|
1
|
-
require_dependency 'spree/shipping_calculator'
|
|
2
|
-
|
|
3
1
|
module Spree
|
|
4
2
|
module Calculator::Shipping
|
|
5
3
|
class PriceSack < ShippingCalculator
|
|
6
|
-
preference :minimal_amount, :
|
|
7
|
-
preference :normal_amount, :
|
|
8
|
-
preference :discount_amount, :
|
|
9
|
-
preference :currency, :string, default: -> { Spree::Store.default.default_currency }
|
|
4
|
+
preference :minimal_amount, :money, default: 0
|
|
5
|
+
preference :normal_amount, :money, default: 0
|
|
6
|
+
preference :discount_amount, :money, default: 0
|
|
7
|
+
preference :currency, :string, format: :currency, default: -> { Spree::Store.default.default_currency }
|
|
10
8
|
|
|
11
9
|
# Single-currency amounts: quoting another currency would mislabel
|
|
12
10
|
# the configured numbers, so the method stays hidden there.
|
|
@@ -15,7 +13,7 @@ module Spree
|
|
|
15
13
|
end
|
|
16
14
|
|
|
17
15
|
def self.description
|
|
18
|
-
|
|
16
|
+
I18n.t('spree.shipping_price_sack')
|
|
19
17
|
end
|
|
20
18
|
|
|
21
19
|
def compute_package(package)
|
|
@@ -1,42 +1,25 @@
|
|
|
1
|
-
require_dependency 'spree/calculator'
|
|
2
|
-
|
|
3
1
|
module Spree
|
|
4
2
|
class Calculator::TieredFlatRate < Calculator
|
|
5
|
-
|
|
6
|
-
preference :currency, :string, default: -> { Spree::Store.default.default_currency }
|
|
7
|
-
preference :tiers, :hash, default: {}
|
|
8
|
-
|
|
9
|
-
before_validation do
|
|
10
|
-
# Convert tier values to decimals. Strings don't do us much good.
|
|
11
|
-
if preferred_tiers.is_a?(Hash)
|
|
12
|
-
self.preferred_tiers = Hash[*preferred_tiers.flatten.map(&:to_f)]
|
|
13
|
-
end
|
|
14
|
-
end
|
|
3
|
+
include Spree::Calculator::Tiers
|
|
15
4
|
|
|
16
|
-
|
|
5
|
+
preference :base_amount, :money, default: 0
|
|
6
|
+
preference :currency, :string, format: :currency, default: -> { Spree::Store.default.default_currency }
|
|
17
7
|
|
|
18
8
|
def self.description
|
|
19
|
-
|
|
9
|
+
I18n.t('spree.tiered_flat_rate')
|
|
20
10
|
end
|
|
21
11
|
|
|
22
12
|
def compute(object = nil)
|
|
23
13
|
return 0 unless object&.currency.present?
|
|
24
14
|
return 0 unless preferred_currency.casecmp(object.currency.upcase).zero?
|
|
25
15
|
|
|
26
|
-
|
|
27
|
-
amount || preferred_base_amount
|
|
16
|
+
tier_value_for(object.amount) || preferred_base_amount
|
|
28
17
|
end
|
|
29
18
|
|
|
30
19
|
private
|
|
31
20
|
|
|
32
|
-
def
|
|
33
|
-
|
|
34
|
-
unless preferred_tiers.keys.all? { |k| k.is_a?(Numeric) && k > 0 }
|
|
35
|
-
errors.add(:base, :keys_should_be_positive_number)
|
|
36
|
-
end
|
|
37
|
-
else
|
|
38
|
-
errors.add(:preferred_tiers, :should_be_hash)
|
|
39
|
-
end
|
|
21
|
+
def validate_tier_values(values)
|
|
22
|
+
errors.add(:preferred_tiers, :values_should_be_number) unless values.all? { |value| value && value >= 0 }
|
|
40
23
|
end
|
|
41
24
|
end
|
|
42
25
|
end
|
|
@@ -1,45 +1,27 @@
|
|
|
1
|
-
require_dependency 'spree/calculator'
|
|
2
|
-
|
|
3
1
|
module Spree
|
|
4
2
|
class Calculator::TieredPercent < Calculator
|
|
5
|
-
|
|
6
|
-
preference :tiers, :hash, default: {}
|
|
3
|
+
include Spree::Calculator::Tiers
|
|
7
4
|
|
|
8
|
-
|
|
9
|
-
# Convert tier values to decimals. Strings don't do us much good.
|
|
10
|
-
if preferred_tiers.is_a?(Hash)
|
|
11
|
-
self.preferred_tiers = Hash[*preferred_tiers.flatten.map(&:to_f)]
|
|
12
|
-
end
|
|
13
|
-
end
|
|
5
|
+
preference :base_percent, :decimal, default: 0
|
|
14
6
|
|
|
15
7
|
validates :preferred_base_percent, numericality: {
|
|
16
8
|
greater_than_or_equal_to: 0,
|
|
17
9
|
less_than_or_equal_to: 100
|
|
18
10
|
}
|
|
19
|
-
validate :preferred_tiers_content
|
|
20
11
|
|
|
21
12
|
def self.description
|
|
22
|
-
|
|
13
|
+
I18n.t('spree.tiered_percent')
|
|
23
14
|
end
|
|
24
15
|
|
|
25
16
|
def compute(object)
|
|
26
|
-
|
|
27
|
-
(object.amount *
|
|
17
|
+
percent = tier_value_for(object.amount) || preferred_base_percent
|
|
18
|
+
Spree::Money::Rounding.to_currency(object.amount * percent / 100, object.try(:currency))
|
|
28
19
|
end
|
|
29
20
|
|
|
30
21
|
private
|
|
31
22
|
|
|
32
|
-
def
|
|
33
|
-
|
|
34
|
-
unless preferred_tiers.keys.all? { |k| k.is_a?(Numeric) && k > 0 }
|
|
35
|
-
errors.add(:base, :keys_should_be_positive_number)
|
|
36
|
-
end
|
|
37
|
-
unless preferred_tiers.values.all? { |k| k.is_a?(Numeric) && k >= 0 && k <= 100 }
|
|
38
|
-
errors.add(:base, :values_should_be_percent)
|
|
39
|
-
end
|
|
40
|
-
else
|
|
41
|
-
errors.add(:preferred_tiers, :should_be_hash)
|
|
42
|
-
end
|
|
23
|
+
def validate_tier_values(values)
|
|
24
|
+
errors.add(:preferred_tiers, :values_should_be_percent) unless values.all? { |value| value&.between?(0, 100) }
|
|
43
25
|
end
|
|
44
26
|
end
|
|
45
27
|
end
|
data/app/models/spree/cart.rb
CHANGED
|
@@ -36,6 +36,7 @@ module Spree
|
|
|
36
36
|
include Spree::Purchase::Validations
|
|
37
37
|
include Spree::Purchase::Totals
|
|
38
38
|
include Spree::Purchase::Lifecycle
|
|
39
|
+
include Spree::Purchase::DeprecatedAliases
|
|
39
40
|
|
|
40
41
|
# Concurrency is manual (the API's OrderLock semantics — compare
|
|
41
42
|
# client-sent version, 409 on mismatch); Rails auto-locking must not
|
|
@@ -54,16 +55,7 @@ module Spree
|
|
|
54
55
|
:discount_total, :fee_total, :delivery_total, :total, :payment_total, :outstanding_balance,
|
|
55
56
|
:tax_total, :pre_tax_item_amount, :pre_tax_total, :amount_due
|
|
56
57
|
|
|
57
|
-
alias display_promo_total display_discount_total
|
|
58
|
-
alias display_ship_total display_delivery_total
|
|
59
|
-
alias_attribute :ship_total, :delivery_total
|
|
60
|
-
|
|
61
58
|
belongs_to :customer, class_name: "::#{Spree.customer_class}", optional: true
|
|
62
|
-
# Order-parity aliases — shared Cart/Order code (services, Purchase
|
|
63
|
-
# concerns) reads #user; the cart column is customer_id.
|
|
64
|
-
alias_method :user, :customer
|
|
65
|
-
alias_method :user=, :customer=
|
|
66
|
-
alias_attribute :user_id, :customer_id
|
|
67
59
|
# Codes are stored stripped + lowercased so lookups stay case-insensitive;
|
|
68
60
|
# normalizes also applies to finder values.
|
|
69
61
|
normalizes :coupon_code, with: ->(code) { code.to_s.strip.downcase.presence }
|
|
@@ -87,6 +79,8 @@ module Spree
|
|
|
87
79
|
end
|
|
88
80
|
end
|
|
89
81
|
has_many :fulfillment_items, through: :fulfillments, class_name: 'Spree::FulfillmentItem'
|
|
82
|
+
# Legacy name (5.x carts were orders) — removed in 6.1
|
|
83
|
+
has_many :shipments, -> { order(:created_at, :id) }, class_name: 'Spree::Fulfillment', inverse_of: :cart, deprecated: true
|
|
90
84
|
has_many :order_promotions, class_name: 'Spree::OrderPromotion', inverse_of: :cart, dependent: :destroy
|
|
91
85
|
has_many :promotions, through: :order_promotions, class_name: 'Spree::Promotion'
|
|
92
86
|
has_many :payments, class_name: 'Spree::Payment', inverse_of: :cart, dependent: :destroy
|
|
@@ -167,10 +161,18 @@ module Spree
|
|
|
167
161
|
|
|
168
162
|
# Idempotent delivery-proposal rebuild — replaces the destructive
|
|
169
163
|
# order-side create_proposed_fulfillments. Open fulfillments are rebuilt from
|
|
170
|
-
# the current items/address; nothing here touches a completed cart.
|
|
171
|
-
|
|
164
|
+
# the current items/address; nothing here touches a completed cart. Until
|
|
165
|
+
# deliveries can be proposed the cart gets none: preselecting the pickup
|
|
166
|
+
# rate that is all a destination-less quote finds would choose pickup for
|
|
167
|
+
# a customer who had not been offered anything.
|
|
168
|
+
#
|
|
169
|
+
# @param keep_selection [Boolean] false when the destination changed: a
|
|
170
|
+
# choice made for one address is not a choice for another
|
|
171
|
+
def rebuild_fulfillments!(keep_selection: true)
|
|
172
172
|
return if completed?
|
|
173
173
|
|
|
174
|
+
previous_selections = keep_selection ? fulfillments.selected_rates_by_stock_location : {}
|
|
175
|
+
|
|
174
176
|
discounts.for_fulfillments.delete_all
|
|
175
177
|
tax_lines.for_fulfillments.delete_all
|
|
176
178
|
fees.for_fulfillments.delete_all
|
|
@@ -179,6 +181,7 @@ module Spree
|
|
|
179
181
|
DeliveryRate.where(fulfillment_id: fulfillment_ids).delete_all
|
|
180
182
|
fulfillments.delete_all
|
|
181
183
|
fulfillment_items.reset
|
|
184
|
+
return fulfillments.reload unless can_propose_deliveries?
|
|
182
185
|
|
|
183
186
|
# Appended rather than assigned: setting `cart` on each proposal already
|
|
184
187
|
# files it under this cart's `fulfillments` (the association is
|
|
@@ -188,6 +191,7 @@ module Spree
|
|
|
188
191
|
Spree::Stock::Coordinator.new(self).fulfillments.each do |fulfillment|
|
|
189
192
|
fulfillment.address_id = ship_address_id
|
|
190
193
|
fulfillment.order = nil
|
|
194
|
+
fulfillment.carry_over_selection(previous_selections.fetch(fulfillment.stock_location_id, []))
|
|
191
195
|
fulfillments << fulfillment
|
|
192
196
|
end
|
|
193
197
|
prune_undeliverable_fulfillments!
|
|
@@ -206,7 +210,7 @@ module Spree
|
|
|
206
210
|
self.warnings |= affected_line_items.map do |line_item|
|
|
207
211
|
{
|
|
208
212
|
code: 'delivery_unavailable',
|
|
209
|
-
message:
|
|
213
|
+
message: I18n.t('spree.cart_line_item.delivery_unavailable', li_name: line_item.name),
|
|
210
214
|
line_item_id: line_item.prefixed_id
|
|
211
215
|
}
|
|
212
216
|
end
|
|
@@ -214,7 +218,7 @@ module Spree
|
|
|
214
218
|
|
|
215
219
|
def ensure_available_delivery_rates
|
|
216
220
|
if fulfillments.empty? || fulfillments.any? { |fulfillment| fulfillment.delivery_rates.blank? }
|
|
217
|
-
errors.add(:base, :items_cannot_be_shipped, message:
|
|
221
|
+
errors.add(:base, :items_cannot_be_shipped, message: I18n.t('spree.items_cannot_be_shipped'))
|
|
218
222
|
return false
|
|
219
223
|
end
|
|
220
224
|
true
|
|
@@ -229,7 +233,6 @@ module Spree
|
|
|
229
233
|
updated_at: Time.current
|
|
230
234
|
)
|
|
231
235
|
end
|
|
232
|
-
alias set_shipments_cost set_fulfillments_cost
|
|
233
236
|
|
|
234
237
|
def ensure_updated_fulfillments
|
|
235
238
|
rebuild_fulfillments! unless completed?
|
|
@@ -238,7 +241,11 @@ module Spree
|
|
|
238
241
|
# Re-prices, re-taxes and rebuilds delivery proposals — the
|
|
239
242
|
# recalculation-on-write replacement for transition-triggered rebuilds.
|
|
240
243
|
# Called by Carts::Update after address/market changes.
|
|
241
|
-
|
|
244
|
+
#
|
|
245
|
+
# @param keep_selection [Boolean] true when the parcel still goes where it
|
|
246
|
+
# did (a market change, a corrected phone number), so the chosen
|
|
247
|
+
# delivery is kept and quoted again
|
|
248
|
+
def recalculate_for_address_change!(keep_selection: false)
|
|
242
249
|
# One provider round for the whole cart, and persisted: a per-item loop
|
|
243
250
|
# would ask an external pricing system once per line, and nothing here
|
|
244
251
|
# saves the line items — rebuild_fulfillments! and recalculate_totals!
|
|
@@ -251,8 +258,7 @@ module Spree
|
|
|
251
258
|
raise Spree::Pricing::PriceResolution::ProviderUnavailable, result.error.to_s if result.failure?
|
|
252
259
|
|
|
253
260
|
Spree::Carts::PriceItems.apply(result.value)
|
|
254
|
-
rebuild_fulfillments!
|
|
255
|
-
set_fulfillments_cost
|
|
261
|
+
rebuild_fulfillments!(keep_selection: keep_selection)
|
|
256
262
|
recalculate_totals!
|
|
257
263
|
end
|
|
258
264
|
|
|
@@ -269,11 +275,27 @@ module Spree
|
|
|
269
275
|
reload
|
|
270
276
|
end
|
|
271
277
|
|
|
278
|
+
# The variants this cart's buyer may order: the channel's live
|
|
279
|
+
# publications, narrowed to the catalogs the cart's company, customer
|
|
280
|
+
# group or channel resolve to. Status, stock and currency are left to the
|
|
281
|
+
# add and checkout checks, which explain a refusal rather than reading as
|
|
282
|
+
# not found.
|
|
283
|
+
#
|
|
284
|
+
# @return [ActiveRecord::Relation<Spree::Variant>]
|
|
285
|
+
def orderable_variants
|
|
286
|
+
products = Spree.products_for_context_service.call(
|
|
287
|
+
store: store, channel: channel, customer: customer, company: resolved_company,
|
|
288
|
+
base: store.products.not_discontinued_on(channel)
|
|
289
|
+
).value
|
|
290
|
+
|
|
291
|
+
Spree::Variant.for_products(products)
|
|
292
|
+
end
|
|
293
|
+
|
|
272
294
|
# Removes out-of-stock/discontinued items and populates warnings
|
|
273
295
|
# (mirrors Order#remove_out_of_stock_items!).
|
|
274
296
|
def remove_out_of_stock_items!
|
|
275
297
|
existing_warnings = warnings
|
|
276
|
-
result = Spree
|
|
298
|
+
result = Spree.cart_remove_out_of_stock_items_service.call(cart: self)
|
|
277
299
|
return self unless result.success?
|
|
278
300
|
|
|
279
301
|
cart, _messages, new_warnings = result.value
|
|
@@ -281,5 +303,43 @@ module Spree
|
|
|
281
303
|
cart
|
|
282
304
|
end
|
|
283
305
|
|
|
306
|
+
# Whether this cart shows a batch coupon code it does not hold — used,
|
|
307
|
+
# taken by another cart or order, or given up by one — and so can never
|
|
308
|
+
# discount it.
|
|
309
|
+
#
|
|
310
|
+
# @return [Boolean]
|
|
311
|
+
def coupon_code_unavailable?
|
|
312
|
+
code = read_attribute(:coupon_code)
|
|
313
|
+
return false if code.blank?
|
|
314
|
+
|
|
315
|
+
record = Spree::CouponCode.where(promotion_id: store.promotions.select(:id)).find_by(code: code)
|
|
316
|
+
record.present? && record.cart_id != id
|
|
317
|
+
end
|
|
318
|
+
|
|
319
|
+
# Drops an entered batch coupon code this cart no longer holds, and warns
|
|
320
|
+
# the shopper, who otherwise sees the discount vanish.
|
|
321
|
+
#
|
|
322
|
+
# @return [Spree::Cart]
|
|
323
|
+
def remove_unavailable_coupon_code!
|
|
324
|
+
return self unless coupon_code_unavailable?
|
|
325
|
+
|
|
326
|
+
# The lock refuses unsaved attributes and reloads the cart, so this
|
|
327
|
+
# request's warnings are set aside and put back.
|
|
328
|
+
existing_warnings = warnings
|
|
329
|
+
clear_attribute_changes([:warnings])
|
|
330
|
+
removed = with_lock do
|
|
331
|
+
# Checked under the lock, as the completion claim itself is: a
|
|
332
|
+
# completing cart's code sits on its draft order while the payment
|
|
333
|
+
# runs, and a failed payment hands it back.
|
|
334
|
+
next false if completion_claimed? || !coupon_code_unavailable?
|
|
335
|
+
|
|
336
|
+
Spree.coupon_handler.new(self, enable_gift_cards: false).remove(read_attribute(:coupon_code))
|
|
337
|
+
true
|
|
338
|
+
end
|
|
339
|
+
self.warnings = existing_warnings
|
|
340
|
+
self.warnings |= [{ code: 'coupon_code_unavailable', message: I18n.t('spree.coupon_code_unavailable') }] if removed
|
|
341
|
+
self
|
|
342
|
+
end
|
|
343
|
+
|
|
284
344
|
end
|
|
285
345
|
end
|
data/app/models/spree/catalog.rb
CHANGED
|
@@ -86,6 +86,7 @@ module Spree
|
|
|
86
86
|
scope :by_position, -> { ordered }
|
|
87
87
|
|
|
88
88
|
self.whitelisted_ransackable_attributes = %w[name active]
|
|
89
|
+
search_by :name
|
|
89
90
|
|
|
90
91
|
# The catalogs that apply to a purchase node, nearest node first: the
|
|
91
92
|
# node's own assignments before its parent's, catalog position breaking
|
|
@@ -80,13 +80,6 @@ module Spree
|
|
|
80
80
|
break_count.to_i.positive?
|
|
81
81
|
end
|
|
82
82
|
|
|
83
|
-
# The amount as the wire carries it — see CatalogPriceTier#display_value.
|
|
84
|
-
#
|
|
85
|
-
# @return [String]
|
|
86
|
-
def display_value
|
|
87
|
-
amount.to_s
|
|
88
|
-
end
|
|
89
|
-
|
|
90
83
|
# @return [Spree::Money]
|
|
91
84
|
def money
|
|
92
85
|
Spree::Money.new(amount, currency: currency)
|
|
@@ -15,14 +15,6 @@ module Spree
|
|
|
15
15
|
|
|
16
16
|
validates :min_quantity, numericality: { greater_than: 1 }
|
|
17
17
|
|
|
18
|
-
# The amount as the wire carries it — a string, like every other
|
|
19
|
-
# money-shaped value, since a float would round the merchant's figure.
|
|
20
|
-
#
|
|
21
|
-
# @return [String]
|
|
22
|
-
def display_value
|
|
23
|
-
amount.to_s
|
|
24
|
-
end
|
|
25
|
-
|
|
26
18
|
# @return [Spree::Money]
|
|
27
19
|
def money
|
|
28
20
|
Spree::Money.new(amount, currency: currency)
|
|
@@ -61,6 +61,7 @@ module Spree
|
|
|
61
61
|
#
|
|
62
62
|
has_one_attached :image, service: Spree.public_storage_service_name
|
|
63
63
|
has_one_attached :square_image, service: Spree.public_storage_service_name
|
|
64
|
+
signed_id_attachments :image, :square_image
|
|
64
65
|
# The slots double as media-library placements, so an upload here is
|
|
65
66
|
# visible and reusable there (Spree::HasLibraryMedia).
|
|
66
67
|
has_library_media :image, :square_image
|
|
@@ -133,8 +134,9 @@ module Spree
|
|
|
133
134
|
# Ransack
|
|
134
135
|
#
|
|
135
136
|
self.whitelisted_ransackable_associations = %w[parent]
|
|
136
|
-
self.whitelisted_ransackable_attributes = %w[name permalink automatic depth
|
|
137
|
+
self.whitelisted_ransackable_attributes = %w[name permalink automatic depth children_count
|
|
137
138
|
products_count pretty_name parent_id]
|
|
139
|
+
search_by :name, :pretty_name
|
|
138
140
|
|
|
139
141
|
#
|
|
140
142
|
# Translations
|
|
@@ -17,8 +17,9 @@ module Spree
|
|
|
17
17
|
# Empty -> falls back to the Store-level preference. Both are `nullable`
|
|
18
18
|
# so a blank write stays nil (inherit) rather than coercing to "" or
|
|
19
19
|
# false, while an explicit value remains a channel override.
|
|
20
|
-
preference :storefront_access, :string, default: nil, nullable: true
|
|
20
|
+
preference :storefront_access, :string, default: nil, nullable: true, choices: STOREFRONT_ACCESS
|
|
21
21
|
preference :guest_checkout, :boolean, default: nil, nullable: true
|
|
22
|
+
exposes_preferences :storefront_access, :guest_checkout
|
|
22
23
|
|
|
23
24
|
validate :storefront_access_must_be_valid
|
|
24
25
|
end
|
|
@@ -58,7 +59,7 @@ module Spree
|
|
|
58
59
|
return if STOREFRONT_ACCESS.include?(value.to_s)
|
|
59
60
|
|
|
60
61
|
errors.add(
|
|
61
|
-
:preferred_storefront_access, :invalid_storefront_access, message:
|
|
62
|
+
:preferred_storefront_access, :invalid_storefront_access, message: I18n.t('spree.errors.messages.invalid_storefront_access')
|
|
62
63
|
)
|
|
63
64
|
end
|
|
64
65
|
end
|
data/app/models/spree/channel.rb
CHANGED
|
@@ -14,9 +14,10 @@ module Spree
|
|
|
14
14
|
include Spree::Channel::Gating
|
|
15
15
|
|
|
16
16
|
# Empty -> falls back to the Store-level preference.
|
|
17
|
-
preference :order_routing_strategy, :string, default: nil
|
|
17
|
+
preference :order_routing_strategy, :string, default: nil,
|
|
18
|
+
parse_on_set: ->(value) { Spree::ApiTyped.class_name_for(Spree.order_routing.strategies, value) }
|
|
19
|
+
exposes_preferences :order_routing_strategy
|
|
18
20
|
|
|
19
|
-
belongs_to :store, class_name: 'Spree::Store'
|
|
20
21
|
|
|
21
22
|
has_many :orders, class_name: 'Spree::Order', inverse_of: :channel, dependent: :nullify
|
|
22
23
|
has_many :order_routing_rules, class_name: 'Spree::OrderRoutingRule', dependent: :destroy
|
|
@@ -59,6 +60,7 @@ module Spree
|
|
|
59
60
|
scope :default, -> { where(default: true) }
|
|
60
61
|
|
|
61
62
|
self.whitelisted_ransackable_attributes = %w[name code active default store_id]
|
|
63
|
+
search_by :name
|
|
62
64
|
|
|
63
65
|
# Publishes the given products on this channel by creating/upserting ProductPublications.
|
|
64
66
|
# Optionally sets the publication window; if not given, the products will be published immediately
|
|
@@ -163,7 +165,7 @@ module Spree
|
|
|
163
165
|
return unless default?
|
|
164
166
|
return if destroyed_by_association.present?
|
|
165
167
|
|
|
166
|
-
errors.add(:base, :cannot_delete_default_channel, message:
|
|
168
|
+
errors.add(:base, :cannot_delete_default_channel, message: I18n.t('spree.errors.messages.cannot_delete_default_channel'))
|
|
167
169
|
throw :abort
|
|
168
170
|
end
|
|
169
171
|
|
|
@@ -176,7 +178,7 @@ module Spree
|
|
|
176
178
|
return unless api_keys.active.exists?
|
|
177
179
|
return if destroyed_by_association.present?
|
|
178
180
|
|
|
179
|
-
errors.add(:base, :cannot_delete_channel_with_active_api_keys, message:
|
|
181
|
+
errors.add(:base, :cannot_delete_channel_with_active_api_keys, message: I18n.t('spree.errors.messages.cannot_delete_channel_with_active_api_keys'))
|
|
180
182
|
throw :abort
|
|
181
183
|
end
|
|
182
184
|
|
data/app/models/spree/claim.rb
CHANGED
|
@@ -16,8 +16,10 @@ module Spree
|
|
|
16
16
|
include Spree::HasStatus
|
|
17
17
|
include Spree::HasCustomFields
|
|
18
18
|
include Spree::Metadata
|
|
19
|
+
include Spree::PostSale::Taxation
|
|
19
20
|
|
|
20
21
|
publishes_lifecycle_events
|
|
22
|
+
publishes_events :approved, :canceled, :denied, :opened, :resolved
|
|
21
23
|
|
|
22
24
|
has_status :open, :approved, :resolved, :denied, :canceled, default: :open
|
|
23
25
|
|
|
@@ -25,7 +27,6 @@ module Spree
|
|
|
25
27
|
# stays closed — an unrecognised value would silently do nothing.
|
|
26
28
|
RESOLUTIONS = %w[refund replacement refund_and_replacement].freeze
|
|
27
29
|
|
|
28
|
-
belongs_to :store, class_name: 'Spree::Store'
|
|
29
30
|
belongs_to :order, class_name: 'Spree::Order', inverse_of: :claims
|
|
30
31
|
belongs_to :reason, class_name: 'Spree::ClaimReason', optional: true, inverse_of: :claims
|
|
31
32
|
acted_by :created_by
|
|
@@ -43,6 +44,7 @@ module Spree
|
|
|
43
44
|
delegate :currency, to: :order
|
|
44
45
|
|
|
45
46
|
self.whitelisted_ransackable_attributes = %w[number status created_at]
|
|
47
|
+
search_by :number
|
|
46
48
|
self.whitelisted_ransackable_associations = %w[order reason]
|
|
47
49
|
|
|
48
50
|
def refund_total
|
|
@@ -59,6 +61,21 @@ module Spree
|
|
|
59
61
|
end
|
|
60
62
|
end
|
|
61
63
|
|
|
64
|
+
# The tax inside {#refunded_line_amounts}, for the lines whose tax is
|
|
65
|
+
# recorded: each line's refund carries its tax in proportion to what the
|
|
66
|
+
# customer paid for it.
|
|
67
|
+
#
|
|
68
|
+
# @return [Hash{Integer => BigDecimal}] line item id => tax
|
|
69
|
+
def refunded_line_taxes
|
|
70
|
+
claim_line_items.each_with_object(Hash.new(0)) do |line, taxes|
|
|
71
|
+
next unless line.settles_tax? && line.paid_amount.positive?
|
|
72
|
+
|
|
73
|
+
taxes[line.line_item_id] += Spree::Money::Rounding.to_currency(
|
|
74
|
+
line.tax_total * line.refund_amount.to_d / line.paid_amount, currency
|
|
75
|
+
)
|
|
76
|
+
end
|
|
77
|
+
end
|
|
78
|
+
|
|
62
79
|
def display_refund_total
|
|
63
80
|
Spree::Money.new(refund_total, currency: currency)
|
|
64
81
|
end
|
|
@@ -66,5 +83,9 @@ module Spree
|
|
|
66
83
|
def replacement_line_items
|
|
67
84
|
claim_line_items.select(&:send_replacement)
|
|
68
85
|
end
|
|
86
|
+
|
|
87
|
+
def taxed_lines
|
|
88
|
+
claim_line_items
|
|
89
|
+
end
|
|
69
90
|
end
|
|
70
91
|
end
|
|
@@ -2,6 +2,8 @@ module Spree
|
|
|
2
2
|
# One problem item on a {Spree::Claim}, and how it is being made right:
|
|
3
3
|
# money back, a replacement, or both.
|
|
4
4
|
class ClaimLineItem < Spree.base_class
|
|
5
|
+
include Spree::PostSale::TaxedLine
|
|
6
|
+
|
|
5
7
|
has_prefix_id :cli
|
|
6
8
|
|
|
7
9
|
belongs_to :claim, class_name: 'Spree::Claim', inverse_of: :claim_line_items
|
|
@@ -20,16 +22,45 @@ module Spree
|
|
|
20
22
|
|
|
21
23
|
delegate :order, :currency, to: :claim
|
|
22
24
|
|
|
23
|
-
|
|
24
|
-
|
|
25
|
+
extend Spree::DisplayMoney
|
|
26
|
+
money_methods :refund_amount, :paid_amount, :pre_tax_amount, :included_tax_total,
|
|
27
|
+
:additional_tax_total, :tax_total
|
|
28
|
+
|
|
29
|
+
# What the customer paid for the affected units, after discounts and with
|
|
30
|
+
# the tax charged on top of the price — the ceiling for a refund on this
|
|
31
|
+
# line, which is entered tax included. A claim opened before claims
|
|
32
|
+
# carried tax has none, so its ceiling is unchanged.
|
|
33
|
+
#
|
|
34
|
+
# @return [BigDecimal]
|
|
25
35
|
def paid_amount
|
|
26
|
-
|
|
36
|
+
discounted_amount + additional_tax_total
|
|
37
|
+
end
|
|
27
38
|
|
|
28
|
-
|
|
39
|
+
# @return [BigDecimal] the affected units before tax
|
|
40
|
+
def pre_tax_amount
|
|
41
|
+
discounted_amount - included_tax_total
|
|
29
42
|
end
|
|
30
43
|
|
|
31
|
-
def
|
|
32
|
-
|
|
44
|
+
def tax_total
|
|
45
|
+
included_tax_total + additional_tax_total
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
# Nothing is given back on a claim that was denied or withdrawn.
|
|
49
|
+
#
|
|
50
|
+
# @return [Integer]
|
|
51
|
+
def credited_quantity
|
|
52
|
+
claim.denied? || claim.canceled? ? 0 : quantity.to_i
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
# @return [BigDecimal]
|
|
56
|
+
def credited_worth
|
|
57
|
+
paid_amount
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
# @return [void]
|
|
61
|
+
def fold_tax_lines!
|
|
62
|
+
included, additional = tax_totals_from(tax_lines.credits.reload)
|
|
63
|
+
update_columns(included_tax_total: included, additional_tax_total: additional)
|
|
33
64
|
end
|
|
34
65
|
|
|
35
66
|
# What actually ships when the claim is resolved with a replacement.
|
|
@@ -39,6 +70,10 @@ module Spree
|
|
|
39
70
|
|
|
40
71
|
private
|
|
41
72
|
|
|
73
|
+
def discounted_amount
|
|
74
|
+
line_item&.discounted_amount_for(quantity) || 0
|
|
75
|
+
end
|
|
76
|
+
|
|
42
77
|
def set_variant_from_line_item
|
|
43
78
|
self.variant ||= line_item&.variant
|
|
44
79
|
end
|
|
@@ -58,7 +58,6 @@ module Spree
|
|
|
58
58
|
#
|
|
59
59
|
# Associations
|
|
60
60
|
#
|
|
61
|
-
belongs_to :store, class_name: 'Spree::Store'
|
|
62
61
|
|
|
63
62
|
has_many :product_collections, class_name: 'Spree::ProductCollection', dependent: :destroy_async, inverse_of: :collection
|
|
64
63
|
has_many :products, through: :product_collections
|
|
@@ -73,6 +72,7 @@ module Spree
|
|
|
73
72
|
#
|
|
74
73
|
has_one_attached :image, service: Spree.public_storage_service_name
|
|
75
74
|
has_one_attached :square_image, service: Spree.public_storage_service_name
|
|
75
|
+
signed_id_attachments :image, :square_image
|
|
76
76
|
# The slots double as media-library placements, so an upload here is
|
|
77
77
|
# visible and reusable there (Spree::HasLibraryMedia).
|
|
78
78
|
has_library_media :image, :square_image
|
|
@@ -102,6 +102,7 @@ module Spree
|
|
|
102
102
|
# Ransack
|
|
103
103
|
#
|
|
104
104
|
self.whitelisted_ransackable_attributes = %w[permalink automatic sort_order products_count]
|
|
105
|
+
search_by :name
|
|
105
106
|
|
|
106
107
|
#
|
|
107
108
|
# Automatic (rule-based) membership
|