/** * Adds variations specific fields to the CMS. */ public function updateCMSFields(FieldList $fields) { $fields->addFieldsToTab('Root.Variations', array(ListboxField::create("VariationAttributeTypes", _t('ProductVariationsExtension.ATTRIBUTES', "Attributes"), ProductAttributeType::get()->map("ID", "Title")->toArray())->setMultiple(true)->setDescription(_t('ProductVariationsExtension.ATTRIBUTES_DESCRIPTION', "These are fields to indicate the way(s) each variation varies. Once selected, they can be edited on each variation.")), GridField::create("Variations", _t('ProductVariationsExtension.VARIATIONS', "Variations"), $this->owner->Variations(), GridFieldConfig_RecordEditor::create()))); if ($this->owner->Variations()->exists()) { $fields->addFieldToTab('Root.Pricing', LabelField::create('variationspriceinstructinos', _t('ProductVariationsExtension.VARIATIONS_INSTRUCTIONS', "Price - Because you have one or more variations, the price can be set in the \"Variations\" tab."))); $fields->removeFieldFromTab('Root.Pricing', 'BasePrice'); $fields->removeFieldFromTab('Root.Pricing', 'CostPrice'); $fields->removeFieldFromTab('Root.Main', 'InternalItemID'); } }
public static function find_or_make($name) { if ($type = ProductAttributeType::get()->filter("Name:nocase", $name)->first()) { return $type; } $type = new ProductAttributeType(); $type->Name = $name; $type->Label = $name; $type->write(); return $type; }
/** * Adds variations specific fields to the CMS. */ public function updateCMSFields(FieldList $fields) { $fields->addFieldsToTab('Root.Attributes', array(HeaderField::create('Applicable Attribute Types'), CheckboxSetField::create('StaticAttributeTypes', 'Static Attribute Types', ProductAttributeType::get()->map("ID", "Title")), LiteralField::create('staticattributehelp', '<p>Select any attributes that apply to this product and click Save.</p>'), HeaderField::create('Attributes'))); foreach ($this->owner->StaticAttributeTypes() as $type) { $source = $this->getValuesClosure($type->ID); $newValFields = FieldList::create(array(TextField::create('Value', 'Label'), HiddenField::create('TypeID', '', $type->ID))); $newValReq = RequiredFields::create('Value'); $valuesField = HasStaticAttributes_CheckboxSetField::create('StaticAttributeValues-' . $type->ID, $type->Title, $source()); $valuesField->setValue($this->owner->StaticAttributeValues()->filter('TypeID', $type->ID)->getIDList()); $valuesField->useAddNew('ProductAttributeValue', $source, $newValFields, $newValReq); $fields->addFieldToTab('Root.Attributes', $valuesField); } }
/** * NOTE: this will break if applied to something that's not a SiteTree subclass. * @param DataList|PaginatedList $matches * @param array $facet * @param int $typeID */ protected function buildAttributeFacet($matches, array &$facet, $typeID) { $q = $matches instanceof PaginatedList ? $matches->getList()->dataQuery()->query() : $matches->dataQuery()->query(); if (empty($facet['Label'])) { $type = ProductAttributeType::get()->byID($typeID); $facet['Label'] = $type->Label; } $baseTable = $q->getFrom(); if (is_array($baseTable)) { $baseTable = reset($baseTable); } $q = $q->setSelect(array())->selectField('"ProductAttributeValue"."ID"', 'Value')->selectField('"ProductAttributeValue"."Value"', 'Label')->selectField('count(distinct ' . $baseTable . '."ID")', 'Count')->selectField('"ProductAttributeValue"."Sort"')->addInnerJoin('Product_StaticAttributeValues', $baseTable . '."ID" = "Product_StaticAttributeValues"."ProductID"')->addInnerJoin('ProductAttributeValue', '"Product_StaticAttributeValues"."ProductAttributeValueID" = "ProductAttributeValue"."ID"')->addWhere(sprintf("\"ProductAttributeValue\".\"TypeID\" = '%d'", $typeID))->setOrderBy('"ProductAttributeValue"."Sort"', 'ASC')->setGroupBy('"ProductAttributeValue"."ID"')->execute(); $facet['Values'] = array(); foreach ($q as $row) { $facet['Values'][$row['Value']] = new ArrayData($row); } }
function cleanup() { $sql = "\r\n\t\t\tSelect \"ProductAttributeTypeID\"\r\n\t\t\tFROM \"Product_VariationAttributes\"\r\n\t\t\tWHERE \"ProductID\" = " . $this->owner->ID; $data = DB::query($sql); $array = $data->keyedColumn(); if (is_array($array) && count($array)) { foreach ($array as $key => $productAttributeTypeID) { //attribute type does not exist. if (!ProductAttributeType::get()->byID($productAttributeTypeID)) { //delete non-existing combinations of Product_VariationAttributes (where the attribute does not exist) //DB::query("DELETE FROM \"Product_VariationAttributes\" WHERE \"ProductAttributeTypeID\" = $productAttributeTypeID"); //non-existing product attribute values. $productAttributeValues = ProductAttributeValue::get()->filter(array("TypeID" => $productAttributeTypeID)); if ($productAttributeValues->count()) { foreach ($productAttributeValues as $productAttributeValue) { $productAttributeValue->delete(); } } } } } }
private function addvariations() { $colourObject = ProductAttributeType::get()->where("\"Name\" = 'Colour'")->First(); if (!$colourObject) { $colourObject = new ProductAttributeType(); $colourObject->Name = "Colour"; $colourObject->Label = "Colour"; $colourObject->IsColour = true; $colourObject->Sort = 100; $colourObject->write(); } if ($colourObject) { $redObject = ProductAttributeValue::get()->where("\"Value\" = 'red'")->First(); if (!$redObject) { $redObject = new ProductAttributeValue(); $redObject->Value = "red"; $redObject->RGBCode = "ff0000"; $redObject->ContrastRGBCode = "BFC1C1"; $redObject->TypeID = $colourObject->ID; $redObject->Sort = 100; $redObject->write(); } $blueObject = ProductAttributeValue::get()->where("\"Value\" = 'blue'")->First(); if (!$blueObject) { $blueObject = new ProductAttributeValue(); $blueObject->Value = "blue"; $blueObject->RGBCode = "0000ff"; $blueObject->ContrastRGBCode = "BFC1C1"; $blueObject->TypeID = $colourObject->ID; $blueObject->Sort = 110; $blueObject->write(); } } else { die("COULD NOT CREATE COLOUR OBJECT"); } $sizeObject = ProductAttributeType::get()->filter("Name", 'Size')->First(); if (!$sizeObject) { $sizeObject = new ProductAttributeType(); $sizeObject->Name = "Size"; $sizeObject->Label = "Size"; $sizeObject->Sort = 110; $sizeObject->write(); } if ($sizeObject) { $smallObject = ProductAttributeValue::get()->where("\"Value\" = 'S'")->First(); if (!$smallObject) { $smallObject = new ProductAttributeValue(); $smallObject->Value = "S"; $smallObject->TypeID = $sizeObject->ID; $smallObject->Sort = 100; $smallObject->write(); } $xtraLargeObject = ProductAttributeValue::get()->where("\"Value\" = 'XL'")->First(); if (!$xtraLargeObject) { $xtraLargeObject = new ProductAttributeValue(); $xtraLargeObject->Value = "XL"; $xtraLargeObject->TypeID = $sizeObject->ID; $xtraLargeObject->Sort = 110; $xtraLargeObject->write(); } } else { die("COULD NOT CREATE SIZE OBJECT"); } $products = Product::get()->where("ClassName = 'Product'")->sort("RAND()")->limit(2); $this->addExamplePages(1, "products with variations (size, colour, etc...)", $products); if ($products->count() && $colourObject && $sizeObject) { $variationCombos = array(array("Size" => $xtraLargeObject, "Colour" => $redObject), array("Size" => $xtraLargeObject, "Colour" => $blueObject), array("Size" => $smallObject, "Colour" => $redObject), array("Size" => $smallObject, "Colour" => $blueObject)); foreach ($products as $product) { $existingAttributeTypes = $product->VariationAttributes(); $existingAttributeTypes->add($sizeObject); $existingAttributeTypes->add($colourObject); $this->addToTitle($product, "with variation", false); $product->Content .= "<p>On this page you can see two example of how you customers can add variations to their products (form / table)... In a real-life shop you would probably choose one or the other.</p>"; $product->write(); $product->Publish('Stage', 'Live'); $product->flushCache(); $descriptionOptions = array("", "Per Month", "", "", "Per Year", "This option has limited warranty"); if (!ProductVariation::get()->where("ProductID = " . $product->ID)->count()) { foreach ($variationCombos as $variationCombo) { $productVariation = new ProductVariation(); $productVariation->ProductID = $product->ID; $productVariation->Price = $product->Price * 2; $productVariation->Description = $descriptionOptions[rand(0, 5)]; $productVariation->ImageID = rand(0, 1) ? 0 : $this->getRandomImageID(); $productVariation->write(); $existingAttributeValues = $productVariation->AttributeValues(); $existingAttributeValues->add($variationCombo["Size"]); $existingAttributeValues->add($variationCombo["Colour"]); DB::alteration_message(" Creating variation for " . $product->Title . " // COLOUR " . $variationCombo["Colour"]->Value . " SIZE " . $variationCombo["Size"]->Value, "created"); } } } } }
/** * * @param Int | ProductAttributeType * * @return DataList of ProductAttributeValues */ function possibleValuesForAttributeType($type) { if ($type instanceof ProductAttributeType) { $typeID = $type->ID; } elseif ($type = ProductAttributeType::get()->byID(intval($type))) { $typeID = $type->ID; } else { return null; } $vals = ProductAttributeValue::get()->where("\"TypeID\" = {$typeID} AND \"ProductVariation\".\"ProductID\" = " . $this->owner->ID . " AND \"ProductVariation\".\"AllowPurchase\" = 1")->sort(array("ProductAttributeValue.Sort" => "ASC"))->innerJoin("ProductVariation_AttributeValues", "\"ProductAttributeValue\".\"ID\" = \"ProductVariation_AttributeValues\".\"ProductAttributeValueID\"")->innerJoin("ProductVariation", "\"ProductVariation_AttributeValues\".\"ProductVariationID\" = \"ProductVariation\".\"ID\""); if ($this->variationFilter) { $vals = $vals->filter(array("ProductVariation.ID" => $this->variationFilter)); } return $vals; }
protected function createVariations() { $this->alterationMessage("================================================ CREATING VARIATIONS ================================================", "show"); foreach ($this->data as $data) { $types = array(); $values = array(); $product = $data["Product"]; $arrayForCreation = array(); $variationFilter = array(); $this->alterationMessage("<h1>Working out variations for " . $product->Title . "</h1>"); //create attribute types for one product $this->alterationMessage("....Creating attribute types"); foreach ($this->Config()->get("attribute_type_field_names") as $fieldKey => $fieldName) { $startMessage = "........Checking field {$fieldName}"; $attributeTypeName = trim($data["Product"]->Title) . "_" . $fieldName; $filterArray = array("Name" => $attributeTypeName); $type = ProductAttributeType::get()->filter($filterArray)->first(); if (!$type) { $this->alterationMessage($startMessage . " ... creating new attribute type: " . $attributeTypeName, "created"); $type = new ProductAttributeType($filterArray); $type->Label = $attributeTypeName; $type->Sort = $fieldKey; } else { $this->alterationMessage($startMessage . " ... \tfound existing attribute type: " . $attributeTypeName); } $this->addMoreAttributeType($type, $fieldName, $product); $type->write(); $types[$fieldName] = $type; $product->VariationAttributes()->add($type); } //go through each variation to make the values $this->alterationMessage("....Creating attribute values"); foreach ($data["VariationRows"] as $key => $row) { //go through each value foreach ($this->Config()->get("attribute_type_field_names") as $fieldName) { if (!isset($row["Data"][$fieldName])) { $this->alterationMessage("ERROR; {$fieldName} not set at all....", "deleted"); continue; } elseif (!trim($row["Data"][$fieldName])) { $this->alterationMessage("skipping {$fieldName} as there are no entries..."); continue; } $startMessage = "........Checking field {$fieldName}"; //create attribute value $attributeValueName = $row["Data"][$fieldName]; $filterArray = array("Code" => $attributeValueName, "TypeID" => $types[$fieldName]->ID); $value = ProductAttributeValue::get()->filter($filterArray)->first(); if (!$value) { $this->alterationMessage($startMessage . "............creating new attribute value: <strong>" . $attributeValueName . "</strong> for " . $types[$fieldName]->Name, "created"); $value = ProductAttributeValue::create($filterArray); $value->Code = $attributeValueName; $value->Value = $attributeValueName; } else { $this->alterationMessage($startMessage . "............found existing attribute value: <strong>" . $attributeValueName . "</strong> for " . $types[$fieldName]->Name); } $this->addMoreAttributeType($value, $types[$fieldName], $product); $value->write(); $values[$fieldName] = $value; //add at arrays for creation... if (!isset($arrayForCreation[$types[$fieldName]->ID])) { $arrayForCreation[$types[$fieldName]->ID] = array(); } $arrayForCreation[$types[$fieldName]->ID][] = $value->ID; if (!isset($variationFilters[$key])) { $variationFilters[$key] = array(); } $variationFilters[$key][$types[$fieldName]->ID] = $value->ID; } } //remove attribute types without values... (i.e. product only has size of colour) foreach ($product->VariationAttributes() as $productTypeToBeDeleted) { if ($productTypeToBeDeleted->Values()->count() == 0) { $this->alterationMessage("....deleting attribute type with no values: " . $productTypeToBeDeleted->Title); $product->VariationAttributes()->remove($productTypeToBeDeleted); } } $this->alterationMessage("....Creating Variations ///"); //$this->alterationMessage("....Creating Variations From: ".print_r(array_walk($arrayForCreation, array($this, 'implodeWalk')))); //generate variations $variationAttributeValuesPerVariation = array(); foreach ($arrayForCreation as $typeID => $variationEntry) { foreach ($variationEntry as $positionOfVariation => $attributeValueID) { $variationAttributeValuesPerVariation[$positionOfVariation][$typeID] = $attributeValueID; } } foreach ($variationAttributeValuesPerVariation as $variationAttributes) { $variation = $product->getVariationByAttributes($variationAttributes); if ($variation instanceof ProductVariation) { $this->alterationMessage(".... Variation " . $variation->FullName . " Already Exists ///"); } else { //2. if not, create variation with attributes $className = $product->getClassNameOfVariations(); $newVariation = new $className(array('ProductID' => $product->ID, 'Price' => $product->Price)); $newVariation->setSaveParentProduct(false); $newVariation->write(); $newVariation->AttributeValues()->addMany($variationAttributes); $this->alterationMessage(".... Variation " . $newVariation->FullName . " created ///", "created"); } } //find variations and add to VariationsRows foreach ($data["VariationRows"] as $key => $row) { $variation = $product->getVariationByAttributes($variationFilters[$key]); if ($variation instanceof ProductVariation) { $this->alterationMessage("........Created variation, " . $variation->getTitle()); $this->data[$product->ID]["VariationRows"][$key]["Variation"] = $variation; } else { $this->alterationMessage("........Could not find variation", "deleted"); } } } $this->alterationMessage("================================================", "show"); }