PluginProbe
Property Hive / 2.3.0
Property Hive v2.3.0
2.3.1 2.3.0 2.2.6 2.2.5 2.2.4 2.2.3 2.2.2 1.4.46 1.4.47 1.4.48 1.4.49 1.4.5 1.4.50 1.4.51 1.4.52 1.4.53 1.4.54 1.4.55 1.4.56 1.4.57 1.4.58 1.4.59 1.4.6 1.4.60 1.4.61 All 261 releases
← All changes | includes/class-ph-install.php +228 -39 1.4.522.3.0 View file →
@@ -17,8 +17,25 @@
17 17 */
18 18 class PH_Install {
19 19
20 20 /**
21 + * DB updates and callbacks that need to be run per version.
22 + *
23 + * @var array
24 + */
25 + private static $db_updates = array(
26 + '1.4.68' => array(
27 + 'propertyhive_update_1468_on_market_change_dates',
28 + ),
29 + '2.0.0' => array(
30 + 'propertyhive_update_200_pre_pro_record_installed_plugins',
31 + ),
32 + '2.2.0' => array(
33 + 'propertyhive_deactivate_template_assistant', // different naming convention as needs to be run elsewhere too
34 + ),
35 + );
36 +
37 + /**
21 38 * Hook in tabs.
22 39 */
23 40 public function __construct() {
24 41 register_activation_hook( PH_PLUGIN_FILE, array( $this, 'install' ) );
@@ -69,8 +86,10 @@
69 86
70 87 $this->create_primary_office();
71 88 $this->create_cron_jobs();
72 89
90 + $this->update();
91 +
73 92 // Clear transient cache
74 93
75 94 // Queue upgrades
76 95 $current_version = get_option( 'propertyhive_version', null );
@@ -79,8 +98,9 @@
79 98 // No existing version set. This must be a new fresh install
80 99 if ( is_null( $current_version ) && is_null( $current_db_version ) )
81 100 {
82 101 $this->create_terms();
102 + $this->create_pages();
83 103 set_transient( '_ph_activation_redirect', 1, 30 );
84 104 }
85 105
86 106 update_option( 'propertyhive_db_version', PH()->version );
@@ -105,11 +125,22 @@
105 125 wp_clear_scheduled_hook( 'propertyhive_update_currency_exchange_rates' );
106 126 wp_clear_scheduled_hook( 'propertyhive_process_email_log' );
107 127 wp_clear_scheduled_hook( 'propertyhive_auto_email_match' );
108 128 wp_clear_scheduled_hook( 'propertyhive_check_licenses' );
129 + wp_clear_scheduled_hook( 'propertyhive_update_address_concatenated' );
130 + wp_clear_scheduled_hook( 'propertyhive_cleanup_search_analytics' );
109 131 }
110 132
111 133 /**
134 + * Get list of DB update callbacks.
135 + *
136 + * @return array
137 + */
138 + public static function get_db_update_callbacks() {
139 + return self::$db_updates;
140 + }
141 +
142 + /**
112 143 * Handle updates
113 144 */
114 145 public function update() {
115 146 // Do updates
@@ -114,19 +145,17 @@
114 145 public function update() {
115 146 // Do updates
116 147 $current_db_version = get_option( 'propertyhive_db_version' );
117 148
118 - /*if ( version_compare( $current_db_version, '1.4', '<' ) ) {
119 - include( 'updates/propertyhive-update-1.4.php' );
120 - update_option( 'propertyhive_db_version', '1.4' );
149 + foreach ( self::get_db_update_callbacks() as $version => $update_callbacks ) {
150 + if ( version_compare( $current_db_version, $version, '<' ) ) {
151 + foreach ( $update_callbacks as $update_callback ) {
152 + add_action('property_run_update_actions', $update_callback);
153 + }
154 + }
121 155 }
122 -
123 - if ( version_compare( $current_db_version, '2.1.0', '<' ) || PH_VERSION == '2.1-bleeding' ) {
124 - include( 'updates/propertyhive-update-2.1.php' );
125 - update_option( 'propertyhive_db_version', '2.1.0' );
126 - }*/
127 -
128 - update_option( 'propertyhive_db_version', PH()->version );
156 + // phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedHooknameFound -- Existing public Property Hive extension hook property_run_update_actions; changing the established name would detach installed callbacks.
157 + do_action('property_run_update_actions');
129 158 }
130 159
131 160 /**
132 161 * Create cron jobs (clear them first)
@@ -137,13 +166,13 @@
137 166 wp_clear_scheduled_hook( 'propertyhive_update_currency_exchange_rates' );
138 167 wp_clear_scheduled_hook( 'propertyhive_process_email_log' );
139 168 wp_clear_scheduled_hook( 'propertyhive_auto_email_match' );
140 169 wp_clear_scheduled_hook( 'propertyhive_check_licenses' );
170 + wp_clear_scheduled_hook( 'propertyhive_update_address_concatenated' );
171 + wp_clear_scheduled_hook( 'propertyhive_cleanup_search_analytics' );
141 172
142 - $ve = get_option( 'gmt_offset' ) > 0 ? '+' : '-';
143 -
144 173 // Schedule for midnight as it's likely traffic will be quieter at that time
145 - wp_schedule_event( strtotime( '00:00 tomorrow ' . $ve . get_option( 'gmt_offset' ) . ' HOURS' ), 'daily', 'propertyhive_update_currency_exchange_rates' );
174 + wp_schedule_event( strtotime( 'tomorrow' ) - ( (int)get_option( 'gmt_offset' ) * HOUR_IN_SECONDS ), 'daily', 'propertyhive_update_currency_exchange_rates' );
146 175
147 176 wp_schedule_event( time(), 'every_fifteen_minutes', 'propertyhive_process_email_log' );
148 177
149 178 $auto_property_match_enabled = get_option( 'propertyhive_auto_property_match', '' );
@@ -149,14 +178,31 @@
149 178 $auto_property_match_enabled = get_option( 'propertyhive_auto_property_match', '' );
150 179
151 180 if ( $auto_property_match_enabled == 'yes' )
152 181 {
153 - wp_schedule_event( strtotime( '02:00 tomorrow ' . $ve . get_option( 'gmt_offset' ) . ' HOURS' ), 'daily', 'propertyhive_auto_email_match' );
182 + $recurrence = apply_filters( 'propertyhive_auto_email_match_cron_recurrence', 'daily' );
183 + if ( $recurrence != 'hourly' )
184 + {
185 + $timestamp = strtotime( 'tomorrow +2hours') - ( (int)get_option( 'gmt_offset' ) * HOUR_IN_SECONDS );
186 + }
187 + else
188 + {
189 + $timestamp = strtotime( '+1 hours' );
190 + }
191 + wp_schedule_event(
192 + apply_filters( 'propertyhive_auto_email_match_cron_timestamp', $timestamp ),
193 + $recurrence,
194 + 'propertyhive_auto_email_match'
195 + );
154 196 }
155 197
156 198 // Schedule for 1am as it's likely traffic will be quieter at that time
157 199 // 1am so it doesn't run at exactly the same time as the exchange rate cron
158 - wp_schedule_event( strtotime( '01:00 tomorrow ' . $ve . get_option( 'gmt_offset' ) . ' HOURS' ), 'daily', 'propertyhive_check_licenses' );
200 + wp_schedule_event( strtotime( 'tomorrow +1hours' ) - ( (int)get_option( 'gmt_offset' ) * HOUR_IN_SECONDS ), 'daily', 'propertyhive_check_licenses' );
201 +
202 + wp_schedule_event( strtotime( 'tomorrow +3hours' ) - ( (int)get_option( 'gmt_offset' ) * HOUR_IN_SECONDS ), 'daily', 'propertyhive_update_address_concatenated' );
203 +
204 + wp_schedule_event( time() + HOUR_IN_SECONDS, 'daily', 'propertyhive_cleanup_search_analytics' );
159 205 }
160 206
161 207 public function custom_cron_recurrence( $schedules )
162 208 {
@@ -161,9 +207,9 @@
161 207 public function custom_cron_recurrence( $schedules )
162 208 {
163 209 $schedules['every_fifteen_minutes'] = array(
164 210 'interval' => 900,
165 - 'display' => __( 'Every 15 Minutes', 'textdomain' )
211 + 'display' => __( 'Every 15 Minutes', 'propertyhive' )
166 212 );
167 213
168 214 return $schedules;
169 215 }
@@ -173,9 +219,9 @@
173 219 *
174 220 * @access public
175 221 * @return void
176 222 */
177 - public static function create_pages() {
223 + public function create_pages() {
178 224
179 225 // Create page object
180 226 $my_post = array(
181 227 'post_title' => __( 'Property Search', 'propertyhive' ),
@@ -186,11 +232,14 @@
186 232 'ping_status' => 'closed',
187 233 );
188 234
189 235 // Insert the post into the database
190 - $page_id = wp_insert_post( $my_post );
236 + $page_id = wp_insert_post( $my_post, true );
191 237
192 - update_option( 'propertyhive_search_results_page_id', $page_id );
238 + if ( !is_wp_error($page_id) )
239 + {
240 + update_option( 'propertyhive_search_results_page_id', $page_id );
241 + }
193 242 }
194 243
195 244 /**
196 245 * Add the default terms for PH taxonomies - property types, tenures etc. Modify this at your own risk.
@@ -202,27 +251,34 @@
202 251
203 252 $taxonomies = array(
204 253 'availability' => array(
205 254 array(
206 - 'name' => 'For Sale'
255 + 'name' => 'For Sale',
256 + 'departments' => array('residential-sales', 'commercial')
207 257 ),
208 258 array(
209 - 'name' => 'Under Offer'
259 + 'name' => 'Under Offer',
260 + 'departments' => array('residential-sales', 'commercial')
210 261 ),
211 262 array(
212 - 'name' => 'Sold STC'
263 + 'name' => 'Sold STC',
264 + 'departments' => array('residential-sales', 'commercial')
213 265 ),
214 266 array(
215 - 'name' => 'Sold'
267 + 'name' => 'Sold',
268 + 'departments' => array('residential-sales', 'commercial')
216 269 ),
217 270 array(
218 - 'name' => 'To Let'
271 + 'name' => 'To Let',
272 + 'departments' => array('residential-lettings', 'commercial')
219 273 ),
220 274 array(
221 - 'name' => 'Let Agreed'
275 + 'name' => 'Let Agreed',
276 + 'departments' => array('residential-lettings', 'commercial')
222 277 ),
223 278 array(
224 - 'name' => 'Let'
279 + 'name' => 'Let',
280 + 'departments' => array('residential-lettings', 'commercial')
225 281 ),
226 282 ),
227 283 'property_type' => array(
228 284 // HOUSE
@@ -277,9 +333,9 @@
277 333 'name' => 'Terraced Bungalow',
278 334 'child_of_previous' => true
279 335 ),
280 336 array(
281 - 'name' => 'End of Terrace House',
337 + 'name' => 'End of Terrace Bungalow',
282 338 'child_of_previous' => true
283 339 ),
284 340 // FLATS
285 341 array(
@@ -417,8 +473,14 @@
417 473 'name' => 'Freehold'
418 474 ),
419 475 array(
420 476 'name' => 'Leasehold'
477 + ),
478 + array(
479 + 'name' => 'Share of Freehold'
480 + ),
481 + array(
482 + 'name' => 'Commonhold'
421 483 )
422 484 ),
423 485 'commercial_tenure' => array(
424 486 array(
@@ -425,8 +487,14 @@
425 487 'name' => 'Freehold'
426 488 ),
427 489 array(
428 490 'name' => 'Leasehold'
491 + ),
492 + array(
493 + 'name' => 'Share of Freehold'
494 + ),
495 + array(
496 + 'name' => 'Commonhold'
429 497 )
430 498 ),
431 499 'furnished' => array(
432 500 array(
@@ -446,10 +514,30 @@
446 514 array(
447 515 'name' => 'Chain Free'
448 516 )
449 517 ),
518 + 'management_key_date_type' => array(
519 + array(
520 + 'name' => 'Initial Inventory',
521 + 'recurrence_type' => 'tenancy_management',
522 + 'recurrence_rule' => 'FREQ=ONCE',
523 + ),
524 + array(
525 + 'name' => 'Inspection',
526 + 'recurrence_type' => 'tenancy_management',
527 + 'recurrence_rule' => 'FREQ=MONTHLY;INTERVAL=3',
528 + ),
529 + array(
530 + 'name' => 'Gas Safety Check',
531 + 'recurrence_type' => 'property_management',
532 + 'recurrence_rule' => 'FREQ=YEARLY;INTERVAL=1',
533 + ),
534 + ),
450 535 );
451 536
537 + $availability_departments = get_option( 'propertyhive_availability_departments', array() );
538 + if ( !is_array($availability_departments) ) { $availability_departments = array(); }
539 +
452 540 $previous_term_id = '';
453 541 foreach ( $taxonomies as $taxonomy => $terms )
454 542 {
455 543 // Make sure no terms for this taxonomy exist already
@@ -471,8 +559,26 @@
471 559 if ( !isset($term['child_of_previous']) || (isset($term['child_of_previous']) && !$term['child_of_previous']) )
472 560 {
473 561 $previous_term_id = $return['term_id'];
474 562 }
563 +
564 + if ( $taxonomy == 'availability' && is_array($term['departments']) && !empty($term['departments']) )
565 + {
566 + $availability_departments[$return['term_id']] = $term['departments'];
567 + }
568 +
569 + if ( $taxonomy == 'management_key_date_type' && isset($term['recurrence_type']) && isset($term['recurrence_rule']) )
570 + {
571 + $options = get_option( 'propertyhive_key_date_type', array() );
572 + if ( !is_array($options) ) { $options = array(); }
573 +
574 + $options[$return['term_id']] = array(
575 + 'recurrence_rule' => $term['recurrence_rule'],
576 + 'recurrence_type' => $term['recurrence_type'],
577 + );
578 +
579 + update_option( 'propertyhive_key_date_type', $options );
580 + }
475 581 }
476 582 else
477 583 {
478 584 // Hmm... an error occurred
@@ -481,8 +587,10 @@
481 587 }
482 588 }
483 589 }
484 590 }
591 +
592 + update_option( 'propertyhive_availability_departments', $availability_departments );
485 593 }
486 594
487 595 /**
488 596 * Add the first office so at least one exists
@@ -525,8 +633,11 @@
525 633 add_option( 'propertyhive_active_departments_sales', 'yes', '', 'yes' );
526 634 add_option( 'propertyhive_active_departments_lettings', 'yes', '', 'yes' );
527 635 add_option( 'propertyhive_primary_department', 'residential-sales', '', 'yes' );
528 636
637 + add_option( 'propertyhive_maps_provider', 'osm', '', 'no' );
638 + add_option( 'propertyhive_geocoding_provider', 'osm', '', 'no' );
639 +
529 640 add_option( 'propertyhive_default_country', 'GB', '', 'yes' );
530 641 add_option( 'propertyhive_countries', array('GB'), '', 'yes' );
531 642
532 643 add_option( 'propertyhive_applicant_match_price_range_percentage_lower', 20, '', 'no' );
@@ -531,22 +642,28 @@
531 642
532 643 add_option( 'propertyhive_applicant_match_price_range_percentage_lower', 20, '', 'no' );
533 644 add_option( 'propertyhive_applicant_match_price_range_percentage_higher', 5, '', 'no' );
534 645
646 + add_option( 'propertyhive_license_type', 'pro', '', 'yes' );
647 +
535 648 add_option( 'propertyhive_install_timestamp', time(), '', 'no' );
536 649 add_option( 'propertyhive_review_prompt_due_timestamp', strtotime('+30 days'), '', 'no' );
537 650
538 651 add_option( 'propertyhive_enquiry_auto_responder_email_subject', __( 'Thank you for your enquiry', 'propertyhive' ), '', 'no' );
539 - add_option( 'propertyhive_enquiry_auto_responder_email_body', __( "Thank you for your recent property enquiry about [property_address_hyperlinked]. A member of our team will be in touch shortly.
652 + add_option( 'propertyhive_enquiry_auto_responder_email_body', sprintf(
653 + /* translators: %s: blog name shown in the email sign-off */
654 + __( "Thank you for your recent property enquiry about [property_address_hyperlinked]. A member of our team will be in touch shortly.
540 655
541 656 Kind regards,
542 657
543 -" . get_bloginfo('name') . "
658 +%s
544 659
545 -[similar_properties]", 'propertyhive' ), '', 'no' );
660 +[similar_properties]", 'propertyhive' ),
661 + get_bloginfo('name')
662 + ), '', 'no' );
546 663
547 664 add_option( 'propertyhive_property_match_default_email_subject', __( 'We found [property_count] that might be of interest to you', 'propertyhive' ), '', 'no' );
548 - add_option( 'propertyhive_property_match_default_email_body', __( "Hi [contact_name],
665 + add_option( 'propertyhive_property_match_default_email_body', __( "Hi [contact_dear],
549 666
550 667 Based on your requirements, we've found [property_count] below that we believe might be suitable for you:
551 668
552 669 [properties]
@@ -554,28 +671,84 @@
554 671 If you have any questions or require more information about any of the properties shown above please let me know.
555 672
556 673 Kind regards,
557 674
558 -" . get_bloginfo('name'), 'propertyhive' ), '', 'no' );
675 +", 'propertyhive' ) . get_bloginfo('name'), '', 'no' );
559 676
560 - add_option( 'propertyhive_viewing_applicant_booking_confirmation_email_subject', 'Your Viewing On [property_address]', '', 'no' );
561 - add_option( 'propertyhive_viewing_applicant_booking_confirmation_email_body', "Dear [applicant_name],
677 + // Applicant Viewing Booking Confirmation
678 + add_option( 'propertyhive_viewing_applicant_booking_confirmation_email_subject', __( 'Your Viewing On [property_address]', 'propertyhive' ), '', 'no' );
679 + add_option( 'propertyhive_viewing_applicant_booking_confirmation_email_body', __( "Dear [applicant_dear],
562 680
563 681 This is confirmation that your viewing on [property_address] has been booked for [viewing_time] on [viewing_date].
564 682
565 683 Should you need to cancel or amend your booking please do not hesitate to contact us.
566 684
567 -" . get_bloginfo('name'), '', 'no' );
685 +", 'propertyhive' ) . get_bloginfo('name'), '', 'no' );
568 686
569 - add_option( 'propertyhive_viewing_owner_booking_confirmation_email_subject', 'Viewing Booked On [property_address]', '', 'no' );
570 - add_option( 'propertyhive_viewing_owner_booking_confirmation_email_body', "Dear [owner_name],
687 + // Applicant Viewing Cancellation Notification
688 + add_option( 'propertyhive_viewing_applicant_cancellation_notification_email_subject', __( 'Your Viewing On [property_address] Has Been Cancelled', 'propertyhive' ), '', 'no' );
689 + add_option( 'propertyhive_viewing_applicant_cancellation_notification_email_body', __( "Dear [applicant_dear],
571 690
691 +This is confirmation that a viewing on [property_address] that was booked for [viewing_time] on [viewing_date] has been cancelled. [cancelled_reason]
692 +
693 +Should you have any questions please do not hesitate to contact us.
694 +
695 +", 'propertyhive' ) . get_bloginfo('name'), '', 'no' );
696 +
697 + // Owner/Landlord Viewing Booking Confirmation
698 + add_option( 'propertyhive_viewing_owner_booking_confirmation_email_subject', __( 'Viewing Booked On [property_address]', 'propertyhive' ), '', 'no' );
699 + add_option( 'propertyhive_viewing_owner_booking_confirmation_email_body', __( "Dear [owner_dear],
700 +
572 701 This is confirmation that a viewing has been booked at your property, [property_address], for [viewing_time] on [viewing_date].
573 702
574 703 Should you need to cancel or amend this viewing please do not hesitate to contact us.
575 704
576 -" . get_bloginfo('name'), '', 'no' );
705 +", 'propertyhive' ) . get_bloginfo('name'), '', 'no' );
577 706
707 + // Owner/Landlord Viewing Cancellation Notification
708 + add_option( 'propertyhive_viewing_owner_cancellation_notification_email_subject', __( 'Viewing Cancelled On [property_address]', 'propertyhive' ), '', 'no' );
709 + add_option( 'propertyhive_viewing_owner_cancellation_notification_email_body', __( "Dear [owner_dear],
710 +
711 +This is confirmation that a viewing on [property_address] that was booked for [viewing_time] on [viewing_date] has been cancelled. [cancelled_reason]
712 +
713 +Should you have any questions please do not hesitate to contact us.
714 +
715 +", 'propertyhive' ) . get_bloginfo('name'), '', 'no' );
716 +
717 + // Attending Negotiator Viewing Booking Confirmation
718 + add_option( 'propertyhive_viewing_attending_negotiator_booking_confirmation_email_subject', __( 'Viewing Booked On [property_address]', 'propertyhive' ), '', 'no' );
719 + add_option( 'propertyhive_viewing_attending_negotiator_booking_confirmation_email_body', __( "This is confirmation you've been assigned to attend a viewing at property, [property_address], for [viewing_time] on [viewing_date].
720 +
721 +Applicant Details:
722 +[applicant_details]
723 +
724 +Owner Details:
725 +[owner_details]
726 +
727 +", 'propertyhive' ) . get_bloginfo('name'), '', 'no' );
728 +
729 + // Attending Negotiator Viewing Cancellation Notification
730 + add_option( 'propertyhive_viewing_attending_negotiator_cancellation_notification_email_subject', __( 'Viewing Cancelled On [property_address]', 'propertyhive' ), '', 'no' );
731 + add_option( 'propertyhive_viewing_attending_negotiator_cancellation_notification_email_body', __( "This is confirmation that a viewing you were assigned to carry out on [property_address] that was booked for [viewing_time] on [viewing_date] has been cancelled. [cancelled_reason]
732 +
733 +Applicant Details:
734 +[applicant_details]
735 +
736 +Owner Details:
737 +[owner_details]
738 +
739 +", 'propertyhive' ) . get_bloginfo('name'), '', 'no' );
740 +
741 + // Owner/Landlord Appraisal Booking Confirmation
742 + add_option( 'propertyhive_appraisal_owner_booking_confirmation_email_subject', __( 'Appraisal Booked On [property_address]', 'propertyhive' ), '', 'no' );
743 + add_option( 'propertyhive_appraisal_owner_booking_confirmation_email_body', __( "Dear [owner_dear],
744 +
745 +This is confirmation that an appraisal has been booked for your property, [property_address], for [appraisal_time] on [appraisal_date].
746 +
747 +Should you need to cancel or amend this appraisal, please do not hesitate to contact us.
748 +
749 +", 'propertyhive' ) . get_bloginfo('name'), '', 'no' );
750 +
578 751 }
579 752
580 753 /**
581 754 * Set up the database tables which the plugin needs to function.
@@ -605,12 +778,14 @@
605 778 contact_id bigint(20) unsigned NOT NULL,
606 779 property_ids text NOT NULL,
607 780 applicant_profile_id tinyint(3) unsigned NOT NULL,
608 781 to_email_address varchar(255) NOT NULL,
782 + cc_email_address varchar(255) NOT NULL,
783 + bcc_email_address varchar(255) NOT NULL,
609 784 from_name varchar(255) NOT NULL,
610 785 from_email_address varchar(255) NOT NULL,
611 786 subject varchar(255) NOT NULL,
612 - body longtext NOT NULL,
787 + body blob NOT NULL,
613 788 lock_id varchar(23) NOT NULL,
614 789 locked_at datetime NOT NULL DEFAULT '0000-00-00 00:00:00',
615 790 status varchar(5) NOT NULL,
616 791 send_at datetime NOT NULL DEFAULT '0000-00-00 00:00:00',
@@ -615,8 +790,22 @@
615 790 status varchar(5) NOT NULL,
616 791 send_at datetime NOT NULL DEFAULT '0000-00-00 00:00:00',
617 792 sent_by bigint(20) unsigned NOT NULL,
618 793 PRIMARY KEY (email_id)
794 + ) $collate;";
795 +
796 + $tables .= "
797 + CREATE TABLE {$wpdb->prefix}ph_address_keyword_polygon (
798 + address_keyword varchar(255) NOT NULL,
799 + polygon_coordinates longtext NOT NULL
800 + ) $collate;";
801 +
802 + $tables .= "
803 + CREATE TABLE {$wpdb->prefix}ph_search_log (
804 + id bigint(20) unsigned NOT NULL AUTO_INCREMENT,
805 + searched_at datetime NOT NULL,
806 + PRIMARY KEY (id),
807 + KEY searched_at (searched_at)
619 808 ) $collate;";
620 809
621 810 dbDelta( $tables );
622 811 }