PluginProbe
Jetpack – WP Security, Backup, Speed, & Growth / 16.3-beta
Jetpack – WP Security, Backup, Speed, & Growth v16.3-beta
16.3 16.3-beta 16.3-a.5 16.3-a.7 16.3-a.3 16.3-a.1 16.2 16.2-beta 12.0.3 12.1.3 12.2.3 12.3.2 12.4.2 12.5.2 12.6.4 12.7.3 12.8.3 12.9.5 13.0.2 13.1.5 13.2.4 13.3.3 13.4.5 13.5.2 13.6.2 All 508 releases
jetpack / jetpack_vendor / automattic / jetpack-seo / src / class-local-business-schema-node.php

class-local-business-schema-node.php in Jetpack – WP Security, Backup, Speed, & Growth 16.3-beta, at jetpack_vendor/automattic/jetpack-seo/src/class-local-business-schema-node.php

130 lines 4.0 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * LocalBusiness Schema.org decorator for the site-level Organization node.
4 *
5 * Adds LocalBusiness properties to the existing Organization entity when the
6 * admin has enabled local-business schema and configured an address. This keeps
7 * all publisher references pointing at the same stable `#organization` node
8 * instead of introducing a second business entity.
9 *
10 * @package automattic/jetpack-seo-package
11 */
12
13 namespace Automattic\Jetpack\SEO;
14
15 /**
16 * Decorates the site-level Organization node with LocalBusiness details.
17 */
18 class Local_Business_Schema_Node {
19
20 /**
21 * Schema.org opening-hours day-code order and emitted day names.
22 *
23 * @var array<string, string>
24 */
25 const DAY_NAMES = array(
26 'Mo' => 'Monday',
27 'Tu' => 'Tuesday',
28 'We' => 'Wednesday',
29 'Th' => 'Thursday',
30 'Fr' => 'Friday',
31 'Sa' => 'Saturday',
32 'Su' => 'Sunday',
33 );
34
35 /**
36 * Extend an Organization node with LocalBusiness properties.
37 *
38 * @param array|null $organization Built Organization node (null passes through).
39 * @param array $settings Effective values from Schema_Settings::get_local_business().
40 * @return array|null
41 */
42 public static function extend( $organization, array $settings ) {
43 if ( null === $organization || ! is_array( $organization ) ) {
44 return $organization;
45 }
46
47 if ( empty( $settings['enabled'] ) ) {
48 return $organization;
49 }
50
51 $address = self::postal_address( isset( $settings['address'] ) && is_array( $settings['address'] ) ? $settings['address'] : array() );
52 if ( null === $address ) {
53 return $organization;
54 }
55
56 $organization['@type'] = array( 'Organization', 'LocalBusiness' );
57 $organization['address'] = $address;
58
59 foreach ( array( 'telephone', 'priceRange' ) as $field ) {
60 if ( ! empty( $settings[ $field ] ) && is_string( $settings[ $field ] ) ) {
61 $organization[ $field ] = $settings[ $field ];
62 }
63 }
64
65 if ( isset( $settings['geo'] ) && is_array( $settings['geo'] ) ) {
66 $latitude = $settings['geo']['latitude'] ?? '';
67 $longitude = $settings['geo']['longitude'] ?? '';
68 if ( is_numeric( $latitude ) && is_numeric( $longitude ) ) {
69 $organization['geo'] = array(
70 '@type' => 'GeoCoordinates',
71 'latitude' => (float) $latitude,
72 'longitude' => (float) $longitude,
73 );
74 }
75 }
76
77 $hours = self::opening_hours_specification( isset( $settings['openingHours'] ) && is_array( $settings['openingHours'] ) ? $settings['openingHours'] : array() );
78 if ( ! empty( $hours ) ) {
79 $organization['openingHoursSpecification'] = $hours;
80 }
81
82 return $organization;
83 }
84
85 /**
86 * Build a PostalAddress from non-empty address subfields.
87 *
88 * @param array $address Address settings.
89 * @return array|null
90 */
91 private static function postal_address( array $address ) {
92 $postal_address = array( '@type' => 'PostalAddress' );
93 foreach ( array( 'streetAddress', 'addressLocality', 'addressRegion', 'postalCode', 'addressCountry' ) as $field ) {
94 if ( ! empty( $address[ $field ] ) && is_string( $address[ $field ] ) ) {
95 $postal_address[ $field ] = $address[ $field ];
96 }
97 }
98
99 return count( $postal_address ) > 1 ? $postal_address : null;
100 }
101
102 /**
103 * Build OpeningHoursSpecification rows for fully configured days.
104 *
105 * @param array $opening_hours Opening-hours settings keyed by schema.org day code.
106 * @return array<int, array<string, string>>
107 */
108 private static function opening_hours_specification( array $opening_hours ) {
109 $specification = array();
110 foreach ( self::DAY_NAMES as $code => $day_name ) {
111 $entry = isset( $opening_hours[ $code ] ) && is_array( $opening_hours[ $code ] ) ? $opening_hours[ $code ] : array();
112 $opens = isset( $entry['opens'] ) && is_string( $entry['opens'] ) ? $entry['opens'] : '';
113 $closes = isset( $entry['closes'] ) && is_string( $entry['closes'] ) ? $entry['closes'] : '';
114
115 if ( '' === $opens || '' === $closes ) {
116 continue;
117 }
118
119 $specification[] = array(
120 '@type' => 'OpeningHoursSpecification',
121 'dayOfWeek' => $day_name,
122 'opens' => $opens,
123 'closes' => $closes,
124 );
125 }
126
127 return $specification;
128 }
129 }
130