├── .gitattributes ├── .gitignore ├── Chapter_01_Codes ├── rest-chash.txt ├── rest-java.txt ├── rest-js.txt ├── rest-perl.txt ├── rest-php.txt ├── rest-python.txt └── rest-ruby.txt ├── Chapter_02_Codes ├── chapter2-getmeta.txt ├── chapter2-getrequest.txt ├── chapter2-postmeta.txt ├── chapter2-postoutputs.txt ├── chapter2-remotecopy.txt └── chapter2-remotecreate.txt ├── Chapter_03_Codes ├── code-file-1.txt ├── code-file-2.txt ├── code-file-3.txt ├── code-file-4.txt └── code-file-5.txt ├── Chapter_04_Codes ├── code-file-chap4-1.txt ├── code-file-chap4-2.txt └── code-file-chap4-3.txt ├── Chapter_05_Codes ├── code-file-1.txt └── code-file-2.txt ├── Chapter_06_Codes ├── code-chap6-1.txt ├── code-chap6-2.txt ├── code-chap6-3.txt └── code-chap6-4.txt ├── README.md └── license /.gitattributes: -------------------------------------------------------------------------------- 1 | # Auto detect text files and perform LF normalization 2 | * text=auto 3 | 4 | # Custom for Visual Studio 5 | *.cs diff=csharp 6 | 7 | # Standard to msysgit 8 | *.doc diff=astextplain 9 | *.DOC diff=astextplain 10 | *.docx diff=astextplain 11 | *.DOCX diff=astextplain 12 | *.dot diff=astextplain 13 | *.DOT diff=astextplain 14 | *.pdf diff=astextplain 15 | *.PDF diff=astextplain 16 | *.rtf diff=astextplain 17 | *.RTF diff=astextplain 18 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Windows image file caches 2 | Thumbs.db 3 | ehthumbs.db 4 | 5 | # Folder config file 6 | Desktop.ini 7 | 8 | # Recycle Bin used on file shares 9 | $RECYCLE.BIN/ 10 | 11 | # Windows Installer files 12 | *.cab 13 | *.msi 14 | *.msm 15 | *.msp 16 | 17 | # Windows shortcuts 18 | *.lnk 19 | 20 | # ========================= 21 | # Operating System Files 22 | # ========================= 23 | 24 | # OSX 25 | # ========================= 26 | 27 | .DS_Store 28 | .AppleDouble 29 | .LSOverride 30 | 31 | # Thumbnails 32 | ._* 33 | 34 | # Files that might appear in the root of a volume 35 | .DocumentRevisions-V100 36 | .fseventsd 37 | .Spotlight-V100 38 | .TemporaryItems 39 | .Trashes 40 | .VolumeIcon.icns 41 | 42 | # Directories potentially created on remote AFP share 43 | .AppleDB 44 | .AppleDesktop 45 | Network Trash Folder 46 | Temporary Items 47 | .apdisk 48 | -------------------------------------------------------------------------------- /Chapter_01_Codes/rest-chash.txt: -------------------------------------------------------------------------------- 1 | static string HttpGet(string url) { 2 | HttpWebRequest req = WebRequest.Create(url) 3 | as HttpWebRequest; 4 | string result = null; 5 | using (HttpWebResponse resp = req.GetResponse() 6 | as HttpWebResponse) 7 | { 8 | StreamReader reader = 9 | new StreamReader(resp.GetResponseStream()); 10 | result = reader.ReadToEnd(); 11 | } 12 | return result; 13 | } 14 | 15 | /*POST request*/ 16 | static string HttpPost(string url, 17 | string[] prName, string[] prVal) 18 | { 19 | HttpWebRequest req = WebRequest.Create(new Uri(url)) 20 | as HttpWebRequest; 21 | req.Method = "POST"; 22 | req.ContentType = "application/x-www-form-urlencoded"; 23 | 24 | // Creating a string, encoded and with all parameters 25 | // Assuming that the arrays prName and prVal are of equal length 26 | StringBuilder przz = new StringBuilder(); 27 | for (int i = 0; i < prName.Length; i++) { 28 | przz.Append(prName[i]); 29 | przz.Append("="); 30 | przz.Append(HttpUtility.UrlEncode(prVal[i])); 31 | przz.Append("&"); 32 | } 33 | 34 | // Encoding the parameters 35 | byte[] frDat = 36 | UTF8Encoding.UTF8.GetBytes(przz.ToString()); 37 | req.ContentLength = frDat.Length; 38 | 39 | // Sending the request 40 | using (Stream post = req.GetRequestStream()) 41 | { 42 | post.Write(frDat, 0, frDat.Length); 43 | } 44 | 45 | // Getting the response 46 | string result = null; 47 | using (HttpWebResponse resp = req.GetResponse() 48 | as HttpWebResponse) 49 | { 50 | StreamReader reader = 51 | new StreamReader(resp.GetResponseStream()); 52 | result = reader.ReadToEnd(); 53 | } 54 | 55 | return result; 56 | } 57 | -------------------------------------------------------------------------------- /Chapter_01_Codes/rest-java.txt: -------------------------------------------------------------------------------- 1 | public static String httpGet(String urlStr) throws IOException { 2 | URL url = new URL(urlStr); 3 | HttpURLConnection conn = 4 | (HttpURLConnection) url.openConnection(); 5 | if (conn.getResponseCode() != 200) { 6 | throw new IOException(conn.getResponseMessage()); 7 | } 8 | // Buffering the result into a string 9 | BufferedReader drdr = new BufferedReader( 10 | new InputStreamReader(conn.getInputStream())); 11 | StringBuilder sb = new StringBuilder(); 12 | String line; 13 | while ((line = drdr.readLine()) != null) { 14 | sb.append(line); 15 | } 16 | drdr.close(); 17 | conn.disconnect(); 18 | return sb.toString(); 19 | } 20 | 21 | //POST request 22 | 23 | public static String httpPost(String urlStr, String[] prName, 24 | String[] prVal) throws Exception { 25 | URL url = new URL(urlStr); 26 | HttpURLConnection conn = 27 | (HttpURLConnection) url.openConnection(); 28 | conn.setRequestMethod("POST"); 29 | conn.setDoOutput(true); 30 | conn.setDoInput(true); 31 | conn.setUseCaches(false); 32 | conn.setAllowUserInteraction(false); 33 | conn.setRequestProperty("Content-Type", 34 | "application/x-www-form-urlencoded"); 35 | 36 | // Creating form content 37 | OutputStream out = conn.getOutputStream(); 38 | Writer writer = new OutputStreamWriter(out, "UTF-8"); 39 | for (int i = 0; i < prName.length; i++) { 40 | writer.write(prName[i]); 41 | writer.write("="); 42 | writer.write(URLEncoder.encode(prVal[i], "UTF-8")); 43 | writer.write("&"); 44 | } 45 | writer.close(); 46 | out.close(); 47 | 48 | if (conn.getResponseCode() != 200) { 49 | throw new IOException(conn.getResponseMessage()); 50 | } 51 | 52 | // Buffering the result into a string 53 | BufferedReader drdr = new BufferedReader( 54 | new InputStreamReader(conn.getInputStream())); 55 | StringBuilder bsbs = new StringBuilder(); 56 | String line; 57 | while ((line = drdr.readLine()) != null) { 58 | bsbs.append(line); 59 | } 60 | drdr.close(); 61 | 62 | conn.disconnect(); 63 | return bsbs.toString(); 64 | } 65 | 66 | -------------------------------------------------------------------------------- /Chapter_01_Codes/rest-js.txt: -------------------------------------------------------------------------------- 1 | function createRequest() { 2 | var result = null; 3 | if (window.XMLHttpRequest) { 4 | result = new XMLHttpRequest(); 5 | if (typeof xmlhttp.overrideMimeType != 'undefined') { 6 | result.overrideMimeType('text/xml'); // Or anything else 7 | } 8 | } 9 | else if (window.ActiveXObject) { 10 | result = new ActiveXObject("Microsoft.XMLHTTP"); 11 | } 12 | return result; 13 | } 14 | 15 | -------------------------------------------------------------------------------- /Chapter_01_Codes/rest-perl.txt: -------------------------------------------------------------------------------- 1 | my $browser = LWP::UserAgent->new; 2 | my $url = 'http://www.example.com/database/1191'; 3 | my $response = $browser->post($url, 4 | [ 5 | 'firstName' => 'Sample', 6 | 'lastName' => 'User' 7 | ]; 8 | ); 9 | die 'Error getting $url' unless $response->is_success; 10 | print 'Content type is ', $response->content_type; 11 | print 'Content is:'; 12 | print $response->content; 13 | -------------------------------------------------------------------------------- /Chapter_01_Codes/rest-php.txt: -------------------------------------------------------------------------------- 1 | function httpRequest($host, $port, $method, $path, $prms) { 2 | // prms is to map from name to value 3 | $prmstr = ""; 4 | foreach ($prms as $name, $val) { 5 | $prmstr .= $name . "="; 6 | $prmstr .= urlencode($val); 7 | $prmstr .= "&"; 8 | } 9 | // Assign defaults to $method and $port 10 | if (empty($method)) { 11 | $method = 'GET'; 12 | } 13 | $method = strtoupper($method); 14 | if (empty($port)) { 15 | $port = 80; // Default HTTP port 16 | } 17 | 18 | // Create the connection 19 | $sock = fsockopen($host, $port); 20 | if ($method == "GET") { 21 | $path .= "?" . $prmstr; 22 | } 23 | fputs($sock, "$method $path HTTP/1.1\r\n"); 24 | fputs($sock, "Host: $host\r\n"); 25 | fputs($sock, "Content-type: " . 26 | "application/x-www-form-urlencoded\r\n"); 27 | if ($method == "POST") { 28 | fputs($sock, "Content-length: " . 29 | strlen($prmstr) . "\r\n"); 30 | } 31 | fputs($sock, "Connection: close\r\n\r\n"); 32 | if ($method == "POST") { 33 | fputs($sock, $prmstr); 34 | } 35 | // Buffer the result 36 | $result = ""; 37 | while (!feof($sock)) { 38 | $result .= fgets($sock,1024); 39 | } 40 | fclose($sock); 41 | return $result; 42 | } 43 | 44 | -------------------------------------------------------------------------------- /Chapter_01_Codes/rest-python.txt: -------------------------------------------------------------------------------- 1 | import urllib2 2 | url = 'http://www.example.com/database/1191' 3 | response = urllib2.urlopen(url).read() 4 | And for POST requests, we will once again rely on the urllib2 module: 5 | import urllib 6 | import urllib2 7 | url = 'http://www.example.com/database/user' 8 | params = urllib.urlencode({ 9 | 'firstName': 'Sample', 10 | 'lastName': 'User' 11 | }) 12 | response = urllib2.urlopen(url, params).read() 13 | -------------------------------------------------------------------------------- /Chapter_01_Codes/rest-ruby.txt: -------------------------------------------------------------------------------- 1 | require 'net/http' 2 | url = 'http://www.example.com/database/1191' 3 | resp = Net::HTTP.get_response(URI.parse(url)) 4 | resp_text = resp.body 5 | In the above example, we are using an object to handle the HTTP response code. 6 | Similarly, for POST requests: 7 | require 'net/http' 8 | url = 'http://www.example.com/database/user' 9 | params = { 10 | firstName => 'Sample', 11 | lastName => 'User' 12 | } 13 | resp = Net::HTTP.post_form(url, params) 14 | resp_text = resp.body 15 | -------------------------------------------------------------------------------- /Chapter_02_Codes/chapter2-getmeta.txt: -------------------------------------------------------------------------------- 1 | //GET post meta fields; chapter 2 2 | 3 | function get_post_meta_clbk( $object, $field_name, $request ) { 4 | return get_post_meta( $object[ 'id' ], $field_name ); 5 | } 6 | function update_post_meta_clbk( $value, $object, $field_name ) { 7 | return update_post_meta( $object[ 'id' ], $field_name, $value ); 8 | } 9 | 10 | add_action( 'rest_api_init', function() { 11 | register_api_field( 'painter', 12 | 'water_color', 13 | array( 14 | 'get_callback' => 'get_post_meta_clbk', 15 | 'update_callback' => 'update_post_meta_clbk', 16 | 'schema' => null, 17 | ) 18 | ); 19 | }); 20 | -------------------------------------------------------------------------------- /Chapter_02_Codes/chapter2-getrequest.txt: -------------------------------------------------------------------------------- 1 | //GET request; chapter 2 2 | 3 | $response = wp_remote_get( $url ); 4 | function get_json( $url ) { 5 | //GET remote site 6 | $response = wp_remote_get( $url ); 7 | //Checking for errors 8 | if ( is_wp_error( $response ) ) { 9 | return sprintf( 'Your URL %1s could not be retrieved', $url ); 10 | //GET only body 11 | $data = wp_remote_retrieve_body( $response ); 12 | } 13 | //return if no error 14 | if ( ! is_wp_error( $response ) ) { 15 | //Now, decode and return 16 | return json_decode( $response ); 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /Chapter_02_Codes/chapter2-postmeta.txt: -------------------------------------------------------------------------------- 1 | //POST meta fields; chapter 2 2 | 3 | //GET URL request 4 | $url = rest_url( 'wp/v2/posts/1/meta' ); 5 | //ADD basic headers for authentication 6 | $headers = array ( 7 | 'Authorization' => 'Basic ' . base64_encode( 'admin' . ':' . 'password' ), 8 | ); 9 | //ADD meta value to body 10 | $body = array( 11 | 'key' => 'water_color', 12 | 'value' => 'blue' 13 | ); 14 | //POST request 15 | $response = wp_remote_request( $url, array( 16 | 'method' => 'POST', 17 | 'headers' => $headers, 18 | 'body' => $body 19 | ) 20 | ); 21 | //if no error, we GET ID of meta key 22 | $body = wp_remote_retrieve_body( $response ); 23 | if ( ! is_wp_error( $body ) ) { 24 | $body = json_decode( $body ); 25 | $meta_id = $body->id; 26 | echo $body->value; 27 | if ( $meta_id ) { 28 | //ADD meta ID to URL 29 | $url .= '/' . $meta_id; 30 | //SEND value 31 | $body = array( 32 | 'value' => 'blue' 33 | ); 34 | $response = wp_remote_request( $url, array( 35 | 'method' => 'POST', 36 | ) 37 | ); 38 | 'headers' => $headers, 39 | 'body' => $body 40 | //if no error, then echo the value 41 | $body = wp_remote_retrieve_body( $response ); 42 | if ( ! is_wp_error( $body ) ) { 43 | $body = json_decode( $body ); 44 | echo $body->value; 45 | } 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /Chapter_02_Codes/chapter2-postoutputs.txt: -------------------------------------------------------------------------------- 1 | //Post output; chapter 2 2 | 3 | $response = wp_remote_get( $url ); 4 | function get_json( $url ) { 5 | //GET remote site 6 | $response = wp_remote_get( $url ); 7 | //Checking for errors 8 | if ( is_wp_error( $response ) ) { 9 | return sprintf( 'Your URL %1s could not be retrieved', $url ); 10 | //GET only body 11 | $data = wp_remote_retrieve_body( $response ); 12 | } 13 | //return if no error 14 | if ( ! is_wp_error( $response ) ) { 15 | //Now, decode and return 16 | return json_decode( $response ); 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /Chapter_02_Codes/chapter2-remotecopy.txt: -------------------------------------------------------------------------------- 1 | //Copy post from remote site; chapter 2 2 | 3 | function insert_post_from_json( $post ) { 4 | //checking to see if array or object; because we can work only with array 5 | if ( is_array( $post ) || ( is_object( $post ) && ! is_wp_error( $post ) ) ) { 6 | //ensure $post is an array; or force typecast 7 | $post = (array) $post; 8 | } 9 | else { 10 | return sprintf( '%1s must be an object or array', __FUNCTION__ ); 11 | } 12 | //Create new array for conversion 13 | //Set ID as post_id to try and use the same ID; note that leaving ID as ID would //UPDATE an existing post of the same ID 14 | $convert_keys = array( 15 | 'title' => 'post_title', 16 | 'content' => 'post_content', 17 | 'slug' => 'post_name', 18 | 'status' => 'post_status', 19 | 'parent' => 'post_parent', 20 | 'excerpt' => 'post_excerpt', 21 | 'date' => 'post_date', 22 | 'type' => 'post_type', 23 | 'ID' => 'post_id', 24 | ); 25 | //copy API response and unset old key 26 | foreach ( $convert_keys as $from => $to ) { 27 | if ( isset( $post[ $from ] ) ) { 28 | $post[ $to ] = $post[ $from ]; 29 | unset( $post[ $from ] ); 30 | } 31 | } 32 | //remove all keys of $post that are disallowed and convert objects (if any) to strings 33 | $allowed = array_values( $convert_keys ); 34 | foreach( $post as $key => $value ) { 35 | if( ! in_array( $key, $allowed ) ) { 36 | unset( $post[ $key ] ); 37 | } else{ 38 | if ( is_object( $value ) ) { 39 | $post[ $key ] = $value->rendered; 40 | } 41 | } 42 | } 43 | //All done. Create post and return its ID 44 | return wp_insert_post( $post ); 45 | } 46 | 47 | -------------------------------------------------------------------------------- /Chapter_02_Codes/chapter2-remotecreate.txt: -------------------------------------------------------------------------------- 1 | //Create post on remote site; chapter 2 2 | 3 | //Authentication 4 | $url = 'http://example.com/wp-json/wp/v2/posts/1'; 5 | $body = get_json( $url ); 6 | if ( is_object( $post ) ) { 7 | $body = $post; 8 | $headers = array ( 9 | 'Authorization' => 'Basic ' . base64_encode( 'admin' . ':' . 'password' ), 10 | ); 11 | $remote_url = 'http://example-remote.com/wp-json/wp/v2/posts'; 12 | } 13 | 14 | $headers = array ('Authorization' => 'Basic ' . base64_encode( 'admin' . ':' . 'password' ), 15 | ); 16 | 17 | //Copying response 18 | $response = wp_remote_post( $remote_url, array ( 19 | 'method' => 'POST', 20 | 'timeout' => 45, 21 | 'redirection' => 5, 22 | 'httpversion' => '1.0', 23 | 'blocking' => true, 24 | 'headers' => $headers, 25 | 'body' => json_encode( $post ), 26 | 'cookies' => array () 27 | ) 28 | ); 29 | 30 | //Checking if error occurred. 31 | if ( is_wp_error( $response ) ) { 32 | $error_message = $response->get_error_message(); 33 | echo sprintf( '

Error: %1s

', $error_message ); 34 | } 35 | else { 36 | echo 'Response:
';	
37 | 	print_r( $response );
38 | 	echo '
'; 39 | } 40 | } 41 | else { 42 | $error_message = 'Data invalid!'; 43 | echo sprintf( '

Error: %1s

', $error_message ); 44 | } 45 | 46 | -------------------------------------------------------------------------------- /Chapter_03_Codes/code-file-1.txt: -------------------------------------------------------------------------------- 1 | $sites = wp_get_sites(); 2 | $the_list = arr(); 3 | foreach( $sites as $site ) { 4 | $response = wp_remote_get( get_rest_url( $site->site_id, 'wp/v2/terms/categories' ) ); 5 | if ( ! is_wp_error( $response ) ) { 6 | $terms = json_decode( wp_remote_retrieve_body( $response ) ); 7 | $term_list = arr(); 8 | foreach( $terms as $term ) { 9 | $term_list[] = sprintf( '
  • %2s
  • ', esc_url( $term->link 10 | ),$term->name ); 11 | } 12 | if ( ! empty( $term_list ) ) { 13 | $site_info = get_blog_details( $site->site_id ); 14 | $term_list = sprintf( '', implode( $term_list ) ); 15 | $the_list[] = sprintf( '
  • %2s', $site_info- 16 | >siteurl, $site_info->blogname, $term_list ); 17 | } 18 | 19 | } 20 | } 21 | if ( ! empty( $the_list ) ) { 22 | echo sprintf( '', implode( $the_list ) ); 23 | } 24 | //end of code 25 | 26 | //Same code, but not multisite. (this will not run on WPMU) 27 | $response = wp_remote_get( rest_url( 'wp/v2/terms/categories' ) ); 28 | if ( ! is_wp_error( $response ) ) { 29 | $terms = json_decode( wp_remote_retrieve_body( $response ) ); 30 | $term_list = array(); 31 | foreach( $terms as $term ) { 32 | $term_list[] = sprintf( '
  • %2s
  • ', esc_url( $term->link 33 | ),$term->name ); 34 | } 35 | if ( ! empty( $term_list ) ) { 36 | echo sprintf( '', implode( $term_list ) ); 37 | } 38 | } 39 | 40 | -------------------------------------------------------------------------------- /Chapter_03_Codes/code-file-2.txt: -------------------------------------------------------------------------------- 1 | //GET request 2 | $url = rest_url( 'wp/v2/posts/1/terms/category' ); 3 | $response = wp_remote_request( $url, array( 4 | 'method' => 'GET' 5 | ) 6 | ); 7 | $body = wp_remote_retrieve_body( $response ); 8 | if ( ! is_wp_error( $body ) ) { 9 | //Decoding 10 | $terms = json_decode( $body ); 11 | $terms = array_combine( wp_list_pluck( $terms, 'slug' ), wp_list_pluck( $terms, id ) ); 12 | } 13 | 14 | //Checking for the taxonomy terms 15 | if ( isset( $terms[ 'example' ] ) ) { 16 | 17 | //get term ID 18 | $term_id = $terms['example']; 19 | 20 | //Adding ID to URL 21 | $term_url = $url . '/' . $term_id; 22 | //DELETE request 23 | $headers = array( 24 | 'headers' => array( 25 | 'Authorization' => 'Basic ' . base64_encode( 'admin : password' ), 26 | ) 27 | ); 28 | $response = wp_remote_request( $term_url, 29 | array( 30 | 'method' => 'DELETE', 31 | 'headers' => $headers 32 | ) 33 | ); 34 | } 35 | 36 | -------------------------------------------------------------------------------- /Chapter_03_Codes/code-file-3.txt: -------------------------------------------------------------------------------- 1 | 'GET', 16 | ) 17 | ); 18 | $body = wp_remote_retrieve_body( $response ); 19 | if ( ! is_wp_error( $body ) ) { 20 | $terms = json_decode( $body ); 21 | if ( ! empty( $terms ) ) { 22 | $term_id = false; 23 | foreach ( $terms as $term ) { 24 | if ( $term->slug == $term_slug ) { 25 | $term_id = $term->id; 26 | break; 27 | } 28 | } 29 | //Auth headers for POST request 30 | $headers['Authorization'] = $auth_header; 31 | //If term doesn't exist, we create it 32 | if ( ! $term_id ) { 33 | //PUT term slug and name in request 34 | $body = array( 35 | 'slug' => sanitize_title( $term_slug ), 36 | 'name' => $term_name 37 | ); 38 | //POST request 39 | $create_term_url = rest_url( 'wp/v2/terms/' . $taxonomy ); 40 | //Create term 41 | $response = wp_remote_request( $create_term_url, 42 | array( 43 | 'method' => 'POST', 44 | 'headers' => $headers, 45 | 'body' => $body, 46 | ) 47 | ); 48 | //wp_die( print_r( $response ) ); 49 | //Finding term ID 50 | $body = wp_remote_retrieve_body( $response ); 51 | if ( ! is_wp_error( $body ) ) { 52 | $term = json_decode( $body ); 53 | if ( is_object( $term ) && isset( $term->id ) ) { 54 | $term_id = $term->id; 55 | } 56 | } 57 | } 58 | //Adding term ID to post 59 | if ( $term_id ) { 60 | //Create URL for request 61 | $post_term_url = rest_url( 'wp/v2/' . $post_type . '/' . $post_id . '/ 62 | terms/' . $taxonomy . '/' . $term_id ); 63 | //POST request 64 | $response = wp_remote_request( $post_term_url, 65 | array( 66 | 'method' => 'POST', 67 | 'headers' => $headers 68 | ) 69 | ); 70 | do_action( 'slug_post_term_update', $response, $post_id, $post_type, 71 | $taxonomy, $term_slug ) 72 | } 73 | } 74 | return $term_id; 75 | } 76 | } 77 | 78 | -------------------------------------------------------------------------------- /Chapter_03_Codes/code-file-4.txt: -------------------------------------------------------------------------------- 1 | $.ajax( { 2 | url: Slug_API_Settings.root + 'wp/v2/users/', 3 | method: 'POST', 4 | beforeSend: function ( xhr ) { 5 | xhr.setRequestHeader( 'X-WP-Nonce', Slug_API_Settings.nonce ); 6 | }, 7 | data:{ 8 | email: 'test@example.com', 9 | username: 'usertest', 10 | password: Math.random().toString(46).substring(8) 11 | } 12 | } ).done( function ( response ) { 13 | console.log( response ); 14 | } ) 15 | 16 | //same code, but authentication is different 17 | add_action( 'wp_enqueue_scripts', function() { 18 | wp_enqueue_scripts( 'user-editor', plugin_dir_url( __FILE__ ) .'user-editor.js', array('jquery') 19 | ); 20 | wp_localize_scripts( 'user-editor', 'Slug_API_Settings', array( 21 | 'root' => esc_url_raw( rest_url() ), 22 | 'nonce' => wp_create_nonce( 'wp_rest' ), 23 | 'current_user_id' => (int) get_current_user_id() 24 | ) ); 25 | }); 26 | 27 | -------------------------------------------------------------------------------- /Chapter_03_Codes/code-file-5.txt: -------------------------------------------------------------------------------- 1 | jQuery( document ).ready(function( $ ) { 2 | $.ajax( { 3 | url: Slug_API_Settings.root + 'wp/v2/users/' + Slug_API_Settings.current_user_id + '?context=edit', 4 | method: 'GET', 5 | beforeSend: function ( xhr ) { 6 | xhr.setRequestHeader( 'X-WP-Nonce', Slug_API_Settings.nonce ); 7 | } 8 | } ).done( function ( user ) { 9 | $( '#username' ).html( '

    ' + user.name + '

    ' ); 10 | $( '#email' ).val( user.email ); 11 | } ); 12 | }); 13 | 14 | jQuery( document ).ready(function( $ ) { 15 | var get_user_data; 16 | (get_user_data = function () { 17 | $.ajax( { 18 | url: Slug_API_Settings.root + 'wp/v2/users/' + Slug_API_Settings.current_user_id + 19 | '?context=edit', 20 | method: 'GET', 21 | beforeSend: function ( xhr ) { 22 | xhr.setRequestHeader( 'X-WP-Nonce', Slug_API_Settings.nonce ); 23 | } 24 | } ).done( function ( user ) { 25 | $( '#username' ).html( '

    ' + user.name + '

    ' ); 26 | $( '#email' ).val( user.email ); 27 | } ); 28 | })(); 29 | $( '#profile-form' ).on( 'submit', function(e) { 30 | e.preventDefault(); 31 | $.ajax( { 32 | url: Slug_API_Settings.root + 'wp/v2/users/' + Slug_API_Settings.current_user_id, 33 | method: 'POST', 34 | beforeSend: function ( xhr ) { 35 | xhr.setRequestHeader( 'X-WP-Nonce', Slug_API_Settings.nonce ); 36 | }, 37 | data:{ 38 | email: $( '#email' ).val() 39 | } 40 | } ).done( function ( response ) { 41 | console.log( response ) 42 | } ) 43 | }); 44 | }); 45 | 46 | -------------------------------------------------------------------------------- /Chapter_04_Codes/code-file-chap4-1.txt: -------------------------------------------------------------------------------- 1 | //Basic function for setup 2 | 3 | function my_rest_post_editor_form( ) { 4 | $form = ' 5 |
    6 | 7 | 8 | 9 |
    10 |
    11 |
    12 | '; 13 | if ( 14 | is_user_logged_in() ) { 15 | if ( user_can( get_current_user_id(), 'edit_posts' ) ) { 16 | return $form; 17 | } 18 | else { 19 | return __( 'You do not have permissions to do this.', 'my-rest-post-editor' ); 20 | } 21 | } 22 | else { 23 | return sprintf( '%2s', wp_login_url( get_permalink( get_ 24 | queried_object_id() ) ), __( 'You must be logged in to do this, please click here to log in.', 25 | 'my-rest-post-editor') ); 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /Chapter_04_Codes/code-file-chap4-2.txt: -------------------------------------------------------------------------------- 1 | //Create basic post editor 2 | 3 | (function($){ 4 | $( '#editor' ).on( 'submit', function(e) { 5 | e.preventDefault(); 6 | var title = $( '#title' ).val(); 7 | var content = $( '#content' ).val(); 8 | var JSONObj = { 9 | "title" 10 | 11 | :title, 12 | "content_raw" :content, 13 | "status" 14 | :'publish' 15 | }; 16 | var data = JSON.stringify(JSONObj); 17 | var url = MY_POST_EDITOR.root; 18 | url += 'wp/v2/posts'; 19 | $.ajax({ 20 | type:"POST", 21 | url: url, 22 | dataType : 'json', 23 | data: data, 24 | beforeSend : function( xhr ) { 25 | xhr.setRequestHeader( 'X-WP-Nonce', MY_POST_EDITOR.nonce ); 26 | }, 27 | success: function(response) { 28 | alert( MY_POST_EDITOR.successMessage ); 29 | $( "#results").append( JSON.stringify( response ) ); 30 | }, 31 | failure: function( response ) { 32 | alert( MY_POST_EDITOR.failureMessage ); 33 | } 34 | }); 35 | }); 36 | })(jQuery); 37 | -------------------------------------------------------------------------------- /Chapter_04_Codes/code-file-chap4-3.txt: -------------------------------------------------------------------------------- 1 | //Final processing function 2 | 3 | $( '#editor' ).on( 'submit', function(e) { 4 | e.preventDefault(); 5 | var title = $( '#title' ).val(); 6 | var content = $( '#content' ).val(); 7 | console.log( content ); 8 | var JSONObj = { 9 | "title" 10 | "content_raw" 11 | "status" 12 | }; 13 | :title, 14 | :content, 15 | :'publish' 16 | var data = JSON.stringify(JSONObj); 17 | var postID = $( '#post-id').val(); 18 | if ( undefined !== postID ) { 19 | url += '/'; 20 | url += postID; 21 | } 22 | $.ajax({ 23 | type:"POST", 24 | url: url, 25 | dataType : 'json', 26 | data: data, 27 | beforeSend : function( xhr ) { 28 | xhr.setRequestHeader( 'X-WP-Nonce', MY_POST_EDITOR.nonce ); 29 | }, 30 | success: function(response) { 31 | alert( MY_POST_EDITOR.successMessage ); 32 | getPostsByUser( response.ID ); 33 | results( response ); 34 | }, 35 | failure: function( response ) { 36 | alert( MY_POST_EDITOR.failureMessage ); 37 | } 38 | }); 39 | }); 40 | -------------------------------------------------------------------------------- /Chapter_05_Codes/code-file-1.txt: -------------------------------------------------------------------------------- 1 | protected function create_resp( $reqst, $argz, $data ) { 2 | $response 3 | = rest_ensure_response( $data ); 4 | $count_query = new \WP_Query(); 5 | unset( $argz['paged'] ); 6 | $query_result = $count_query->query( $argz ); 7 | $total_posts = $count_query->found_posts; 8 | $response->header( 'X-WP-Total', (int) $total_posts ); 9 | $max_pages = ceil( $total_posts / $reqst['per_page'] ); 10 | $response->header( 'X-WP-TotalPages', (int) $max_pages ); 11 | if ( $reqst['page'] > 1 ) { 12 | $prev_page = $reqst['page'] - 1; 13 | if ( $prev_page > $max_pages ) { 14 | $prev_page = $max_pages; 15 | } 16 | $prev_link = add_query_arg( 'page', $prev_page, rest_url( $this->base ) ); 17 | $response->link_header( 'prev', $prev_link ); 18 | } 19 | if ( $max_pages > $reqst['page'] ) { 20 | $next_page = $reqst['page'] + 1; 21 | $next_link = add_query_arg( 'page', $next_page, rest_url( $this->base ) ); 22 | $response->link_header( 'next', $next_link ); 23 | } 24 | return $response; 25 | } 26 | -------------------------------------------------------------------------------- /Chapter_05_Codes/code-file-2.txt: -------------------------------------------------------------------------------- 1 | protected function perform_query( $reqst, $argz, $respond = true) { 2 | $posts_query = new \WP_Query(); 3 | $query_result = $posts_query->query( $argz ); 4 | $data = array(); 5 | if ( ! empty( $query_result ) ) { 6 | foreach ( $query_result as $post ) { 7 | $image = get_post_thumbnail_id( $post->ID ); 8 | if ( $image ) { 9 | $_image = wp_get_attachment_image_src( $image, 'large' ); 10 | if ( is_array( $_image ) ) { 11 | $image = $_image[0]; 12 | } 13 | } 14 | $data[ $post->ID ] = 15 | 'name' => 16 | 'link' => 17 | 'image_markup' => 18 | 'image_src' => 19 | 'excerpt' => 20 | 'tagline' => 21 | 'price' => 22 | 'slug' => 23 | ); 24 | array( 25 | $post->post_title, 26 | get_the_permalink( $post->ID ), 27 | get_the_post_thumbnail( $post->ID, 'large' ), 28 | $image, 29 | $post->post_excerpt, 30 | get_post_meta( $post->ID, 'product_tagline', true ), 31 | edd_get_variable_price( $post->ID ), 32 | $post->post_name, 33 | for ( $i = 1; $i <= 3; $i++ ) { 34 | foreach( array( 35 | 'title', 36 | 'text', 37 | 'image' 38 | ) as $field ) { 39 | if ( 'image' != $field ) { 40 | $field = "sample_{$i}_{$field}"; 41 | $data[ $post->ID ][ $field ] = get_post_meta( $post->ID, $field, true ); 42 | }else{ 43 | $field = "sample_{$i}_{$field}"; 44 | $_field = get_post_meta( $post->ID, $field, true ); 45 | $url = false; 46 | if ( is_array( $_field ) && isset( $_field[ 'ID' ] )) { 47 | $img = $_field[ 'ID' ]; 48 | $img = wp_get_attachment_image_src( $img, 'large' ); 49 | if ( is_array( $img ) ) { 50 | $url = $img[0]; 51 | } 52 | } 53 | $_field[ 'image_src' ] = $url; 54 | $data[ $post->ID ][ $field ] = $_field; 55 | } 56 | } 57 | } 58 | } 59 | } 60 | return $data; 61 | if ( $respond ) { 62 | return $this->create_resp( $reqst, $argz, $data ); 63 | } else { 64 | return $data; 65 | } 66 | } 67 | -------------------------------------------------------------------------------- /Chapter_06_Codes/code-chap6-1.txt: -------------------------------------------------------------------------------- 1 | //Setting the Domain 2 | 3 | remove_filter ( 'rest_pre_serve_request', 'rest_send_cors_headers' ); 4 | 5 | add_filter ( 'rest_pre_serve_request', function($value ) { 6 | $origin = get_http_origin(); 7 | if ( $origin && in_array( $origin, array('example_content', 'example2' 8 | ) ) ) { 9 | header( 'Access-Control-Allow-Origin: ' . esc_url_raw( $origin ) ); 10 | header( 'Access-Control-Allow-Methods: POST, GET, OPTIONS, PUT, DELETE' ); 11 | header( 'Access-Control-Allow-Credentials: true' ); 12 | } 13 | return $value; 14 | }); 15 | -------------------------------------------------------------------------------- /Chapter_06_Codes/code-chap6-2.txt: -------------------------------------------------------------------------------- 1 | //Fetching and returning the variables 2 | 3 | add_filter ( rest_pre_dispatch', 'rest_cache_get', 10, 2 ); 4 | function rest_cache_get( $result, $server ) { 5 | //Checking to see if rebuild callback exists, if it does not then return unmodified. 6 | 7 | if ( ! function_exists('rest_cache_rebuild') ) { 8 | return $result; 9 | } 10 | 11 | //get the REST request and hash it to make the transient key 12 | $request_uri = $_SERVER[ 'REQUEST_URI' ]; 13 | $key = md5( $request_uri ); 14 | 15 | 16 | 17 | //return the cache or build cache 18 | $result = transient( __FUNCTION__ . $key ) 19 | 20 | ->updates_with( 'rest_cache_rebuild', array( $server ) ) 21 | 22 | ->expires_in( 600 ) 23 | 24 | ->get(); 25 | return $result; 26 | } 27 | -------------------------------------------------------------------------------- /Chapter_06_Codes/code-chap6-3.txt: -------------------------------------------------------------------------------- 1 | //Sending data using forms 2 | 3 | var postForm = $( '#post-form' ); 4 |   5 | postForm.on( 'submit', function( f ) { 6 |     e.preventDefault(); 7 |       8 |     $.ajax({ 9 |         url: 'http://example/wp-json/wp/v2/posts', 10 |         method: 'POST', 11 |         data: postForm.serialize(), 12 |         crossDomain: true, 13 |         beforeSend: function ( xrh ) { 14 |             xhr.setRequestHeader( 'Authorization', 'Basic username:password' ); 15 |         }, 16 |         success: function( data ) { 17 |             console.log( data ); 18 |         } 19 |     }); 20 | }); 21 | -------------------------------------------------------------------------------- /Chapter_06_Codes/code-chap6-4.txt: -------------------------------------------------------------------------------- 1 | //Form submission 2 | 3 | var imageForm = $( '#image-form' ), 4 |     fileInput = $('#file'), 5 |     formData = new FormData(); 6 |   7 | imageForm.on( 'submit', function( m ) { 8 |     e.preventDefault(); 9 |       10 |     formData.append( 'file', fileInput[0].files[0] ); 11 |       12 |     $.ajax({ 13 |         url: 'http://example/wp-json/wp/v2/media', 14 |         method: 'POST', 15 |         data: formData, 16 |         crossDomain: true, 17 |         contentType: false, 18 |         processData: false, 19 |         beforeSend: function ( xrh ) { 20 |             xhr.setRequestHeader( 'Authorization', 'Basic username:password' ); 21 |         }, 22 |         success: function( data ) { 23 |             console.log( data ); 24 |         }, 25 |         error: function( error ) { 26 |             console.log( error ); 27 |         } 28 |     }); 29 | }); 30 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | # Learning-WordPress-REST-API 5 | By Packt Publishing 6 | 7 | This is the code repository for [Learning-WordPress-REST-API](https://www.packtpub.com/web-development/learning-wordpress-rest-api?utm_source=github&utm_medium=repository&utm_campaign=9781786469243), published by [Packt Publishing](https://www.packtpub.com/). It contains all the required files to run the code. 8 | 9 | This book is for WordPress developers and designers who want to get a complete practical understanding of the WordPress REST API and leverage it to create fully featured web apps. 10 | 11 | 12 | ###Software and Hardware Requirements 13 | 14 | | Chapter number | Software required (With version) | Hardware specifications | OS required | 15 | |:--------------:|:--------------------------------:|:-----------------------:|:-----------:| 16 | | 1 | Relevant coding language (if implementing REST API in non-PHP/JS) | Code editor of choice; relevant libraries | Linux; Win; Mac | 17 | | 2-9 | WordPress (version 4.3 and above; latest version recommended) PHP 5.4 (preferably higher) Compatible version of MySQL (MariaDB and other enhanceents accepted) | For custom queries, 512 MB of pMem and 512 MB of vMem is preferred to ensure a stable environment (WP in itself can operate at much lesser than that); API calls might need I/O speeds at 2 MB/s If running on shared hosting, make sure your host allows concurrent MySQL connections. | Linux (LAMP stack); Windows (WAMP); if Apache is not available, WP can run well on NGINX or LiteSpeed as well. | 18 | 19 | ###Related Books 20 | 21 | * [WordPress for Education](https://www.packtpub.com/web-development/wordpress-education?utm_source=github&utm_medium=repository&utm_campaign=9781849518208) 22 | 23 | * [WordPress Web Application Development](https://www.packtpub.com/web-development/wordpress-web-application-development?utm_source=github&utm_medium=repository&utm_campaign=9781783280759) 24 | 25 | * [WordPress Web Application Development - Second Edition](https://www.packtpub.com/application-development/wordpress-web-application-development-second-edition?utm_source=github&utm_medium=repository&utm_campaign=9781782174394) 26 | ### Download a free PDF 27 | 28 | If you have already purchased a print or Kindle version of this book, you can get a DRM-free PDF version at no cost.
    Simply click on the link to claim your free PDF.
    29 |

    https://packt.link/free-ebook/9781786469243

    -------------------------------------------------------------------------------- /license: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2016 Packt Publishing 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | --------------------------------------------------------------------------------