Skip to content
This repository was archived by the owner on Oct 4, 2019. It is now read-only.

Commit 1c4e22f

Browse files
author
Justin Shreve
committed
Adds location data endpoints. Reviewed in woocommerce/woocommerce#15162
1 parent 3e799c1 commit 1c4e22f

File tree

5 files changed

+846
-0
lines changed

5 files changed

+846
-0
lines changed
Lines changed: 280 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,280 @@
1+
<?php
2+
/**
3+
* REST API Data controller.
4+
*
5+
* Handles requests to the /data/continents endpoint.
6+
*
7+
* @author Automattic
8+
* @category API
9+
* @package WooCommerce/API
10+
* @since 3.1.0
11+
*/
12+
13+
if ( ! defined( 'ABSPATH' ) ) {
14+
exit;
15+
}
16+
17+
/**
18+
* REST API Data controller class.
19+
*
20+
* @package WooCommerce/API
21+
* @extends WC_REST_Controller
22+
*/
23+
class WC_REST_Dev_Data_Continents_Controller extends WC_REST_Dev_Data_Controller {
24+
25+
/**
26+
* Endpoint namespace.
27+
*
28+
* @var string
29+
*/
30+
protected $namespace = 'wc/v3';
31+
32+
/**
33+
* Route base.
34+
*
35+
* @var string
36+
*/
37+
protected $rest_base = 'data/continents';
38+
39+
/**
40+
* Register routes.
41+
*
42+
* @since 3.1.0
43+
*/
44+
public function register_routes() {
45+
register_rest_route( $this->namespace, '/' . $this->rest_base, array(
46+
array(
47+
'methods' => WP_REST_Server::READABLE,
48+
'callback' => array( $this, 'get_items' ),
49+
'permission_callback' => array( $this, 'get_items_permissions_check' ),
50+
),
51+
'schema' => array( $this, 'get_public_item_schema' ),
52+
) );
53+
register_rest_route( $this->namespace, '/' . $this->rest_base . '/(?P<location>[\w-]+)', array(
54+
array(
55+
'methods' => WP_REST_Server::READABLE,
56+
'callback' => array( $this, 'get_item' ),
57+
'permission_callback' => array( $this, 'get_items_permissions_check' ),
58+
'args' => array(
59+
'continent' => array(
60+
'description' => __( '2 character continent code.', 'woocommerce' ),
61+
'type' => 'string',
62+
),
63+
),
64+
),
65+
'schema' => array( $this, 'get_public_item_schema' ),
66+
) );
67+
}
68+
69+
/**
70+
* Return the list of countries and states for a given continent.
71+
*
72+
* @since 3.1.0
73+
* @param string $continent_code
74+
* @param WP_REST_Request $request
75+
* @return array|mixed Response data, ready for insertion into collection data.
76+
*/
77+
public function get_continent( $continent_code = false, $request ) {
78+
$continents = WC()->countries->get_continents();
79+
$countries = WC()->countries->get_countries();
80+
$states = WC()->countries->get_states();
81+
$data = array();
82+
83+
if ( ! array_key_exists( $continent_code, $continents ) ) {
84+
return false;
85+
}
86+
87+
$continent_list = $continents[ $continent_code ];
88+
89+
$continent = array(
90+
'code' => $continent_code,
91+
'name' => $continent_list['name'],
92+
);
93+
94+
$local_countries = array();
95+
foreach ( $continent_list['countries'] as $country_code ) {
96+
if ( isset( $countries[ $country_code ] ) ) {
97+
$country = array(
98+
'code' => $country_code,
99+
'name' => $countries[ $country_code ],
100+
);
101+
102+
$local_states = array();
103+
if ( isset( $states[ $country_code ] ) ) {
104+
foreach ( $states[ $country_code ] as $state_code => $state_name ) {
105+
$local_states[] = array(
106+
'code' => $state_code,
107+
'name' => $state_name,
108+
);
109+
}
110+
}
111+
$country['states'] = $local_states;
112+
$local_countries[] = $country;
113+
}
114+
}
115+
116+
$continent['countries'] = $local_countries;
117+
return $continent;
118+
}
119+
120+
/**
121+
* Return the list of states for all continents.
122+
*
123+
* @since 3.1.0
124+
* @param WP_REST_Request $request
125+
* @return WP_Error|WP_REST_Response
126+
*/
127+
public function get_items( $request ) {
128+
$continents = WC()->countries->get_continents();
129+
$data = array();
130+
131+
foreach ( array_keys( $continents ) as $continent_code ) {
132+
$continent = $this->get_continent( $continent_code, $request );
133+
$response = $this->prepare_item_for_response( $continent, $request );
134+
$data[] = $this->prepare_response_for_collection( $response );
135+
}
136+
137+
return rest_ensure_response( $data );
138+
}
139+
140+
/**
141+
* Return the list of locations for a given continent.
142+
*
143+
* @since 3.1.0
144+
* @param WP_REST_Request $request
145+
* @return WP_Error|WP_REST_Response
146+
*/
147+
public function get_item( $request ) {
148+
$data = $this->get_continent( strtoupper( $request['location'] ), $request );
149+
if ( empty( $data ) ) {
150+
return new WP_Error( 'woocommerce_rest_data_invalid_location', __( 'There are no locations matching these parameters.', 'woocommerce' ), array( 'status' => 404 ) );
151+
}
152+
return $this->prepare_item_for_response( $data, $request );
153+
}
154+
155+
/**
156+
* Prepare the data object for response.
157+
*
158+
* @since 3.1.0
159+
* @param object $item Data object.
160+
* @param WP_REST_Request $request Request object.
161+
* @return WP_REST_Response $response Response data.
162+
*/
163+
public function prepare_item_for_response( $item, $request ) {
164+
$data = $this->add_additional_fields_to_object( $item, $request );
165+
$data = $this->filter_response_by_context( $data, 'view' );
166+
$response = rest_ensure_response( $data );
167+
168+
$response->add_links( $this->prepare_links( $item ) );
169+
170+
/**
171+
* Filter the location list returned from the API.
172+
*
173+
* Allows modification of the loction data right before it is returned.
174+
*
175+
* @param WP_REST_Response $response The response object.
176+
* @param array $item The original list of continent(s), countries, and states.
177+
* @param WP_REST_Request $request Request used to generate the response.
178+
*/
179+
return apply_filters( 'woocommerce_rest_prepare_data_continent', $response, $item, $request );
180+
}
181+
182+
/**
183+
* Prepare links for the request.
184+
*
185+
* @param object $item Data object.
186+
* @return array Links for the given continent.
187+
*/
188+
protected function prepare_links( $item ) {
189+
$continent_code = strtolower( $item['code'] );
190+
$links = array(
191+
'self' => array(
192+
'href' => rest_url( sprintf( '/%s/%s/%s', $this->namespace, $this->rest_base, $continent_code ) ),
193+
),
194+
'collection' => array(
195+
'href' => rest_url( sprintf( '/%s/%s', $this->namespace, $this->rest_base ) ),
196+
),
197+
);
198+
return $links;
199+
}
200+
201+
/**
202+
* Get the location schema, conforming to JSON Schema.
203+
*
204+
* @since 3.1.0
205+
* @return array
206+
*/
207+
public function get_item_schema() {
208+
$schema = array(
209+
'$schema' => 'http://json-schema.org/draft-04/schema#',
210+
'title' => 'data_continents',
211+
'type' => 'object',
212+
'properties' => array(
213+
'code' => array(
214+
'type' => 'string',
215+
'description' => __( '2 character continent code.', 'woocommerce' ),
216+
'context' => array( 'view' ),
217+
'readonly' => true,
218+
),
219+
'name' => array(
220+
'type' => 'string',
221+
'description' => __( 'Full name of continent.', 'woocommerce' ),
222+
'context' => array( 'view' ),
223+
'readonly' => true,
224+
),
225+
'countries' => array(
226+
'type' => 'array',
227+
'description' => __( 'List of countries on this continent.', 'woocommerce' ),
228+
'context' => array( 'view' ),
229+
'readonly' => true,
230+
'items' => array(
231+
'type' => 'object',
232+
'context' => array( 'view' ),
233+
'readonly' => true,
234+
'properties' => array(
235+
'code' => array(
236+
'type' => 'string',
237+
'description' => __( 'ISO3166 alpha-2 country code.', 'woocommerce' ),
238+
'context' => array( 'view' ),
239+
'readonly' => true,
240+
),
241+
'name' => array(
242+
'type' => 'string',
243+
'description' => __( 'Full name of country.', 'woocommerce' ),
244+
'context' => array( 'view' ),
245+
'readonly' => true,
246+
),
247+
'states' => array(
248+
'type' => 'array',
249+
'description' => __( 'List of states in this country.', 'woocommerce' ),
250+
'context' => array( 'view' ),
251+
'readonly' => true,
252+
'items' => array(
253+
'type' => 'object',
254+
'context' => array( 'view' ),
255+
'readonly' => true,
256+
'properties' => array(
257+
'code' => array(
258+
'type' => 'string',
259+
'description' => __( 'State code.', 'woocommerce' ),
260+
'context' => array( 'view' ),
261+
'readonly' => true,
262+
),
263+
'name' => array(
264+
'type' => 'string',
265+
'description' => __( 'Full name of state.', 'woocommerce' ),
266+
'context' => array( 'view' ),
267+
'readonly' => true,
268+
),
269+
),
270+
),
271+
),
272+
),
273+
),
274+
),
275+
),
276+
);
277+
278+
return $this->add_additional_fields_schema( $schema );
279+
}
280+
}

0 commit comments

Comments
 (0)