Completed
Push — issues/3312 ( 6b1a83 )
by Ravinder
1313:55 queued 1307:48
created

Give_Clone_Form::row_action()   A

Complexity

Conditions 4
Paths 3

Size

Total Lines 24

Duplication

Lines 13
Ratio 54.17 %

Importance

Changes 0
Metric Value
cc 4
nc 3
nop 2
dl 13
loc 24
rs 9.536
c 0
b 0
f 0
1
<?php
2
/**
3
 * The class contains logic to clone a donation form.
4
 *
5
 * @package     Give
6
 * @subpackage  Admin/Forms
7
 * @copyright   Copyright (c) 2018, WordImpress
8
 * @license     http://opensource.org/licenses/gpl-2.0.php GNU Public License
9
 * @since       2.2.0
10
 */
11
12
if ( ! class_exists( 'Give_Clone_Form' ) ) {
13
14
	/**
15
	 * Give_Clone_Form class
16
	 */
17
	class Give_Clone_Form {
18
19
		/**
20
		 * Constructor Function
21
		 */
22
		public function __construct() {
23
24
			// Add the 'Clone Form' to Row Actions.
25
			add_filter( 'post_row_actions', array( $this, 'row_action' ), 10, 2 );
26
27
			// Run admin_action hook.
28
			add_action( 'admin_action_give_clone_form', array( $this, 'handler' ) );
29
		}
30
31
32
		/**
33
		 * Adds the 'Clone Form' in the row actions.
34
		 *
35
		 * @param array          $actions Array of Row Actions.
36
		 * @param WP_Post Object $post    Post Object.
37
		 *
38
		 * @since 2.2.0
39
		 *
40
		 * @return array
41
		 */
42
		public function row_action( $actions, $post ) {
43
44
			// @codingStandardsIgnoreStart
45
46
			if ( isset( $_GET['post_type'] ) && 'give_forms' === give_clean( $_GET['post_type'] ) ) { // WPCS: input var ok.
47 View Code Duplication
				if ( current_user_can( 'edit_posts' ) ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
48
					$actions['clone_form'] = sprintf(
49
						'<a href="%1$s">%2$s</a>',
50
						wp_nonce_url( add_query_arg(
51
							array(
52
								'action'  => 'give_clone_form',
53
								'form_id' => $post->ID,
54
							),
55
							admin_url( 'admin.php' )
56
						), 'give-clone-form' ),
57
						__( 'Clone Form', 'give' )
58
					);
59
				}
60
			}
61
62
			// @codingStandardsIgnoreEnd
63
64
			return $actions;
65
		}
66
67
68
		/**
69
		 * Clones the Form
70
		 *
71
		 * @since 2.2.0
72
		 *
73
		 * @return void
74
		 */
75
		public function handler() {
76
			// Validate action.
77
			// @codingStandardsIgnoreStart
78
			if (
79
				! isset( $_REQUEST['form_id'] )
80
				|| ! isset( $_REQUEST['action'] )
81
				|| ( 'give_clone_form' !== $_REQUEST['action'] )
82
			) {
83
				wp_die( esc_html__( 'Form ID not found in the query string', 'give' ) );
84
85
			} elseif ( ! wp_verify_nonce( give_clean( $_REQUEST['_wpnonce'] ), 'give-clone-form' ) ) {
86
87
				wp_die( esc_html__( 'Nonce verification failed', 'give' ) );
88
			}
89
			// @codingStandardsIgnoreEnd
90
91
			$form_id      = give_clean( $_REQUEST['form_id'] ); // @codingStandardsIgnoreLine
92
			$post_data         = get_post( $form_id );
93
			$current_user = wp_get_current_user();
94
			$error_notice = sprintf(
95
				/* translators: %s: Form ID */
96
				esc_html__( 'Cloning failed. Form with ID %s does not exist.', 'give' ),
97
				absint( $form_id )
98
			);
99
100
			if ( isset( $post_data ) && null !== $post_data ) {
101
102
				$args = array(
103
					'comment_status' => $post_data->comment_status,
104
					'ping_status'    => $post_data->ping_status,
105
					'post_author'    => $current_user->ID,
106
					'post_content'   => $post_data->post_content,
107
					'post_excerpt'   => $post_data->post_excerpt,
108
					'post_name'      => $post_data->post_name,
109
					'post_parent'    => $post_data->post_parent,
110
					'post_password'  => $post_data->post_password,
111
					'post_status'    => 'draft',
112
					'post_title'     => $post_data->post_title,
113
					'post_type'      => $post_data->post_type,
114
					'to_ping'        => $post_data->to_ping,
115
					'menu_order'     => $post_data->menu_order,
116
				);
117
118
				// Get the ID of the cloned post.
119
				$clone_form_id = wp_insert_post( $args );
120
121
				$this->clone_taxonomies( $clone_form_id, $post_data );
122
				$this->clone_meta_data( $clone_form_id, $post_data );
123
124
				if ( ! is_wp_error( $clone_form_id ) ) {
125
					// Redirect to the cloned form editor page.
126
					wp_safe_redirect(
127
						add_query_arg(
128
							array(
129
								'action' => 'edit',
130
								'post'   => $clone_form_id,
131
							),
132
							admin_url( 'post.php' )
133
						)
134
					);
135
				} else {
136
					wp_die( $error_notice ); // @codingStandardsIgnoreLine
137
				}
138
139
				exit;
140
141
			} else {
142
143
				wp_die( $error_notice ); // @codingStandardsIgnoreLine
144
			}
145
		}
146
147
148
		/**
149
		 * Clone taxonomies
150
		 *
151
		 * @since  2.2.0
152
		 * @access private
153
		 *
154
		 * @param int     $new_form_id New form ID.
155
		 * @param WP_Post $old_form    Old form object.
156
		 */
157
		private function clone_taxonomies( $new_form_id, $old_form ) {
158
			// Get the taxonomies of the post type `give_forms`.
159
			$taxonomies = get_object_taxonomies( $old_form->post_type );
160
161
			foreach ( $taxonomies as $taxonomy ) {
162
163
				$post_terms = wp_get_object_terms(
164
					$old_form->ID,
165
					$taxonomy,
166
					array(
167
						'fields' => 'slugs',
168
					)
169
				);
170
171
				wp_set_object_terms(
172
					$new_form_id,
173
					$post_terms,
174
					$taxonomy,
175
					false
176
				);
177
			}
178
		}
179
180
181
		/**
182
		 * Clone meta data
183
		 *
184
		 * @since  2.2.0
185
		 * @access private
186
		 *
187
		 * @param int     $new_form_id New Form ID.
188
		 * @param WP_Post $old_form    Old form object.
189
		 */
190
		private function clone_meta_data( $new_form_id, $old_form ) {
191
			global $wpdb;
192
193
			// Clone the metadata of the form.
194
			$post_meta_query = $wpdb->prepare( "SELECT meta_key, meta_value FROM {$wpdb->formmeta} WHERE form_id=%s", $old_form->ID );
195
196
			$post_meta_data = $wpdb->get_results( $post_meta_query ); // WPCS: db call ok. WPCS: cache ok. WPCS: unprepared SQL OK.
197
198
			if ( ! empty( $post_meta_data ) ) {
199
200
				$clone_query        = "INSERT INTO {$wpdb->formmeta} (form_id, meta_key, meta_value) ";
201
				$clone_query_select = array();
202
203
				foreach ( $post_meta_data as $meta_data ) {
204
					$meta_key             = $meta_data->meta_key;
205
					$meta_value           = $meta_data->meta_value;
206
					$clone_query_select[] = $wpdb->prepare( 'SELECT %s, %s, %s', $new_form_id, $meta_key, $meta_value );
207
				}
208
209
				$clone_query .= implode( ' UNION ALL ', $clone_query_select );
210
211
				$wpdb->query( $clone_query ); // WPCS: db call ok. WPCS: cache ok. WPCS: unprepared SQL OK.
212
			}
213
		}
214
	}
215
216
	new Give_Clone_Form();
217
}
218