Magento 2: How the quantity_and_stock_status attribute value is populated in product object?

August 6, 2016  |  No Comments  |  by Raj (MagePsycho)  |  Magento 2

Well, a new product attribute that you may notice in Magento2 is quantity_and_stock_status.

SELECT * FROM eav_attribute WHERE attribute_code = 'quantity_and_stock_status';

Query Result:
quantity_and_stock_status attribute info

If you load a product object as:

$product = $this->_productRepository->getById($productId);
var_dump($product->getData());

You will see the value of quantity_and_stock_status as an array of is_in_stock and qty.
You must be thinking from where the heck it came from? These values are supposed to be in the stock item object.

Let’s dig it out.
Try to load any product:

$product = $this->_productRepository->getById($productId);

Inspect the value of following using X-Debug

$product->getData('quantity_and_stock_status')

You will notice that the value of quantity_and_stock_status is 1 initially (i.e. the default value).
Once the product is loaded, afterLoad() method of attribute’s backend_model: Magento\Catalog\Model\Product\Attribute\Backend\Stock is executed.

# Class: \Magento\Catalog\Model\Product\Attribute\Backend\Stock
/**
 * Set inventory data to custom attribute
 *
 * @param Product $object
 * @return $this
 */
public function afterLoad($object)
{
    $stockItem = $this->stockRegistry->getStockItem($object->getId(), $object->getStore()->getWebsiteId());
    $object->setData(
        $this->getAttribute()->getAttributeCode(),
        ['is_in_stock' => $stockItem->getIsInStock(), 'qty' => $stockItem->getQty()]
    );
    return parent::afterLoad($object);
}

From above you can see clearly that is_in_stock and qty value are being fed by the $stockItem object.
And hence scalar value becomes an array.
Now it’s no more mystery, right? Cool.

Now let’s comment on – “Why has Magento2 team introduced quantity_and_stock_status attribute?”

Updating product qty in Magento in an easier & faster way

December 2, 2011  |  42 Comments  |  by Raj (MagePsycho)  |  Latest, Magento, Mysql

Introduction

Product Qty can be updated via default import profile though but this is very slow and requires lots of csv fields(besides sku & qty) for updating.
Today i am going to talk about updating product qty just by using csv with two fields: sku & qty(new) which is very fast enough even for thousands of products.

Steps:

1> Prepare CSV file(stocks.csv) with two fields: sku & qty and upload in the root of Magento installation.
You can see the snapshot how it should look like:
stocks.csv

2> Create a file: update_stocks.php in the root of magento installation and paste the following code:

<?php
/**
 * @author		MagePsycho <info@magepsycho.com>
 * @website		http://www.magepsycho.com
 * @category	Export / Import
 */
$mageFilename = 'app/Mage.php';
require_once $mageFilename;
Mage::setIsDeveloperMode(true);
ini_set('display_errors', 1);
umask(0);
Mage::app('admin');
Mage::register('isSecureArea', 1);
Mage::app()->setCurrentStore(Mage_Core_Model_App::ADMIN_STORE_ID);

set_time_limit(0);
ini_set('memory_limit','1024M');

/***************** UTILITY FUNCTIONS ********************/
function _getConnection($type = 'core_read'){
	return Mage::getSingleton('core/resource')->getConnection($type);
}

function _getTableName($tableName){
	return Mage::getSingleton('core/resource')->getTableName($tableName);
}

function _getAttributeId($attribute_code = 'price'){
	$connection = _getConnection('core_read');
	$sql = "SELECT attribute_id
				FROM " . _getTableName('eav_attribute') . "
			WHERE
				entity_type_id = ?
				AND attribute_code = ?";
	$entity_type_id = _getEntityTypeId();
	return $connection->fetchOne($sql, array($entity_type_id, $attribute_code));
}

function _getEntityTypeId($entity_type_code = 'catalog_product'){
	$connection = _getConnection('core_read');
	$sql		= "SELECT entity_type_id FROM " . _getTableName('eav_entity_type') . " WHERE entity_type_code = ?";
	return $connection->fetchOne($sql, array($entity_type_code));
}

function _checkIfSkuExists($sku){
	$connection = _getConnection('core_read');
	$sql		= "SELECT COUNT(*) AS count_no FROM " . _getTableName('catalog_product_entity') . "	WHERE sku = ?";
	$count		= $connection->fetchOne($sql, array($sku));
	if($count > 0){
		return true;
	}else{
		return false;
	}
}

function _getIdFromSku($sku){
	$connection = _getConnection('core_read');
	$sql		= "SELECT entity_id FROM " . _getTableName('catalog_product_entity') . " WHERE sku = ?";
	return $connection->fetchOne($sql, array($sku));
}

function _updateStocks($data){
	$connection		= _getConnection('core_write');
	$sku			= $data[0];
	$newQty			= $data[1];
	$productId		= _getIdFromSku($sku);
	$attributeId	= _getAttributeId();

	$sql			= "UPDATE " . _getTableName('cataloginventory_stock_item') . " csi,
					   " . _getTableName('cataloginventory_stock_status') . " css
	                   SET
					   csi.qty = ?,
					   csi.is_in_stock = ?,
	                   css.qty = ?,
					   css.stock_status = ?
					   WHERE
					   csi.product_id = ?
			           AND csi.product_id = css.product_id";
	$isInStock		= $newQty > 0 ? 1 : 0;
	$stockStatus	= $newQty > 0 ? 1 : 0;
	$connection->query($sql, array($newQty, $isInStock, $newQty, $stockStatus, $productId));
}
/***************** UTILITY FUNCTIONS ********************/

$csv				= new Varien_File_Csv();
$data				= $csv->getData('stocks.csv'); //path to csv
array_shift($data);

$message = '';
$count   = 1;
foreach($data as $_data){
	if(_checkIfSkuExists($_data[0])){
		try{
			_updateStocks($_data);
			$message .= $count . '> Success:: Qty (' . $_data[1] . ') of Sku (' . $_data[0] . ') has been updated. <br />';

		}catch(Exception $e){
			$message .=  $count .'> Error:: while Upating  Qty (' . $_data[1] . ') of Sku (' . $_data[0] . ') => '.$e->getMessage().'<br />';
		}
	}else{
		$message .=  $count .'> Error:: Product with Sku (' . $_data[0] . ') does\'t exist.<br />';
	}
	$count++;
}
echo $message;

3> Open your browser and run the following url:
http://your-magento-url/update_stocks.php
You will see how fast the qty of corresponding skus are updated.

Thanks for reading guys!!

Happy Importing!!