Skip to content

Commit

Permalink
MAGETWO-56941: CLONE - CLONE - [Github] Allowed countries for custome…
Browse files Browse the repository at this point in the history
…r address in admin using storeview configuration #2946
  • Loading branch information
Sergii Kovalenko committed Aug 19, 2016
1 parent 25b6600 commit 1b4ba9f
Show file tree
Hide file tree
Showing 14 changed files with 848 additions and 22 deletions.
2 changes: 1 addition & 1 deletion app/code/Magento/Backend/etc/adminhtml/system.xml
Original file line number Diff line number Diff line change
Expand Up @@ -198,7 +198,7 @@
<resource>Magento_Config::config_general</resource>
<group id="country" translate="label" type="text" sortOrder="1" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Country Options</label>
<field id="allow" translate="label" type="multiselect" sortOrder="2" showInDefault="1" showInWebsite="1" showInStore="1" canRestore="1">
<field id="allow" translate="label" type="multiselect" sortOrder="2" showInDefault="1" showInWebsite="1" showInStore="0" canRestore="1">
<label>Allow Countries</label>
<source_model>Magento\Directory\Model\Config\Source\Country</source_model>
<can_be_empty>1</can_be_empty>
Expand Down
45 changes: 44 additions & 1 deletion app/code/Magento/Customer/Model/Customer/DataProvider.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,12 @@

use Magento\Customer\Api\AddressMetadataInterface;
use Magento\Customer\Api\CustomerMetadataInterface;
use Magento\Customer\Api\Data\AddressInterface;
use Magento\Customer\Api\Data\CustomerInterface;
use Magento\Customer\Model\Attribute;
use Magento\Customer\Model\FileProcessor;
use Magento\Customer\Model\FileProcessorFactory;
use Magento\Customer\Model\ResourceModel\Address\Attribute\Source\CountryByWebsite;
use Magento\Eav\Api\Data\AttributeInterface;
use Magento\Eav\Model\Config;
use Magento\Eav\Model\Entity\Attribute\AbstractAttribute;
Expand Down Expand Up @@ -292,6 +295,7 @@ protected function getAttributesMeta(Type $entityType)
$this->processFrontendInput($attribute, $meta);

$code = $attribute->getAttributeCode();

// use getDataUsingMethod, since some getters are defined and apply additional processing of returning value
foreach ($this->metaProperties as $metaName => $origName) {
$value = $attribute->getDataUsingMethod($origName);
Expand All @@ -304,7 +308,12 @@ protected function getAttributesMeta(Type $entityType)
}

if ($attribute->usesSource()) {
$meta[$code]['arguments']['data']['config']['options'] = $attribute->getSource()->getAllOptions();
if ($code == AddressInterface::COUNTRY_ID) {
$meta[$code]['arguments']['data']['config']['options'] = $this->getCountryByWebsiteSource()
->getAllOptions();
} else {
$meta[$code]['arguments']['data']['config']['options'] = $attribute->getSource()->getAllOptions();
}
}

$rules = $this->eavValidationRules->build($attribute, $meta[$code]['arguments']['data']['config']);
Expand All @@ -315,9 +324,43 @@ protected function getAttributesMeta(Type $entityType)

$this->overrideFileUploaderMetadata($entityType, $attribute, $meta[$code]['arguments']['data']['config']);
}

$this->processWebsiteMeta($meta);
return $meta;
}

/**
* @deprecated
* @return CountryByWebsite
*/
private function getCountryByWebsiteSource()
{
return ObjectManager::getInstance()->get(CountryByWebsite::class);
}

/**
* @deprecated
* @return \Magento\Customer\Model\Config\Share
*/
private function getShareConfig()
{
return ObjectManager::getInstance()->get(\Magento\Customer\Model\Config\Share::class);
}

private function processWebsiteMeta(&$meta)
{
if (isset($meta[CustomerInterface::WEBSITE_ID]) && $this->getShareConfig()->isGlobalScope()) {
$meta[CustomerInterface::WEBSITE_ID]['arguments']['data']['config']['isGlobalScope'] = 1;
}

if (isset($meta[AddressInterface::COUNTRY_ID]) && !$this->getShareConfig()->isGlobalScope()) {
$meta[AddressInterface::COUNTRY_ID]['arguments']['data']['config']['filterBy'] = [
'target' => '${ $.provider }:data.customer.website_id',
'field' => 'website_ids'
];
}
}

/**
* Override file uploader UI component metadata
*
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
<?php
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/

/**
* Customer country with website specified attribute source
*
* @author Magento Core Team <core@magentocommerce.com>
*/
namespace Magento\Customer\Model\ResourceModel\Address\Attribute\Source;

use Magento\Customer\Api\Data\CustomerInterface;
use Magento\Customer\Model\Customer;
use Magento\Framework\App\Config\ScopeConfigInterface;
use Magento\Framework\App\ObjectManager;
use Magento\Store\Model\ScopeInterface;
use Magento\Store\Model\StoreManagerInterface;

class CountryByWebsite extends \Magento\Eav\Model\Entity\Attribute\Source\Table
{
/**
* @var \Magento\Directory\Model\ResourceModel\Country\CollectionFactory
*/
private $countriesFactory;

/**
* @var \Magento\Directory\Model\CountryHandler
*/
private $countryHandler;

/**
* @var array
*/
private $options;

/**
* @var \Magento\Store\Model\StoreManagerInterface
*/
private $storeManager;

/**
* @param \Magento\Eav\Model\ResourceModel\Entity\Attribute\Option\CollectionFactory $attrOptionCollectionFactory
* @param \Magento\Eav\Model\ResourceModel\Entity\Attribute\OptionFactory $attrOptionFactory
* @param \Magento\Directory\Model\ResourceModel\Country\CollectionFactory $countriesFactory
*/
public function __construct(
\Magento\Eav\Model\ResourceModel\Entity\Attribute\Option\CollectionFactory $attrOptionCollectionFactory,
\Magento\Eav\Model\ResourceModel\Entity\Attribute\OptionFactory $attrOptionFactory,
\Magento\Directory\Model\ResourceModel\Country\CollectionFactory $countriesFactory,
\Magento\Directory\Model\CountryHandler $countryHandler,
\Magento\Store\Model\StoreManagerInterface $storeManager
)
{
$this->countriesFactory = $countriesFactory;
$this->countryHandler = $countryHandler;
$this->storeManager = $storeManager;
parent::__construct($attrOptionCollectionFactory, $attrOptionFactory);
}

/**
* Retrieve all options
*
* @return array
*/
public function getAllOptions()
{
if (!$this->options) {
$allowedCountries = [];
$websiteIds = [];

foreach ($this->storeManager->getWebsites() as $website) {
$countries = $this->countryHandler
->getAllowedCountries($website->getId(), ScopeInterface::SCOPE_WEBSITE, true);
$allowedCountries = array_merge($allowedCountries, $countries);

foreach ($countries as $countryCode) {
$websiteIds[$countryCode][] = $website->getId();
}
}

$this->options = $this->createCountriesCollection()
->addFieldToFilter('country_id', ['in' => $allowedCountries])
->toOptionArray();

foreach ($this->options as &$option) {
if (isset($websiteIds[$option['value']])) {
$option['website_ids'] = $websiteIds[$option['value']];
}
}
}

return $this->options;
}

/**
* @return \Magento\Directory\Model\ResourceModel\Country\Collection
*/
private function createCountriesCollection()
{
return $this->countriesFactory->create();
}
}
106 changes: 106 additions & 0 deletions app/code/Magento/Customer/Setup/UpgradeData.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,18 @@
namespace Magento\Customer\Setup;

use Magento\Customer\Model\Customer;
use Magento\Directory\Model\CountryHandler;
use Magento\Framework\App\Config\ScopeConfigInterface;
use Magento\Framework\Encryption\Encryptor;
use Magento\Framework\Indexer\IndexerRegistry;
use Magento\Framework\ObjectManager\ObjectManager;
use Magento\Framework\Setup\SetupInterface;
use Magento\Framework\Setup\UpgradeDataInterface;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Framework\Setup\ModuleDataSetupInterface;
use Magento\Store\Api\Data\WebsiteInterface;
use Magento\Store\Model\ScopeInterface;
use Magento\Store\Model\StoreManagerInterface;

/**
* @codeCoverageIgnore
Expand Down Expand Up @@ -106,12 +113,111 @@ public function upgrade(ModuleDataSetupInterface $setup, ModuleContextInterface
$this->upgradeCustomerPasswordResetlinkExpirationPeriodConfig($setup);
}

if (version_compare($context->getVersion(), '2.0.9', '<')) {
$setup->getConnection()->beginTransaction();

try {
$this->migrateStoresAllowedCountriesToWebsite($setup);
$setup->getConnection()->commit();
} catch (\Exception $e) {
$setup->getConnection()->rollBack();
throw $e;
}
}

$indexer = $this->indexerRegistry->get(Customer::CUSTOMER_GRID_INDEXER_ID);
$indexer->reindexAll();
$this->eavConfig->clear();
$setup->endSetup();
}

/**
* @deprecated
* @return StoreManagerInterface
*/
private function getStoreManager()
{
return \Magento\Framework\App\ObjectManager::getInstance()->get(StoreManagerInterface::class);
}

/**
* @deprecated
* @return CountryHandler
*/
private function getCountryHandler()
{
return \Magento\Framework\App\ObjectManager::getInstance()->get(CountryHandler::class);
}

/**
* @param array $countries
* @param array $newCountries
* @param $identifier
* @return array
*/
private function mergeAllowedCountries(array $countries, array $newCountries, $identifier)
{
if (!isset($countries[$identifier])) {
$countries[$identifier] = $newCountries;
} else {
$countries[$identifier] =
array_replace($countries[$identifier], $newCountries);
}

return $countries;
}

/**
* @param SetupInterface $setup
* @return void
*/
private function migrateStoresAllowedCountriesToWebsite(SetupInterface $setup)
{
$allowedCountries = [];
//Process Websites
foreach ($this->getStoreManager()->getStores() as $store) {
$allowedCountries = $this->mergeAllowedCountries(
$allowedCountries,
$this->getCountryHandler()->getAllowedCountries($store->getId(), ScopeInterface::SCOPE_STORE),
$store->getWebsiteId()
);
}
//Process stores
foreach ($this->getStoreManager()->getWebsites() as $website) {
$allowedCountries = $this->mergeAllowedCountries(
$allowedCountries,
$this->getCountryHandler()->getAllowedCountries($website->getId(), ScopeInterface::SCOPE_WEBSITE),
$website->getId()
);
}

$connection = $setup->getConnection();

//Remove everything from stores scope
$connection->delete(
$connection->getTableName('core_config_data'),
[
'path = ?' => CountryHandler::ALLOWED_COUNTRIES_PATH,
'scope = ?' => ScopeInterface::SCOPE_STORES
]
);

//Update websites
foreach ($allowedCountries as $scopeId => $countries) {
$connection->update(
$connection->getTableName('core_config_data'),
[
'value' => implode(',', $countries)
],
[
'path = ?' => CountryHandler::ALLOWED_COUNTRIES_PATH,
'scope_id = ?' => $scopeId,
'scope = ?' => ScopeInterface::SCOPE_WEBSITES
]
);
}
}

/**
* @param array $entityAttributes
* @param CustomerSetup $customerSetup
Expand Down
Loading

0 comments on commit 1b4ba9f

Please sign in to comment.