Validate and prepare GTIN in structured data (#50926)

* Validate and prepare GTIN in structured data

* Add changelog

* PHPCS

* PHPCS

* Verify gtin is string in prepare gtin

* Tweak tests

* PHPCS

* Tweak is_valid_gtin

* LINT

* Update plugins/woocommerce/includes/class-wc-structured-data.php

Co-authored-by: Mik <mikkamp@users.noreply.github.com>

* Update plugins/woocommerce/includes/class-wc-structured-data.php

Co-authored-by: Mik <mikkamp@users.noreply.github.com>

* Update plugins/woocommerce/includes/class-wc-structured-data.php

Co-authored-by: Mik <mikkamp@users.noreply.github.com>

---------

Co-authored-by: Mik <mikkamp@users.noreply.github.com>
This commit is contained in:
Miguel Pérez Pellicer 2024-09-13 19:11:11 +04:00 committed by GitHub
parent ce618d6250
commit 737afc62e1
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 116 additions and 3 deletions

View File

@ -0,0 +1,4 @@
Significance: patch
Type: tweak
Validate and prepare GTIN in structured data

View File

@ -214,9 +214,9 @@ class WC_Structured_Data {
$markup['sku'] = $product->get_id();
}
// Add GTIN only if it's a valid number.
$gtin = $product->get_global_unique_id();
if ( $gtin && is_numeric( $gtin ) ) {
// Prepare GTIN and load it if it's valid.
$gtin = $this->prepare_gtin( $product->get_global_unique_id() );
if ( $this->is_valid_gtin( $gtin ) ) {
$markup['gtin'] = $gtin;
}
@ -577,4 +577,30 @@ class WC_Structured_Data {
$this->set_data( apply_filters( 'woocommerce_structured_data_order', $markup, $sent_to_admin, $order ), true );
}
/**
* Check if a GTIN is valid.
* A valid GTIN is a string containing 8,12,13 or 14 digits.
*
* @see https://schema.org/gtin
* @param string $gtin The GTIN to check.
* @return bool True if valid. False otherwise.
*/
public function is_valid_gtin( $gtin ) {
return is_string( $gtin ) && preg_match( '/^(\d{8}|\d{12,14})$/', $gtin );
}
/**
* Prepare a GTIN input removing everything except numbers.
*
* @param string $gtin The GTIN to prepare.
* @return string Empty string if no GTIN is provided or the string with the replacements.
*/
public function prepare_gtin( $gtin ) {
if ( ! $gtin || ! is_string( $gtin ) ) {
return '';
}
return preg_replace( '/[^0-9]/', '', $gtin );
}
}

View File

@ -0,0 +1,83 @@
<?php
declare( strict_types = 1 );
/**
* Class WC_Structured_Data_Test.
*/
class WC_Structured_Data_Test extends \WC_Unit_Test_Case {
/** @var WC_Structured_Data $structured_data */
public $structured_data;
/**
* Set up test
*
* @return void
*/
public function setUp(): void {
include_once WC_ABSPATH . 'includes/class-wc-structured-data.php';
$this->structured_data = new WC_Structured_Data();
parent::setUp();
}
/**
* Test is_valid_gtin function
*
* @return void
*/
public function test_is_valid_gtin(): void {
$valid_gtins = array(
'12345678',
'123456789012',
'1234567890123',
'12345678901234',
);
$invalid_gtins = array(
'',
null,
false,
12345678,
123.4e-5,
+1234567,
'abcdefgh',
'-9999999',
'12-45-66',
'123',
'123456789012345',
'123456789',
'1234567890',
'12 34 56 78',
'12 34 56',
'+12345678',
'123.4e-5',
);
foreach ( $valid_gtins as $valid_gtin ) {
$this->assertTrue( $this->structured_data->is_valid_gtin( $valid_gtin ) );
}
foreach ( $invalid_gtins as $invalid_gtin ) {
$this->assertFalse( $this->structured_data->is_valid_gtin( $invalid_gtin ) );
}
}
/**
* Test prepare_gtin function
*
* @return void
*/
public function test_prepare_gtin(): void {
$this->assertEquals( $this->structured_data->prepare_gtin( '123-456-78' ), '12345678' );
$this->assertEquals( $this->structured_data->prepare_gtin( '-123-456-78' ), '12345678' );
$this->assertEquals( $this->structured_data->prepare_gtin( 'GTIN: 123-456-78' ), '12345678' );
$this->assertEquals( $this->structured_data->prepare_gtin( '123 456 78' ), '12345678' );
$this->assertEquals( $this->structured_data->prepare_gtin( null ), '' );
$this->assertEquals( $this->structured_data->prepare_gtin( 'GTIN' ), '' );
$this->assertEquals( $this->structured_data->prepare_gtin( 123 ), '' );
$this->assertEquals( $this->structured_data->prepare_gtin( array( '123-456-78', '123-456-78' ) ), '' );
$this->assertEquals( $this->structured_data->prepare_gtin( '+12345678' ), '12345678' );
$this->assertEquals( $this->structured_data->prepare_gtin( '123.4e-5' ), '12345' );
}
}