PodsAPI

The Pods - Custom Content Types and Fields PodsAPI class.

Defined (1)

The class is defined in the following location(s).

/classes/PodsAPI.php  
  1. class PodsAPI { 
  2.  
  3. /** 
  4. * @var PodsAPI 
  5. */ 
  6. static $instance = null; 
  7.  
  8. /** 
  9. * @var array PodsAPI 
  10. */ 
  11. static $instances = array(); 
  12.  
  13.  
  14. /** 
  15. * @var bool 
  16. */ 
  17. public $display_errors = false; 
  18.  
  19. /** 
  20. * @var array|bool|mixed|null|void 
  21. */ 
  22. public $pod_data; 
  23.  
  24. /** 
  25. * @var 
  26. */ 
  27. public $pod; 
  28.  
  29. /** 
  30. * @var 
  31. */ 
  32. public $pod_id; 
  33.  
  34. /** 
  35. * @var 
  36. */ 
  37. public $fields; 
  38.  
  39. /** 
  40. * @var 
  41. * @deprecated 2.0 
  42. */ 
  43. public $format = null; 
  44.  
  45. /** 
  46. * @var 
  47. */ 
  48. private $deprecated; 
  49.  
  50. /** 
  51. * @var array 
  52. * @since 2.5 
  53. */ 
  54. private $fields_cache = array(); 
  55.  
  56. /** 
  57. * @var array 
  58. * @since 2.5 
  59. */ 
  60. private static $table_info_cache = array(); 
  61.  
  62. /** 
  63. * @var array 
  64. * @since 2.5 
  65. */ 
  66. private static $related_item_cache = array(); 
  67.  
  68. /** 
  69. * Singleton-ish handling for a basic pods_api() request 
  70. * @param string $pod (optional) The pod name 
  71. * @param string $format (deprecated) Format for import/export, "php" or "csv" 
  72. * @return \PodsAPI 
  73. * @since 2.3.5 
  74. */ 
  75. public static function init ( $pod = null, $format = null ) { 
  76. if ( null !== $pod || null !== $format ) { 
  77. if ( ! isset( self::$instances[ $pod ] ) ) { 
  78. // Cache API singleton per Pod 
  79. self::$instances[ $pod ] = new PodsAPI( $pod, $format ); 
  80. return self::$instances[ $pod ]; 
  81. elseif ( !is_object( self::$instance ) ) { 
  82. self::$instance = new PodsAPI(); 
  83.  
  84. return self::$instance; 
  85.  
  86.  
  87. /** 
  88. * Store and retrieve data programatically 
  89. * @param string $pod (optional) The pod name 
  90. * @param string $format (deprecated) Format for import/export, "php" or "csv" 
  91. * @return \PodsAPI 
  92. * @license http://www.gnu.org/licenses/gpl-2.0.html 
  93. * @since 1.7.1 
  94. */ 
  95. public function __construct ( $pod = null, $format = null ) { 
  96. if ( null !== $pod && 0 < strlen( (string) $pod ) ) { 
  97. if ( null !== $format ) { 
  98. $this->format = $format; 
  99.  
  100. pods_deprecated( 'pods_api( $pod, $format )', '2.0', 'pods_api( $pod )' ); 
  101.  
  102. $pod = pods_clean_name( $pod ); 
  103.  
  104. $pod = $this->load_pod( array( 'name' => $pod, 'table_info' => true ), false ); 
  105.  
  106. if ( !empty( $pod ) ) { 
  107. $this->pod_data = $pod; 
  108. $this->pod = $pod[ 'name' ]; 
  109. $this->pod_id = $pod[ 'id' ]; 
  110. $this->fields = $pod[ 'fields' ]; 
  111.  
  112. /** 
  113. * Save a WP object and its meta 
  114. * @param string $object_type Object type: post|taxonomy|user|comment|setting 
  115. * @param array $data All post data to be saved 
  116. * @param array $meta (optional) Associative array of meta keys and values 
  117. * @param bool $strict (optional) Decides whether the previous saved meta should be deleted or not 
  118. * @param bool $sanitized (optional) Will unsanitize the data, should be passed if the data is sanitized before sending. 
  119. * @param array $fields (optional) The array of fields and their options, for further processing with 
  120. * @return bool|mixed 
  121. * @since 2.0 
  122. */ 
  123. public function save_wp_object ( $object_type, $data, $meta = array(), $strict = false, $sanitized = false, $fields = array() ) { 
  124. if ( in_array( $object_type, array( 'post_type', 'media' ) ) ) 
  125. $object_type = 'post'; 
  126.  
  127. if ( 'taxonomy' == $object_type ) 
  128. $object_type = 'term'; 
  129.  
  130. if ( $sanitized ) { 
  131. $data = pods_unsanitize( $data ); 
  132. $meta = pods_unsanitize( $meta ); 
  133.  
  134. if ( in_array( $object_type, array( 'post', 'term', 'user', 'comment' ) ) ) 
  135. return call_user_func( array( $this, 'save_' . $object_type ), $data, $meta, $strict, false, $fields ); 
  136. elseif ( 'settings' == $object_type ) { 
  137. // Nothing to save 
  138. if ( empty( $meta ) ) 
  139. return true; 
  140.  
  141. return $this->save_setting( pods_var( 'option_id', $data ), $meta, false ); 
  142.  
  143. return false; 
  144.  
  145. /** 
  146. * Delete a WP object 
  147. * @param string $object_type Object type: post|user|comment 
  148. * @param int $id Object ID 
  149. * @param bool $force_delete (optional) Force deletion instead of trashing (post types only) 
  150. * @return bool|mixed 
  151. * @since 2.0 
  152. */ 
  153. public function delete_wp_object ( $object_type, $id, $force_delete = true ) { 
  154. if ( in_array( $object_type, array( 'post_type', 'media' ) ) ) 
  155. $object_type = 'post'; 
  156.  
  157. if ( 'taxonomy' == $object_type ) 
  158. $object_type = 'term'; 
  159.  
  160. if ( empty( $id ) ) 
  161. return false; 
  162.  
  163. if ( in_array( $object_type, array( 'post' ) ) ) 
  164. return wp_delete_post( $id, $force_delete ); 
  165.  
  166. if ( function_exists( 'wp_delete_' . $object_type ) ) 
  167. return call_user_func( 'wp_delete_' . $object_type, $id ); 
  168.  
  169. return false; 
  170.  
  171. /** 
  172. * Save a post and it's meta 
  173. * @param array $post_data All post data to be saved (using wp_insert_post / wp_update_post) 
  174. * @param array $post_meta (optional) All meta to be saved (set value to null to delete) 
  175. * @param bool $strict (optional) Whether to delete previously saved meta not in $post_meta 
  176. * @param bool $sanitized (optional) Will unsanitize the data, should be passed if the data is sanitized before sending. 
  177. * @param array $fields (optional) The array of fields and their options, for further processing with 
  178. * @return mixed|void 
  179. * @since 2.0 
  180. */ 
  181. public function save_post ( $post_data, $post_meta = null, $strict = false, $sanitized = false, $fields = array() ) { 
  182. $conflicted = pods_no_conflict_check( 'post' ); 
  183.  
  184. if ( !$conflicted ) 
  185. pods_no_conflict_on( 'post' ); 
  186.  
  187. if ( !is_array( $post_data ) || empty( $post_data ) ) 
  188. $post_data = array( 'post_title' => '' ); 
  189.  
  190. if ( !is_array( $post_meta ) ) 
  191. $post_meta = array(); 
  192.  
  193. if ( $sanitized ) { 
  194. $post_data = pods_unsanitize( $post_data ); 
  195. $post_meta = pods_unsanitize( $post_meta ); 
  196.  
  197. if ( !isset( $post_data[ 'ID' ] ) || empty( $post_data[ 'ID' ] ) ) 
  198. $post_data[ 'ID' ] = wp_insert_post( $post_data, true ); 
  199. elseif ( 2 < count( $post_data ) || !isset( $post_data[ 'post_type' ] ) ) 
  200. $post_data[ 'ID' ] = wp_update_post( $post_data, true ); 
  201.  
  202. if ( is_wp_error( $post_data[ 'ID' ] ) ) { 
  203. if ( !$conflicted ) 
  204. pods_no_conflict_off( 'post' ); 
  205.  
  206. /** 
  207. * @var $post_error WP_Error 
  208. */ 
  209. $post_error = $post_data[ 'ID' ]; 
  210.  
  211. return pods_error( $post_error->get_error_message(), $this ); 
  212.  
  213. $this->save_post_meta( $post_data[ 'ID' ], $post_meta, $strict, $fields ); 
  214.  
  215. if ( !$conflicted ) 
  216. pods_no_conflict_off( 'post' ); 
  217.  
  218. return $post_data[ 'ID' ]; 
  219.  
  220. /** 
  221. * Save a post's meta 
  222. * @param int $id Post ID 
  223. * @param array $post_meta All meta to be saved (set value to null to delete) 
  224. * @param bool $strict Whether to delete previously saved meta not in $post_meta 
  225. * @param array $fields (optional) The array of fields and their options, for further processing with 
  226. * @return int Id of the post with the meta 
  227. * @since 2.0 
  228. */ 
  229. public function save_post_meta ( $id, $post_meta = null, $strict = false, $fields = array() ) { 
  230. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  231.  
  232. $conflicted = pods_no_conflict_check( 'post' ); 
  233.  
  234. if ( !$conflicted ) 
  235. pods_no_conflict_on( 'post' ); 
  236.  
  237. if ( !is_array( $post_meta ) ) 
  238. $post_meta = array(); 
  239.  
  240. $id = (int) $id; 
  241.  
  242. $meta = get_post_meta( $id ); 
  243.  
  244. foreach ( $meta as $k => $value ) { 
  245. if ( is_array( $value ) && 1 == count( $value ) ) 
  246. $meta[ $k ] = current( $value ); 
  247.  
  248. foreach ( $post_meta as $meta_key => $meta_value ) { 
  249. if ( null === $meta_value || ( $strict && '' === $post_meta[ $meta_key ] ) ) { 
  250. $old_meta_value = ''; 
  251.  
  252. if ( isset( $meta[ $meta_key ] ) ) 
  253. $old_meta_value = $meta[ $meta_key ]; 
  254.  
  255. delete_post_meta( $id, $meta_key, $old_meta_value ); 
  256. else { 
  257. $simple = false; 
  258.  
  259. if ( isset( $fields[ $meta_key ] ) ) { 
  260. $field_data = $fields[ $meta_key ]; 
  261.  
  262. $simple = ( 'pick' == $field_data[ 'type' ] && in_array( pods_var( 'pick_object', $field_data ), $simple_tableless_objects ) ); 
  263.  
  264. if ( $simple ) { 
  265. delete_post_meta( $id, $meta_key ); 
  266.  
  267. update_post_meta( $id, '_pods_' . $meta_key, $meta_value ); 
  268.  
  269. if ( ! is_array( $meta_value ) ) { 
  270. $meta_value = array( $meta_value ); 
  271.  
  272. foreach ( $meta_value as $value ) { 
  273. add_post_meta( $id, $meta_key, $value ); 
  274. else { 
  275. update_post_meta( $id, $meta_key, $meta_value ); 
  276.  
  277. if ( $strict ) { 
  278. foreach ( $meta as $meta_key => $meta_value ) { 
  279. if ( !isset( $post_meta[ $meta_key ] ) ) 
  280. delete_post_meta( $id, $meta_key, $meta_value ); 
  281.  
  282. if ( !$conflicted ) 
  283. pods_no_conflict_off( 'post' ); 
  284.  
  285. return $id; 
  286.  
  287. /** 
  288. * Save a user and it's meta 
  289. * @param array $user_data All user data to be saved (using wp_insert_user / wp_update_user) 
  290. * @param array $user_meta (optional) All meta to be saved (set value to null to delete) 
  291. * @param bool $strict (optional) Whether to delete previously saved meta not in $user_meta 
  292. * @param bool $sanitized (optional) Will unsanitize the data, should be passed if the data is sanitized before sending. 
  293. * @param array $fields (optional) The array of fields and their options, for further processing with 
  294. * @return int Returns user id on success 
  295. * @since 2.0 
  296. */ 
  297. public function save_user ( $user_data, $user_meta = null, $strict = false, $sanitized = false, $fields = array() ) { 
  298. if ( !is_array( $user_data ) || empty( $user_data ) ) 
  299. return pods_error( __( 'User data is required but is either invalid or empty', 'pods' ), $this ); 
  300.  
  301. $conflicted = pods_no_conflict_check( 'user' ); 
  302.  
  303. if ( !$conflicted ) 
  304. pods_no_conflict_on( 'user' ); 
  305.  
  306. if ( !is_array( $user_meta ) ) 
  307. $user_meta = array(); 
  308.  
  309. if ( $sanitized ) { 
  310. $user_data = pods_unsanitize( $user_data ); 
  311. $user_meta = pods_unsanitize( $user_meta ); 
  312.  
  313. // Set role 
  314. if ( isset( $user_meta[ 'role' ] ) ) { 
  315. $user_data[ 'role' ] = $user_meta[ 'role' ]; 
  316.  
  317. unset( $user_meta[ 'role' ] ); 
  318.  
  319. if ( !isset( $user_data[ 'ID' ] ) || empty( $user_data[ 'ID' ] ) ) 
  320. $user_data[ 'ID' ] = wp_insert_user( $user_data ); 
  321. elseif ( 1 < count( $user_data ) ) 
  322. wp_update_user( $user_data ); 
  323.  
  324. if ( is_wp_error( $user_data[ 'ID' ] ) ) { 
  325. if ( !$conflicted ) 
  326. pods_no_conflict_off( 'user' ); 
  327.  
  328. /** 
  329. * @var $user_error WP_Error 
  330. */ 
  331. $user_error = $user_data[ 'ID' ]; 
  332.  
  333. return pods_error( $user_error->get_error_message(), $this ); 
  334.  
  335. $this->save_user_meta( $user_data[ 'ID' ], $user_meta, $strict, $fields ); 
  336.  
  337. if ( !$conflicted ) 
  338. pods_no_conflict_off( 'user' ); 
  339.  
  340. return $user_data[ 'ID' ]; 
  341.  
  342. /** 
  343. * Save a user meta 
  344. * @param int $id User ID 
  345. * @param array $user_meta (optional) All meta to be saved (set value to null to delete) 
  346. * @param bool $strict (optional) Whether to delete previously saved meta not in $user_meta 
  347. * @param array $fields (optional) The array of fields and their options, for further processing with 
  348. * @return int User ID 
  349. * @since 2.0 
  350. */ 
  351. public function save_user_meta ( $id, $user_meta = null, $strict = false, $fields = array() ) { 
  352. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  353.  
  354. $conflicted = pods_no_conflict_check( 'user' ); 
  355.  
  356. if ( !$conflicted ) 
  357. pods_no_conflict_on( 'user' ); 
  358.  
  359. if ( !is_array( $user_meta ) ) 
  360. $user_meta = array(); 
  361.  
  362. $id = (int) $id; 
  363.  
  364. $meta = get_user_meta( $id ); 
  365.  
  366. foreach ( $user_meta as $meta_key => $meta_value ) { 
  367. if ( null === $meta_value ) { 
  368. $old_meta_value = ''; 
  369.  
  370. if ( isset( $meta[ $meta_key ] ) ) 
  371. $old_meta_value = $meta[ $meta_key ]; 
  372.  
  373. delete_user_meta( $id, $meta_key, $old_meta_value ); 
  374. else { 
  375. $simple = false; 
  376.  
  377. if ( isset( $fields[ $meta_key ] ) ) { 
  378. $field_data = $fields[ $meta_key ]; 
  379.  
  380. $simple = ( 'pick' == $field_data[ 'type' ] && in_array( pods_var( 'pick_object', $field_data ), $simple_tableless_objects ) ); 
  381.  
  382. if ( $simple ) { 
  383. delete_user_meta( $id, $meta_key ); 
  384.  
  385. if ( ! is_array( $meta_value ) ) { 
  386. $meta_value = array( $meta_value ); 
  387.  
  388. foreach ( $meta_value as $value ) { 
  389. add_user_meta( $id, $meta_key, $value ); 
  390. else { 
  391. update_user_meta( $id, $meta_key, $meta_value ); 
  392.  
  393. if ( $strict ) { 
  394. foreach ( $meta as $meta_key => $meta_value ) { 
  395. if ( !isset( $user_meta[ $meta_key ] ) ) 
  396. delete_user_meta( $id, $meta_key, $user_meta[ $meta_key ] ); 
  397.  
  398. if ( !$conflicted ) 
  399. pods_no_conflict_off( 'user' ); 
  400.  
  401. return $id; 
  402.  
  403. /** 
  404. * Save a comment and it's meta 
  405. * @param array $comment_data All comment data to be saved (using wp_insert_comment / wp_update_comment) 
  406. * @param array $comment_meta (optional) All meta to be saved (set value to null to delete) 
  407. * @param bool $strict (optional) Whether to delete previously saved meta not in $comment_meta 
  408. * @param bool $sanitized (optional) Will unsanitize the data, should be passed if the data is sanitized before sending. 
  409. * @param array $fields (optional) The array of fields and their options, for further processing with 
  410. * @return int Comment ID 
  411. * @since 2.0 
  412. */ 
  413. public function save_comment ( $comment_data, $comment_meta = null, $strict = false, $sanitized = false, $fields = array() ) { 
  414. if ( !is_array( $comment_data ) || empty( $comment_data ) ) 
  415. return pods_error( __( 'Comment data is required but is either invalid or empty', 'pods' ), $this ); 
  416.  
  417. $conflicted = pods_no_conflict_check( 'comment' ); 
  418.  
  419. if ( !$conflicted ) 
  420. pods_no_conflict_on( 'comment' ); 
  421.  
  422. if ( !is_array( $comment_meta ) ) 
  423. $comment_meta = array(); 
  424.  
  425. if ( $sanitized ) { 
  426. $comment_data = pods_unsanitize( $comment_data ); 
  427. $comment_meta = pods_unsanitize( $comment_meta ); 
  428.  
  429. if ( !isset( $comment_data[ 'comment_ID' ] ) || empty( $comment_data[ 'comment_ID' ] ) ) 
  430. $comment_data[ 'comment_ID' ] = wp_insert_comment( pods_slash( $comment_data ) ); // Expects slashed 
  431. elseif ( 1 < count( $comment_data ) ) 
  432. wp_update_comment( $comment_data ); 
  433.  
  434. if ( is_wp_error( $comment_data[ 'comment_ID' ] ) ) { 
  435. if ( !$conflicted ) 
  436. pods_no_conflict_off( 'comment' ); 
  437.  
  438. /** 
  439. * @var $comment_error WP_Error 
  440. */ 
  441. $comment_error = $comment_data[ 'comment_ID' ]; 
  442.  
  443. return pods_error( $comment_error->get_error_message(), $this ); 
  444.  
  445. $this->save_comment_meta( $comment_data[ 'comment_ID' ], $comment_meta, $strict, $fields ); 
  446.  
  447. if ( !$conflicted ) 
  448. pods_no_conflict_off( 'comment' ); 
  449.  
  450. return $comment_data[ 'comment_ID' ]; 
  451.  
  452. /** 
  453. * Save a comment meta 
  454. * @param int $id Comment ID 
  455. * @param array $comment_meta (optional) All meta to be saved (set value to null to delete) 
  456. * @param bool $strict (optional) Whether to delete previously saved meta not in $comment_meta 
  457. * @param array $fields (optional) The array of fields and their options, for further processing with 
  458. * @return int Comment ID 
  459. * @since 2.0 
  460. */ 
  461. public function save_comment_meta ( $id, $comment_meta = null, $strict = false, $fields = array() ) { 
  462. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  463.  
  464. $conflicted = pods_no_conflict_check( 'comment' ); 
  465.  
  466. if ( !$conflicted ) 
  467. pods_no_conflict_on( 'comment' ); 
  468.  
  469. if ( !is_array( $comment_meta ) ) 
  470. $comment_meta = array(); 
  471.  
  472. $id = (int) $id; 
  473.  
  474. $meta = get_comment_meta( $id ); 
  475.  
  476. foreach ( $comment_meta as $meta_key => $meta_value ) { 
  477. if ( null === $meta_value ) { 
  478. $old_meta_value = ''; 
  479.  
  480. if ( isset( $meta[ $meta_key ] ) ) 
  481. $old_meta_value = $meta[ $meta_key ]; 
  482.  
  483. delete_comment_meta( $id, $meta_key, $old_meta_value ); 
  484. else { 
  485. $simple = false; 
  486.  
  487. if ( isset( $fields[ $meta_key ] ) ) { 
  488. $field_data = $fields[ $meta_key ]; 
  489.  
  490. $simple = ( 'pick' == $field_data[ 'type' ] && in_array( pods_var( 'pick_object', $field_data ), $simple_tableless_objects ) ); 
  491.  
  492. if ( $simple ) { 
  493. delete_comment_meta( $id, $meta_key ); 
  494.  
  495. if ( ! is_array( $meta_value ) ) { 
  496. $meta_value = array( $meta_value ); 
  497.  
  498. foreach ( $meta_value as $value ) { 
  499. add_comment_meta( $id, $meta_key, $value ); 
  500. else { 
  501. update_comment_meta( $id, $meta_key, $meta_value ); 
  502.  
  503. if ( $strict ) { 
  504. foreach ( $meta as $meta_key => $meta_value ) { 
  505. if ( !isset( $comment_meta[ $meta_key ] ) ) 
  506. delete_comment_meta( (int) $id, $meta_key, $comment_meta[ $meta_key ] ); 
  507.  
  508. if ( !$conflicted ) 
  509. pods_no_conflict_off( 'comment' ); 
  510.  
  511. return $id; 
  512.  
  513. /** 
  514. * Save a taxonomy's term 
  515. * @param array $term_data All term data to be saved (using wp_insert_term / wp_update_term) 
  516. * @param array $term_meta All meta to be saved (set value to null to delete) 
  517. * @param bool $strict (optional) Whether to delete previously saved meta not in $post_meta 
  518. * @param bool $sanitized (optional) Will unsanitize the data, should be passed if the data is sanitized before sending. 
  519. * @param array $fields (optional) The array of fields and their options, for further processing with 
  520. * @return int Term ID 
  521. * @since 2.0 
  522. */ 
  523. public function save_term ( $term_data, $term_meta, $strict = false, $sanitized = false, $fields = array() ) { 
  524. if ( empty( $term_data['taxonomy'] ) ) { 
  525. return 0; 
  526.  
  527. $conflicted = pods_no_conflict_check( 'taxonomy' ); 
  528.  
  529. if ( !is_array( $term_data ) || empty( $term_data ) ) 
  530. $term_data = array( 'name' => '' ); 
  531.  
  532. if ( !$conflicted ) 
  533. pods_no_conflict_on( 'taxonomy' ); 
  534.  
  535. if ( !is_array( $term_meta ) ) 
  536. $term_meta = array(); 
  537.  
  538. if ( $sanitized ) { 
  539. $term_data = pods_unsanitize( $term_data ); 
  540. $term_meta = pods_unsanitize( $term_meta ); 
  541.  
  542. $taxonomy = $term_data['taxonomy']; 
  543.  
  544. unset( $term_data['taxonomy'] ); 
  545.  
  546. if ( empty( $term_data['term_id'] ) ) { 
  547. $term_name = $term_data['name']; 
  548.  
  549. unset( $term_data['name'] ); 
  550.  
  551. $term_data['term_id'] = wp_insert_term( $term_name, $taxonomy, $term_data ); 
  552. } elseif ( 2 < count( $term_data ) ) { 
  553. $term_data['term_id'] = wp_update_term( $term_data['term_id'], $taxonomy, $term_data ); 
  554.  
  555. if ( is_wp_error( $term_data['term_id'] ) ) { 
  556. if ( !$conflicted ) 
  557. pods_no_conflict_off( 'taxonomy' ); 
  558.  
  559. /** 
  560. * @var $term_error WP_Error 
  561. */ 
  562. $term_error = $term_data[ 'term_id' ]; 
  563.  
  564. return pods_error( $term_error->get_error_message(), $this ); 
  565. elseif ( is_array( $term_data['term_id'] ) ) 
  566. $term_data['term_id'] = $term_data['term_id'][ 'term_id' ]; 
  567.  
  568. $this->save_term_meta( $term_data['term_id'], $term_meta, $strict, $fields ); 
  569.  
  570. if ( !$conflicted ) 
  571. pods_no_conflict_off( 'taxonomy' ); 
  572.  
  573. return $term_data['term_id']; 
  574.  
  575. /** 
  576. * Save a term's meta 
  577. * @param int $id Term ID 
  578. * @param array $term_meta All meta to be saved (set value to null to delete) 
  579. * @param bool $strict Whether to delete previously saved meta not in $term_meta 
  580. * @param array $fields (optional) The array of fields and their options, for further processing with 
  581. * @return int Id of the term with the meta 
  582. * @since 2.0 
  583. */ 
  584. public function save_term_meta ( $id, $term_meta = null, $strict = false, $fields = array() ) { 
  585. if ( ! function_exists( 'get_term_meta' ) ) { 
  586. return $id; 
  587.  
  588. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  589.  
  590. $conflicted = pods_no_conflict_check( 'taxonomy' ); 
  591.  
  592. if ( !$conflicted ) 
  593. pods_no_conflict_on( 'taxonomy' ); 
  594.  
  595. if ( !is_array( $term_meta ) ) 
  596. $term_meta = array(); 
  597.  
  598. $id = (int) $id; 
  599.  
  600. $meta = get_term_meta( $id ); 
  601.  
  602. foreach ( $meta as $k => $value ) { 
  603. if ( is_array( $value ) && 1 == count( $value ) ) 
  604. $meta[ $k ] = current( $value ); 
  605.  
  606. foreach ( $term_meta as $meta_key => $meta_value ) { 
  607. if ( null === $meta_value || ( $strict && '' === $term_meta[ $meta_key ] ) ) { 
  608. $old_meta_value = ''; 
  609.  
  610. if ( isset( $meta[ $meta_key ] ) ) 
  611. $old_meta_value = $meta[ $meta_key ]; 
  612.  
  613. delete_term_meta( $id, $meta_key, $old_meta_value ); 
  614. else { 
  615. $simple = false; 
  616.  
  617. if ( isset( $fields[ $meta_key ] ) ) { 
  618. $field_data = $fields[ $meta_key ]; 
  619.  
  620. $simple = ( 'pick' == $field_data[ 'type' ] && in_array( pods_var( 'pick_object', $field_data ), $simple_tableless_objects ) ); 
  621.  
  622. if ( $simple ) { 
  623. delete_term_meta( $id, $meta_key ); 
  624.  
  625. update_term_meta( $id, '_pods_' . $meta_key, $meta_value ); 
  626.  
  627. if ( ! is_array( $meta_value ) ) { 
  628. $meta_value = array( $meta_value ); 
  629.  
  630. foreach ( $meta_value as $value ) { 
  631. add_term_meta( $id, $meta_key, $value ); 
  632. else { 
  633. update_term_meta( $id, $meta_key, $meta_value ); 
  634.  
  635. if ( $strict ) { 
  636. foreach ( $meta as $meta_key => $meta_value ) { 
  637. if ( !isset( $term_meta[ $meta_key ] ) ) 
  638. delete_term_meta( $id, $meta_key, $meta_value ); 
  639.  
  640. if ( !$conflicted ) 
  641. pods_no_conflict_off( 'taxonomy' ); 
  642.  
  643. return $id; 
  644.  
  645. /** 
  646. * Save a set of options 
  647. * @param string $setting Setting group name 
  648. * @param array $option_data All option data to be saved 
  649. * @param bool $sanitized (optional) Will unsanitize the data, should be passed if the data is sanitized before sending. 
  650. * @return bool 
  651. * @since 2.3 
  652. */ 
  653. public function save_setting ( $setting, $option_data, $sanitized = false ) { 
  654. if ( !is_array( $option_data ) || empty( $option_data ) ) 
  655. return pods_error( __( 'Setting data is required but is either invalid or empty', 'pods' ), $this ); 
  656.  
  657. $conflicted = pods_no_conflict_check( 'settings' ); 
  658.  
  659. if ( !$conflicted ) 
  660. pods_no_conflict_on( 'settings' ); 
  661.  
  662. if ( $sanitized ) 
  663. $option_data = pods_unsanitize( $option_data ); 
  664.  
  665. foreach ( $option_data as $option => $value ) { 
  666. if ( !empty( $setting ) ) 
  667. $option = $setting . '_' . $option; 
  668.  
  669. update_option( $option, $value ); 
  670.  
  671. if ( !$conflicted ) 
  672. pods_no_conflict_off( 'settings' ); 
  673.  
  674. return true; 
  675.  
  676. /** 
  677. * Rename a WP object's type 
  678. * @param string $object_type Object type: post|taxonomy|comment|setting 
  679. * @param string $old_name The old name 
  680. * @param string $new_name The new name 
  681. * @return bool 
  682. * @since 2.0 
  683. */ 
  684. public function rename_wp_object_type ( $object_type, $old_name, $new_name ) { 
  685. /** 
  686. * @var $wpdb wpdb 
  687. */ 
  688. global $wpdb; 
  689.  
  690. if ( 'post_type' == $object_type ) 
  691. $object_type = 'post'; 
  692.  
  693. if ( 'post' == $object_type ) { 
  694. pods_query( "UPDATE `{$wpdb->posts}` SET `post_type` = %s WHERE `post_type` = %s", array( 
  695. $new_name,  
  696. $old_name 
  697. ) ); 
  698. elseif ( 'taxonomy' == $object_type ) { 
  699. pods_query( "UPDATE `{$wpdb->term_taxonomy}` SET `taxonomy` = %s WHERE `taxonomy` = %s", array( 
  700. $new_name,  
  701. $old_name 
  702. ) ); 
  703. elseif ( 'comment' == $object_type ) { 
  704. pods_query( "UPDATE `{$wpdb->comments}` SET `comment_type` = %s WHERE `comment_type` = %s", array( 
  705. $new_name,  
  706. $old_name 
  707. ) ); 
  708. elseif ( 'settings' == $object_type ) { 
  709. pods_query( "UPDATE `{$wpdb->options}` SET `option_name` = REPLACE( `option_name`, %s, %s ) WHERE `option_name` LIKE '" . pods_sanitize_like( $old_name ) . "_%'", array( 
  710. $new_name . '_',  
  711. $old_name . '_' 
  712. ) ); 
  713.  
  714. return true; 
  715.  
  716. /** 
  717. * Get a list of core WP object fields for a specific object 
  718. * @param string $object The pod type to look for, possible values: post_type, user, comment, taxonomy 
  719. * @param array $pod Array of Pod data 
  720. * @param boolean $refresh Whether to force refresh the information 
  721. * @return array Array of fields 
  722. * @since 2.0 
  723. */ 
  724. public function get_wp_object_fields ( $object = 'post_type', $pod = null, $refresh = false ) { 
  725. $pod_name = pods_var_raw( 'name', $pod, $object, null, true ); 
  726.  
  727. if ( 'media' == $pod_name ) { 
  728. $object = 'post_type'; 
  729. $pod_name = 'attachment'; 
  730.  
  731. $fields = false; 
  732.  
  733. if ( pods_api_cache() ) 
  734. $fields = pods_transient_get( trim( 'pods_api_object_fields_' . $object . $pod_name . '_', '_' ) ); 
  735.  
  736. if ( false !== $fields && !$refresh ) 
  737. return $this->do_hook( 'get_wp_object_fields', $fields, $object, $pod ); 
  738.  
  739. $fields = array(); 
  740.  
  741. if ( 'post_type' == $object ) { 
  742. $fields = array( 
  743. 'ID' => array( 
  744. 'name' => 'ID',  
  745. 'label' => 'ID',  
  746. 'type' => 'number',  
  747. 'alias' => array( 'id' ),  
  748. 'options' => array( 
  749. 'number_format' => '9999.99' 
  750. ),  
  751. 'post_title' => array( 
  752. 'name' => 'post_title',  
  753. 'label' => 'Title',  
  754. 'type' => 'text',  
  755. 'alias' => array( 'title', 'name' ),  
  756. 'options' => array( 
  757. 'display_filter' => 'the_title',  
  758. 'display_filter_args' => array( 'post_ID' ) 
  759. ),  
  760. 'post_content' => array( 
  761. 'name' => 'post_content',  
  762. 'label' => 'Content',  
  763. 'type' => 'wysiwyg',  
  764. 'alias' => array( 'content' ),  
  765. 'options' => array( 
  766. 'wysiwyg_allowed_html_tags' => '',  
  767. 'display_filter' => 'the_content',  
  768. 'pre_save' => 0 
  769. ),  
  770. 'post_excerpt' => array( 
  771. 'name' => 'post_excerpt',  
  772. 'label' => 'Excerpt',  
  773. 'type' => 'paragraph',  
  774. 'alias' => array( 'excerpt' ),  
  775. 'options' => array( 
  776. 'paragraph_allow_html' => 1,  
  777. 'paragraph_allowed_html_tags' => '',  
  778. 'display_filter' => 'the_excerpt',  
  779. 'pre_save' => 0 
  780. ),  
  781. 'post_author' => array( 
  782. 'name' => 'post_author',  
  783. 'label' => 'Author',  
  784. 'type' => 'pick',  
  785. 'alias' => array( 'author' ),  
  786. 'pick_object' => 'user',  
  787. 'options' => array( 
  788. 'pick_format_type' => 'single',  
  789. 'pick_format_single' => 'autocomplete',  
  790. 'default_value' => '{@user.ID}' 
  791. ),  
  792. 'post_date' => array( 
  793. 'name' => 'post_date',  
  794. 'label' => 'Publish Date',  
  795. 'type' => 'datetime',  
  796. 'alias' => array( 'created', 'date' ) 
  797. ),  
  798. 'post_date_gmt' => array( 
  799. 'name' => 'post_date_gmt',  
  800. 'label' => 'Publish Date (GMT)',  
  801. 'type' => 'datetime',  
  802. 'alias' => array(),  
  803. 'hidden' => true 
  804. ),  
  805. 'post_status' => array( 
  806. 'name' => 'post_status',  
  807. 'label' => 'Status',  
  808. 'type' => 'pick',  
  809. 'pick_object' => 'post-status',  
  810. 'default' => $this->do_hook( 'default_status_' . $pod_name, pods_var( 'default_status', pods_var_raw( 'options', $pod ), 'draft', null, true ), $pod ),  
  811. 'alias' => array( 'status' ) 
  812. ),  
  813. 'comment_status' => array( 
  814. 'name' => 'comment_status',  
  815. 'label' => 'Comment Status',  
  816. 'type' => 'text',  
  817. 'default' => get_option( 'default_comment_status', 'open' ),  
  818. 'alias' => array(),  
  819. 'data' => array( 
  820. 'open' => __( 'Open', 'pods' ),  
  821. 'closed' => __( 'Closed', 'pods' ) 
  822. ),  
  823. 'ping_status' => array( 
  824. 'name' => 'ping_status',  
  825. 'label' => 'Ping Status',  
  826. 'default' => get_option( 'default_ping_status', 'open' ),  
  827. 'type' => 'text',  
  828. 'alias' => array(),  
  829. 'data' => array( 
  830. 'open' => __( 'Open', 'pods' ),  
  831. 'closed' => __( 'Closed', 'pods' ) 
  832. ),  
  833. 'post_password' => array( 
  834. 'name' => 'post_password',  
  835. 'label' => 'Password',  
  836. 'type' => 'text',  
  837. 'alias' => array() 
  838. ),  
  839. 'post_name' => array( 
  840. 'name' => 'post_name',  
  841. 'label' => 'Permalink',  
  842. 'type' => 'slug',  
  843. 'alias' => array( 'slug', 'permalink' ) 
  844. ),  
  845. 'to_ping' => array( 
  846. 'name' => 'to_ping',  
  847. 'label' => 'To Ping',  
  848. 'type' => 'text',  
  849. 'alias' => array(),  
  850. 'hidden' => true 
  851. ),  
  852. 'pinged' => array( 
  853. 'name' => 'pinged',  
  854. 'label' => 'Pinged',  
  855. 'type' => 'text',  
  856. 'alias' => array(),  
  857. 'hidden' => true 
  858. ),  
  859. 'post_modified' => array( 
  860. 'name' => 'post_modified',  
  861. 'label' => 'Last Modified Date',  
  862. 'type' => 'datetime',  
  863. 'alias' => array( 'modified' ),  
  864. 'hidden' => true 
  865. ),  
  866. 'post_modified_gmt' => array( 
  867. 'name' => 'post_modified_gmt',  
  868. 'label' => 'Last Modified Date (GMT)',  
  869. 'type' => 'datetime',  
  870. 'alias' => array(),  
  871. 'hidden' => true 
  872. ),  
  873. 'post_content_filtered' => array( 
  874. 'name' => 'post_content_filtered',  
  875. 'label' => 'Content (filtered)',  
  876. 'type' => 'paragraph',  
  877. 'alias' => array(),  
  878. 'hidden' => true,  
  879. 'options' => array( 
  880. 'paragraph_allow_html' => 1,  
  881. 'paragraph_oembed' => 1,  
  882. 'paragraph_wptexturize' => 1,  
  883. 'paragraph_convert_chars' => 1,  
  884. 'paragraph_wpautop' => 1,  
  885. 'paragraph_allow_shortcode' => 1,  
  886. 'paragraph_allowed_html_tags' => '' 
  887. ),  
  888. 'post_parent' => array( 
  889. 'name' => 'post_parent',  
  890. 'label' => 'Parent',  
  891. 'type' => 'pick',  
  892. 'pick_object' => 'post_type',  
  893. 'pick_val' => '__current__',  
  894. 'alias' => array( 'parent' ),  
  895. 'data' => array(),  
  896. 'hidden' => true 
  897. ),  
  898. 'guid' => array( 
  899. 'name' => 'guid',  
  900. 'label' => 'GUID',  
  901. 'type' => 'text',  
  902. 'alias' => array(),  
  903. 'hidden' => true 
  904. ),  
  905. 'menu_order' => array( 
  906. 'name' => 'menu_order',  
  907. 'label' => 'Menu Order',  
  908. 'type' => 'number',  
  909. 'alias' => array(),  
  910. 'options' => array( 
  911. 'number_format' => '9999.99' 
  912. ),  
  913. 'post_type' => array( 
  914. 'name' => 'post_type',  
  915. 'label' => 'Type',  
  916. 'type' => 'text',  
  917. 'alias' => array( 'type' ),  
  918. 'hidden' => true 
  919. ),  
  920. 'post_mime_type' => array( 
  921. 'name' => 'post_mime_type',  
  922. 'label' => 'Mime Type',  
  923. 'type' => 'text',  
  924. 'alias' => array(),  
  925. 'hidden' => true 
  926. ),  
  927. 'comment_count' => array( 
  928. 'name' => 'comment_count',  
  929. 'label' => 'Comment Count',  
  930. 'type' => 'number',  
  931. 'alias' => array(),  
  932. 'hidden' => true 
  933. ); 
  934.  
  935. if ( !empty( $pod ) ) { 
  936. $taxonomies = get_object_taxonomies( $pod_name, 'objects' ); 
  937.  
  938. foreach ( $taxonomies as $taxonomy ) { 
  939. $fields[ $taxonomy->name ] = array( 
  940. 'name' => $taxonomy->name,  
  941. 'label' => $taxonomy->labels->name,  
  942. 'type' => 'taxonomy',  
  943. 'pick_object' => 'taxonomy',  
  944. 'pick_val' => $taxonomy->name,  
  945. 'alias' => array(),  
  946. 'hidden' => true,  
  947. 'options' => array( 
  948. 'taxonomy_format_type' => 'multi' 
  949. ); 
  950. elseif ( 'user' == $object ) { 
  951. $fields = array( 
  952. 'ID' => array( 
  953. 'name' => 'ID',  
  954. 'label' => 'ID',  
  955. 'type' => 'number',  
  956. 'alias' => array( 'id' ),  
  957. 'options' => array( 
  958. 'number_format' => '9999.99' 
  959. ),  
  960. 'user_login' => array( 
  961. 'name' => 'user_login',  
  962. 'label' => 'Title',  
  963. 'type' => 'text',  
  964. 'alias' => array( 'login' ),  
  965. 'options' => array( 
  966. 'required' => 1 
  967. ),  
  968. 'user_nicename' => array( 
  969. 'name' => 'user_nicename',  
  970. 'label' => 'Permalink',  
  971. 'type' => 'slug',  
  972. 'alias' => array( 'nicename', 'slug', 'permalink' ) 
  973. ),  
  974. 'display_name' => array( 
  975. 'name' => 'display_name',  
  976. 'label' => 'Display Name',  
  977. 'type' => 'text',  
  978. 'alias' => array( 'title', 'name' ) 
  979. ),  
  980. 'user_pass' => array( 
  981. 'name' => 'user_pass',  
  982. 'label' => 'Password',  
  983. 'type' => 'text',  
  984. 'alias' => array( 'password', 'pass' ),  
  985. 'options' => array( 
  986. 'required' => 1,  
  987. 'text_format_type' => 'password' 
  988. ),  
  989. 'user_email' => array( 
  990. 'name' => 'user_email',  
  991. 'label' => 'E-mail',  
  992. 'type' => 'text',  
  993. 'alias' => array( 'email' ),  
  994. 'options' => array( 
  995. 'required' => 1,  
  996. 'text_format_type' => 'email' 
  997. ),  
  998. 'user_url' => array( 
  999. 'name' => 'user_url',  
  1000. 'label' => 'URL',  
  1001. 'type' => 'text',  
  1002. 'alias' => array( 'url', 'website' ),  
  1003. 'options' => array( 
  1004. 'required' => 0,  
  1005. 'text_format_type' => 'website',  
  1006. 'text_format_website' => 'normal' 
  1007. ),  
  1008. 'user_registered' => array( 
  1009. 'name' => 'user_registered',  
  1010. 'label' => 'Registration Date',  
  1011. 'type' => 'date',  
  1012. 'alias' => array( 'created', 'date', 'registered' ),  
  1013. 'options' => array( 
  1014. 'date_format_type' => 'datetime' 
  1015. ); 
  1016. elseif ( 'comment' == $object ) { 
  1017. $fields = array( 
  1018. 'comment_ID' => array( 
  1019. 'name' => 'comment_ID',  
  1020. 'label' => 'ID',  
  1021. 'type' => 'number',  
  1022. 'alias' => array( 'id', 'ID', 'comment_id' ),  
  1023. 'options' => array( 
  1024. 'number_format' => '9999.99' 
  1025. ),  
  1026. 'comment_content' => array( 
  1027. 'name' => 'comment_content',  
  1028. 'label' => 'Content',  
  1029. 'type' => 'wysiwyg',  
  1030. 'alias' => array( 'content' ) 
  1031. ),  
  1032. 'comment_approved' => array( 
  1033. 'name' => 'comment_approved',  
  1034. 'label' => 'Approved',  
  1035. 'type' => 'number',  
  1036. 'alias' => array( 'approved' ),  
  1037. 'options' => array( 
  1038. 'number_format' => '9999.99' 
  1039. ),  
  1040. 'comment_post_ID' => array( 
  1041. 'name' => 'comment_post_ID',  
  1042. 'label' => 'Post',  
  1043. 'type' => 'pick',  
  1044. 'alias' => array( 'post', 'post_id' ),  
  1045. 'data' => array() 
  1046. ),  
  1047. 'user_id' => array( 
  1048. 'name' => 'user_id',  
  1049. 'label' => 'Author',  
  1050. 'type' => 'pick',  
  1051. 'alias' => array( 'author' ),  
  1052. 'pick_object' => 'user',  
  1053. 'data' => array() 
  1054. ),  
  1055. 'comment_date' => array( 
  1056. 'name' => 'comment_date',  
  1057. 'label' => 'Date',  
  1058. 'type' => 'date',  
  1059. 'alias' => array( 'created', 'date' ),  
  1060. 'options' => array( 
  1061. 'date_format_type' => 'datetime' 
  1062. ),  
  1063. 'comment_author' => array( 
  1064. 'name' => 'comment_author',  
  1065. 'label' => 'Author',  
  1066. 'type' => 'text',  
  1067. 'alias' => array( 'author' ) 
  1068. ),  
  1069. 'comment_author_email' => array( 
  1070. 'name' => 'comment_author_email',  
  1071. 'label' => 'Author E-mail',  
  1072. 'type' => 'email',  
  1073. 'alias' => array( 'author_email' ) 
  1074. ),  
  1075. 'comment_author_url' => array( 
  1076. 'name' => 'comment_author_url',  
  1077. 'label' => 'Author URL',  
  1078. 'type' => 'text',  
  1079. 'alias' => array( 'author_url' ) 
  1080. ),  
  1081. 'comment_author_IP' => array( 
  1082. 'name' => 'comment_author_IP',  
  1083. 'label' => 'Author IP',  
  1084. 'type' => 'text',  
  1085. 'alias' => array( 'author_IP' ) 
  1086. ),  
  1087. 'comment_type' => array( 
  1088. 'name' => 'comment_type',  
  1089. 'label' => 'Type',  
  1090. 'type' => 'text',  
  1091. 'alias' => array( 'type' ),  
  1092. 'hidden' => true 
  1093. ),  
  1094. 'comment_parent' => array( 
  1095. 'name' => 'comment_parent',  
  1096. 'label' => 'Parent',  
  1097. 'type' => 'pick',  
  1098. 'pick_object' => 'comment',  
  1099. 'pick_val' => '__current__',  
  1100. 'alias' => array( 'parent' ),  
  1101. 'data' => array(),  
  1102. 'hidden' => true 
  1103. ); 
  1104. elseif ( 'taxonomy' == $object ) { 
  1105. $fields = array( 
  1106. 'term_id' => array( 
  1107. 'name' => 'term_id',  
  1108. 'label' => 'ID',  
  1109. 'type' => 'number',  
  1110. 'alias' => array( 'id', 'ID' ),  
  1111. 'options' => array( 
  1112. 'number_format' => '9999.99' 
  1113. ),  
  1114. 'name' => array( 
  1115. 'name' => 'name',  
  1116. 'label' => 'Title',  
  1117. 'type' => 'text',  
  1118. 'alias' => array( 'title' ) 
  1119. ),  
  1120. 'slug' => array( 
  1121. 'name' => 'slug',  
  1122. 'label' => 'Permalink',  
  1123. 'type' => 'slug',  
  1124. 'alias' => array( 'permalink' ) 
  1125. ),  
  1126. 'description' => array( 
  1127. 'name' => 'description',  
  1128. 'label' => 'Description',  
  1129. 'type' => 'wysiwyg',  
  1130. 'alias' => array( 'content' ) 
  1131. ),  
  1132. 'taxonomy' => array( 
  1133. 'name' => 'taxonomy',  
  1134. 'label' => 'Taxonomy',  
  1135. 'type' => 'pick',  
  1136. 'alias' => array() 
  1137. ),  
  1138. 'parent' => array( 
  1139. 'name' => 'parent',  
  1140. 'label' => 'Parent',  
  1141. 'type' => 'pick',  
  1142. 'pick_object' => 'taxonomy',  
  1143. 'pick_val' => '__current__',  
  1144. 'alias' => array( 'parent' ),  
  1145. 'data' => array(),  
  1146. 'hidden' => true 
  1147. ),  
  1148. 'term_taxonomy_id' => array( 
  1149. 'name' => 'term_taxonomy_id',  
  1150. 'label' => 'Term Taxonomy ID',  
  1151. 'type' => 'number',  
  1152. 'alias' => array(),  
  1153. 'hidden' => true,  
  1154. 'options' => array( 
  1155. 'number_format' => '9999.99' 
  1156. ),  
  1157. 'term_group' => array( 
  1158. 'name' => 'term_group',  
  1159. 'label' => 'Term Group',  
  1160. 'type' => 'number',  
  1161. 'alias' => array( 'group' ),  
  1162. 'hidden' => true,  
  1163. 'options' => array( 
  1164. 'number_format' => '9999.99' 
  1165. ),  
  1166. 'count' => array( 
  1167. 'name' => 'count',  
  1168. 'label' => 'Count',  
  1169. 'type' => 'number',  
  1170. 'alias' => array(),  
  1171. 'hidden' => true,  
  1172. 'options' => array( 
  1173. 'number_format' => '9999.99' 
  1174. ); 
  1175.  
  1176. $fields = $this->do_hook( 'get_wp_object_fields', $fields, $object, $pod ); 
  1177.  
  1178. foreach ( $fields as $field => $options ) { 
  1179. if ( !isset( $options[ 'alias' ] ) ) 
  1180. $options[ 'alias' ] = array(); 
  1181. else 
  1182. $options[ 'alias' ] = (array) $options[ 'alias' ]; 
  1183.  
  1184. if ( !isset( $options[ 'name' ] ) ) 
  1185. $options[ 'name' ] = $field; 
  1186.  
  1187. $fields[ $field ] = $options; 
  1188.  
  1189. $fields = PodsForm::fields_setup( $fields ); 
  1190.  
  1191. if ( did_action( 'init' ) && pods_api_cache() ) 
  1192. pods_transient_set( trim( 'pods_api_object_fields_' . $object . $pod_name . '_', '_' ), $fields ); 
  1193.  
  1194. return $fields; 
  1195.  
  1196. /** 
  1197. * @see PodsAPI::save_pod 
  1198. * Add a Pod via the Wizard 
  1199. * $params['create_extend'] string Create or Extend a Content Type 
  1200. * $params['create_pod_type'] string Pod Type (for Creating) 
  1201. * $params['create_name'] string Pod Name (for Creating) 
  1202. * $params['create_label_plural'] string Plural Label (for Creating) 
  1203. * $params['create_label_singular'] string Singular Label (for Creating) 
  1204. * $params['create_storage'] string Storage Type (for Creating Post Types) 
  1205. * $params['create_storage_taxonomy'] string Storage Type (for Creating Taxonomies) 
  1206. * $params['extend_pod_type'] string Pod Type (for Extending) 
  1207. * $params['extend_post_type'] string Post Type (for Extending Post Types) 
  1208. * $params['extend_taxonomy'] string Taxonomy (for Extending Taxonomies) 
  1209. * $params['extend_storage'] string Storage Type (for Extending Post Types / Users / Comments) 
  1210. * @param array $params An associative array of parameters 
  1211. * @return bool|int Pod ID 
  1212. * @since 2.0 
  1213. */ 
  1214. public function add_pod ( $params ) { 
  1215. $defaults = array( 
  1216. 'create_extend' => 'create',  
  1217. 'create_pod_type' => 'post_type',  
  1218.  
  1219. 'create_name' => '',  
  1220. 'create_label_singular' => '',  
  1221. 'create_label_plural' => '',  
  1222. 'create_storage' => 'meta',  
  1223. 'create_storage_taxonomy' => ( function_exists( 'get_term_meta' ) ? 'meta' : 'none' ),  
  1224.  
  1225. 'create_setting_name' => '',  
  1226. 'create_label_title' => '',  
  1227. 'create_label_menu' => '',  
  1228. 'create_menu_location' => 'settings',  
  1229.  
  1230. 'extend_pod_type' => 'post_type',  
  1231. 'extend_post_type' => 'post',  
  1232. 'extend_taxonomy' => 'category',  
  1233. 'extend_table' => '',  
  1234. 'extend_storage' => 'meta',  
  1235. 'extend_storage_taxonomy' => ( function_exists( 'get_term_meta' ) ? 'meta' : 'table' ),  
  1236. ); 
  1237.  
  1238. $params = (object) array_merge( $defaults, (array) $params ); 
  1239.  
  1240. if ( empty( $params->create_extend ) || !in_array( $params->create_extend, array( 'create', 'extend' ) ) ) 
  1241. return pods_error( __( 'Please choose whether to Create or Extend a Content Type', 'pods' ), $this ); 
  1242.  
  1243. $pod_params = array( 
  1244. 'name' => '',  
  1245. 'label' => '',  
  1246. 'type' => '',  
  1247. 'storage' => 'table',  
  1248. 'object' => '',  
  1249. 'options' => array() 
  1250. ); 
  1251.  
  1252. if ( 'create' == $params->create_extend ) { 
  1253. $label = ucwords( str_replace( '_', ' ', $params->create_name ) ); 
  1254.  
  1255. if ( !empty( $params->create_label_singular ) ) 
  1256. $label = $params->create_label_singular; 
  1257.  
  1258. $pod_params[ 'name' ] = $params->create_name; 
  1259. $pod_params[ 'label' ] = ( !empty( $params->create_label_plural ) ? $params->create_label_plural : $label ); 
  1260. $pod_params[ 'type' ] = $params->create_pod_type; 
  1261. $pod_params[ 'options' ] = array( 
  1262. 'label_singular' => ( !empty( $params->create_label_singular ) ? $params->create_label_singular : $pod_params[ 'label' ] ),  
  1263. 'public' => 1,  
  1264. 'show_ui' => 1 
  1265. ); 
  1266.  
  1267. // Auto-generate name if not provided 
  1268. if ( empty( $pod_params[ 'name' ] ) && !empty( $pod_params[ 'options' ][ 'label_singular' ] ) ) 
  1269. $pod_params[ 'name' ] = pods_clean_name( $pod_params[ 'options' ][ 'label_singular' ] ); 
  1270.  
  1271. if ( 'post_type' == $pod_params[ 'type' ] ) { 
  1272. if ( empty( $pod_params[ 'name' ] ) ) 
  1273. return pods_error( 'Please enter a Name for this Pod', $this ); 
  1274.  
  1275. $pod_params[ 'storage' ] = $params->create_storage; 
  1276.  
  1277. if ( pods_tableless() ) 
  1278. $pod_params[ 'storage' ] = 'meta'; 
  1279. elseif ( 'taxonomy' == $pod_params[ 'type' ] ) { 
  1280. if ( empty( $pod_params[ 'name' ] ) ) 
  1281. return pods_error( 'Please enter a Name for this Pod', $this ); 
  1282.  
  1283. $pod_params[ 'storage' ] = $params->create_storage_taxonomy; 
  1284.  
  1285. if ( pods_tableless() ) 
  1286. $pod_params[ 'storage' ] = ( function_exists( 'get_term_meta' ) ? 'meta' : 'none' ); 
  1287. elseif ( 'pod' == $pod_params[ 'type' ] ) { 
  1288. if ( empty( $pod_params[ 'name' ] ) ) 
  1289. return pods_error( 'Please enter a Name for this Pod', $this ); 
  1290.  
  1291. if ( pods_tableless() ) { 
  1292. $pod_params[ 'type' ] = 'post_type'; 
  1293. $pod_params[ 'storage' ] = 'meta'; 
  1294. elseif ( 'settings' == $pod_params[ 'type' ] ) { 
  1295. $pod_params[ 'name' ] = $params->create_setting_name; 
  1296. $pod_params[ 'label' ] = ( !empty( $params->create_label_title ) ? $params->create_label_title : ucwords( str_replace( '_', ' ', $params->create_setting_name ) ) ); 
  1297. $pod_params[ 'options' ] = array( 
  1298. 'menu_name' => ( !empty( $params->create_label_menu ) ? $params->create_label_menu : $pod_params[ 'label' ] ),  
  1299. 'menu_location' => $params->create_menu_location 
  1300. ); 
  1301. $pod_params[ 'storage' ] = 'none'; 
  1302.  
  1303. // Auto-generate name if not provided 
  1304. if ( empty( $pod_params[ 'name' ] ) && !empty( $pod_params[ 'label' ] ) ) 
  1305. $pod_params[ 'name' ] = pods_clean_name( $pod_params[ 'label' ] ); 
  1306.  
  1307. if ( empty( $pod_params[ 'name' ] ) ) 
  1308. return pods_error( 'Please enter a Name for this Pod', $this ); 
  1309. elseif ( 'extend' == $params->create_extend ) { 
  1310. $pod_params[ 'type' ] = $params->extend_pod_type; 
  1311.  
  1312. if ( 'post_type' == $pod_params[ 'type' ] ) { 
  1313. $pod_params[ 'storage' ] = $params->extend_storage; 
  1314.  
  1315. if ( pods_tableless() ) 
  1316. $pod_params[ 'storage' ] = 'meta'; 
  1317.  
  1318. $pod_params[ 'name' ] = $params->extend_post_type; 
  1319. elseif ( 'taxonomy' == $pod_params[ 'type' ] ) { 
  1320. $pod_params[ 'storage' ] = $params->extend_storage_taxonomy; 
  1321.  
  1322. if ( pods_tableless() ) 
  1323. $pod_params[ 'storage' ] = ( function_exists( 'get_term_meta' ) ? 'meta' : 'none' ); 
  1324.  
  1325. $pod_params[ 'name' ] = $params->extend_taxonomy; 
  1326. elseif ( 'table' == $pod_params[ 'type' ] ) { 
  1327. $pod_params[ 'storage' ] = 'table'; 
  1328. $pod_params[ 'name' ] = $params->extend_table; 
  1329. else { 
  1330. $pod_params[ 'storage' ] = $params->extend_storage; 
  1331.  
  1332. if ( pods_tableless() ) 
  1333. $pod_params[ 'storage' ] = 'meta'; 
  1334.  
  1335. $pod_params[ 'name' ] = $params->extend_pod_type; 
  1336.  
  1337. $pod_params[ 'label' ] = ucwords( str_replace( '_', ' ', $pod_params[ 'name' ] ) ); 
  1338. $pod_params[ 'object' ] = $pod_params[ 'name' ]; 
  1339.  
  1340. if ( empty( $pod_params[ 'object' ] ) ) { 
  1341. if ( 'post_type' == $pod_params[ 'type' ] ) { 
  1342. $check = get_post_type_object( $pod_params[ 'name' ] ); 
  1343.  
  1344. if ( !empty( $check ) ) 
  1345. return pods_error( sprintf( __( 'Post Type %s already exists, try extending it instead', 'pods' ), $pod_params[ 'name' ] ), $this ); 
  1346.  
  1347. $pod_params[ 'options' ][ 'supports_title' ] = 1; 
  1348. $pod_params[ 'options' ][ 'supports_editor' ] = 1; 
  1349. elseif ( 'taxonomy' == $pod_params[ 'type' ] ) { 
  1350. $check = get_taxonomy( $pod_params[ 'name' ] ); 
  1351.  
  1352. if ( !empty( $check ) ) 
  1353. return pods_error( sprintf( __( 'Taxonomy %s already exists, try extending it instead', 'pods' ), $pod_params[ 'name' ] ), $this ); 
  1354.  
  1355. if ( !empty( $pod_params ) ) 
  1356. return $this->save_pod( $pod_params ); 
  1357.  
  1358. return false; 
  1359.  
  1360. /** 
  1361. * Add or edit a Pod 
  1362. * $params['id'] int The Pod ID 
  1363. * $params['name'] string The Pod name 
  1364. * $params['label'] string The Pod label 
  1365. * $params['type'] string The Pod type 
  1366. * $params['object'] string The object being extended (if any) 
  1367. * $params['storage'] string The Pod storage 
  1368. * $params['options'] array Options 
  1369. * @param array $params An associative array of parameters 
  1370. * @param bool $sanitized (optional) Decides whether the params have been sanitized before being passed, will sanitize them if false. 
  1371. * @param bool|int $db (optional) Whether to save into the DB or just return Pod array. 
  1372. * @return int Pod ID 
  1373. * @since 1.7.9 
  1374. */ 
  1375. public function save_pod ( $params, $sanitized = false, $db = true ) { 
  1376. $tableless_field_types = PodsForm::tableless_field_types(); 
  1377. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  1378.  
  1379. $load_params = (object) $params; 
  1380.  
  1381. if ( isset( $load_params->id ) && isset( $load_params->name ) ) 
  1382. unset( $load_params->name ); 
  1383.  
  1384. if ( isset( $load_params->old_name ) ) 
  1385. $load_params->name = $load_params->old_name; 
  1386.  
  1387. $load_params->table_info = true; 
  1388.  
  1389. $pod = $this->load_pod( $load_params, false ); 
  1390.  
  1391. $params = (object) $params; 
  1392.  
  1393. if ( false === $sanitized ) 
  1394. $params = pods_sanitize( $params ); 
  1395.  
  1396. $old_id = $old_name = $old_storage = null; 
  1397.  
  1398. $old_fields = $old_options = array(); 
  1399.  
  1400. if ( isset( $params->name ) && ! isset( $params->object ) ) { 
  1401. $params->name = pods_clean_name( $params->name ); 
  1402.  
  1403. if ( !empty( $pod ) ) { 
  1404. if ( isset( $params->id ) && 0 < $params->id ) 
  1405. $old_id = $params->id; 
  1406.  
  1407. $params->id = $pod[ 'id' ]; 
  1408.  
  1409. $old_name = $pod[ 'name' ]; 
  1410. $old_storage = $pod[ 'storage' ]; 
  1411. $old_fields = $pod[ 'fields' ]; 
  1412. $old_options = $pod[ 'options' ]; 
  1413.  
  1414. if ( !isset( $params->name ) && empty( $params->name ) ) 
  1415. $params->name = $pod[ 'name' ]; 
  1416.  
  1417. if ( $old_name != $params->name && false !== $this->pod_exists( array( 'name' => $params->name ) ) ) 
  1418. return pods_error( sprintf( __( 'Pod %s already exists, you cannot rename %s to that', 'pods' ), $params->name, $old_name ), $this ); 
  1419.  
  1420. if ( $old_name != $params->name && in_array( $pod[ 'type' ], array( 'user', 'comment', 'media' ) ) && in_array( $pod[ 'object' ], array( 'user', 'comment', 'media' ) ) ) 
  1421. return pods_error( sprintf( __( 'Pod %s cannot be renamed, it extends an existing WP Object', 'pods' ), $old_name ), $this ); 
  1422.  
  1423. if ( $old_name != $params->name && in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) && !empty( $pod[ 'object' ] ) && $pod[ 'object' ] == $old_name ) 
  1424. return pods_error( sprintf( __( 'Pod %s cannot be renamed, it extends an existing WP Object', 'pods' ), $old_name ), $this ); 
  1425.  
  1426. if ( $old_id != $params->id ) { 
  1427. if ( $params->type == $pod[ 'type' ] && isset( $params->object ) && $params->object == $pod[ 'object' ] ) 
  1428. return pods_error( sprintf( __( 'Pod using %s already exists, you can not reuse an object across multiple pods', 'pods' ), $params->object ), $this ); 
  1429. else 
  1430. return pods_error( sprintf( __( 'Pod %s already exists', 'pods' ), $params->name ), $this ); 
  1431. elseif ( in_array( $params->name, array( 'order', 'orderby', 'post_type' ) ) && 'post_type' == pods_var( 'type', $params ) ) { 
  1432. return pods_error( sprintf( 'There are certain names that a Custom Post Types cannot be named and unfortunately, %s is one of them.', $params->name ), $this ); 
  1433. else { 
  1434. $pod = array( 
  1435. 'id' => 0,  
  1436. 'name' => $params->name,  
  1437. 'label' => $params->name,  
  1438. 'description' => '',  
  1439. 'type' => 'pod',  
  1440. 'storage' => 'table',  
  1441. 'object' => '',  
  1442. 'alias' => '',  
  1443. 'options' => array(),  
  1444. 'fields' => array() 
  1445. ); 
  1446.  
  1447. // Blank out fields and options for AJAX calls (everything should be sent to it for a full overwrite) 
  1448. if ( defined( 'DOING_AJAX' ) && DOING_AJAX ) { 
  1449. $pod[ 'fields' ] = array(); 
  1450. $pod[ 'options' ] = array(); 
  1451.  
  1452. // Setup options 
  1453. $options = get_object_vars( $params ); 
  1454.  
  1455. if ( isset( $options[ 'method' ] ) ) 
  1456. unset( $options[ 'method' ] ); 
  1457.  
  1458. $options_ignore = array( 
  1459. 'object_type',  
  1460. 'object_name',  
  1461. 'table',  
  1462. 'meta_table',  
  1463. 'pod_table',  
  1464. 'field_id',  
  1465. 'field_index',  
  1466. 'field_slug',  
  1467. 'field_type',  
  1468. 'field_parent',  
  1469. 'field_parent_select',  
  1470. 'meta_field_id',  
  1471. 'meta_field_index',  
  1472. 'meta_field_value',  
  1473. 'pod_field_id',  
  1474. 'pod_field_index',  
  1475. 'object_fields',  
  1476. 'join',  
  1477. 'where',  
  1478. 'where_default',  
  1479. 'orderby',  
  1480. 'pod',  
  1481. 'recurse',  
  1482. 'table_info',  
  1483. 'attributes',  
  1484. 'group',  
  1485. 'grouped',  
  1486. 'developer_mode',  
  1487. 'dependency',  
  1488. 'depends-on',  
  1489. 'excludes-on' 
  1490. ); 
  1491.  
  1492. foreach ( $options_ignore as $ignore ) { 
  1493. if ( isset( $options[ $ignore ] ) ) 
  1494. unset( $options[ $ignore ] ); 
  1495.  
  1496. $exclude = array( 
  1497. 'id',  
  1498. 'name',  
  1499. 'label',  
  1500. 'description',  
  1501. 'type',  
  1502. 'storage',  
  1503. 'object',  
  1504. 'alias',  
  1505. 'options',  
  1506. 'fields' 
  1507. ); 
  1508.  
  1509. foreach ( $exclude as $k => $exclude_field ) { 
  1510. $aliases = array( $exclude_field ); 
  1511.  
  1512. if ( is_array( $exclude_field ) ) { 
  1513. $aliases = array_merge( array( $k ), $exclude_field ); 
  1514. $exclude_field = $k; 
  1515.  
  1516. foreach ( $aliases as $alias ) { 
  1517. if ( isset( $options[ $alias ] ) ) { 
  1518. $pod[ $exclude_field ] = pods_trim( $options[ $alias ] ); 
  1519.  
  1520. unset( $options[ $alias ] ); 
  1521.  
  1522. if ( pods_tableless() && !in_array( $pod[ 'type' ], array( 'settings', 'table' ) ) ) { 
  1523. if ( 'pod' == $pod[ 'type' ] ) 
  1524. $pod[ 'type' ] = 'post_type'; 
  1525.  
  1526. if ( 'table' == $pod[ 'storage' ] ) { 
  1527. if ( 'taxonomy' == $pod[ 'type' ] && ! function_exists( 'get_term_meta' ) ) 
  1528. $pod[ 'storage' ] = 'none'; 
  1529. else 
  1530. $pod[ 'storage' ] = 'meta'; 
  1531.  
  1532. $pod[ 'options' ][ 'type' ] = $pod[ 'type' ]; 
  1533. $pod[ 'options' ][ 'storage' ] = $pod[ 'storage' ]; 
  1534. $pod[ 'options' ][ 'object' ] = $pod[ 'object' ]; 
  1535. $pod[ 'options' ][ 'alias' ] = $pod[ 'alias' ]; 
  1536.  
  1537. $pod[ 'options' ] = array_merge( $pod[ 'options' ], $options ); 
  1538.  
  1539. /** 
  1540. * @var WP_Query 
  1541. */ 
  1542. global $wp_query; 
  1543.  
  1544. $reserved_query_vars = array( 
  1545. 'post_type',  
  1546. 'taxonomy',  
  1547. 'output' 
  1548. ); 
  1549.  
  1550. if ( is_object( $wp_query ) ) { 
  1551. $reserved_query_vars = array_merge( $reserved_query_vars, array_keys( $wp_query->fill_query_vars( array() ) ) ); 
  1552.  
  1553. if ( isset( $pod[ 'options' ][ 'query_var_string' ] ) ) { 
  1554. if ( in_array( $pod[ 'options' ][ 'query_var_string' ], $reserved_query_vars ) ) { 
  1555. $pod[ 'options' ][ 'query_var_string' ] = $pod[ 'options' ][ 'type' ] . '_' . $pod[ 'options' ][ 'query_var_string' ]; 
  1556.  
  1557. if ( isset( $pod[ 'options' ][ 'query_var' ] ) ) { 
  1558. if ( in_array( $pod[ 'options' ][ 'query_var' ], $reserved_query_vars ) ) { 
  1559. $pod[ 'options' ][ 'query_var' ] = $pod[ 'options' ][ 'type' ] . '_' . $pod[ 'options' ][ 'query_var' ]; 
  1560.  
  1561. if ( strlen( $pod[ 'label' ] ) < 1 ) 
  1562. $pod[ 'label' ] = $pod[ 'name' ]; 
  1563.  
  1564. if ( 'post_type' == $pod[ 'type' ] ) { 
  1565. // Max length for post types are 20 characters 
  1566. $pod[ 'name' ] = substr( $pod[ 'name' ], 0, 20 ); 
  1567. elseif ( 'taxonomy' == $pod[ 'type' ] ) { 
  1568. // Max length for taxonomies are 32 characters 
  1569. $pod[ 'name' ] = substr( $pod[ 'name' ], 0, 32 ); 
  1570.  
  1571. $params->id = $pod[ 'id' ]; 
  1572. $params->name = $pod[ 'name' ]; 
  1573.  
  1574. if ( null !== $old_name && $old_name != $params->name && empty( $pod[ 'object' ] ) ) { 
  1575. if ( 'post_type' == $pod[ 'type' ] ) { 
  1576. $check = get_post_type_object( $params->name ); 
  1577.  
  1578. if ( !empty( $check ) ) 
  1579. return pods_error( sprintf( __( 'Post Type %s already exists, you cannot rename %s to that', 'pods' ), $params->name, $old_name ), $this ); 
  1580. elseif ( 'taxonomy' == $pod[ 'type' ] ) { 
  1581. $check = get_taxonomy( $params->name ); 
  1582.  
  1583. if ( !empty( $check ) ) 
  1584. return pods_error( sprintf( __( 'Taxonomy %s already exists, you cannot rename %s to that', 'pods' ), $params->name, $old_name ), $this ); 
  1585.  
  1586. $field_table_operation = true; 
  1587.  
  1588. // Add new pod 
  1589. if ( empty( $params->id ) ) { 
  1590. if ( strlen( $params->name ) < 1 ) 
  1591. return pods_error( __( 'Pod name cannot be empty', 'pods' ), $this ); 
  1592.  
  1593. $post_data = array( 
  1594. 'post_name' => $pod[ 'name' ],  
  1595. 'post_title' => $pod[ 'label' ],  
  1596. 'post_content' => $pod[ 'description' ],  
  1597. 'post_type' => '_pods_pod',  
  1598. 'post_status' => 'publish' 
  1599. ); 
  1600.  
  1601. if ( 'pod' == $pod[ 'type' ] && ( !is_array( $pod[ 'fields' ] ) || empty( $pod[ 'fields' ] ) ) ) { 
  1602. $pod[ 'fields' ] = array(); 
  1603.  
  1604. $pod[ 'fields' ][ 'name' ] = array( 
  1605. 'name' => 'name',  
  1606. 'label' => 'Name',  
  1607. 'type' => 'text',  
  1608. 'options' => array( 
  1609. 'required' => '1' 
  1610. ); 
  1611.  
  1612. $pod[ 'fields' ][ 'created' ] = array( 
  1613. 'name' => 'created',  
  1614. 'label' => 'Date Created',  
  1615. 'type' => 'datetime',  
  1616. 'options' => array( 
  1617. 'datetime_format' => 'ymd_slash',  
  1618. 'datetime_time_type' => '12',  
  1619. 'datetime_time_format' => 'h_mm_ss_A' 
  1620. ); 
  1621.  
  1622. $pod[ 'fields' ][ 'modified' ] = array( 
  1623. 'name' => 'modified',  
  1624. 'label' => 'Date Modified',  
  1625. 'type' => 'datetime',  
  1626. 'options' => array( 
  1627. 'datetime_format' => 'ymd_slash',  
  1628. 'datetime_time_type' => '12',  
  1629. 'datetime_time_format' => 'h_mm_ss_A' 
  1630. ); 
  1631.  
  1632. $pod[ 'fields' ][ 'author' ] = array( 
  1633. 'name' => 'author',  
  1634. 'label' => 'Author',  
  1635. 'type' => 'pick',  
  1636. 'pick_object' => 'user',  
  1637. 'options' => array( 
  1638. 'pick_format_type' => 'single',  
  1639. 'pick_format_single' => 'autocomplete',  
  1640. 'default_value' => '{@user.ID}' 
  1641. ); 
  1642.  
  1643. $pod[ 'fields' ][ 'permalink' ] = array( 
  1644. 'name' => 'permalink',  
  1645. 'label' => 'Permalink',  
  1646. 'type' => 'slug',  
  1647. 'description' => 'Leave blank to auto-generate from Name' 
  1648. ); 
  1649.  
  1650. if ( !isset( $pod[ 'options' ][ 'pod_index' ] ) ) 
  1651. $pod[ 'options' ][ 'pod_index' ] = 'name'; 
  1652.  
  1653. $pod = $this->do_hook( 'save_pod_default_pod', $pod, $params, $sanitized, $db ); 
  1654.  
  1655. $field_table_operation = false; 
  1656. else { 
  1657. $post_data = array( 
  1658. 'ID' => $pod[ 'id' ],  
  1659. 'post_name' => $pod[ 'name' ],  
  1660. 'post_title' => $pod[ 'label' ],  
  1661. 'post_content' => $pod[ 'description' ],  
  1662. 'post_status' => 'publish' 
  1663. ); 
  1664.  
  1665. if ( true === $db ) { 
  1666. if ( !has_filter( 'wp_unique_post_slug', array( $this, 'save_slug_fix' ) ) ) 
  1667. add_filter( 'wp_unique_post_slug', array( $this, 'save_slug_fix' ), 100, 6 ); 
  1668.  
  1669. $conflicted = false; 
  1670.  
  1671. // Headway compatibility fix 
  1672. if ( has_filter( 'wp_insert_post_data', 'headway_clean_slug', 0 ) ) { 
  1673. remove_filter( 'wp_insert_post_data', 'headway_clean_slug', 0 ); 
  1674.  
  1675. $conflicted = true; 
  1676.  
  1677. $params->id = $this->save_wp_object( 'post', $post_data, $pod[ 'options' ], true, true ); 
  1678.  
  1679. if ( $conflicted ) 
  1680. add_filter( 'wp_insert_post_data', 'headway_clean_slug', 0 ); 
  1681.  
  1682. if ( false === $params->id ) 
  1683. return pods_error( __( 'Cannot save Pod', 'pods' ), $this ); 
  1684. elseif ( empty( $params->id ) ) 
  1685. $params->id = (int) $db; 
  1686.  
  1687. $pod[ 'id' ] = $params->id; 
  1688.  
  1689. // Setup / update tables 
  1690. if ( 'table' != $pod[ 'type' ] && 'table' == $pod[ 'storage' ] && $old_storage != $pod[ 'storage' ] && $db ) { 
  1691. $definitions = array( "`id` BIGINT(20) UNSIGNED AUTO_INCREMENT PRIMARY KEY" ); 
  1692.  
  1693. $defined_fields = array(); 
  1694.  
  1695. foreach ( $pod[ 'fields' ] as $field ) { 
  1696. if ( !is_array( $field ) || !isset( $field[ 'name' ] ) || in_array( $field[ 'name' ], $defined_fields ) ) 
  1697. continue; 
  1698.  
  1699. $defined_fields[] = $field[ 'name' ]; 
  1700.  
  1701. if ( !in_array( $field[ 'type' ], $tableless_field_types ) || ( 'pick' == $field[ 'type' ] && in_array( pods_var( 'pick_object', $field ), $simple_tableless_objects ) ) ) { 
  1702. $definition = $this->get_field_definition( $field[ 'type' ], array_merge( $field, pods_var_raw( 'options', $field, array() ) ) ); 
  1703.  
  1704. if ( 0 < strlen( $definition ) ) 
  1705. $definitions[] = "`{$field['name']}` " . $definition; 
  1706.  
  1707. pods_query( "DROP TABLE IF EXISTS `@wp_pods_{$params->name}`" ); 
  1708.  
  1709. $result = pods_query( "CREATE TABLE `@wp_pods_{$params->name}` (" . implode( ', ', $definitions ) . ") DEFAULT CHARSET utf8", $this ); 
  1710.  
  1711. if ( empty( $result ) ) 
  1712. return pods_error( __( 'Cannot add Database Table for Pod', 'pods' ), $this ); 
  1713.  
  1714. elseif ( 'table' != $pod[ 'type' ] && 'table' == $pod[ 'storage' ] && $pod[ 'storage' ] == $old_storage && null !== $old_name && $old_name != $params->name && $db ) { 
  1715. $result = pods_query( "ALTER TABLE `@wp_pods_{$old_name}` RENAME `@wp_pods_{$params->name}`", $this ); 
  1716.  
  1717. if ( empty( $result ) ) 
  1718. return pods_error( __( 'Cannot update Database Table for Pod', 'pods' ), $this ); 
  1719.  
  1720. /** 
  1721. * @var $wpdb wpdb 
  1722. */ 
  1723. global $wpdb; 
  1724.  
  1725. if ( null !== $old_name && $old_name != $params->name && $db ) { 
  1726. // Rename items in the DB pointed at the old WP Object names 
  1727. if ( 'post_type' == $pod[ 'type' ] && empty( $pod[ 'object' ] ) ) { 
  1728. $this->rename_wp_object_type( 'post', $old_name, $params->name ); 
  1729. elseif ( 'taxonomy' == $pod[ 'type' ] && empty( $pod[ 'object' ] ) ) { 
  1730. $this->rename_wp_object_type( 'taxonomy', $old_name, $params->name ); 
  1731. elseif ( 'comment' == $pod[ 'type' ] && empty( $pod[ 'object' ] ) ) { 
  1732. $this->rename_wp_object_type( 'comment', $old_name, $params->name ); 
  1733. elseif ( 'settings' == $pod[ 'type' ] ) { 
  1734. $this->rename_wp_object_type( 'settings', $old_name, $params->name ); 
  1735.  
  1736. // Sync any related fields if the name has changed 
  1737. $fields = pods_query( " 
  1738. SELECT `p`.`ID` 
  1739. FROM `{$wpdb->posts}` AS `p` 
  1740. LEFT JOIN `{$wpdb->postmeta}` AS `pm` ON `pm`.`post_id` = `p`.`ID` 
  1741. LEFT JOIN `{$wpdb->postmeta}` AS `pm2` ON `pm2`.`post_id` = `p`.`ID` 
  1742. WHERE 
  1743. `p`.`post_type` = '_pods_field' 
  1744. AND `pm`.`meta_key` = 'pick_object' 
  1745. AND ( 
  1746. `pm`.`meta_value` = 'pod' 
  1747. OR `pm`.`meta_value` = '" . $pod[ 'type' ] . "' 
  1748. AND `pm2`.`meta_key` = 'pick_val' 
  1749. AND `pm2`.`meta_value` = '{$old_name}' 
  1750. " ); 
  1751.  
  1752. if ( !empty( $fields ) ) { 
  1753. foreach ( $fields as $field ) { 
  1754. update_post_meta( $field->ID, 'pick_object', $pod[ 'type' ] ); 
  1755. update_post_meta( $field->ID, 'pick_val', $params->name ); 
  1756.  
  1757. $fields = pods_query( " 
  1758. SELECT `p`.`ID` 
  1759. FROM `{$wpdb->posts}` AS `p` 
  1760. LEFT JOIN `{$wpdb->postmeta}` AS `pm` ON `pm`.`post_id` = `p`.`ID` 
  1761. WHERE 
  1762. `p`.`post_type` = '_pods_field' 
  1763. AND `pm`.`meta_key` = 'pick_object' 
  1764. AND ( 
  1765. `pm`.`meta_value` = 'pod-{$old_name}' 
  1766. OR `pm`.`meta_value` = '" . $pod[ 'type' ] . "-{$old_name}' 
  1767. " ); 
  1768.  
  1769. if ( !empty( $fields ) ) { 
  1770. foreach ( $fields as $field ) { 
  1771. update_post_meta( $field->ID, 'pick_object', $pod[ 'type' ] ); 
  1772. update_post_meta( $field->ID, 'pick_val', $params->name ); 
  1773.  
  1774. // Sync built-in options for post types and taxonomies 
  1775. if ( in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) && empty( $pod[ 'object' ] ) && $db ) { 
  1776. // Build list of 'built_in' for later 
  1777. $built_in = array(); 
  1778.  
  1779. foreach ( $pod[ 'options' ] as $key => $val ) { 
  1780. if ( false === strpos( $key, 'built_in_' ) ) 
  1781. continue; 
  1782. elseif ( false !== strpos( $key, 'built_in_post_types_' ) ) 
  1783. $built_in_type = 'post_type'; 
  1784. elseif ( false !== strpos( $key, 'built_in_taxonomies_' ) ) 
  1785. $built_in_type = 'taxonomy'; 
  1786. else 
  1787. continue; 
  1788.  
  1789. if ( $built_in_type == $pod[ 'type' ] ) 
  1790. continue; 
  1791.  
  1792. if ( !isset( $built_in[ $built_in_type ] ) ) 
  1793. $built_in[ $built_in_type ] = array(); 
  1794.  
  1795. $built_in_object = str_replace( array( 'built_in_post_types_', 'built_in_taxonomies_' ), '', $key ); 
  1796.  
  1797. $built_in[ $built_in_type ][ $built_in_object ] = (int) $val; 
  1798.  
  1799. $lookup_option = $lookup_built_in = false; 
  1800.  
  1801. $lookup_name = $pod[ 'name' ]; 
  1802.  
  1803. if ( 'post_type' == $pod[ 'type' ] ) { 
  1804. $lookup_option = 'built_in_post_types_' . $lookup_name; 
  1805. $lookup_built_in = 'taxonomy'; 
  1806. elseif ( 'taxonomy' == $pod[ 'type' ] ) { 
  1807. $lookup_option = 'built_in_taxonomies_' . $lookup_name; 
  1808. $lookup_built_in = 'post_type'; 
  1809.  
  1810. if ( !empty( $lookup_option ) && !empty( $lookup_built_in ) && isset( $built_in[ $lookup_built_in ] ) ) { 
  1811. foreach ( $built_in[ $lookup_built_in ] as $built_in_object => $val ) { 
  1812. $search_val = 1; 
  1813.  
  1814. if ( 1 == $val ) 
  1815. $search_val = 0; 
  1816.  
  1817. $query = "SELECT p.ID FROM {$wpdb->posts} AS p 
  1818. LEFT JOIN {$wpdb->postmeta} AS pm ON pm.post_id = p.ID AND pm.meta_key = '{$lookup_option}' 
  1819. LEFT JOIN {$wpdb->postmeta} AS pm2 ON pm2.post_id = p.ID AND pm2.meta_key = 'type' AND pm2.meta_value = '{$lookup_built_in}' 
  1820. LEFT JOIN {$wpdb->postmeta} AS pm3 ON pm3.post_id = p.ID AND pm3.meta_key = 'object' AND pm3.meta_value = '' 
  1821. WHERE p.post_type = '_pods_pod' AND p.post_name = '{$built_in_object}' 
  1822. AND pm2.meta_id IS NOT NULL 
  1823. AND ( pm.meta_id IS NULL OR pm.meta_value = {$search_val} )"; 
  1824.  
  1825. $results = pods_query( $query ); 
  1826.  
  1827. if ( !empty( $results ) ) { 
  1828. foreach ( $results as $the_pod ) { 
  1829. delete_post_meta( $the_pod->ID, $lookup_option ); 
  1830.  
  1831. add_post_meta( $the_pod->ID, $lookup_option, $val ); 
  1832.  
  1833. $saved = array(); 
  1834. $errors = array(); 
  1835.  
  1836. $field_index_change = false; 
  1837. $field_index_id = 0; 
  1838.  
  1839. $id_required = false; 
  1840.  
  1841. $field_index = pods_var( 'pod_index', $pod[ 'options' ], 'id', null, true ); 
  1842.  
  1843. if ( 'pod' == $pod[ 'type' ] && !empty( $pod[ 'fields' ] ) && isset( $pod[ 'fields' ][ $field_index ] ) ) 
  1844. $field_index_id = $pod[ 'fields' ][ $field_index ]; 
  1845.  
  1846. if ( isset( $params->fields ) || ( defined( 'DOING_AJAX' ) && DOING_AJAX ) ) { 
  1847. $fields = array(); 
  1848.  
  1849. if ( isset( $params->fields ) ) { 
  1850. $params->fields = (array) $params->fields; 
  1851.  
  1852. $weight = 0; 
  1853.  
  1854. foreach ( $params->fields as $field ) { 
  1855. if ( !is_array( $field ) || !isset( $field[ 'name' ] ) ) 
  1856. continue; 
  1857.  
  1858. if ( !isset( $field[ 'weight' ] ) ) { 
  1859. $field[ 'weight' ] = $weight; 
  1860.  
  1861. $weight++; 
  1862.  
  1863. $fields[ $field[ 'name' ] ] = $field; 
  1864.  
  1865. $weight = 0; 
  1866.  
  1867. $saved_field_ids = array(); 
  1868.  
  1869. foreach ( $pod[ 'fields' ] as $k => $field ) { 
  1870. if ( !empty( $old_id ) && ( !is_array( $field ) || !isset( $field[ 'name' ] ) || !isset( $fields[ $field[ 'name' ] ] ) ) ) { 
  1871. // Iterative change handling for setup-edit.php 
  1872. if ( !is_array( $field ) && isset( $old_fields[ $k ] ) ) 
  1873. $saved[ $old_fields[ $k ][ 'name' ] ] = true; 
  1874.  
  1875. continue; 
  1876.  
  1877. if ( !empty( $old_id ) ) 
  1878. $field = array_merge( $field, $fields[ $field[ 'name' ] ] ); 
  1879.  
  1880. $field[ 'pod' ] = $pod; 
  1881.  
  1882. if ( !isset( $field[ 'weight' ] ) ) { 
  1883. $field[ 'weight' ] = $weight; 
  1884.  
  1885. $weight++; 
  1886.  
  1887. if ( 0 < $field_index_id && pods_var( 'id', $field ) == $field_index_id ) 
  1888. $field_index_change = $field[ 'name' ]; 
  1889.  
  1890. if ( 0 < pods_var( 'id', $field ) ) 
  1891. $id_required = true; 
  1892.  
  1893. if ( $id_required ) 
  1894. $field[ 'id_required' ] = true; 
  1895.  
  1896. $field_data = $field; 
  1897.  
  1898. $field = $this->save_field( $field_data, $field_table_operation, true, $db ); 
  1899.  
  1900. if ( true !== $db ) { 
  1901. $pod[ 'fields' ][ $k ] = $field; 
  1902. $saved_field_ids[] = $field[ 'id' ]; 
  1903. else { 
  1904. if ( !empty( $field ) && 0 < $field ) { 
  1905. $saved[ $field_data[ 'name' ] ] = true; 
  1906. $saved_field_ids[] = $field; 
  1907. else 
  1908. $errors[] = sprintf( __( 'Cannot save the %s field', 'pods' ), $field_data[ 'name' ] ); 
  1909.  
  1910. if ( true === $db ) { 
  1911. foreach ( $old_fields as $field ) { 
  1912. if ( isset( $pod[ 'fields' ][ $field[ 'name' ] ] ) || isset( $saved[ $field[ 'name' ] ] ) || in_array( $field[ 'id' ], $saved_field_ids ) ) 
  1913. continue; 
  1914.  
  1915. if ( $field[ 'id' ] == $field_index_id ) 
  1916. $field_index_change = 'id'; 
  1917. elseif ( $field[ 'name' ] == $field_index ) 
  1918. $field_index_change = 'id'; 
  1919.  
  1920. $this->delete_field( array( 
  1921. 'id' => (int) $field[ 'id' ],  
  1922. 'name' => $field[ 'name' ],  
  1923. 'pod' => $pod 
  1924. ), $field_table_operation ); 
  1925.  
  1926. // Update field index if the name has changed or the field has been removed 
  1927. if ( false !== $field_index_change && true === $db ) 
  1928. update_post_meta( $pod[ 'id' ], 'pod_index', $field_index_change ); 
  1929.  
  1930. if ( !empty( $errors ) ) 
  1931. return pods_error( $errors, $this ); 
  1932.  
  1933. $this->cache_flush_pods( $pod ); 
  1934.  
  1935. if ( 'post_type' == $pod[ 'type' ] ) 
  1936. PodsMeta::$post_types[ $pod[ 'id' ] ] = $this->load_pod( array( 'name' => $pod[ 'name' ] ) ); 
  1937. elseif ( 'taxonomy' == $pod[ 'type' ] ) 
  1938. PodsMeta::$taxonomies[ $pod[ 'id' ] ] = $this->load_pod( array( 'name' => $pod[ 'name' ] ) ); 
  1939. elseif ( 'media' == $pod[ 'type' ] ) 
  1940. PodsMeta::$media[ $pod[ 'id' ] ] = $this->load_pod( array( 'name' => $pod[ 'name' ] ) ); 
  1941. elseif ( 'user' == $pod[ 'type' ] ) 
  1942. PodsMeta::$user[ $pod[ 'id' ] ] = $this->load_pod( array( 'name' => $pod[ 'name' ] ) ); 
  1943. elseif ( 'comment' == $pod[ 'type' ] ) 
  1944. PodsMeta::$comment[ $pod[ 'id' ] ] = $this->load_pod( array( 'name' => $pod[ 'name' ] ) ); 
  1945.  
  1946. // Register Post Types / Taxonomies post-registration from PodsInit 
  1947. if ( !empty( PodsInit::$content_types_registered ) && in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) && empty( $pod[ 'object' ] ) ) { 
  1948. global $pods_init; 
  1949.  
  1950. $pods_init->setup_content_types( true ); 
  1951.  
  1952. if ( true === $db ) 
  1953. return $pod[ 'id' ]; 
  1954. else 
  1955. return $pod; 
  1956.  
  1957. /** 
  1958. * Add or edit a field within a Pod 
  1959. * $params['id'] int Field ID (id OR pod_id+pod+name required) 
  1960. * $params['pod_id'] int Pod ID (id OR pod_id+pod+name required) 
  1961. * $params['pod'] string Pod name (id OR pod_id+pod+name required) 
  1962. * $params['name'] string Field name (id OR pod_id+pod+name required) 
  1963. * $params['label'] string (optional) Field label 
  1964. * $params['type'] string (optional) Field type (avatar, boolean, code, color, currency, date, datetime, email, file, number, paragraph, password, phone, pick, slug, text, time, website, wysiwyg) 
  1965. * $params['pick_object'] string (optional) Related Object (for relationships) 
  1966. * $params['pick_val'] string (optional) Related Object name (for relationships) 
  1967. * $params['sister_id'] int (optional) Related Field ID (for bidirectional relationships) 
  1968. * $params['weight'] int (optional) Order in which the field appears 
  1969. * $params['options'] array (optional) Options 
  1970. * @param array $params An associative array of parameters 
  1971. * @param bool $table_operation (optional) Whether or not to handle table operations 
  1972. * @param bool $sanitized (optional) Decides wether the params have been sanitized before being passed, will sanitize them if false. 
  1973. * @param bool|int $db (optional) Whether to save into the DB or just return field array. 
  1974. * @return int|array The field ID or field array (if !$db) 
  1975. * @since 1.7.9 
  1976. */ 
  1977. public function save_field ( $params, $table_operation = true, $sanitized = false, $db = true ) { 
  1978. /** 
  1979. * @var $wpdb wpdb 
  1980. */ 
  1981. global $wpdb; 
  1982.  
  1983. if ( true !== $db ) 
  1984. $table_operation = false; 
  1985.  
  1986. $tableless_field_types = PodsForm::tableless_field_types(); 
  1987. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  1988.  
  1989. $params = (object) $params; 
  1990.  
  1991. if ( false === $sanitized ) 
  1992. $params = pods_sanitize( $params ); 
  1993.  
  1994. if ( isset( $params->pod_id ) ) 
  1995. $params->pod_id = pods_absint( $params->pod_id ); 
  1996.  
  1997. if ( true !== $db ) 
  1998. $params->pod_id = (int) $db; 
  1999.  
  2000. $pod = null; 
  2001. $save_pod = false; 
  2002. $id_required = false; 
  2003.  
  2004. if ( isset( $params->id_required ) ) { 
  2005. unset( $params->id_required ); 
  2006.  
  2007. $id_required = true; 
  2008.  
  2009. if ( ( !isset( $params->pod ) || empty( $params->pod ) ) && ( !isset( $params->pod_id ) || empty( $params->pod_id ) ) ) 
  2010. return pods_error( __( 'Pod ID or name is required', 'pods' ), $this ); 
  2011.  
  2012. if ( isset( $params->pod ) && is_array( $params->pod ) ) { 
  2013. $pod = $params->pod; 
  2014.  
  2015. $save_pod = true; 
  2016. elseif ( ( !isset( $params->pod_id ) || empty( $params->pod_id ) ) && ( true === $db || 0 < $db ) ) 
  2017. $pod = $this->load_pod( array( 'name' => $params->pod, 'table_info' => true ) ); 
  2018. elseif ( !isset( $params->pod ) && ( true === $db || 0 < $db ) ) 
  2019. $pod = $this->load_pod( array( 'id' => $params->pod_id, 'table_info' => true ) ); 
  2020. elseif ( true === $db || 0 < $db ) 
  2021. $pod = $this->load_pod( array( 'id' => $params->pod_id, 'name' => $params->pod, 'table_info' => true ) ); 
  2022.  
  2023. if ( empty( $pod ) && true === $db ) 
  2024. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  2025.  
  2026. $params->pod_id = $pod[ 'id' ]; 
  2027. $params->pod = $pod[ 'name' ]; 
  2028. $params->pod_data = $pod; 
  2029.  
  2030. $params->name = pods_clean_name( $params->name, true, ( 'meta' == $pod[ 'storage' ] ? false : true ) ); 
  2031.  
  2032. if ( !isset( $params->id ) ) 
  2033. $params->id = 0; 
  2034.  
  2035. if ( empty( $params->name ) ) 
  2036. return pods_error( 'Pod field name is required', $this ); 
  2037.  
  2038. $field = $this->load_field( $params ); 
  2039.  
  2040. unset( $params->pod_data ); 
  2041.  
  2042. $old_id = $old_name = $old_type = $old_definition = $old_simple = $old_options = $old_sister_id = null; 
  2043.  
  2044. if ( !empty( $field ) ) { 
  2045. $old_id = pods_var( 'id', $field ); 
  2046. $old_name = pods_clean_name( $field[ 'name' ], true, ( 'meta' == $pod[ 'storage' ] ? false : true ) ); 
  2047. $old_type = $field[ 'type' ]; 
  2048. $old_options = $field[ 'options' ]; 
  2049. $old_sister_id = (int) pods_var( 'sister_id', $old_options, 0 ); 
  2050.  
  2051. $old_simple = ( 'pick' == $old_type && in_array( pods_var( 'pick_object', $field ), $simple_tableless_objects ) ); 
  2052.  
  2053. if ( isset( $params->name ) && !empty( $params->name ) ) 
  2054. $field[ 'name' ] = $params->name; 
  2055.  
  2056. if ( $old_name != $field[ 'name' ] && false !== $this->field_exists( $params ) ) 
  2057. return pods_error( sprintf( __( 'Field %s already exists, you cannot rename %s to that', 'pods' ), $field[ 'name' ], $old_name ), $this ); 
  2058.  
  2059. if ( ( $id_required || !empty( $params->id ) ) && ( empty( $old_id ) || $old_id != $params->id ) ) 
  2060. return pods_error( sprintf( __( 'Field %s already exists', 'pods' ), $field[ 'name' ] ), $this ); 
  2061.  
  2062. if ( empty( $params->id ) ) 
  2063. $params->id = $old_id; 
  2064.  
  2065. if ( !in_array( $old_type, $tableless_field_types ) || $old_simple ) { 
  2066. $definition = $this->get_field_definition( $old_type, array_merge( $field, $old_options ) ); 
  2067.  
  2068. if ( 0 < strlen( $definition ) ) 
  2069. $old_definition = "`{$old_name}` " . $definition; 
  2070. else { 
  2071. $field = array( 
  2072. 'id' => 0,  
  2073. 'pod_id' => $params->pod_id,  
  2074. 'name' => $params->name,  
  2075. 'label' => $params->name,  
  2076. 'description' => '',  
  2077. 'type' => 'text',  
  2078. 'pick_object' => '',  
  2079. 'pick_val' => '',  
  2080. 'sister_id' => '',  
  2081. 'weight' => null,  
  2082. 'options' => array() 
  2083. ); 
  2084.  
  2085. // Setup options 
  2086. $options = get_object_vars( $params ); 
  2087.  
  2088. $options_ignore = array( 
  2089. 'method',  
  2090. 'table_info',  
  2091. 'attributes',  
  2092. 'group',  
  2093. 'grouped',  
  2094. 'developer_mode',  
  2095. 'dependency',  
  2096. 'depends-on',  
  2097. 'excludes-on' 
  2098. ); 
  2099.  
  2100. foreach ( $options_ignore as $ignore ) { 
  2101. if ( isset( $options[ $ignore ] ) ) 
  2102. unset( $options[ $ignore ] ); 
  2103.  
  2104. if ( isset( $options[ 'method' ] ) ) 
  2105. unset( $options[ 'method' ] ); 
  2106. elseif ( isset( $options[ 'table_info' ] ) ) 
  2107. unset( $options[ 'table_info' ] ); 
  2108.  
  2109. $exclude = array( 
  2110. 'id',  
  2111. 'pod_id',  
  2112. 'pod',  
  2113. 'name',  
  2114. 'label',  
  2115. 'description',  
  2116. 'type',  
  2117. 'pick_object',  
  2118. 'pick_val',  
  2119. 'sister_id',  
  2120. 'weight',  
  2121. 'options' 
  2122. ); 
  2123.  
  2124. foreach ( $exclude as $k => $exclude_field ) { 
  2125. $aliases = array( $exclude_field ); 
  2126.  
  2127. if ( is_array( $exclude_field ) ) { 
  2128. $aliases = array_merge( array( $k ), $exclude_field ); 
  2129. $exclude_field = $k; 
  2130.  
  2131. foreach ( $aliases as $alias ) { 
  2132. if ( isset( $options[ $alias ] ) ) { 
  2133. $field[ $exclude_field ] = pods_trim( $options[ $alias ] ); 
  2134.  
  2135. unset( $options[ $alias ] ); 
  2136.  
  2137. if ( strlen( $field[ 'label' ] ) < 1 ) 
  2138. $field[ 'label' ] = $field[ 'name' ]; 
  2139.  
  2140. $field[ 'options' ][ 'type' ] = $field[ 'type' ]; 
  2141.  
  2142. if ( in_array( $field[ 'options' ][ 'type' ], $tableless_field_types ) ) { 
  2143. // Clean up special drop-down in field editor and save out pick_val 
  2144. $field[ 'pick_object' ] = pods_var( 'pick_object', $field, '', null, true ); 
  2145.  
  2146. if ( 0 === strpos( $field[ 'pick_object' ], 'pod-' ) ) { 
  2147. $field[ 'pick_val' ] = pods_str_replace( 'pod-', '', $field[ 'pick_object' ], 1 ); 
  2148. $field[ 'pick_object' ] = 'pod'; 
  2149. elseif ( 0 === strpos( $field[ 'pick_object' ], 'post_type-' ) ) { 
  2150. $field[ 'pick_val' ] = pods_str_replace( 'post_type-', '', $field[ 'pick_object' ], 1 ); 
  2151. $field[ 'pick_object' ] = 'post_type'; 
  2152. elseif ( 0 === strpos( $field[ 'pick_object' ], 'taxonomy-' ) ) { 
  2153. $field[ 'pick_val' ] = pods_str_replace( 'taxonomy-', '', $field[ 'pick_object' ], 1 ); 
  2154. $field[ 'pick_object' ] = 'taxonomy'; 
  2155. elseif ( 'table' == $field[ 'pick_object' ] && 0 < strlen( pods_var_raw( 'pick_table', $field[ 'options' ] ) ) ) { 
  2156. $field[ 'pick_val' ] = $field[ 'options' ][ 'pick_table' ]; 
  2157. $field[ 'pick_object' ] = 'table'; 
  2158. elseif ( false === strpos( $field[ 'pick_object' ], '-' ) && !in_array( $field[ 'pick_object' ], array( 'pod', 'post_type', 'taxonomy' ) ) ) { 
  2159. $field[ 'pick_val' ] = ''; 
  2160. elseif ( 'custom-simple' == $field[ 'pick_object' ] ) { 
  2161. $field[ 'pick_val' ] = ''; 
  2162.  
  2163. $field[ 'options' ][ 'pick_object' ] = $field[ 'pick_object' ]; 
  2164. $field[ 'options' ][ 'pick_val' ] = $field[ 'pick_val' ]; 
  2165. $field[ 'options' ][ 'sister_id' ] = pods_var( 'sister_id', $field ); 
  2166.  
  2167. unset( $field[ 'pick_object' ] ); 
  2168. unset( $field[ 'pick_val' ] ); 
  2169.  
  2170. if ( isset( $field[ 'sister_id' ] ) ) 
  2171. unset( $field[ 'sister_id' ] ); 
  2172.  
  2173. $field[ 'options' ] = array_merge( $field[ 'options' ], $options ); 
  2174.  
  2175. $object_fields = (array) pods_var_raw( 'object_fields', $pod, array(), null, true ); 
  2176.  
  2177. if ( 0 < $old_id && defined( 'PODS_FIELD_STRICT' ) && !PODS_FIELD_STRICT ) 
  2178. $params->id = $field[ 'id' ] = $old_id; 
  2179.  
  2180. // Add new field 
  2181. if ( !isset( $params->id ) || empty( $params->id ) || empty( $field ) ) { 
  2182. if ( $table_operation && in_array( $field[ 'name' ], array( 'created', 'modified' ) ) && !in_array( $field[ 'type' ], array( 'date', 'datetime' ) ) && ( !defined( 'PODS_FIELD_STRICT' ) || PODS_FIELD_STRICT ) ) 
  2183. return pods_error( sprintf( __( '%s is reserved for internal Pods usage, please try a different name', 'pods' ), $field[ 'name' ] ), $this ); 
  2184.  
  2185. if ( $table_operation && 'author' == $field[ 'name' ] && 'pick' != $field[ 'type' ] && ( !defined( 'PODS_FIELD_STRICT' ) || PODS_FIELD_STRICT ) ) 
  2186. return pods_error( sprintf( __( '%s is reserved for internal Pods usage, please try a different name', 'pods' ), $field[ 'name' ] ), $this ); 
  2187.  
  2188. if ( in_array( $field[ 'name' ], array( 'id', 'ID' ) ) ) 
  2189. return pods_error( sprintf( __( '%s is reserved for internal Pods usage, please try a different name', 'pods' ), $field[ 'name' ] ), $this ); 
  2190.  
  2191. foreach ( $object_fields as $object_field => $object_field_opt ) { 
  2192. if ( $object_field == $field[ 'name' ] || in_array( $field[ 'name' ], $object_field_opt[ 'alias' ] ) ) 
  2193. return pods_error( sprintf( __( '%s is reserved for internal WordPress or Pods usage, please try a different name. Also consider what WordPress and Pods provide you built-in.', 'pods' ), $field[ 'name' ] ), $this ); 
  2194.  
  2195. if ( in_array( $field[ 'name' ], array( 'rss' ) ) ) // Reserved post_name values that can't be used as field names 
  2196. $field[ 'name' ] .= '2'; 
  2197.  
  2198. if ( 'slug' == $field[ 'type' ] && true === $db ) { 
  2199. if ( in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy', 'user' ) ) ) 
  2200. return pods_error( __( 'This pod already has an internal WordPress permalink field', 'pods' ), $this ); 
  2201.  
  2202. $slug_field = get_posts( array( 
  2203. 'post_type' => '_pods_field',  
  2204. 'orderby' => 'menu_order',  
  2205. 'order' => 'ASC',  
  2206. 'posts_per_page' => 1,  
  2207. 'post_parent' => $field[ 'pod_id' ],  
  2208. 'meta_query' => array( 
  2209. array( 
  2210. 'key' => 'type',  
  2211. 'value' => 'slug' 
  2212. ) ); 
  2213.  
  2214. if ( !empty( $slug_field ) ) 
  2215. return pods_error( __( 'This pod already has a permalink field', 'pods' ), $this ); 
  2216.  
  2217. // Sink the new field to the bottom of the list 
  2218. if ( null === $field[ 'weight' ] ) { 
  2219. $field[ 'weight' ] = 0; 
  2220.  
  2221. $bottom_most_field = get_posts( array( 
  2222. 'post_type' => '_pods_field',  
  2223. 'orderby' => 'menu_order',  
  2224. 'order' => 'DESC',  
  2225. 'posts_per_page' => 1,  
  2226. 'post_parent' => $field[ 'pod_id' ] 
  2227. ) ); 
  2228.  
  2229. if ( !empty( $bottom_most_field ) ) 
  2230. $field[ 'weight' ] = pods_absint( $bottom_most_field[ 0 ]->menu_order ) + 1; 
  2231.  
  2232. $field[ 'weight' ] = pods_absint( $field[ 'weight' ] ); 
  2233.  
  2234. $post_data = array( 
  2235. 'post_name' => $field[ 'name' ],  
  2236. 'post_title' => $field[ 'label' ],  
  2237. 'post_content' => $field[ 'description' ],  
  2238. 'post_type' => '_pods_field',  
  2239. 'post_parent' => $field[ 'pod_id' ],  
  2240. 'post_status' => 'publish',  
  2241. 'menu_order' => $field[ 'weight' ] 
  2242. ); 
  2243. else { 
  2244. if ( in_array( $field[ 'name' ], array( 'id', 'ID' ) ) ) { 
  2245. if ( null !== $old_name ) 
  2246. return pods_error( sprintf( __( '%s is reserved for internal Pods usage, please try a different name', 'pods' ), $field[ 'name' ] ), $this ); 
  2247. else 
  2248. return pods_error( sprintf( __( '%s is not editable', 'pods' ), $field[ 'name' ] ), $this ); 
  2249.  
  2250. if ( null !== $old_name && $field[ 'name' ] != $old_name && in_array( $field[ 'name' ], array( 'created', 'modified' ) ) && !in_array( $field[ 'type' ], array( 'date', 'datetime' ) ) && ( !defined( 'PODS_FIELD_STRICT' ) || PODS_FIELD_STRICT ) ) 
  2251. return pods_error( sprintf( __( '%s is reserved for internal Pods usage, please try a different name', 'pods' ), $field[ 'name' ] ), $this ); 
  2252.  
  2253. if ( null !== $old_name && $field[ 'name' ] != $old_name && 'author' == $field[ 'name' ] && 'pick' != $field[ 'type' ] && ( !defined( 'PODS_FIELD_STRICT' ) || PODS_FIELD_STRICT ) ) 
  2254. return pods_error( sprintf( __( '%s is reserved for internal Pods usage, please try a different name', 'pods' ), $field[ 'name' ] ), $this ); 
  2255.  
  2256. foreach ( $object_fields as $object_field => $object_field_opt ) { 
  2257. if ( $object_field != $field[ 'name' ] && !in_array( $field[ 'name' ], $object_field_opt[ 'alias' ] ) ) 
  2258. continue; 
  2259.  
  2260. if ( null !== $old_name ) 
  2261. return pods_error( sprintf( __( '%s is reserved for internal WordPress or Pods usage, please try a different name', 'pods' ), $field[ 'name' ] ), $this ); 
  2262. else 
  2263. return pods_error( sprintf( __( '%s is not editable', 'pods' ), $field[ 'name' ] ), $this ); 
  2264.  
  2265. $post_data = array( 
  2266. 'ID' => $field[ 'id' ],  
  2267. 'post_name' => $field[ 'name' ],  
  2268. 'post_title' => $field[ 'label' ],  
  2269. 'post_content' => $field[ 'description' ] 
  2270. ); 
  2271.  
  2272. if ( null !== $field[ 'weight' ] ) { 
  2273. $field[ 'weight' ] = pods_absint( $field[ 'weight' ] ); 
  2274.  
  2275. $post_data[ 'menu_order' ] = $field[ 'weight' ]; 
  2276.  
  2277. if ( true === $db ) { 
  2278. if ( !has_filter( 'wp_unique_post_slug', array( $this, 'save_slug_fix' ) ) ) 
  2279. add_filter( 'wp_unique_post_slug', array( $this, 'save_slug_fix' ), 100, 6 ); 
  2280.  
  2281. $conflicted = false; 
  2282.  
  2283. // Headway compatibility fix 
  2284. if ( has_filter( 'wp_insert_post_data', 'headway_clean_slug', 0 ) ) { 
  2285. remove_filter( 'wp_insert_post_data', 'headway_clean_slug', 0 ); 
  2286.  
  2287. $conflicted = true; 
  2288.  
  2289. $params->id = $this->save_wp_object( 'post', $post_data, $field[ 'options' ], true, true ); 
  2290.  
  2291. if ( $conflicted ) 
  2292. add_filter( 'wp_insert_post_data', 'headway_clean_slug', 0 ); 
  2293.  
  2294. if ( false === $params->id ) 
  2295. return pods_error( __( 'Cannot save Field', 'pods' ), $this ); 
  2296. else 
  2297. $params->id = $field[ 'name' ]; 
  2298.  
  2299. $field[ 'id' ] = $params->id; 
  2300.  
  2301. $simple = ( 'pick' == $field[ 'type' ] && in_array( pods_var( 'pick_object', $field[ 'options' ] ), $simple_tableless_objects ) ); 
  2302.  
  2303. $definition = false; 
  2304.  
  2305. if ( !in_array( $field[ 'type' ], $tableless_field_types ) || $simple ) { 
  2306. $field_definition = $this->get_field_definition( $field[ 'type' ], array_merge( $field, $field[ 'options' ] ) ); 
  2307.  
  2308. if ( 0 < strlen( $field_definition ) ) 
  2309. $definition = '`' . $field[ 'name' ] . '` ' . $field_definition; 
  2310.  
  2311. $sister_id = (int) pods_var( 'sister_id', $field[ 'options' ], 0 ); 
  2312.  
  2313. if ( $table_operation && 'table' == $pod[ 'storage' ] && !pods_tableless() ) { 
  2314. if ( !empty( $old_id ) ) { 
  2315. if ( ( $field[ 'type' ] != $old_type || $old_simple != $simple ) && empty( $definition ) ) 
  2316. pods_query( "ALTER TABLE `@wp_pods_{$params->pod}` DROP COLUMN `{$old_name}`", false ); 
  2317. elseif ( 0 < strlen( $definition ) ) { 
  2318. if ( $old_name != $field[ 'name' ] || $old_simple != $simple ) { 
  2319. $test = false; 
  2320.  
  2321. if ( 0 < strlen( $old_definition ) ) 
  2322. $test = pods_query( "ALTER TABLE `@wp_pods_{$params->pod}` CHANGE `{$old_name}` {$definition}", false ); 
  2323.  
  2324. // If the old field doesn't exist, continue to add a new field 
  2325. if ( false === $test ) 
  2326. pods_query( "ALTER TABLE `@wp_pods_{$params->pod}` ADD COLUMN {$definition}", __( 'Cannot create new field', 'pods' ) ); 
  2327. elseif ( null !== $old_definition && $definition != $old_definition ) { 
  2328. $test = pods_query( "ALTER TABLE `@wp_pods_{$params->pod}` CHANGE `{$old_name}` {$definition}", false ); 
  2329.  
  2330. // If the old field doesn't exist, continue to add a new field 
  2331. if ( false === $test ) 
  2332. pods_query( "ALTER TABLE `@wp_pods_{$params->pod}` ADD COLUMN {$definition}", __( 'Cannot create new field', 'pods' ) ); 
  2333. elseif ( 0 < strlen( $definition ) ) { 
  2334. $test = false; 
  2335.  
  2336. if ( 0 < strlen( $old_definition ) ) 
  2337. $test = pods_query( "ALTER TABLE `@wp_pods_{$params->pod}` CHANGE `" . $field[ 'name' ] . "` {$definition}", false ); 
  2338.  
  2339. // If the old field doesn't exist, continue to add a new field 
  2340. if ( false === $test ) 
  2341. pods_query( "ALTER TABLE `@wp_pods_{$params->pod}` ADD COLUMN {$definition}", __( 'Cannot create new field', 'pods' ) ); 
  2342.  
  2343. if ( !empty( $old_id ) && 'meta' == $pod[ 'storage' ] && $old_name != $field[ 'name' ] && $pod[ 'meta_table' ] != $pod[ 'table' ] ) { 
  2344. $prepare = array( 
  2345. $field[ 'name' ],  
  2346. $old_name 
  2347. ); 
  2348.  
  2349. // Users don't have a type 
  2350. if ( !empty( $pod[ 'field_type' ] ) ) 
  2351. $prepare[] = $pod[ 'name' ]; 
  2352.  
  2353. pods_query( " 
  2354. UPDATE `{$pod[ 'meta_table' ]}` AS `m` 
  2355. LEFT JOIN `{$pod[ 'table' ]}` AS `t` 
  2356. ON `t`.`{$pod[ 'field_id' ]}` = `m`.`{$pod[ 'meta_field_id' ]}` 
  2357. SET 
  2358. `m`.`{$pod[ 'meta_field_index' ]}` = %s 
  2359. WHERE 
  2360. `m`.`{$pod[ 'meta_field_index' ]}` = %s 
  2361. " . ( !empty( $pod[ 'field_type' ] ) ? " AND `t`.`{$pod[ 'field_type' ]}` = %s" : "" ),  
  2362. $prepare 
  2363. ); 
  2364.  
  2365. if ( $field[ 'type' ] != $old_type && in_array( $old_type, $tableless_field_types ) ) { 
  2366. delete_post_meta( $old_sister_id, 'sister_id' ); 
  2367.  
  2368. if ( true === $db ) { 
  2369. pods_query( " 
  2370. DELETE pm 
  2371. FROM {$wpdb->postmeta} AS pm 
  2372. LEFT JOIN {$wpdb->posts} AS p 
  2373. ON p.post_type = '_pods_field' 
  2374. AND p.ID = pm.post_id 
  2375. WHERE 
  2376. p.ID IS NOT NULL 
  2377. AND pm.meta_key = 'sister_id' 
  2378. AND pm.meta_value = %d 
  2379. ", array( 
  2380. $params->id 
  2381. ); 
  2382.  
  2383. if ( !pods_tableless() ) { 
  2384. pods_query( "DELETE FROM @wp_podsrel WHERE `field_id` = {$params->id}", false ); 
  2385.  
  2386. pods_query( " 
  2387. UPDATE `@wp_podsrel` 
  2388. SET `related_field_id` = 0 
  2389. WHERE `field_id` = %d 
  2390. ", array( 
  2391. $old_sister_id 
  2392. ); 
  2393. elseif ( 0 < $sister_id ) { 
  2394. update_post_meta( $sister_id, 'sister_id', $params->id ); 
  2395.  
  2396. if ( true === $db && ( !pods_tableless() ) ) { 
  2397. pods_query( " 
  2398. UPDATE `@wp_podsrel` 
  2399. SET `related_field_id` = %d 
  2400. WHERE `field_id` = %d 
  2401. ",  
  2402. array( 
  2403. $params->id,  
  2404. $sister_id 
  2405. ); 
  2406. elseif ( 0 < $old_sister_id ) { 
  2407. delete_post_meta( $old_sister_id, 'sister_id' ); 
  2408.  
  2409. if ( true === $db && ( !pods_tableless() ) ) { 
  2410. pods_query( " 
  2411. UPDATE `@wp_podsrel` 
  2412. SET `related_field_id` = 0 
  2413. WHERE `field_id` = %d 
  2414. ", array( 
  2415. $old_sister_id 
  2416. ); 
  2417.  
  2418. if ( !empty( $old_id ) && $old_name != $field[ 'name' ] && true === $db ) { 
  2419. pods_query( " 
  2420. UPDATE `@wp_postmeta` 
  2421. SET `meta_value` = %s 
  2422. WHERE 
  2423. `post_id` = %d 
  2424. AND `meta_key` = 'pod_index' 
  2425. AND `meta_value` = %s 
  2426. ", array( 
  2427. $field[ 'name' ],  
  2428. $pod[ 'id' ],  
  2429. $old_name 
  2430. ); 
  2431.  
  2432. if ( !$save_pod ) 
  2433. $this->cache_flush_pods( $pod ); 
  2434. else { 
  2435. pods_transient_clear( 'pods_field_' . $pod[ 'name' ] . '_' . $field[ 'name' ] ); 
  2436.  
  2437. if ( !empty( $old_id ) && $old_name != $field[ 'name' ] ) 
  2438. pods_transient_clear( 'pods_field_' . $pod[ 'name' ] . '_' . $old_name ); 
  2439.  
  2440. if ( true === $db ) 
  2441. return $params->id; 
  2442. else 
  2443. return $field; 
  2444.  
  2445. /** 
  2446. * Fix Pod / Field post_name to ensure they are exactly as saved (allow multiple posts w/ same post_name) 
  2447. * @param string $slug Unique slug value 
  2448. * @param int $post_ID Post ID 
  2449. * @param string $post_status Post Status 
  2450. * @param string $post_type Post Type 
  2451. * @param int $post_parent Post Parent ID 
  2452. * @param string $original_slug Original slug value 
  2453. * @return string Final slug value 
  2454. * @since 2.3.3 
  2455. */ 
  2456. public function save_slug_fix ( $slug, $post_ID, $post_status, $post_type, $post_parent = 0, $original_slug = null ) { 
  2457. if ( in_array( $post_type, array( '_pods_field', '_pods_pod' ) ) && false !== strpos( $slug, '-' ) ) 
  2458. $slug = $original_slug; 
  2459.  
  2460. return $slug; 
  2461.  
  2462. /** 
  2463. * Add or Edit a Pods Object 
  2464. * $params['id'] int The Object ID 
  2465. * $params['name'] string The Object name 
  2466. * $params['type'] string The Object type 
  2467. * $params['options'] Associative array of Object options 
  2468. * @param array|object $params An associative array of parameters 
  2469. * @param bool $sanitized (optional) Decides whether the params have been sanitized before being passed, will sanitize them if false. 
  2470. * @return int The Object ID 
  2471. * @since 2.0 
  2472. */ 
  2473. public function save_object ( $params, $sanitized = false ) { 
  2474. $params = (object) $params; 
  2475.  
  2476. if ( false === $sanitized ) 
  2477. $params = pods_sanitize( $params ); 
  2478.  
  2479. if ( !isset( $params->name ) || empty( $params->name ) ) 
  2480. return pods_error( __( 'Name must be given to save an Object', 'pods' ), $this ); 
  2481.  
  2482. if ( !isset( $params->type ) || empty( $params->type ) ) 
  2483. return pods_error( __( 'Type must be given to save an Object', 'pods' ), $this ); 
  2484.  
  2485. $object = array( 
  2486. 'id' => 0,  
  2487. 'name' => $params->name,  
  2488. 'type' => $params->type,  
  2489. 'code' => '',  
  2490. 'options' => array() 
  2491. ); 
  2492.  
  2493. // Setup options 
  2494. $options = get_object_vars( $params ); 
  2495.  
  2496. if ( isset( $options[ 'method' ] ) ) 
  2497. unset( $options[ 'method' ] ); 
  2498.  
  2499. $exclude = array( 
  2500. 'id',  
  2501. 'name',  
  2502. 'helper_type',  
  2503. 'code',  
  2504. 'options',  
  2505. 'status' 
  2506. ); 
  2507.  
  2508. foreach ( $exclude as $k => $exclude_field ) { 
  2509. $aliases = array( $exclude_field ); 
  2510.  
  2511. if ( is_array( $exclude_field ) ) { 
  2512. $aliases = array_merge( array( $k ), $exclude_field ); 
  2513. $exclude_field = $k; 
  2514.  
  2515. foreach ( $aliases as $alias ) { 
  2516. if ( isset( $options[ $alias ] ) ) { 
  2517. $object[ $exclude_field ] = pods_trim( $options[ $alias ] ); 
  2518.  
  2519. unset( $options[ $alias ] ); 
  2520.  
  2521. if ( 'helper' == $object[ 'type' ] ) 
  2522. $object[ 'options' ][ 'helper_type' ] = $object[ 'helper_type' ]; 
  2523.  
  2524. if ( isset( $object[ 'options' ][ 'code' ] ) ) 
  2525. unset( $object[ 'options' ][ 'code' ] ); 
  2526.  
  2527. $object[ 'options' ] = array_merge( $object[ 'options' ], $options ); 
  2528.  
  2529. $post_data = array( 
  2530. 'post_name' => pods_clean_name( $object[ 'name' ], true),  
  2531. 'post_title' => $object[ 'name' ],  
  2532. 'post_content' => $object[ 'code' ],  
  2533. 'post_type' => '_pods_' . $object[ 'type' ],  
  2534. 'post_status' => 'publish' 
  2535. ); 
  2536.  
  2537. if ( !empty( $object[ 'id' ] ) ) 
  2538. $post_data[ 'ID' ] = $object[ 'id' ]; 
  2539.  
  2540. if ( null !== pods_var( 'status', $object, null, null, true ) ) 
  2541. $post_data[ 'post_status' ] = pods_var( 'status', $object, null, null, true ); 
  2542.  
  2543. remove_filter( 'content_save_pre', 'balanceTags', 50 ); 
  2544.  
  2545. $post_data = pods_sanitize( $post_data ); 
  2546.  
  2547. $params->id = $this->save_post( $post_data, $object[ 'options' ], true, true ); 
  2548.  
  2549. pods_transient_clear( 'pods_objects_' . $params->type ); 
  2550. pods_transient_clear( 'pods_objects_' . $params->type . '_get' ); 
  2551.  
  2552. return $params->id; 
  2553.  
  2554. /** 
  2555. * @see PodsAPI::save_object 
  2556. * Add or edit a Pod Template 
  2557. * $params['id'] int The template ID 
  2558. * $params['name'] string The template name 
  2559. * $params['code'] string The template code 
  2560. * @param array|object $params An associative array of parameters 
  2561. * @param bool $sanitized (optional) Decides wether the params have been sanitized before being passed, will sanitize them if false. 
  2562. * @return int The Template ID 
  2563. * @since 1.7.9 
  2564. */ 
  2565. public function save_template ( $params, $sanitized = false ) { 
  2566. $params = (object) $params; 
  2567.  
  2568. $params->type = 'template'; 
  2569.  
  2570. return $this->save_object( $params, $sanitized ); 
  2571.  
  2572. /** 
  2573. * @see PodsAPI::save_object 
  2574. * Add or edit a Pod Page 
  2575. * $params['id'] int The page ID 
  2576. * $params['name'] string The page URI 
  2577. * $params['code'] string The page code 
  2578. * @param array|object $params An associative array of parameters 
  2579. * @param bool $sanitized (optional) Decides wether the params have been sanitized before being passed, will sanitize them if false. 
  2580. * @return int The page ID 
  2581. * @since 1.7.9 
  2582. */ 
  2583. public function save_page ( $params, $sanitized = false ) { 
  2584. $params = (object) $params; 
  2585.  
  2586. if ( !isset( $params->name ) ) { 
  2587. $params->name = $params->uri; 
  2588. unset( $params->uri ); 
  2589.  
  2590. if ( isset( $params->phpcode ) ) { 
  2591. $params->code = $params->phpcode; 
  2592. unset( $params->phpcode ); 
  2593.  
  2594. $params->name = trim( $params->name, '/' ); 
  2595. $params->type = 'page'; 
  2596.  
  2597. return $this->save_object( $params, $sanitized ); 
  2598.  
  2599. /** 
  2600. * @see PodsAPI::save_object 
  2601. * Add or edit a Pod Helper 
  2602. * $params['id'] int The helper ID 
  2603. * $params['name'] string The helper name 
  2604. * $params['helper_type'] string The helper type ("pre_save", "display", etc) 
  2605. * $params['code'] string The helper code 
  2606. * @param array $params An associative array of parameters 
  2607. * @param bool $sanitized (optional) Decides wether the params have been sanitized before being passed, will sanitize them if false. 
  2608. * @return int The helper ID 
  2609. * @since 1.7.9 
  2610. */ 
  2611. public function save_helper ( $params, $sanitized = false ) { 
  2612. $params = (object) $params; 
  2613.  
  2614. if ( isset( $params->phpcode ) ) { 
  2615. $params->code = $params->phpcode; 
  2616. unset( $params->phpcode ); 
  2617.  
  2618. if ( isset( $params->type ) ) { 
  2619. $params->helper_type = $params->type; 
  2620. unset( $params->type ); 
  2621.  
  2622. $params->type = 'helper'; 
  2623.  
  2624. return $this->save_object( $params, $sanitized ); 
  2625.  
  2626. /** 
  2627. * Add or edit a single pod item 
  2628. * $params['pod'] string The Pod name (pod or pod_id is required) 
  2629. * $params['pod_id'] string The Pod ID (pod or pod_id is required) 
  2630. * $params['id'] int The item ID 
  2631. * $params['data'] array (optional) Associative array of field names + values 
  2632. * $params['bypass_helpers'] bool Set to true to bypass running pre-save and post-save helpers 
  2633. * $params['track_changed_fields'] bool Set to true to enable tracking of saved fields via PodsAPI::get_changed_fields() 
  2634. * @param array|object $params An associative array of parameters 
  2635. * @return int The item ID 
  2636. * @since 1.7.9 
  2637. */ 
  2638. public function save_pod_item ( $params ) { 
  2639.  
  2640. global $wpdb; 
  2641.  
  2642. $params = (object) pods_str_replace( '@wp_', '{prefix}', $params ); 
  2643.  
  2644. $tableless_field_types = PodsForm::tableless_field_types(); 
  2645. $repeatable_field_types = PodsForm::repeatable_field_types(); 
  2646. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  2647.  
  2648. // @deprecated 2.0 
  2649. if ( isset( $params->datatype ) ) { 
  2650. pods_deprecated( '$params->pod instead of $params->datatype', '2.0' ); 
  2651.  
  2652. $params->pod = $params->datatype; 
  2653.  
  2654. unset( $params->datatype ); 
  2655.  
  2656. if ( isset( $params->pod_id ) ) { 
  2657. pods_deprecated( '$params->id instead of $params->pod_id', '2.0' ); 
  2658.  
  2659. $params->id = $params->pod_id; 
  2660.  
  2661. unset( $params->pod_id ); 
  2662.  
  2663. if ( isset( $params->data ) && !empty( $params->data ) && is_array( $params->data ) ) { 
  2664. $check = current( $params->data ); 
  2665.  
  2666. if ( is_array( $check ) ) { 
  2667. pods_deprecated( 'PodsAPI::save_pod_items', '2.0' ); 
  2668.  
  2669. return $this->save_pod_items( $params, $params->data ); 
  2670.  
  2671. // @deprecated 2.0 
  2672. if ( isset( $params->tbl_row_id ) ) { 
  2673. pods_deprecated( '$params->id instead of $params->tbl_row_id', '2.0' ); 
  2674.  
  2675. $params->id = $params->tbl_row_id; 
  2676.  
  2677. unset( $params->tbl_row_id ); 
  2678.  
  2679. // @deprecated 2.0 
  2680. if ( isset( $params->columns ) ) { 
  2681. pods_deprecated( '$params->data instead of $params->columns', '2.0' ); 
  2682.  
  2683. $params->data = $params->columns; 
  2684.  
  2685. unset( $params->columns ); 
  2686.  
  2687. if ( !isset( $params->pod ) ) 
  2688. $params->pod = false; 
  2689. if ( isset( $params->pod_id ) ) 
  2690. $params->pod_id = pods_absint( $params->pod_id ); 
  2691. else 
  2692. $params->pod_id = 0; 
  2693.  
  2694. if ( isset( $params->id ) ) 
  2695. $params->id = pods_absint( $params->id ); 
  2696. else 
  2697. $params->id = 0; 
  2698.  
  2699. if ( !isset( $params->from ) ) 
  2700. $params->from = 'save'; 
  2701.  
  2702. if ( !isset( $params->location ) ) 
  2703. $params->location = null; 
  2704.  
  2705. if ( !isset( $params->track_changed_fields ) ) 
  2706. $params->track_changed_fields = false; 
  2707.  
  2708. /** 
  2709. * Override $params['track_changed_fields'] 
  2710. * Use for globally setting field change tracking. 
  2711. * @param bool 
  2712. * @since 2.3.19 
  2713. */ 
  2714. $track_changed_fields = apply_filters( 'pods_api_save_pod_item_track_changed_fields_' . $params->pod, (boolean) $params->track_changed_fields, $params ); 
  2715. $changed_fields = array(); 
  2716.  
  2717. if ( !isset( $params->clear_slug_cache ) ) { 
  2718. $params->clear_slug_cache = true; 
  2719.  
  2720. // Support for bulk edit 
  2721. if ( isset( $params->id ) && !empty( $params->id ) && is_array( $params->id ) ) { 
  2722. $ids = array(); 
  2723. $new_params = $params; 
  2724.  
  2725. foreach ( $params->id as $id ) { 
  2726. $new_params->id = $id; 
  2727.  
  2728. $ids[] = $this->save_pod_item( $new_params ); 
  2729.  
  2730. return $ids; 
  2731.  
  2732. // Allow Helpers to know what's going on, are we adding or saving? 
  2733. $is_new_item = false; 
  2734.  
  2735. if ( empty( $params->id ) ) 
  2736. $is_new_item = true; 
  2737.  
  2738. if ( isset( $params->is_new_item ) ) 
  2739. $is_new_item = (boolean) $params->is_new_item; 
  2740.  
  2741. // Allow Helpers to bypass subsequent helpers in recursive save_pod_item calls 
  2742. $bypass_helpers = false; 
  2743.  
  2744. if ( isset( $params->bypass_helpers ) && false !== $params->bypass_helpers ) 
  2745. $bypass_helpers = true; 
  2746.  
  2747. // Allow Custom Fields not defined by Pods to be saved 
  2748. $allow_custom_fields = false; 
  2749.  
  2750. if ( isset( $params->allow_custom_fields ) && false !== $params->allow_custom_fields ) 
  2751. $allow_custom_fields = true; 
  2752.  
  2753. // Get array of Pods 
  2754. $pod = $this->load_pod( array( 'id' => $params->pod_id, 'name' => $params->pod, 'table_info' => true ) ); 
  2755.  
  2756. if ( false === $pod ) 
  2757. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  2758.  
  2759. $params->pod = $pod[ 'name' ]; 
  2760. $params->pod_id = $pod[ 'id' ]; 
  2761.  
  2762. if ( 'settings' == $pod[ 'type' ] ) 
  2763. $params->id = $pod[ 'id' ]; 
  2764.  
  2765. $fields = $pod[ 'fields' ]; 
  2766.  
  2767. $object_fields = (array) pods_var_raw( 'object_fields', $pod, array(), null, true ); 
  2768.  
  2769. $fields_active = array(); 
  2770. $custom_data = array(); 
  2771.  
  2772. // Find the active fields (loop through $params->data to retain order) 
  2773. if ( !empty( $params->data ) && is_array( $params->data ) ) { 
  2774. $custom_fields = array(); 
  2775.  
  2776. foreach ( $params->data as $field => $value ) { 
  2777. if ( isset( $object_fields[ $field ] ) ) { 
  2778. $object_fields[ $field ][ 'value' ] = $value; 
  2779. $fields_active[] = $field; 
  2780. elseif ( isset( $fields[ $field ] ) ) { 
  2781. if ( 'save' == $params->from || true === PodsForm::permission( $fields[ $field ][ 'type' ], $field, $fields[ $field ], $fields, $pod, $params->id, $params ) ) { 
  2782. $fields[ $field ][ 'value' ] = $value; 
  2783. $fields_active[] = $field; 
  2784. elseif ( !pods_has_permissions( $fields[ $field ][ 'options' ] ) && pods_var( 'hidden', $fields[ $field ][ 'options' ], false ) ) { 
  2785. $fields[ $field ][ 'value' ] = $value; 
  2786. $fields_active[] = $field; 
  2787. else { 
  2788. $found = false; 
  2789.  
  2790. foreach ( $object_fields as $object_field => $object_field_opt ) { 
  2791. if ( in_array( $field, $object_field_opt[ 'alias' ] ) ) { 
  2792. $object_fields[ $object_field ][ 'value' ] = $value; 
  2793. $fields_active[] = $object_field; 
  2794.  
  2795. $found = true; 
  2796.  
  2797. break; 
  2798.  
  2799. if ( $allow_custom_fields && !$found ) 
  2800. $custom_fields[] = $field; 
  2801.  
  2802. if ( $allow_custom_fields && !empty( $custom_fields ) ) { 
  2803. foreach ( $custom_fields as $field ) { 
  2804. $custom_data[ $field ] = $params->data[ $field ]; 
  2805.  
  2806. unset( $params->data ); 
  2807.  
  2808. if ( empty( $params->id ) && !in_array( 'created', $fields_active ) && isset( $fields[ 'created' ] ) && in_array( $fields[ 'created' ][ 'type' ], array( 'date', 'datetime' ) ) ) { 
  2809. $fields[ 'created' ][ 'value' ] = current_time( 'mysql' ); 
  2810. $fields_active[] = 'created'; 
  2811.  
  2812. if ( !in_array( 'modified', $fields_active ) && isset( $fields[ 'modified' ] ) && in_array( $fields[ 'modified' ][ 'type' ], array( 'date', 'datetime' ) ) ) { 
  2813. $fields[ 'modified' ][ 'value' ] = current_time( 'mysql' ); 
  2814. $fields_active[] = 'modified'; 
  2815.  
  2816. if ( in_array( $pod[ 'type' ], array( 'pod', 'table' ) ) && empty( $params->id ) && !empty( $pod[ 'pod_field_index' ] ) && in_array( $pod[ 'pod_field_index' ], $fields_active ) && !in_array( $pod[ 'pod_field_slug' ], $fields_active ) && isset( $fields[ $pod[ 'pod_field_slug' ] ] ) ) { 
  2817. $fields[ $pod[ 'pod_field_slug' ] ][ 'value' ] = ''; // this will get picked up by slug pre_save method 
  2818. $fields_active[] = $pod[ 'pod_field_slug' ]; 
  2819.  
  2820. // Handle hidden fields 
  2821. if ( empty( $params->id ) ) { 
  2822. foreach ( $fields as $field => $field_data ) { 
  2823. if ( in_array( $field, $fields_active ) ) 
  2824. continue; 
  2825.  
  2826. if ( in_array( $params->from, array( 'save', 'process_form' ) ) || true === PodsForm::permission( $fields[ $field ][ 'type' ], $field, $fields[ $field ], $fields, $pod, $params->id, $params ) ) { 
  2827. $value = PodsForm::default_value( pods_var_raw( $field, 'post' ), $field_data[ 'type' ], $field, pods_var_raw( 'options', $field_data, $field_data, null, true ), $pod, $params->id ); 
  2828.  
  2829. if ( null !== $value && '' !== $value && false !== $value ) { 
  2830. $fields[ $field ][ 'value' ] = $value; 
  2831. $fields_active[] = $field; 
  2832.  
  2833. // Set default field values for object fields 
  2834. if ( !empty( $object_fields ) ) { 
  2835. foreach ( $object_fields as $field => $field_data ) { 
  2836. if ( in_array( $field, $fields_active ) ) { 
  2837. continue; 
  2838. elseif ( !isset( $field_data[ 'default' ] ) || strlen( $field_data[ 'default' ] ) < 1 ) { 
  2839. continue; 
  2840.  
  2841. $value = PodsForm::default_value( pods_var_raw( $field, 'post' ), $field_data[ 'type' ], $field, pods_var_raw( 'options', $field_data, $field_data, null, true ), $pod, $params->id ); 
  2842.  
  2843. if ( null !== $value && '' !== $value && false !== $value ) { 
  2844. $object_fields[ $field ][ 'value' ] = $value; 
  2845. $fields_active[] = $field; 
  2846.  
  2847. // Set default field values for Pod fields 
  2848. foreach ( $fields as $field => $field_data ) { 
  2849. if ( in_array( $field, $fields_active ) ) { 
  2850. continue; 
  2851. elseif ( !isset( $field_data[ 'default' ] ) || strlen( $field_data[ 'default' ] ) < 1 ) { 
  2852. continue; 
  2853.  
  2854. $value = PodsForm::default_value( pods_var_raw( $field, 'post' ), $field_data[ 'type' ], $field, pods_var_raw( 'options', $field_data, $field_data, null, true ), $pod, $params->id ); 
  2855.  
  2856. if ( null !== $value && '' !== $value && false !== $value ) { 
  2857. $fields[ $field ][ 'value' ] = $value; 
  2858. $fields_active[] = $field; 
  2859.  
  2860. $columns =& $fields; // @deprecated 2.0 
  2861. $active_columns =& $fields_active; // @deprecated 2.0 
  2862. $params->tbl_row_id =& $params->id; // @deprecated 2.0 
  2863.  
  2864. $pre_save_helpers = $post_save_helpers = array(); 
  2865.  
  2866. $pieces = array( 
  2867. 'fields',  
  2868. 'params',  
  2869. 'pod',  
  2870. 'fields_active',  
  2871. 'object_fields',  
  2872. 'custom_fields',  
  2873. 'custom_data',  
  2874. 'track_changed_fields',  
  2875. 'changed_fields' 
  2876. ); 
  2877.  
  2878. if ( false === $bypass_helpers ) { 
  2879. // Plugin hooks 
  2880. $hooked = $this->do_hook( 'pre_save_pod_item', compact( $pieces ), $is_new_item, $params->id ); 
  2881.  
  2882. if ( is_array( $hooked ) && !empty( $hooked ) ) 
  2883. extract( $hooked ); 
  2884.  
  2885. $hooked = $this->do_hook( "pre_save_pod_item_{$params->pod}", compact( $pieces ), $is_new_item, $params->id ); 
  2886.  
  2887. if ( is_array( $hooked ) && !empty( $hooked ) ) 
  2888. extract( $hooked ); 
  2889.  
  2890. if ( $is_new_item ) { 
  2891. $hooked = $this->do_hook( 'pre_create_pod_item', compact( $pieces ) ); 
  2892.  
  2893. if ( is_array( $hooked ) && !empty( $hooked ) ) 
  2894. extract( $hooked ); 
  2895.  
  2896. $hooked = $this->do_hook( "pre_create_pod_item_{$params->pod}", compact( $pieces ) ); 
  2897.  
  2898. if ( is_array( $hooked ) && !empty( $hooked ) ) 
  2899. extract( $hooked ); 
  2900. else { 
  2901. $hooked = $this->do_hook( 'pre_edit_pod_item', compact( $pieces ), $params->id ); 
  2902.  
  2903. if ( is_array( $hooked ) && !empty( $hooked ) ) 
  2904. extract( $hooked ); 
  2905.  
  2906. $hooked = $this->do_hook( "pre_edit_pod_item_{$params->pod}", compact( $pieces ), $params->id ); 
  2907.  
  2908. if ( is_array( $hooked ) && !empty( $hooked ) ) 
  2909. extract( $hooked ); 
  2910.  
  2911. // Call any pre-save helpers (if not bypassed) 
  2912. if ( !defined( 'PODS_DISABLE_EVAL' ) || !PODS_DISABLE_EVAL ) { 
  2913. if ( !empty( $pod[ 'options' ] ) && is_array( $pod[ 'options' ] ) ) { 
  2914. $helpers = array( 'pre_save_helpers', 'post_save_helpers' ); 
  2915.  
  2916. foreach ( $helpers as $helper ) { 
  2917. if ( isset( $pod[ 'options' ][ $helper ] ) && !empty( $pod[ 'options' ][ $helper ] ) ) 
  2918. ${$helper} = explode( ', ', $pod[ 'options' ][ $helper ] ); 
  2919.  
  2920. if ( !empty( $pre_save_helpers ) ) { 
  2921. pods_deprecated( sprintf( __( 'Pre-save helpers are deprecated, use the action pods_pre_save_pod_item_%s instead', 'pods' ), $params->pod ), '2.0' ); 
  2922.  
  2923. foreach ( $pre_save_helpers as $helper ) { 
  2924. $helper = $this->load_helper( array( 'name' => $helper ) ); 
  2925.  
  2926. if ( false !== $helper ) 
  2927. eval( '?>' . $helper[ 'code' ] ); 
  2928.  
  2929. if ( $track_changed_fields ) { 
  2930. $changed_fields = $this->get_changed_fields( compact( $pieces ) ); 
  2931.  
  2932. $table_data = $table_formats = $update_values = $rel_fields = $rel_field_ids = array(); 
  2933.  
  2934. $object_type = $pod[ 'type' ]; 
  2935.  
  2936. $object_ID = 'ID'; 
  2937.  
  2938. if ( 'comment' == $object_type ) 
  2939. $object_ID = 'comment_ID'; 
  2940. elseif ( 'taxonomy' == $object_type ) 
  2941. $object_ID = 'term_id'; 
  2942.  
  2943. $object_data = $object_meta = $post_term_data = array(); 
  2944.  
  2945. if ( 'settings' == $object_type ) 
  2946. $object_data[ 'option_id' ] = $pod[ 'name' ]; 
  2947. elseif ( !empty( $params->id ) ) 
  2948. $object_data[ $object_ID ] = $params->id; 
  2949.  
  2950. $fields_active = array_unique( $fields_active ); 
  2951.  
  2952. // Loop through each active field, validating and preparing the table data 
  2953. foreach ( $fields_active as $field ) { 
  2954. if ( isset( $object_fields[ $field ] ) ) 
  2955. $field_data = $object_fields[ $field ]; 
  2956. elseif ( isset( $fields[ $field ] ) ) 
  2957. $field_data = $fields[ $field ]; 
  2958. else 
  2959. continue; 
  2960.  
  2961. $value = $field_data[ 'value' ]; 
  2962. $type = $field_data[ 'type' ]; 
  2963. $options = pods_var( 'options', $field_data, array() ); 
  2964.  
  2965. // WPML AJAX compatibility 
  2966. if ( is_admin() && isset( $_GET[ 'page' ] ) && false !== strpos( $_GET[ 'page' ], '/menu/languages.php' ) && isset( $_POST[ 'icl_ajx_action' ] ) && isset( $_POST[ '_icl_nonce' ] ) && wp_verify_nonce( $_POST[ '_icl_nonce' ], $_POST[ 'icl_ajx_action' ] . '_nonce' ) ) 
  2967. $options[ 'unique' ] = $fields[ $field ][ 'options' ][ 'unique' ] = $options[ 'required' ] = $fields[ $field ][ 'options' ][ 'required' ] = 0; 
  2968. else { 
  2969. // Validate value 
  2970. $validate = $this->handle_field_validation( $value, $field, $object_fields, $fields, $pod, $params ); 
  2971.  
  2972. if ( false === $validate ) 
  2973. $validate = sprintf( __( 'There was an issue validating the field %s', 'pods' ), $field_data[ 'label' ] ); 
  2974. elseif ( true !== $validate ) 
  2975. $validate = (array) $validate; 
  2976.  
  2977. if ( !is_bool( $validate ) && !empty( $validate ) ) 
  2978. return pods_error( $validate, $this ); 
  2979.  
  2980. $value = PodsForm::pre_save( $field_data[ 'type' ], $value, $params->id, $field, array_merge( $field_data, $options ), array_merge( $fields, $object_fields ), $pod, $params ); 
  2981.  
  2982. $field_data[ 'value' ] = $value; 
  2983.  
  2984. if ( isset( $object_fields[ $field ] ) ) { 
  2985. if ( 'taxonomy' == $object_fields[ $field ][ 'type' ] ) { 
  2986. $post_term_data[ $field ] = $value; 
  2987. else { 
  2988. $object_data[ $field ] = $value; 
  2989. else { 
  2990. $simple = ( 'pick' == $type && in_array( pods_var( 'pick_object', $field_data ), $simple_tableless_objects ) ); 
  2991. $simple = (boolean) $this->do_hook( 'tableless_custom', $simple, $field_data, $field, $fields, $pod, $params ); 
  2992.  
  2993. // Handle Simple Relationships 
  2994. if ( $simple ) { 
  2995. if ( !is_array( $value ) ) 
  2996. $value = explode( ', ', $value ); 
  2997.  
  2998. $pick_limit = (int) pods_var_raw( 'pick_limit', $options, 0 ); 
  2999.  
  3000. if ( 'single' == pods_var_raw( 'pick_format_type', $options ) ) 
  3001. $pick_limit = 1; 
  3002.  
  3003. if ( 'custom-simple' == pods_var( 'pick_object', $field_data ) ) { 
  3004. $custom = pods_var_raw( 'pick_custom', $options, '' ); 
  3005.  
  3006. $custom = apply_filters( 'pods_form_ui_field_pick_custom_values', $custom, $field_data[ 'name' ], $value, array_merge( $field_data, $options ), $pod, $params->id ); 
  3007.  
  3008. if ( empty( $value ) || empty( $custom ) ) 
  3009. $value = ''; 
  3010. elseif ( !empty( $custom ) ) { 
  3011. if ( !is_array( $custom ) ) { 
  3012. $custom = explode( "\n", $custom ); 
  3013.  
  3014. $custom_values = array(); 
  3015.  
  3016. foreach ( $custom as $c => $cv ) { 
  3017. if ( 0 < strlen( $cv ) ) { 
  3018. $custom_label = explode( '|', $cv ); 
  3019.  
  3020. if ( !isset( $custom_label[ 1 ] ) ) 
  3021. $custom_label[ 1 ] = $custom_label[ 0 ]; 
  3022.  
  3023. $custom_label[ 0 ] = trim( (string) $custom_label[ 0 ] ); 
  3024. $custom_label[ 1 ] = trim( (string) $custom_label[ 1 ] ); 
  3025. $custom_values[ $custom_label[ 0 ] ] = $custom_label[ 1 ]; 
  3026. else 
  3027. $custom_values = $custom; 
  3028.  
  3029. $values = array(); 
  3030.  
  3031. foreach ( $value as $k => $v ) { 
  3032. $v = pods_unsanitize( $v ); 
  3033.  
  3034. if ( isset( $custom_values[ $v ] ) ) 
  3035. $values[ $k ] = $v; 
  3036.  
  3037. $value = $values; 
  3038.  
  3039. if ( 0 < $pick_limit && !empty( $value ) ) 
  3040. $value = array_slice( $value, 0, $pick_limit ); 
  3041.  
  3042. // Don't save an empty array, just make it an empty string 
  3043. if ( empty( $value ) ) 
  3044. $value = ''; 
  3045. elseif ( is_array( $value ) ) { 
  3046. // If there's just one item, don't save as an array, save the string 
  3047. if ( 1 == $pick_limit || 1 == count( $value ) ) 
  3048. $value = implode( '', $value ); 
  3049. // If storage is set to table, json encode, otherwise WP will serialize automatically 
  3050. elseif ( 'table' == pods_var( 'storage', $pod ) ) 
  3051. $value = version_compare( PHP_VERSION, '5.4.0', '>=' ) ? json_encode( $value, JSON_UNESCAPED_UNICODE ) : json_encode( $value ); 
  3052.  
  3053. // Prepare all table / meta data 
  3054. if ( !in_array( $type, $tableless_field_types ) || $simple ) { 
  3055. if ( in_array( $type, $repeatable_field_types ) && 1 == pods_var( $type . '_repeatable', $field_data, 0 ) ) { 
  3056. // Don't save an empty array, just make it an empty string 
  3057. if ( empty( $value ) ) 
  3058. $value = ''; 
  3059. elseif ( is_array( $value ) ) { 
  3060. // If there's just one item, don't save as an array, save the string 
  3061. if ( 1 == count( $value ) ) 
  3062. $value = implode( '', $value ); 
  3063. // If storage is set to table, json encode, otherwise WP will serialize automatically 
  3064. elseif ( 'table' == pods_var( 'storage', $pod ) ) 
  3065. $value = version_compare( PHP_VERSION, '5.4.0', '>=' ) ? json_encode( $value, JSON_UNESCAPED_UNICODE ) : json_encode( $value ); 
  3066.  
  3067. $table_data[ $field ] = str_replace( array( '{prefix}', '@wp_' ), array( '{/prefix/}', '{prefix}' ), $value ); // Fix for pods_query 
  3068. $table_formats[] = PodsForm::prepare( $type, $options ); 
  3069.  
  3070. $object_meta[ $field ] = $value; 
  3071. // Store relational field data to be looped through later 
  3072. else { 
  3073. // Convert values from a comma-separated string into an array 
  3074. if ( !is_array( $value ) ) 
  3075. $value = explode( ', ', $value ); 
  3076.  
  3077. $rel_fields[ $type ][ $field ] = $value; 
  3078. $rel_field_ids[] = $field_data[ 'id' ]; 
  3079.  
  3080. if ( in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) ) { 
  3081. $object_name = $pod[ 'name' ]; 
  3082.  
  3083. if ( !empty( $pod[ 'object' ] ) ) 
  3084. $object_name = $pod[ 'object' ]; 
  3085.  
  3086. $object_name_field = 'post_type'; 
  3087.  
  3088. if ( 'taxonomy' == $pod['type'] ) { 
  3089. $object_name_field = 'taxonomy'; 
  3090.  
  3091. $object_data[ $object_name_field ] = $object_name; 
  3092.  
  3093. if ( ( 'meta' == $pod[ 'storage' ] || 'settings' == $pod[ 'type' ] || ( 'taxonomy' == $pod[ 'type' ] && 'none' == $pod[ 'storage' ] ) ) && !in_array( $pod[ 'type' ], array( 'pod', 'table', '' ) ) ) { 
  3094. if ( $allow_custom_fields && !empty( $custom_data ) ) 
  3095. $object_meta = array_merge( $custom_data, $object_meta ); 
  3096.  
  3097. $fields_to_send = array_flip( array_keys( $object_meta ) ); 
  3098.  
  3099. foreach ( $fields_to_send as $field => $field_data ) { 
  3100. if ( isset( $object_fields[ $field ] ) ) { 
  3101. $field_data = $object_fields[ $field ]; 
  3102. elseif ( isset( $fields[ $field ] ) ) { 
  3103. $field_data = $fields[ $field ]; 
  3104. else { 
  3105. unset( $fields_to_send[ $field ] ); 
  3106.  
  3107. $fields_to_send[ $field ] = $field_data; 
  3108.  
  3109. $params->id = $this->save_wp_object( $object_type, $object_data, $object_meta, false, true, $fields_to_send ); 
  3110.  
  3111. if ( !empty( $params->id ) && 'settings' == $object_type ) 
  3112. $params->id = $pod[ 'id' ]; 
  3113. else { 
  3114. if ( ! in_array( $pod[ 'type' ], array( 'pod', 'table', '' ) ) ) { 
  3115. $params->id = $this->save_wp_object( $object_type, $object_data, array(), false, true ); 
  3116.  
  3117. if ( 'table' == $pod[ 'storage' ] ) { 
  3118. // Every row should have an id set here, otherwise Pods with nothing 
  3119. // but relationship fields won't get properly ID'd 
  3120. if ( empty( $params->id ) ) 
  3121. $params->id = 0; 
  3122.  
  3123. $table_data = array( 'id' => $params->id ) + $table_data; 
  3124. array_unshift( $table_formats, '%d' ); 
  3125.  
  3126. if ( !empty( $table_data ) ) { 
  3127. $sql = pods_data()->insert_on_duplicate( "@wp_pods_{$params->pod}", $table_data, $table_formats ); 
  3128.  
  3129. $id = pods_query( $sql, 'Cannot add/save table row' ); 
  3130.  
  3131. if ( empty( $params->id ) ) 
  3132. $params->id = $id; 
  3133.  
  3134. $params->id = (int) $params->id; 
  3135.  
  3136. // Save terms for taxonomies associated to a post type 
  3137. if ( 0 < $params->id && 'post_type' == $pod[ 'type' ] && !empty( $post_term_data ) ) { 
  3138. foreach ( $post_term_data as $post_taxonomy => $post_terms ) { 
  3139. $post_terms = (array) $post_terms; 
  3140.  
  3141. foreach ( $post_terms as $k => $v ) { 
  3142. if ( ! preg_match( '/[^0-9]/', $v ) ) { 
  3143. $v = (int) $v; 
  3144.  
  3145. $post_terms[ $k ] = $v; 
  3146.  
  3147. wp_set_object_terms( $params->id, $post_terms, $post_taxonomy ); 
  3148.  
  3149. $no_conflict = pods_no_conflict_check( $pod[ 'type' ] ); 
  3150.  
  3151. if ( !$no_conflict ) 
  3152. pods_no_conflict_on( $pod[ 'type' ] ); 
  3153.  
  3154. // Save relationship / file data 
  3155. if ( !empty( $rel_fields ) ) { 
  3156. foreach ( $rel_fields as $type => $data ) { 
  3157. // Only handle tableless fields 
  3158. if ( !in_array( $type, $tableless_field_types ) ) { 
  3159. continue; 
  3160.  
  3161. foreach ( $data as $field => $values ) { 
  3162. $pick_val = pods_var( 'pick_val', $fields[ $field ] ); 
  3163.  
  3164. if ( 'table' == pods_var( 'pick_object', $fields[ $field ] ) ) { 
  3165. $pick_val = pods_var( 'pick_table', $fields[ $field ][ 'options' ], $pick_val, null, true ); 
  3166.  
  3167. if ( '__current__' == $pick_val ) { 
  3168. if ( is_object( $pod ) ) { 
  3169. $pick_val = $pod->pod; 
  3170. elseif ( is_array( $pod ) ) { 
  3171. $pick_val = $pod[ 'name' ]; 
  3172. elseif ( 0 < strlen( $pod ) ) { 
  3173. $pick_val = $pod; 
  3174.  
  3175. $fields[ $field ][ 'options' ][ 'table_info' ] = pods_api()->get_table_info( pods_var( 'pick_object', $fields[ $field ] ), $pick_val, null, null, $fields[ $field ][ 'options' ] ); 
  3176.  
  3177. if ( isset( $fields[ $field ][ 'options' ][ 'table_info' ][ 'pod' ] ) && !empty( $fields[ $field ][ 'options' ][ 'table_info' ][ 'pod' ] ) && isset( $fields[ $field ][ 'options' ][ 'table_info' ][ 'pod' ][ 'name' ] ) ) { 
  3178. $search_data = pods( $fields[ $field ][ 'options' ][ 'table_info' ][ 'pod' ][ 'name' ] ); 
  3179.  
  3180. $data_mode = 'pods'; 
  3181. else { 
  3182. $search_data = pods_data(); 
  3183. $search_data->table( $fields[ $field ][ 'options' ][ 'table_info' ] ); 
  3184.  
  3185. $data_mode = 'data'; 
  3186.  
  3187. $find_rel_params = array( 
  3188. 'select' => "`t`.`{$search_data->field_id}`",  
  3189. 'where' => "`t`.`{$search_data->field_slug}` = %s OR `t`.`{$search_data->field_index}` = %s",  
  3190. 'limit' => 1,  
  3191. 'pagination' => false,  
  3192. 'search' => false 
  3193. ); 
  3194.  
  3195. if ( empty( $search_data->field_slug ) && !empty( $search_data->field_index ) ) { 
  3196. $find_rel_params[ 'where' ] = "`t`.`{$search_data->field_index}` = %s"; 
  3197. elseif ( empty( $search_data->field_slug ) && empty( $search_data->field_index ) ) { 
  3198. $find_rel_params = false; 
  3199.  
  3200. $related_limit = (int) pods_var_raw( $type . '_limit', $fields[ $field ][ 'options' ], 0 ); 
  3201.  
  3202. if ( 'single' == pods_var_raw( $type . '_format_type', $fields[ $field ][ 'options' ] ) ) { 
  3203. $related_limit = 1; 
  3204.  
  3205. // Enforce integers / unique values for IDs 
  3206. $value_ids = array(); 
  3207.  
  3208. $is_file_field = in_array( $type, PodsForm::file_field_types() ); 
  3209. $is_taggable = ( in_array( $type, PodsForm::tableless_field_types() ) && 1 == pods_v( $type . '_taggable', $fields[ $field ][ 'options' ] ) ); 
  3210.  
  3211. // @todo Handle simple relationships eventually 
  3212. foreach ( $values as $v ) { 
  3213. if ( !empty( $v ) ) { 
  3214. if ( !is_array( $v ) ) { 
  3215. if ( !preg_match( '/[^0-9]/', $v ) ) { 
  3216. $v = (int) $v; 
  3217. // File handling 
  3218. elseif ( $is_file_field ) { 
  3219. // Get ID from GUID 
  3220. $v = pods_image_id_from_field( $v ); 
  3221.  
  3222. // If file not found, add it 
  3223. if ( empty( $v ) ) { 
  3224. $v = pods_attachment_import( $v ); 
  3225. // Reference by slug 
  3226. else { 
  3227. $v_data = false; 
  3228.  
  3229. if ( false !== $find_rel_params ) { 
  3230. $rel_params = $find_rel_params; 
  3231. $rel_params[ 'where' ] = $wpdb->prepare( $rel_params[ 'where' ], array( $v, $v ) ); 
  3232.  
  3233. $search_data->select( $rel_params ); 
  3234.  
  3235. $v_data = $search_data->fetch( $v ); 
  3236.  
  3237. if ( !empty( $v_data ) && isset( $v_data[ $search_data->field_id ] ) ) { 
  3238. $v = (int) $v_data[ $search_data->field_id ]; 
  3239. // Allow tagging for Pods objects 
  3240. elseif ( $is_taggable && 'pods' == $data_mode ) { 
  3241. $tag_data = array( 
  3242. $search_data->field_index => $v 
  3243. ); 
  3244.  
  3245. if ( 'post_type' == $search_data->pod_data[ 'type' ] ) { 
  3246. $tag_data[ 'post_status' ] = 'publish'; 
  3247.  
  3248. /** 
  3249. * Filter for changing tag before adding new item. 
  3250. * @param array $tag_data Fields for creating new item. 
  3251. * @param int $v Field ID of tag. 
  3252. * @param obj $search_data Search object for tag. 
  3253. * @param string $field Table info for field. 
  3254. * @param array $pieces Field array. 
  3255. * @since 2.3.19 
  3256. */ 
  3257. $tag_data = apply_filters( 'pods_api_save_pod_item_taggable_data', $tag_data, $v, $search_data, $field, compact( $pieces ) ); 
  3258.  
  3259. // Save $v to a new item on related object 
  3260. $v = $search_data->add( $tag_data ); 
  3261.  
  3262. // @todo Support non-Pods for tagging 
  3263. elseif ( $is_file_field && isset( $v[ 'id' ] ) ) { 
  3264. $v = (int) $v[ 'id' ]; 
  3265. else { 
  3266. continue; 
  3267.  
  3268. if ( !empty( $v ) && !in_array( $v, $value_ids ) ) { 
  3269. $value_ids[] = $v; 
  3270.  
  3271. $value_ids = array_unique( array_filter( $value_ids ) ); 
  3272.  
  3273. // Limit values 
  3274. if ( 0 < $related_limit && !empty( $value_ids ) ) 
  3275. $value_ids = array_slice( $value_ids, 0, $related_limit ); 
  3276.  
  3277. // Get current values 
  3278. if ( 'pick' == $type && isset( PodsField_Pick::$related_data[ $fields[ $field ][ 'id' ] ] ) && isset( PodsField_Pick::$related_data[ $fields[ $field ][ 'id' ] ][ 'current_ids' ] ) ) 
  3279. $related_ids = PodsField_Pick::$related_data[ $fields[ $field ][ 'id' ] ][ 'current_ids' ]; 
  3280. else 
  3281. $related_ids = $this->lookup_related_items( $fields[ $field ][ 'id' ], $pod[ 'id' ], $params->id, $fields[ $field ], $pod ); 
  3282.  
  3283. // Get ids to remove 
  3284. $remove_ids = array_diff( $related_ids, $value_ids ); 
  3285.  
  3286. // Delete relationships 
  3287. if ( !empty( $remove_ids ) ) 
  3288. $this->delete_relationships( $params->id, $remove_ids, $pod, $fields[ $field ] ); 
  3289.  
  3290. // Save relationships 
  3291. if ( !empty( $value_ids ) ) 
  3292. $this->save_relationships( $params->id, $value_ids, $pod, $fields[ $field ] ); 
  3293.  
  3294. // Run save function for field type (where needed) 
  3295. PodsForm::save( $type, $values, $params->id, $field, array_merge( $fields[ $field ], $fields[ $field ][ 'options' ] ), array_merge( $fields, $object_fields ), $pod, $params ); 
  3296.  
  3297. // Unset data no longer needed 
  3298. if ( 'pick' == $type ) { 
  3299. foreach ( $data as $field => $values ) { 
  3300. if ( isset( PodsField_Pick::$related_data[ $fields[ $field ][ 'id' ] ] ) ) { 
  3301. unset( PodsField_Pick::$related_data[ PodsField_Pick::$related_data[ $fields[ $field ][ 'id' ] ][ 'related_field' ][ 'id' ] ] ); 
  3302. unset( PodsField_Pick::$related_data[ $fields[ $field ][ 'id' ] ] ); 
  3303.  
  3304. if ( !$no_conflict ) 
  3305. pods_no_conflict_off( $pod[ 'type' ] ); 
  3306.  
  3307. if ( false === $bypass_helpers ) { 
  3308. $pieces = compact( $pieces ); 
  3309.  
  3310. // Plugin hooks 
  3311. $this->do_hook( 'post_save_pod_item', $pieces, $is_new_item, $params->id ); 
  3312. $this->do_hook( "post_save_pod_item_{$params->pod}", $pieces, $is_new_item, $params->id ); 
  3313.  
  3314. if ( $is_new_item ) { 
  3315. $this->do_hook( 'post_create_pod_item', $pieces, $params->id ); 
  3316. $this->do_hook( "post_create_pod_item_{$params->pod}", $pieces, $params->id ); 
  3317. else { 
  3318. $this->do_hook( 'post_edit_pod_item', $pieces, $params->id ); 
  3319. $this->do_hook( "post_edit_pod_item_{$params->pod}", $pieces, $params->id ); 
  3320.  
  3321. // Call any post-save helpers (if not bypassed) 
  3322. if ( !defined( 'PODS_DISABLE_EVAL' ) || !PODS_DISABLE_EVAL ) { 
  3323. if ( !empty( $post_save_helpers ) ) { 
  3324. pods_deprecated( sprintf( __( 'Post-save helpers are deprecated, use the action pods_post_save_pod_item_%s instead', 'pods' ), $params->pod ), '2.0' ); 
  3325.  
  3326. foreach ( $post_save_helpers as $helper ) { 
  3327. $helper = $this->load_helper( array( 'name' => $helper ) ); 
  3328.  
  3329. if ( false !== $helper && ( !defined( 'PODS_DISABLE_EVAL' ) || !PODS_DISABLE_EVAL ) ) 
  3330. eval( '?>' . $helper[ 'code' ] ); 
  3331.  
  3332. // Clear cache 
  3333. pods_cache_clear( $params->id, 'pods_items_' . $pod[ 'name' ] ); 
  3334.  
  3335. if ( $params->clear_slug_cache && !empty( $pod[ 'field_slug' ] ) ) { 
  3336. $slug = pods( $pod[ 'name' ], $params->id )->field( $pod[ 'field_slug' ] ); 
  3337.  
  3338. if ( 0 < strlen( $slug ) ) { 
  3339. pods_cache_clear( $slug, 'pods_items_' . $pod[ 'name' ] ); 
  3340.  
  3341. // Clear WP meta cache 
  3342. if ( in_array( $pod[ 'type' ], array( 'post_type', 'media', 'taxonomy', 'user', 'comment' ) ) ) { 
  3343. $meta_type = $pod[ 'type' ]; 
  3344.  
  3345. if ( 'post_type' == $meta_type ) 
  3346. $meta_type = 'post'; 
  3347.  
  3348. wp_cache_delete( $params->id, $meta_type . '_meta' ); 
  3349. wp_cache_delete( $params->id, 'pods_' . $meta_type . '_meta' ); 
  3350.  
  3351. // Success! Return the id 
  3352. return $params->id; 
  3353.  
  3354.  
  3355. /** 
  3356. * @see PodsAPI::save_pod_item 
  3357. * Add multiple pod items 
  3358. * $params['pod'] string The Pod name (pod or pod_id is required) 
  3359. * $params['pod_id'] string The Pod ID (pod or pod_id is required) 
  3360. * $params['bypass_helpers'] bool Set to true to bypass running pre-save and post-save helpers 
  3361. * $data['id'] int The item ID (optional) 
  3362. * $data['data'] array An associative array of field names + values 
  3363. * @param array|object $params An associative array of parameters, data excluded 
  3364. * @param array $data An associative array of pod ids and field names + values (arrays of field data) 
  3365. * @return int The item ID 
  3366. * @since 2.0 
  3367. */ 
  3368. public function save_pod_items ( $params, $data ) { 
  3369. $params = (object) $params; 
  3370.  
  3371. $ids = array(); 
  3372.  
  3373. foreach ( $data as $fields ) { 
  3374. $params->data = $fields; 
  3375.  
  3376. if ( isset( $fields[ 'id' ] ) && isset( $fields[ 'data' ] ) ) { 
  3377. $params->id = $fields[ 'id' ]; 
  3378. $params->data = $fields[ 'data' ]; 
  3379.  
  3380. $ids[] = $this->save_pod_item( $params ); 
  3381.  
  3382. return $ids; 
  3383.  
  3384. /** 
  3385. * Get the fields that have changed during a save 
  3386. * @param array $pieces Pieces array from save_pod_item 
  3387. * @return array Array of fields and values that have changed 
  3388. */ 
  3389. public function get_changed_fields( $pieces ) { 
  3390.  
  3391. $fields = $pieces[ 'fields' ]; 
  3392. $fields_active = $pieces[ 'fields_active' ]; 
  3393.  
  3394. $fields_changed = array(); 
  3395.  
  3396. if ( 0 < $pieces[ 'params' ]->id ) { 
  3397. $pod = pods( $pieces[ 'params' ]->pod, $pieces[ 'params' ]->id ); 
  3398.  
  3399. foreach ( $fields_active as $field ) { 
  3400. if ( isset( $fields[ $field ] ) && $pod->raw( $field ) != $fields[ $field ][ 'value' ] ) { 
  3401. $fields_changed[ $field ] = $fields[ $field ][ 'value' ]; 
  3402.  
  3403. return $fields_changed; 
  3404.  
  3405.  
  3406. /** 
  3407. * Save relationships 
  3408. * @param int $id ID of item 
  3409. * @param int|array $related_id ID or IDs to save 
  3410. * @param array $pod Pod data 
  3411. * @param array $field Field data 
  3412. */ 
  3413. public function save_relationships ( $id, $related_ids, $pod, $field ) { 
  3414. // Get current values 
  3415. if ( 'pick' == $field[ 'type' ] && isset( PodsField_Pick::$related_data[ $field[ 'id' ] ] ) && isset( PodsField_Pick::$related_data[ $field[ 'id' ] ][ 'current_ids' ] ) ) 
  3416. $current_ids = PodsField_Pick::$related_data[ $field[ 'id' ] ][ 'current_ids' ]; 
  3417. else 
  3418. $current_ids = $this->lookup_related_items( $field[ 'id' ], $pod[ 'id' ], $id, $field, $pod ); 
  3419.  
  3420. if ( !is_array( $related_ids ) ) 
  3421. $related_ids = implode( ', ', $related_ids ); 
  3422.  
  3423. foreach ( $related_ids as $k => $related_id ) { 
  3424. $related_ids[ $k ] = (int) $related_id; 
  3425.  
  3426. $related_ids = array_unique( array_filter( $related_ids ) ); 
  3427.  
  3428. $related_limit = (int) pods_var_raw( $field[ 'type' ] . '_limit', $field[ 'options' ], 0 ); 
  3429.  
  3430. if ( 'single' == pods_var_raw( $field[ 'type' ] . '_format_type', $field[ 'options' ] ) ) 
  3431. $related_limit = 1; 
  3432.  
  3433. // Limit values 
  3434. if ( 0 < $related_limit && !empty( $related_ids ) ) 
  3435. $related_ids = array_slice( $related_ids, 0, $related_limit ); 
  3436.  
  3437. // Post Types, Media, Users, and Comments (meta-based) 
  3438. if ( in_array( $pod[ 'type' ], array( 'post_type', 'media', 'taxonomy', 'user', 'comment' ) ) ) { 
  3439. $object_type = $pod[ 'type' ]; 
  3440.  
  3441. if ( in_array( $object_type, array( 'post_type', 'media' ) ) ) 
  3442. $object_type = 'post'; 
  3443. elseif ( 'taxonomy' == $object_type ) 
  3444. $object_type = 'term'; 
  3445.  
  3446. delete_metadata( $object_type, $id, $field[ 'name' ] ); 
  3447.  
  3448. if ( !empty( $related_ids ) ) { 
  3449. update_metadata( $object_type, $id, '_pods_' . $field[ 'name' ], $related_ids ); 
  3450.  
  3451. foreach ( $related_ids as $related_id ) { 
  3452. add_metadata( $object_type, $id, $field[ 'name' ], $related_id ); 
  3453. else 
  3454. delete_metadata( $object_type, $id, '_pods_' . $field[ 'name' ] ); 
  3455. // Custom Settings Pages (options-based) 
  3456. elseif ( 'settings' == $pod[ 'type' ] ) { 
  3457. if ( !empty( $related_ids ) ) 
  3458. update_option( $pod[ 'name' ] . '_' . $field[ 'name' ], $related_ids ); 
  3459. else 
  3460. delete_option( $pod[ 'name' ] . '_' . $field[ 'name' ] ); 
  3461.  
  3462. $related_pod_id = $related_field_id = 0; 
  3463.  
  3464. if ( 'pick' == $field[ 'type' ] && isset( PodsField_Pick::$related_data[ $field[ 'id' ] ] ) && !empty( PodsField_Pick::$related_data[ $field[ 'id' ] ][ 'related_field' ] ) ) { 
  3465. $related_pod_id = PodsField_Pick::$related_data[ $field[ 'id' ] ][ 'related_pod' ][ 'id' ]; 
  3466. $related_field_id = PodsField_Pick::$related_data[ $field[ 'id' ] ][ 'related_field' ][ 'id' ]; 
  3467.  
  3468. // Relationships table 
  3469. if ( !pods_tableless() ) { 
  3470. $related_weight = 0; 
  3471.  
  3472. foreach ( $related_ids as $related_id ) { 
  3473. if ( in_array( $related_id, $current_ids ) ) { 
  3474. pods_query( " 
  3475. UPDATE `@wp_podsrel` 
  3476. SET 
  3477. `pod_id` = %d,  
  3478. `field_id` = %d,  
  3479. `item_id` = %d,  
  3480. `related_pod_id` = %d,  
  3481. `related_field_id` = %d,  
  3482. `related_item_id` = %d,  
  3483. `weight` = %d 
  3484. WHERE 
  3485. `pod_id` = %d 
  3486. AND `field_id` = %d 
  3487. AND `item_id` = %d 
  3488. AND `related_item_id` = %d 
  3489. ", array( 
  3490. $pod[ 'id' ],  
  3491. $field[ 'id' ],  
  3492. $id,  
  3493. $related_pod_id,  
  3494. $related_field_id,  
  3495. $related_id,  
  3496. $related_weight,  
  3497.  
  3498. $pod[ 'id' ],  
  3499. $field[ 'id' ],  
  3500. $id,  
  3501. $related_id,  
  3502. ) ); 
  3503. else { 
  3504. pods_query( " 
  3505. INSERT INTO `@wp_podsrel` 
  3506. `pod_id`,  
  3507. `field_id`,  
  3508. `item_id`,  
  3509. `related_pod_id`,  
  3510. `related_field_id`,  
  3511. `related_item_id`,  
  3512. `weight` 
  3513. VALUES ( %d, %d, %d, %d, %d, %d, %d ) 
  3514. ", array( 
  3515. $pod[ 'id' ],  
  3516. $field[ 'id' ],  
  3517. $id,  
  3518. $related_pod_id,  
  3519. $related_field_id,  
  3520. $related_id,  
  3521. $related_weight 
  3522. ) ); 
  3523.  
  3524. $related_weight++; 
  3525.  
  3526. /** 
  3527. * Duplicate a Pod 
  3528. * $params['id'] int The Pod ID 
  3529. * $params['name'] string The Pod name 
  3530. * $params['new_name'] string The new Pod name 
  3531. * @param array $params An associative array of parameters 
  3532. * @param bool $strict (optional) Makes sure a pod exists, if it doesn't throws an error 
  3533. * @return int New Pod ID 
  3534. * @since 2.3 
  3535. */ 
  3536. public function duplicate_pod ( $params, $strict = false ) { 
  3537. if ( !is_object( $params ) && !is_array( $params ) ) { 
  3538. if ( is_numeric( $params ) ) 
  3539. $params = array( 'id' => $params ); 
  3540. else 
  3541. $params = array( 'name' => $params ); 
  3542.  
  3543. $params = (object) pods_sanitize( $params ); 
  3544. else 
  3545. $params = (object) pods_sanitize( $params ); 
  3546.  
  3547. $params->table_info = false; 
  3548.  
  3549. $pod = $this->load_pod( $params, $strict ); 
  3550.  
  3551. if ( empty( $pod ) ) { 
  3552. if ( false !== $strict ) 
  3553. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  3554.  
  3555. return false; 
  3556. elseif ( in_array( $pod[ 'type' ], array( 'media', 'user', 'comment' ) ) ) { 
  3557. if ( false !== $strict ) 
  3558. return pods_error( __( 'Pod not allowed to be duplicated', 'pods' ), $this ); 
  3559.  
  3560. return false; 
  3561. elseif ( in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) && 0 < strlen( $pod[ 'object' ] ) ) { 
  3562. $pod[ 'object' ] = ''; 
  3563.  
  3564. unset( $pod[ 'id' ] ); 
  3565.  
  3566. if ( isset( $params->new_name ) ) 
  3567. $pod[ 'name' ] = $params->new_name; 
  3568.  
  3569. $try = 1; 
  3570.  
  3571. $check_name = $pod[ 'name' ]; 
  3572. $new_label = $pod[ 'label' ]; 
  3573.  
  3574. while ( $this->load_pod( array( 'name' => $check_name, 'table_info' => false ), false ) ) { 
  3575. $try++; 
  3576.  
  3577. $check_name = $pod[ 'name' ] . $try; 
  3578. $new_label = $pod[ 'label' ] . $try; 
  3579.  
  3580. $pod[ 'name' ] = $check_name; 
  3581. $pod[ 'label' ] = $new_label; 
  3582.  
  3583. foreach ( $pod[ 'fields' ] as $field => $field_data ) { 
  3584. unset( $pod[ 'fields' ][ $field ][ 'id' ] ); 
  3585.  
  3586. return $this->save_pod( $pod ); 
  3587.  
  3588. /** 
  3589. * Duplicate a Field 
  3590. * $params['pod_id'] int The Pod ID 
  3591. * $params['pod'] string The Pod name 
  3592. * $params['id'] int The Field ID 
  3593. * $params['name'] string The Field name 
  3594. * $params['new_name'] string The new Field name 
  3595. * @param array $params An associative array of parameters 
  3596. * @param bool $strict (optional) Makes sure a field exists, if it doesn't throws an error 
  3597. * @return int New Field ID 
  3598. * @since 2.3.10 
  3599. */ 
  3600. public function duplicate_field( $params, $strict = false ) { 
  3601.  
  3602. if ( !is_object( $params ) && !is_array( $params ) ) { 
  3603. if ( is_numeric( $params ) ) { 
  3604. $params = array( 'id' => $params ); 
  3605. else { 
  3606. $params = array( 'name' => $params ); 
  3607.  
  3608. $params = (object) pods_sanitize( $params ); 
  3609.  
  3610. $params->table_info = false; 
  3611.  
  3612. $field = $this->load_field( $params, $strict ); 
  3613.  
  3614. if ( empty( $field ) ) { 
  3615. if ( false !== $strict ) { 
  3616. return pods_error( __( 'Field not found', 'pods' ), $this ); 
  3617.  
  3618. return false; 
  3619.  
  3620. unset( $field[ 'id' ] ); 
  3621.  
  3622. if ( isset( $params->new_name ) ) { 
  3623. $field[ 'name' ] = $params->new_name; 
  3624.  
  3625. $try = 1; 
  3626.  
  3627. $check_name = $field[ 'name' ]; 
  3628. $new_label = $field[ 'label' ]; 
  3629.  
  3630. while ( $this->load_field( array( 'pod_id' => $field[ 'pod_id' ], 'name' => $check_name, 'table_info' => false ), false ) ) { 
  3631. $try++; 
  3632.  
  3633. $check_name = $field[ 'name' ] . $try; 
  3634. $new_label = $field[ 'label' ] . $try; 
  3635.  
  3636. $field[ 'name' ] = $check_name; 
  3637. $field[ 'label' ] = $new_label; 
  3638.  
  3639. return $this->save_field( $field ); 
  3640.  
  3641.  
  3642. /** 
  3643. * @see PodsAPI::save_pod_item 
  3644. * Duplicate a pod item 
  3645. * $params['pod'] string The Pod name 
  3646. * $params['id'] int The item's ID from the wp_pods_* table 
  3647. * @param array $params An associative array of parameters 
  3648. * @return int The table row ID 
  3649. * @since 1.12 
  3650. */ 
  3651. public function duplicate_pod_item ( $params ) { 
  3652. $params = (object) pods_sanitize( $params ); 
  3653.  
  3654. $pod = $this->load_pod( array( 'name' => $params->pod, 'table_info' => false ) ); 
  3655.  
  3656. if ( false === $pod ) 
  3657. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  3658.  
  3659. $pod = pods( $params->pod, $params->id ); 
  3660.  
  3661. $params->pod = $pod->pod; 
  3662. $params->pod_id = $pod->pod_id; 
  3663.  
  3664. $fields = (array) pods_var_raw( 'fields', $pod->pod_data, array(), null, true ); 
  3665. $object_fields = (array) pods_var_raw( 'object_fields', $pod->pod_data, array(), null, true ); 
  3666.  
  3667. if ( !empty( $object_fields ) ) 
  3668. $fields = array_merge( $object_fields, $fields ); 
  3669.  
  3670. $save_params = array( 
  3671. 'pod' => $params->pod,  
  3672. 'data' => array() 
  3673. ); 
  3674.  
  3675. foreach ( $fields as $field ) { 
  3676. $value = $pod->field( array( 'name' => $field[ 'name' ], 'output' => 'ids' ) ); 
  3677.  
  3678. if ( !empty( $value ) || ( !is_array( $value ) && 0 < strlen( $value ) ) ) 
  3679. $save_params[ 'data' ][ $field[ 'name' ] ] = $value; 
  3680.  
  3681. $save_params = $this->do_hook( 'duplicate_pod_item', $save_params, $pod->pod, $pod->id(), $params ); 
  3682.  
  3683. $id = $this->save_pod_item( $save_params ); 
  3684.  
  3685. return $id; 
  3686.  
  3687. /** 
  3688. * @see pods() 
  3689. * Export a pod item 
  3690. * $params['pod'] string The Pod name 
  3691. * $params['id'] int The item's ID from the wp_pods_* table 
  3692. * $params['fields'] array The fields to export 
  3693. * $params['depth'] int How many levels deep to export data 
  3694. * @param array $params An associative array of parameters 
  3695. * @param object $pod (optional) Pods object 
  3696. * @return int The table row ID 
  3697. * @since 1.12 
  3698. */ 
  3699. public function export_pod_item ( $params, $pod = null ) { 
  3700. if ( !is_object( $pod ) || 'Pods' != get_class( $pod ) ) { 
  3701. if ( empty( $params ) ) 
  3702. return false; 
  3703.  
  3704. $params = (object) pods_sanitize( $params ); 
  3705.  
  3706. $pod = pods( $params->pod, $params->id, false ); 
  3707.  
  3708. if ( empty( $pod ) ) 
  3709. return false; 
  3710.  
  3711. $fields = (array) pods_var_raw( 'fields', $params, array(), null, true ); 
  3712. $depth = (int) pods_var_raw( 'depth', $params, 2, null, true ); 
  3713. $object_fields = (array) pods_var_raw( 'object_fields', $pod->pod_data, array(), null, true ); 
  3714. $flatten = (boolean) pods_var( 'flatten', $params, false, null, true ); 
  3715.  
  3716. if ( empty( $fields ) ) { 
  3717. $fields = $pod->fields; 
  3718. $fields = array_merge( $fields, $object_fields ); 
  3719.  
  3720. $data = $this->export_pod_item_level( $pod, $fields, $depth, $flatten ); 
  3721.  
  3722. $data = $this->do_hook( 'export_pod_item', $data, $pod->pod, $pod->id(), $pod, $fields, $depth, $flatten ); 
  3723.  
  3724. return $data; 
  3725.  
  3726. /** 
  3727. * Export a pod item by depth level 
  3728. * @param Pods $pod Pods object 
  3729. * @param array $fields Fields to export 
  3730. * @param int $depth Depth limit 
  3731. * @param boolean $flatten Whether to flatten arrays for display 
  3732. * @param int $current_depth Current depth level 
  3733. * @return array Data array 
  3734. * @since 2.3 
  3735. */ 
  3736. private function export_pod_item_level ( $pod, $fields, $depth, $flatten = false, $current_depth = 1 ) { 
  3737. $tableless_field_types = PodsForm::tableless_field_types(); 
  3738. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  3739.  
  3740. $object_fields = (array) pods_var_raw( 'object_fields', $pod->pod_data, array(), null, true ); 
  3741.  
  3742. $export_fields = array(); 
  3743.  
  3744. foreach ( $fields as $k => $field ) { 
  3745. if ( !is_array( $field ) ) { 
  3746. $field = array( 
  3747. 'id' => 0,  
  3748. 'name' => $field 
  3749. ); 
  3750.  
  3751. if ( isset( $pod->fields[ $field[ 'name' ] ] ) ) { 
  3752. $field = $pod->fields[ $field[ 'name' ] ]; 
  3753. $field[ 'lookup_name' ] = $field[ 'name' ]; 
  3754.  
  3755. if ( in_array( $field[ 'type' ], $tableless_field_types ) && !in_array( pods_var( 'pick_object', $field ), $simple_tableless_objects ) ) { 
  3756. if ( 'pick' == $field[ 'type' ] ) { 
  3757. if ( empty( $field[ 'table_info' ] ) ) 
  3758. $field[ 'table_info' ] = $this->get_table_info( pods_var_raw( 'pick_object', $field ), pods_var_raw( 'pick_val', $field ), null, null, $field ); 
  3759.  
  3760. if ( !empty( $field[ 'table_info' ] ) ) 
  3761. $field[ 'lookup_name' ] .= '.' . $field[ 'table_info' ][ 'field_id' ]; 
  3762. elseif ( in_array( $field[ 'type' ], PodsForm::file_field_types() ) ) 
  3763. $field[ 'lookup_name' ] .= '.guid'; 
  3764.  
  3765. $export_fields[ $field[ 'name' ] ] = $field; 
  3766. elseif ( isset( $object_fields[ $field[ 'name' ] ] ) ) { 
  3767. $field = $object_fields[ $field[ 'name' ] ]; 
  3768. $field[ 'lookup_name' ] = $field[ 'name' ]; 
  3769.  
  3770. $export_fields[ $field[ 'name' ] ] = $field; 
  3771. elseif ( $field[ 'name' ] == $pod->pod_data[ 'field_id' ] ) { 
  3772. $field[ 'type' ] = 'number'; 
  3773. $field[ 'lookup_name' ] = $field[ 'name' ]; 
  3774.  
  3775. $export_fields[ $field[ 'name' ] ] = $field; 
  3776.  
  3777. $data = array(); 
  3778.  
  3779. foreach ( $export_fields as $field ) { 
  3780. // Return IDs (or guid for files) if only one level deep 
  3781. if ( 1 == $depth ) 
  3782. $data[ $field[ 'name' ] ] = $pod->field( array( 'name' => $field[ 'lookup_name' ], 'output' => 'arrays' ) ); 
  3783. // Recurse depth levels for pick fields if $depth allows 
  3784. elseif ( ( -1 == $depth || $current_depth < $depth ) && 'pick' == $field[ 'type' ] && !in_array( pods_var( 'pick_object', $field ), $simple_tableless_objects ) ) { 
  3785. $related_data = array(); 
  3786.  
  3787. $related_ids = $pod->field( array( 'name' => $field[ 'name' ], 'output' => 'ids' ) ); 
  3788.  
  3789. if ( !empty( $related_ids ) ) { 
  3790. $related_ids = (array) $related_ids; 
  3791.  
  3792. $pick_object = pods_var_raw( 'pick_object', $field ); 
  3793.  
  3794. $related_pod = pods( pods_var_raw( 'pick_val', $field ), null, false ); 
  3795.  
  3796. // If this isn't a Pod, return data exactly as Pods does normally 
  3797. if ( empty( $related_pod ) || ( 'pod' != $pick_object && $pick_object != $related_pod->pod_data[ 'type' ] ) || $related_pod->pod == $pod->pod ) 
  3798. $related_data = $pod->field( array( 'name' => $field[ 'name' ], 'output' => 'arrays' ) ); 
  3799. else { 
  3800. $related_object_fields = (array) pods_var_raw( 'object_fields', $related_pod->pod_data, array(), null, true ); 
  3801.  
  3802. $related_fields = array_merge( $related_pod->fields, $related_object_fields ); 
  3803.  
  3804. foreach ( $related_ids as $related_id ) { 
  3805. if ( $related_pod->fetch( $related_id ) ) { 
  3806. $related_item = $this->export_pod_item_level( $related_pod, $related_fields, $depth, $flatten, ( $current_depth + 1 ) ); 
  3807.  
  3808. $related_data[ $related_id ] = $this->do_hook( 'export_pod_item_level', $related_item, $related_pod->pod, $related_pod->id(), $related_pod, $related_fields, $depth, $flatten, ( $current_depth + 1 ) ); 
  3809.  
  3810. if ( $flatten && !empty( $related_data ) ) 
  3811. $related_data = pods_serial_comma( array_values( $related_data ), array( 'and' => '', 'field_index' => $related_pod->pod_data[ 'field_index' ] ) ); 
  3812.  
  3813. $data[ $field[ 'name' ] ] = $related_data; 
  3814. // Return data exactly as Pods does normally 
  3815. else 
  3816. $data[ $field[ 'name' ] ] = $pod->field( array( 'name' => $field[ 'name' ], 'output' => 'arrays' ) ); 
  3817.  
  3818. if ( $flatten && is_array( $data[ $field[ 'name' ] ] ) ) 
  3819. $data[ $field[ 'name' ] ] = pods_serial_comma( $data[ $field[ 'name' ] ], array( 'field' => $field[ 'name' ], 'fields' => $export_fields, 'and' => '' ) ); 
  3820.  
  3821. $data[ 'id' ] = (int) $pod->id(); 
  3822. return $data; 
  3823.  
  3824. /** 
  3825. * Reorder a Pod 
  3826. * $params['pod'] string The Pod name 
  3827. * $params['field'] string The field name of the field to reorder 
  3828. * $params['order'] array The key => value array of items to reorder (key should be an integer) 
  3829. * @param array $params An associative array of parameters 
  3830. * @return bool 
  3831. * @since 1.9.0 
  3832. */ 
  3833. public function reorder_pod_item ( $params ) { 
  3834. $params = (object) pods_sanitize( $params ); 
  3835.  
  3836. // @deprecated 2.0 
  3837. if ( isset( $params->datatype ) ) { 
  3838. pods_deprecated( __( '$params->pod instead of $params->datatype', 'pods' ), '2.0' ); 
  3839.  
  3840. $params->pod = $params->datatype; 
  3841.  
  3842. unset( $params->datatype ); 
  3843.  
  3844. if ( null === pods_var_raw( 'pod', $params, null, null, true ) ) 
  3845. return pods_error( __( '$params->pod is required', 'pods' ), $this ); 
  3846.  
  3847. if ( !is_array( $params->order ) ) 
  3848. $params->order = explode( ', ', $params->order ); 
  3849.  
  3850. $pod = $this->load_pod( array( 'name' => $params->pod, 'table_info' => true ) ); 
  3851.  
  3852. $params->name = $pod[ 'name' ]; 
  3853.  
  3854. if ( false === $pod ) 
  3855. return pods_error( __( 'Pod is required', 'pods' ), $this ); 
  3856.  
  3857. foreach ( $params->order as $order => $id ) { 
  3858. if ( isset( $pod[ 'fields' ][ $params->field ] ) || isset( $pod[ 'object_fields' ][ $params->field ] ) ) { 
  3859. if ( 'table' == $pod[ 'storage' ] && ( !pods_tableless() ) ) { 
  3860. if ( isset( $pod[ 'fields' ][ $params->field ] ) ) 
  3861. pods_query( "UPDATE `@wp_pods_{$params->name}` SET `{$params->field}` = " . pods_absint( $order ) . " WHERE `id` = " . pods_absint( $id ) . " LIMIT 1" ); 
  3862. else 
  3863. pods_query( "UPDATE `{$pod['table']}` SET `{$params->field}` = " . pods_absint( $order ) . " WHERE `{$pod['field_id']}` = " . pods_absint( $id ) . " LIMIT 1" ); 
  3864. else 
  3865. $this->save_pod_item( array( 'pod' => $params->pod, 'pod_id' => $params->pod_id, 'id' => $id, 'data' => array( $params->field => pods_absint( $order ) ) ) ); 
  3866.  
  3867. return true; 
  3868.  
  3869. /** 
  3870. * Delete all content for a Pod 
  3871. * $params['id'] int The Pod ID 
  3872. * $params['name'] string The Pod name 
  3873. * @param array $params An associative array of parameters 
  3874. * @param array $pod Pod data 
  3875. * @return bool 
  3876. * @uses pods_query 
  3877. * @uses pods_cache_clear 
  3878. * @since 1.9.0 
  3879. */ 
  3880. public function reset_pod ( $params, $pod = false ) { 
  3881. $params = (object) pods_sanitize( $params ); 
  3882.  
  3883. $params->table_info = true; 
  3884.  
  3885. if ( empty( $pod ) ) 
  3886. $pod = $this->load_pod( $params ); 
  3887.  
  3888. if ( false === $pod ) 
  3889. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  3890.  
  3891. $params->id = $pod[ 'id' ]; 
  3892. $params->name = $pod[ 'name' ]; 
  3893.  
  3894. if ( !pods_tableless() ) { 
  3895. if ( 'table' == $pod[ 'storage' ] ) { 
  3896. try { 
  3897. pods_query( "TRUNCATE `@wp_pods_{$params->name}`", false ); 
  3898. catch ( Exception $e ) { 
  3899. // Allow pod to be reset if the table doesn't exist 
  3900. if ( false === strpos( $e->getMessage(), 'Unknown table' ) ) 
  3901. return pods_error( $e->getMessage(), $this ); 
  3902.  
  3903. pods_query( "DELETE FROM `@wp_podsrel` WHERE `pod_id` = {$params->id} OR `related_pod_id` = {$params->id}", false ); 
  3904.  
  3905. // @todo Delete relationships from tableless relationships 
  3906.  
  3907. // Delete all posts/revisions from this post type 
  3908. if ( in_array( $pod[ 'type' ], array( 'post_type', 'media' ) ) ) { 
  3909. $type = pods_var( 'object', $pod, $pod[ 'name' ], null, true ); 
  3910.  
  3911. $sql = " 
  3912. DELETE `t`, `r`, `m` 
  3913. FROM `{$pod['table']}` AS `t` 
  3914. LEFT JOIN `{$pod['meta_table']}` AS `m` 
  3915. ON `m`.`{$pod['meta_field_id']}` = `t`.`{$pod['field_id']}` 
  3916. LEFT JOIN `{$pod['table']}` AS `r` 
  3917. ON `r`.`post_parent` = `t`.`{$pod['field_id']}` AND `r`.`post_status` = 'inherit' 
  3918. WHERE `t`.`{$pod['field_type']}` = '{$type}' 
  3919. "; 
  3920.  
  3921. pods_query( $sql, false ); 
  3922. // Delete all terms from this taxonomy 
  3923. elseif ( 'taxonomy' == $pod[ 'type' ] ) { 
  3924. if ( function_exists( 'get_term_meta' ) ) { 
  3925. $sql = " 
  3926. DELETE `t`, `m`, `tt`, `tr` 
  3927. FROM `{$pod['table']}` AS `t` 
  3928. LEFT JOIN `{$pod['meta_table']}` AS `m` 
  3929. ON `m`.`{$pod['meta_field_id']}` = `t`.`{$pod['field_id']}` 
  3930. " . $pod['join']['tt'] . " 
  3931. " . $pod['join']['tr'] . " 
  3932. WHERE " . implode( ' AND ', $pod['where'] ) . " 
  3933. "; 
  3934. } else { 
  3935. $sql = " 
  3936. DELETE `t`, `tt`, `tr` 
  3937. FROM `{$pod['table']}` AS `t` 
  3938. " . $pod['join']['tt'] . " 
  3939. " . $pod['join']['tr'] . " 
  3940. WHERE " . implode( ' AND ', $pod['where'] ) . " 
  3941. "; 
  3942.  
  3943. pods_query( $sql, false ); 
  3944. // Delete all users except the current one 
  3945. elseif ( 'user' == $pod[ 'type' ] ) { 
  3946. $sql = " 
  3947. DELETE `t`, `m` 
  3948. FROM `{$pod['table']}` AS `t` 
  3949. LEFT JOIN `{$pod['meta_table']}` AS `m` 
  3950. ON `m`.`{$pod['meta_field_id']}` = `t`.`{$pod['field_id']}` 
  3951. WHERE `t`.`{$pod['field_id']}` != " . (int) get_current_user_id() . " 
  3952. "; 
  3953.  
  3954. pods_query( $sql, false ); 
  3955. // Delete all comments 
  3956. elseif ( 'comment' == $pod[ 'type' ] ) { 
  3957. $type = pods_var( 'object', $pod, $pod[ 'name' ], null, true ); 
  3958.  
  3959. $sql = " 
  3960. DELETE `t`, `m` 
  3961. FROM `{$pod['table']}` AS `t` 
  3962. LEFT JOIN `{$pod['meta_table']}` AS `m` 
  3963. ON `m`.`{$pod['meta_field_id']}` = `t`.`{$pod['field_id']}` 
  3964. WHERE `t`.`{$pod['field_type']}` = '{$type}' 
  3965. "; 
  3966.  
  3967. pods_query( $sql, false ); 
  3968.  
  3969. pods_cache_clear( true ); // only way to reliably clear out cached data across an entire group 
  3970.  
  3971. return true; 
  3972.  
  3973. /** 
  3974. * Delete a Pod and all its content 
  3975. * $params['id'] int The Pod ID 
  3976. * $params['name'] string The Pod name 
  3977. * @param array $params An associative array of parameters 
  3978. * @param bool $strict (optional) Makes sure a pod exists, if it doesn't throws an error 
  3979. * @param bool $delete_all (optional) Whether to delete all content from a WP object 
  3980. * @uses PodsAPI::load_pod 
  3981. * @uses wp_delete_post 
  3982. * @uses pods_query 
  3983. * @return bool 
  3984. * @since 1.7.9 
  3985. */ 
  3986. public function delete_pod ( $params, $strict = false, $delete_all = false ) { 
  3987. /** 
  3988. * @var $wpdb wpdb 
  3989. */ 
  3990. global $wpdb; 
  3991.  
  3992. if ( !is_object( $params ) && !is_array( $params ) ) { 
  3993. if ( is_numeric( $params ) ) 
  3994. $params = array( 'id' => $params ); 
  3995. else 
  3996. $params = array( 'name' => $params ); 
  3997.  
  3998. $params = (object) pods_sanitize( $params ); 
  3999. else 
  4000. $params = (object) pods_sanitize( $params ); 
  4001.  
  4002. $params->table_info = false; 
  4003.  
  4004. $pod = $this->load_pod( $params, $strict ); 
  4005.  
  4006. if ( empty( $pod ) ) { 
  4007. if ( false !== $strict ) 
  4008. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  4009.  
  4010. return false; 
  4011.  
  4012. $params->id = (int) $pod[ 'id' ]; 
  4013. $params->name = $pod[ 'name' ]; 
  4014.  
  4015. foreach ( $pod[ 'fields' ] as $field ) { 
  4016. $field[ 'pod' ] = $pod; 
  4017.  
  4018. $this->delete_field( $field, false ); 
  4019.  
  4020. // Only delete the post once the fields are taken care of, it's not required anymore 
  4021. $success = wp_delete_post( $params->id ); 
  4022.  
  4023. if ( !$success ) 
  4024. return pods_error( __( 'Pod unable to be deleted', 'pods' ), $this ); 
  4025.  
  4026. // Reset content 
  4027. if ( $delete_all ) 
  4028. $this->reset_pod( $params, $pod ); 
  4029.  
  4030. if ( !pods_tableless() ) { 
  4031. if ( 'table' == $pod[ 'storage' ] ) { 
  4032. try { 
  4033. pods_query( "DROP TABLE IF EXISTS `@wp_pods_{$params->name}`", false ); 
  4034. catch ( Exception $e ) { 
  4035. // Allow pod to be deleted if the table doesn't exist 
  4036. if ( false === strpos( $e->getMessage(), 'Unknown table' ) ) 
  4037. return pods_error( $e->getMessage(), $this ); 
  4038.  
  4039. pods_query( "DELETE FROM `@wp_podsrel` WHERE `pod_id` = {$params->id} OR `related_pod_id` = {$params->id}", false ); 
  4040.  
  4041. // @todo Delete relationships from tableless relationships 
  4042.  
  4043. // Delete any relationship references 
  4044. $sql = " 
  4045. DELETE `pm` 
  4046. FROM `{$wpdb->postmeta}` AS `pm` 
  4047. LEFT JOIN `{$wpdb->posts}` AS `p` 
  4048. ON `p`.`post_type` = '_pods_field' 
  4049. AND `p`.`ID` = `pm`.`post_id` 
  4050. LEFT JOIN `{$wpdb->postmeta}` AS `pm2` 
  4051. ON `pm2`.`meta_key` = 'pick_object' 
  4052. AND `pm2`.`meta_value` = 'pod' 
  4053. AND `pm2`.`post_id` = `pm`.`post_id` 
  4054. WHERE 
  4055. `p`.`ID` IS NOT NULL 
  4056. AND `pm2`.`meta_id` IS NOT NULL 
  4057. AND `pm`.`meta_key` = 'pick_val' 
  4058. AND `pm`.`meta_value` = '{$params->name}' 
  4059. "; 
  4060.  
  4061. pods_query( $sql ); 
  4062.  
  4063. $this->cache_flush_pods( $pod ); 
  4064.  
  4065. return true; 
  4066.  
  4067. /** 
  4068. * Drop a field within a Pod 
  4069. * $params['id'] int The field ID 
  4070. * $params['name'] int The field name 
  4071. * $params['pod'] string The Pod name 
  4072. * $params['pod_id'] string The Pod name 
  4073. * @param array $params An associative array of parameters 
  4074. * @param bool $table_operation Whether or not to handle table operations 
  4075. * @uses PodsAPI::load_field 
  4076. * @uses wp_delete_post 
  4077. * @uses pods_query 
  4078. * @return bool 
  4079. * @since 1.7.9 
  4080. */ 
  4081. public function delete_field ( $params, $table_operation = true ) { 
  4082. /** 
  4083. * @var $wpdb wpdb 
  4084. */ 
  4085. global $wpdb; 
  4086.  
  4087. $tableless_field_types = PodsForm::tableless_field_types(); 
  4088. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  4089.  
  4090. $params = (object) pods_sanitize( $params ); 
  4091.  
  4092. if ( !isset( $params->pod ) ) 
  4093. $params->pod = ''; 
  4094.  
  4095. if ( !isset( $params->pod_id ) ) 
  4096. $params->pod_id = 0; 
  4097.  
  4098. $pod = $params->pod; 
  4099.  
  4100. $save_pod = false; 
  4101.  
  4102. if ( !is_array( $pod ) ) 
  4103. $pod = $this->load_pod( array( 'name' => $pod, 'id' => $params->pod_id, 'table_info' => false ) ); 
  4104. else 
  4105. $save_pod = true; 
  4106.  
  4107. if ( empty( $pod ) ) 
  4108. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  4109.  
  4110. $params->pod_id = $pod[ 'id' ]; 
  4111. $params->pod = $pod[ 'name' ]; 
  4112.  
  4113. if ( !isset( $params->name ) ) 
  4114. $params->name = ''; 
  4115.  
  4116. if ( !isset( $params->id ) ) 
  4117. $params->id = 0; 
  4118.  
  4119. $field = $this->load_field( array( 'name' => $params->name, 'id' => $params->id, 'pod' => $params->pod, 'pod_id' => $params->pod_id ) ); 
  4120.  
  4121. if ( false === $field ) 
  4122. return pods_error( __( 'Field not found', 'pods' ), $this ); 
  4123.  
  4124. $params->id = $field[ 'id' ]; 
  4125. $params->name = $field[ 'name' ]; 
  4126.  
  4127. $simple = ( 'pick' == $field[ 'type' ] && in_array( pods_var( 'pick_object', $field ), $simple_tableless_objects ) ); 
  4128. $simple = (boolean) $this->do_hook( 'tableless_custom', $simple, $field, $pod, $params ); 
  4129.  
  4130. if ( $table_operation && 'table' == $pod[ 'storage' ] && ( !in_array( $field[ 'type' ], $tableless_field_types ) || $simple ) ) 
  4131. pods_query( "ALTER TABLE `@wp_pods_{$params->pod}` DROP COLUMN `{$params->name}`", false ); 
  4132.  
  4133. $success = wp_delete_post( $params->id ); 
  4134.  
  4135. if ( !$success ) 
  4136. return pods_error( __( 'Field unable to be deleted', 'pods' ), $this ); 
  4137.  
  4138. $wpdb->query( $wpdb->prepare( "DELETE pm FROM {$wpdb->postmeta} AS pm 
  4139. LEFT JOIN {$wpdb->posts} AS p 
  4140. ON p.post_type = '_pods_field' AND p.ID = pm.post_id 
  4141. WHERE p.ID IS NOT NULL AND pm.meta_key = 'sister_id' AND pm.meta_value = %d", $params->id ) ); 
  4142.  
  4143. if ( ( !pods_tableless() ) && $table_operation ) { 
  4144. pods_query( "DELETE FROM `@wp_podsrel` WHERE (`pod_id` = {$params->pod_id} AND `field_id` = {$params->id}) OR (`related_pod_id` = {$params->pod_id} AND `related_field_id` = {$params->id})", false ); 
  4145.  
  4146. // @todo Delete tableless relationship meta 
  4147.  
  4148. if ( true === $save_pod ) 
  4149. $this->cache_flush_pods( $pod ); 
  4150.  
  4151. return true; 
  4152.  
  4153. /** 
  4154. * Drop a Pod Object 
  4155. * $params['id'] int The object ID 
  4156. * $params['name'] string The object name 
  4157. * $params['type'] string The object type 
  4158. * @param array|object $params An associative array of parameters 
  4159. * @uses wp_delete_post 
  4160. * @return bool 
  4161. * @since 2.0 
  4162. */ 
  4163. public function delete_object ( $params ) { 
  4164. $params = (object) $params; 
  4165. $object = $this->load_object( $params ); 
  4166.  
  4167. if ( empty( $object ) ) 
  4168. return pods_error( sprintf( __( "%s Object not found", 'pods' ), ucwords( $params->type ) ), $this ); 
  4169.  
  4170. $success = wp_delete_post( $params->id ); 
  4171.  
  4172. if ( !$success ) 
  4173. return pods_error( sprintf( __( "%s Object not deleted", 'pods' ), ucwords( $params->type ) ), $this ); 
  4174.  
  4175. pods_transient_clear( 'pods_objects_' . $params->type ); 
  4176.  
  4177. return true; 
  4178.  
  4179. /** 
  4180. * @see PodsAPI::delete_object 
  4181. * Drop a Pod Template 
  4182. * $params['id'] int The template ID 
  4183. * $params['name'] string The template name 
  4184. * @param array $params An associative array of parameters 
  4185. * @return bool 
  4186. * @since 1.7.9 
  4187. */ 
  4188. public function delete_template ( $params ) { 
  4189. $params = (object) $params; 
  4190. $params->type = 'template'; 
  4191. return $this->delete_object( $params ); 
  4192.  
  4193. /** 
  4194. * @see PodsAPI::delete_object 
  4195. * Drop a Pod Page 
  4196. * $params['id'] int The page ID 
  4197. * $params['uri'] string The page URI 
  4198. * @param array $params An associative array of parameters 
  4199. * @return bool 
  4200. * @since 1.7.9 
  4201. */ 
  4202. public function delete_page ( $params ) { 
  4203. $params = (object) $params; 
  4204. if ( isset( $params->uri ) ) { 
  4205. $params->name = $params->uri; 
  4206. unset( $params->uri ); 
  4207. if ( isset( $params->name ) ) 
  4208. $params->name = trim( $params->name, '/' ); 
  4209. $params->type = 'page'; 
  4210. return $this->delete_object( $params ); 
  4211.  
  4212. /** 
  4213. * @see PodsAPI::delete_object 
  4214. * Drop a Pod Helper 
  4215. * $params['id'] int The helper ID 
  4216. * $params['name'] string The helper name 
  4217. * @param array $params An associative array of parameters 
  4218. * @return bool 
  4219. * @since 1.7.9 
  4220. */ 
  4221. public function delete_helper ( $params ) { 
  4222. $params = (object) $params; 
  4223. $params->type = 'helper'; 
  4224. return $this->delete_object( $params ); 
  4225.  
  4226. /** 
  4227. * Drop a single pod item 
  4228. * $params['id'] int (optional) The item's ID from the wp_pod_* table (used with datatype parameter) 
  4229. * $params['pod'] string (optional) The Pod name (used with id parameter) 
  4230. * $params['pod_id'] int (optional) The Pod ID (used with id parameter) 
  4231. * $params['bypass_helpers'] bool Set to true to bypass running pre-save and post-save helpers 
  4232. * @param array $params An associative array of parameters 
  4233. * @param bool $wp Whether to run WP object delete action 
  4234. * @return bool 
  4235. * @since 1.7.9 
  4236. */ 
  4237. public function delete_pod_item ( $params, $wp = true ) { 
  4238. $params = (object) pods_sanitize( $params ); 
  4239.  
  4240. // @deprecated 2.0 
  4241. if ( isset( $params->datatype_id ) || isset( $params->datatype ) || isset( $params->tbl_row_id ) ) { 
  4242. if ( isset( $params->tbl_row_id ) ) { 
  4243. pods_deprecated( __( '$params->id instead of $params->tbl_row_id', 'pods' ), '2.0' ); 
  4244. $params->id = $params->tbl_row_id; 
  4245. unset( $params->tbl_row_id ); 
  4246.  
  4247. if ( isset( $params->pod_id ) ) { 
  4248. pods_deprecated( __( '$params->id instead of $params->pod_id', 'pods' ), '2.0' ); 
  4249. $params->id = $params->pod_id; 
  4250. unset( $params->pod_id ); 
  4251.  
  4252. if ( isset( $params->dataype_id ) ) { 
  4253. pods_deprecated( __( '$params->pod_id instead of $params->datatype_id', 'pods' ), '2.0' ); 
  4254. $params->pod_id = $params->dataype_id; 
  4255. unset( $params->dataype_id ); 
  4256.  
  4257. if ( isset( $params->datatype ) ) { 
  4258. pods_deprecated( __( '$params->pod instead of $params->datatype', 'pods' ), '2.0' ); 
  4259. $params->pod = $params->datatype; 
  4260. unset( $params->datatype ); 
  4261.  
  4262. if ( !isset( $params->id ) ) 
  4263. return pods_error( __( 'Pod Item not found', 'pods' ), $this ); 
  4264.  
  4265. $params->id = pods_absint( $params->id ); 
  4266.  
  4267. if ( !isset( $params->pod ) ) 
  4268. $params->pod = ''; 
  4269.  
  4270. if ( !isset( $params->pod_id ) ) 
  4271. $params->pod_id = 0; 
  4272.  
  4273. $pod = $this->load_pod( array( 'name' => $params->pod, 'id' => $params->pod_id, 'table_info' => false ) ); 
  4274.  
  4275. if ( false === $pod ) 
  4276. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  4277.  
  4278. $params->pod_id = $pod[ 'id' ]; 
  4279. $params->pod = $pod[ 'name' ]; 
  4280.  
  4281. // Allow Helpers to bypass subsequent helpers in recursive delete_pod_item calls 
  4282. $bypass_helpers = false; 
  4283.  
  4284. if ( isset( $params->bypass_helpers ) && false !== $params->bypass_helpers ) 
  4285. $bypass_helpers = true; 
  4286.  
  4287. $pre_delete_helpers = $post_delete_helpers = array(); 
  4288.  
  4289. if ( false === $bypass_helpers ) { 
  4290. // Plugin hook 
  4291. $this->do_hook( 'pre_delete_pod_item', $params, $pod ); 
  4292. $this->do_hook( "pre_delete_pod_item_{$params->pod}", $params, $pod ); 
  4293.  
  4294. // Call any pre-save helpers (if not bypassed) 
  4295. if ( !defined( 'PODS_DISABLE_EVAL' ) || !PODS_DISABLE_EVAL ) { 
  4296. if ( !empty( $pod[ 'options' ] ) && is_array( $pod[ 'options' ] ) ) { 
  4297. $helpers = array( 'pre_delete_helpers', 'post_delete_helpers' ); 
  4298.  
  4299. foreach ( $helpers as $helper ) { 
  4300. if ( isset( $pod[ 'options' ][ $helper ] ) && !empty( $pod[ 'options' ][ $helper ] ) ) 
  4301. ${$helper} = explode( ', ', $pod[ 'options' ][ $helper ] ); 
  4302.  
  4303. if ( !empty( $pre_delete_helpers ) ) { 
  4304. pods_deprecated( sprintf( __( 'Pre-delete helpers are deprecated, use the action pods_pre_delete_pod_item_%s instead', 'pods' ), $params->pod ), '2.0' ); 
  4305.  
  4306. foreach ( $pre_delete_helpers as $helper ) { 
  4307. $helper = $this->load_helper( array( 'name' => $helper ) ); 
  4308.  
  4309. if ( false !== $helper ) 
  4310. eval( '?>' . $helper[ 'code' ] ); 
  4311.  
  4312. // Delete object from relationship fields 
  4313. $this->delete_object_from_relationships( $params->id, $pod ); 
  4314.  
  4315. if ( 'table' == $pod[ 'storage' ] ) 
  4316. pods_query( "DELETE FROM `@wp_pods_{$params->pod}` WHERE `id` = {$params->id} LIMIT 1" ); 
  4317.  
  4318. if ( $wp ) { 
  4319. if ( 'taxonomy' == $pod['type'] ) { 
  4320. $taxonomy = $pod['name']; 
  4321.  
  4322. if ( ! empty( $pod['object'] ) ) { 
  4323. $taxonomy = $pod['object']; 
  4324.  
  4325. wp_delete_term( $params->id, $taxonomy ); 
  4326. } elseif ( ! in_array( $pod['type'], array( 'pod', 'table', '', 'taxonomy' ) ) ) { 
  4327. $this->delete_wp_object( $pod['type'], $params->id ); 
  4328.  
  4329. if ( false === $bypass_helpers ) { 
  4330. // Plugin hook 
  4331. $this->do_hook( 'post_delete_pod_item', $params, $pod ); 
  4332. $this->do_hook( "post_delete_pod_item_{$params->pod}", $params, $pod ); 
  4333.  
  4334. // Call any post-save helpers (if not bypassed) 
  4335. if ( !defined( 'PODS_DISABLE_EVAL' ) || !PODS_DISABLE_EVAL ) { 
  4336. if ( !empty( $post_delete_helpers ) ) { 
  4337. pods_deprecated( sprintf( __( 'Post-delete helpers are deprecated, use the action pods_post_delete_pod_item_%s instead', 'pods' ), $params->pod ), '2.0' ); 
  4338.  
  4339. foreach ( $post_delete_helpers as $helper ) { 
  4340. $helper = $this->load_helper( array( 'name' => $helper ) ); 
  4341.  
  4342. if ( false !== $helper ) 
  4343. eval( '?>' . $helper[ 'code' ] ); 
  4344.  
  4345. pods_cache_clear( $params->id, 'pods_items_' . $params->pod ); 
  4346.  
  4347. return true; 
  4348.  
  4349. /** 
  4350. * Delete an object from tableless fields 
  4351. * @param int $id 
  4352. * @param string $type 
  4353. * @param string $name 
  4354. * @return bool 
  4355. * @since 2.3 
  4356. */ 
  4357. public function delete_object_from_relationships ( $id, $object, $name = null ) { 
  4358. /** 
  4359. * @var $pods_init \PodsInit 
  4360. */ 
  4361. global $pods_init; 
  4362.  
  4363. $pod = false; 
  4364.  
  4365. // Run any bidirectional delete operations 
  4366. if ( is_array( $object ) ) 
  4367. $pod = $object; 
  4368. elseif ( is_object( $pods_init ) ) 
  4369. $pod = PodsInit::$meta->get_object( $object, $name ); 
  4370.  
  4371. if ( !empty( $pod ) ) { 
  4372. $object = $pod[ 'type' ]; 
  4373. $name = $pod[ 'name' ]; 
  4374.  
  4375. foreach ( $pod[ 'fields' ] as $field ) { 
  4376. PodsForm::delete( $field[ 'type' ], $id, $field[ 'name' ], array_merge( $field, $field[ 'options' ] ), $pod ); 
  4377.  
  4378. // Lookup related fields (non-bidirectional) 
  4379. $params = array( 
  4380. 'where' => array( 
  4381. array( 
  4382. 'key' => 'type',  
  4383. 'value' => 'pick' 
  4384. ),  
  4385. array( 
  4386. 'key' => 'pick_object',  
  4387. 'value' => $object 
  4388. ); 
  4389.  
  4390. if ( !empty( $name ) && $name != $object ) { 
  4391. $params[ 'where' ][] = array( 
  4392. 'key' => 'pick_val',  
  4393. 'value' => $name 
  4394. ); 
  4395.  
  4396. $fields = $this->load_fields( $params, false ); 
  4397.  
  4398. if ( !empty( $pod ) && 'media' == $pod[ 'type' ] ) { 
  4399. $params[ 'where' ] = array( 
  4400. array( 
  4401. 'key' => 'type',  
  4402. 'value' => 'file' 
  4403. ); 
  4404.  
  4405. $fields = array_merge( $fields, $this->load_fields( $params, false ) ); 
  4406.  
  4407. if ( is_array( $fields ) && !empty( $fields ) ) { 
  4408. foreach ( $fields as $related_field ) { 
  4409. $related_pod = $this->load_pod( array( 'id' => $related_field[ 'pod_id' ], 'fields' => false ), false ); 
  4410.  
  4411. if ( empty( $related_pod ) ) 
  4412. continue; 
  4413.  
  4414. $related_from = $this->lookup_related_items_from( $related_field[ 'id' ], $related_pod[ 'id' ], $id, $related_field, $related_pod ); 
  4415.  
  4416. $this->delete_relationships( $related_from, $id, $related_pod, $related_field ); 
  4417.  
  4418. if ( !empty( $pod ) && !pods_tableless() ) { 
  4419. pods_query( " 
  4420. DELETE FROM `@wp_podsrel` 
  4421. WHERE 
  4422. `pod_id` = %d 
  4423. AND `item_id` = %d 
  4424. OR ( 
  4425. `related_pod_id` = %d 
  4426. AND `related_item_id` = %d 
  4427. ", array( 
  4428. $pod[ 'id' ],  
  4429. $id,  
  4430.  
  4431. $pod[ 'id' ],  
  4432. $id 
  4433. ) ); 
  4434.  
  4435. return true; 
  4436.  
  4437. /** 
  4438. * Delete relationships 
  4439. * @param int|array $related_id IDs for items to save 
  4440. * @param int|array $id ID or IDs to remove 
  4441. * @param array $related_pod Pod data 
  4442. * @param array $related_field Field data 
  4443. * @return void 
  4444. * @since 2.3 
  4445. */ 
  4446. public function delete_relationships ( $related_id, $id, $related_pod, $related_field ) { 
  4447. if ( is_array( $related_id ) ) { 
  4448. foreach ( $related_id as $rid ) { 
  4449. $this->delete_relationships( $rid, $id, $related_pod, $related_field ); 
  4450.  
  4451. return; 
  4452.  
  4453. if ( is_array( $id ) ) { 
  4454. foreach ( $id as $rid ) { 
  4455. $this->delete_relationships( $related_id, $rid, $related_pod, $related_field ); 
  4456.  
  4457. return; 
  4458.  
  4459. $id = (int) $id; 
  4460.  
  4461. if ( empty( $id ) ) 
  4462. return; 
  4463.  
  4464. $related_ids = $this->lookup_related_items( $related_field[ 'id' ], $related_pod[ 'id' ], $related_id, $related_field, $related_pod ); 
  4465.  
  4466. if ( empty( $related_ids ) ) 
  4467. return; 
  4468. elseif ( !in_array( $id, $related_ids ) ) 
  4469. return; 
  4470.  
  4471. if ( isset( self::$related_item_cache[ $related_pod[ 'id' ] ][ $related_field[ 'id' ] ] ) ) { 
  4472. // Delete relationship from cache 
  4473. unset( self::$related_item_cache[ $related_pod[ 'id' ] ][ $related_field[ 'id' ] ] ); 
  4474. unset( $related_ids[ array_search( $id, $related_ids ) ] ); 
  4475.  
  4476. $no_conflict = pods_no_conflict_check( $related_pod[ 'type' ] ); 
  4477.  
  4478. if ( !$no_conflict ) 
  4479. pods_no_conflict_on( $related_pod[ 'type' ] ); 
  4480.  
  4481. // Post Types, Media, Users, and Comments (meta-based) 
  4482. if ( in_array( $related_pod[ 'type' ], array( 'post_type', 'media', 'taxonomy', 'user', 'comment' ) ) ) { 
  4483. $object_type = $related_pod[ 'type' ]; 
  4484.  
  4485. if ( in_array( $object_type, array( 'post_type', 'media' ) ) ) 
  4486. $object_type = 'post'; 
  4487. elseif ( 'taxonomy' == $object_type ) 
  4488. $object_type = 'term'; 
  4489.  
  4490. delete_metadata( $object_type, $related_id, $related_field[ 'name' ] ); 
  4491.  
  4492. if ( !empty( $related_ids ) ) { 
  4493. update_metadata( $object_type, $related_id, '_pods_' . $related_field[ 'name' ], $related_ids ); 
  4494.  
  4495. foreach ( $related_ids as $rel_id ) { 
  4496. add_metadata( $object_type, $related_id, $related_field[ 'name' ], $rel_id ); 
  4497. else 
  4498. delete_metadata( $object_type, $related_id, '_pods_' . $related_field[ 'name' ] ); 
  4499. // Custom Settings Pages (options-based) 
  4500. elseif ( 'settings' == $related_pod[ 'type' ] ) { 
  4501. if ( !empty( $related_ids ) ) 
  4502. update_option( $related_pod[ 'name' ] . '_' . $related_field[ 'name' ], $related_ids ); 
  4503. else 
  4504. delete_option( $related_pod[ 'name' ] . '_' . $related_field[ 'name' ] ); 
  4505.  
  4506. // Relationships table 
  4507. if ( !pods_tableless() ) { 
  4508. pods_query( " 
  4509. DELETE FROM `@wp_podsrel` 
  4510. WHERE 
  4511. `pod_id` = %d 
  4512. AND `field_id` = %d 
  4513. AND `item_id` = %d 
  4514. AND `related_item_id` = %d 
  4515. OR ( 
  4516. `related_pod_id` = %d 
  4517. AND `related_field_id` = %d 
  4518. AND `related_item_id` = %d 
  4519. AND `item_id` = %d 
  4520. ", array( 
  4521. $related_pod[ 'id' ],  
  4522. $related_field[ 'id' ],  
  4523. $related_id,  
  4524. $id,  
  4525.  
  4526. $related_pod[ 'id' ],  
  4527. $related_field[ 'id' ],  
  4528. $related_id,  
  4529. $id 
  4530. ) ); 
  4531.  
  4532. if ( !$no_conflict ) 
  4533. pods_no_conflict_off( $related_pod[ 'type' ] ); 
  4534.  
  4535. /** 
  4536. * Check if a Pod exists 
  4537. * $params['id'] int Pod ID 
  4538. * $params['name'] string Pod name 
  4539. * @param array $params An associative array of parameters 
  4540. * @return bool True if exists 
  4541. * @since 1.12 
  4542. */ 
  4543. public function pod_exists ( $params, $type = null ) { 
  4544. if ( is_string( $params ) ) 
  4545. $params = array( 'name' => $params ); 
  4546.  
  4547. $params = (object) pods_sanitize( $params ); 
  4548.  
  4549. if ( !empty( $params->id ) || !empty( $params->name ) ) { 
  4550. if ( !isset( $params->name ) ) 
  4551. $pod = get_post( $dummy = (int) $params->id ); 
  4552. else { 
  4553. $pod = get_posts( array( 
  4554. 'name' => $params->name,  
  4555. 'post_type' => '_pods_pod',  
  4556. 'posts_per_page' => 1 
  4557. ) ); 
  4558.  
  4559. if ( !empty( $pod ) && ( empty( $type ) || $type == get_post_meta( $pod->ID, 'type', true ) ) ) 
  4560. return true; 
  4561.  
  4562. return false; 
  4563.  
  4564. /** 
  4565. * Load a Pod and all of its fields 
  4566. * $params['id'] int The Pod ID 
  4567. * $params['name'] string The Pod name 
  4568. * $params['fields'] bool Whether to load fields (default is true) 
  4569. * @param array|object $params An associative array of parameters or pod name as a string 
  4570. * @param bool $strict Makes sure the pod exists, throws an error if it doesn't work 
  4571. * @return array|bool|mixed|void 
  4572. * @since 1.7.9 
  4573. */ 
  4574. public function load_pod ( $params, $strict = true ) { 
  4575.  
  4576. /** 
  4577. * @var $sitepress SitePress 
  4578. * @var $wpdb wpdb 
  4579. */ 
  4580. global $sitepress, $icl_adjust_id_url_filter_off, $wpdb; 
  4581.  
  4582. $current_language = false; 
  4583. $load_fields = true; 
  4584.  
  4585. // WPML support 
  4586. if ( is_object( $sitepress ) && !$icl_adjust_id_url_filter_off ) 
  4587. $current_language = pods_sanitize( ICL_LANGUAGE_CODE ); 
  4588. // Polylang support 
  4589. elseif ( function_exists( 'pll_current_language' ) ) 
  4590. $current_language = pll_current_language( 'slug' ); 
  4591.  
  4592. if ( !is_array( $params ) && !is_object( $params ) ) 
  4593. $params = array( 'name' => $params, 'table_info' => false, 'fields' => true ); 
  4594.  
  4595. if ( is_object( $params ) && isset( $params->fields ) && !$params->fields ) 
  4596. $load_fields = false; 
  4597. elseif ( is_array( $params ) && isset( $params[ 'fields' ] ) && !$params[ 'fields' ] ) 
  4598. $load_fields = false; 
  4599.  
  4600. $table_info = false; 
  4601.  
  4602. if ( is_object( $params ) && ! empty( $params->table_info ) ) 
  4603. $table_info = true; 
  4604. elseif ( is_array( $params ) && ! empty( $params[ 'table_info' ] ) ) 
  4605. $table_info = true; 
  4606.  
  4607. $transient = 'pods_' . $wpdb->prefix . '_pod'; 
  4608.  
  4609. if ( !empty( $current_language ) ) 
  4610. $transient .= '_' . $current_language; 
  4611.  
  4612. if ( !$load_fields ) 
  4613. $transient .= '_nofields'; 
  4614.  
  4615. if ( $table_info ) 
  4616. $transient .= '_tableinfo'; 
  4617.  
  4618. if ( is_object( $params ) && isset( $params->post_name ) ) { 
  4619. $pod = false; 
  4620.  
  4621. if ( pods_api_cache() ) 
  4622. $pod = pods_transient_get( $transient . '_' . $params->post_name ); 
  4623.  
  4624. if ( false !== $pod && ( ! $table_info || isset( $pod[ 'table' ] ) ) ) { 
  4625. if ( in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) && is_object( $sitepress ) && !$icl_adjust_id_url_filter_off ) 
  4626. $pod = array_merge( $pod, $this->get_table_info( $pod[ 'type' ], $pod[ 'object' ], $pod[ 'name' ], $pod ) ); 
  4627.  
  4628. return $pod; 
  4629.  
  4630. $_pod = get_object_vars( $params ); 
  4631. else { 
  4632. $params = (object) pods_sanitize( $params ); 
  4633.  
  4634. if ( ( !isset( $params->id ) || empty( $params->id ) ) && ( !isset( $params->name ) || empty( $params->name ) ) ) { 
  4635. if ( $strict ) 
  4636. return pods_error( 'Either Pod ID or Name are required', $this ); 
  4637.  
  4638. return false; 
  4639.  
  4640. if ( isset( $params->name ) ) { 
  4641. $pod = false; 
  4642.  
  4643. if ( '_pods_pod' == $params->name ) { 
  4644. $pod = array( 
  4645. 'id' => 0,  
  4646. 'name' => $params->name,  
  4647. 'label' => __( 'Pods', 'pods' ),  
  4648. 'type' => 'post_type',  
  4649. 'storage' => 'meta',  
  4650. 'options' => array( 
  4651. 'label_singular' => __( 'Pod', 'pods' ) 
  4652. ),  
  4653. 'fields' => array() 
  4654. ); 
  4655. elseif ( '_pods_field' == $params->name ) { 
  4656. $pod = array( 
  4657. 'id' => 0,  
  4658. 'name' => $params->name,  
  4659. 'label' => __( 'Pod Fields', 'pods' ),  
  4660. 'type' => 'post_type',  
  4661. 'storage' => 'meta',  
  4662. 'options' => array( 
  4663. 'label_singular' => __( 'Pod Field', 'pods' ) 
  4664. ),  
  4665. 'fields' => array() 
  4666. ); 
  4667. elseif ( pods_api_cache() ) 
  4668. $pod = pods_transient_get( $transient . '_' . $params->name ); 
  4669.  
  4670. if ( false !== $pod && ( ! $table_info || isset( $pod[ 'table' ] ) ) ) { 
  4671. if ( in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) && is_object( $sitepress ) && !$icl_adjust_id_url_filter_off ) 
  4672. $pod = array_merge( $pod, $this->get_table_info( $pod[ 'type' ], $pod[ 'object' ], $pod[ 'name' ], $pod ) ); 
  4673.  
  4674. return $pod; 
  4675.  
  4676. if ( !isset( $params->name ) ) 
  4677. $pod = get_post( $dummy = (int) $params->id ); 
  4678. else { 
  4679. $pod = get_posts( array( 
  4680. 'name' => $params->name,  
  4681. 'post_type' => '_pods_pod',  
  4682. 'posts_per_page' => 1 
  4683. ) ); 
  4684.  
  4685. if ( empty( $pod ) ) { 
  4686. if ( $strict ) 
  4687. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  4688.  
  4689. return false; 
  4690.  
  4691. if ( is_array( $pod ) ) 
  4692. $pod = $pod[ 0 ]; 
  4693.  
  4694. $_pod = get_object_vars( $pod ); 
  4695.  
  4696. $pod = false; 
  4697.  
  4698. if ( pods_api_cache() ) 
  4699. $pod = pods_transient_get( $transient . '_' . $_pod[ 'post_name' ] ); 
  4700.  
  4701. if ( false !== $pod && ( ! $table_info || isset( $pod[ 'table' ] ) ) ) { 
  4702. if ( in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) && is_object( $sitepress ) && !$icl_adjust_id_url_filter_off ) 
  4703. $pod = array_merge( $pod, $this->get_table_info( $pod[ 'type' ], $pod[ 'object' ], $pod[ 'name' ], $pod ) ); 
  4704.  
  4705. return $pod; 
  4706.  
  4707. $pod = array( 
  4708. 'id' => $_pod[ 'ID' ],  
  4709. 'name' => $_pod[ 'post_name' ],  
  4710. 'label' => $_pod[ 'post_title' ],  
  4711. 'description' => $_pod[ 'post_content' ] 
  4712. ); 
  4713.  
  4714. if ( strlen( $pod[ 'label' ] ) < 1 ) 
  4715. $pod[ 'label' ] = $pod[ 'name' ]; 
  4716.  
  4717. // @todo update with a method to put all options in 
  4718. $defaults = array( 
  4719. 'show_in_menu' => 1,  
  4720. 'type' => 'post_type',  
  4721. 'storage' => 'meta',  
  4722. 'object' => '',  
  4723. 'alias' => '' 
  4724. ); 
  4725.  
  4726. $pod[ 'options' ] = get_post_meta( $pod[ 'id' ] ); 
  4727.  
  4728. foreach ( $pod[ 'options' ] as $option => $value ) { 
  4729. if ( is_array( $value ) ) { 
  4730. foreach ( $value as $k => $v ) { 
  4731. if ( !is_array( $v ) ) 
  4732. $value[ $k ] = maybe_unserialize( $v ); 
  4733.  
  4734. if ( 1 == count( $value ) ) 
  4735. $value = current( $value ); 
  4736. else 
  4737. $value = maybe_unserialize( $value ); 
  4738.  
  4739. $pod[ 'options' ][ $option ] = $value; 
  4740.  
  4741. $pod[ 'options' ] = array_merge( $defaults, $pod[ 'options' ] ); 
  4742.  
  4743. $pod[ 'type' ] = $pod[ 'options' ][ 'type' ]; 
  4744. $pod[ 'storage' ] = $pod[ 'options' ][ 'storage' ]; 
  4745. $pod[ 'object' ] = $pod[ 'options' ][ 'object' ]; 
  4746. $pod[ 'alias' ] = $pod[ 'options' ][ 'alias' ]; 
  4747.  
  4748. unset( $pod[ 'options' ][ 'type' ] ); 
  4749. unset( $pod[ 'options' ][ 'storage' ] ); 
  4750. unset( $pod[ 'options' ][ 'object' ] ); 
  4751. unset( $pod[ 'options' ][ 'alias' ] ); 
  4752.  
  4753. if ( $table_info ) 
  4754. $pod = array_merge( $this->get_table_info( $pod[ 'type' ], $pod[ 'object' ], $pod[ 'name' ], $pod ), $pod ); 
  4755.  
  4756. // Override old 'none' storage type 
  4757. if ( 'taxonomy' == $pod['type'] && 'none' == $pod['storage'] && function_exists( 'get_term_meta' ) ) { 
  4758. $pod[ 'storage' ] = 'meta'; 
  4759.  
  4760. if ( isset( $pod[ 'pod' ] ) ) 
  4761. unset( $pod[ 'pod' ] ); 
  4762.  
  4763. $pod[ 'fields' ] = array(); 
  4764.  
  4765. $pod[ 'object_fields' ] = array(); 
  4766.  
  4767. if ( 'pod' != $pod[ 'type' ] ) 
  4768. $pod[ 'object_fields' ] = $this->get_wp_object_fields( $pod[ 'type' ], $pod ); 
  4769.  
  4770. $fields = get_posts( array( 
  4771. 'post_type' => '_pods_field',  
  4772. 'posts_per_page' => -1,  
  4773. 'nopaging' => true,  
  4774. 'post_parent' => $pod[ 'id' ],  
  4775. 'orderby' => 'menu_order',  
  4776. 'order' => 'ASC' 
  4777. ) ); 
  4778.  
  4779. if ( !empty( $fields ) ) { 
  4780. foreach ( $fields as $field ) { 
  4781. $field->pod = $pod[ 'name' ]; 
  4782. $field->table_info = $table_info; 
  4783.  
  4784. if ( $load_fields ) { 
  4785. $field = $this->load_field( $field ); 
  4786.  
  4787. $field = PodsForm::field_setup( $field, null, $field[ 'type' ] ); 
  4788. else { 
  4789. $field = array( 
  4790. 'id' => $field->ID,  
  4791. 'name' => $field->post_name,  
  4792. 'label' => $field->post_title,  
  4793. 'type' => get_post_meta( $field->ID, 'type', true ) 
  4794. ); 
  4795.  
  4796. $pod[ 'fields' ][ $field[ 'name' ] ] = $field; 
  4797.  
  4798. if ( did_action( 'init' ) && pods_api_cache() ) 
  4799. pods_transient_set( $transient . '_' . $pod[ 'name' ], $pod ); 
  4800.  
  4801. return $pod; 
  4802.  
  4803. /** 
  4804. * Load a list of Pods based on filters specified. 
  4805. * $params['type'] string/array Pod Type(s) to filter by 
  4806. * $params['object'] string/array Pod Object(s) to filter by 
  4807. * $params['options'] array Pod Option(s) key=>value array to filter by 
  4808. * $params['orderby'] string ORDER BY clause of query 
  4809. * $params['limit'] string Number of Pods to return 
  4810. * $params['where'] string WHERE clause of query 
  4811. * $params['ids'] string|array IDs of Objects 
  4812. * $params['count'] boolean Return only a count of Pods 
  4813. * $params['names'] boolean Return only an array of name => label 
  4814. * $params['ids'] boolean Return only an array of ID => label 
  4815. * $params['fields'] boolean Return pod fields with Pods (default is true) 
  4816. * $params['key_names'] boolean Return pods keyed by name 
  4817. * @param array $params An associative array of parameters 
  4818. * @return array|mixed 
  4819. * @uses PodsAPI::load_pod 
  4820. * @since 2.0 
  4821. */ 
  4822. public function load_pods ( $params = null ) { 
  4823.  
  4824. /** 
  4825. * @var $sitepress SitePress 
  4826. */ 
  4827. global $sitepress, $icl_adjust_id_url_filter_off; 
  4828.  
  4829. $current_language = false; 
  4830.  
  4831. // WPML support 
  4832. if ( is_object( $sitepress ) && !$icl_adjust_id_url_filter_off ) 
  4833. $current_language = pods_sanitize( ICL_LANGUAGE_CODE ); 
  4834. // Polylang support 
  4835. elseif ( function_exists( 'pll_current_language' ) ) 
  4836. $current_language = pll_current_language( 'slug' ); 
  4837.  
  4838. $params = (object) pods_sanitize( $params ); 
  4839.  
  4840. $order = 'ASC'; 
  4841. $orderby = 'menu_order title'; 
  4842. $limit = -1; 
  4843. $ids = false; 
  4844.  
  4845. $meta_query = array(); 
  4846. $cache_key = ''; 
  4847.  
  4848. if ( isset( $params->type ) && !empty( $params->type ) ) { 
  4849. if ( !is_array( $params->type ) ) 
  4850. $params->type = array( trim( $params->type ) ); 
  4851.  
  4852. sort( $params->type ); 
  4853.  
  4854. $meta_query[] = array( 
  4855. 'key' => 'type',  
  4856. 'value' => $params->type,  
  4857. 'compare' => 'IN' 
  4858. ); 
  4859.  
  4860. if ( 0 < count( $params->type ) ) 
  4861. $cache_key .= '_type_' . trim( implode( '_', $params->type ) ); 
  4862.  
  4863. if ( isset( $params->object ) && !empty( $params->object ) ) { 
  4864. if ( !is_array( $params->object ) ) 
  4865. $params->object = array( $params->object ); 
  4866.  
  4867. $params->object = pods_trim( $params->object ); 
  4868.  
  4869. sort( $params->object ); 
  4870.  
  4871. $meta_query[] = array( 
  4872. 'key' => 'object',  
  4873. 'value' => $params->object,  
  4874. 'compare' => 'IN' 
  4875. ); 
  4876.  
  4877. if ( 1 == count( $params->object ) ) 
  4878. $cache_key .= '_object_' . trim( implode( '', $params->object ) ); 
  4879.  
  4880. if ( isset( $params->options ) && !empty( $params->options ) && is_array( $params->options ) ) { 
  4881. foreach ( $params->options as $option => $value ) { 
  4882. if ( !is_array( $value ) ) 
  4883. $value = array( $value ); 
  4884.  
  4885. $value = pods_trim( $value ); 
  4886.  
  4887. sort( $value ); 
  4888.  
  4889. $meta_query[] = array( 
  4890. 'key' => $option,  
  4891. 'value' => pods_sanitize( $value ),  
  4892. 'compare' => 'IN' 
  4893. ); 
  4894.  
  4895. $cache_key = ''; 
  4896.  
  4897. if ( isset( $params->where ) && is_array( $params->where ) ) 
  4898. $meta_query = array_merge( $meta_query, (array) $params->where ); 
  4899.  
  4900. if ( isset( $params->order ) && !empty( $params->order ) && in_array( strtoupper( $params->order ), array( 'ASC', 'DESC' ) ) ) 
  4901. $order = strtoupper( $params->order ); 
  4902.  
  4903. if ( isset( $params->orderby ) && !empty( $params->orderby ) ) 
  4904. $orderby = strtoupper( $params->orderby ); 
  4905.  
  4906. if ( isset( $params->limit ) && !empty( $params->limit ) ) 
  4907. $limit = pods_absint( $params->limit ); 
  4908.  
  4909. if ( isset( $params->ids ) && !empty( $params->ids ) ) { 
  4910. $ids = $params->ids; 
  4911.  
  4912. if ( !is_array( $ids ) ) 
  4913. $ids = explode( ', ', $ids ); 
  4914.  
  4915. if ( empty( $ids ) ) 
  4916. $ids = false; 
  4917.  
  4918. $pre_key = ''; 
  4919.  
  4920. if ( !empty( $current_language ) ) 
  4921. $pre_key .= '_' . $current_language; 
  4922.  
  4923. if ( isset( $params->count ) && $params->count ) 
  4924. $pre_key .= '_count'; 
  4925.  
  4926. if ( isset( $params->ids ) && $params->ids && !empty( $ids ) ) 
  4927. $pre_key .= '_ids_' . implode( '_', $ids ); 
  4928.  
  4929. if ( isset( $params->names ) && $params->names ) 
  4930. $pre_key .= '_names'; 
  4931. elseif ( isset( $params->names_ids ) && $params->names_ids ) 
  4932. $pre_key .= '_names_ids'; 
  4933.  
  4934. if ( isset( $params->key_names ) && $params->key_names ) 
  4935. $pre_key .= '_namekeys'; 
  4936.  
  4937. if ( isset( $params->fields ) && !$params->fields ) 
  4938. $pre_key .= '_nofields'; 
  4939.  
  4940. if ( isset( $params->table_info ) && $params->table_info ) 
  4941. $pre_key .= '_tableinfo'; 
  4942.  
  4943.  
  4944. $pre_key .= '_get'; 
  4945.  
  4946. if ( empty( $cache_key ) ) 
  4947. $cache_key = 'pods' . $pre_key . '_all'; 
  4948. else 
  4949. $cache_key = 'pods' . $pre_key . $cache_key; 
  4950.  
  4951. if ( pods_api_cache() && !empty( $cache_key ) && ( 'pods' . ( !empty( $current_language ) ? '_' . $current_language : '' ) . '_get_all' != $cache_key || empty( $meta_query ) ) && $limit < 1 && ( empty( $orderby ) || 'menu_order title' == $orderby ) && empty( $ids ) ) { 
  4952. $the_pods = pods_transient_get( $cache_key ); 
  4953.  
  4954. if ( false === $the_pods ) 
  4955. $the_pods = pods_cache_get( $cache_key, 'pods' ); 
  4956.  
  4957. if ( !is_array( $the_pods ) && 'none' == $the_pods ) 
  4958. return array(); 
  4959. elseif ( false !== $the_pods ) 
  4960. return $the_pods; 
  4961.  
  4962. $the_pods = array(); 
  4963.  
  4964. $args = array( 
  4965. 'post_type' => '_pods_pod',  
  4966. 'nopaging' => true,  
  4967. 'posts_per_page' => $limit,  
  4968. 'order' => $order,  
  4969. 'orderby' => $orderby,  
  4970. 'meta_query' => $meta_query,  
  4971. ); 
  4972.  
  4973. // Only set post__in if there are ids to filter (see https://core.trac.wordpress.org/ticket/28099) 
  4974. if ( false != $ids ) { 
  4975. $args[ 'post__in' ] = $ids; 
  4976.  
  4977. $_pods = get_posts( $args ); 
  4978.  
  4979. $export_ignore = array( 
  4980. 'object_type',  
  4981. 'object_name',  
  4982. 'table',  
  4983. 'meta_table',  
  4984. 'pod_table',  
  4985. 'field_id',  
  4986. 'field_index',  
  4987. 'field_slug',  
  4988. 'field_type',  
  4989. 'field_parent',  
  4990. 'field_parent_select',  
  4991. 'meta_field_id',  
  4992. 'meta_field_index',  
  4993. 'meta_field_value',  
  4994. 'pod_field_id',  
  4995. 'pod_field_index',  
  4996. 'object_fields',  
  4997. 'join',  
  4998. 'where',  
  4999. 'where_default',  
  5000. 'orderby',  
  5001. 'pod',  
  5002. 'recurse',  
  5003. 'table_info',  
  5004. 'attributes',  
  5005. 'group',  
  5006. 'grouped',  
  5007. 'developer_mode',  
  5008. 'dependency',  
  5009. 'depends-on',  
  5010. 'excludes-on' 
  5011. ); 
  5012.  
  5013. $total_fields = 0; 
  5014.  
  5015. if ( isset( $params->count ) && $params->count ) 
  5016. $the_pods = count( $_pods ); 
  5017. else { 
  5018. foreach ( $_pods as $pod ) { 
  5019. if ( isset( $params->names ) && $params->names ) 
  5020. $the_pods[ $pod->post_name ] = $pod->post_title; 
  5021. elseif ( isset( $params->names_ids ) && $params->names_ids ) 
  5022. $the_pods[ $pod->ID ] = $pod->post_name; 
  5023. else { 
  5024. if ( isset( $params->fields ) && !$params->fields ) 
  5025. $pod->fields = false; 
  5026.  
  5027. $pod = $this->load_pod( $pod ); 
  5028.  
  5029. // Remove extra data not needed 
  5030. if ( pods_var( 'export', $params, false ) && ( !isset( $params->fields ) || $params->fields ) ) { 
  5031. foreach ( $export_ignore as $ignore ) { 
  5032. if ( isset( $pod[ $ignore ] ) ) 
  5033. unset( $pod[ $ignore ] ); 
  5034.  
  5035. foreach ( $pod[ 'fields' ] as $field => $field_data ) { 
  5036. if ( isset( $pod[ 'fields' ][ $field ][ 'table_info' ] ) ) 
  5037. unset( $pod[ 'fields' ][ $field ][ 'table_info' ] ); 
  5038.  
  5039. $total_fields += count( $pod[ 'fields' ] ); 
  5040.  
  5041. if ( isset( $params->key_names ) && $params->key_names ) 
  5042. $the_pods[ $pod[ 'name' ] ] = $pod; 
  5043. else 
  5044. $the_pods[ $pod[ 'id' ] ] = $pod; 
  5045.  
  5046. if ( ( !function_exists( 'pll_current_language' ) || ( isset( $params->refresh ) && $params->refresh ) ) && !empty( $cache_key ) && ( 'pods' != $cache_key || empty( $meta_query ) ) && $limit < 1 && ( empty( $orderby ) || 'menu_order title' == $orderby ) && empty( $ids ) ) { 
  5047. // Too many Pods can cause issues with the DB when caching is not enabled 
  5048. if ( 15 < count( $the_pods ) || 75 < count( $total_fields ) ) { 
  5049. pods_transient_clear( $cache_key ); 
  5050.  
  5051. if ( pods_api_cache() ) { 
  5052. if ( empty( $the_pods ) && ( !isset( $params->count ) || !$params->count ) ) 
  5053. pods_cache_set( $cache_key, 'none', 'pods' ); 
  5054. else 
  5055. pods_cache_set( $cache_key, $the_pods, 'pods' ); 
  5056. else { 
  5057. pods_cache_clear( $cache_key, 'pods' ); 
  5058.  
  5059. if ( pods_api_cache() ) { 
  5060. if ( empty( $the_pods ) && ( !isset( $params->count ) || !$params->count ) ) 
  5061. pods_transient_set( $cache_key, 'none' ); 
  5062. else 
  5063. pods_transient_set( $cache_key, $the_pods ); 
  5064.  
  5065. return $the_pods; 
  5066.  
  5067. /** 
  5068. * Check if a Pod's field exists 
  5069. * $params['pod_id'] int The Pod ID 
  5070. * $params['id'] int The field ID 
  5071. * $params['name'] string The field name 
  5072. * @param array $params An associative array of parameters 
  5073. * @return bool 
  5074. * @since 1.12 
  5075. */ 
  5076. public function field_exists ( $params ) { 
  5077. $params = (object) pods_sanitize( $params ); 
  5078.  
  5079. if ( ( !empty( $params->id ) || !empty( $params->name ) ) && isset( $params->pod_id ) && !empty( $params->pod_id ) ) { 
  5080. if ( !isset( $params->name ) ) 
  5081. $field = get_post( $dummy = (int) $params->id ); 
  5082. else { 
  5083. $field = get_posts( array( 
  5084. 'name' => $params->name,  
  5085. 'post_type' => '_pods_field',  
  5086. 'posts_per_page' => 1,  
  5087. 'post_parent' => $params->pod_id 
  5088. ) ); 
  5089.  
  5090. if ( !empty( $field ) ) 
  5091. return true; 
  5092.  
  5093. return false; 
  5094.  
  5095. /** 
  5096. * Load a field 
  5097. * $params['pod_id'] int The Pod ID 
  5098. * $params['pod'] string The Pod name 
  5099. * $params['id'] int The field ID 
  5100. * $params['name'] string The field name 
  5101. * $params['table_info'] boolean Whether to lookup a pick field's table info 
  5102. * @param array $params An associative array of parameters 
  5103. * @param boolean $strict Whether to require a field exist or not when loading the info 
  5104. * @return array|bool Array with field data, false if field not found 
  5105. * @since 1.7.9 
  5106. */ 
  5107. public function load_field ( $params, $strict = false ) { 
  5108. $params = (object) $params; 
  5109.  
  5110. if ( !isset( $params->table_info ) ) 
  5111. $params->table_info = false; 
  5112.  
  5113. $pod = array(); 
  5114. $field = array(); 
  5115.  
  5116. if ( isset( $params->post_title ) ) 
  5117. $_field = $params; 
  5118. elseif ( isset( $params->id ) && !empty( $params->id ) ) 
  5119. $_field = get_post( $dumb = (int) $params->id ); 
  5120. else { 
  5121. if ( !isset( $params->pod ) ) 
  5122. $params->pod = ''; 
  5123.  
  5124. if ( !isset( $params->pod_id ) ) 
  5125. $params->pod_id = 0; 
  5126.  
  5127. if ( isset( $params->pod_data ) ) 
  5128. $pod = $params->pod_data; 
  5129. else { 
  5130. $pod = $this->load_pod( array( 'name' => $params->pod, 'id' => $params->pod_id, 'table_info' => false ), false ); 
  5131.  
  5132. if ( false === $pod ) { 
  5133. if ( $strict ) 
  5134. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  5135.  
  5136. return false; 
  5137.  
  5138. $params->pod_id = $pod[ 'id' ]; 
  5139. $params->pod = $pod[ 'name' ]; 
  5140.  
  5141. if ( empty( $params->name ) && empty( $params->pod ) && empty( $params->pod_id ) ) 
  5142. return pods_error( __( 'Either Field Name or Field ID / Pod ID are required', 'pods' ), $this ); 
  5143.  
  5144. $params->name = pods_clean_name( $params->name, true, ( 'meta' == $pod[ 'storage' ] ? false : true ) ); 
  5145.  
  5146. if ( isset( $pod[ 'fields' ][ $params->name ] ) && isset( $pod[ 'fields' ][ $params->name ][ 'id' ] ) ) 
  5147. return $pod[ 'fields' ][ $params->name ]; 
  5148.  
  5149. $field = false; 
  5150.  
  5151. if ( pods_api_cache() ) 
  5152. $field = pods_transient_get( 'pods_field_' . $params->pod . '_' . $params->name ); 
  5153.  
  5154. if ( empty( $field ) ) { 
  5155. $field = get_posts( array( 
  5156. 'name' => $params->name,  
  5157. 'post_type' => '_pods_field',  
  5158. 'posts_per_page' => 1,  
  5159. 'post_parent' => $params->pod_id 
  5160. ) ); 
  5161.  
  5162. if ( empty( $field ) ) { 
  5163. if ( $strict ) 
  5164. return pods_error( __( 'Field not found', 'pods' ), $this ); 
  5165.  
  5166. return false; 
  5167.  
  5168. $_field = $field[ 0 ]; 
  5169.  
  5170. $field = array(); 
  5171.  
  5172. if ( empty( $_field ) ) { 
  5173. if ( $strict ) 
  5174. return pods_error( __( 'Field not found', 'pods' ), $this ); 
  5175.  
  5176. return false; 
  5177.  
  5178. $_field = get_object_vars( $_field ); 
  5179.  
  5180. if ( !isset( $pod[ 'name' ] ) && !isset( $_field[ 'pod' ] ) ) { 
  5181. if ( 0 < $_field[ 'post_parent' ] ) 
  5182. $pod = $this->load_pod( array( 'id' => $_field[ 'post_parent' ], 'table_info' => false ), false ); 
  5183.  
  5184. if ( empty( $pod ) ) { 
  5185. if ( $strict ) 
  5186. return pods_error( __( 'Pod for field not found', 'pods' ), $this ); 
  5187.  
  5188. return false; 
  5189.  
  5190. if ( empty( $field ) ) { 
  5191. if ( pods_api_cache() && ( isset( $pod[ 'name' ] ) || isset( $_field[ 'pod' ] ) ) ) 
  5192. $field = pods_transient_get( 'pods_field_' . pods_var( 'name', $pod, pods_var( 'pod', $_field ), null, true ) . '_' . $_field[ 'post_name' ] ); 
  5193.  
  5194. if ( empty( $field ) ) { 
  5195. $defaults = array( 
  5196. 'type' => 'text' 
  5197. ); 
  5198.  
  5199. $field = array( 
  5200. 'id' => $_field[ 'ID' ],  
  5201. 'name' => $_field[ 'post_name' ],  
  5202. 'label' => $_field[ 'post_title' ],  
  5203. 'description' => $_field[ 'post_content' ],  
  5204. 'weight' => $_field[ 'menu_order' ],  
  5205. 'pod_id' => $_field[ 'post_parent' ],  
  5206. 'pick_object' => '',  
  5207. 'pick_val' => '',  
  5208. 'sister_id' => '',  
  5209. 'table_info' => array() 
  5210. ); 
  5211.  
  5212. if ( isset( $pod[ 'name' ] ) ) 
  5213. $field[ 'pod' ] = $pod[ 'name' ]; 
  5214. elseif ( isset( $_field[ 'pod' ] ) ) 
  5215. $field[ 'pod' ] = $_field[ 'pod' ]; 
  5216.  
  5217. $field[ 'options' ] = get_post_meta( $field[ 'id' ] ); 
  5218.  
  5219. $options_ignore = array( 
  5220. 'method',  
  5221. 'table_info',  
  5222. 'attributes',  
  5223. 'group',  
  5224. 'grouped',  
  5225. 'developer_mode',  
  5226. 'dependency',  
  5227. 'depends-on',  
  5228. 'excludes-on' 
  5229. ); 
  5230.  
  5231. foreach ( $options_ignore as $ignore ) { 
  5232. if ( isset( $field[ 'options' ][ $ignore ] ) ) 
  5233. unset( $field[ 'options' ][ $ignore ] ); 
  5234.  
  5235. foreach ( $field[ 'options' ] as $option => $value ) { 
  5236. if ( is_array( $value ) ) { 
  5237. foreach ( $value as $k => $v ) { 
  5238. if ( !is_array( $v ) ) 
  5239. $value[ $k ] = maybe_unserialize( $v ); 
  5240.  
  5241. if ( 1 == count( $value ) ) 
  5242. $value = current( $value ); 
  5243. else 
  5244. $value = maybe_unserialize( $value ); 
  5245.  
  5246. $field[ 'options' ][ $option ] = $value; 
  5247.  
  5248. $field[ 'options' ] = array_merge( $defaults, $field[ 'options' ] ); 
  5249.  
  5250. $field[ 'type' ] = $field[ 'options' ][ 'type' ]; 
  5251.  
  5252. unset( $field[ 'options' ][ 'type' ] ); 
  5253.  
  5254. if ( isset( $field[ 'options' ][ 'pick_object' ] ) ) { 
  5255. $field[ 'pick_object' ] = $field[ 'options' ][ 'pick_object' ]; 
  5256.  
  5257. unset( $field[ 'options' ][ 'pick_object' ] ); 
  5258.  
  5259. if ( isset( $field[ 'options' ][ 'pick_val' ] ) ) { 
  5260. $field[ 'pick_val' ] = $field[ 'options' ][ 'pick_val' ]; 
  5261.  
  5262. unset( $field[ 'options' ][ 'pick_val' ] ); 
  5263.  
  5264. if ( isset( $field[ 'options' ][ 'sister_id' ] ) ) { 
  5265. $field[ 'sister_id' ] = $field[ 'options' ][ 'sister_id' ]; 
  5266.  
  5267. unset( $field[ 'options' ][ 'sister_id' ] ); 
  5268.  
  5269. if ( isset( $field[ 'options' ][ 'sister_field_id' ] ) ) 
  5270. unset( $field[ 'options' ][ 'sister_field_id' ] ); 
  5271.  
  5272. if ( pods_api_cache() && ( isset( $pod[ 'name' ] ) || isset( $_field[ 'pod' ] ) ) ) 
  5273. pods_transient_set( 'pods_field_' . pods_var( 'name', $pod, pods_var( 'pod', $_field ), null, true ) . '_' . $field[ 'name' ], $field ); 
  5274.  
  5275. $field[ 'table_info' ] = array(); 
  5276.  
  5277. if ( 'pick' == $field[ 'type' ] && $params->table_info ) 
  5278. $field[ 'table_info' ] = $this->get_table_info( $field[ 'pick_object' ], $field[ 'pick_val' ], null, null, $field ); 
  5279.  
  5280. return $field; 
  5281.  
  5282. /** 
  5283. * Load fields by Pod, ID, Name, and/or Type 
  5284. * $params['pod_id'] int The Pod ID 
  5285. * $params['pod'] string The Pod name 
  5286. * $params['id'] array The field IDs 
  5287. * $params['name'] array The field names 
  5288. * $params['type'] array The field types 
  5289. * $params['options'] array Field Option(s) key=>value array to filter by 
  5290. * $params['where'] string WHERE clause of query 
  5291. * @param array $params An associative array of parameters 
  5292. * @param bool $strict Whether to require a field exist or not when loading the info 
  5293. * @return array Array of field data. 
  5294. * @since 1.7.9 
  5295. */ 
  5296. public function load_fields ( $params, $strict = false ) { 
  5297. // @todo Get away from using md5/serialize, I'm sure we can cache specific parts 
  5298. $cache_key = md5( serialize( $params ) ); 
  5299. if ( isset( $this->fields_cache[ $cache_key ] ) ) { 
  5300. return $this->fields_cache[ $cache_key ]; 
  5301.  
  5302. $params = (object) pods_sanitize( $params ); 
  5303.  
  5304. if ( !isset( $params->pod ) || empty( $params->pod ) ) 
  5305. $params->pod = ''; 
  5306.  
  5307. if ( !isset( $params->pod_id ) || empty( $params->pod_id ) ) 
  5308. $params->pod_id = 0; 
  5309.  
  5310. if ( !isset( $params->name ) || empty( $params->name ) ) 
  5311. $params->name = array(); 
  5312. else 
  5313. $params->name = (array) $params->name; 
  5314.  
  5315. if ( !isset( $params->id ) || empty( $params->id ) ) 
  5316. $params->id = array(); 
  5317. else { 
  5318. $params->id = (array) $params->id; 
  5319.  
  5320. foreach ( $params->id as &$id ) { 
  5321. $id = pods_absint( $id ); 
  5322.  
  5323. if ( !isset( $params->type ) || empty( $params->type ) ) 
  5324. $params->type = array(); 
  5325. else 
  5326. $params->type = (array) $params->type; 
  5327.  
  5328. $fields = array(); 
  5329.  
  5330. if ( !empty( $params->pod ) || !empty( $params->pod_id ) ) { 
  5331. $pod = $this->load_pod( array( 'name' => $params->pod, 'id' => $params->pod_id, 'table_info' => true ), false ); 
  5332.  
  5333. if ( false === $pod ) { 
  5334. if ( $strict ) 
  5335. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  5336.  
  5337. return $fields; 
  5338.  
  5339. $pod[ 'fields' ] = array_merge( pods_var_raw( 'object_fields', $pod, array() ), $pod[ 'fields' ] ); 
  5340.  
  5341. foreach ( $pod[ 'fields' ] as $field ) { 
  5342. if ( empty( $params->name ) && empty( $params->id ) && empty( $params->type ) ) 
  5343. $fields[ $field[ 'name' ] ] = $field; 
  5344. elseif ( in_array( $fields[ 'name' ], $params->name ) || in_array( $fields[ 'id' ], $params->id ) || in_array( $fields[ 'type' ], $params->type ) ) 
  5345. $fields[ $field[ 'name' ] ] = $field; 
  5346. elseif ( ( isset( $params->options ) && !empty( $params->options ) && is_array( $params->options ) ) || ( isset( $params->where ) && !empty( $params->where ) && is_array( $params->where ) ) ) { 
  5347. $order = 'ASC'; 
  5348. $orderby = 'menu_order title'; 
  5349. $limit = -1; 
  5350. $ids = false; 
  5351.  
  5352. $meta_query = array(); 
  5353.  
  5354. if ( isset( $params->options ) && !empty( $params->options ) && is_array( $params->options ) ) { 
  5355. foreach ( $params->options as $option => $value ) { 
  5356. if ( !is_array( $value ) ) 
  5357. $value = array( $value ); 
  5358.  
  5359. $value = pods_trim( $value ); 
  5360.  
  5361. sort( $value ); 
  5362.  
  5363. $meta_query[] = array( 
  5364. 'key' => $option,  
  5365. 'value' => pods_sanitize( $value ),  
  5366. 'compare' => 'IN' 
  5367. ); 
  5368.  
  5369. if ( isset( $params->where ) && !empty( $params->where ) && is_array( $params->where ) ) 
  5370. $meta_query = array_merge( $meta_query, (array) $params->where ); 
  5371.  
  5372. $args = array( 
  5373. 'post_type' => '_pods_field',  
  5374. 'nopaging' => true,  
  5375. 'posts_per_page' => $limit,  
  5376. 'order' => $order,  
  5377. 'orderby' => $orderby,  
  5378. 'meta_query' => $meta_query,  
  5379. ); 
  5380.  
  5381. // Only set post__in if there are ids to filter (see https://core.trac.wordpress.org/ticket/28099) 
  5382. if ( false != $ids ) { 
  5383. $args[ 'post__in' ] = $ids; 
  5384.  
  5385. $fields = array(); 
  5386.  
  5387. $_fields = get_posts( $args ); 
  5388.  
  5389. foreach ( $_fields as $field ) { 
  5390. $field = $this->load_field( $field, false ); 
  5391.  
  5392. if ( !empty( $field ) ) 
  5393. $fields[ $field[ 'id' ] ] = $field; 
  5394. else { 
  5395. if ( empty( $params->name ) && empty( $params->id ) && empty( $params->type ) ) 
  5396. return pods_error( __( 'Either Field Name / Field ID / Field Type, or Pod Name / Pod ID are required', 'pods' ), $this ); 
  5397.  
  5398. $lookup = array(); 
  5399.  
  5400. if ( !empty( $params->name ) ) { 
  5401. $fields = implode( "', '", $params->name ); 
  5402.  
  5403. $lookup[] = "`post_name` IN ( '{$fields}' )"; 
  5404.  
  5405. if ( !empty( $params->id ) ) { 
  5406. $fields = implode( ", ", $params->id ); 
  5407.  
  5408. $lookup[] = "`ID` IN ( {$fields} )"; 
  5409.  
  5410. $lookup = implode( ' AND ', $lookup ); 
  5411.  
  5412. $result = pods_query( "SELECT `ID`, `post_name`, `post_parent` FROM `@wp_posts` WHERE `post_type` = '_pods_field' AND ( {$lookup} )" ); 
  5413.  
  5414. $fields = array(); 
  5415.  
  5416. if ( !empty( $result ) ) { 
  5417. foreach ( $result as $field ) { 
  5418. $field = $this->load_field( array( 
  5419. 'id' => $field->ID,  
  5420. 'name' => $field->post_name,  
  5421. 'pod_id' => $field->post_parent 
  5422. ), false ); 
  5423.  
  5424. if ( !empty( $field ) && ( empty( $params->type ) || in_array( $field[ 'type' ], $params->type ) ) ) 
  5425. $fields[ $field[ 'id' ] ] = $field; 
  5426. if ( isset( $cache_key ) ) { 
  5427. $this->fields_cache[ $cache_key ] = $fields; 
  5428. return $fields; 
  5429.  
  5430. /** 
  5431. * Load a Pods Object 
  5432. * $params['id'] int The Object ID 
  5433. * $params['name'] string The Object name 
  5434. * $params['type'] string The Object type 
  5435. * @param array|object $params An associative array of parameters 
  5436. * @param bool $strict 
  5437. * @return array|bool 
  5438. * @since 2.0 
  5439. */ 
  5440. public function load_object ( $params, $strict = false ) { 
  5441. if ( is_object( $params ) && isset( $params->post_title ) ) 
  5442. $_object = get_object_vars( $params ); 
  5443. else { 
  5444. $params = (object) pods_sanitize( $params ); 
  5445.  
  5446. if ( !isset( $params->type ) || empty( $params->type ) ) 
  5447. return pods_error( __( 'Object type is required', 'pods' ), $this ); 
  5448.  
  5449. if ( ( !isset( $params->id ) || empty( $params->id ) ) && ( !isset( $params->name ) || empty( $params->name ) ) ) 
  5450. return pods_error( __( 'Either Object ID or Name are required', 'pods' ), $this ); 
  5451.  
  5452. /** 
  5453. * @var $wpdb wpdb 
  5454. */ 
  5455. global $wpdb; 
  5456.  
  5457. if ( isset( $params->name ) ) 
  5458. $_object = pods_by_title( $params->name, ARRAY_A, '_pods_' . $params->type, 'publish' ); 
  5459. else { 
  5460. $object = $params->id; 
  5461.  
  5462. $_object = get_post( $object, ARRAY_A ); 
  5463.  
  5464. if ( empty( $_object ) ) { 
  5465. if ( $strict ) 
  5466. return pods_error( __( 'Object not found', 'pods' ), $this ); 
  5467.  
  5468. return false; 
  5469.  
  5470. $object = array( 
  5471. 'id' => $_object[ 'ID' ],  
  5472. 'name' => $_object[ 'post_title' ],  
  5473. 'code' => $_object[ 'post_content' ],  
  5474. 'type' => str_replace( '_pods_', '', $_object[ 'post_type' ] ),  
  5475. 'slug' => $_object[ 'post_name' ] 
  5476. ); 
  5477.  
  5478. $object[ 'options' ] = get_post_meta( $object[ 'id' ] ); 
  5479.  
  5480. foreach ( $object[ 'options' ] as $option => &$value ) { 
  5481. if ( is_array( $value ) && 1 == count( $value ) ) 
  5482. $value = current( $value ); 
  5483.  
  5484. return $object; 
  5485.  
  5486. /** 
  5487. * Load Multiple Pods Objects 
  5488. * $params['type'] string The Object type 
  5489. * $params['options'] array Pod Option(s) key=>value array to filter by 
  5490. * $params['orderby'] string ORDER BY clause of query 
  5491. * $params['limit'] string Number of objects to return 
  5492. * $params['where'] string WHERE clause of query 
  5493. * $params['ids'] string|array IDs of Objects 
  5494. * @param array|object $params An associative array of parameters 
  5495. * @return array 
  5496. * @since 2.0 
  5497. */ 
  5498. public function load_objects ( $params ) { 
  5499. $params = (object) pods_sanitize( $params ); 
  5500.  
  5501. if ( !isset( $params->type ) || empty( $params->type ) ) 
  5502. return pods_error( __( 'Pods Object type is required', 'pods' ), $this ); 
  5503.  
  5504. $order = 'ASC'; 
  5505. $orderby = 'menu_order'; 
  5506. $limit = -1; 
  5507. $ids = false; 
  5508.  
  5509. $meta_query = array(); 
  5510. $cache_key = ''; 
  5511.  
  5512. if ( isset( $params->options ) && !empty( $params->options ) && is_array( $params->options ) ) { 
  5513. foreach ( $params->options as $option => $value ) { 
  5514. if ( !is_array( $value ) ) 
  5515. $value = array( $value ); 
  5516.  
  5517. $value = pods_trim( $value ); 
  5518.  
  5519. sort( $value ); 
  5520.  
  5521. $meta_query[] = array( 
  5522. 'key' => $option,  
  5523. 'value' => pods_sanitize( $value ),  
  5524. 'compare' => 'IN' 
  5525. ); 
  5526.  
  5527. if ( isset( $params->where ) && is_array( $params->where ) ) 
  5528. $meta_query = array_merge( $meta_query, (array) $params->where ); 
  5529.  
  5530. if ( isset( $params->order ) && !empty( $params->order ) && in_array( strtoupper( $params->order ), array( 'ASC', 'DESC' ) ) ) 
  5531. $order = strtoupper( $params->order ); 
  5532.  
  5533. if ( isset( $params->orderby ) && !empty( $params->orderby ) ) 
  5534. $orderby = strtoupper( $params->orderby ); 
  5535.  
  5536. if ( isset( $params->limit ) && !empty( $params->limit ) ) 
  5537. $limit = pods_absint( $params->limit ); 
  5538.  
  5539. if ( isset( $params->ids ) && !empty( $params->ids ) ) { 
  5540. $ids = $params->ids; 
  5541.  
  5542. if ( !is_array( $ids ) ) 
  5543. $ids = explode( ', ', $ids ); 
  5544.  
  5545. if ( empty( $ids ) ) 
  5546. $ids = false; 
  5547.  
  5548. if ( pods_api_cache() && empty( $meta_query ) && empty( $limit ) && ( empty( $orderby ) || 'menu_order' == $orderby ) && empty( $ids ) ) { 
  5549. $cache_key = 'pods_objects_' . $params->type; 
  5550.  
  5551. $the_objects = pods_transient_get( $cache_key ); 
  5552.  
  5553. if ( false !== $the_objects ) 
  5554. return $the_objects; 
  5555.  
  5556. $the_objects = array(); 
  5557.  
  5558. $args = array( 
  5559. 'post_type' => '_pods_' . $params->type,  
  5560. 'nopaging' => true,  
  5561. 'posts_per_page' => $limit,  
  5562. 'order' => $order,  
  5563. 'orderby' => $orderby,  
  5564. 'meta_query' => $meta_query,  
  5565. ); 
  5566.  
  5567. // Only set post__in if there are ids to filter (see https://core.trac.wordpress.org/ticket/28099) 
  5568. if ( false != $ids ) { 
  5569. $args[ 'post__in' ] = $ids; 
  5570.  
  5571. $objects = get_posts( $args ); 
  5572.  
  5573. foreach ( $objects as $object ) { 
  5574. $object = $this->load_object( $object ); 
  5575.  
  5576. $the_objects[ $object[ 'name' ] ] = $object; 
  5577.  
  5578. if ( pods_api_cache() && !empty( $cache_key ) ) 
  5579. pods_transient_set( $cache_key, $the_objects ); 
  5580.  
  5581. return $the_objects; 
  5582.  
  5583. /** 
  5584. * @see PodsAPI::load_object 
  5585. * Load a Pod Template 
  5586. * $params['id'] int The template ID 
  5587. * $params['name'] string The template name 
  5588. * @param array $params An associative array of parameters 
  5589. * @return array|bool 
  5590. * @since 1.7.9 
  5591. */ 
  5592. public function load_template ( $params ) { 
  5593. if ( !class_exists( 'Pods_Templates' ) ) 
  5594. return false; 
  5595.  
  5596. $params = (object) $params; 
  5597. $params->type = 'template'; 
  5598. return $this->load_object( $params ); 
  5599.  
  5600. /** 
  5601. * @see PodsAPI::load_objects 
  5602. * Load Multiple Pod Templates 
  5603. * $params['where'] string The WHERE clause of query 
  5604. * $params['options'] array Pod Option(s) key=>value array to filter by 
  5605. * $params['orderby'] string ORDER BY clause of query 
  5606. * $params['limit'] string Number of templates to return 
  5607. * @param array $params (optional) An associative array of parameters 
  5608. * @return array 
  5609. * @since 2.0 
  5610. */ 
  5611. public function load_templates ( $params = null ) { 
  5612. if ( !class_exists( 'Pods_Templates' ) ) 
  5613. return array(); 
  5614.  
  5615. $params = (object) $params; 
  5616. $params->type = 'template'; 
  5617. return $this->load_objects( $params ); 
  5618.  
  5619. /** 
  5620. * @see PodsAPI::load_object 
  5621. * Load a Pod Page 
  5622. * $params['id'] int The page ID 
  5623. * $params['name'] string The page URI 
  5624. * @param array $params An associative array of parameters 
  5625. * @return array|bool 
  5626. * @since 1.7.9 
  5627. */ 
  5628. public function load_page ( $params ) { 
  5629. if ( !class_exists( 'Pods_Pages' ) ) 
  5630. return false; 
  5631.  
  5632. $params = (object) $params; 
  5633. if ( !isset( $params->name ) && isset( $params->uri ) ) { 
  5634. $params->name = $params->uri; 
  5635. unset( $params->uri ); 
  5636. $params->type = 'page'; 
  5637. return $this->load_object( $params ); 
  5638.  
  5639. /** 
  5640. * @see PodsAPI::load_objects 
  5641. * Load Multiple Pod Pages 
  5642. * $params['where'] string The WHERE clause of query 
  5643. * $params['options'] array Pod Option(s) key=>value array to filter by 
  5644. * $params['orderby'] string ORDER BY clause of query 
  5645. * $params['limit'] string Number of pages to return 
  5646. * @param array $params (optional) An associative array of parameters 
  5647. * @return array 
  5648. * @since 2.0 
  5649. */ 
  5650. public function load_pages ( $params = null ) { 
  5651. if ( !class_exists( 'Pods_Pages' ) ) 
  5652. return array(); 
  5653.  
  5654. $params = (object) $params; 
  5655. $params->type = 'page'; 
  5656. return $this->load_objects( $params ); 
  5657.  
  5658. /** 
  5659. * @see PodsAPI::load_object 
  5660. * Load a Pod Helper 
  5661. * $params['id'] int The helper ID 
  5662. * $params['name'] string The helper name 
  5663. * @param array $params An associative array of parameters 
  5664. * @return array|bool 
  5665. * @since 1.7.9 
  5666. */ 
  5667. public function load_helper ( $params ) { 
  5668. if ( !class_exists( 'Pods_Helpers' ) ) 
  5669. return false; 
  5670.  
  5671. $params = (object) $params; 
  5672. $params->type = 'helper'; 
  5673. return $this->load_object( $params ); 
  5674.  
  5675. /** 
  5676. * @see PodsAPI::load_objects 
  5677. * Load Multiple Pod Helpers 
  5678. * $params['where'] string The WHERE clause of query 
  5679. * $params['options'] array Pod Option(s) key=>value array to filter by 
  5680. * $params['orderby'] string ORDER BY clause of query 
  5681. * $params['limit'] string Number of pages to return 
  5682. * @param array $params (optional) An associative array of parameters 
  5683. * @return array 
  5684. * @since 2.0 
  5685. */ 
  5686. public function load_helpers ( $params = null ) { 
  5687. if ( !class_exists( 'Pods_Helpers' ) ) 
  5688. return array(); 
  5689.  
  5690. $params = (object) $params; 
  5691. $params->type = 'helper'; 
  5692. return $this->load_objects( $params ); 
  5693.  
  5694. /** 
  5695. * Load the pod item object 
  5696. * $params['pod'] string The datatype name 
  5697. * $params['id'] int (optional) The item's ID 
  5698. * @param array $params An associative array of parameters 
  5699. * @return bool|\Pods 
  5700. * @uses pods() 
  5701. * @since 2.0 
  5702. */ 
  5703. public function load_pod_item ( $params ) { 
  5704. $params = (object) pods_sanitize( $params ); 
  5705.  
  5706. if ( !isset( $params->pod ) || empty( $params->pod ) ) 
  5707. return pods_error( __( 'Pod name required', 'pods' ), $this ); 
  5708. if ( !isset( $params->id ) || empty( $params->id ) ) 
  5709. return pods_error( __( 'Item ID required', 'pods' ), $this ); 
  5710.  
  5711. $pod = false; 
  5712.  
  5713. if ( pods_api_cache() ) 
  5714. $pod = pods_cache_get( $params->id, 'pods_item_object_' . $params->pod ); 
  5715.  
  5716. if ( false !== $pod ) 
  5717. return $pod; 
  5718.  
  5719. $pod = pods( $params->pod, $params->id ); 
  5720.  
  5721. if ( pods_api_cache() ) 
  5722. pods_cache_set( $params->id, $pod, 'pods_item_object_' . $params->pod ); 
  5723.  
  5724. return $pod; 
  5725.  
  5726. /** 
  5727. * Load potential sister fields for a specific field 
  5728. * $params['pod'] int The Pod name 
  5729. * $params['related_pod'] string The related Pod name 
  5730. * @param array $params An associative array of parameters 
  5731. * @param array $pod (optional) Array of Pod data to use (to avoid lookup) 
  5732. * @return array|bool 
  5733. * @since 1.7.9 
  5734. * @uses PodsAPI::load_pod 
  5735. */ 
  5736. public function load_sister_fields ( $params, $pod = null ) { 
  5737. $params = (object) pods_sanitize( $params ); 
  5738.  
  5739. if ( empty( $pod ) ) { 
  5740. $pod = $this->load_pod( array( 'name' => $params->pod, 'table_info' => false ), false ); 
  5741.  
  5742. if ( false === $pod ) 
  5743. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  5744.  
  5745. $params->pod_id = $pod[ 'id' ]; 
  5746. $params->pod = $pod[ 'name' ]; 
  5747.  
  5748. $type = false; 
  5749.  
  5750. if ( 0 === strpos( $params->related_pod, 'pod-' ) ) { 
  5751. $params->related_pod = pods_str_replace( 'pod-', '', $params->related_pod, 1 ); 
  5752. $type = 'pod'; 
  5753. elseif ( 0 === strpos( $params->related_pod, 'post_type-' ) ) { 
  5754. $params->related_pod = pods_str_replace( 'post_type-', '', $params->related_pod, 1 ); 
  5755. $type = 'post_type'; 
  5756. elseif ( 0 === strpos( $params->related_pod, 'taxonomy-' ) ) { 
  5757. $params->related_pod = pods_str_replace( 'taxonomy-', '', $params->related_pod, 1 ); 
  5758. $type = 'taxonomy'; 
  5759.  
  5760. $related_pod = $this->load_pod( array( 'name' => $params->related_pod, 'table_info' => false ), false ); 
  5761.  
  5762. if ( false === $related_pod || ( false !== $type && 'pod' != $type && $type != $related_pod[ 'type' ] ) ) 
  5763. return pods_error( __( 'Related Pod not found', 'pods' ), $this ); 
  5764.  
  5765. $params->related_pod_id = $related_pod[ 'id' ]; 
  5766. $params->related_pod = $related_pod[ 'name' ]; 
  5767.  
  5768. $sister_fields = array(); 
  5769.  
  5770. foreach ( $related_pod[ 'fields' ] as $field ) { 
  5771. if ( 'pick' == $field[ 'type' ] && in_array( $field[ 'pick_object' ], array( $pod[ 'type' ], 'pod' ) ) && ( $params->pod == $field[ 'pick_object' ] || $params->pod == $field[ 'pick_val' ] ) ) 
  5772. $sister_fields[ $field[ 'id' ] ] = esc_html( $field[ 'label' ] . ' (' . $field[ 'name' ] . ')' ); 
  5773.  
  5774. return $sister_fields; 
  5775.  
  5776. /** 
  5777. * Takes a sql field such as tinyint and returns the pods field type, such as num. 
  5778. * @param string $sql_field The SQL field to look for 
  5779. * @return string The field type 
  5780. * @since 2.0 
  5781. */ 
  5782. public static function detect_pod_field_from_sql_data_type ( $sql_field ) { 
  5783. $sql_field = strtolower( $sql_field ); 
  5784.  
  5785. $field_to_field_map = array( 
  5786. 'tinyint' => 'number',  
  5787. 'smallint' => 'number',  
  5788. 'mediumint' => 'number',  
  5789. 'int' => 'number',  
  5790. 'bigint' => 'number',  
  5791. 'float' => 'number',  
  5792. 'double' => 'number',  
  5793. 'decimal' => 'number',  
  5794. 'date' => 'date',  
  5795. 'datetime' => 'datetime',  
  5796. 'timestamp' => 'datetime',  
  5797. 'time' => 'time',  
  5798. 'year' => 'date',  
  5799. 'varchar' => 'text',  
  5800. 'text' => 'paragraph',  
  5801. 'mediumtext' => 'paragraph',  
  5802. 'longtext' => 'paragraph' 
  5803. ); 
  5804.  
  5805. return ( array_key_exists( $sql_field, $field_to_field_map ) ) ? $field_to_field_map[ $sql_field ] : 'paragraph'; 
  5806.  
  5807. /** 
  5808. * Gets all field types 
  5809. * @return array Array of field types 
  5810. * @uses PodsForm::field_loader 
  5811. * @since 2.0 
  5812. * @deprecated 
  5813. */ 
  5814. public function get_field_types () { 
  5815. return PodsForm::field_types(); 
  5816.  
  5817. /** 
  5818. * Gets the schema definition of a field. 
  5819. * @param string $type Field type to look for 
  5820. * @param array $options (optional) Options of the field to pass to the schema function. 
  5821. * @return array|bool|mixed|null 
  5822. * @since 2.0 
  5823. */ 
  5824. private function get_field_definition ( $type, $options = null ) { 
  5825. $definition = PodsForm::field_method( $type, 'schema', $options ); 
  5826.  
  5827. return $this->do_hook( 'field_definition', $definition, $type, $options ); 
  5828.  
  5829. /** 
  5830. * @see PodsForm:validate 
  5831. * Validates the value of a field. 
  5832. * @param mixed $value The value to validate 
  5833. * @param string $field Field to use for validation 
  5834. * @param array $object_fields Fields of the object we're validating 
  5835. * @param array $fields Array of all fields data 
  5836. * @param array|Pods $pod Array of pod data (or Pods object) 
  5837. * @param array|object $params Extra parameters to pass to the validation function of the field. 
  5838. * @return array|bool 
  5839. * @uses PodsForm::validate 
  5840. * @since 2.0 
  5841. */ 
  5842. public function handle_field_validation ( &$value, $field, $object_fields, $fields, $pod, $params ) { 
  5843. $tableless_field_types = PodsForm::tableless_field_types(); 
  5844.  
  5845. $fields = array_merge( $fields, $object_fields ); 
  5846.  
  5847. $options = $fields[ $field ]; 
  5848.  
  5849. $id = ( is_object( $params ) ? $params->id : ( is_object( $pod ) ? $pod->id() : 0 ) ); 
  5850.  
  5851. if ( is_object( $pod ) ) 
  5852. $pod = $pod->pod_data; 
  5853.  
  5854. $type = $options[ 'type' ]; 
  5855. $label = $options[ 'label' ]; 
  5856. $label = empty( $label ) ? $field : $label; 
  5857.  
  5858. // Verify required fields 
  5859. if ( 1 == pods_var( 'required', $options[ 'options' ], 0 ) && 'slug' != $type ) { 
  5860. if ( '' == $value || null === $value || array() === $value ) 
  5861. return pods_error( sprintf( __( '%s is empty', 'pods' ), $label ), $this ); 
  5862.  
  5863. if ( 'multi' == pods_var( 'pick_format_type', $options[ 'options' ] ) && 'autocomplete' != pods_var( 'pick_format_multi', $options[ 'options' ] ) ) { 
  5864. $has_value = false; 
  5865.  
  5866. $check_value = (array) $value; 
  5867.  
  5868. foreach ( $check_value as $val ) { 
  5869. if ( '' != $val && null !== $val && 0 !== $val && '0' !== $val ) { 
  5870. $has_value = true; 
  5871.  
  5872. continue; 
  5873.  
  5874. if ( !$has_value ) 
  5875. return pods_error( sprintf( __( '%s is required', 'pods' ), $label ), $this ); 
  5876.  
  5877.  
  5878. // @todo move this to after pre-save preparations 
  5879. // Verify unique fields 
  5880. if ( 1 == pods_var( 'unique', $options[ 'options' ], 0 ) && '' !== $value && null !== $value && array() !== $value ) { 
  5881. if ( empty( $pod ) ) 
  5882. return false; 
  5883.  
  5884. if ( !in_array( $type, $tableless_field_types ) ) { 
  5885. $exclude = ''; 
  5886.  
  5887. if ( !empty( $id ) ) 
  5888. $exclude = "AND `id` != {$id}"; 
  5889.  
  5890. $check = false; 
  5891.  
  5892. $check_value = pods_sanitize( $value ); 
  5893.  
  5894. // @todo handle meta-based fields 
  5895. // Trigger an error if not unique 
  5896. if ( 'table' == $pod[ 'storage' ] ) 
  5897. $check = pods_query( "SELECT `id` FROM `@wp_pods_" . $pod[ 'name' ] . "` WHERE `{$field}` = '{$check_value}' {$exclude} LIMIT 1", $this ); 
  5898.  
  5899. if ( !empty( $check ) ) 
  5900. return pods_error( sprintf( __( '%s needs to be unique', 'pods' ), $label ), $this ); 
  5901. else { 
  5902. // @todo handle tableless check 
  5903.  
  5904. $validate = PodsForm::validate( $options[ 'type' ], $value, $field, array_merge( $options, pods_var( 'options', $options, array() ) ), $fields, $pod, $id, $params ); 
  5905.  
  5906. $validate = $this->do_hook( 'field_validation', $validate, $value, $field, $object_fields, $fields, $pod, $params ); 
  5907.  
  5908. return $validate; 
  5909.  
  5910. /** 
  5911. * Find items related to a parent field 
  5912. * @param int $field_id The Field ID 
  5913. * @param int $pod_id The Pod ID 
  5914. * @param mixed $ids A comma-separated string (or array) of item IDs 
  5915. * @param array $field Field data array 
  5916. * @param array $pod Pod data array 
  5917. * @return array 
  5918. * @since 2.0 
  5919. * @uses pods_query() 
  5920. */ 
  5921. public function lookup_related_items ( $field_id, $pod_id, $ids, $field = null, $pod = null ) { 
  5922. $related_ids = array(); 
  5923.  
  5924. if ( !is_array( $ids ) ) 
  5925. $ids = explode( ', ', $ids ); 
  5926.  
  5927. foreach ( $ids as $k => $id ) { 
  5928. $ids[ $k ] = (int) $id; 
  5929.  
  5930. $ids = array_unique( array_filter( $ids ) ); 
  5931.  
  5932. $idstring = implode( ', ', $ids ); 
  5933. if ( 0 != $pod_id && 0 != $field_id && isset( self::$related_item_cache[ $pod_id ][ $field_id ][ $idstring ] ) ) { 
  5934. // Check cache first, no point in running the same query multiple times 
  5935. return self::$related_item_cache[ $pod_id ][ $field_id ][ $idstring ]; 
  5936.  
  5937. $tableless_field_types = PodsForm::tableless_field_types(); 
  5938.  
  5939. $field_type = pods_v( 'type', $field ); 
  5940.  
  5941. if ( empty( $ids ) || !in_array( $field_type, $tableless_field_types ) ) 
  5942. return array(); 
  5943.  
  5944. $related_pick_limit = 0; 
  5945.  
  5946. if ( empty( $field ) ) { 
  5947. $field = $this->load_field( array( 'id' => $field_id ) ); 
  5948.  
  5949. if ( !empty( $field ) ) { 
  5950. $options = (array) pods_var_raw( 'options', $field, $field, null, true ); 
  5951.  
  5952. $related_pick_limit = (int) pods_v( $field_type . '_limit', $options, 0 ); 
  5953.  
  5954. if ( 'single' == pods_var_raw( $field_type . '_format_type', $options ) ) 
  5955. $related_pick_limit = 1; 
  5956.  
  5957. // Temporary hack until there's some better handling here 
  5958. $related_pick_limit = $related_pick_limit * count( $ids ); 
  5959.  
  5960. if ( 'taxonomy' == $field_type ) { 
  5961. $related = wp_get_object_terms( $ids, pods_v( 'name', $field ), array( 'fields' => 'ids' ) ); 
  5962.  
  5963. if ( !is_wp_error( $related ) ) { 
  5964. $related_ids = $related; 
  5965. elseif ( !pods_tableless() ) { 
  5966. $ids = implode( ', ', $ids ); 
  5967.  
  5968. $field_id = (int) $field_id; 
  5969. $sister_id = (int) pods_var_raw( 'sister_id', $field, 0 ); 
  5970.  
  5971. $related_where = " 
  5972. `field_id` = {$field_id} 
  5973. AND `item_id` IN ( {$ids} ) 
  5974. "; 
  5975.  
  5976. $sql = " 
  5977. SELECT item_id, related_item_id, related_field_id 
  5978. FROM `@wp_podsrel` 
  5979. WHERE 
  5980. {$related_where} 
  5981. ORDER BY `weight` 
  5982. "; 
  5983.  
  5984. $relationships = pods_query( $sql ); 
  5985.  
  5986. if ( !empty( $relationships ) ) { 
  5987. foreach ( $relationships as $relation ) { 
  5988. if ( !in_array( $relation->related_item_id, $related_ids ) ) 
  5989. $related_ids[] = (int) $relation->related_item_id; 
  5990. elseif ( 0 < $sister_id && $field_id == $relation->related_field_id && !in_array( $relation->item_id, $related_ids ) ) 
  5991. $related_ids[] = (int) $relation->item_id; 
  5992. else { 
  5993. if ( !is_array( $pod ) ) 
  5994. $pod = $this->load_pod( array( 'id' => $pod_id, 'table_info' => false ), false ); 
  5995.  
  5996. if ( !empty( $pod ) && in_array( $pod[ 'type' ], array( 'post_type', 'media', 'taxonomy', 'user', 'comment', 'settings' ) ) ) { 
  5997. $meta_type = $pod[ 'type' ]; 
  5998.  
  5999. if ( in_array( $meta_type, array( 'post_type', 'media' ) ) ) 
  6000. $meta_type = 'post'; 
  6001. elseif ( 'taxonomy' == $meta_type ) 
  6002. $meta_type = 'term'; 
  6003.  
  6004. $no_conflict = pods_no_conflict_check( ( 'term' == $meta_type ? 'taxonomy' : $meta_type ) ); 
  6005.  
  6006. if ( !$no_conflict ) 
  6007. pods_no_conflict_on( ( 'term' == $meta_type ? 'taxonomy' : $meta_type ) ); 
  6008.  
  6009. foreach ( $ids as $id ) { 
  6010. if ( 'settings' == $meta_type ) { 
  6011. $related_id = get_option( '_pods_' . $pod[ 'name' ] . '_' . $field[ 'name' ] ); 
  6012.  
  6013. if ( empty( $related_id ) ) 
  6014. $related_id = get_option( $pod[ 'name' ] . '_' . $field[ 'name' ] ); 
  6015.  
  6016. if ( is_array( $related_id ) && !empty( $related_id ) ) { 
  6017. foreach ( $related_id as $related ) { 
  6018. if ( is_array( $related ) && !empty( $related ) ) { 
  6019. if ( isset( $related[ 'id' ] ) ) 
  6020. $related_ids[] = (int) $related[ 'id' ]; 
  6021. else { 
  6022. foreach ( $related as $r ) { 
  6023. $related_ids[] = (int) $r; 
  6024. else 
  6025. $related_ids[] = (int) $related; 
  6026. else { 
  6027. $related_id = get_metadata( $meta_type, $id, '_pods_' . $field[ 'name' ], true ); 
  6028.  
  6029. if ( empty( $related_id ) ) 
  6030. $related_id = get_metadata( $meta_type, $id, $field[ 'name' ] ); 
  6031.  
  6032. if ( is_array( $related_id ) && !empty( $related_id ) ) { 
  6033. foreach ( $related_id as $related ) { 
  6034. if ( is_array( $related ) && !empty( $related ) ) { 
  6035. if ( isset( $related[ 'id' ] ) ) 
  6036. $related_ids[] = (int) $related[ 'id' ]; 
  6037. else { 
  6038. foreach ( $related as $r ) { 
  6039. if ( isset( $related[ 'id' ] ) ) 
  6040. $related_ids[] = (int) $r[ 'id' ]; 
  6041. else 
  6042. $related_ids[] = (int) $r; 
  6043. else 
  6044. $related_ids[] = (int) $related; 
  6045.  
  6046. if ( !$no_conflict ) 
  6047. pods_no_conflict_off( ( 'term' == $meta_type ? 'taxonomy' : $meta_type ) ); 
  6048.  
  6049. if ( is_array( $related_ids ) ) { 
  6050. $related_ids = array_unique( array_filter( $related_ids ) ); 
  6051.  
  6052. if ( 0 < $related_pick_limit && !empty( $related_ids ) ) 
  6053. $related_ids = array_slice( $related_ids, 0, $related_pick_limit ); 
  6054. if ( 0 != $pod_id && 0 != $field_id && ! empty( $related_ids ) ) { 
  6055. // Only cache if $pod_id and $field_id were passed 
  6056. self::$related_item_cache[ $pod_id ][ $field_id ][ $idstring ] = $related_ids; 
  6057.  
  6058. return $related_ids; 
  6059.  
  6060. /** 
  6061. * Find related items related to an item 
  6062. * @param int $field_id The Field ID 
  6063. * @param int $pod_id The Pod ID 
  6064. * @param int $id Item ID to get related IDs from 
  6065. * @param array $field Field data array 
  6066. * @param array $pod Pod data array 
  6067. * @return array|bool 
  6068. * @since 2.3 
  6069. * @uses pods_query() 
  6070. */ 
  6071. public function lookup_related_items_from ( $field_id, $pod_id, $id, $field = null, $pod = null ) { 
  6072. $related_ids = false; 
  6073.  
  6074. $id = (int) $id; 
  6075.  
  6076. $tableless_field_types = PodsForm::tableless_field_types(); 
  6077.  
  6078. if ( empty( $id ) || !in_array( pods_v( 'type', $field ), $tableless_field_types ) ) 
  6079. return false; 
  6080.  
  6081. $related_pick_limit = 0; 
  6082.  
  6083. if ( !empty( $field ) ) { 
  6084. $options = (array) pods_var_raw( 'options', $field, $field, null, true ); 
  6085.  
  6086. $related_pick_limit = (int) pods_v( 'pick_limit', $options, 0 ); 
  6087.  
  6088. if ( 'single' == pods_var_raw( 'pick_format_type', $options ) ) 
  6089. $related_pick_limit = 1; 
  6090.  
  6091. if ( !pods_tableless() ) { 
  6092. $field_id = (int) $field_id; 
  6093. $sister_id = (int) pods_var_raw( 'sister_id', $field, 0 ); 
  6094.  
  6095. $related_where = " 
  6096. `field_id` = {$field_id} 
  6097. AND `related_item_id` = {$id} 
  6098. "; 
  6099.  
  6100. $sql = " 
  6101. SELECT * 
  6102. FROM `@wp_podsrel` 
  6103. WHERE 
  6104. {$related_where} 
  6105. ORDER BY `weight` 
  6106. "; 
  6107.  
  6108. $relationships = pods_query( $sql ); 
  6109.  
  6110. if ( !empty( $relationships ) ) { 
  6111. $related_ids = array(); 
  6112.  
  6113. foreach ( $relationships as $relation ) { 
  6114. if ( $field_id == $relation->field_id && !in_array( $relation->item_id, $related_ids ) ) 
  6115. $related_ids[] = (int) $relation->item_id; 
  6116. elseif ( 0 < $sister_id && $field_id == $relation->related_field_id && !in_array( $relation->related_item_id, $related_ids ) ) 
  6117. $related_ids[] = (int) $relation->related_item_id; 
  6118. else { 
  6119. // @todo handle meta-based lookups 
  6120. return false; 
  6121.  
  6122. if ( !is_array( $pod ) ) 
  6123. $pod = $this->load_pod( array( 'id' => $pod_id, 'table_info' => false ), false ); 
  6124.  
  6125. if ( !empty( $pod ) && in_array( $pod[ 'type' ], array( 'post_type', 'media', 'taxonomy', 'user', 'comment', 'settings' ) ) ) { 
  6126. $related_ids = array(); 
  6127.  
  6128. $meta_type = $pod[ 'type' ]; 
  6129.  
  6130. if ( in_array( $meta_type, array( 'post_type', 'media' ) ) ) 
  6131. $meta_type = 'post'; 
  6132. elseif ( 'taxonomy' == $meta_type ) 
  6133. $meta_type = 'term'; 
  6134.  
  6135. $no_conflict = pods_no_conflict_check( ( 'term' == $meta_type ? 'taxonomy' : $meta_type ) ); 
  6136.  
  6137. if ( !$no_conflict ) 
  6138. pods_no_conflict_on( ( 'term' == $meta_type ? 'taxonomy' : $meta_type ) ); 
  6139.  
  6140. if ( 'settings' == $meta_type ) { 
  6141. $related_id = get_option( '_pods_' . $pod[ 'name' ] . '_' . $field[ 'name' ] ); 
  6142.  
  6143. if ( empty( $related_id ) ) 
  6144. $related_id = get_option( $pod[ 'name' ] . '_' . $field[ 'name' ] ); 
  6145.  
  6146. if ( is_array( $related_id ) && !empty( $related_id ) ) { 
  6147. foreach ( $related_id as $related ) { 
  6148. if ( is_array( $related ) && !empty( $related ) ) { 
  6149. if ( isset( $related[ 'id' ] ) ) 
  6150. $related_ids[] = (int) $related[ 'id' ]; 
  6151. else { 
  6152. foreach ( $related as $r ) { 
  6153. $related_ids[] = (int) $r; 
  6154. else 
  6155. $related_ids[] = (int) $related; 
  6156. else { 
  6157. $related_id = get_metadata( $meta_type, $id, '_pods_' . $field[ 'name' ], true ); 
  6158.  
  6159. if ( empty( $related_id ) ) 
  6160. $related_id = get_metadata( $meta_type, $id, $field[ 'name' ] ); 
  6161.  
  6162. if ( is_array( $related_id ) && !empty( $related_id ) ) { 
  6163. foreach ( $related_id as $related ) { 
  6164. if ( is_array( $related ) && !empty( $related ) ) { 
  6165. if ( isset( $related[ 'id' ] ) ) 
  6166. $related_ids[] = (int) $related[ 'id' ]; 
  6167. else { 
  6168. foreach ( $related as $r ) { 
  6169. if ( isset( $related[ 'id' ] ) ) 
  6170. $related_ids[] = (int) $r[ 'id' ]; 
  6171. else 
  6172. $related_ids[] = (int) $r; 
  6173. else 
  6174. $related_ids[] = (int) $related; 
  6175.  
  6176. if ( !$no_conflict ) 
  6177. pods_no_conflict_off( ( 'term' == $meta_type ? 'taxonomy' : $meta_type ) ); 
  6178.  
  6179. if ( is_array( $related_ids ) ) 
  6180. $related_ids = array_unique( array_filter( $related_ids ) ); 
  6181.  
  6182. return $related_ids; 
  6183.  
  6184. /** 
  6185. * Load the information about an objects MySQL table 
  6186. * @param $object_type 
  6187. * @param string $object The object to look for 
  6188. * @param null $name (optional) Name of the pod to load 
  6189. * @param array $pod (optional) Array with pod information 
  6190. * @return array 
  6191. * @since 2.5 
  6192. */ 
  6193. public function get_table_info_load ( $object_type, $object, $name = null, $pod = null ) { 
  6194.  
  6195. $info = array(); 
  6196.  
  6197. if ( 'pod' == $object_type && null === $pod ) { 
  6198. if ( empty( $name ) ) { 
  6199. $prefix = 'pod-'; 
  6200.  
  6201. // Make sure we actually have the prefix before trying anything with the name 
  6202. if ( 0 === strpos( $object_type, $prefix ) ) 
  6203. $name = substr( $object_type, strlen( $prefix ), strlen( $object_type ) ); 
  6204.  
  6205. if ( empty( $name ) && !empty( $object ) ) 
  6206. $name = $object; 
  6207.  
  6208. $pod = $this->load_pod( array( 'name' => $name, 'table_info' => false ), false ); 
  6209.  
  6210. if ( !empty( $pod ) ) { 
  6211. $object_type = $pod[ 'type' ]; 
  6212. $name = $pod[ 'name' ]; 
  6213. $object = $pod[ 'object' ]; 
  6214.  
  6215. $info[ 'pod' ] = $pod; 
  6216. elseif ( null === $pod ) { 
  6217. if ( empty( $name ) ) { 
  6218. $prefix = $object_type . '-'; 
  6219.  
  6220. // Make sure we actually have the prefix before trying anything with the name 
  6221. if ( 0 === strpos( $object_type, $prefix ) ) 
  6222. $name = substr( $object_type, strlen( $prefix ), strlen( $object_type ) ); 
  6223.  
  6224. if ( empty( $name ) && !empty( $object ) ) 
  6225. $name = $object; 
  6226.  
  6227. if ( !empty( $name ) ) { 
  6228. $pod = $this->load_pod( array( 'name' => $name, 'table_info' => false ), false ); 
  6229.  
  6230. if ( !empty( $pod ) && ( null === $object_type || $object_type == $pod[ 'type' ] ) ) { 
  6231. $object_type = $pod[ 'type' ]; 
  6232. $name = $pod[ 'name' ]; 
  6233. $object = $pod[ 'object' ]; 
  6234.  
  6235. $info[ 'pod' ] = $pod; 
  6236. elseif ( !empty( $pod ) ) 
  6237. $info[ 'pod' ] = $pod; 
  6238.  
  6239. if ( 0 === strpos( $object_type, 'pod' ) ) { 
  6240. if ( empty( $name ) ) { 
  6241. $prefix = 'pod-'; 
  6242.  
  6243. // Make sure we actually have the prefix before trying anything with the name 
  6244. if ( 0 === strpos( $object_type, $prefix ) ) 
  6245. $name = substr( $object_type, strlen( $prefix ), strlen( $object_type ) ); 
  6246.  
  6247. $info[ 'type' ] = 'pod'; 
  6248. global $wpdb; 
  6249.  
  6250. $info[ 'table' ] = $info[ 'meta_table' ] = $wpdb->prefix . 'pods_' . ( empty( $object ) ? $name : $object ); 
  6251.  
  6252. if ( is_array( $info[ 'pod' ] ) && 'pod' == pods_v( 'type', $info[ 'pod' ] ) ) { 
  6253. $info[ 'pod_field_index' ] = $info[ 'field_index' ] = $info[ 'meta_field_index' ] = $info[ 'meta_field_value' ] = pods_v( 'pod_index', $info[ 'pod' ][ 'options' ], 'id', true ); 
  6254.  
  6255. $slug_field = get_posts( array( 
  6256. 'post_type' => '_pods_field',  
  6257. 'posts_per_page' => 1,  
  6258. 'nopaging' => true,  
  6259. 'post_parent' => $info[ 'pod' ][ 'id' ],  
  6260. 'orderby' => 'menu_order',  
  6261. 'order' => 'ASC',  
  6262. 'meta_query' => array( 
  6263. array( 
  6264. 'key' => 'type',  
  6265. 'value' => 'slug',  
  6266. ) ); 
  6267.  
  6268. if ( !empty( $slug_field ) ) { 
  6269. $slug_field = $slug_field[ 0 ]; 
  6270.  
  6271. $info[ 'field_slug' ] = $info[ 'pod_field_slug' ] = $slug_field->post_name; 
  6272.  
  6273. if ( 1 == pods_v( 'hierarchical', $info[ 'pod' ][ 'options' ], 0 ) ) { 
  6274. $parent_field = pods_v( 'pod_parent', $info[ 'pod' ][ 'options' ], 'id', true ); 
  6275.  
  6276. if ( !empty( $parent_field ) && isset( $info[ 'pod' ][ 'fields' ][ $parent_field ] ) ) { 
  6277. $info[ 'object_hierarchical' ] = true; 
  6278.  
  6279. $info[ 'pod_field_parent' ] = $info[ 'field_parent' ] = $parent_field . '_select'; 
  6280. $info[ 'field_parent_select' ] = '`' . $parent_field . '`.`id` AS `' . $info[ 'field_parent' ] . '`'; 
  6281. return $info; 
  6282.  
  6283. /** 
  6284. * Get information about an objects MySQL table 
  6285. * @param string $object_type 
  6286. * @param string $object The object to look for 
  6287. * @param null $name (optional) Name of the pod to load 
  6288. * @param array $pod (optional) Array with pod information 
  6289. * @param array $field (optional) Array with field information 
  6290. * @return array|bool 
  6291. * @since 2.0 
  6292. */ 
  6293. public function get_table_info ( $object_type, $object, $name = null, $pod = null, $field = null ) { 
  6294. /** 
  6295. * @var $wpdb wpdb 
  6296. * @var $sitepress SitePress 
  6297. * @var $icl_adjust_id_url_filter_off boolean 
  6298. */ 
  6299. global $wpdb, $sitepress, $icl_adjust_id_url_filter_off, $polylang; 
  6300.  
  6301. // @todo Handle $object arrays for Post Types, Taxonomies, Comments (table pulled from first object in array) 
  6302.  
  6303. $info = array( 
  6304. //'select' => '`t`.*',  
  6305. 'object_type' => $object_type,  
  6306. 'type' => null,  
  6307. 'object_name' => $object,  
  6308. 'object_hierarchical' => false,  
  6309.  
  6310. 'table' => $object,  
  6311. 'meta_table' => $object,  
  6312. 'pod_table' => $wpdb->prefix . 'pods_' . ( empty( $object ) ? $name : $object ),  
  6313.  
  6314. 'field_id' => 'id',  
  6315. 'field_index' => 'name',  
  6316. 'field_slug' => null,  
  6317. 'field_type' => null,  
  6318. 'field_parent' => null,  
  6319. 'field_parent_select' => null,  
  6320.  
  6321. 'meta_field_id' => 'id',  
  6322. 'meta_field_index' => 'name',  
  6323. 'meta_field_value' => 'name',  
  6324.  
  6325. 'pod_field_id' => 'id',  
  6326. 'pod_field_index' => 'name',  
  6327. 'pod_field_slug' => null,  
  6328. 'pod_field_parent' => null,  
  6329.  
  6330. 'join' => array(),  
  6331.  
  6332. 'where' => null,  
  6333. 'where_default' => null,  
  6334.  
  6335. 'orderby' => null,  
  6336.  
  6337. 'pod' => null,  
  6338. 'recurse' => false 
  6339. ); 
  6340.  
  6341. if ( empty( $object_type ) ) { 
  6342. $object_type = 'post_type'; 
  6343. $object = 'post'; 
  6344. elseif ( empty( $object ) && in_array( $object_type, array( 'user', 'media', 'comment' ) ) ) { 
  6345. $object = $object_type; 
  6346.  
  6347. $pod_name = $pod; 
  6348.  
  6349. if ( is_array( $pod_name ) ) 
  6350. $pod_name = pods_var_raw( 'name', $pod_name, ( version_compare( PHP_VERSION, '5.4.0', '>=' ) ? json_encode( $pod_name, JSON_UNESCAPED_UNICODE ) : json_encode( $pod_name ) ), null, true ); 
  6351. else { 
  6352. $pod_name = $object; 
  6353.  
  6354. $field_name = $field; 
  6355.  
  6356. if ( is_array( $field_name ) ) 
  6357. $field_name = pods_var_raw( 'name', $field_name, ( version_compare( PHP_VERSION, '5.4.0', '>=' ) ? json_encode( $pod_name, JSON_UNESCAPED_UNICODE ) : json_encode( $field_name ) ), null, true ); 
  6358.  
  6359. $transient = 'pods_' . $wpdb->prefix . '_get_table_info_' . md5( $object_type . '_object_' . $object . '_name_' . $name . '_pod_' . $pod_name . '_field_' . $field_name ); 
  6360.  
  6361. $current_language = false; 
  6362. $current_language_t_id = $current_language_tt_id = 0; 
  6363.  
  6364. // WPML support 
  6365. if ( is_object( $sitepress ) && !$icl_adjust_id_url_filter_off ) 
  6366. $current_language = pods_sanitize( ICL_LANGUAGE_CODE ); 
  6367. // Polylang support 
  6368. elseif ( is_object( $polylang ) && function_exists( 'pll_current_language' ) ) { 
  6369. $current_language = pods_sanitize( pll_current_language( 'slug' ) ); 
  6370.  
  6371. if ( !empty( $current_language ) ) { 
  6372. if ( isset( $polylang->model ) && method_exists( $polylang->model, 'get_language' )) { 
  6373. $current_language_t_id = (int) $polylang->model->get_language( $current_language )->term_id; 
  6374. $current_language_tt_id = (int) $polylang->model->get_language( $current_language )->term_taxonomy_id; 
  6375. } else { 
  6376. $current_language_t_id = (int) $polylang->get_language( $current_language )->term_id; 
  6377. $current_language_tt_id = (int) $polylang->get_language( $current_language )->term_taxonomy_id; 
  6378.  
  6379. if ( !empty( $current_language ) ) 
  6380. $transient = 'pods_' . $wpdb->prefix . '_get_table_info_' . $current_language . '_' . md5( $object_type . '_object_' . $object . '_name_' . $name . '_pod_' . $pod_name . '_field_' . $field_name ); 
  6381.  
  6382. $_info = false; 
  6383.  
  6384. if ( isset( self::$table_info_cache[ $transient ] ) ) { 
  6385. // Prefer info from the object internal cache 
  6386. $_info = self::$table_info_cache[ $transient ]; 
  6387. } elseif ( pods_api_cache() ) { 
  6388. $_info = pods_transient_get( $transient ); 
  6389. if ( false === $_info && ! did_action( 'init' ) ) { 
  6390. $_info = pods_transient_get( $transient . '_pre_init' ); 
  6391.  
  6392. if ( false !== $_info ) { 
  6393. // Data was cached, use that 
  6394. $info = $_info; 
  6395. } else { 
  6396. // Data not cached, load it up 
  6397. $_info = $this->get_table_info_load( $object_type, $object, $name, $pod ); 
  6398. if ( isset( $_info[ 'type' ] ) ) { 
  6399. // Allow function to override $object_type 
  6400. $object_type = $_info[ 'type' ]; 
  6401. $info = array_merge( $info, $_info ); 
  6402.  
  6403. if ( 0 === strpos( $object_type, 'post_type' ) || 'media' == $object_type || in_array( pods_var_raw( 'type', $info[ 'pod' ] ), array( 'post_type', 'media' ) ) ) { 
  6404. $info[ 'table' ] = $wpdb->posts; 
  6405. $info[ 'meta_table' ] = $wpdb->postmeta; 
  6406.  
  6407. $info[ 'field_id' ] = 'ID'; 
  6408. $info[ 'field_index' ] = 'post_title'; 
  6409. $info[ 'field_slug' ] = 'post_name'; 
  6410. $info[ 'field_type' ] = 'post_type'; 
  6411. $info[ 'field_parent' ] = 'post_parent'; 
  6412. $info[ 'field_parent_select' ] = '`t`.`' . $info[ 'field_parent' ] . '`'; 
  6413.  
  6414. $info[ 'meta_field_id' ] = 'post_id'; 
  6415. $info[ 'meta_field_index' ] = 'meta_key'; 
  6416. $info[ 'meta_field_value' ] = 'meta_value'; 
  6417.  
  6418. if ( 'media' == $object_type ) 
  6419. $object = 'attachment'; 
  6420.  
  6421. if ( empty( $name ) ) { 
  6422. $prefix = 'post_type-'; 
  6423.  
  6424. // Make sure we actually have the prefix before trying anything with the name 
  6425. if ( 0 === strpos( $object_type, $prefix ) ) 
  6426. $name = substr( $object_type, strlen( $prefix ), strlen( $object_type ) ); 
  6427.  
  6428. if ( 'media' != $object_type ) 
  6429. $object_type = 'post_type'; 
  6430.  
  6431. $post_type = pods_sanitize( ( empty( $object ) ? $name : $object ) ); 
  6432.  
  6433. if ( 'attachment' == $post_type || 'media' == $object_type ) 
  6434. $info[ 'pod_table' ] = $wpdb->prefix . 'pods_media'; 
  6435. else 
  6436. $info[ 'pod_table' ] = $wpdb->prefix . 'pods_' . pods_clean_name( $post_type, true, false ); 
  6437.  
  6438. $post_type_object = get_post_type_object( $post_type ); 
  6439.  
  6440. if ( is_object( $post_type_object ) && $post_type_object->hierarchical ) 
  6441. $info[ 'object_hierarchical' ] = true; 
  6442.  
  6443. /** 
  6444. * Default Post Status to query for. 
  6445. * Use to change "default" post status from publish to any other status or statuses. 
  6446. * @param array $post_status List of post statuses. Default is 'publish' 
  6447. * @param string $post_type Post type of current object 
  6448. * @param array $info Array of information about the object. 
  6449. * @param string $object Type of object 
  6450. * @param string $name Name of pod to load 
  6451. * @param array $pod Array with Pod information. Result of PodsAPI::load_pod() 
  6452. * @param array $field Array with field information 
  6453. * @since unknown 
  6454. */ 
  6455. $post_status = apply_filters( 'pods_api_get_table_info_default_post_status', array( 'publish' ), $post_type, $info, $object_type, $object, $name, $pod, $field ); 
  6456.  
  6457. $info[ 'where' ] = array( 
  6458. //'post_status' => '`t`.`post_status` IN ( "inherit", "publish" )', // @todo Figure out what statuses Attachments can be 
  6459. 'post_type' => '`t`.`' . $info[ 'field_type' ] . '` = "' . $post_type . '"' 
  6460. ); 
  6461.  
  6462. if ( 'post_type' == $object_type ) 
  6463. $info[ 'where_default' ] = '`t`.`post_status` IN ( "' . implode( '", "', $post_status ) . '" )'; 
  6464.  
  6465. $info[ 'orderby' ] = '`t`.`menu_order`, `t`.`' . $info[ 'field_index' ] . '`, `t`.`post_date`'; 
  6466.  
  6467. // WPML support 
  6468. if ( is_object( $sitepress ) && $sitepress->is_translated_post_type( $post_type ) && !$icl_adjust_id_url_filter_off ) { 
  6469. $info[ 'join' ][ 'wpml_translations' ] = " 
  6470. LEFT JOIN `{$wpdb->prefix}icl_translations` AS `wpml_translations` 
  6471. ON `wpml_translations`.`element_id` = `t`.`ID` 
  6472. AND `wpml_translations`.`element_type` = 'post_{$post_type}' 
  6473. AND `wpml_translations`.`language_code` = '{$current_language}' 
  6474. "; 
  6475.  
  6476. $info[ 'join' ][ 'wpml_languages' ] = " 
  6477. LEFT JOIN `{$wpdb->prefix}icl_languages` AS `wpml_languages` 
  6478. ON `wpml_languages`.`code` = `wpml_translations`.`language_code` AND `wpml_languages`.`active` = 1 
  6479. "; 
  6480.  
  6481. $info[ 'where' ][ 'wpml_languages' ] = "`wpml_languages`.`code` IS NOT NULL"; 
  6482. // Polylang support 
  6483. elseif( is_object( $polylang ) && !empty( $current_language ) && function_exists( 'pll_is_translated_post_type' ) && pll_is_translated_post_type( $post_type ) ) { 
  6484. $info[ 'join' ][ 'polylang_languages' ] = " 
  6485. LEFT JOIN `{$wpdb->term_relationships}` AS `polylang_languages` 
  6486. ON `polylang_languages`.`object_id` = `t`.`ID` 
  6487. AND `polylang_languages`.`term_taxonomy_id` = {$current_language_tt_id} 
  6488. "; 
  6489.  
  6490. $info[ 'where' ][ 'polylang_languages' ] = "`polylang_languages`.`object_id` IS NOT NULL"; 
  6491.  
  6492. $info[ 'object_fields' ] = $this->get_wp_object_fields( $object_type, $info[ 'pod' ] ); 
  6493. elseif ( 0 === strpos( $object_type, 'taxonomy' ) || in_array( $object_type, array( 'nav_menu', 'post_format' ) ) || 'taxonomy' == pods_var_raw( 'type', $info[ 'pod' ] ) ) { 
  6494. $info[ 'table' ] = $info[ 'meta_table' ] = $wpdb->terms; 
  6495.  
  6496. $info[ 'join' ][ 'tt' ] = "LEFT JOIN `{$wpdb->term_taxonomy}` AS `tt` ON `tt`.`term_id` = `t`.`term_id`"; 
  6497. $info[ 'join' ][ 'tr' ] = "LEFT JOIN `{$wpdb->term_relationships}` AS `tr` ON `tr`.`term_taxonomy_id` = `tt`.`term_taxonomy_id`"; 
  6498. $info[ 'field_id' ] = $info[ 'meta_field_id' ] = 'term_id'; 
  6499. $info[ 'field_index' ] = $info[ 'meta_field_index' ] = $info[ 'meta_field_value' ] = 'name'; 
  6500. $info[ 'field_slug' ] = 'slug'; 
  6501. $info[ 'field_type' ] = 'taxonomy'; 
  6502. $info[ 'field_parent' ] = 'parent'; 
  6503. $info[ 'field_parent_select' ] = '`tt`.`' . $info[ 'field_parent' ] . '`'; 
  6504.  
  6505. if ( ! empty( $wpdb->termmeta ) ) { 
  6506. $info[ 'meta_table' ] = $wpdb->termmeta; 
  6507.  
  6508. $info[ 'meta_field_id' ] = 'term_id'; 
  6509. $info[ 'meta_field_index' ] = 'meta_key'; 
  6510. $info[ 'meta_field_value' ] = 'meta_value'; 
  6511.  
  6512. if ( 'nav_menu' == $object_type ) 
  6513. $object = 'nav_menu'; 
  6514. elseif ( 'post_format' == $object_type ) 
  6515. $object = 'post_format'; 
  6516.  
  6517. if ( empty( $name ) ) { 
  6518. $prefix = 'taxonomy-'; 
  6519.  
  6520. // Make sure we actually have the prefix before trying anything with the name 
  6521. if ( 0 === strpos( $object_type, $prefix ) ) 
  6522. $name = substr( $object_type, strlen( $prefix ), strlen( $object_type ) ); 
  6523.  
  6524. if ( !in_array( $object_type, array( 'nav_menu', 'post_format' ) ) ) 
  6525. $object_type = 'taxonomy'; 
  6526.  
  6527. $taxonomy = pods_sanitize( ( empty( $object ) ? $name : $object ) ); 
  6528.  
  6529. $info[ 'pod_table' ] = $wpdb->prefix . 'pods_' . pods_clean_name( $taxonomy, true, false ); 
  6530.  
  6531. $taxonomy_object = get_taxonomy( $taxonomy ); 
  6532.  
  6533. if ( is_object( $taxonomy_object ) && $taxonomy_object->hierarchical ) 
  6534. $info[ 'object_hierarchical' ] = true; 
  6535.  
  6536. $info[ 'where' ] = array( 
  6537. 'tt.taxonomy' => '`tt`.`' . $info[ 'field_type' ] . '` = "' . $taxonomy . '"' 
  6538. ); 
  6539.  
  6540. // WPML Support 
  6541. if ( is_object( $sitepress ) && $sitepress->is_translated_taxonomy( $taxonomy ) && !$icl_adjust_id_url_filter_off ) { 
  6542. $info[ 'join' ][ 'wpml_translations' ] = " 
  6543. LEFT JOIN `{$wpdb->prefix}icl_translations` AS `wpml_translations` 
  6544. ON `wpml_translations`.`element_id` = `tt`.`term_taxonomy_id` 
  6545. AND `wpml_translations`.`element_type` = 'tax_{$taxonomy}' 
  6546. AND `wpml_translations`.`language_code` = '{$current_language}' 
  6547. "; 
  6548.  
  6549. $info[ 'join' ][ 'wpml_languages' ] = " 
  6550. LEFT JOIN `{$wpdb->prefix}icl_languages` AS `wpml_languages` 
  6551. ON `wpml_languages`.`code` = `wpml_translations`.`language_code` AND `wpml_languages`.`active` = 1 
  6552. "; 
  6553.  
  6554. $info[ 'where' ][ 'wpml_languages' ] = "`wpml_languages`.`code` IS NOT NULL"; 
  6555. // Polylang support 
  6556. elseif ( is_object( $polylang ) && !empty( $current_language ) && function_exists( 'pll_is_translated_taxonomy' ) && pll_is_translated_taxonomy( $taxonomy ) ) { 
  6557. $info[ 'join' ][ 'polylang_languages' ] = " 
  6558. LEFT JOIN `{$wpdb->termmeta}` AS `polylang_languages` 
  6559. ON `polylang_languages`.`term_id` = `t`.`term_id` 
  6560. AND `polylang_languages`.`meta_value` = {$current_language_t_id} 
  6561. "; 
  6562.  
  6563. $info[ 'where' ][ 'polylang_languages' ] = "`polylang_languages`.`term_id` IS NOT NULL"; 
  6564.  
  6565. $info[ 'object_fields' ] = $this->get_wp_object_fields( $object_type, $info[ 'pod' ] ); 
  6566. elseif ( 'user' == $object_type || 'user' == pods_var_raw( 'type', $info[ 'pod' ] ) ) { 
  6567. $info[ 'table' ] = $wpdb->users; 
  6568. $info[ 'meta_table' ] = $wpdb->usermeta; 
  6569. $info[ 'pod_table' ] = $wpdb->prefix . 'pods_user'; 
  6570.  
  6571. $info[ 'field_id' ] = 'ID'; 
  6572. $info[ 'field_index' ] = 'display_name'; 
  6573. $info[ 'field_slug' ] = 'user_nicename'; 
  6574.  
  6575. $info[ 'meta_field_id' ] = 'user_id'; 
  6576. $info[ 'meta_field_index' ] = 'meta_key'; 
  6577. $info[ 'meta_field_value' ] = 'meta_value'; 
  6578.  
  6579. $info[ 'where' ] = array( 
  6580. 'user_status' => '`t`.`user_status` = 0' 
  6581. ); 
  6582.  
  6583. $info[ 'object_fields' ] = $this->get_wp_object_fields( $object_type, $info[ 'pod' ] ); 
  6584. elseif ( 'comment' == $object_type || 'comment' == pods_var_raw( 'type', $info[ 'pod' ] ) ) { 
  6585. //$info[ 'object_hierarchical' ] = true; 
  6586.  
  6587. $info[ 'table' ] = $wpdb->comments; 
  6588. $info[ 'meta_table' ] = $wpdb->commentmeta; 
  6589. $info[ 'pod_table' ] = $wpdb->prefix . 'pods_comment'; 
  6590.  
  6591. $info[ 'field_id' ] = 'comment_ID'; 
  6592. $info[ 'field_index' ] = 'comment_date'; 
  6593. $info[ 'field_type' ] = 'comment_type'; 
  6594. $info[ 'field_parent' ] = 'comment_parent'; 
  6595. $info[ 'field_parent_select' ] = '`t`.`' . $info[ 'field_parent' ] . '`'; 
  6596.  
  6597. $info[ 'meta_field_id' ] = 'comment_id'; 
  6598. $info[ 'meta_field_index' ] = 'meta_key'; 
  6599. $info[ 'meta_field_value' ] = 'meta_value'; 
  6600.  
  6601. $object = 'comment'; 
  6602.  
  6603. $comment_type = ( empty( $object ) ? $name : $object ); 
  6604.  
  6605. $comment_type_clause = '`t`.`' . $info[ 'field_type' ] . '` = "' . $comment_type . '"'; 
  6606.  
  6607. if ( 'comment' == $comment_type ) { 
  6608. $comment_type_clause = '( ' . $comment_type_clause . ' OR `t`.`' . $info[ 'field_type' ] . '` = "" )'; 
  6609.  
  6610. $info[ 'where' ] = array( 
  6611. 'comment_approved' => '`t`.`comment_approved` = 1',  
  6612. 'comment_type' => $comment_type_clause 
  6613. ); 
  6614.  
  6615. $info[ 'orderby' ] = '`t`.`' . $info[ 'field_index' ] . '` DESC, `t`.`' . $info[ 'field_id' ] . '`'; 
  6616. elseif ( in_array( $object_type, array( 'option', 'settings' ) ) || 'settings' == pods_var_raw( 'type', $info[ 'pod' ] ) ) { 
  6617. $info[ 'table' ] = $wpdb->options; 
  6618. $info[ 'meta_table' ] = $wpdb->options; 
  6619.  
  6620. $info[ 'field_id' ] = 'option_id'; 
  6621. $info[ 'field_index' ] = 'option_name'; 
  6622.  
  6623. $info[ 'meta_field_id' ] = 'option_id'; 
  6624. $info[ 'meta_field_index' ] = 'option_name'; 
  6625. $info[ 'meta_field_value' ] = 'option_value'; 
  6626.  
  6627. $info[ 'orderby' ] = '`t`.`' . $info[ 'field_index' ] . '` ASC'; 
  6628. elseif ( is_multisite() && ( in_array( $object_type, array( 'site_option', 'site_settings' ) ) || 'site_settings' == pods_var_raw( 'type', $info[ 'pod' ] ) ) ) { 
  6629. $info[ 'table' ] = $wpdb->sitemeta; 
  6630. $info[ 'meta_table' ] = $wpdb->sitemeta; 
  6631.  
  6632. $info[ 'field_id' ] = 'site_id'; 
  6633. $info[ 'field_index' ] = 'meta_key'; 
  6634.  
  6635. $info[ 'meta_field_id' ] = 'site_id'; 
  6636. $info[ 'meta_field_index' ] = 'meta_key'; 
  6637. $info[ 'meta_field_value' ] = 'meta_value'; 
  6638.  
  6639. $info[ 'orderby' ] = '`t`.`' . $info[ 'field_index' ] . '` ASC'; 
  6640. elseif ( is_multisite() && 'network' == $object_type ) { // Network = Site 
  6641. $info[ 'table' ] = $wpdb->site; 
  6642. $info[ 'meta_table' ] = $wpdb->sitemeta; 
  6643.  
  6644. $info[ 'field_id' ] = 'id'; 
  6645. $info[ 'field_index' ] = 'domain'; 
  6646.  
  6647. $info[ 'meta_field_id' ] = 'site_id'; 
  6648. $info[ 'meta_field_index' ] = 'meta_key'; 
  6649. $info[ 'meta_field_value' ] = 'meta_value'; 
  6650.  
  6651. $info[ 'orderby' ] = '`t`.`' . $info[ 'field_index' ] . '` ASC, `t`.`path` ASC, `t`.`' . $info[ 'field_id' ] . '`'; 
  6652. elseif ( is_multisite() && 'site' == $object_type ) { // Site = Blog 
  6653. $info[ 'table' ] = $wpdb->blogs; 
  6654.  
  6655. $info[ 'field_id' ] = 'blog_id'; 
  6656. $info[ 'field_index' ] = 'domain'; 
  6657. $info[ 'field_type' ] = 'site_id'; 
  6658.  
  6659. $info[ 'where' ] = array( 
  6660. 'archived' => '`t`.`archived` = 0',  
  6661. 'spam' => '`t`.`spam` = 0',  
  6662. 'deleted' => '`t`.`deleted` = 0',  
  6663. 'site_id' => '`t`.`' . $info[ 'field_type' ] . '` = ' . (int) get_current_site()->id 
  6664. ); 
  6665.  
  6666. $info[ 'orderby' ] = '`t`.`' . $info[ 'field_index' ] . '` ASC, `t`.`path` ASC, `t`.`' . $info[ 'field_id' ] . '`'; 
  6667. elseif ( 'table' == $object_type || 'table' == pods_var_raw( 'type', $info[ 'pod' ] ) ) { 
  6668. $info[ 'table' ] = ( empty( $object ) ? $name : $object ); 
  6669. $info[ 'pod_table' ] = $wpdb->prefix . 'pods_' . $info[ 'table' ]; 
  6670.  
  6671. if ( !empty( $field ) && is_array( $field ) ) { 
  6672. $info[ 'table' ] = pods_var_raw( 'pick_table', pods_var_raw( 'options', $field, $field ) ); 
  6673. $info[ 'field_id' ] = pods_var_raw( 'pick_table_id', pods_var_raw( 'options', $field, $field ) ); 
  6674. $info[ 'field_index' ] = $info[ 'meta_field_index' ] = $info[ 'meta_field_value' ] = pods_var_raw( 'pick_table_index', pods_var_raw( 'options', $field, $field ) ); 
  6675.  
  6676. $info[ 'table' ] = pods_clean_name( $info[ 'table' ], false, false ); 
  6677. $info[ 'meta_table' ] = pods_clean_name( $info[ 'meta_table' ], false, false ); 
  6678. $info[ 'pod_table' ] = pods_clean_name( $info[ 'pod_table' ], false, false ); 
  6679.  
  6680. $info[ 'field_id' ] = pods_clean_name( $info[ 'field_id' ], false, false ); 
  6681. $info[ 'field_index' ] = pods_clean_name( $info[ 'field_index' ], false, false ); 
  6682. $info[ 'field_slug' ] = pods_clean_name( $info[ 'field_slug' ], false, false ); 
  6683.  
  6684. $info[ 'meta_field_id' ] = pods_clean_name( $info[ 'meta_field_id' ], false, false ); 
  6685. $info[ 'meta_field_index' ] = pods_clean_name( $info[ 'meta_field_index' ], false, false ); 
  6686. $info[ 'meta_field_value' ] = pods_clean_name( $info[ 'meta_field_value' ], false, false ); 
  6687.  
  6688. if ( empty( $info[ 'orderby' ] ) ) 
  6689. $info[ 'orderby' ] = '`t`.`' . $info[ 'field_index' ] . '`, `t`.`' . $info[ 'field_id' ] . '`'; 
  6690.  
  6691. if ( 'table' == pods_var_raw( 'storage', $info[ 'pod' ] ) && !in_array( $object_type, array( 'pod', 'table' ) ) ) { 
  6692. $info[ 'join' ][ 'd' ] = 'LEFT JOIN `' . $info[ 'pod_table' ] . '` AS `d` ON `d`.`id` = `t`.`' . $info[ 'field_id' ] . '`'; 
  6693. //$info[ 'select' ] .= ', `d`.*'; 
  6694.  
  6695. if ( !empty( $info[ 'pod' ] ) && is_array( $info[ 'pod' ] ) ) 
  6696. $info[ 'recurse' ] = true; 
  6697.  
  6698. $info[ 'type' ] = $object_type; 
  6699. $info[ 'object_name' ] = $object; 
  6700.  
  6701. if ( pods_api_cache() ) { 
  6702. if ( ! did_action( 'init' ) ) { 
  6703. $transient .= '_pre_init'; 
  6704. pods_transient_set( $transient, $info ); 
  6705.  
  6706.  
  6707. self::$table_info_cache[ $transient ] = apply_filters( 'pods_api_get_table_info', $info, $object_type, $object, $name, $pod, $field, $this ); 
  6708.  
  6709. return self::$table_info_cache[ $transient ]; 
  6710.  
  6711. /** 
  6712. * Export a package 
  6713. * $params['pod'] string Pod Type IDs to export 
  6714. * $params['template'] string Template IDs to export 
  6715. * $params['podpage'] string Pod Page IDs to export 
  6716. * $params['helper'] string Helper IDs to export 
  6717. * @param array $params An associative array of parameters 
  6718. * @return array|bool 
  6719. * @since 1.9.0 
  6720. * @deprecated 2.0 
  6721. */ 
  6722. public function export_package ( $params ) { 
  6723. if ( class_exists( 'Pods_Migrate_Packages' ) ) 
  6724. return Pods_Migrate_Packages::export( $params ); 
  6725.  
  6726. return false; 
  6727.  
  6728. /** 
  6729. * Replace an existing package 
  6730. * @param mixed $data (optional) An associative array containing a package, or the json encoded package 
  6731. * @return bool 
  6732. * @since 1.9.8 
  6733. * @deprecated 2.0 
  6734. */ 
  6735. public function replace_package ( $data = false ) { 
  6736. return $this->import_package( $data, true ); 
  6737.  
  6738. /** 
  6739. * Import a package 
  6740. * @param mixed $data (optional) An associative array containing a package, or the json encoded package 
  6741. * @param bool $replace (optional) Replace existing items when found 
  6742. * @return bool 
  6743. * @since 1.9.0 
  6744. * @deprecated 2.0 
  6745. */ 
  6746. public function import_package ( $data = false, $replace = false ) { 
  6747. if ( class_exists( 'Pods_Migrate_Packages' ) ) 
  6748. return Pods_Migrate_Packages::import( $data, $replace ); 
  6749.  
  6750. return false; 
  6751.  
  6752. /** 
  6753. * Validate a package 
  6754. * @param array|string $data (optional) An associative array containing a package, or the json encoded package 
  6755. * @param bool $output (optional) 
  6756. * @return array|bool 
  6757. * @since 1.9.0 
  6758. * @deprecated 2.0 
  6759. */ 
  6760. public function validate_package ( $data = false, $output = false ) { 
  6761. return true; 
  6762.  
  6763. /** 
  6764. * Import data from an array or a CSV file. 
  6765. * @param mixed $import_data PHP associative array or CSV input 
  6766. * @param bool $numeric_mode Use IDs instead of the name field when matching 
  6767. * @param string $format Format of import data, options are php or csv 
  6768. * @return array IDs of imported items 
  6769. * @since 1.7.1 
  6770. * @todo This needs some love and use of table_info etc for relationships 
  6771. */ 
  6772. public function import ( $import_data, $numeric_mode = false, $format = null ) { 
  6773. /** 
  6774. * @var $wpdb wpdb 
  6775. */ 
  6776. global $wpdb; 
  6777.  
  6778. if ( null === $format && null !== $this->format ) 
  6779. $format = $this->format; 
  6780.  
  6781. if ( 'csv' == $format && !is_array( $import_data ) ) { 
  6782. $data = pods_migrate( 'sv', ', ' )->parse( $import_data ); 
  6783.  
  6784. $import_data = $data[ 'items' ]; 
  6785.  
  6786. pods_query( "SET NAMES utf8" ); 
  6787. pods_query( "SET CHARACTER SET utf8" ); 
  6788.  
  6789. // Loop through the array of items 
  6790. $ids = array(); 
  6791.  
  6792. // Test to see if it's an array of arrays 
  6793. if ( !is_array( @current( $import_data ) ) ) 
  6794. $import_data = array( $import_data ); 
  6795.  
  6796. $pod = $this->load_pod( array( 'name' => $this->pod ) ); 
  6797.  
  6798. if ( false === $pod ) 
  6799. return pods_error( __( 'Pod not found', 'pods' ), $this ); 
  6800.  
  6801. $fields = array_merge( $pod[ 'fields' ], $pod[ 'object_fields' ] ); 
  6802.  
  6803. $simple_tableless_objects = PodsForm::simple_tableless_objects(); 
  6804.  
  6805. foreach ( $import_data as $key => $data_row ) { 
  6806. $data = array(); 
  6807.  
  6808. // Loop through each field (use $fields so only valid fields get parsed) 
  6809. foreach ( $fields as $field_name => $field_data ) { 
  6810. if ( !isset( $data_row[ $field_name ] ) && !isset( $data_row[ $field_data[ 'label' ] ] ) ) 
  6811. continue; 
  6812.  
  6813. $field_id = $field_data[ 'id' ]; 
  6814. $type = $field_data[ 'type' ]; 
  6815. $pick_object = isset( $field_data[ 'pick_object' ] ) ? $field_data[ 'pick_object' ] : ''; 
  6816. $pick_val = isset( $field_data[ 'pick_val' ] ) ? $field_data[ 'pick_val' ] : ''; 
  6817.  
  6818. if ( isset( $data_row[ $field_name] ) ) 
  6819. $field_value = $data_row[ $field_name ]; 
  6820. else 
  6821. $field_value = $data_row[ $field_data[ 'label' ] ]; 
  6822.  
  6823. if ( null !== $field_value && false !== $field_value && '' !== $field_value ) { 
  6824. if ( 'pick' == $type || in_array( $type, PodsForm::file_field_types() ) ) { 
  6825. $field_values = is_array( $field_value ) ? $field_value : array( $field_value ); 
  6826. $pick_values = array(); 
  6827.  
  6828. foreach ( $field_values as $pick_value ) { 
  6829. if ( in_array( $type, PodsForm::file_field_types() ) || 'media' == $pick_object ) { 
  6830. $where = "`guid` = '" . pods_sanitize( $pick_value ) . "'"; 
  6831.  
  6832. if ( 0 < pods_absint( $pick_value ) && false !== $numeric_mode ) 
  6833. $where = "`ID` = " . pods_absint( $pick_value ); 
  6834.  
  6835. $result = pods_query( "SELECT `ID` AS `id` FROM `{$wpdb->posts}` WHERE `post_type` = 'attachment' AND {$where} ORDER BY `ID`", $this ); 
  6836.  
  6837. if ( !empty( $result ) ) 
  6838. $pick_values[] = $result[ 0 ]->id; 
  6839. // @todo This could and should be abstracted better and simplified 
  6840. elseif ( 'pick' == $type ) { 
  6841. $related_pod = false; 
  6842.  
  6843. if ( 'pod' == $pick_object ) 
  6844. $related_pod = $this->load_pod( array( 'name' => $pick_val, 'table_info' => true ), false ); 
  6845.  
  6846. if ( empty( $related_pod ) ) { 
  6847. $related_pod = array( 
  6848. 'id' => 0,  
  6849. 'type' => $pick_object 
  6850. ); 
  6851.  
  6852. if ( in_array( 'taxonomy', array( $pick_object, $related_pod[ 'type' ] ) ) ) { 
  6853. $where = "`t`.`name` = '" . pods_sanitize( $pick_value ) . "'"; 
  6854.  
  6855. if ( 0 < pods_absint( $pick_value ) && false !== $numeric_mode ) 
  6856. $where = "`tt`.`term_id` = " . pods_absint( $pick_value ); 
  6857.  
  6858. $result = pods_query( "SELECT `t`.`term_id` AS `id` FROM `{$wpdb->term_taxonomy}` AS `tt` LEFT JOIN `{$wpdb->terms}` AS `t` ON `t`.`term_id` = `tt`.`term_id` WHERE `taxonomy` = '{$pick_val}' AND {$where} ORDER BY `t`.`term_id`", $this ); 
  6859.  
  6860. if ( !empty( $result ) ) 
  6861. $pick_values[] = $result[ 0 ]->id; 
  6862. elseif ( in_array( 'post_type', array( $pick_object, $related_pod[ 'type' ] ) ) || in_array( 'media', array( $pick_object, $related_pod[ 'type' ] ) ) ) { 
  6863. $where = "`post_title` = '" . pods_sanitize( $pick_value ) . "'"; 
  6864.  
  6865. if ( 0 < pods_absint( $pick_value ) && false !== $numeric_mode ) 
  6866. $where = "`ID` = " . pods_absint( $pick_value ); 
  6867.  
  6868. $result = pods_query( "SELECT `ID` AS `id` FROM `{$wpdb->posts}` WHERE `post_type` = '{$pick_val}' AND {$where} ORDER BY `ID`", $this ); 
  6869.  
  6870. if ( !empty( $result ) ) 
  6871. $pick_values[] = $result[ 0 ]->id; 
  6872. elseif ( in_array( 'user', array( $pick_object, $related_pod[ 'type' ] ) ) ) { 
  6873. $where = "`user_login` = '" . pods_sanitize( $pick_value ) . "'"; 
  6874.  
  6875. if ( 0 < pods_absint( $pick_value ) && false !== $numeric_mode ) 
  6876. $where = "`ID` = " . pods_absint( $pick_value ); 
  6877.  
  6878. $result = pods_query( "SELECT `ID` AS `id` FROM `{$wpdb->users}` WHERE {$where} ORDER BY `ID`", $this ); 
  6879.  
  6880. if ( !empty( $result ) ) 
  6881. $pick_values[] = $result[ 0 ]->id; 
  6882. elseif ( in_array( 'comment', array( $pick_object, $related_pod[ 'type' ] ) ) ) { 
  6883. $where = "`comment_ID` = " . pods_absint( $pick_value ); 
  6884.  
  6885. $result = pods_query( "SELECT `comment_ID` AS `id` FROM `{$wpdb->comments}` WHERE {$where} ORDER BY `ID`", $this ); 
  6886.  
  6887. if ( !empty( $result ) ) 
  6888. $pick_values[] = $result[ 0 ]->id; 
  6889. elseif ( in_array( $pick_object, $simple_tableless_objects ) ) 
  6890. $pick_values[] = $pick_value; 
  6891. elseif ( !empty( $related_pod[ 'id' ] ) ) { 
  6892. $where = "`" . $related_pod[ 'field_index' ] . "` = '" . pods_sanitize( $pick_value ) . "'"; 
  6893.  
  6894. if ( 0 < pods_absint( $pick_value ) && false !== $numeric_mode ) 
  6895. $where = "`" . $related_pod[ 'field_id' ] . "` = " . pods_absint( $pick_value ); 
  6896.  
  6897. $result = pods_query( "SELECT `" . $related_pod[ 'field_id' ] . "` AS `id` FROM `" . $related_pod[ 'table' ] . "` WHERE {$where} ORDER BY `" . $related_pod[ 'field_id' ] . "`", $this ); 
  6898.  
  6899. if ( !empty( $result ) ) 
  6900. $pick_values[] = $result[ 0 ]->id; 
  6901.  
  6902. $field_value = implode( ', ', $pick_values ); 
  6903.  
  6904. $data[ $field_name ] = $field_value; 
  6905.  
  6906. if ( !empty( $data ) ) { 
  6907. $params = array( 
  6908. 'pod' => $this->pod,  
  6909. 'data' => $data 
  6910. ); 
  6911.  
  6912. $ids[] = $this->save_pod_item( $params ); 
  6913.  
  6914. return $ids; 
  6915.  
  6916. /** 
  6917. * Export data from a Pod 
  6918. * @param string|object $pod The pod name or Pods object 
  6919. * @param array $params An associative array of parameters 
  6920. * @return array Data arrays of all exported pod items 
  6921. * @since 1.7.1 
  6922. */ 
  6923. public function export ( $pod = null, $params = null ) { 
  6924.  
  6925. if ( empty( $pod ) ) { 
  6926. $pod = $this->pod; 
  6927.  
  6928. $find = array( 
  6929. 'limit' => -1,  
  6930. 'search' => false,  
  6931. 'pagination' => false 
  6932. ); 
  6933.  
  6934. if ( !empty( $params ) && isset( $params[ 'params' ] ) ) { 
  6935. $find = array_merge( $find, (array) $params[ 'params' ] ); 
  6936.  
  6937. unset( $params[ 'params' ] ); 
  6938.  
  6939. $pod = pods( $pod, $find ); 
  6940. elseif ( !is_object( $pod ) ) { 
  6941. $pod = pods( $pod, $find ); 
  6942.  
  6943. $data = array(); 
  6944.  
  6945. while ( $pod->fetch() ) { 
  6946. $data[ $pod->id() ] = $this->export_pod_item( $params, $pod ); 
  6947.  
  6948. $data = $this->do_hook( 'export', $data, $pod->pod, $pod ); 
  6949.  
  6950. return $data; 
  6951.  
  6952. /** 
  6953. * Convert CSV to a PHP array 
  6954. * @param string $data The CSV input 
  6955. * @return array 
  6956. * @since 1.7.1 
  6957. * @deprecated 2.3.5 
  6958. */ 
  6959. public function csv_to_php ( $data, $delimiter = ', ' ) { 
  6960. pods_deprecated( "PodsAPI->csv_to_php", '2.3.5' ); 
  6961.  
  6962. $data = pods_migrate( 'sv', $delimiter, $data )->parse(); 
  6963.  
  6964. return $data[ 'items' ]; 
  6965.  
  6966. /** 
  6967. * Clear Pod-related cache 
  6968. * @param array $pod 
  6969. * @return void 
  6970. * @since 2.0 
  6971. */ 
  6972. public function cache_flush_pods ( $pod = null ) { 
  6973. /** 
  6974. * @var $wpdb wpdb 
  6975. */ 
  6976. global $wpdb; 
  6977.  
  6978. pods_transient_clear( 'pods' ); 
  6979. pods_transient_clear( 'pods_components' ); 
  6980.  
  6981. if ( null !== $pod && is_array( $pod ) ) { 
  6982. pods_transient_clear( 'pods_pod_' . $pod[ 'name' ] ); 
  6983. pods_cache_clear( $pod[ 'name' ], 'pods-class' ); 
  6984.  
  6985. foreach ( $pod[ 'fields' ] as $field ) { 
  6986. pods_transient_clear( 'pods_field_' . $pod[ 'name' ] . '_' . $field[ 'name' ] ); 
  6987.  
  6988. if ( in_array( $pod[ 'type' ], array( 'post_type', 'taxonomy' ) ) ) 
  6989. pods_transient_clear( 'pods_wp_cpt_ct' ); 
  6990. else 
  6991. pods_transient_clear( 'pods_wp_cpt_ct' ); 
  6992.  
  6993. $wpdb->query( "DELETE FROM `{$wpdb->options}` WHERE `option_name` LIKE '_transient_pods%'" ); 
  6994. $wpdb->query( "DELETE FROM `{$wpdb->options}` WHERE `option_name` LIKE '_transient_timeout_pods%'" ); 
  6995.  
  6996. pods_cache_clear( true ); 
  6997.  
  6998. pods_transient_set( 'pods_flush_rewrites', 1 ); 
  6999.  
  7000. /** 
  7001. * Process a Pod-based form 
  7002. * @param mixed $params 
  7003. * @param object $obj Pod object 
  7004. * @param array $fields Fields being submitted in form ( key => settings ) 
  7005. * @param string $thank_you URL to send to upon success 
  7006. * @return mixed 
  7007. * @since 2.0 
  7008. */ 
  7009. public function process_form ( $params, $obj = null, $fields = null, $thank_you = null ) { 
  7010. $this->display_errors = false; 
  7011.  
  7012. $form = null; 
  7013.  
  7014. $nonce = pods_var( '_pods_nonce', $params ); 
  7015. $pod = pods_var( '_pods_pod', $params ); 
  7016. $id = pods_var( '_pods_id', $params ); 
  7017. $uri = pods_var( '_pods_uri', $params ); 
  7018. $form = pods_var( '_pods_form', $params ); 
  7019. $location = pods_var( '_pods_location', $params ); 
  7020.  
  7021. if ( is_object( $obj ) ) { 
  7022. $pod = $obj->pod; 
  7023. $id = $obj->id(); 
  7024.  
  7025. if ( !empty( $fields ) ) { 
  7026. $fields = array_keys( $fields ); 
  7027. $form = implode( ', ', $fields ); 
  7028. else 
  7029. $fields = explode( ', ', $form ); 
  7030.  
  7031. if ( empty( $nonce ) || empty( $pod ) || empty( $uri ) || empty( $fields ) ) 
  7032. return pods_error( __( 'Invalid submission', 'pods' ), $this ); 
  7033.  
  7034. $uid = @session_id(); 
  7035.  
  7036. if ( is_user_logged_in() ) 
  7037. $uid = 'user_' . get_current_user_id(); 
  7038.  
  7039. $field_hash = wp_create_nonce( 'pods_fields_' . $form ); 
  7040.  
  7041. $action = 'pods_form_' . $pod . '_' . $uid . '_' . $id . '_' . $uri . '_' . $field_hash; 
  7042.  
  7043. if ( empty( $uid ) ) 
  7044. return pods_error( __( 'Access denied for your session, please refresh and try again.', 'pods' ), $this ); 
  7045.  
  7046. if ( false === wp_verify_nonce( $nonce, $action ) ) 
  7047. return pods_error( __( 'Access denied, please refresh and try again.', 'pods' ), $this ); 
  7048.  
  7049. $data = array(); 
  7050.  
  7051. foreach ( $fields as $field ) { 
  7052. $data[ $field ] = pods_var_raw( 'pods_field_' . $field, $params, '' ); 
  7053.  
  7054. $params = array( 
  7055. 'pod' => $pod,  
  7056. 'id' => $id,  
  7057. 'data' => $data,  
  7058. 'from' => 'process_form',  
  7059. 'location' => $location 
  7060. ); 
  7061.  
  7062. $id = $this->save_pod_item( $params ); 
  7063.  
  7064. if ( 0 < $id && !empty( $thank_you ) ) { 
  7065. $thank_you = str_replace( 'X_ID_X', $id, $thank_you ); 
  7066.  
  7067. pods_redirect( $thank_you ); 
  7068.  
  7069. return $id; 
  7070.  
  7071. /** 
  7072. * Handle filters / actions for the class 
  7073. * @since 2.0 
  7074. */ 
  7075. private function do_hook () { 
  7076. $args = func_get_args(); 
  7077. if ( empty( $args ) ) 
  7078. return false; 
  7079. $name = array_shift( $args ); 
  7080. return pods_do_hook( "api", $name, $args, $this ); 
  7081.  
  7082. /** 
  7083. * Handle variables that have been deprecated 
  7084. * @since 2.0 
  7085. */ 
  7086. public function __get ( $name ) { 
  7087. $name = (string) $name; 
  7088.  
  7089. if ( !isset( $this->deprecated ) ) { 
  7090. require_once( PODS_DIR . 'deprecated/classes/PodsAPI.php' ); 
  7091. $this->deprecated = new PodsAPI_Deprecated( $this ); 
  7092.  
  7093. $var = null; 
  7094.  
  7095. if ( isset( $this->deprecated->{$name} ) ) { 
  7096. pods_deprecated( "PodsAPI->{$name}", '2.0' ); 
  7097.  
  7098. $var = $this->deprecated->{$name}; 
  7099. else 
  7100. pods_deprecated( "PodsAPI->{$name}", '2.0' ); 
  7101.  
  7102. return $var; 
  7103.  
  7104. /** 
  7105. * Handle methods that have been deprecated 
  7106. * @since 2.0 
  7107. */ 
  7108. public function __call ( $name, $args ) { 
  7109. $name = (string) $name; 
  7110.  
  7111. if ( !isset( $this->deprecated ) ) { 
  7112. require_once( PODS_DIR . 'deprecated/classes/PodsAPI.php' ); 
  7113. $this->deprecated = new PodsAPI_Deprecated( $this ); 
  7114.  
  7115. if ( method_exists( $this->deprecated, $name ) ) 
  7116. return call_user_func_array( array( $this->deprecated, $name ), $args ); 
  7117. else 
  7118. pods_deprecated( "PodsAPI::{$name}", '2.0' );