Easy Attribute Manager
======================

Target
------
CE Phoenix Cart 1.1.0.6
PHP 8.2

Purpose
-------
Select products, review their existing attributes, choose one option to add or
change, review every pending assignment and option-library change, then apply
the staged changes explicitly in one operation.

Core files
----------
No Phoenix core files are changed or replaced.

New files
---------
admin/easy_attributes.php
admin/includes/easy_attributes_defaults.php
admin/includes/actions/easy_attributes/delete.php
admin/includes/actions/easy_attributes/clean_orphans.php
admin/includes/actions/easy_attributes/remove_product_option.php
admin/includes/actions/easy_attributes/save.php
admin/includes/actions/easy_attributes/search_products.php
admin/includes/boxes/catalog_easy_attributes.php
admin/includes/js/easy_attributes.js
admin/includes/languages/english/easy_attributes.php
admin/includes/languages/english/modules/boxes/catalog_easy_attributes.php
includes/hooks/shop/siteWide/easyAttributesCartGuard.php

Installation
------------
1. Rename the package's "admin" directory if your Phoenix admin directory has
   a custom name.
2. Upload the contents to the store root, preserving the directory structure.
3. Open Admin and select:
     Catalog -> Easy Attribute Manager

   The native Catalog -> Products Attributes page remains installed and
   available as a fallback.

Upgrade from version 0.2.0
--------------------------
After uploading version 0.3.0, delete these two obsolete add-on files:

admin/includes/actions/easy_attributes/delete_option.php
admin/includes/actions/easy_attributes/delete_value.php

Deletion is now handled by the single fixed action file delete.php.

Upgrade from version 0.8.0
--------------------------
Version 1.0.0 replaces background default-price autosaving with the explicit
Apply changes workflow. After uploading, delete this obsolete add-on file:

admin/includes/actions/easy_attributes/save_defaults.php

Behaviour
---------
* Uses the native products_options, products_options_values,
  products_options_values_to_products_options and products_attributes tables.
* Creates one add-on-owned easy_attribute_defaults table automatically. This
  stores the reusable default price and prefix for each option value because
  native Phoenix only stores prices on individual product assignments.
* Nothing on the main form saves automatically. Product assignments and
  option-library settings are staged together, listed in a pending-changes
  review and saved through one explicit Apply changes button.
* Several options can be prepared in one batch. For example, Size, Colour and
  Giftwrap can all be assigned to the same selected products and applied in one
  transaction. Staged options can be reopened or removed before saving.
* The Add another attribute action is displayed prominently below the staged
  attributes. Sort-order and deletion tools are grouped under the clearer
  Option maintenance (optional) heading.
* The page has three visible stages: select products, add or change attributes,
  then review and apply. Store-wide option-library settings are contained in an
  optional expandable area inside the attribute stage.
* Value names, price prefixes and default price adjustments are entered directly
  in the main attribute table. The optional area is reserved for sort orders
  and permanent deletion, so essential price fields are never hidden.
* Trying to switch options while changes are pending displays a discard warning
  so edits cannot disappear silently.
* Selecting a product loads all of its existing native attributes, regardless
  of whether the product or option was selected first. Existing option names
  are shown with the selected product and remain available while switching
  options.
* Existing option values start with Assign unticked. Existing assignments are
  still displayed automatically; tick Assign only to add a value to selected
  products that do not already have it.
* Existing attribute rows and prices are preserved unless an explicit product
  override is selected.
* Existing product assignments can be explicitly removed from the product
  override matrix.
* Every existing option detected on a selected product has a direct product-
  level Remove control. It deletes all value assignments for that option from
  that product only, after confirmation; the global option, its values and
  assignments on other products are preserved.
* Product searches detect orphaned products_attributes rows whose option, value
  or option/value link no longer exists. The manager displays the affected
  product and database IDs and offers a confirmed repair action. The action
  rechecks every row and deletes only records that are still orphaned; valid
  assignments are never included.
* If a shopper still has a deleted product-attribute combination in an active
  cart session, the storefront guard removes only that invalid cart line before
  Phoenix calculates it. This prevents stale-cart warnings without changing a
  Phoenix core file. Valid cart lines remain untouched.
* Existing option values and complete options can be deleted. A confirmation
  warning shows the current product-assignment count before deletion.
* New option and value names are copied to every installed language so the
  records remain complete. Translate them later in the native manager if
  required.
* Product searches match partial model numbers or product names and return up
  to 50 results at a time. Existing attributes for the complete result set are
  loaded in one batched query rather than one query per product.
* The product search is a compact, clearly labelled block on the left. The
  actual input is focused when the page opens and search results have their own
  heading. The complete results area remains hidden until a valid search runs,
  so there is no empty panel that can be mistaken for another input.
* A How to use this page button opens an on-page guide covering product
  selection, library-only creation, multiple staged options, prices, overrides,
  review and the actions that save immediately.
* Every PHP file carries the Phoenix/GPL copyright header and its package-
  relative file location immediately after the opening PHP tag.
* Selected products stay selected across searches.

Current scope
-------------
Version 1.1.5 manages standard Phoenix attributes and price adjustments.
Downloadable attribute records connected directly to a deleted native
products_attributes row are removed with that row. Optional third-party fields
and related data such as attribute weight, images, wholesale pricing, Option
Types and QTPro stock are not managed. Test deletion carefully if any attribute
extension is installed.

Uninstall
---------
Delete only the twelve new files listed above. Database attributes created with
the manager remain native Phoenix data. The optional command below removes only
the add-on's saved defaults:

  DROP TABLE easy_attribute_defaults;
