Remove postal code required












3















In Magento 2, at the Checkout, some fields are required. But for some reason the Postal code (postcode) field always has a red border and the 'required' notification below it. How do I remove this? Can't find it in any template.required










share|improve this question























  • see magento.stackexchange.com/questions/138454/…

    – Aaron Allen
    Oct 31 '16 at 9:31













  • Can you remove data-validate="{required:true}"? You can also change from Configuration magento.stackexchange.com/questions/19542/…

    – Ankit Shah
    Oct 31 '16 at 9:50
















3















In Magento 2, at the Checkout, some fields are required. But for some reason the Postal code (postcode) field always has a red border and the 'required' notification below it. How do I remove this? Can't find it in any template.required










share|improve this question























  • see magento.stackexchange.com/questions/138454/…

    – Aaron Allen
    Oct 31 '16 at 9:31













  • Can you remove data-validate="{required:true}"? You can also change from Configuration magento.stackexchange.com/questions/19542/…

    – Ankit Shah
    Oct 31 '16 at 9:50














3












3








3


1






In Magento 2, at the Checkout, some fields are required. But for some reason the Postal code (postcode) field always has a red border and the 'required' notification below it. How do I remove this? Can't find it in any template.required










share|improve this question














In Magento 2, at the Checkout, some fields are required. But for some reason the Postal code (postcode) field always has a red border and the 'required' notification below it. How do I remove this? Can't find it in any template.required







magento2 checkout






share|improve this question













share|improve this question











share|improve this question




share|improve this question










asked Oct 31 '16 at 8:25









CakeCake

821311




821311













  • see magento.stackexchange.com/questions/138454/…

    – Aaron Allen
    Oct 31 '16 at 9:31













  • Can you remove data-validate="{required:true}"? You can also change from Configuration magento.stackexchange.com/questions/19542/…

    – Ankit Shah
    Oct 31 '16 at 9:50



















  • see magento.stackexchange.com/questions/138454/…

    – Aaron Allen
    Oct 31 '16 at 9:31













  • Can you remove data-validate="{required:true}"? You can also change from Configuration magento.stackexchange.com/questions/19542/…

    – Ankit Shah
    Oct 31 '16 at 9:50

















see magento.stackexchange.com/questions/138454/…

– Aaron Allen
Oct 31 '16 at 9:31







see magento.stackexchange.com/questions/138454/…

– Aaron Allen
Oct 31 '16 at 9:31















Can you remove data-validate="{required:true}"? You can also change from Configuration magento.stackexchange.com/questions/19542/…

– Ankit Shah
Oct 31 '16 at 9:50





Can you remove data-validate="{required:true}"? You can also change from Configuration magento.stackexchange.com/questions/19542/…

– Ankit Shah
Oct 31 '16 at 9:50










3 Answers
3






active

oldest

votes


















9














We will begin with a research that will lead to a simple solution without any modifications in a code. If you don't have time to read the full answer, scroll down to the latest paragraphs with the answer.



The magento/module-ui/view/base/web/js/form/element/post-code.js element has built-in validation right in the code:



<script>
/**
* @param {String} value
*/
update: function (value) {
var country = registry.get(this.parentName + '.' + 'country_id'),
options = country.indexedOptions,
option;

if (!value) {
return;
}

option = options[value];

if (option['is_zipcode_optional']) {
this.error(false);
this.validation = _.omit(this.validation, 'required-entry');
} else {
this.validation['required-entry'] = true;
}

this.required(!option['is_zipcode_optional']);
}
</script>


That's why it is enabled all the time. The fastest solution is to rewrite this element and add your own code that will be inherited from the default.
You can do this in the following way:



The element itself for the post code is declared here:




magento/module-checkout/view/frontend/layout/checkout_index_index.xml




and has the following view:



<item name="postcode" xsi:type="array">
<!-- post-code field has custom UI component -->
<item name="component" xsi:type="string">Magento_Ui/js/form/element/post-code</item>
<item name="validation" xsi:type="array">
<item name="required-entry" xsi:type="string">true</item>
</item>
</item>


It is located in the <item name="shipping-address-fieldset" xsi:type="array"> container.



To replace this element you will need your own module that will include a form update and a js element. This is the Vendor_Rules module in the example.



Create a file:




app/code/Vendor/Rules/view/frontend/requirejs-config.js`




var config = {
map: {
'*': {
"Magento_Ui/js/form/element/post-code": 'Vendor_Rules/js/form/element/post-code'
}
}
};


It should replace the default post-code element on the front-end.




app/code/Vendor/Rules/view/frontend/web/js/form/element/post-code.js




define([
'underscore',
'uiRegistry',
'Magento_Ui/js/form/element/abstract'
], function (_, registry, Abstract) {
'use strict';

return Abstract.extend({
defaults: {
imports: {
update: '${ $.parentName }.country_id:value'
}
},

/**
* @param {String} value
*/
update: function (value) {
var country = registry.get(this.parentName + '.' + 'country_id'),
options = country.indexedOptions,
option;

if (!value) {
return;
}

option = options[value];

this.error(false);
this.validation = _.omit(this.validation, 'required-entry');

this.required(false);
}
});
});


This is almost the exact copy of the default element, excluding a zip validation for countries where it is not optional. Ino other words, it is required from Magento point of view.



When done, run an update:



bin/magento setup:upgrade
bin/magento setup:static-content:deploy


Refresh a cache and check the result. It will look the following way in our case:



A new address form without required a zip code:
enter image description here



A new address saving without a zip code:
enter image description here



The last step at the Checkout:
enter image description here



And an error in the place order without a zip code:
enter image description here



As you can see, there is a validation of a zip code at the back-end. We should come over it.



A validation is located in the customer address model MagentoCustomerModelAddressAbstractAddress, validate method:



    $_havingOptionalZip = $this->_directoryData->getCountriesWithOptionalZip();
if (!in_array(
$this->getCountryId(),
$_havingOptionalZip
) && !Zend_Validate::is(
$this->getPostcode(),
'NotEmpty'
)
) {
$errors = __('Please enter the zip/postal code.');
}


The first solution is to add a zip code for all countries as optional. Let's check the getCountriesWithOptionalZip method:



/**
* Return ISO2 country codes, which have optional Zip/Postal pre-configured
*
* @param bool $asJson
* @return array|string
*/
public function getCountriesWithOptionalZip($asJson = false)
{
if (null === $this->_optZipCountries) {
$value = trim(
$this->scopeConfig->getValue(
self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
ScopeInterface::SCOPE_STORE
)
);
$this->_optZipCountries = preg_split('/,/', $value, 0, PREG_SPLIT_NO_EMPTY);
}
if ($asJson) {
return $this->jsonHelper->jsonEncode($this->_optZipCountries);
}
return $this->_optZipCountries;
}


As you can see from the country code, the countries with the optional zip code are taken from the _optZipCountries attribute that is filled in with data in the following way:



$this->scopeConfig->getValue(
self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
ScopeInterface::SCOPE_STORE
)


Values are stored in the system settings general/country/optional_zip_countries:



enter image description here



Finally, a simple solution:



You don't need to modify a code. You should only select all countries as countries with an optional zip code. After that a validation for them will be disabled!



Select all countries in the multiselect and save changes for the selected store. Then, disable our module and check the checkout:



A new address in the checkout:
enter image description here



The last step at the checkout:
enter image description here



An order placed has been placed successfully without a zip code:
enter image description here



In the admin panel:
enter image description here



Everything works correctly!



We provided the full research because it may help someone else.



UPDATE (11.01.16)



Sorry, we have misunderstood your question. Then, you need to use our first recommendation and slightly correct a code for the 'Magento_Ui/js/form/element/post-code.js' element. Perform the same actions, as described above but use the following code instead:



return Abstract.extend({
defaults: {
imports: {
update: '${ $.parentName }.country_id:value'
}
},

/**
* @param {String} value
*/
update: function (value) {
var country = registry.get(this.parentName + '.' + 'country_id'),
options = country.indexedOptions,
option;

if (!value) {
return;
}

option = options[value];

if (option['is_zipcode_optional']) {
this.error(false);
this.validation = _.omit(this.validation, 'required-entry');
} else {
this.validation['required-entry'] = true;
}
}
});


We removed the this.required(!option['is_zipcode_optional']); line because it has activated the validation mechanism and caused the red frame to appear. Without this line everything should work smooth and the red frame won't appear.






share|improve this answer


























  • Thanks for the elaborate answer. However, the 'required' system is working just fine. The only problem is that it highlights the postal code field when that checkout page loads. This is because in the previous step, you can already 'calculate shipping cost'. If you leave the field blank there and move on, the postal code field is the only field that highlights.. This looks weird. Is there a way to not 'trigger the requirement' on the load of this page?

    – Cake
    Oct 31 '16 at 13:32











  • @Cake please check the updated solution.

    – MageWorx
    Nov 1 '16 at 7:09











  • I've added these 2 files with the code you provided but it doesn't solve the issue. I did need to create all these folders, they weren't there: (app/code/)Vendor/Rules/view/frontend/web/js/form/element/ I presume 'Vendor' is the vendor of the template right?

    – Cake
    Nov 3 '16 at 23:18













  • Alright so i got it to work but now the field doesn't get checked anymore at all. Even if I set required to true..

    – Cake
    Nov 4 '16 at 0:04






  • 2





    @Cake It is possible, but we haven't tested the code at every step because we've tried to give you the right direction to solve your problem. Hope our solution has helped you.

    – MageWorx
    Nov 4 '16 at 9:14



















1














This error is caused by a magento2 core error.



Please have a look to this link : https://github.com/magento/magento2/issues/7724






share|improve this answer































    0














    please also look at this link it solved my issue : https://github.com/magento/magento2/issues/18630





    share























      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
      });


      }
      });














      draft saved

      draft discarded


















      StackExchange.ready(
      function () {
      StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fmagento.stackexchange.com%2fquestions%2f143353%2fremove-postal-code-required%23new-answer', 'question_page');
      }
      );

      Post as a guest















      Required, but never shown

























      3 Answers
      3






      active

      oldest

      votes








      3 Answers
      3






      active

      oldest

      votes









      active

      oldest

      votes






      active

      oldest

      votes









      9














      We will begin with a research that will lead to a simple solution without any modifications in a code. If you don't have time to read the full answer, scroll down to the latest paragraphs with the answer.



      The magento/module-ui/view/base/web/js/form/element/post-code.js element has built-in validation right in the code:



      <script>
      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      if (option['is_zipcode_optional']) {
      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');
      } else {
      this.validation['required-entry'] = true;
      }

      this.required(!option['is_zipcode_optional']);
      }
      </script>


      That's why it is enabled all the time. The fastest solution is to rewrite this element and add your own code that will be inherited from the default.
      You can do this in the following way:



      The element itself for the post code is declared here:




      magento/module-checkout/view/frontend/layout/checkout_index_index.xml




      and has the following view:



      <item name="postcode" xsi:type="array">
      <!-- post-code field has custom UI component -->
      <item name="component" xsi:type="string">Magento_Ui/js/form/element/post-code</item>
      <item name="validation" xsi:type="array">
      <item name="required-entry" xsi:type="string">true</item>
      </item>
      </item>


      It is located in the <item name="shipping-address-fieldset" xsi:type="array"> container.



      To replace this element you will need your own module that will include a form update and a js element. This is the Vendor_Rules module in the example.



      Create a file:




      app/code/Vendor/Rules/view/frontend/requirejs-config.js`




      var config = {
      map: {
      '*': {
      "Magento_Ui/js/form/element/post-code": 'Vendor_Rules/js/form/element/post-code'
      }
      }
      };


      It should replace the default post-code element on the front-end.




      app/code/Vendor/Rules/view/frontend/web/js/form/element/post-code.js




      define([
      'underscore',
      'uiRegistry',
      'Magento_Ui/js/form/element/abstract'
      ], function (_, registry, Abstract) {
      'use strict';

      return Abstract.extend({
      defaults: {
      imports: {
      update: '${ $.parentName }.country_id:value'
      }
      },

      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');

      this.required(false);
      }
      });
      });


      This is almost the exact copy of the default element, excluding a zip validation for countries where it is not optional. Ino other words, it is required from Magento point of view.



      When done, run an update:



      bin/magento setup:upgrade
      bin/magento setup:static-content:deploy


      Refresh a cache and check the result. It will look the following way in our case:



      A new address form without required a zip code:
      enter image description here



      A new address saving without a zip code:
      enter image description here



      The last step at the Checkout:
      enter image description here



      And an error in the place order without a zip code:
      enter image description here



      As you can see, there is a validation of a zip code at the back-end. We should come over it.



      A validation is located in the customer address model MagentoCustomerModelAddressAbstractAddress, validate method:



          $_havingOptionalZip = $this->_directoryData->getCountriesWithOptionalZip();
      if (!in_array(
      $this->getCountryId(),
      $_havingOptionalZip
      ) && !Zend_Validate::is(
      $this->getPostcode(),
      'NotEmpty'
      )
      ) {
      $errors = __('Please enter the zip/postal code.');
      }


      The first solution is to add a zip code for all countries as optional. Let's check the getCountriesWithOptionalZip method:



      /**
      * Return ISO2 country codes, which have optional Zip/Postal pre-configured
      *
      * @param bool $asJson
      * @return array|string
      */
      public function getCountriesWithOptionalZip($asJson = false)
      {
      if (null === $this->_optZipCountries) {
      $value = trim(
      $this->scopeConfig->getValue(
      self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
      ScopeInterface::SCOPE_STORE
      )
      );
      $this->_optZipCountries = preg_split('/,/', $value, 0, PREG_SPLIT_NO_EMPTY);
      }
      if ($asJson) {
      return $this->jsonHelper->jsonEncode($this->_optZipCountries);
      }
      return $this->_optZipCountries;
      }


      As you can see from the country code, the countries with the optional zip code are taken from the _optZipCountries attribute that is filled in with data in the following way:



      $this->scopeConfig->getValue(
      self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
      ScopeInterface::SCOPE_STORE
      )


      Values are stored in the system settings general/country/optional_zip_countries:



      enter image description here



      Finally, a simple solution:



      You don't need to modify a code. You should only select all countries as countries with an optional zip code. After that a validation for them will be disabled!



      Select all countries in the multiselect and save changes for the selected store. Then, disable our module and check the checkout:



      A new address in the checkout:
      enter image description here



      The last step at the checkout:
      enter image description here



      An order placed has been placed successfully without a zip code:
      enter image description here



      In the admin panel:
      enter image description here



      Everything works correctly!



      We provided the full research because it may help someone else.



      UPDATE (11.01.16)



      Sorry, we have misunderstood your question. Then, you need to use our first recommendation and slightly correct a code for the 'Magento_Ui/js/form/element/post-code.js' element. Perform the same actions, as described above but use the following code instead:



      return Abstract.extend({
      defaults: {
      imports: {
      update: '${ $.parentName }.country_id:value'
      }
      },

      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      if (option['is_zipcode_optional']) {
      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');
      } else {
      this.validation['required-entry'] = true;
      }
      }
      });


      We removed the this.required(!option['is_zipcode_optional']); line because it has activated the validation mechanism and caused the red frame to appear. Without this line everything should work smooth and the red frame won't appear.






      share|improve this answer


























      • Thanks for the elaborate answer. However, the 'required' system is working just fine. The only problem is that it highlights the postal code field when that checkout page loads. This is because in the previous step, you can already 'calculate shipping cost'. If you leave the field blank there and move on, the postal code field is the only field that highlights.. This looks weird. Is there a way to not 'trigger the requirement' on the load of this page?

        – Cake
        Oct 31 '16 at 13:32











      • @Cake please check the updated solution.

        – MageWorx
        Nov 1 '16 at 7:09











      • I've added these 2 files with the code you provided but it doesn't solve the issue. I did need to create all these folders, they weren't there: (app/code/)Vendor/Rules/view/frontend/web/js/form/element/ I presume 'Vendor' is the vendor of the template right?

        – Cake
        Nov 3 '16 at 23:18













      • Alright so i got it to work but now the field doesn't get checked anymore at all. Even if I set required to true..

        – Cake
        Nov 4 '16 at 0:04






      • 2





        @Cake It is possible, but we haven't tested the code at every step because we've tried to give you the right direction to solve your problem. Hope our solution has helped you.

        – MageWorx
        Nov 4 '16 at 9:14
















      9














      We will begin with a research that will lead to a simple solution without any modifications in a code. If you don't have time to read the full answer, scroll down to the latest paragraphs with the answer.



      The magento/module-ui/view/base/web/js/form/element/post-code.js element has built-in validation right in the code:



      <script>
      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      if (option['is_zipcode_optional']) {
      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');
      } else {
      this.validation['required-entry'] = true;
      }

      this.required(!option['is_zipcode_optional']);
      }
      </script>


      That's why it is enabled all the time. The fastest solution is to rewrite this element and add your own code that will be inherited from the default.
      You can do this in the following way:



      The element itself for the post code is declared here:




      magento/module-checkout/view/frontend/layout/checkout_index_index.xml




      and has the following view:



      <item name="postcode" xsi:type="array">
      <!-- post-code field has custom UI component -->
      <item name="component" xsi:type="string">Magento_Ui/js/form/element/post-code</item>
      <item name="validation" xsi:type="array">
      <item name="required-entry" xsi:type="string">true</item>
      </item>
      </item>


      It is located in the <item name="shipping-address-fieldset" xsi:type="array"> container.



      To replace this element you will need your own module that will include a form update and a js element. This is the Vendor_Rules module in the example.



      Create a file:




      app/code/Vendor/Rules/view/frontend/requirejs-config.js`




      var config = {
      map: {
      '*': {
      "Magento_Ui/js/form/element/post-code": 'Vendor_Rules/js/form/element/post-code'
      }
      }
      };


      It should replace the default post-code element on the front-end.




      app/code/Vendor/Rules/view/frontend/web/js/form/element/post-code.js




      define([
      'underscore',
      'uiRegistry',
      'Magento_Ui/js/form/element/abstract'
      ], function (_, registry, Abstract) {
      'use strict';

      return Abstract.extend({
      defaults: {
      imports: {
      update: '${ $.parentName }.country_id:value'
      }
      },

      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');

      this.required(false);
      }
      });
      });


      This is almost the exact copy of the default element, excluding a zip validation for countries where it is not optional. Ino other words, it is required from Magento point of view.



      When done, run an update:



      bin/magento setup:upgrade
      bin/magento setup:static-content:deploy


      Refresh a cache and check the result. It will look the following way in our case:



      A new address form without required a zip code:
      enter image description here



      A new address saving without a zip code:
      enter image description here



      The last step at the Checkout:
      enter image description here



      And an error in the place order without a zip code:
      enter image description here



      As you can see, there is a validation of a zip code at the back-end. We should come over it.



      A validation is located in the customer address model MagentoCustomerModelAddressAbstractAddress, validate method:



          $_havingOptionalZip = $this->_directoryData->getCountriesWithOptionalZip();
      if (!in_array(
      $this->getCountryId(),
      $_havingOptionalZip
      ) && !Zend_Validate::is(
      $this->getPostcode(),
      'NotEmpty'
      )
      ) {
      $errors = __('Please enter the zip/postal code.');
      }


      The first solution is to add a zip code for all countries as optional. Let's check the getCountriesWithOptionalZip method:



      /**
      * Return ISO2 country codes, which have optional Zip/Postal pre-configured
      *
      * @param bool $asJson
      * @return array|string
      */
      public function getCountriesWithOptionalZip($asJson = false)
      {
      if (null === $this->_optZipCountries) {
      $value = trim(
      $this->scopeConfig->getValue(
      self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
      ScopeInterface::SCOPE_STORE
      )
      );
      $this->_optZipCountries = preg_split('/,/', $value, 0, PREG_SPLIT_NO_EMPTY);
      }
      if ($asJson) {
      return $this->jsonHelper->jsonEncode($this->_optZipCountries);
      }
      return $this->_optZipCountries;
      }


      As you can see from the country code, the countries with the optional zip code are taken from the _optZipCountries attribute that is filled in with data in the following way:



      $this->scopeConfig->getValue(
      self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
      ScopeInterface::SCOPE_STORE
      )


      Values are stored in the system settings general/country/optional_zip_countries:



      enter image description here



      Finally, a simple solution:



      You don't need to modify a code. You should only select all countries as countries with an optional zip code. After that a validation for them will be disabled!



      Select all countries in the multiselect and save changes for the selected store. Then, disable our module and check the checkout:



      A new address in the checkout:
      enter image description here



      The last step at the checkout:
      enter image description here



      An order placed has been placed successfully without a zip code:
      enter image description here



      In the admin panel:
      enter image description here



      Everything works correctly!



      We provided the full research because it may help someone else.



      UPDATE (11.01.16)



      Sorry, we have misunderstood your question. Then, you need to use our first recommendation and slightly correct a code for the 'Magento_Ui/js/form/element/post-code.js' element. Perform the same actions, as described above but use the following code instead:



      return Abstract.extend({
      defaults: {
      imports: {
      update: '${ $.parentName }.country_id:value'
      }
      },

      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      if (option['is_zipcode_optional']) {
      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');
      } else {
      this.validation['required-entry'] = true;
      }
      }
      });


      We removed the this.required(!option['is_zipcode_optional']); line because it has activated the validation mechanism and caused the red frame to appear. Without this line everything should work smooth and the red frame won't appear.






      share|improve this answer


























      • Thanks for the elaborate answer. However, the 'required' system is working just fine. The only problem is that it highlights the postal code field when that checkout page loads. This is because in the previous step, you can already 'calculate shipping cost'. If you leave the field blank there and move on, the postal code field is the only field that highlights.. This looks weird. Is there a way to not 'trigger the requirement' on the load of this page?

        – Cake
        Oct 31 '16 at 13:32











      • @Cake please check the updated solution.

        – MageWorx
        Nov 1 '16 at 7:09











      • I've added these 2 files with the code you provided but it doesn't solve the issue. I did need to create all these folders, they weren't there: (app/code/)Vendor/Rules/view/frontend/web/js/form/element/ I presume 'Vendor' is the vendor of the template right?

        – Cake
        Nov 3 '16 at 23:18













      • Alright so i got it to work but now the field doesn't get checked anymore at all. Even if I set required to true..

        – Cake
        Nov 4 '16 at 0:04






      • 2





        @Cake It is possible, but we haven't tested the code at every step because we've tried to give you the right direction to solve your problem. Hope our solution has helped you.

        – MageWorx
        Nov 4 '16 at 9:14














      9












      9








      9







      We will begin with a research that will lead to a simple solution without any modifications in a code. If you don't have time to read the full answer, scroll down to the latest paragraphs with the answer.



      The magento/module-ui/view/base/web/js/form/element/post-code.js element has built-in validation right in the code:



      <script>
      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      if (option['is_zipcode_optional']) {
      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');
      } else {
      this.validation['required-entry'] = true;
      }

      this.required(!option['is_zipcode_optional']);
      }
      </script>


      That's why it is enabled all the time. The fastest solution is to rewrite this element and add your own code that will be inherited from the default.
      You can do this in the following way:



      The element itself for the post code is declared here:




      magento/module-checkout/view/frontend/layout/checkout_index_index.xml




      and has the following view:



      <item name="postcode" xsi:type="array">
      <!-- post-code field has custom UI component -->
      <item name="component" xsi:type="string">Magento_Ui/js/form/element/post-code</item>
      <item name="validation" xsi:type="array">
      <item name="required-entry" xsi:type="string">true</item>
      </item>
      </item>


      It is located in the <item name="shipping-address-fieldset" xsi:type="array"> container.



      To replace this element you will need your own module that will include a form update and a js element. This is the Vendor_Rules module in the example.



      Create a file:




      app/code/Vendor/Rules/view/frontend/requirejs-config.js`




      var config = {
      map: {
      '*': {
      "Magento_Ui/js/form/element/post-code": 'Vendor_Rules/js/form/element/post-code'
      }
      }
      };


      It should replace the default post-code element on the front-end.




      app/code/Vendor/Rules/view/frontend/web/js/form/element/post-code.js




      define([
      'underscore',
      'uiRegistry',
      'Magento_Ui/js/form/element/abstract'
      ], function (_, registry, Abstract) {
      'use strict';

      return Abstract.extend({
      defaults: {
      imports: {
      update: '${ $.parentName }.country_id:value'
      }
      },

      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');

      this.required(false);
      }
      });
      });


      This is almost the exact copy of the default element, excluding a zip validation for countries where it is not optional. Ino other words, it is required from Magento point of view.



      When done, run an update:



      bin/magento setup:upgrade
      bin/magento setup:static-content:deploy


      Refresh a cache and check the result. It will look the following way in our case:



      A new address form without required a zip code:
      enter image description here



      A new address saving without a zip code:
      enter image description here



      The last step at the Checkout:
      enter image description here



      And an error in the place order without a zip code:
      enter image description here



      As you can see, there is a validation of a zip code at the back-end. We should come over it.



      A validation is located in the customer address model MagentoCustomerModelAddressAbstractAddress, validate method:



          $_havingOptionalZip = $this->_directoryData->getCountriesWithOptionalZip();
      if (!in_array(
      $this->getCountryId(),
      $_havingOptionalZip
      ) && !Zend_Validate::is(
      $this->getPostcode(),
      'NotEmpty'
      )
      ) {
      $errors = __('Please enter the zip/postal code.');
      }


      The first solution is to add a zip code for all countries as optional. Let's check the getCountriesWithOptionalZip method:



      /**
      * Return ISO2 country codes, which have optional Zip/Postal pre-configured
      *
      * @param bool $asJson
      * @return array|string
      */
      public function getCountriesWithOptionalZip($asJson = false)
      {
      if (null === $this->_optZipCountries) {
      $value = trim(
      $this->scopeConfig->getValue(
      self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
      ScopeInterface::SCOPE_STORE
      )
      );
      $this->_optZipCountries = preg_split('/,/', $value, 0, PREG_SPLIT_NO_EMPTY);
      }
      if ($asJson) {
      return $this->jsonHelper->jsonEncode($this->_optZipCountries);
      }
      return $this->_optZipCountries;
      }


      As you can see from the country code, the countries with the optional zip code are taken from the _optZipCountries attribute that is filled in with data in the following way:



      $this->scopeConfig->getValue(
      self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
      ScopeInterface::SCOPE_STORE
      )


      Values are stored in the system settings general/country/optional_zip_countries:



      enter image description here



      Finally, a simple solution:



      You don't need to modify a code. You should only select all countries as countries with an optional zip code. After that a validation for them will be disabled!



      Select all countries in the multiselect and save changes for the selected store. Then, disable our module and check the checkout:



      A new address in the checkout:
      enter image description here



      The last step at the checkout:
      enter image description here



      An order placed has been placed successfully without a zip code:
      enter image description here



      In the admin panel:
      enter image description here



      Everything works correctly!



      We provided the full research because it may help someone else.



      UPDATE (11.01.16)



      Sorry, we have misunderstood your question. Then, you need to use our first recommendation and slightly correct a code for the 'Magento_Ui/js/form/element/post-code.js' element. Perform the same actions, as described above but use the following code instead:



      return Abstract.extend({
      defaults: {
      imports: {
      update: '${ $.parentName }.country_id:value'
      }
      },

      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      if (option['is_zipcode_optional']) {
      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');
      } else {
      this.validation['required-entry'] = true;
      }
      }
      });


      We removed the this.required(!option['is_zipcode_optional']); line because it has activated the validation mechanism and caused the red frame to appear. Without this line everything should work smooth and the red frame won't appear.






      share|improve this answer















      We will begin with a research that will lead to a simple solution without any modifications in a code. If you don't have time to read the full answer, scroll down to the latest paragraphs with the answer.



      The magento/module-ui/view/base/web/js/form/element/post-code.js element has built-in validation right in the code:



      <script>
      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      if (option['is_zipcode_optional']) {
      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');
      } else {
      this.validation['required-entry'] = true;
      }

      this.required(!option['is_zipcode_optional']);
      }
      </script>


      That's why it is enabled all the time. The fastest solution is to rewrite this element and add your own code that will be inherited from the default.
      You can do this in the following way:



      The element itself for the post code is declared here:




      magento/module-checkout/view/frontend/layout/checkout_index_index.xml




      and has the following view:



      <item name="postcode" xsi:type="array">
      <!-- post-code field has custom UI component -->
      <item name="component" xsi:type="string">Magento_Ui/js/form/element/post-code</item>
      <item name="validation" xsi:type="array">
      <item name="required-entry" xsi:type="string">true</item>
      </item>
      </item>


      It is located in the <item name="shipping-address-fieldset" xsi:type="array"> container.



      To replace this element you will need your own module that will include a form update and a js element. This is the Vendor_Rules module in the example.



      Create a file:




      app/code/Vendor/Rules/view/frontend/requirejs-config.js`




      var config = {
      map: {
      '*': {
      "Magento_Ui/js/form/element/post-code": 'Vendor_Rules/js/form/element/post-code'
      }
      }
      };


      It should replace the default post-code element on the front-end.




      app/code/Vendor/Rules/view/frontend/web/js/form/element/post-code.js




      define([
      'underscore',
      'uiRegistry',
      'Magento_Ui/js/form/element/abstract'
      ], function (_, registry, Abstract) {
      'use strict';

      return Abstract.extend({
      defaults: {
      imports: {
      update: '${ $.parentName }.country_id:value'
      }
      },

      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');

      this.required(false);
      }
      });
      });


      This is almost the exact copy of the default element, excluding a zip validation for countries where it is not optional. Ino other words, it is required from Magento point of view.



      When done, run an update:



      bin/magento setup:upgrade
      bin/magento setup:static-content:deploy


      Refresh a cache and check the result. It will look the following way in our case:



      A new address form without required a zip code:
      enter image description here



      A new address saving without a zip code:
      enter image description here



      The last step at the Checkout:
      enter image description here



      And an error in the place order without a zip code:
      enter image description here



      As you can see, there is a validation of a zip code at the back-end. We should come over it.



      A validation is located in the customer address model MagentoCustomerModelAddressAbstractAddress, validate method:



          $_havingOptionalZip = $this->_directoryData->getCountriesWithOptionalZip();
      if (!in_array(
      $this->getCountryId(),
      $_havingOptionalZip
      ) && !Zend_Validate::is(
      $this->getPostcode(),
      'NotEmpty'
      )
      ) {
      $errors = __('Please enter the zip/postal code.');
      }


      The first solution is to add a zip code for all countries as optional. Let's check the getCountriesWithOptionalZip method:



      /**
      * Return ISO2 country codes, which have optional Zip/Postal pre-configured
      *
      * @param bool $asJson
      * @return array|string
      */
      public function getCountriesWithOptionalZip($asJson = false)
      {
      if (null === $this->_optZipCountries) {
      $value = trim(
      $this->scopeConfig->getValue(
      self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
      ScopeInterface::SCOPE_STORE
      )
      );
      $this->_optZipCountries = preg_split('/,/', $value, 0, PREG_SPLIT_NO_EMPTY);
      }
      if ($asJson) {
      return $this->jsonHelper->jsonEncode($this->_optZipCountries);
      }
      return $this->_optZipCountries;
      }


      As you can see from the country code, the countries with the optional zip code are taken from the _optZipCountries attribute that is filled in with data in the following way:



      $this->scopeConfig->getValue(
      self::OPTIONAL_ZIP_COUNTRIES_CONFIG_PATH,
      ScopeInterface::SCOPE_STORE
      )


      Values are stored in the system settings general/country/optional_zip_countries:



      enter image description here



      Finally, a simple solution:



      You don't need to modify a code. You should only select all countries as countries with an optional zip code. After that a validation for them will be disabled!



      Select all countries in the multiselect and save changes for the selected store. Then, disable our module and check the checkout:



      A new address in the checkout:
      enter image description here



      The last step at the checkout:
      enter image description here



      An order placed has been placed successfully without a zip code:
      enter image description here



      In the admin panel:
      enter image description here



      Everything works correctly!



      We provided the full research because it may help someone else.



      UPDATE (11.01.16)



      Sorry, we have misunderstood your question. Then, you need to use our first recommendation and slightly correct a code for the 'Magento_Ui/js/form/element/post-code.js' element. Perform the same actions, as described above but use the following code instead:



      return Abstract.extend({
      defaults: {
      imports: {
      update: '${ $.parentName }.country_id:value'
      }
      },

      /**
      * @param {String} value
      */
      update: function (value) {
      var country = registry.get(this.parentName + '.' + 'country_id'),
      options = country.indexedOptions,
      option;

      if (!value) {
      return;
      }

      option = options[value];

      if (option['is_zipcode_optional']) {
      this.error(false);
      this.validation = _.omit(this.validation, 'required-entry');
      } else {
      this.validation['required-entry'] = true;
      }
      }
      });


      We removed the this.required(!option['is_zipcode_optional']); line because it has activated the validation mechanism and caused the red frame to appear. Without this line everything should work smooth and the red frame won't appear.







      share|improve this answer














      share|improve this answer



      share|improve this answer








      edited Nov 1 '16 at 7:09

























      answered Oct 31 '16 at 10:23









      MageWorxMageWorx

      3,328512




      3,328512













      • Thanks for the elaborate answer. However, the 'required' system is working just fine. The only problem is that it highlights the postal code field when that checkout page loads. This is because in the previous step, you can already 'calculate shipping cost'. If you leave the field blank there and move on, the postal code field is the only field that highlights.. This looks weird. Is there a way to not 'trigger the requirement' on the load of this page?

        – Cake
        Oct 31 '16 at 13:32











      • @Cake please check the updated solution.

        – MageWorx
        Nov 1 '16 at 7:09











      • I've added these 2 files with the code you provided but it doesn't solve the issue. I did need to create all these folders, they weren't there: (app/code/)Vendor/Rules/view/frontend/web/js/form/element/ I presume 'Vendor' is the vendor of the template right?

        – Cake
        Nov 3 '16 at 23:18













      • Alright so i got it to work but now the field doesn't get checked anymore at all. Even if I set required to true..

        – Cake
        Nov 4 '16 at 0:04






      • 2





        @Cake It is possible, but we haven't tested the code at every step because we've tried to give you the right direction to solve your problem. Hope our solution has helped you.

        – MageWorx
        Nov 4 '16 at 9:14



















      • Thanks for the elaborate answer. However, the 'required' system is working just fine. The only problem is that it highlights the postal code field when that checkout page loads. This is because in the previous step, you can already 'calculate shipping cost'. If you leave the field blank there and move on, the postal code field is the only field that highlights.. This looks weird. Is there a way to not 'trigger the requirement' on the load of this page?

        – Cake
        Oct 31 '16 at 13:32











      • @Cake please check the updated solution.

        – MageWorx
        Nov 1 '16 at 7:09











      • I've added these 2 files with the code you provided but it doesn't solve the issue. I did need to create all these folders, they weren't there: (app/code/)Vendor/Rules/view/frontend/web/js/form/element/ I presume 'Vendor' is the vendor of the template right?

        – Cake
        Nov 3 '16 at 23:18













      • Alright so i got it to work but now the field doesn't get checked anymore at all. Even if I set required to true..

        – Cake
        Nov 4 '16 at 0:04






      • 2





        @Cake It is possible, but we haven't tested the code at every step because we've tried to give you the right direction to solve your problem. Hope our solution has helped you.

        – MageWorx
        Nov 4 '16 at 9:14

















      Thanks for the elaborate answer. However, the 'required' system is working just fine. The only problem is that it highlights the postal code field when that checkout page loads. This is because in the previous step, you can already 'calculate shipping cost'. If you leave the field blank there and move on, the postal code field is the only field that highlights.. This looks weird. Is there a way to not 'trigger the requirement' on the load of this page?

      – Cake
      Oct 31 '16 at 13:32





      Thanks for the elaborate answer. However, the 'required' system is working just fine. The only problem is that it highlights the postal code field when that checkout page loads. This is because in the previous step, you can already 'calculate shipping cost'. If you leave the field blank there and move on, the postal code field is the only field that highlights.. This looks weird. Is there a way to not 'trigger the requirement' on the load of this page?

      – Cake
      Oct 31 '16 at 13:32













      @Cake please check the updated solution.

      – MageWorx
      Nov 1 '16 at 7:09





      @Cake please check the updated solution.

      – MageWorx
      Nov 1 '16 at 7:09













      I've added these 2 files with the code you provided but it doesn't solve the issue. I did need to create all these folders, they weren't there: (app/code/)Vendor/Rules/view/frontend/web/js/form/element/ I presume 'Vendor' is the vendor of the template right?

      – Cake
      Nov 3 '16 at 23:18







      I've added these 2 files with the code you provided but it doesn't solve the issue. I did need to create all these folders, they weren't there: (app/code/)Vendor/Rules/view/frontend/web/js/form/element/ I presume 'Vendor' is the vendor of the template right?

      – Cake
      Nov 3 '16 at 23:18















      Alright so i got it to work but now the field doesn't get checked anymore at all. Even if I set required to true..

      – Cake
      Nov 4 '16 at 0:04





      Alright so i got it to work but now the field doesn't get checked anymore at all. Even if I set required to true..

      – Cake
      Nov 4 '16 at 0:04




      2




      2





      @Cake It is possible, but we haven't tested the code at every step because we've tried to give you the right direction to solve your problem. Hope our solution has helped you.

      – MageWorx
      Nov 4 '16 at 9:14





      @Cake It is possible, but we haven't tested the code at every step because we've tried to give you the right direction to solve your problem. Hope our solution has helped you.

      – MageWorx
      Nov 4 '16 at 9:14













      1














      This error is caused by a magento2 core error.



      Please have a look to this link : https://github.com/magento/magento2/issues/7724






      share|improve this answer




























        1














        This error is caused by a magento2 core error.



        Please have a look to this link : https://github.com/magento/magento2/issues/7724






        share|improve this answer


























          1












          1








          1







          This error is caused by a magento2 core error.



          Please have a look to this link : https://github.com/magento/magento2/issues/7724






          share|improve this answer













          This error is caused by a magento2 core error.



          Please have a look to this link : https://github.com/magento/magento2/issues/7724







          share|improve this answer












          share|improve this answer



          share|improve this answer










          answered Aug 10 '17 at 10:07









          Mathias ArlaudMathias Arlaud

          111




          111























              0














              please also look at this link it solved my issue : https://github.com/magento/magento2/issues/18630





              share




























                0














                please also look at this link it solved my issue : https://github.com/magento/magento2/issues/18630





                share


























                  0












                  0








                  0







                  please also look at this link it solved my issue : https://github.com/magento/magento2/issues/18630





                  share













                  please also look at this link it solved my issue : https://github.com/magento/magento2/issues/18630






                  share











                  share


                  share










                  answered 8 mins ago









                  TaseenTaseen

                  609




                  609






























                      draft saved

                      draft discarded




















































                      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.




                      draft saved


                      draft discarded














                      StackExchange.ready(
                      function () {
                      StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fmagento.stackexchange.com%2fquestions%2f143353%2fremove-postal-code-required%23new-answer', 'question_page');
                      }
                      );

                      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







                      Popular posts from this blog

                      What other Star Trek series did the main TNG cast show up in?

                      Berlina muro

                      Berlina aerponto