PluginProbe
bbPress / 2.6.17
bbPress v2.6.17
2.6.17 trunk 2.0 2.0-beta-1 2.0-beta-2b 2.0-beta-3 2.0-beta-3b 2.0-rc-2 2.0-rc-3 2.0-rc-4 2.0-rc-5 2.0.1 2.0.2 2.0.3 2.1 2.1-beta-1 2.1-rc1 2.1-rc2 2.1-rc3 2.1-rc4 2.1.1 2.1.2 2.1.3 2.2 2.2.1 All 72 releases
bbpress / includes / common / xmlrpc.php

xmlrpc.php in bbPress 2.6.17, at includes/common/xmlrpc.php

193 lines 5.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 /**
4 * bbPress XML-RPC Functions.
5 *
6 * @package bbPress
7 * @subpackage Common
8 */
9
10 // Exit if accessed directly
11 defined( 'ABSPATH' ) || exit;
12
13 /**
14 * Validate an XML-RPC edit against bbPress posting rules.
15 *
16 * @since 2.6.17 bbPress
17 *
18 * @param string $method XML-RPC method name.
19 * @param array $args XML-RPC method arguments.
20 */
21 function bbp_validate_xmlrpc_post( $method = '', $args = array() ) {
22 global $bbp_xmlrpc_error_post_id;
23
24 $bbp_xmlrpc_error_post_id = 0;
25
26 $is_restore = ( 'wp.restoreRevision' === $method );
27
28 // Validate an edit or resolve its revision back to a bbPress post
29 if ( 'wp.editPost' === $method ) {
30 if ( empty( $args[3] ) || empty( $args[4] ) || ! is_array( $args[4] ) ) {
31 return;
32 }
33
34 $post_id = (int) $args[3];
35 $post_data = $args[4];
36 } elseif ( $is_restore && ! empty( $args[3] ) ) {
37 $revision_id = (int) $args[3];
38 $revision = wp_get_post_revision( $revision_id );
39
40 if ( empty( $revision ) ) {
41 return;
42 }
43
44 $post_id = (int) $revision->post_parent;
45 $post_data = array(
46 'post_title' => $revision->post_title,
47 'post_content' => $revision->post_content,
48 );
49 } else {
50 return;
51 }
52
53 $post = get_post( $post_id );
54
55 if ( empty( $post ) ) {
56 return;
57 }
58
59 $post_type = $post->post_type;
60
61 if ( ! in_array( $post_type, array( bbp_get_forum_post_type(), bbp_get_topic_post_type(), bbp_get_reply_post_type() ), true ) ) {
62 return;
63 }
64
65 $post_parent = isset( $post_data['post_parent'] )
66 ? (int) $post_data['post_parent']
67 : (int) $post->post_parent;
68 $parent_changed = ( $post_parent !== (int) $post->post_parent );
69 $status_changed = isset( $post_data['post_status'] ) && ( $post_data['post_status'] !== $post->post_status );
70 $order_changed = isset( $post_data['menu_order'] ) && ( (int) $post_data['menu_order'] !== (int) $post->menu_order );
71 $invalid = false;
72
73 // Validate forum structure and visibility changes
74 if ( bbp_get_forum_post_type() === $post_type ) {
75 if ( ! $is_restore && $parent_changed && ! current_user_can( 'assign_moderators' ) ) {
76 $invalid = true;
77 }
78
79 if ( ! $is_restore && $status_changed && ! current_user_can( 'manage_forum_attributes', $post_id ) ) {
80 $invalid = true;
81 }
82
83 if ( ! $is_restore && $order_changed && ! current_user_can( 'assign_moderators' ) ) {
84 $invalid = true;
85 }
86
87 if ( $invalid ) {
88 $bbp_xmlrpc_error_post_id = $post_id;
89 }
90
91 return;
92 }
93
94 // Structural changes require bbPress lifecycle handlers to keep related metadata and counts synchronized
95 if ( ! $is_restore && ( $parent_changed || $status_changed || $order_changed ) ) {
96 $invalid = true;
97 }
98
99 // Validate topic forum access
100 if ( bbp_get_topic_post_type() === $post_type ) {
101 if ( empty( $post_parent ) || bbp_is_forum_category( $post_parent ) ) {
102 $invalid = true;
103 } elseif ( ! current_user_can( 'edit_forum', $post_parent ) && bbp_is_forum_closed( $post_parent ) ) {
104 $invalid = true;
105 } elseif ( ! current_user_can( 'read_forum', $post_parent ) ) {
106 $invalid = true;
107 }
108 }
109
110 // Validate reply topic and forum access
111 if ( bbp_get_reply_post_type() === $post_type ) {
112 $topic_id = bbp_get_reply_topic_id( $post_id );
113 $forum_id = bbp_get_topic_forum_id( $topic_id );
114
115 if ( ! current_user_can( 'read_topic', $topic_id ) || ! current_user_can( 'read_forum', $forum_id ) ) {
116 $invalid = true;
117 }
118 }
119
120 $title = isset( $post_data['post_title'] ) ? wp_unslash( $post_data['post_title'] ) : $post->post_title;
121 $content = isset( $post_data['post_content'] ) ? wp_unslash( $post_data['post_content'] ) : $post->post_content;
122
123 if ( empty( $content ) || ( ( bbp_get_topic_post_type() === $post_type ) && empty( $title ) ) || bbp_is_title_too_long( $title ) ) {
124 $invalid = true;
125 }
126
127 if ( ! bbp_check_for_moderation( array(), (int) $post->post_author, $title, $content, true ) ) {
128 $invalid = true;
129 }
130
131 // Revision restoration cannot change the post status to pending
132 if ( $is_restore && ! bbp_check_for_moderation( array(), (int) $post->post_author, $title, $content ) ) {
133 $invalid = true;
134 }
135
136 if ( $invalid ) {
137 $bbp_xmlrpc_error_post_id = $post_id;
138 }
139 }
140
141 /**
142 * Deny a post capability when an XML-RPC edit failed bbPress validation.
143 *
144 * @since 2.6.17 bbPress
145 *
146 * @param array $caps Required capabilities.
147 * @param string $cap Requested capability.
148 * @param int $user_id User ID.
149 * @param array $args Capability arguments.
150 * @return array Required capabilities.
151 */
152 function bbp_map_xmlrpc_meta_caps( $caps = array(), $cap = '', $user_id = 0, $args = array() ) {
153 global $bbp_xmlrpc_error_post_id;
154
155 $edit_caps = array( 'edit_post', 'edit_topic', 'edit_reply' );
156
157 if ( ! empty( $bbp_xmlrpc_error_post_id ) && in_array( $cap, $edit_caps, true ) && ! empty( $args[0] ) && ( (int) $args[0] === $bbp_xmlrpc_error_post_id ) ) {
158 $caps[] = 'do_not_allow';
159 }
160
161 return $caps;
162 }
163
164 /**
165 * Apply bbPress moderation to XML-RPC post data.
166 *
167 * @since 2.6.17 bbPress
168 *
169 * @param array $post_data Parsed post data.
170 * @return array Parsed post data.
171 */
172 function bbp_xmlrpc_wp_insert_post_data( $post_data = array() ) {
173 $post_id = ! empty( $post_data['ID'] ) ? (int) $post_data['ID'] : 0;
174 $post_type = isset( $post_data['post_type'] ) ? $post_data['post_type'] : '';
175
176 if ( empty( $post_id ) || ! in_array( $post_type, array( bbp_get_topic_post_type(), bbp_get_reply_post_type() ), true ) ) {
177 return $post_data;
178 }
179
180 $title = isset( $post_data['post_title'] ) ? wp_unslash( $post_data['post_title'] ) : '';
181 $content = isset( $post_data['post_content'] ) ? wp_unslash( $post_data['post_content'] ) : '';
182 $author_id = isset( $post_data['post_author'] ) ? (int) $post_data['post_author'] : 0;
183 $is_public = ( bbp_get_topic_post_type() === $post_type )
184 ? bbp_is_topic_public( $post_id )
185 : bbp_is_reply_public( $post_id );
186
187 if ( $is_public && ! bbp_check_for_moderation( array(), $author_id, $title, $content ) ) {
188 $post_data['post_status'] = bbp_get_pending_status_id();
189 }
190
191 return $post_data;
192 }
193