WordPress.org

Make WordPress Core

Ticket #2: 0000002-xmlrpc.php

File 0000002-xmlrpc.php, 85.5 KB (added by steamedpenguin, 10 years ago)
Line 
1<?php
2
3# fix for mozBlog and other cases where '<?xml' isn't on the very first line
4$HTTP_RAW_POST_DATA = trim($HTTP_RAW_POST_DATA);
5
6include('wp-config.php');
7
8require_once(ABSPATH.WPINC."/class-xmlrpc.php");
9require_once(ABSPATH.WPINC."/class-xmlrpcs.php");
10require_once(ABSPATH.WPINC."/template-functions.php");
11require_once(ABSPATH.WPINC."/functions.php");
12require_once(ABSPATH.WPINC."/vars.php");
13
14$use_cache = 1;
15$post_autobr = 0;
16$post_default_title = ""; // posts submitted via the xmlrpc interface get that title
17$post_default_category = 1; // posts submitted via the xmlrpc interface go into that category
18
19$xmlrpc_logging = 0;
20
21function logIO($io,$msg) {
22        global $xmlrpc_logging;
23        if ($xmlrpc_logging) {
24                $fp = fopen("./xmlrpc.log","a+");
25                $date = date("Y-m-d H:i:s ");
26                $iot = ($io == "I") ? " Input: " : " Output: ";
27                fwrite($fp, "\n\n".$date.$iot.$msg);
28                fclose($fp);
29        }
30        return true;
31        }
32
33function starify($string) {
34        $i = strlen($string);
35        return str_repeat('*', $i);
36}
37
38logIO("I",$HTTP_RAW_POST_DATA);
39
40/**** DB Functions ****/
41
42/*
43 * These really should be moved into wp-includes/functions.php,
44 * and re-used throughout the code, where possible. -- emc3
45 */
46
47/*
48 * generic function for inserting data into the posts table.
49 */
50function wp_insert_post($postarr = array()) {
51        global $wpdb, $tableposts;
52
53        // export array as variables
54        extract($postarr);
55       
56        // Do some escapes for safety
57        $post_content = $wpdb->escape($post_content);
58        $post_title = $wpdb->escape($post_title);
59       
60        $post_cat = $post_category[0];
61       
62        $sql = "INSERT INTO $tableposts 
63                (post_author, post_date, post_content, post_title, post_excerpt, post_category, post_status)
64                VALUES ('$post_author','$post_date','$post_content','$post_title', '$post_excerpt','$post_cat', '$post_status')";
65
66        $result = $wpdb->query($sql);
67        $post_ID = $wpdb->insert_id;
68       
69        wp_set_post_cats('',$post_ID,$post_category);
70
71        // Return insert_id if we got a good result, otherwise return zero.
72        return $result?$post_ID:0;
73}
74
75function wp_get_single_post($postid = 0, $mode = OBJECT) {
76        global $wpdb, $tableposts;
77
78        $sql = "SELECT * FROM $tableposts WHERE ID=$postid";
79        $result = $wpdb->get_row($sql, $mode);
80
81        return $result;
82}
83
84function wp_get_recent_posts($num = 10) {
85        global $wpdb, $tableposts;
86
87        // Set the limit clause, if we got a limit
88        if ($num) {
89                $limit = "LIMIT $num";
90        }
91
92        $sql = "SELECT * FROM $tableposts ORDER BY post_date DESC $limit";
93        $result = $wpdb->get_results($sql,ARRAY_A);
94
95        return $result?$result:array();
96}
97
98function wp_update_post($postarr = array()) {
99        global $wpdb, $tableposts;
100
101        // First get all of the original fields
102        extract(wp_get_single_post($postarr['ID']));   
103
104        // Now overwrite any changed values being passed in
105        extract($postarr);
106       
107        // Do some escapes for safety
108        $post_content = $wpdb->escape($post_content);
109        $post_title = $wpdb->escape($post_title);
110        $post_excerpt = $wpdb->escape($post_excerpt);
111       
112        $sql = "UPDATE $tableposts 
113                SET post_content = '$post_content',
114                post_title = '$post_title',
115                post_category = $post_category[0],
116                post_status = '$post_status',
117                post_date = '$post_date',
118                post_excerpt = '$post_excerpt',
119                ping_status = '$ping_status',
120                comment_status = '$comment_status'
121                WHERE ID = $ID";
122               
123        $result = $wpdb->query($sql);
124
125        wp_set_post_cats('',$ID,$post_category);
126       
127        return $wpdb->rows_affected;
128}
129
130function wp_get_post_cats($blogid = '1', $post_ID = 0) {
131        global $wpdb, $tablepost2cat;
132       
133        $sql = "SELECT category_id FROM $tablepost2cat WHERE post_id = $post_ID ORDER BY category_id";
134
135        $result = $wpdb->get_col($sql);
136
137        return $result;
138}
139
140function wp_set_post_cats($blogid = '1', $post_ID = 0, $post_categories = array()) {
141        global $wpdb, $tablepost2cat;
142        // If $post_categories isn't already an array, make it one:
143        if (!is_array($post_categories)) {
144                if (!$post_categories) {
145                        $post_categories = 1;
146                }
147                $post_categories = array($post_categories);
148        }
149
150        // First the old categories
151        $old_categories = $wpdb->get_col("SELECT category_id FROM $tablepost2cat WHERE post_id = $post_ID");
152
153        // Delete any?
154        foreach ($old_categories as $old_cat) {
155                if (!in_array($old_cat, $post_categories)) // If a category was there before but isn't now
156                        $wpdb->query("DELETE FROM $tablepost2cat WHERE category_id = $old_cat AND post_id = $post_ID LIMIT 1");
157logio("O","deleting post/cat: $post_ID, $old_cat");
158        }
159
160        // Add any?
161        foreach ($post_categories as $new_cat) {
162                if (!in_array($new_cat, $old_categories))
163                        $wpdb->query("INSERT INTO $tablepost2cat (post_id, category_id) VALUES ($post_ID, $new_cat)");
164logio("O","adding post/cat: $post_ID, $new_cat");
165        }
166}
167
168function wp_delete_post($postid = 0) {
169        global $wpdb, $tableposts, $tablepost2cat;
170       
171        $sql = "DELETE FROM $tablepost2cat WHERE post_id = $postid";
172        $wpdb->query($sql);
173               
174        $sql = "DELETE FROM $tableposts WHERE ID = $postid";
175       
176        $wpdb->query($sql);
177
178        $result = $wpdb->rows_affected;
179       
180        return $result;
181}
182
183/**** /DB Functions ****/
184
185/**** Misc ****/
186
187// get permalink from post ID
188function post_permalink($post_ID=0, $mode = 'id') {
189    global $wpdb;
190        global $tableposts;
191        global $siteurl, $blogfilename, $querystring_start, $querystring_equal, $querystring_separator;
192
193        $blog_URL = $siteurl.'/'.$blogfilename;
194
195        $postdata = get_postdata($post_ID);
196
197        // this will probably change to $blog_ID = $postdata['Blog_ID'] one day.
198        $blog_ID = 1;
199
200        if (!($postdata===false)) {
201       
202                switch(strtolower($mode)) {
203                        case 'title':
204                                $title = preg_replace('/[^a-zA-Z0-9_\.-]/', '_', $postdata['Title']);
205                                break;
206                        case 'id':
207                        default:
208                                $title = "post-$post_ID";
209                                break;
210                }
211
212                // this code is blatantly derived from permalink_link()
213                $archive_mode = get_settings('archive_mode');
214                switch($archive_mode) {
215                        case 'daily':
216                                $post_URL = $blog_URL.$querystring_start.'m'.$querystring_equal.substr($postdata['Date'],0,4).substr($postdata['Date'],5,2).substr($postdata['Date'],8,2).'#'.$title;
217                                break;
218                        case 'monthly':
219                                $post_URL = $blog_URL.$querystring_start.'m'.$querystring_equal.substr($postdata['Date'],0,4).substr($postdata['Date'],5,2).'#'.$title;
220                                break;
221                        case 'weekly':
222                                if((!isset($cacheweekly)) || (empty($cacheweekly[$postdata['Date']]))) {
223                                        $sql = "SELECT WEEK('".$postdata['Date']."') as wk";
224                            $row = $wpdb->get_row($sql);
225                                        $cacheweekly[$postdata['Date']] = $row->wk;
226                                }
227                                $post_URL = $blog_URL.$querystring_start.'m'.$querystring_equal.substr($postdata['Date'],0,4).$querystring_separator.'w'.$querystring_equal.$cacheweekly[$postdata['Date']].'#'.$title;
228                                break;
229                        case 'postbypost':
230                                $post_URL = $blog_URL.$querystring_start.'p'.$querystring_equal.$post_ID;
231                                break;
232                }
233        } 
234
235        return $post_URL;
236}
237
238// Get the name of a category from its ID
239function get_cat_name($cat_id) {
240        global $wpdb,$tablecategories;
241       
242        $cat_id -= 0;   // force numeric
243        $name = $wpdb->get_var("SELECT cat_name FROM $tablecategories WHERE cat_ID=$cat_id");
244       
245        return $name;
246}
247
248// Get the ID of a category from its name
249function get_cat_ID($cat_name='General') {
250        global $wpdb,$tablecategories;
251       
252        $cid = $wpdb->get_var("SELECT cat_ID FROM $tablecategories WHERE cat_name='$cat_name'");
253
254        return $cid?$cid:1;     // default to cat 1
255}
256
257// Get author's preferred display name
258function get_author_name($auth_id) {
259        $authordata = get_userdata($auth_id);
260
261        switch($authordata["user_idmode"]) {
262                case "nickname":
263                        $authorname = $authordata["user_nickname"];
264
265                case "login":
266                        $authorname = $authordata["user_login"];
267                        break;
268       
269                case "firstname":
270                        $authorname = $authordata["user_firstname"];
271                        break;
272
273                case "lastname":
274                        $authorname = $authordata["user_lastname"];
275                        break;
276
277                case "namefl":
278                        $authorname = $authordata["user_firstname"]." ".$authordata["user_lastname"];
279                        break;
280
281                case "namelf":
282                        $authorname = $authordata["user_lastname"]." ".$authordata["user_firstname"];
283                        break;
284
285                default:
286                        $authorname = $authordata["user_nickname"];
287                        break;
288        }
289
290        return $authorname;
291}
292
293// get extended entry info (<!--more-->)
294function get_extended($post) {
295        list($main,$extended) = explode('<!--more-->',$post);
296
297        // Strip leading and trailing whitespace
298        $main = preg_replace('/^[\s]*(.*)[\s]*$/','\\1',$main);
299        $extended = preg_replace('/^[\s]*(.*)[\s]*$/','\\1',$extended);
300
301        return array('main' => $main, 'extended' => $extended);
302}
303
304// do trackbacks for a list of urls
305// borrowed from edit.php
306// accepts a comma-separated list of trackback urls and a post id
307function trackback_url_list($tb_list, $post_id) {
308        if (!empty($tb_list)) {
309                // get post data
310                $postdata = wp_get_single_post($post_id, ARRAY_A);
311
312                // import postdata as variables
313                extract($postdata);
314               
315                // form an excerpt
316                $excerpt = strip_tags($post_excerpt?$post_excerpt:$post_content);
317               
318                if (strlen($excerpt) > 255) {
319                        $exerpt = substr($excerpt,0,252) . '...';
320                }
321               
322                $trackback_urls = explode(',', $tb_list);
323                foreach($trackback_urls as $tb_url) {
324                    $tb_url = trim($tb_url);
325                    trackback($tb_url, stripslashes($post_title), $excerpt, $post_id);
326                }
327    }
328}
329
330/**** /Misc ****/
331
332/**** B2 API ****/
333
334
335# note: the b2 API currently consists of the Blogger API,
336#       plus the following methods:
337#
338# b2.newPost , b2.getCategories
339
340# Note: the b2 API will be replaced by the standard Weblogs.API once the specs are defined.
341
342
343### b2.newPost ###
344
345$wpnewpost_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcBoolean, $xmlrpcString, $xmlrpcString, $xmlrpcString));
346
347$wpnewpost_doc='Adds a post, blogger-api like, +title +category +postdate';
348
349function b2newpost($m) {
350    global $wpdb;
351
352        global $xmlrpcerruser; // import user errcode value
353        global $blog_ID,$cache_userdata,$tableposts,$use_rss,$use_weblogsping,$post_autobr;
354        global $post_default_title,$post_default_category;
355        global $cafelogID, $sleep_after_edit;
356        $err="";
357
358
359        $username=$m->getParam(2);
360        $password=$m->getParam(3);
361        $content=$m->getParam(4);
362        $title=$m->getParam(6);
363        $category=$m->getParam(7);
364        $postdate=$m->getParam(8);
365
366        $username = $username->scalarval();
367        $password = $password->scalarval();
368        $content = $content->scalarval();
369        $title = $title->scalarval();
370        $post_category = $category->scalarval();
371        $postdate = $postdate->scalarval();
372
373
374        if (user_pass_ok($username,$password)) {
375
376                $userdata = get_userdatabylogin($username);
377                $post_author = $userdata->ID;
378                $user_level = $userdata->user_level;
379                if ($user_level < 1) {
380                        return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
381           "Sorry, level 0 users can not post");
382                }
383
384
385                $post_content = format_to_post($content);
386                $post_title = addslashes($title);
387
388
389                $time_difference = get_settings("time_difference");
390                if ($postdate != "") {
391                        $post_date = $postdate;
392                } else {
393                        $post_date = date("Y-m-d H:i:s",(time() + ($time_difference * 3600)));
394                }
395
396                $post_data = compact('post_content','post_title','post_date','post_author','post_category');
397               
398                $result = wp_insert_post($post_data);
399
400                if (!$result)
401                        return new xmlrpcresp(0, $xmlrpcerruser+2, // user error 2
402           "For some strange yet very annoying reason, your entry couldn't be posted.");
403
404
405                $post_ID = $result;
406
407                if (!isset($blog_ID)) { $blog_ID = 1; }
408               
409                if (isset($sleep_after_edit) && $sleep_after_edit > 0) {
410                        sleep($sleep_after_edit);
411                }
412
413
414
415                pingWeblogs($blog_ID);
416                pingCafelog($cafelogID, $post_title, $post_ID);
417                pingBlogs($blog_ID);
418                pingback($content, $post_ID);
419
420
421                return new xmlrpcresp(new xmlrpcval("$post_ID"));
422
423        } else {
424
425                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
426           'Wrong username/password combination '.$username.' / '.starify($password));
427        }
428}
429
430
431
432### b2.getCategories ###
433
434$wpgetcategories_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString));
435
436$wpgetcategories_doc='given a blogID, gives a struct that list categories in that blog, using categoryID and categoryName. categoryName is there so the user would choose a category name from the client, rather than just a number. however, when using b2.newPost, only the category ID number should be sent.';
437
438function b2getcategories($m) {
439    global $wpdb;
440        global $xmlrpcerruser,$tablecategories;
441
442
443        $blogid=$m->getParam(0);
444        $blogid = $blogid->scalarval(); // we dot not use that yet, that will be used with multiple blogs
445
446        $username=$m->getParam(1);
447        $username = $username->scalarval();
448
449        $password=$m->getParam(2);
450        $password = $password->scalarval();
451
452        $userdata = get_userdatabylogin($username);
453
454
455        if (user_pass_ok($username,$password)) {
456
457                $results = $wpdb->get_results("SELECT * FROM $tablecategories ORDER BY cat_ID ASC");
458        if (!$results) die("Error getting data");
459                $i = 0;
460        foreach($results as $row) {
461                        $cat_name = $row->cat_name;
462                        $cat_ID = $row->cat_ID;
463
464                        $struct[$i] = new xmlrpcval(array("categoryID" => new xmlrpcval($cat_ID),
465                                                                                  "categoryName" => new xmlrpcval($cat_name)
466                                                                                  ),"struct");
467                        $i = $i + 1;
468                }
469
470                $data = array($struct[0]);
471                for ($j=1; $j<$i; $j++) {
472                        array_push($data, $struct[$j]);
473                }
474
475                $resp = new xmlrpcval($data, "array");
476
477                return new xmlrpcresp($resp);
478
479        } else {
480                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
481           'Wrong username/password combination '.$username.' / '.starify($password));
482        }
483}
484
485
486
487### b2.getPostURL ###
488
489$wp_getPostURL_sig = array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString));
490
491$wp_getPostURL_doc = 'Given a blog ID, username, password, and a post ID, returns the URL to that post.';
492
493function b2_getPostURL($m) {
494    global $wpdb;
495        global $xmlrpcerruser, $tableposts;
496        global $siteurl, $blogfilename, $querystring_start, $querystring_equal, $querystring_separator;
497
498
499        // ideally, this would be used:
500        // $blog_ID = $m->getParam(0);
501        // $blog_ID = $blog_ID->scalarval();
502        // but right now, b2 handles only one blog, so... :P
503        $blog_ID = 1;
504
505        $username=$m->getParam(2);
506        $username = $username->scalarval();
507
508        $password=$m->getParam(3);
509        $password = $password->scalarval();
510
511        $post_ID = $m->getParam(4);
512        $post_ID = intval($post_ID->scalarval());
513
514        $userdata = get_userdatabylogin($username);
515
516        if ($userdata->user_level < 1) {
517                return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
518           "Sorry, users whose level is zero, can not use this method.");
519        }
520
521        if (user_pass_ok($username,$password)) {
522
523                $blog_URL = $siteurl.'/'.$blogfilename;
524
525                $postdata = get_postdata($post_ID);
526
527                if (!($postdata===false)) {
528
529                        $title = preg_replace('/[^a-zA-Z0-9_\.-]/', '_', $postdata['Title']);
530
531                        // this code is blatantly derived from permalink_link()
532                        $archive_mode = get_settings('archive_mode');
533                        switch($archive_mode) {
534                                case 'daily':
535                                        $post_URL = $blog_URL.$querystring_start.'m'.$querystring_equal.substr($postdata['Date'],0,4).substr($postdata['Date'],5,2).substr($postdata['Date'],8,2).'#'.$title;
536                                        break;
537                                case 'monthly':
538                                        $post_URL = $blog_URL.$querystring_start.'m'.$querystring_equal.substr($postdata['Date'],0,4).substr($postdata['Date'],5,2).'#'.$title;
539                                        break;
540                                case 'weekly':
541                                        if((!isset($cacheweekly)) || (empty($cacheweekly[$postdata['Date']]))) {
542                                                $sql = "SELECT WEEK('".$postdata['Date']."') as wk";
543                        $row = $wpdb->get_row($sql);
544                                                $cacheweekly[$postdata['Date']] = $row->wk;
545                                        }
546                                        $post_URL = $blog_URL.$querystring_start.'m'.$querystring_equal.substr($postdata['Date'],0,4).$querystring_separator.'w'.$querystring_equal.$cacheweekly[$postdata['Date']].'#'.$title;
547                                        break;
548                                case 'postbypost':
549                                        $post_URL = $blog_URL.$querystring_start.'p'.$querystring_equal.$post_ID;
550                                        break;
551                        }
552                } else {
553                        $err = 'This post ID ('.$post_ID.') does not correspond to any post here.';
554                }
555
556                if ($err) {
557                        return new xmlrpcresp(0, $xmlrpcerruser, $err);
558                } else {
559                        return new xmlrpcresp(new xmlrpcval($post_URL));;
560                }
561
562        } else {
563                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
564           'Wrong username/password combination '.$username.' / '.starify($password));
565        }
566
567}
568
569/**** /B2 API ****/
570
571
572
573/**** Blogger API ****/
574
575# as described on http://plant.blogger.com/api and in various messages in http://groups.yahoo.com/group/bloggerDev/
576#
577# another list of these methods is there http://www.tswoam.co.uk/blogger_method_listing.html
578# so you won't have to browse the eGroup to find all the methods
579#
580# special note: Evan please keep _your_ API page up to date :p
581
582
583
584### blogger.newPost ###
585
586$bloggernewpost_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcBoolean));
587
588$bloggernewpost_doc='Adds a post, blogger-api like';
589
590function bloggernewpost($m) {
591    global $wpdb;
592
593        global $xmlrpcerruser; // import user errcode value
594        global $blog_ID,$cache_userdata,$tableposts,$use_rss,$use_weblogsping,$post_autobr;
595        global $post_default_title,$post_default_category;
596        global $cafelogID, $sleep_after_edit;
597        $err="";
598
599
600        $username=$m->getParam(2);
601        $password=$m->getParam(3);
602        $content=$m->getParam(4);
603        $publish=$m->getParam(5);
604
605        $username = $username->scalarval();
606        $password = $password->scalarval();
607        $content = $content->scalarval();
608        // publish flag sets post status appropriately
609        $post_status = $publish->scalarval()?'publish':'draft';
610       
611        if (user_pass_ok($username,$password)) {
612
613                $userdata = get_userdatabylogin($username);
614                $post_author = $userdata->ID;
615                $user_level = $userdata->user_level;
616                if ($user_level < 1) {
617                        return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
618           "Sorry, level 0 users can not post");
619                }
620
621                $post_title = addslashes(xmlrpc_getposttitle($content));
622                $post_category = xmlrpc_getpostcategory($content);
623
624                $content = xmlrpc_removepostdata($content);
625                $post_content = format_to_post($content);
626
627                $time_difference = get_settings("time_difference");
628                $post_date = date("Y-m-d H:i:s",(time() + ($time_difference * 3600)));
629               
630                $postdata = compact('post_author', 'post_date', 'post_content', 'post_title', 'post_category', 'post_status');
631
632                $post_ID = wp_insert_post($postdata);
633
634                if (!$post_ID)
635                        return new xmlrpcresp(0, $xmlrpcerruser+2, // user error 2
636           "For some strange yet very annoying reason, your entry couldn't be posted.");
637
638                if (!isset($blog_ID)) { $blog_ID = 1; }
639               
640                if (isset($sleep_after_edit) && $sleep_after_edit > 0) {
641                        sleep($sleep_after_edit);
642                }
643
644
645                pingWeblogs($blog_ID);
646                pingCafelog($cafelogID, $post_title, $post_ID);
647                pingBlogs($blog_ID);
648                pingback($content, $post_ID);
649
650                logIO("O","Posted ! ID: $post_ID");
651                return new xmlrpcresp(new xmlrpcval("$post_ID"));
652
653        } else {
654                logIO("O","Wrong username/password combination <b>$username / $password</b>");
655                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
656           'Wrong username/password combination '.$username.' / '.starify($password));
657        }
658}
659
660
661
662### blogger.editPost ###
663
664$bloggereditpost_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcBoolean));
665
666$bloggereditpost_doc='Edits a post, blogger-api like';
667
668function bloggereditpost($m) {
669    global $wpdb;
670
671        global $xmlrpcerruser; // import user errcode value
672        global $blog_ID,$cache_userdata,$tableposts,$use_rss,$use_weblogsping,$post_autobr;
673        global $post_default_title,$post_default_category, $sleep_after_edit;
674        $err="";
675
676
677        $post_ID=$m->getParam(1);
678        $username=$m->getParam(2);
679        $password=$m->getParam(3);
680        $newcontent=$m->getParam(4);
681        $publish=$m->getParam(5);
682
683        $ID = $post_ID->scalarval();
684        $username = $username->scalarval();
685        $password = $password->scalarval();
686        $newcontent = $newcontent->scalarval();
687        $post_status = $publish->scalarval()?'publish':'draft';
688
689        $result = wp_get_single_post($ID,ARRAY_A);
690
691        if (!$result)
692                return new xmlrpcresp(0, $xmlrpcerruser+2, // user error 2
693          "No such post '$ID'.");
694
695        $userdata = get_userdatabylogin($username);
696        $user_ID = $userdata->ID;
697        $user_level = $userdata->user_level;
698
699        $postdata=get_postdata($ID);
700        $post_authordata=get_userdata($postdata["Author_ID"]);
701        $post_author_ID=$postdata["Author_ID"];
702
703        if (($user_ID != $post_author_ID) && ($user_level <= $post_authordata->user_level)) {
704                        return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
705           "Sorry, you do not have the right to edit this post");
706        }
707
708        if (user_pass_ok($username,$password)) {
709
710                if ($user_level < 1) {
711                        return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
712           "Sorry, level 0 users can not edit posts");
713                }
714               
715                extract($result);
716
717                $content = $newcontent;
718
719                $post_title = xmlrpc_getposttitle($content);
720                $post_category = xmlrpc_getpostcategory($content);
721
722                $content = xmlrpc_removepostdata($content);
723                $post_content = format_to_post($content);
724               
725                $postdata = compact('ID','post_content','post_title','post_category','post_status','post_date','post_excerpt');
726
727                $result = wp_update_post($postdata);
728
729                if (!$result)
730                        return new xmlrpcresp(0, $xmlrpcerruser+2, // user error 2
731           "For some strange yet very annoying reason, the entry couldn't be edited.");
732
733                if (!isset($blog_ID)) { $blog_ID = 1; }
734               
735                if (isset($sleep_after_edit) && $sleep_after_edit > 0) {
736                        sleep($sleep_after_edit);
737                }
738
739
740                pingWeblogs($blog_ID);
741
742                return new xmlrpcresp(new xmlrpcval("1", "boolean"));
743
744        } else {
745                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
746           'Wrong username/password combination '.$username.' / '.starify($password));
747        }
748}
749
750
751
752### blogger.deletePost ###
753
754$bloggerdeletepost_sig=array(array($xmlrpcBoolean, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcBoolean));
755
756$bloggerdeletepost_doc='Deletes a post, blogger-api like';
757
758function bloggerdeletepost($m) {
759    global $wpdb;
760
761        global $xmlrpcerruser; // import user errcode value
762        global $blog_ID,$cache_userdata,$tableposts,$use_rss,$use_weblogsping,$post_autobr;
763        global $post_default_title,$post_default_category, $sleep_after_edit;
764        $err="";
765
766
767        $post_ID=$m->getParam(1);
768        $username=$m->getParam(2);
769        $password=$m->getParam(3);
770        $newcontent=$m->getParam(4);
771
772        $post_ID = $post_ID->scalarval();
773        $username = $username->scalarval();
774        $password = $password->scalarval();
775        $newcontent = $newcontent->scalarval();
776
777        $sql = "SELECT * FROM $tableposts WHERE ID = '$post_ID'";
778    $result = $wpdb->get_results($sql);
779        if (!$result)
780                return new xmlrpcresp(0, $xmlrpcerruser+2, // user error 2
781          "No such post '$post_ID'.");
782
783        $userdata = get_userdatabylogin($username);
784        $user_ID = $userdata->ID;
785        $user_level = $userdata->user_level;
786
787        $postdata=get_postdata($post_ID);
788        $post_authordata=get_userdata($postdata["Author_ID"]);
789        $post_author_ID=$postdata["Author_ID"];
790
791        if (($user_ID != $post_author_ID) && ($user_level <= $post_authordata->user_level)) {
792                        return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
793           "Sorry, you do not have the right to delete this post");
794        }
795
796        if (user_pass_ok($username,$password)) {
797
798                if ($user_level < 1) {
799                        return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
800           "Sorry, level 0 users can not delete posts");
801                }
802
803                $result = wp_delete_post($post_ID);
804
805                if (!$result)
806                        return new xmlrpcresp(0, $xmlrpcerruser+2, // user error 2
807           "For some strange yet very annoying reason, the entry couldn't be deleted.");
808
809                if (!isset($blog_ID)) { $blog_ID = 1; }
810               
811                if (isset($sleep_after_edit) && $sleep_after_edit > 0) {
812                        sleep($sleep_after_edit);
813                }
814
815
816                pingWeblogs($blog_ID);
817
818                return new xmlrpcresp(new xmlrpcval(1,'boolean'));
819
820        } else {
821                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
822           'Wrong username/password combination '.$username.' / '.starify($password));
823        }
824}
825
826
827
828### blogger.getUsersBlogs ###
829
830$bloggergetusersblogs_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString));
831
832$bloggergetusersblogs_doc='returns the user\'s blogs - this is a dummy function, just so that BlogBuddy and other blogs-retrieving apps work';
833
834function bloggergetusersblogs($m) {
835    global $wpdb;
836        // this function will have a real purpose with CafeLog's multiple blogs capability
837
838        global $xmlrpcerruser,$siteurl,$blogfilename,$blogname;
839        global $tableusers;
840
841        $user_login = $m->getParam(1);
842        $user_login = $user_login->scalarval();
843
844
845        $sql = "SELECT user_level FROM $tableusers WHERE user_login = '$user_login' AND user_level > 3";
846    $result = $wpdb->get_results($sql);
847
848
849        $is_admin = $wpdb->num_rows;
850
851        $struct = new xmlrpcval(array("isAdmin" => new xmlrpcval($is_admin,"boolean"),
852                                                                        "url" => new xmlrpcval($siteurl."/".$blogfilename),
853                                                                        "blogid" => new xmlrpcval("1"),
854                                                                        "blogName" => new xmlrpcval($blogname)
855                                                                        ),"struct");
856    $resp = new xmlrpcval(array($struct), "array");
857
858        return new xmlrpcresp($resp);
859}
860
861
862
863### blogger.getUserInfo ###
864
865$bloggergetuserinfo_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString));
866
867$bloggergetuserinfo_doc='gives the info about a user';
868
869function bloggergetuserinfo($m) {
870        global $xmlrpcerruser,$tableusers;
871
872
873        $username=$m->getParam(1);
874        $username = $username->scalarval();
875
876        $password=$m->getParam(2);
877        $password = $password->scalarval();
878
879        $userdata = get_userdatabylogin($username);
880
881        if (user_pass_ok($username,$password)) {
882                $struct = new xmlrpcval(array("nickname" => new xmlrpcval($userdata->user_nickname),
883                                                                          "userid" => new xmlrpcval($userdata->ID),
884                                                                          "url" => new xmlrpcval($userdata->user_url),
885                                                                          "email" => new xmlrpcval($userdata->user_email),
886                                                                          "lastname" => new xmlrpcval($userdata->user_lastname),
887                                                                          "firstname" => new xmlrpcval($userdata->user_firstname)
888                                                                          ),"struct");
889                $resp = $struct;
890                return new xmlrpcresp($resp);
891
892        } else {
893                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
894           'Wrong username/password combination '.$username.' / '.starify($password));
895        }
896}
897
898
899
900### blogger.getPost ###
901
902$bloggergetpost_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString));
903
904$bloggergetpost_doc='fetches a post, blogger-api like';
905
906function bloggergetpost($m) {
907        global $xmlrpcerruser,$tableposts;
908
909
910        $post_ID=$m->getParam(1);
911        $post_ID = $post_ID->scalarval();
912
913        $username=$m->getParam(2);
914        $username = $username->scalarval();
915
916        $password=$m->getParam(3);
917        $password = $password->scalarval();
918
919        if (user_pass_ok($username,$password)) {
920                $postdata = get_postdata($post_ID);
921
922                if ($postdata["Date"] != "") {
923                        // Don't convert to GMT
924                        //$post_date = mysql2date("U", $postdata["Date"]);
925                        $post_date = strtotime($postdata['Date']);
926                        $post_date = date("Ymd", $post_date)."T".date("H:i:s", $post_date);
927
928                        $content  = "<title>".stripslashes($postdata["Title"])."</title>";
929                        $content .= "<category>".$postdata["Category"]."</category>";
930                        $content .= stripslashes($postdata["Content"]);
931
932                        $struct = new xmlrpcval(array("userid" => new xmlrpcval($postdata["Author_ID"]),
933                                                                                  "dateCreated" => new xmlrpcval($post_date,"dateTime.iso8601"),
934                                                                                  "content" => new xmlrpcval($content),
935                                                                                  "postid" => new xmlrpcval($postdata["ID"])
936                                                                                  ),"struct");
937
938                        $resp = $struct;
939                        return new xmlrpcresp($resp);
940                } else {
941                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 4
942           "No such post #$post_ID");
943                }
944        } else {
945                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
946           'Wrong username/password combination '.$username.' / '.starify($password));
947        }
948}
949
950
951
952### blogger.getRecentPosts ###
953
954$bloggergetrecentposts_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcInt));
955
956$bloggergetrecentposts_doc='fetches X most recent posts, blogger-api like';
957
958function bloggergetrecentposts($m) {
959    global $wpdb;
960        global $xmlrpcerruser,$tableposts;
961
962        error_reporting(0); // there is a bug in phpxmlrpc that makes it say there are errors while the output is actually valid, so let's disable errors for that function
963
964
965        $blogid = 1;    // we don't need that yet
966
967        $numposts=$m->getParam(4);
968        $numposts = $numposts->scalarval();
969
970        if ($numposts > 0) {
971                $limit = " LIMIT $numposts";
972        } else {
973                $limit = "";
974        }
975
976        $username=$m->getParam(2);
977        $username = $username->scalarval();
978
979        $password=$m->getParam(3);
980        $password = $password->scalarval();
981
982        if (user_pass_ok($username,$password)) {
983
984                $sql = "SELECT * FROM $tableposts ORDER BY post_date DESC".$limit;
985                $result = $wpdb->get_results($sql);
986                if (!$result)
987                        return new xmlrpcresp(0, $xmlrpcerruser+2, // user error 2
988           "For some strange yet very annoying reason, the entries couldn't be fetched.");
989
990                $data = new xmlrpcval("","array");
991
992                $i = 0;
993                foreach ($result as $row) {
994                        $postdata = array(
995                                "ID" => $row->ID,
996                                "Author_ID" => $row->post_author,
997                                "Date" => $row->post_date,
998                                "Content" => $row->post_content,
999                                "Title" => $row->post_title,
1000                                "Category" => $row->post_category
1001                        );
1002
1003                        // Don't convert to GMT
1004                        //$post_date = mysql2date("U", $postdata["Date"]);
1005                        $post_date = strtotime($postdata['Date']);
1006                        $post_date = date("Ymd", $post_date)."T".date("H:i:s", $post_date);
1007
1008                        $content  = "<title>".stripslashes($postdata["Title"])."</title>";
1009                        $content .= "<category>".get_cat_name($postdata["Category"])."</category>";
1010                        $content .= stripslashes($postdata["Content"]);
1011
1012//                      $content = convert_chars($content,"html");
1013//                      $content = $postdata["Title"];
1014
1015                        $category = new xmlrpcval($postdata['Category']);
1016
1017                        $authordata = get_userdata($postdata["Author_ID"]);
1018                        switch($authordata["user_idmode"]) {
1019                                case "nickname":
1020                                        $authorname = $authordata["user_nickname"];
1021
1022                        case "login":
1023                                        $authorname = $authordata["user_login"];
1024                                        break;
1025                        case "firstname":
1026                                        $authorname = $authordata["user_firstname"];
1027                                        break;
1028                        case "lastname":
1029                                        $authorname = $authordata["user_lastname"];
1030                                        break;
1031                        case "namefl":
1032                                        $authorname = $authordata["user_firstname"]." ".$authordata["user_lastname"];
1033                                        break;
1034                        case "namelf":
1035                                        $authorname = $authordata["user_lastname"]." ".$authordata["user_firstname"];
1036                                        break;
1037                        default:
1038                                        $authorname = $authordata["user_nickname"];
1039                                        break;
1040                        }
1041
1042                        $struct[$i] = new xmlrpcval(array("authorName" => new xmlrpcval($authorname),
1043                                                                                "userid" => new xmlrpcval($postdata["Author_ID"]),
1044                                                                                "dateCreated" => new xmlrpcval($post_date,"dateTime.iso8601"),
1045                                                                                "content" => new xmlrpcval($content),
1046                                                                                "postid" => new xmlrpcval($postdata["ID"]),
1047                                                                                'category' => $category
1048                                                                                ),"struct");
1049                        $i = $i + 1;
1050                }
1051
1052                $data = array($struct[0]);
1053                for ($j=1; $j<$i; $j++) {
1054                        array_push($data, $struct[$j]);
1055                }
1056
1057                $resp = new xmlrpcval($data, "array");
1058
1059                return new xmlrpcresp($resp);
1060
1061        } else {
1062                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1063           'Wrong username/password combination '.$username.' / '.starify($password));
1064        }
1065}
1066
1067
1068
1069### blogger.getTemplate ###
1070
1071# note: on b2, it fetches your $blogfilename, or b2.php if you didn't specify the variable
1072
1073$bloggergettemplate_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString));
1074
1075$bloggergettemplate_doc='returns the default template file\'s code';
1076
1077function bloggergettemplate($m) {
1078        global $xmlrpcerruser,$tableusers,$blogfilename;
1079
1080        error_reporting(0); // there is a bug in phpxmlrpc that makes it say there are errors while the output is actually valid, so let's disable errors for that function
1081
1082
1083        $blogid = 1;    // we do not need this yet
1084
1085        $templateType=$m->getParam(4);
1086        $templateType = $templateType->scalarval();
1087
1088        $username=$m->getParam(2);
1089        $username = $username->scalarval();
1090
1091        $password=$m->getParam(3);
1092        $password = $password->scalarval();
1093
1094        $userdata = get_userdatabylogin($username);
1095
1096        if ($userdata->user_level < 3) {
1097                return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
1098           "Sorry, users whose level is less than 3, can not edit the template.");
1099        }
1100
1101        if (user_pass_ok($username,$password)) {
1102
1103        if ($templateType == "main") {
1104                if ($blogfilename != "") {
1105                        $file = $blogfilename;
1106                } else {
1107                        $file = "wp.php";
1108                }
1109        } elseif ($templateType == "archiveIndex") {
1110                $file = "wp.php";
1111        }
1112
1113        $f = fopen($file,"r");
1114        $content = fread($f,filesize($file));
1115        fclose($file);
1116
1117        $content = str_replace("\n","\r\n",$content);   // so it is actually editable with a windows/mac client, instead of being returned as a looooooooooong line of code
1118
1119        return new xmlrpcresp(new xmlrpcval("$content"));
1120
1121        } else {
1122                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1123           'Wrong username/password combination '.$username.' / '.starify($password));
1124        }
1125}
1126
1127
1128
1129### blogger.setTemplate ###
1130
1131# note: on b2, it saves that in your $blogfilename, or b2.php if you didn't specify the variable
1132
1133$bloggersettemplate_sig=array(array($xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcString));
1134
1135$bloggersettemplate_doc='saves the default template file\'s code';
1136
1137function bloggersettemplate($m) {
1138        global $xmlrpcerruser,$tableusers,$blogfilename;
1139
1140        error_reporting(0); // there is a bug in phpxmlrpc that makes it say there are errors while the output is actually valid, so let's disable errors for that function
1141
1142
1143        $blogid = 1;    // we do not need this yet
1144
1145        $template=$m->getParam(4);
1146        $template = $template->scalarval();
1147
1148        $templateType=$m->getParam(5);
1149        $templateType = $templateType->scalarval();
1150
1151        $username=$m->getParam(2);
1152        $username = $username->scalarval();
1153
1154        $password=$m->getParam(3);
1155        $password = $password->scalarval();
1156
1157        $userdata = get_userdatabylogin($username);
1158
1159        if ($userdata->user_level < 3) {
1160                return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
1161           "Sorry, users whose level is less than 3, can not edit the template.");
1162        }
1163
1164        if (user_pass_ok($username,$password)) {
1165
1166        if ($templateType == "main") {
1167                if ($blogfilename != "") {
1168                        $file = $blogfilename;
1169                } else {
1170                        $file = "wp.php";
1171                }
1172        } elseif ($templateType == "archiveIndex") {
1173                $file = "wp.php";
1174        }
1175
1176        $f = fopen($file,"w+");
1177        fwrite($f, $template);
1178        fclose($file);
1179
1180        return new xmlrpcresp(new xmlrpcval("1", "boolean"));
1181
1182        } else {
1183                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1184           'Wrong username/password combination '.$username.' / '.starify($password));
1185        }
1186}
1187
1188/**** /Blogger API ****/
1189
1190
1191
1192/**** metaWeblog API ****/
1193
1194/**********************
1195 *
1196 * metaWeblog API extensions
1197 * added by
1198 *  Dougal Campbell <dougal@gunters.org>
1199 *  http://dougal.gunters.org/
1200 *
1201 **********************/
1202
1203$mwnewpost_sig =  array(array($xmlrpcString,$xmlrpcString,$xmlrpcString,$xmlrpcString,$xmlrpcStruct,$xmlrpcBoolean));
1204$mwnewpost_doc = 'Add a post, MetaWeblog API-style';
1205
1206function mwnewpost($params) {
1207        global $xmlrpcerruser;
1208        global $blog_ID, $cache_userdata,$tableposts;
1209        global $use_rss,$use_weblogsping,$post_autobr,$post_default_title;
1210        global $post_default_category,$cafelogID,$sleep_after_edit;
1211
1212        $xblogid = $params->getParam(0);
1213        $xuser = $params->getParam(1);
1214        $xpass = $params->getParam(2);
1215        $xcontent = $params->getParam(3);
1216        $xpublish = $params->getParam(4);
1217       
1218        $blogid = $xblogid->scalarval();
1219        $username = $xuser->scalarval();
1220        $password = $xpass->scalarval();
1221        $contentstruct = xmlrpc_decode($xcontent);
1222        $post_status = $xpublish->scalarval()?'publish':'draft';
1223
1224        // Check login
1225        if (user_pass_ok($username,$password)) {
1226                $userdata = get_userdatabylogin($username);
1227                $post_author = $userdata->ID;
1228                $user_level = $userdata->user_level;
1229                if ($user_level < 1) {
1230                        return new xmlrpcresp(0, $xmlrpcerruser+1,
1231                          "Sorry, level 0 users cannot post");
1232                }
1233
1234
1235                $post_title = $contentstruct['title'];
1236                $post_content = format_to_post($contentstruct['description']);
1237
1238                $post_excerpt = $contentstruct['mt_excerpt'];
1239                $post_more = $contentstruct['mt_text_more'];
1240
1241                $comment_status = $contentstruct['mt_allow_comments']?'open':'closed';
1242                $ping_status = $contentstruct['mt_allow_pings']?'open':'closed';
1243
1244                if ($post_more) {
1245                        $post_content = $post_content . "\n<!--more-->\n" . $post_more;
1246                }
1247               
1248                $time_difference = get_settings("time_difference");
1249                $dateCreated = $contentstruct['dateCreated'];
1250                $dateCreated = $dateCreated?iso8601_decode($dateCreated):(time()+($time_difference * 3600));
1251                $post_date = date("Y-m-d H:i:s", $dateCreated);
1252               
1253                $catnames = $contentstruct['categories'];
1254                if ($catnames) {
1255                        foreach ($catnames as $cat) {
1256                                $post_category[] = get_cat_ID($cat);
1257                        }
1258                } else {
1259                        $post_category[] = 1;
1260                }
1261               
1262                // We've got all the data -- post it:
1263                $postarr = compact('post_author','post_date','post_content','post_title','post_category','post_status','post_excerpt','comment_status','ping_status');
1264
1265                $post_ID = wp_insert_post($postarr);
1266               
1267                if (!$post_ID) {
1268                        return new xmlrpcresp(0, $xmlrpcerruser+2, "For some strange yet very annoying reason, your entry could not be posted.");
1269                }
1270
1271                if (!isset($blog_ID)) { $blog_ID = 1; }
1272
1273                if (isset($sleep_after_edit) && $sleep_after_edit > 0) {
1274                        sleep($sleep_after_edit);
1275                }
1276
1277                pingWeblogs($blog_ID);
1278                pingCafelog($cafelogID, $post_title, $post_ID);
1279                pingBlogs($blog_ID);
1280                pingback($content, $post_ID);
1281                trackback_url_list($content_struct['mt_tb_ping_urls'],$post_ID);
1282
1283                logIO("O","(MW) Posted ! ID: $post_ID");
1284                $myResp = new xmlrpcval($post_ID,"string");
1285
1286                return new xmlrpcresp($myResp);
1287
1288        } else {
1289                logIO("O","(MW) Wrong username/password combination <b>$username / $password</b>");
1290                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1291           'Wrong username/password combination '.$username.' / '.starify($password));
1292        }
1293}
1294
1295$mweditpost_sig =  array(array($xmlrpcBoolean,$xmlrpcString,$xmlrpcString,$xmlrpcString,$xmlrpcStruct,$xmlrpcBoolean));
1296$mweditpost_doc = 'Edit a post, MetaWeblog API-style';
1297
1298function mweditpost ($params) { // ($postid, $user, $pass, $content, $publish)
1299        global $xmlrpcerruser;
1300
1301        $xpostid = $params->getParam(0);
1302        $xuser = $params->getParam(1);
1303        $xpass = $params->getParam(2);
1304        $xcontent = $params->getParam(3);
1305        $xpublish = $params->getParam(4);
1306       
1307        $ID = $xpostid->scalarval();
1308        $username = $xuser->scalarval();
1309        $password = $xpass->scalarval();
1310        $contentstruct = xmlrpc_decode($xcontent);
1311        $postdata = wp_get_single_post($ID);
1312
1313        if (!$postdata)
1314                return new xmlrpcresp(0, $xmlrpcerruser+2, // user error 2
1315                        "No such post $ID.");
1316                       
1317        $userdata = get_userdatabylogin($username);
1318        $user_ID = $userdata->ID;
1319        $user_level = $userdata->user_level;
1320       
1321        $post_author_ID = $postdata->post_author;
1322        $post_authordata = get_userdata($post_author_ID);
1323
1324        if (($user_ID != $post_author_ID) && ($user_level <= $post_authordata->user_level)) {
1325                return new xmlrpcresp(0, $xmlrpcerruser+1, // user error 1
1326                        "Sorry, you do not have the right to edit this post.");
1327        }
1328               
1329        // Check login
1330        if (user_pass_ok($username,$password)) {
1331                if ($user_level < 1) {
1332                        return new xmlrpcresp(0, $xmlrpcerruser+1,
1333                          "Sorry, level 0 users cannot edit posts");
1334                }
1335
1336                extract($postdata);
1337
1338                $post_title = $contentstruct['title'];
1339                $post_content = format_to_post($contentstruct['description']);
1340                $catnames = $contentstruct['categories'];
1341                foreach ($catnames as $cat) {
1342                        $post_category[] = get_cat_ID($cat);
1343                }
1344
1345                $post_excerpt = $contentstruct['mt_excerpt'];
1346                $post_more = $contentstruct['mt_text_more'];
1347                $post_status = $xpublish->scalarval()?'publish':'draft';
1348                if ($post_more) {
1349                        $post_content = $post_content . "\n<!--more-->\n" . $post_more;
1350                }
1351                $comment_status = (1 == $contentstruct['mt_allow_comments'])?'open':'closed';
1352                $ping_status = $contentstruct['mt_allow_pings']?'open':'closed';
1353
1354               
1355                $time_difference = get_settings("time_difference");
1356                $dateCreated = $contentstruct['dateCreated'];
1357                $dateCreated = $dateCreated?iso8601_decode($contentstruct['dateCreated']):(time()+($time_difference * 3600));
1358                $post_date = date("Y-m-d H:i:s", $dateCreated);
1359
1360                // We've got all the data -- post it:
1361                $newpost = compact('ID','post_content','post_title','post_category','post_status','post_excerpt','comment_status','ping_status','post_date');
1362
1363                $newpost_ID = wp_update_post($newpost);
1364               
1365                if (!$newpost_ID) {
1366                        return new xmlrpcresp(0, $xmlrpcerruser+2, "For some strange yet very annoying reason, your entry could not be posted.");
1367                }
1368
1369                if (!isset($blog_ID)) { $blog_ID = 1; }
1370
1371                if (isset($sleep_after_edit) && $sleep_after_edit > 0) {
1372                        sleep($sleep_after_edit);
1373                }
1374
1375                pingWeblogs($blog_ID);
1376                pingCafelog($cafelogID, $post_title, $post_ID);
1377                pingBlogs($blog_ID);
1378                pingback($content, $post_ID);
1379                trackback_url_list($content_struct['mt_tb_ping_urls'],$post_ID);
1380
1381                logIO("O","(MW) Edited ! ID: $post_ID");
1382                $myResp = new xmlrpcval($ID,"string");
1383
1384                return new xmlrpcresp($myResp);
1385
1386        } else {
1387                logIO("O","(MW) Wrong username/password combination <b>$username / $password</b>");
1388                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1389           'Wrong username/password combination '.$username.' / '.starify($password));
1390        }
1391}
1392
1393$mwgetpost_sig =  array(array($xmlrpcStruct,$xmlrpcString,$xmlrpcString,$xmlrpcString));
1394$mwegetpost_doc = 'Get a post, MetaWeblog API-style';
1395
1396function mwgetpost ($params) {  // ($postid, $user, $pass)
1397        global $xmlrpcerruser;
1398       
1399        $xpostid = $params->getParam(0);
1400        $xuser = $params->getParam(1);
1401        $xpass = $params->getParam(2);
1402       
1403        $post_ID = $xpostid->scalarval();
1404        $username = $xuser->scalarval();
1405        $password = $xpass->scalarval();
1406
1407        // Check login
1408        if (user_pass_ok($username,$password)) {
1409                $postdata = get_postdata($post_ID);
1410
1411                if ($postdata["Date"] != "") {
1412
1413                        // why were we converting to GMT here? spec doesn't call for that.
1414                        //$post_date = mysql2date("U", $postdata["Date"]);
1415                        //$post_date = gmdate("Ymd", $post_date)."T".gmdate("H:i:s", $post_date);
1416                        $post_date = strtotime($postdata['Date']);
1417                        $post_date = date("Ymd", $post_date)."T".date("H:i:s", $post_date);
1418                       
1419                        $catids = wp_get_post_cats($post_ID);
1420                        foreach($catids as $catid) {
1421                                $catname = get_cat_name($catid);
1422                                $catnameenc = new xmlrpcval($catname);
1423                                $catlist[] = $catnameenc;
1424                        }                       
1425                        $post = get_extended($postdata['Content']);
1426                        $allow_comments = ('open' == $postdata['comment_status'])?1:0;
1427                        $allow_pings = ('open' == $postdata['ping_status'])?1:0;
1428
1429                        $resp = array(
1430                                'link' => new xmlrpcval(post_permalink($post_ID)),
1431                                'title' => new xmlrpcval($postdata["Title"]),
1432                                'description' => new xmlrpcval($post['main']),
1433                                'dateCreated' => new xmlrpcval($post_date,'dateTime.iso8601'),
1434                                'userid' => new xmlrpcval($postdata["Author_ID"]),
1435                                'postid' => new xmlrpcval($postdata["ID"]),
1436                                'content' => new xmlrpcval($postdata["Content"]),
1437                                'permalink' => new xmlrpcval(post_permalink($post_ID)),
1438                                'categories' => new xmlrpcval($catlist,'array'),
1439                                'mt_excerpt' => new xmlrpcval($postdata['Excerpt']),
1440                                'mt_allow_comments' => new xmlrpcval($allow_comments,'int'),
1441                                'mt_allow_pings' => new xmlrpcval($allow_pings,'int'),
1442                                'mt_text_more' => new xmlrpcval($post['extended'])
1443                        );
1444                       
1445                        $resp = new xmlrpcval($resp,'struct');
1446                       
1447                        return new xmlrpcresp($resp);
1448                } else {
1449                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 4
1450                        "No such post #$post_ID");
1451                }
1452        } else {
1453                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1454           'Wrong username/password combination '.$username.' / '.starify($password));
1455        }
1456
1457}
1458
1459$mwrecentposts_sig =  array(array($xmlrpcArray,$xmlrpcString,$xmlrpcString,$xmlrpcString,$xmlrpcInt));
1460$mwerecentposts_doc = 'Get recent posts, MetaWeblog API-style';
1461
1462function mwrecentposts ($params) {      // ($blogid, $user, $pass, $num)
1463        global $xmlrpcerruser;
1464
1465        $xblogid = $params->getParam(0);
1466        $xuser = $params->getParam(1);
1467        $xpass = $params->getParam(2);
1468        $xnum = $params->getParam(3);
1469       
1470        $blogid = $xblogid->scalarval();
1471        $username = $xuser->scalarval();
1472        $password = $xpass->scalarval();
1473        $num = $xnum->scalarval();
1474
1475        // Check login
1476        if (user_pass_ok($username,$password)) {
1477
1478                $postlist = wp_get_recent_posts($num);
1479               
1480                // Build response packet. We can't just use xmlrpc_encode,
1481                // because of the dateCreated field, which must be a date type.
1482               
1483                // Encode each entry of the array.
1484                foreach($postlist as $entry) {
1485                        $mdate = strtotime($entry['post_date']);
1486                        $isoString = date('Ymd',$mdate).'T'.date('H:i:s',$mdate);
1487                        $date = new xmlrpcval($isoString,"dateTime.iso8601");
1488                        $userid = new xmlrpcval($entry['post_author']);
1489                        $content = new xmlrpcval($entry['post_content']);
1490                        $excerpt = new xmlrpcval($entry['post_excerpt']);
1491                       
1492                        $pcat = stripslashes(get_cat_name($entry['post_category']));
1493                       
1494                        // For multiple cats, we might do something like
1495                        // this in the future:
1496                        //$catstruct['description'] = $pcat;
1497                        //$catstruct['categoryId'] = $entry['post_category'];
1498                        //$catstruct['categoryName'] = $pcat;
1499                        //$catstruct['isPrimary'] = TRUE;
1500                       
1501                        //$catstruct2 = xmlrpc_encode($catstruct);
1502                       
1503                        $categories = new xmlrpcval(array(new xmlrpcval($pcat)),'array');
1504
1505                        $post = get_extended($entry['post_content']);
1506
1507                        $postid = new xmlrpcval($entry['ID']);
1508                        $title = new xmlrpcval(stripslashes($entry['post_title']));
1509                        $description = new xmlrpcval(stripslashes($post['main']));
1510                        $link = new xmlrpcval(post_permalink($entry['ID']));
1511                        $permalink = $link;
1512
1513                        $extended = new xmlrpcval(stripslashes($post['extended']));
1514
1515                        $allow_comments = new xmlrpcval((('open' == $entry['comment_status'])?1:0),'int');
1516                        $allow_pings = new xmlrpcval((('open' == $entry['ping_status'])?1:0),'int');
1517
1518                        $encode_arr = array(
1519                                'dateCreated' => $date,
1520                                'userid' => $userid,
1521                                'postid' => $postid,
1522                                'categories' => $categories,
1523                                'title' => $title,
1524                                'description' => $description,
1525                                'link' => $link,
1526                                'permalink' => $permalink,
1527                                'mt_excerpt' => $excerpt,
1528                                'mt_allow_comments' => $allow_comments,
1529                                'mt_allow_pings' => $allow_pings,
1530                                'mt_text_more' => $extended
1531                        );
1532                       
1533                        $xmlrpcpostarr[] = new xmlrpcval($encode_arr,"struct");
1534                }       
1535
1536                // Now convert that to an xmlrpc array type
1537                $myResp = new xmlrpcval($xmlrpcpostarr,"array");
1538
1539                return new xmlrpcresp($myResp);
1540        } else {
1541                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1542           'Wrong username/password combination '.$username.' / '.starify($password));
1543        }
1544}
1545
1546
1547$mwgetcats_sig =  array(array($xmlrpcArray,$xmlrpcString,$xmlrpcString,$xmlrpcString));
1548$mwgetcats_doc = 'Get a post, MetaWeblog API-style';
1549
1550function mwgetcats ($params) {  // ($blogid, $user, $pass)
1551        global $xmlrpcerruser,$wpdb,$tablecategories;
1552        global $querystring_start, $querystring_equal, $querystring_separator;
1553        global $siteurl,$blogfilename;
1554       
1555        $blog_URL = $siteurl . '/' . $blogfilename;
1556       
1557        if ($cats = $wpdb->get_results("SELECT cat_ID,cat_name FROM $tablecategories",ARRAY_A)) {
1558                foreach ($cats as $cat) {
1559                        $struct['categoryId'] = $cat['cat_ID'];
1560                        $struct['description'] = $cat['cat_name'];
1561                        $struct['categoryName'] = $cat['cat_name'];
1562                        $struct['htmlUrl'] = htmlspecialchars($blog_URL . $querystring_start . 'cat' . $querystring_equal . $cat['cat_ID']);
1563                        $struct['rssUrl'] = ''; // will probably hack alexking's stuff in here
1564                       
1565                        $arr[] = xmlrpc_encode($struct);
1566                }
1567        }
1568       
1569        $resp = new xmlrpcval($arr,'array');
1570
1571        return new xmlrpcresp($resp);
1572}
1573
1574
1575$mwnewmedia_sig =  array(array($xmlrpcStruct,$xmlrpcString,$xmlrpcString,$xmlrpcString,$xmlrpcStruct));
1576$mwnewmedia_doc = 'Upload image or other binary data, MetaWeblog API-style (unimplemented)';
1577
1578function mwnewmedia($params) {  // ($blogid, $user, $pass, $struct)
1579        global $xmlrpcerruser;
1580       
1581        return new xmlrpcresp(0, $xmlrpcerruser+10, // user error 10
1582          'metaWeblog.newMediaObject not implemented (yet)');
1583}
1584
1585
1586/**** /MetaWeblog API ****/
1587
1588
1589/**** MovableType API ****/
1590
1591/**********************
1592 *
1593 * MovableType API extensions
1594 * added by
1595 *  Dougal Campbell <dougal@gunters.org>
1596 *  http://dougal.gunters.org/
1597 *
1598 * DONE:
1599 *  mt.getCategoryList
1600 *  mt.setPostCategories
1601 *  mt.supportedMethods
1602 *  mt.getPostCategories
1603 *  mt.publishPost
1604 *  mt.getRecentPostTitles
1605 *  extend metaWeblog.newPost
1606 *  extend metaWeblog.editPost
1607 *  extend metaWeblog.getPost
1608 *  extend metaWeblog.getRecentPosts
1609 *
1610 * PARTIALLY DONE:
1611 *  mt.supportedTextFilters             // empty stub, because WP doesn't support per-post text filters at this time
1612 *  mt.getTrackbackPings                // another stub.
1613 *  metaWeblog.newMediaObject   // ditto. For now.
1614 *
1615 **********************/
1616
1617$mt_supportedMethods_sig = array(array($xmlrpcArray));
1618$mt_supportedMethods_doc = 'Retrieve information about the XML-RPC methods supported by the server.';
1619
1620// ripped out of system.listMethods
1621function mt_supportedMethods($params) {
1622    global $dispatch_map, $xmlrpcerr, $xmlrpcstr, $_xmlrpcs_dmap;
1623    $v=new xmlrpcval();
1624    $dmap=$dispatch_map;
1625    $outAr=array();
1626    for(reset($dmap); list($key, $val)=each($dmap); ) {
1627        $outAr[]=new xmlrpcval($key, "string");
1628    }
1629    $dmap=$_xmlrpcs_dmap;
1630    for(reset($dmap); list($key, $val)=each($dmap); ) {
1631        $outAr[]=new xmlrpcval($key, "string");
1632    }
1633    $v->addArray($outAr);
1634    return new xmlrpcresp($v);
1635
1636}
1637
1638$mt_getPostCategories_sig = array(array($xmlrpcArray, $xmlrpcString, $xmlrpcString, $xmlrpcString));
1639$mt_getPostCategories_doc = "Returns a list of all categories to which the post is assigned.";
1640
1641function mt_getPostCategories($params) {
1642        global $xmlrpcusererr;
1643
1644        $xpostid = $params->getParam(0);
1645        $xuser = $params->getParam(1);
1646        $xpass = $params->getParam(2);
1647       
1648        $post_ID = $xpostid->scalarval();
1649        $username = $xuser->scalarval();
1650        $password = $xpass->scalarval();
1651
1652        if (user_pass_ok($username,$password)) {
1653                $catids = wp_get_post_cats('1', $post_ID);
1654
1655                // The first category listed will be set as primary
1656                $struct['isPrimary'] = true;
1657                foreach($catids as $catid) {   
1658                        $struct['categoryId'] = $catid;
1659                        $struct['categoryName'] = get_cat_name($catid);
1660
1661                        $resp_struct[] = xmlrpc_encode($struct);
1662                        $struct['isPrimary'] = false;
1663                }
1664               
1665                // Return an array of structs   
1666                $resp_array = new xmlrpcval($resp_struct,'array');
1667               
1668                return new xmlrpcresp($resp_array);
1669
1670        } else {
1671                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1672           'Wrong username/password combination '.$username.' / '.starify($password));
1673        }
1674}
1675
1676$mt_setPostCategories_sig = array(array($xmlrpcBoolean, $xmlrpcString, $xmlrpcString, $xmlrpcString, $xmlrpcArray));
1677$mt_setPostCategories_doc = "Sets the categories for a post";
1678
1679function mt_setPostCategories($params) {
1680        global $xmlrpcusererr;
1681       
1682        $xpostid = $params->getParam(0);
1683        $xuser = $params->getParam(1);
1684        $xpass = $params->getParam(2);
1685        $xcats = $params->getParam(3);
1686       
1687        $post_ID = $xpostid->scalarval();
1688        $username = $xuser->scalarval();
1689        $password = $xpass->scalarval();
1690        $cats = xmlrpc_decode($xcats);
1691       
1692        foreach($cats as $cat) {
1693                $catids[] = $cat['categoryId'];
1694        }
1695       
1696        if (user_pass_ok($username,$password)) {
1697                wp_set_post_cats('', $post_ID, $catids);
1698               
1699                return new xmlrpcresp(new xmlrpcval($result,'boolean'));
1700        } else {
1701                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1702           'Wrong username/password combination '.$username.' / '.starify($password));
1703        }
1704}
1705
1706$mt_publishPost_sig = array(array($xmlrpcBoolean, $xmlrpcString, $xmlrpcString, $xmlrpcString));
1707$mt_publishPost_doc = "Publish (rebuild) all of the static files related to an entry. Equivalent to saving an entry in the system (but without the ping).";
1708
1709function mt_publishPost($params) {
1710        global $xmlrpcusererr;
1711       
1712        $xpostid = $params->getParam(0);
1713        $xuser = $params->getParam(1);
1714        $xpass = $params->getParam(2);
1715       
1716        $post_ID = $xpostid->scalarval();
1717        $username = $xuser->scalarval();
1718        $password = $xpass->scalarval();
1719
1720        if (user_pass_ok($username,$password)) {
1721                $postdata = wp_get_single_post($post_ID,ARRAY_A);
1722               
1723                $postdata['post_status'] = 'publish';
1724               
1725                // retain old cats
1726                $cats = wp_get_post_cats('',$post_ID);
1727                $postdata['post_category'] = $cats;
1728       
1729                $result = wp_update_post($postdata);
1730
1731                return new xmlrpcresp(new xmlrpcval($result,'boolean'));
1732        } else {
1733                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1734           'Wrong username/password combination '.$username.' / '.starify($password));
1735        }
1736}
1737
1738$mt_getRecentPostTitles_sig = array(array($xmlrpcArray,$xmlrpcString,$xmlrpcString,$xmlrpcString,$xmlrpcInt));
1739$mt_getRecentPostTitles_doc = "Returns a bandwidth-friendly list of the most recent posts in the system.";
1740
1741function mt_getRecentPostTitles($params) {
1742        global $xmlrpcusererr, $wpdb, $tableposts;
1743
1744        $xblogid = $params->getParam(0);
1745        $xuser = $params->getParam(1);
1746        $xpass = $params->getParam(2);
1747        $xnumposts = $params->getParam(3);
1748
1749        $blogid = $xblogid->scalarval();
1750        $username = $xuser->scalarval();
1751        $password = $xpass->scalarval();
1752        $numposts = intval($xnumposts->scalarval());
1753
1754        if (user_pass_ok($username,$password)) {
1755                $sql = "SELECT post_date, post_author, ID, post_title FROM $tableposts ORDER BY post_date DESC LIMIT $numposts";
1756                $posts = $wpdb->get_results($sql,ARRAY_A);
1757               
1758                foreach($posts as $post) {
1759                        $post_date = strtotime($post['post_date']);
1760                        $post_date = date("Ymd", $post_date)."T".date("H:i:s", $post_date);
1761
1762                        $struct['dateCreated'] = new xmlrpcval($post_date, 'dateTime.iso8601');
1763                        $struct['userid'] = new xmlrpcval($post['post_author'], 'string');
1764                        $struct['postid'] = new xmlrpcval($post['ID'], 'string');
1765                        $struct['title'] = new xmlrpcval($post['post_title'], 'string');
1766                       
1767                        $result[] = $struct;
1768                }
1769               
1770                return new xmlrpcresp(new xmlrpcval($results,'array'));
1771
1772        } else {
1773                return new xmlrpcresp(0, $xmlrpcerruser+3, // user error 3
1774           'Wrong username/password combination '.$username.' / '.starify($password));
1775        }
1776}
1777
1778
1779$mt_supportedTextFilters_sig = array(array($xmlrpcArray));
1780$mt_supportedTextFilters_doc = "Retrieve information about the text formatting plugins supported by the server. (not implemented)";
1781
1782function mt_supportedTextFilters($params) {
1783        // This should probably check the status of the 'use_bbcode'
1784        // and 'use_gmcode' config options.
1785       
1786        return new xmlrpcresp(new xmlrpcval(array(),'array'));
1787}
1788
1789
1790
1791$mt_getTrackbackPings_sig = array(array($xmlrpcArray,$xmlrpcString));
1792$mt_getTrackbackPings_doc = "Retrieve the list of Trackback pings posted to a particular entry. (not implemented)";
1793
1794function mt_getTrackbackPings($params) {
1795        $struct['pingTitle'] = '';
1796        $struct['pingURL'] = '';
1797        $struct['pingIP'] = '';
1798       
1799        $xmlstruct = xmlrpc_encode($struct);
1800       
1801        return new xmlrpcresp(new xmlrpcval(array($xmlstruct),'array'));
1802}
1803
1804
1805
1806/**** /MovableType API ****/
1807
1808
1809/**** PingBack functions ****/
1810
1811$pingback_ping_sig = array(array($xmlrpcString, $xmlrpcString, $xmlrpcString));
1812
1813$pingback_ping_doc = 'Gets a pingback and registers it as a comment prefixed by &lt;pingback /&gt;';
1814
1815function pingback_ping($m) { // original code by Mort
1816        // (http://mort.mine.nu:8080)
1817        global $tableposts,$tablecomments, $comments_notify, $wpdb; 
1818        global $siteurl, $blogfilename,$wp_version, $use_pingback; 
1819        global $HTTP_SERVER_VARS, $wpdb;
1820
1821           
1822        if (!$use_pingback) {
1823                return new xmlrpcresp(new xmlrpcval('Sorry, this weblog does not allow you to pingback its posts.'));
1824        }
1825
1826
1827        //$log = debug_fopen('./xmlrpc.log', 'w');
1828
1829        $title='';
1830
1831        $pagelinkedfrom = $m->getParam(0);
1832        $pagelinkedfrom = $pagelinkedfrom->scalarval();
1833
1834        $pagelinkedto = $m->getParam(1);
1835        $pagelinkedto = $pagelinkedto->scalarval();
1836
1837        $pagelinkedfrom = str_replace('&amp;', '&', $pagelinkedfrom);
1838        $pagelinkedto = preg_replace('#&([^amp\;])#is', '&amp;$1', $pagelinkedto);
1839
1840        //debug_fwrite($log, 'BEGIN '.time().' - '.date('Y-m-d H:i:s')."\n\n");
1841        //debug_fwrite($log, 'Page linked from: '.$pagelinkedfrom."\n");
1842        //debug_fwrite($log, 'Page linked to: '.$pagelinkedto."\n");
1843
1844        $messages = array(
1845                htmlentities("Pingback from ".$pagelinkedfrom." to "
1846                        . $pagelinkedto . " registered. Keep the web talking! :-)"),
1847                htmlentities("We can't find the URL to the post you are trying to "
1848                        . "link to in your entry. Please check how you wrote the post's permalink in your entry."),
1849                htmlentities("We can't find the post you are trying to link to."
1850                        . " Please check the post's permalink.")
1851        );
1852
1853        $message = $messages[0];
1854
1855        // Check if the page linked to is in our site
1856        $pos1 = strpos($pagelinkedto, str_replace('http://', '', str_replace('www.', '', $siteurl)));
1857        if($pos1) {
1858
1859                // let's find which post is linked to
1860                $urltest = parse_url($pagelinkedto);
1861                if ($post_ID = url_to_postid($pagelinkedto)) {
1862                        $way = 'url_to_postid()';
1863                }
1864                elseif (preg_match('#p/[0-9]{1,}#', $urltest['path'], $match)) {
1865                        // the path defines the post_ID (archives/p/XXXX)
1866                        $blah = explode('/', $match[0]);
1867                        $post_ID = $blah[1];
1868                        $way = 'from the path';
1869                } elseif (preg_match('#p=[0-9]{1,}#', $urltest['query'], $match)) {
1870                        // the querystring defines the post_ID (?p=XXXX)
1871                        $blah = explode('=', $match[0]);
1872                        $post_ID = $blah[1];
1873                        $way = 'from the querystring';
1874                } elseif (isset($urltest['fragment'])) {
1875                        // an #anchor is there, it's either...
1876                        if (intval($urltest['fragment'])) {
1877                                // ...an integer #XXXX (simpliest case)
1878                                $post_ID = $urltest['fragment'];
1879                                $way = 'from the fragment (numeric)';
1880                        } elseif (preg_match('/post-[0-9]+/',$urltest['fragment'])) {
1881                                // ...a post id in the form 'post-###'
1882                                $post_ID = preg_replace('/[^0-9]+/', '', $urltest['fragment']);
1883                                $way = 'from the fragment (post-###)';
1884                        } elseif (is_string($urltest['fragment'])) {
1885                                // ...or a string #title, a little more complicated
1886                                $title = preg_replace('/[^a-zA-Z0-9]/', '.', $urltest['fragment']);
1887                                $sql = "SELECT ID FROM $tableposts WHERE post_title RLIKE '$title'";
1888                                $post_ID = $wpdb->get_var($sql) or die("Query: $sql\n\nError: ");
1889                                $way = 'from the fragment (title)';
1890                        }
1891                } else {
1892                        // TODO: Attempt to extract a post ID from the given URL
1893                        $post_ID = -1;
1894                        $way = 'no match';
1895                }
1896
1897                logIO("O","(PB) URI='$pagelinkedto' ID='$post_ID' Found='$way'");
1898
1899                //debug_fwrite($log, "Found post ID $way: $post_ID\n");
1900
1901                $sql = 'SELECT post_author FROM '.$tableposts.' WHERE ID = '.$post_ID;
1902                $result = $wpdb->get_results($sql);
1903
1904                if ($wpdb->num_rows) {
1905
1906                        //debug_fwrite($log, 'Post exists'."\n");
1907
1908                        // Let's check that the remote site didn't already pingback this entry
1909                        $sql = 'SELECT * FROM '.$tablecomments.'
1910                                WHERE comment_post_ID = '.$post_ID.'
1911                                        AND comment_author_url = \''.$pagelinkedfrom.'\'
1912                                        AND comment_content LIKE \'%<pingback />%\'';
1913                        $result = $wpdb->get_results($sql);
1914           
1915                        if ($wpdb->num_rows || (1==1)) {
1916
1917                                // very stupid, but gives time to the 'from' server to publish !
1918                                sleep(1);
1919
1920                                // Let's check the remote site
1921                                $fp = @fopen($pagelinkedfrom, 'r');
1922
1923                                $puntero = 4096;
1924                                while($remote_read = fread($fp, $puntero)) {
1925                                        $linea .= $remote_read;
1926                                }
1927                                        // Work around bug in strip_tags():
1928                                        $linea = str_replace('<!DOCTYPE','<DOCTYPE',$linea);
1929                                        $linea = strip_tags($linea, '<title><a>');
1930                                        $linea = strip_all_but_one_link($linea, $pagelinkedto);
1931                                        // I don't think we need this? -- emc3
1932                                        //$linea = preg_replace('#&([^amp\;])#is', '&amp;$1', $linea);
1933                                        if (empty($matchtitle)) {
1934                                                preg_match('|<title>([^<]*?)</title>|is', $linea, $matchtitle);
1935                                        }
1936                                        $pos2 = strpos($linea, $pagelinkedto);
1937                                        $pos3 = strpos($linea, str_replace('http://www.', 'http://', $pagelinkedto));
1938                                        if (is_integer($pos2) || is_integer($pos3)) {
1939                                                //debug_fwrite($log, 'The page really links to us :)'."\n");
1940                                                $pos4 = (is_integer($pos2)) ? $pos2 : $pos3;
1941                                                $start = $pos4-100;
1942                                                $context = substr($linea, $start, 250);
1943                                                $context = str_replace("\n", ' ', $context);
1944                                                $context = str_replace('&amp;', '&', $context);
1945                                        } else {
1946                                                //debug_fwrite($log, 'The page doesn\'t link to us, here\'s an excerpt :'."\n\n".$linea."\n\n");
1947                                        }
1948                                //}
1949                                //debug_fwrite($log, '*****'."\n\n");
1950                                fclose($fp);
1951
1952                                if (!empty($context)) {
1953                                        // Check if pings are on, inelegant exit
1954                                        $pingstatus = $wpdb->get_var("SELECT ping_status FROM $tableposts WHERE ID = $post_ID");
1955                                        if ('closed' == $pingstatus) die('Sorry, pings are turned off for this post.');
1956
1957                                        $pagelinkedfrom = preg_replace('#&([^amp\;])#is', '&amp;$1', $pagelinkedfrom);
1958                                        $title = (!strlen($matchtitle[1])) ? $pagelinkedfrom : $matchtitle[1];
1959                                        $original_context = $context;
1960                                        $context = '<pingback />[...] '.addslashes(trim($context)) .' [...]';
1961                                        $context = format_to_post($context);
1962                                        $original_pagelinkedfrom = $pagelinkedfrom;
1963                                        $pagelinkedfrom = addslashes($pagelinkedfrom);
1964                                        $original_title = $title;
1965                                        $title = addslashes(strip_tags(trim($title)));
1966                                        $now = current_time('mysql');
1967                                        $consulta = $wpdb->query("INSERT INTO $tablecomments 
1968                                                (comment_post_ID, comment_author, comment_author_url, comment_date, comment_content)
1969                                                VALUES
1970                                                ($post_ID, '$title', '$pagelinkedfrom', '$now', '$context')
1971                                                ");
1972
1973                                        $comment_ID = $wpdb->get_var('SELECT last_insert_id()');
1974                                        if ($comments_notify)
1975                                                wp_notify_postauthor($comment_ID, 'pingback');
1976                                } else {
1977                                        // URL pattern not found
1978                                        $message = "Page linked to: $pagelinkedto\nPage linked from:"
1979                                                . " $pagelinkedfrom\nTitle: $title\nContext: $context\n\n".$messages[1];
1980                                }
1981                        } else {
1982                                // We already have a Pingback from this URL
1983                                $message = "Sorry, you already did a pingback to $pagelinkedto"
1984                                . " from $pagelinkedfrom.";
1985                        }
1986                } else {
1987                        // Post_ID not found
1988                        $message = $messages[2];
1989                        //debug_fwrite($log, 'Post doesn\'t exist'."\n");
1990                }
1991        }
1992        return new xmlrpcresp(new xmlrpcval($message));
1993}
1994
1995/**** /PingBack functions ****/
1996
1997
1998
1999/**** Legacy functions ****/
2000
2001// a PHP version
2002// of the state-number server
2003// send me an integer and i'll sell you a state
2004
2005$stateNames=array(
2006"Alabama", "Alaska", "Arizona", "Arkansas", "California",
2007"Colorado", "Columbia", "Connecticut", "Delaware", "Florida",
2008"Georgia", "Hawaii", "Idaho", "Illinois", "Indiana", "Iowa", "Kansas",
2009"Kentucky", "Louisiana", "Maine", "Maryland", "Massachusetts", "Michigan",
2010"Minnesota", "Mississippi", "Missouri", "Montana", "Nebraska", "Nevada",
2011"New Hampshire", "New Jersey", "New Mexico", "New York", "North Carolina",
2012"North Dakota", "Ohio", "Oklahoma", "Oregon", "Pennsylvania", "Rhode Island",
2013"South Carolina", "South Dakota", "Tennessee", "Texas", "Utah", "Vermont",
2014"Virginia", "Washington", "West Virginia", "Wisconsin", "Wyoming");
2015
2016$findstate_sig=array(array($xmlrpcString, $xmlrpcInt));
2017
2018$findstate_doc='When passed an integer between 1 and 51 returns the
2019name of a US state, where the integer is the index of that state name
2020in an alphabetic order.';
2021
2022function findstate($m) {
2023  global $xmlrpcerruser, $stateNames;
2024  $err="";
2025  // get the first param
2026  $sno=$m->getParam(0);
2027  // if it's there and the correct type
2028
2029  if (isset($sno) && ($sno->scalartyp()=="int")) {
2030        // extract the value of the state number
2031        $snv=$sno->scalarval();
2032        // look it up in our array (zero-based)
2033        if (isset($stateNames[$snv-1])) {
2034          $sname=$stateNames[$snv-1];
2035        } else {
2036          // not, there so complain
2037          $err="I don't have a state for the index '" . $snv . "'";
2038        }
2039  } else {
2040        // parameter mismatch, complain
2041        $err="One integer parameter required";
2042  }
2043
2044  // if we generated an error, create an error return response
2045  if ($err) {
2046                return new xmlrpcresp(0, $xmlrpcerruser, $err);
2047  } else {
2048                // otherwise, we create the right response
2049                // with the state name
2050                return new xmlrpcresp(new xmlrpcval($sname));
2051  }
2052}
2053
2054$addtwo_sig=array(array($xmlrpcInt, $xmlrpcInt, $xmlrpcInt));
2055
2056$addtwo_doc='Add two integers together and return the result';
2057
2058function addtwo($m) {
2059  $s=$m->getParam(0);
2060        $t=$m->getParam(1);
2061  return new xmlrpcresp(new xmlrpcval($s->scalarval()+$t->scalarval(),
2062                                                                                                                                                        "int"));
2063}
2064
2065$addtwodouble_sig=array(array($xmlrpcDouble, $xmlrpcDouble, $xmlrpcDouble));
2066
2067$addtwodouble_doc='Add two doubles together and return the result';
2068
2069function addtwodouble($m) {
2070  $s=$m->getParam(0);
2071        $t=$m->getParam(1);
2072  return new xmlrpcresp(new xmlrpcval($s->scalarval()+$t->scalarval(),
2073                                                                                                                                                        "double"));
2074}
2075
2076$stringecho_sig=array(array($xmlrpcString, $xmlrpcString));
2077
2078$stringecho_doc='Accepts a string parameter, returns the string.';
2079
2080function stringecho($m) {
2081  // just sends back a string
2082  $s=$m->getParam(0);
2083  return new xmlrpcresp(new xmlrpcval($s->scalarval()));
2084}
2085
2086$echoback_sig=array(array($xmlrpcString, $xmlrpcString));
2087
2088$echoback_doc='Accepts a string parameter, returns the entire incoming payload';
2089
2090function echoback($m) {
2091  // just sends back a string with what i got
2092  // send to me, just escaped, that's all
2093  //
2094  // $m is an incoming message
2095  $s="I got the following message:\n" . $m->serialize();
2096  return new xmlrpcresp(new xmlrpcval($s));
2097}
2098
2099$echosixtyfour_sig=array(array($xmlrpcString, $xmlrpcBase64));
2100
2101$echosixtyfour_doc='Accepts a base64 parameter and returns it decoded as a string';
2102
2103function echosixtyfour($m) {
2104        // accepts an encoded value, but sends it back
2105        // as a normal string. this is to test base64 encoding
2106        // is working as expected
2107        $incoming=$m->getParam(0);
2108        return new xmlrpcresp(new xmlrpcval($incoming->scalarval(), "string"));
2109}
2110
2111$bitflipper_sig=array(array($xmlrpcArray, $xmlrpcArray));
2112
2113$bitflipper_doc='Accepts an array of booleans, and returns them inverted';
2114
2115function bitflipper($m) {
2116        global $xmlrpcArray;
2117
2118        $v=$m->getParam(0);
2119        $sz=$v->arraysize();
2120        $rv=new xmlrpcval(array(), $xmlrpcArray);
2121
2122        for($j=0; $j<$sz; $j++) {
2123                $b=$v->arraymem($j);
2124                if ($b->scalarval()) {
2125
2126                        $rv->addScalar(false, "boolean");
2127                } else {
2128
2129                        $rv->addScalar(true, "boolean");
2130                }
2131        }
2132
2133        return new xmlrpcresp($rv);
2134}
2135
2136// Sorting demo
2137//
2138// send me an array of structs thus:
2139//
2140// Dave 35
2141// Edd  45
2142// Fred 23
2143// Barney 37
2144//
2145// and I'll return it to you in sorted order
2146
2147function agesorter_compare($a, $b) {
2148  global $agesorter_arr;
2149
2150
2151  // don't even ask me _why_ these come padded with
2152  // hyphens, I couldn't tell you :p
2153  $a=ereg_replace("-", "", $a);
2154  $b=ereg_replace("-", "", $b);
2155
2156  if ($agesorter_arr[$a]==$agesorter[$b]) return 0;
2157  return ($agesorter_arr[$a] > $agesorter_arr[$b]) ? -1 : 1;
2158}
2159
2160$agesorter_sig=array(array($xmlrpcArray, $xmlrpcArray));
2161
2162$agesorter_doc='Send this method an array of [string, int] structs, eg:
2163<PRE>
2164 Dave   35
2165 Edd    45
2166 Fred   23
2167 Barney 37
2168</PRE>
2169And the array will be returned with the entries sorted by their numbers.
2170';
2171
2172function agesorter($m) {
2173  global $agesorter_arr, $xmlrpcerruser, $s;
2174
2175        xmlrpc_debugmsg("Entering 'agesorter'");
2176  // get the parameter
2177  $sno=$m->getParam(0);
2178  // error string for [if|when] things go wrong
2179  $err="";
2180  // create the output value
2181  $v=new xmlrpcval();
2182  $agar=array();
2183
2184  if (isset($sno) && $sno->kindOf()=="array") {
2185        $max=$sno->arraysize();
2186        // TODO: create debug method to print can work once more
2187        // print "<!-- found $max array elements -->\n";
2188        for($i = 0; $i < $max; $i = $i + 1) {
2189          $rec=$sno->arraymem($i);
2190          if ($rec->kindOf()!="struct") {
2191                $err="Found non-struct in array at element $i";
2192                break;
2193          }
2194          // extract name and age from struct
2195          $n=$rec->structmem("name");
2196          $a=$rec->structmem("age");
2197          // $n and $a are xmlrpcvals,
2198          // so get the scalarval from them
2199          $agar[$n->scalarval()]=$a->scalarval();
2200        }
2201
2202        $agesorter_arr=$agar;
2203        // hack, must make global as uksort() won't
2204        // allow us to pass any other auxilliary information
2205        uksort($agesorter_arr, agesorter_compare);
2206        $outAr=array();
2207        while (list( $key, $val ) = each( $agesorter_arr ) ) {
2208          // recreate each struct element
2209          $outAr[]=new xmlrpcval(array("name" =>
2210                                                                   new xmlrpcval($key),
2211                                                                   "age" =>
2212                                                                   new xmlrpcval($val, "int")), "struct");
2213        }
2214        // add this array to the output value
2215        $v->addArray($outAr);
2216  } else {
2217          $err="Must be one parameter, an array of structs";
2218  }
2219
2220  if ($err) {
2221                return new xmlrpcresp(0, $xmlrpcerruser, $err);
2222  } else {
2223                return new xmlrpcresp($v);
2224  }
2225}
2226
2227
2228// signature and instructions, place these in the dispatch
2229// map
2230
2231$mail_send_sig=array(array($xmlrpcBoolean, $xmlrpcString, $xmlrpcString,
2232                                                                                                         $xmlrpcString, $xmlrpcString, $xmlrpcString,
2233                                                                                                         $xmlrpcString, $xmlrpcString));
2234
2235$mail_send_doc='mail.send(recipient, subject, text, sender, cc, bcc, mimetype)
2236<BR>recipient, cc, and bcc are strings, comma-separated lists of email addresses, as described above.
2237<BR>subject is a string, the subject of the message.
2238<BR>sender is a string, it\'s the email address of the person sending the message. This string can not be
2239a comma-separated list, it must contain a single email address only.
2240text is a string, it contains the body of the message.
2241<BR>mimetype, a string, is a standard MIME type, for example, text/plain.
2242';
2243
2244// WARNING; this functionality depends on the sendmail -t option
2245// it may not work with Windows machines properly; particularly
2246// the Bcc option.  Sneak on your friends at your own risk!
2247function mail_send($m) {
2248  global $xmlrpcerruser, $xmlrpcBoolean;
2249        $err="";
2250
2251  $mTo=$m->getParam(0);
2252        $mSub=$m->getParam(1);
2253        $mBody=$m->getParam(2);
2254        $mFrom=$m->getParam(3);
2255        $mCc=$m->getParam(4);
2256        $mBcc=$m->getParam(5);
2257        $mMime=$m->getParam(6);
2258
2259        if ($mTo->scalarval()=="")
2260                $err="Error, no 'To' field specified";
2261
2262        if ($mFrom->scalarval()=="")
2263                $err="Error, no 'From' field specified";
2264
2265        $msghdr="From: " . $mFrom->scalarval() . "\n";
2266        $msghdr.="To: ". $mTo->scalarval() . "\n";
2267
2268        if ($mCc->scalarval()!="")
2269                $msghdr.="Cc: " . $mCc->scalarval(). "\n";
2270        if ($mBcc->scalarval()!="")
2271                $msghdr.="Bcc: " . $mBcc->scalarval(). "\n";
2272        if ($mMime->scalarval()!="")
2273                $msghdr.="Content-type: " . $mMime->scalarval() . "\n";
2274
2275        $msghdr.="X-Mailer: XML-RPC for PHP mailer 1.0";
2276
2277        if ($err=="") {
2278                /*
2279                if (!mail("",
2280                                                        $mSub->scalarval(),
2281                                                        $mBody->scalarval(),
2282                                                        $msghdr)) {
2283                        $err="Error, could not send the mail.";
2284                }
2285                */
2286                $err = 'Just in case someone wants to use this for spam, this method is disabled';
2287        }
2288
2289  if ($err) {
2290                return new xmlrpcresp(0, $xmlrpcerruser, $err);
2291  } else {
2292                return new xmlrpcresp(new xmlrpcval("true", $xmlrpcBoolean));
2293  }
2294}
2295
2296$v1_arrayOfStructs_sig=array(array($xmlrpcInt, $xmlrpcArray));
2297
2298$v1_arrayOfStructs_doc='This handler takes a single parameter, an array of structs, each of which contains at least three elements named moe, larry and curly, all <i4>s. Your handler must add all the struct elements named curly and return the result.';
2299
2300function v1_arrayOfStructs($m) {
2301  $sno=$m->getParam(0);
2302        $numcurly=0;
2303        for($i = 0; $i < $sno->arraysize(); $i = $i + 1) {
2304                $str=$sno->arraymem($i);
2305                $str->structreset();
2306                while(list($key,$val)=$str->structeach())
2307                        if ($key=="curly")
2308                                $numcurly+=$val->scalarval();
2309        }
2310        return new xmlrpcresp(new xmlrpcval($numcurly, "int"));
2311}
2312
2313$v1_easyStruct_sig=array(array($xmlrpcInt, $xmlrpcStruct));
2314
2315$v1_easyStruct_doc='This handler takes a single parameter, a struct, containing at least three elements named moe, larry and curly, all &lt;i4&gt;s. Your handler must add the three numbers and return the result.';
2316
2317function v1_easyStruct($m) {
2318  $sno=$m->getParam(0);
2319        $moe=$sno->structmem("moe");
2320        $larry=$sno->structmem("larry");
2321        $curly=$sno->structmem("curly");
2322        $num=$moe->scalarval()+
2323                $larry->scalarval()+
2324                $curly->scalarval();
2325        return new xmlrpcresp(new xmlrpcval($num, "int"));
2326}
2327
2328$v1_echoStruct_sig=array(array($xmlrpcStruct, $xmlrpcStruct));
2329
2330$v1_echoStruct_doc='This handler takes a single parameter, a struct. Your handler must return the struct.';
2331
2332function v1_echoStruct($m) {
2333  $sno=$m->getParam(0);
2334        return new xmlrpcresp($sno);
2335}
2336
2337$v1_manyTypes_sig=array(array($xmlrpcArray, $xmlrpcInt, $xmlrpcBoolean,
2338                                                                                                                        $xmlrpcString, $xmlrpcDouble, $xmlrpcDateTime,
2339                                                                                                                        $xmlrpcBase64));
2340
2341$v1_manyTypes_doc='This handler takes six parameters, and returns an array containing all the parameters.';
2342
2343function v1_manyTypes($m) {
2344        return new xmlrpcresp(new xmlrpcval(array(
2345                                                                                                                                                                                $m->getParam(0),
2346                                                                                                                                                                                $m->getParam(1),
2347                                                                                                                                                                                $m->getParam(2),
2348                                                                                                                                                                                $m->getParam(3),
2349                                                                                                                                                                                $m->getParam(4),
2350                                                                                                                                                                                $m->getParam(5)),
2351                                                                                                                                                        "array"));
2352}
2353
2354$v1_moderateSizeArrayCheck_sig=array(array($xmlrpcString, $xmlrpcArray));
2355
2356$v1_moderateSizeArrayCheck_doc='This handler takes a single parameter, which is an array containing between 100 and 200 elements. Each of the items is a string, your handler must return a string containing the concatenated text of the first and last elements.';
2357
2358function v1_moderateSizeArrayCheck($m) {
2359        $ar=$m->getParam(0);
2360        $sz=$ar->arraysize();
2361        $first=$ar->arraymem(0);
2362        $last=$ar->arraymem($sz-1);
2363        return new xmlrpcresp(new xmlrpcval($first->scalarval() .
2364                                                                                                                                                        $last->scalarval(), "string"));
2365}
2366
2367$v1_simpleStructReturn_sig=array(array($xmlrpcStruct, $xmlrpcInt));
2368
2369$v1_simpleStructReturn_doc='This handler takes one parameter, and returns a struct containing three elements, times10, times100 and times1000, the result of multiplying the number by 10, 100 and 1000.';
2370
2371function v1_simpleStructReturn($m) {
2372  $sno=$m->getParam(0);
2373        $v=$sno->scalarval();
2374        return new xmlrpcresp(new xmlrpcval(array(
2375                                                                                                                                                                                "times10" =>
2376                                                                                                                                                                                new xmlrpcval($v*10, "int"),
2377                                                                                                                                                                                "times100" =>
2378                                                                                                                                                                                new xmlrpcval($v*100, "int"),
2379                                                                                                                                                                                "times1000" =>
2380                                                                                                                                                                                new xmlrpcval($v*1000, "int")),
2381                                                                                                                                                        "struct"));
2382}
2383
2384$v1_nestedStruct_sig=array(array($xmlrpcInt, $xmlrpcStruct));
2385
2386$v1_nestedStruct_doc='This handler takes a single parameter, a struct, that models a daily calendar. At the top level, there is one struct for each year. Each year is broken down into months, and months into days. Most of the days are empty in the struct you receive, but the entry for April 1, 2000 contains a least three elements named moe, larry and curly, all &lt;i4&gt;s. Your handler must add the three numbers and return the result.';
2387
2388function v1_nestedStruct($m) {
2389  $sno=$m->getParam(0);
2390
2391        $twoK=$sno->structmem("2000");
2392        $april=$twoK->structmem("04");
2393        $fools=$april->structmem("01");
2394        $curly=$fools->structmem("curly");
2395        $larry=$fools->structmem("larry");
2396        $moe=$fools->structmem("moe");
2397        return new xmlrpcresp(new xmlrpcval($curly->scalarval()+
2398                                                                                                                                                        $larry->scalarval()+
2399                                                                                                                                                        $moe->scalarval(), "int"));
2400
2401}
2402
2403$v1_countTheEntities_sig=array(array($xmlrpcStruct, $xmlrpcString));
2404
2405$v1_countTheEntities_doc='This handler takes a single parameter, a string, that contains any number of predefined entities, namely &lt;, &gt;, &amp; \' and ".<BR>Your handler must return a struct that contains five fields, all numbers:  ctLeftAngleBrackets, ctRightAngleBrackets, ctAmpersands, ctApostrophes, ctQuotes.';
2406
2407function v1_countTheEntities($m) {
2408  $sno=$m->getParam(0);
2409        $str=$sno->scalarval();
2410        $gt=0; $lt=0; $ap=0; $qu=0; $amp=0;
2411        for($i = 0; $i < strlen($str); $i = $i + 1) {
2412                $c=substr($str, $i, 1);
2413                switch($c) {
2414                case ">":
2415                        $gt++;
2416                        break;
2417                case "<":
2418                        $lt++;
2419                        break;
2420                case "\"":
2421                        $qu++;
2422                        break;
2423                case "'":
2424                        $ap++;
2425                        break;
2426                case "&":
2427                        $amp++;
2428                        break;
2429                default:
2430                        break;
2431                }
2432        }
2433        return new xmlrpcresp(new xmlrpcval(array("ctLeftAngleBrackets" =>
2434                                                                                                                 new xmlrpcval($lt, "int"),
2435                                                                                                                 "ctRightAngleBrackets" =>
2436                                                                                                                 new xmlrpcval($gt, "int"),
2437                                                                                                                 "ctAmpersands" =>
2438                                                                                                                 new xmlrpcval($amp, "int"),
2439                                                                                                                 "ctApostrophes" =>
2440                                                                                                                 new xmlrpcval($ap, "int"),
2441                                                                                                                 "ctQuotes" =>
2442                                                                                                                 new xmlrpcval($qu, "int")),
2443                                                                                         "struct"));
2444}
2445
2446// trivial interop tests
2447// http://www.xmlrpc.com/stories/storyReader$1636
2448
2449$i_echoString_sig=array(array($xmlrpcString, $xmlrpcString));
2450$i_echoString_doc="Echoes string.";
2451
2452$i_echoStringArray_sig=array(array($xmlrpcArray, $xmlrpcArray));
2453$i_echoStringArray_doc="Echoes string array.";
2454
2455$i_echoInteger_sig=array(array($xmlrpcInt, $xmlrpcInt));
2456$i_echoInteger_doc="Echoes integer.";
2457
2458$i_echoIntegerArray_sig=array(array($xmlrpcArray, $xmlrpcArray));
2459$i_echoIntegerArray_doc="Echoes integer array.";
2460
2461$i_echoFloat_sig=array(array($xmlrpcDouble, $xmlrpcDouble));
2462$i_echoFloat_doc="Echoes float.";
2463
2464$i_echoFloatArray_sig=array(array($xmlrpcArray, $xmlrpcArray));
2465$i_echoFloatArray_doc="Echoes float array.";
2466
2467$i_echoStruct_sig=array(array($xmlrpcStruct, $xmlrpcStruct));
2468$i_echoStruct_doc="Echoes struct.";
2469
2470$i_echoStructArray_sig=array(array($xmlrpcArray, $xmlrpcArray));
2471$i_echoStructArray_doc="Echoes struct array.";
2472
2473$i_echoValue_doc="Echoes any value back.";
2474
2475$i_echoBase64_sig=array(array($xmlrpcBase64, $xmlrpcBase64));
2476$i_echoBase64_doc="Echoes base64.";
2477
2478$i_echoDate_sig=array(array($xmlrpcDateTime, $xmlrpcDateTime));
2479$i_echoDate_doc="Echoes dateTime.";
2480
2481function i_echoParam($m) {
2482        $s=$m->getParam(0);
2483        return new xmlrpcresp($s);
2484}
2485
2486function i_echoString($m) { return i_echoParam($m); }
2487function i_echoInteger($m) { return i_echoParam($m); }
2488function i_echoFloat($m) { return i_echoParam($m); }
2489function i_echoStruct($m) { return i_echoParam($m); }
2490function i_echoStringArray($m) { return i_echoParam($m); }
2491function i_echoIntegerArray($m) { return i_echoParam($m); }
2492function i_echoFloatArray($m) { return i_echoParam($m); }
2493function i_echoStructArray($m) { return i_echoParam($m); }
2494function i_echoValue($m) { return i_echoParam($m); }
2495function i_echoBase64($m) { return i_echoParam($m); }
2496function i_echoDate($m) { return i_echoParam($m); }
2497
2498$i_whichToolkit_doc="Returns a struct containing the following strings:  toolkitDocsUrl, toolkitName, toolkitVersion, toolkitOperatingSystem.";
2499
2500function i_whichToolkit($m) {
2501        global $xmlrpcName, $xmlrpcVersion,$SERVER_SOFTWARE,
2502                $xmlrpcStruct;
2503        $ret=array(
2504                                                 "toolkitDocsUrl" => "http://xmlrpc.usefulinc.com/php.html",
2505                                                 "toolkitName" => $xmlrpcName,
2506                                                 "toolkitVersion" => $xmlrpcVersion,
2507                                                 "toolkitOperatingSystem" => $SERVER_SOFTWARE);
2508        return new xmlrpcresp ( xmlrpc_encode($ret));
2509}
2510
2511
2512
2513/**** SERVER FUNCTIONS ARRAY ****/
2514
2515$dispatch_map =  array( "blogger.newPost" =>
2516                                                         array("function" => "bloggernewpost",
2517                                                                                 "signature" => $bloggernewpost_sig,
2518                                                                                 "docstring" => $bloggernewpost_doc),
2519
2520
2521                                                         "blogger.editPost" =>
2522                                                         array("function" => "bloggereditpost",
2523                                                                                 "signature" => $bloggereditpost_sig,
2524                                                                                 "docstring" => $bloggereditpost_doc),
2525
2526
2527                                                         "blogger.deletePost" =>
2528                                                         array("function" => "bloggerdeletepost",
2529                                                                                 "signature" => $bloggerdeletepost_sig,
2530                                                                                 "docstring" => $bloggerdeletepost_doc),
2531
2532
2533                                                         "blogger.getUsersBlogs" =>
2534                                                         array("function" => "bloggergetusersblogs",
2535                                                                                 "signature" => $bloggergetusersblogs_sig,
2536                                                                                 "docstring" => $bloggergetusersblogs_doc),
2537
2538                                                         "blogger.getUserInfo" =>
2539                                                         array("function" => "bloggergetuserinfo",
2540                                                                                 "signature" => $bloggergetuserinfo_sig,
2541                                                                                 "docstring" => $bloggergetuserinfo_doc),
2542
2543                                                         "blogger.getPost" =>
2544                                                         array("function" => "bloggergetpost",
2545                                                                                 "signature" => $bloggergetpost_sig,
2546                                                                                 "docstring" => $bloggergetpost_doc),
2547
2548                                                         "blogger.getRecentPosts" =>
2549                                                         array("function" => "bloggergetrecentposts",
2550                                                                                 "signature" => $bloggergetrecentposts_sig,
2551                                                                                 "docstring" => $bloggergetrecentposts_doc),
2552
2553                                                         "blogger.getTemplate" =>
2554                                                         array("function" => "bloggergettemplate",
2555                                                                                 "signature" => $bloggergettemplate_sig,
2556                                                                                 "docstring" => $bloggergettemplate_doc),
2557
2558                                                         "blogger.setTemplate" =>
2559                                                         array("function" => "bloggersettemplate",
2560                                                                                 "signature" => $bloggersettemplate_sig,
2561                                                                                 "docstring" => $bloggersettemplate_doc),
2562
2563                                                         "metaWeblog.newPost" =>
2564                                                         array("function" => "mwnewpost",
2565                                                                                 "signature" => $mwnewpost_sig,
2566                                                                                 "docstring" => $mwnewpost_doc),
2567
2568                                                         "metaWeblog.editPost" =>
2569                                                         array("function" => "mweditpost",
2570                                                                                 "signature" => $mweditpost_sig,
2571                                                                                 "docstring" => $mweditpost_doc),
2572
2573                                                         "metaWeblog.getPost" =>
2574                                                         array("function" => "mwgetpost",
2575                                                                                 "signature" => $mwgetpost_sig,
2576                                                                                 "docstring" => $mwgetpost_doc),
2577
2578                                                         "metaWeblog.getRecentPosts" =>
2579                                                         array("function" => "mwrecentposts",
2580                                                                                 "signature" => $mwrecentposts_sig,
2581                                                                                 "docstring" => $mwrecentposts_doc),
2582
2583                                                         "metaWeblog.getCategories" =>
2584                                                         array("function" => "mwgetcats",
2585                                                                                 "signature" => $mwgetcats_sig,
2586                                                                                 "docstring" => $mwgetcats_doc),
2587
2588                                                         "metaWeblog.newMediaObject" =>
2589                                                         array("function" => "mwnewmedia",
2590                                                                                 "signature" => $mwnewmedia_sig,
2591                                                                                 "docstring" => $mwnewmedia_doc),
2592
2593                                                         "mt.getCategoryList" =>
2594                                                         array("function" => "mwgetcats",
2595                                                                                 "signature" => $mwgetcats_sig,
2596                                                                                 "docstring" => $mwgetcats_doc),
2597
2598                                                         "mt.getPostCategories" =>
2599                                                         array("function" => "mt_getPostCategories",
2600                                                                                 "signature" => $mt_getPostCategories_sig,
2601                                                                                 "docstring" => $mt_getPostCategories_doc),
2602
2603                                                         "mt.setPostCategories" =>
2604                                                         array("function" => "mt_setPostCategories",
2605                                                                                 "signature" => $mt_setPostCategories_sig,
2606                                                                                 "docstring" => $mt_setPostCategories_doc),
2607
2608                                                         "mt.publishPost" =>
2609                                                         array("function" => "mt_publishPost",
2610                                                                                 "signature" => $mt_publishPost_sig,
2611                                                                                 "docstring" => $mt_publishPost_doc),
2612
2613                                                         "mt.supportedMethods" =>
2614                                                         array("function" => "mt_supportedMethods",
2615                                                                                 "signature" => $mt_supportedMethods_sig,
2616                                                                                 "docstring" => $mt_supportedMethods_doc),
2617
2618                                                         "mt.supportedTextFilters" =>
2619                                                         array("function" => "mt_supportedTextFilters",
2620                                                                                 "signature" => $mt_supportedTextFilters_sig,
2621                                                                                 "docstring" => $mt_supportedTextFilters_doc),
2622
2623                                                         "mt.getRecentPostTitles" =>
2624                                                         array("function" => "mt_getRecentPostTitles",
2625                                                                                 "signature" => $mt_getRecentPostTitles_sig,
2626                                                                                 "docstring" => $mt_getRecentPostTitles_doc),
2627
2628                                                         "mt.getTrackbackPings" =>
2629                                                         array("function" => "mt_getTrackbackPings",
2630                                                                                 "signature" => $mt_getTrackbackPings_sig,
2631                                                                                 "docstring" => $mt_getTrackbackPings_doc),
2632
2633                                                         "b2.newPost" =>
2634                                                         array("function" => "b2newpost",
2635                                                                                 "signature" => $wpnewpost_sig,
2636                                                                                 "docstring" => $wpnewpost_doc),
2637                                                         "b2.getCategories" =>
2638                                                         array("function" => "b2getcategories",
2639                                                                                 "signature" => $wpgetcategories_sig,
2640                                                                                 "docstring" => $wpgetcategories_doc),
2641
2642                                                         "b2.ping" =>
2643                                                         array("function" => "b2ping",
2644                                                                                 "signature" => $wpping_sig,
2645                                                                                 "docstring" => $wpping_doc),
2646
2647                                                         "pingback.ping" =>
2648                                                         array("function" => "pingback_ping",
2649                                                                                 "signature" => $pingback_ping_sig,
2650                                                                                 "docstring" => $pingback_ping_doc),
2651
2652                                                         "b2.getPostURL" =>
2653                                                         array("function" => "pingback_getPostURL",
2654                                                                                 "signature" => $wp_getPostURL_sig,
2655                                                                                 "docstring" => $wp_getPostURL_doc),
2656
2657
2658                                                         "examples.getStateName" =>
2659                                                         array("function" => "findstate",
2660                                                                                 "signature" => $findstate_sig,
2661                                                                                 "docstring" => $findstate_doc),
2662
2663                                                         "examples.sortByAge" =>
2664                                                         array("function" => "agesorter",
2665                                                                                 "signature" => $agesorter_sig,
2666                                                                                 "docstring" => $agesorter_doc),
2667
2668                                                         "examples.addtwo" =>
2669                                                         array("function" => "addtwo",
2670                                                                                 "signature" => $addtwo_sig,
2671                                                                                 "docstring" => $addtwo_doc),
2672
2673                                                         "examples.addtwodouble" =>
2674                                                         array("function" => "addtwodouble",
2675                                                                                 "signature" => $addtwodouble_sig,
2676                                                                                 "docstring" => $addtwodouble_doc),
2677
2678                                                         "examples.stringecho" =>
2679                                                         array("function" => "stringecho",
2680                                                                                 "signature" => $stringecho_sig,
2681                                                                                 "docstring" => $stringecho_doc),
2682
2683                                                         "examples.echo" =>
2684                                                         array("function" => "echoback",
2685                                                                                 "signature" => $echoback_sig,
2686                                                                                 "docstring" => $echoback_doc),
2687
2688                                                         "examples.decode64" =>
2689                                                         array("function" => "echosixtyfour",
2690                                                                                 "signature" => $echosixtyfour_sig,
2691                                                                                 "docstring" => $echosixtyfour_doc),
2692
2693                                                         "examples.invertBooleans" =>
2694                                                         array("function" => "bitflipper",
2695                                                                                 "signature" => $bitflipper_sig,
2696                                                                                 "docstring" => $bitflipper_doc),
2697
2698                                                         "mail.send" =>
2699                                                         array("function" => "mail_send",
2700                                                                                 "signature" => $mail_send_sig,
2701                                                                                 "docstring" => $mail_send_doc),
2702
2703                                                         "validator1.arrayOfStructsTest" =>
2704                                                         array("function" => "v1_arrayOfStructs",
2705                                                                                 "signature" => $v1_arrayOfStructs_sig,
2706                                                                                 "docstring" => $v1_arrayOfStructs_doc),
2707
2708                                                         "validator1.easyStructTest" =>
2709                                                         array("function" => "v1_easyStruct",
2710                                                                                 "signature" => $v1_easyStruct_sig,
2711                                                                                 "docstring" => $v1_easyStruct_doc),
2712
2713                                                          "validator1.echoStructTest" =>
2714                                                         array("function" => "v1_echoStruct",
2715                                                                                 "signature" => $v1_echoStruct_sig,
2716                                                                                 "docstring" => $v1_echoStruct_doc),
2717
2718                                                          "validator1.manyTypesTest" =>
2719                                                         array("function" => "v1_manyTypes",
2720                                                                                 "signature" => $v1_manyTypes_sig,
2721                                                                                 "docstring" => $v1_manyTypes_doc),
2722
2723                                                          "validator1.moderateSizeArrayCheck" =>
2724                                                         array("function" => "v1_moderateSizeArrayCheck",
2725                                                                                 "signature" => $v1_moderateSizeArrayCheck_sig,
2726                                                                                 "docstring" => $v1_moderateSizeArrayCheck_doc),
2727                                                          "validator1.simpleStructReturnTest" =>
2728                                                         array("function" => "v1_simpleStructReturn",
2729                                                                                 "signature" => $v1_simpleStructReturn_sig,
2730                                                                                 "docstring" => $v1_simpleStructReturn_doc),
2731
2732                                                         "validator1.nestedStructTest" =>
2733                                                         array("function" => "v1_nestedStruct",
2734                                                                                 "signature" => $v1_nestedStruct_sig,
2735                                                                                 "docstring" => $v1_nestedStruct_doc),
2736
2737                                                         "validator1.countTheEntities" =>
2738                                                         array("function" => "v1_countTheEntities",
2739                                                                                 "signature" => $v1_countTheEntities_sig,
2740                                                                                 "docstring" => $v1_countTheEntities_doc),
2741
2742                                                         "interopEchoTests.echoString" =>
2743                                                         array("function" => "i_echoString",
2744                                                                                 "signature" => $i_echoString_sig,
2745                                                                                 "docstring" => $i_echoString_doc),
2746
2747                                                         "interopEchoTests.echoStringArray" =>
2748                                                         array("function" => "i_echoStringArray",
2749                                                                                 "signature" => $i_echoStringArray_sig,
2750                                                                                 "docstring" => $i_echoStringArray_doc),
2751
2752                                                         "interopEchoTests.echoInteger" =>
2753                                                         array("function" => "i_echoInteger",
2754                                                                                 "signature" => $i_echoInteger_sig,
2755                                                                                 "docstring" => $i_echoInteger_doc),
2756
2757                                                         "interopEchoTests.echoIntegerArray" =>
2758                                                         array("function" => "i_echoIntegerArray",
2759                                                                                 "signature" => $i_echoIntegerArray_sig,
2760                                                                                 "docstring" => $i_echoIntegerArray_doc),
2761
2762                                                         "interopEchoTests.echoFloat" =>
2763                                                         array("function" => "i_echoFloat",
2764                                                                                 "signature" => $i_echoFloat_sig,
2765                                                                                 "docstring" => $i_echoFloat_doc),
2766
2767                                                         "interopEchoTests.echoFloatArray" =>
2768                                                         array("function" => "i_echoFloatArray",
2769                                                                                 "signature" => $i_echoFloatArray_sig,
2770                                                                                 "docstring" => $i_echoFloatArray_doc),
2771
2772                                                         "interopEchoTests.echoStruct" =>
2773                                                         array("function" => "i_echoStruct",
2774                                                                                 "signature" => $i_echoStruct_sig,
2775                                                                                 "docstring" => $i_echoStruct_doc),
2776
2777                                                         "interopEchoTests.echoStructArray" =>
2778                                                         array("function" => "i_echoStructArray",
2779                                                                                 "signature" => $i_echoStructArray_sig,
2780                                                                                 "docstring" => $i_echoStructArray_doc),
2781
2782                                                          "interopEchoTests.echoValue" =>
2783                                                         array("function" => "i_echoValue",
2784                                                                                 // no sig as takes anytype
2785                                                                                 "docstring" => $i_echoValue_doc),
2786
2787                                                          "interopEchoTests.echoBase64" =>
2788                                                         array("function" => "i_echoBase64",
2789                                                                                 "signature" => $i_echoBase64_sig,
2790                                                                                 "docstring" => $i_echoBase64_doc),
2791
2792                                                          "interopEchoTests.echoDate" =>
2793                                                         array("function" => "i_echoDate",
2794                                                                                 "signature" => $i_echoDate_sig,
2795                                                                                 "docstring" => $i_echoDate_doc),
2796
2797                                                         "interopEchoTests.whichToolkit" =>
2798                                                         array("function" => "i_whichToolkit",
2799                                                                                 // no sig as no parameters
2800                                                                                 "docstring" => $i_whichToolkit_doc),
2801
2802
2803                                                );
2804
2805
2806
2807$s=new xmlrpc_server($dispatch_map);
2808                                               
2809                                               
2810
2811?>