Magento 2 Get Attribute option Id issue with core method
I am using below code to get the option Id with an attribute value/label in a custom extension.
/*
* Get attribute id based on option value
*/
protected function getAttributeOptionId($attributeCode, $label)
{
$productResource = $this->productFactory->create();
$attribute = $productResource->getAttribute($attributeCode);
if ($attribute->usesSource()) {
return $optionId = $attribute->getSource()->getOptionId($label);
}
}
This works fine in most cases. When I do a call with params color
and red
it works just fine.
But there is an issue when i call it with for instance size
20
. This only happens when there is attribute label/value with id 20
. It just returns the first occurrence it finds (20 as a label or as an id).
I did some research and I found out why this is. Below code is the part which returns the id. The second part in the OR
condition $option['value'] == $value
causes my issue. It looks for a match in the label OR
value (which is the id). It just returns the first one found. I looked in the class there is no alternative method without the OR
condtion.
/**
* File: /vendor/magento/module-eav/Model/Entity/Attribute/Source/AbstractSource.php
* @param string $value
* @return null|string
*/
public function getOptionId($value)
{
foreach ($this->getAllOptions() as $option) {
if (strcasecmp($option['label'], $value) == 0 || $option['value'] == $value) {
return $option['value'];
}
}
return null;
}
My question is.
What is the best way to solve this? Is there an alternative way to get an id from a attribute label? Or should I rewrite the method? Or maybe extends the class and use a custom method? In any of these cases I would be glad to see an example or a place to start.
magento2 product-attribute attribute-options
add a comment |
I am using below code to get the option Id with an attribute value/label in a custom extension.
/*
* Get attribute id based on option value
*/
protected function getAttributeOptionId($attributeCode, $label)
{
$productResource = $this->productFactory->create();
$attribute = $productResource->getAttribute($attributeCode);
if ($attribute->usesSource()) {
return $optionId = $attribute->getSource()->getOptionId($label);
}
}
This works fine in most cases. When I do a call with params color
and red
it works just fine.
But there is an issue when i call it with for instance size
20
. This only happens when there is attribute label/value with id 20
. It just returns the first occurrence it finds (20 as a label or as an id).
I did some research and I found out why this is. Below code is the part which returns the id. The second part in the OR
condition $option['value'] == $value
causes my issue. It looks for a match in the label OR
value (which is the id). It just returns the first one found. I looked in the class there is no alternative method without the OR
condtion.
/**
* File: /vendor/magento/module-eav/Model/Entity/Attribute/Source/AbstractSource.php
* @param string $value
* @return null|string
*/
public function getOptionId($value)
{
foreach ($this->getAllOptions() as $option) {
if (strcasecmp($option['label'], $value) == 0 || $option['value'] == $value) {
return $option['value'];
}
}
return null;
}
My question is.
What is the best way to solve this? Is there an alternative way to get an id from a attribute label? Or should I rewrite the method? Or maybe extends the class and use a custom method? In any of these cases I would be glad to see an example or a place to start.
magento2 product-attribute attribute-options
magento.stackexchange.com/questions/256565/…
– Abhishek Panchal
yesterday
add a comment |
I am using below code to get the option Id with an attribute value/label in a custom extension.
/*
* Get attribute id based on option value
*/
protected function getAttributeOptionId($attributeCode, $label)
{
$productResource = $this->productFactory->create();
$attribute = $productResource->getAttribute($attributeCode);
if ($attribute->usesSource()) {
return $optionId = $attribute->getSource()->getOptionId($label);
}
}
This works fine in most cases. When I do a call with params color
and red
it works just fine.
But there is an issue when i call it with for instance size
20
. This only happens when there is attribute label/value with id 20
. It just returns the first occurrence it finds (20 as a label or as an id).
I did some research and I found out why this is. Below code is the part which returns the id. The second part in the OR
condition $option['value'] == $value
causes my issue. It looks for a match in the label OR
value (which is the id). It just returns the first one found. I looked in the class there is no alternative method without the OR
condtion.
/**
* File: /vendor/magento/module-eav/Model/Entity/Attribute/Source/AbstractSource.php
* @param string $value
* @return null|string
*/
public function getOptionId($value)
{
foreach ($this->getAllOptions() as $option) {
if (strcasecmp($option['label'], $value) == 0 || $option['value'] == $value) {
return $option['value'];
}
}
return null;
}
My question is.
What is the best way to solve this? Is there an alternative way to get an id from a attribute label? Or should I rewrite the method? Or maybe extends the class and use a custom method? In any of these cases I would be glad to see an example or a place to start.
magento2 product-attribute attribute-options
I am using below code to get the option Id with an attribute value/label in a custom extension.
/*
* Get attribute id based on option value
*/
protected function getAttributeOptionId($attributeCode, $label)
{
$productResource = $this->productFactory->create();
$attribute = $productResource->getAttribute($attributeCode);
if ($attribute->usesSource()) {
return $optionId = $attribute->getSource()->getOptionId($label);
}
}
This works fine in most cases. When I do a call with params color
and red
it works just fine.
But there is an issue when i call it with for instance size
20
. This only happens when there is attribute label/value with id 20
. It just returns the first occurrence it finds (20 as a label or as an id).
I did some research and I found out why this is. Below code is the part which returns the id. The second part in the OR
condition $option['value'] == $value
causes my issue. It looks for a match in the label OR
value (which is the id). It just returns the first one found. I looked in the class there is no alternative method without the OR
condtion.
/**
* File: /vendor/magento/module-eav/Model/Entity/Attribute/Source/AbstractSource.php
* @param string $value
* @return null|string
*/
public function getOptionId($value)
{
foreach ($this->getAllOptions() as $option) {
if (strcasecmp($option['label'], $value) == 0 || $option['value'] == $value) {
return $option['value'];
}
}
return null;
}
My question is.
What is the best way to solve this? Is there an alternative way to get an id from a attribute label? Or should I rewrite the method? Or maybe extends the class and use a custom method? In any of these cases I would be glad to see an example or a place to start.
magento2 product-attribute attribute-options
magento2 product-attribute attribute-options
edited yesterday
asked Jan 2 at 20:43
Akif
7751033
7751033
magento.stackexchange.com/questions/256565/…
– Abhishek Panchal
yesterday
add a comment |
magento.stackexchange.com/questions/256565/…
– Abhishek Panchal
yesterday
magento.stackexchange.com/questions/256565/…
– Abhishek Panchal
yesterday
magento.stackexchange.com/questions/256565/…
– Abhishek Panchal
yesterday
add a comment |
1 Answer
1
active
oldest
votes
I hope this help for your custom extension helper.
<?php
namespace PackageModuleHelper;
class Data extends MagentoFrameworkAppHelperAbstractHelper
{
protected $scopeConfig;
protected $_objectManager = null;
protected $_attributes = ;
protected $_eavSetup = null;
public function __construct(
MagentoFrameworkAppConfigScopeConfigInterface $scopeConfig,
MagentoFrameworkObjectManagerInterface $objectmanager
)
{
$this->scopeConfig = $scopeConfig;
$this->_objectManager = $objectmanager;
}
public function getAttribute($_code, $_force = false)
{
if(!isset($this->_attributes[$_code]) || $_force) {
$_attribute = $this->_objectManager->get("MagentoCatalogModelResourceModelEavAttributeFactory")->create();
$this->_attributes[$_code] = $_attribute->loadByCode(MagentoCatalogApiDataProductAttributeInterface::ENTITY_TYPE_CODE, $_code);
}
return $this->_attributes[$_code];
}
public function getEavSetup() {
if(!$this->_eavSetup) {
$this->_eavSetup = $this->_objectManager->get('MagentoEavSetupEavSetupFactory')->create([
'setup' => $this->_objectManager->get('MagentoFrameworkSetupModuleDataSetupInterface')
]);
}
return $this->_eavSetup;
}
public function getAttributeOptionId($_code, $_value) {
$attribute = $this->getAttribute($_code);
if(!$_value || !$attribute || !$attribute->getId()) {
return '';
}
$optionId = '';
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
if(!$optionId) {
$option = ;
$option['attribute_id'] = $attribute->getAttributeId();
$option['value']['option'][0] = $_value;
$option['value']['option'][1] = $_value;
$option['order']['option'] = '';
$this->getEavSetup()->addAttributeOption($option);
$attribute = $this->getAttribute($_code, true);
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
}
return $optionId;
}
}
Thanks, good solution! A thing to note for others when they want to use this too; the best practice is to move direct calls of the objectmanager to the constructor and use dependency injection. +1
– Akif
12 hours ago
add a comment |
Your Answer
StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "479"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});
function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: false,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: null,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});
}
});
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fmagento.stackexchange.com%2fquestions%2f256510%2fmagento-2-get-attribute-option-id-issue-with-core-method%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
1 Answer
1
active
oldest
votes
1 Answer
1
active
oldest
votes
active
oldest
votes
active
oldest
votes
I hope this help for your custom extension helper.
<?php
namespace PackageModuleHelper;
class Data extends MagentoFrameworkAppHelperAbstractHelper
{
protected $scopeConfig;
protected $_objectManager = null;
protected $_attributes = ;
protected $_eavSetup = null;
public function __construct(
MagentoFrameworkAppConfigScopeConfigInterface $scopeConfig,
MagentoFrameworkObjectManagerInterface $objectmanager
)
{
$this->scopeConfig = $scopeConfig;
$this->_objectManager = $objectmanager;
}
public function getAttribute($_code, $_force = false)
{
if(!isset($this->_attributes[$_code]) || $_force) {
$_attribute = $this->_objectManager->get("MagentoCatalogModelResourceModelEavAttributeFactory")->create();
$this->_attributes[$_code] = $_attribute->loadByCode(MagentoCatalogApiDataProductAttributeInterface::ENTITY_TYPE_CODE, $_code);
}
return $this->_attributes[$_code];
}
public function getEavSetup() {
if(!$this->_eavSetup) {
$this->_eavSetup = $this->_objectManager->get('MagentoEavSetupEavSetupFactory')->create([
'setup' => $this->_objectManager->get('MagentoFrameworkSetupModuleDataSetupInterface')
]);
}
return $this->_eavSetup;
}
public function getAttributeOptionId($_code, $_value) {
$attribute = $this->getAttribute($_code);
if(!$_value || !$attribute || !$attribute->getId()) {
return '';
}
$optionId = '';
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
if(!$optionId) {
$option = ;
$option['attribute_id'] = $attribute->getAttributeId();
$option['value']['option'][0] = $_value;
$option['value']['option'][1] = $_value;
$option['order']['option'] = '';
$this->getEavSetup()->addAttributeOption($option);
$attribute = $this->getAttribute($_code, true);
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
}
return $optionId;
}
}
Thanks, good solution! A thing to note for others when they want to use this too; the best practice is to move direct calls of the objectmanager to the constructor and use dependency injection. +1
– Akif
12 hours ago
add a comment |
I hope this help for your custom extension helper.
<?php
namespace PackageModuleHelper;
class Data extends MagentoFrameworkAppHelperAbstractHelper
{
protected $scopeConfig;
protected $_objectManager = null;
protected $_attributes = ;
protected $_eavSetup = null;
public function __construct(
MagentoFrameworkAppConfigScopeConfigInterface $scopeConfig,
MagentoFrameworkObjectManagerInterface $objectmanager
)
{
$this->scopeConfig = $scopeConfig;
$this->_objectManager = $objectmanager;
}
public function getAttribute($_code, $_force = false)
{
if(!isset($this->_attributes[$_code]) || $_force) {
$_attribute = $this->_objectManager->get("MagentoCatalogModelResourceModelEavAttributeFactory")->create();
$this->_attributes[$_code] = $_attribute->loadByCode(MagentoCatalogApiDataProductAttributeInterface::ENTITY_TYPE_CODE, $_code);
}
return $this->_attributes[$_code];
}
public function getEavSetup() {
if(!$this->_eavSetup) {
$this->_eavSetup = $this->_objectManager->get('MagentoEavSetupEavSetupFactory')->create([
'setup' => $this->_objectManager->get('MagentoFrameworkSetupModuleDataSetupInterface')
]);
}
return $this->_eavSetup;
}
public function getAttributeOptionId($_code, $_value) {
$attribute = $this->getAttribute($_code);
if(!$_value || !$attribute || !$attribute->getId()) {
return '';
}
$optionId = '';
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
if(!$optionId) {
$option = ;
$option['attribute_id'] = $attribute->getAttributeId();
$option['value']['option'][0] = $_value;
$option['value']['option'][1] = $_value;
$option['order']['option'] = '';
$this->getEavSetup()->addAttributeOption($option);
$attribute = $this->getAttribute($_code, true);
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
}
return $optionId;
}
}
Thanks, good solution! A thing to note for others when they want to use this too; the best practice is to move direct calls of the objectmanager to the constructor and use dependency injection. +1
– Akif
12 hours ago
add a comment |
I hope this help for your custom extension helper.
<?php
namespace PackageModuleHelper;
class Data extends MagentoFrameworkAppHelperAbstractHelper
{
protected $scopeConfig;
protected $_objectManager = null;
protected $_attributes = ;
protected $_eavSetup = null;
public function __construct(
MagentoFrameworkAppConfigScopeConfigInterface $scopeConfig,
MagentoFrameworkObjectManagerInterface $objectmanager
)
{
$this->scopeConfig = $scopeConfig;
$this->_objectManager = $objectmanager;
}
public function getAttribute($_code, $_force = false)
{
if(!isset($this->_attributes[$_code]) || $_force) {
$_attribute = $this->_objectManager->get("MagentoCatalogModelResourceModelEavAttributeFactory")->create();
$this->_attributes[$_code] = $_attribute->loadByCode(MagentoCatalogApiDataProductAttributeInterface::ENTITY_TYPE_CODE, $_code);
}
return $this->_attributes[$_code];
}
public function getEavSetup() {
if(!$this->_eavSetup) {
$this->_eavSetup = $this->_objectManager->get('MagentoEavSetupEavSetupFactory')->create([
'setup' => $this->_objectManager->get('MagentoFrameworkSetupModuleDataSetupInterface')
]);
}
return $this->_eavSetup;
}
public function getAttributeOptionId($_code, $_value) {
$attribute = $this->getAttribute($_code);
if(!$_value || !$attribute || !$attribute->getId()) {
return '';
}
$optionId = '';
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
if(!$optionId) {
$option = ;
$option['attribute_id'] = $attribute->getAttributeId();
$option['value']['option'][0] = $_value;
$option['value']['option'][1] = $_value;
$option['order']['option'] = '';
$this->getEavSetup()->addAttributeOption($option);
$attribute = $this->getAttribute($_code, true);
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
}
return $optionId;
}
}
I hope this help for your custom extension helper.
<?php
namespace PackageModuleHelper;
class Data extends MagentoFrameworkAppHelperAbstractHelper
{
protected $scopeConfig;
protected $_objectManager = null;
protected $_attributes = ;
protected $_eavSetup = null;
public function __construct(
MagentoFrameworkAppConfigScopeConfigInterface $scopeConfig,
MagentoFrameworkObjectManagerInterface $objectmanager
)
{
$this->scopeConfig = $scopeConfig;
$this->_objectManager = $objectmanager;
}
public function getAttribute($_code, $_force = false)
{
if(!isset($this->_attributes[$_code]) || $_force) {
$_attribute = $this->_objectManager->get("MagentoCatalogModelResourceModelEavAttributeFactory")->create();
$this->_attributes[$_code] = $_attribute->loadByCode(MagentoCatalogApiDataProductAttributeInterface::ENTITY_TYPE_CODE, $_code);
}
return $this->_attributes[$_code];
}
public function getEavSetup() {
if(!$this->_eavSetup) {
$this->_eavSetup = $this->_objectManager->get('MagentoEavSetupEavSetupFactory')->create([
'setup' => $this->_objectManager->get('MagentoFrameworkSetupModuleDataSetupInterface')
]);
}
return $this->_eavSetup;
}
public function getAttributeOptionId($_code, $_value) {
$attribute = $this->getAttribute($_code);
if(!$_value || !$attribute || !$attribute->getId()) {
return '';
}
$optionId = '';
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
if(!$optionId) {
$option = ;
$option['attribute_id'] = $attribute->getAttributeId();
$option['value']['option'][0] = $_value;
$option['value']['option'][1] = $_value;
$option['order']['option'] = '';
$this->getEavSetup()->addAttributeOption($option);
$attribute = $this->getAttribute($_code, true);
$options = $attribute->getSource()->getAllOptions(false);
if($options && count($options) > 0) {
foreach($options as $option){
if(trim(strtolower($option['label'])) == strtolower($_value)){
$optionId = $option['value'];
break;
}
}
}
}
return $optionId;
}
}
edited yesterday
Abhishek Panchal
3,4122829
3,4122829
answered yesterday
Vijay-CyberLocker
1376
1376
Thanks, good solution! A thing to note for others when they want to use this too; the best practice is to move direct calls of the objectmanager to the constructor and use dependency injection. +1
– Akif
12 hours ago
add a comment |
Thanks, good solution! A thing to note for others when they want to use this too; the best practice is to move direct calls of the objectmanager to the constructor and use dependency injection. +1
– Akif
12 hours ago
Thanks, good solution! A thing to note for others when they want to use this too; the best practice is to move direct calls of the objectmanager to the constructor and use dependency injection. +1
– Akif
12 hours ago
Thanks, good solution! A thing to note for others when they want to use this too; the best practice is to move direct calls of the objectmanager to the constructor and use dependency injection. +1
– Akif
12 hours ago
add a comment |
Thanks for contributing an answer to Magento Stack Exchange!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Some of your past answers have not been well-received, and you're in danger of being blocked from answering.
Please pay close attention to the following guidance:
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fmagento.stackexchange.com%2fquestions%2f256510%2fmagento-2-get-attribute-option-id-issue-with-core-method%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
magento.stackexchange.com/questions/256565/…
– Abhishek Panchal
yesterday