WordPress Online Booking and Scheduling Plugin – Bookly - Version 13.1

Version Description

  • Added support for WordPress 4.8.2
Download this release

Release Info

Developer Ladela
Plugin Icon 128x128 WordPress Online Booking and Scheduling Plugin – Bookly
Version 13.1
Comparing to
See all releases

Code changes from version 13.0 to 13.1

backend/modules/debug/Controller.php CHANGED
@@ -31,48 +31,45 @@ class Controller extends Lib\Base\Controller
31
) );
32
33
$debug = array();
34
- /** @var Lib\Base\Plugin $plugin */
35
- foreach ( apply_filters( 'bookly_plugins', array() ) as $plugin ) {
36
- foreach ( $plugin::getEntityClasses() as $entity_class ) {
37
- $tableName = $entity_class::getTableName();
38
- $debug[ $tableName ] = array(
39
- 'fields' => null,
40
- 'constraints' => null,
41
- 'status' => null,
42
- );
43
- if ( $this->_tableExists( $tableName ) ) {
44
- $tableStructure = $this->_getTableStructure( $tableName );
45
- $tableConstraints = $this->_getTableConstraints( $tableName );
46
- $entitySchema = $entity_class::getSchema();
47
- $entityConstraints = $entity_class::getConstraints();
48
- $debug[ $tableName ]['status'] = self::TABLE_STATUS_OK;
49
- $debug[ $tableName ]['fields'] = array();
50
-
51
- // Comparing model schema with real DB schema
52
- foreach ( $entitySchema as $field => $data ) {
53
- if ( in_array( $field, $tableStructure ) ) {
54
- $debug[ $tableName ]['fields'][ $field ] = 1;
55
- } else {
56
- $debug[ $tableName ]['fields'][ $field ] = 0;
57
- $debug[ $tableName ]['status'] = self::TABLE_STATUS_WARNING;
58
- }
59
}
60
61
- // Comparing model constraints with real DB constraints
62
- foreach ( $entityConstraints as $constraint ) {
63
- $key = $constraint['column_name'] . $constraint['referenced_table_name'] . $constraint['referenced_column_name'];
64
- $debug[ $tableName ]['constraints'][ $key ] = $constraint;
65
- if ( array_key_exists ( $key, $tableConstraints ) ) {
66
- $debug[ $tableName ]['constraints'][ $key ]['status'] = 1;
67
- } else {
68
- $debug[ $tableName ]['constraints'][ $key ]['status'] = 0;
69
- $debug[ $tableName ]['status'] = self::TABLE_STATUS_WARNING;
70
- }
71
}
72
-
73
- } else {
74
- $debug[ $tableName ]['status'] = self::TABLE_STATUS_ERROR;
75
}
76
}
77
}
78
@@ -90,33 +87,30 @@ class Controller extends Lib\Base\Controller
90
91
$result = array();
92
93
- foreach ( apply_filters( 'bookly_plugins', array() ) as $plugin ) {
94
- /** @var Lib\Base\Plugin $plugin */
95
- $installer_class = $plugin::getRootNamespace() . '\Lib\Installer';
96
- /** @var Lib\Base\Installer $installer */
97
- $installer = new $installer_class();
98
-
99
- foreach ( $plugin::getEntityClasses() as $entity_class ) {
100
- $table_name = $entity_class::getTableName();
101
- $result['entities'][ $entity_class ] = array(
102
- 'fields' => $this->_getTableStructure( $table_name ),
103
- 'values' => $wpdb->get_results( 'SELECT * FROM ' . $table_name, ARRAY_N )
104
- );
105
- }
106
- $plugin_prefix = $plugin::getPrefix();
107
- $options_postfix = array( 'data_loaded', 'grace_start', 'db_version', 'installation_time' );
108
- if ( $plugin_prefix != 'bookly_' ) {
109
- $options_postfix[] = 'enabled';
110
- }
111
- foreach ( $options_postfix as $option ) {
112
- $option_name = $plugin_prefix . $option;
113
- $result['options'][ $option_name ] = get_option( $option_name );
114
- }
115
116
- $result['options'][ $plugin::getPurchaseCodeOption() ] = $plugin::getPurchaseCode();
117
- foreach ( $installer->getOptions() as $option_name => $option_value ) {
118
- $result['options'][ $option_name ] = get_option( $option_name );
119
- }
120
}
121
122
header( 'Content-type: application/json' );
@@ -136,77 +130,74 @@ class Controller extends Lib\Base\Controller
136
137
if ( $file = $_FILES['import']['name'] ) {
138
$json = file_get_contents( $_FILES['import']['tmp_name'] );
139
- if ( $json !== false) {
140
$wpdb->query( 'SET FOREIGN_KEY_CHECKS = 0' );
141
142
$data = json_decode( $json, true );
143
144
- foreach ( apply_filters( 'bookly_plugins', array() ) as $plugin ) {
145
- /** @var Lib\Base\Plugin $plugin */
146
- $installer_class = $plugin::getRootNamespace() . '\Lib\Installer';
147
- /** @var Lib\Base\Installer $installer */
148
- $installer = new $installer_class();
149
-
150
- // Drop all data and options.
151
- $installer->removeData();
152
- $installer->dropTables();
153
- $installer->createTables();
154
-
155
- // Insert tables data.
156
- foreach ( $plugin::getEntityClasses() as $entity_class ) {
157
- if ( isset ( $data['entities'][ $entity_class ]['values'][0] ) ) {
158
- $table_name = $entity_class::getTableName();
159
- $query = sprintf(
160
- 'INSERT INTO `%s` (`%s`) VALUES (%%s)',
161
- $table_name,
162
- implode( '`,`', $data['entities'][ $entity_class ]['fields'] )
163
- );
164
- $placeholders = array();
165
- $values = array();
166
- $counter = 0;
167
- foreach ( $data['entities'][ $entity_class ]['values'] as $row ) {
168
- $params = array();
169
- foreach ( $row as $value ) {
170
- if ( $value === null ) {
171
- $params[] = 'NULL';
172
- } else {
173
- $params[] = '%s';
174
- $values[] = $value;
175
- }
176
- }
177
- $placeholders[] = implode( ',', $params );
178
- if ( ++ $counter > 50 ) {
179
- // Flush.
180
- $wpdb->query( $wpdb->prepare( sprintf( $query, implode( '),(', $placeholders ) ), $values ) );
181
- $placeholders = array();
182
- $values = array();
183
- $counter = 0;
184
}
185
}
186
- if ( ! empty ( $placeholders ) ) {
187
$wpdb->query( $wpdb->prepare( sprintf( $query, implode( '),(', $placeholders ) ), $values ) );
188
}
189
}
190
}
191
192
- // Insert options data.
193
- foreach ( $installer->getOptions() as $option_name => $option_value ) {
194
- add_option( $option_name, $data['options'][ $option_name ] );
195
- }
196
-
197
- $plugin_prefix = $plugin::getPrefix();
198
- $options_postfix = array( 'data_loaded', 'grace_start', 'db_version' );
199
- if ( $plugin_prefix != 'bookly_' ) {
200
- $options_postfix[] = 'enabled';
201
- }
202
- foreach ( $options_postfix as $option ) {
203
- $option_name = $plugin_prefix . $option;
204
- add_option( $option_name, $data['options'][ $option_name ] );
205
- }
206
}
207
208
- header( 'Location: ' . admin_url( 'admin.php?page=bookly-debug&status=imported' ) );
209
}
210
}
211
212
header( 'Location: ' . admin_url( 'admin.php?page=bookly-debug' ) );
31
) );
32
33
$debug = array();
34
+ foreach ( Lib\Plugin::getEntityClasses() as $entity_class ) {
35
+ $tableName = $entity_class::getTableName();
36
+ $debug[ $tableName ] = array(
37
+ 'fields' => null,
38
+ 'constraints' => null,
39
+ 'status' => null,
40
+ );
41
+ if ( $this->_tableExists( $tableName ) ) {
42
+ $tableStructure = $this->_getTableStructure( $tableName );
43
+ $tableConstraints = $this->_getTableConstraints( $tableName );
44
+ $entitySchema = $entity_class::getSchema();
45
+ $entityConstraints = $entity_class::getConstraints();
46
+ $debug[ $tableName ]['status'] = self::TABLE_STATUS_OK;
47
+ $debug[ $tableName ]['fields'] = array();
48
+
49
+ // Comparing model schema with real DB schema
50
+ foreach ( $entitySchema as $field => $data ) {
51
+ if ( in_array( $field, $tableStructure ) ) {
52
+ $debug[ $tableName ]['fields'][ $field ] = 1;
53
+ } else {
54
+ $debug[ $tableName ]['fields'][ $field ] = 0;
55
+ $debug[ $tableName ]['status'] = self::TABLE_STATUS_WARNING;
56
}
57
+ }
58
59
+ // Comparing model constraints with real DB constraints
60
+ foreach ( $entityConstraints as $constraint ) {
61
+ $key = $constraint['column_name'] . $constraint['referenced_table_name'] . $constraint['referenced_column_name'];
62
+ $debug[ $tableName ]['constraints'][ $key ] = $constraint;
63
+ if ( array_key_exists ( $key, $tableConstraints ) ) {
64
+ $debug[ $tableName ]['constraints'][ $key ]['status'] = 1;
65
+ } else {
66
+ $debug[ $tableName ]['constraints'][ $key ]['status'] = 0;
67
+ $debug[ $tableName ]['status'] = self::TABLE_STATUS_WARNING;
68
}
69
}
70
+
71
+ } else {
72
+ $debug[ $tableName ]['status'] = self::TABLE_STATUS_ERROR;
73
}
74
}
75
87
88
$result = array();
89
90
+ $installer_class = Lib\Plugin::getRootNamespace() . '\Lib\Installer';
91
+ /** @var Lib\Base\Installer $installer */
92
+ $installer = new $installer_class();
93
94
+ foreach ( Lib\Plugin::getEntityClasses() as $entity_class ) {
95
+ $table_name = $entity_class::getTableName();
96
+ $result['entities'][ $entity_class ] = array(
97
+ 'fields' => $this->_getTableStructure( $table_name ),
98
+ 'values' => $wpdb->get_results( 'SELECT * FROM ' . $table_name, ARRAY_N )
99
+ );
100
+ }
101
+ $plugin_prefix = Lib\Plugin::getPrefix();
102
+ $options_postfix = array( 'data_loaded', 'grace_start', 'db_version', 'installation_time' );
103
+ if ( $plugin_prefix != 'bookly_' ) {
104
+ $options_postfix[] = 'enabled';
105
+ }
106
+ foreach ( $options_postfix as $option ) {
107
+ $option_name = $plugin_prefix . $option;
108
+ $result['options'][ $option_name ] = get_option( $option_name );
109
+ }
110
+
111
+ $result['options'][ Lib\Plugin::getPurchaseCodeOption() ] = Lib\Plugin::getPurchaseCode();
112
+ foreach ( $installer->getOptions() as $option_name => $option_value ) {
113
+ $result['options'][ $option_name ] = get_option( $option_name );
114
}
115
116
header( 'Content-type: application/json' );
130
131
if ( $file = $_FILES['import']['name'] ) {
132
$json = file_get_contents( $_FILES['import']['tmp_name'] );
133
+ if ( $json !== false ) {
134
$wpdb->query( 'SET FOREIGN_KEY_CHECKS = 0' );
135
136
$data = json_decode( $json, true );
137
138
+ $installer_class = Lib\Plugin::getRootNamespace() . '\Lib\Installer';
139
+ /** @var Lib\Base\Installer $installer */
140
+ $installer = new $installer_class();
141
+
142
+ // Drop all data and options.
143
+ $installer->removeData();
144
+ $installer->dropTables();
145
+ $installer->createTables();
146
+
147
+ // Insert tables data.
148
+ foreach ( Lib\Plugin::getEntityClasses() as $entity_class ) {
149
+ if ( isset ( $data['entities'][ $entity_class ]['values'][0] ) ) {
150
+ $table_name = $entity_class::getTableName();
151
+ $query = sprintf(
152
+ 'INSERT INTO `%s` (`%s`) VALUES (%%s)',
153
+ $table_name,
154
+ implode( '`,`', $data['entities'][ $entity_class ]['fields'] )
155
+ );
156
+ $placeholders = array();
157
+ $values = array();
158
+ $counter = 0;
159
+ foreach ( $data['entities'][ $entity_class ]['values'] as $row ) {
160
+ $params = array();
161
+ foreach ( $row as $value ) {
162
+ if ( $value === null ) {
163
+ $params[] = 'NULL';
164
+ } else {
165
+ $params[] = '%s';
166
+ $values[] = $value;
167
}
168
}
169
+ $placeholders[] = implode( ',', $params );
170
+ if ( ++ $counter > 50 ) {
171
+ // Flush.
172
$wpdb->query( $wpdb->prepare( sprintf( $query, implode( '),(', $placeholders ) ), $values ) );
173
+ $placeholders = array();
174
+ $values = array();
175
+ $counter = 0;
176
}
177
}
178
+ if ( ! empty ( $placeholders ) ) {
179
+ $wpdb->query( $wpdb->prepare( sprintf( $query, implode( '),(', $placeholders ) ), $values ) );
180
+ }
181
}
182
+ }
183
184
+ // Insert options data.
185
+ foreach ( $installer->getOptions() as $option_name => $option_value ) {
186
+ add_option( $option_name, $data['options'][ $option_name ] );
187
}
188
189
+ $plugin_prefix = Lib\Plugin::getPrefix();
190
+ $options_postfix = array( 'data_loaded', 'grace_start', 'db_version' );
191
+ if ( $plugin_prefix != 'bookly_' ) {
192
+ $options_postfix[] = 'enabled';
193
+ }
194
+ foreach ( $options_postfix as $option ) {
195
+ $option_name = $plugin_prefix . $option;
196
+ add_option( $option_name, $data['options'][ $option_name ] );
197
+ }
198
}
199
+
200
+ header( 'Location: ' . admin_url( 'admin.php?page=bookly-debug&status=imported' ) );
201
}
202
203
header( 'Location: ' . admin_url( 'admin.php?page=bookly-debug' ) );
backend/modules/support/Controller.php CHANGED
@@ -29,8 +29,7 @@ class Controller extends Lib\Base\Controller
29
) );
30
}
31
32
- $plugins = apply_filters( 'bookly_plugins', array() );
33
- $message = $this->render( '_email_to_support', compact( 'name', 'email', 'msg', 'plugins' ), false );
34
$headers = array(
35
'Content-Type: text/html; charset=utf-8',
36
'From: ' . get_option( 'bookly_email_sender_name' ) . ' <' . get_option( 'bookly_email_sender' ) . '>',
29
) );
30
}
31
32
+ $message = $this->render( '_email_to_support', compact( 'name', 'email', 'msg' ), false );
33
$headers = array(
34
'Content-Type: text/html; charset=utf-8',
35
'From: ' . get_option( 'bookly_email_sender_name' ) . ' <' . get_option( 'bookly_email_sender' ) . '>',
lib/NotificationCodes.php CHANGED
@@ -42,7 +42,7 @@ class NotificationCodes
42
'total_price' => '',
43
// Extras
44
'extras' => '',
45
- 'extras_total_price' => '',
46
// Recurring Appointments
47
'appointment_schedule' => '',
48
'appointment_schedule_c' => '',
42
'total_price' => '',
43
// Extras
44
'extras' => '',
45
+ 'extras_total_price' => 0,
46
// Recurring Appointments
47
'appointment_schedule' => '',
48
'appointment_schedule_c' => '',
lib/Updater.php CHANGED
@@ -25,9 +25,6 @@ class Updater extends Base\Updater
25
add_option( 'bookly_api_server_error_time', '0' );
26
add_option( 'bookly_grace_notifications', array ( 'bookly' => '0', 'add-ons' => '0', 'sent' => '0' ) );
27
add_option( 'bookly_grace_hide_admin_notice_time', '0' );
28
- foreach ( apply_filters( 'bookly_plugins', array() ) as $plugin_class ) {
29
- add_option( $plugin_class::getPrefix() . 'grace_start', time() + 2 * WEEK_IN_SECONDS );
30
- }
31
32
$options = array(
33
'bookly_email_content_type' => 'bookly_email_send_as',
25
add_option( 'bookly_api_server_error_time', '0' );
26
add_option( 'bookly_grace_notifications', array ( 'bookly' => '0', 'add-ons' => '0', 'sent' => '0' ) );
27
add_option( 'bookly_grace_hide_admin_notice_time', '0' );
28
29
$options = array(
30
'bookly_email_content_type' => 'bookly_email_send_as',
lib/base/Plugin.php CHANGED
@@ -398,13 +398,6 @@ abstract class Plugin
398
load_plugin_textdomain( $plugin_class::getTextDomain(), false, $plugin_class::getSlug() . '/languages' );
399
} );
400
401
- // Add handlers to Bookly filters.
402
- add_filter( 'bookly_plugins', function ( array $plugins ) use ( $plugin_class ) {
403
- $plugins[ $plugin_class::getSlug() ] = $plugin_class;
404
-
405
- return $plugins;
406
- } );
407
-
408
// For admin notices about SMS weekly summary and etc.
409
if ( ! wp_next_scheduled( 'bookly_daily_routine' ) ) {
410
wp_schedule_event( time(), 'daily', 'bookly_daily_routine' );
398
load_plugin_textdomain( $plugin_class::getTextDomain(), false, $plugin_class::getSlug() . '/languages' );
399
} );
400
401
// For admin notices about SMS weekly summary and etc.
402
if ( ! wp_next_scheduled( 'bookly_daily_routine' ) ) {
403
wp_schedule_event( time(), 'daily', 'bookly_daily_routine' );
lib/entities/Payment.php CHANGED
@@ -29,8 +29,8 @@ class Payment extends Lib\Base\Entity
29
'id' => array( 'format' => '%d' ),
30
'created' => array( 'format' => '%s' ),
31
'type' => array( 'format' => '%s' ),
32
- 'total' => array( 'format' => '%.2f' ),
33
- 'paid' => array( 'format' => '%.2f' ),
34
'status' => array( 'format' => '%s', 'default' => self::STATUS_COMPLETED ),
35
'details' => array( 'format' => '%s' ),
36
);
29
'id' => array( 'format' => '%d' ),
30
'created' => array( 'format' => '%s' ),
31
'type' => array( 'format' => '%s' ),
32
+ 'total' => array( 'format' => '%f' ),
33
+ 'paid' => array( 'format' => '%f' ),
34
'status' => array( 'format' => '%s', 'default' => self::STATUS_COMPLETED ),
35
'details' => array( 'format' => '%s' ),
36
);
lib/entities/Service.php CHANGED
@@ -19,7 +19,7 @@ class Service extends Lib\Base\Entity
19
'category_id' => array( 'format' => '%d', 'reference' => array( 'entity' => 'Category' ) ),
20
'title' => array( 'format' => '%s' ),
21
'duration' => array( 'format' => '%d', 'default' => 900 ),
22
- 'price' => array( 'format' => '%.2f', 'default' => '0' ),
23
'color' => array( 'format' => '%s' ),
24
'capacity' => array( 'format' => '%d', 'default' => '1' ),
25
'padding_left' => array( 'format' => '%d', 'default' => '0' ),
19
'category_id' => array( 'format' => '%d', 'reference' => array( 'entity' => 'Category' ) ),
20
'title' => array( 'format' => '%s' ),
21
'duration' => array( 'format' => '%d', 'default' => 900 ),
22
+ 'price' => array( 'format' => '%f', 'default' => '0' ),
23
'color' => array( 'format' => '%s' ),
24
'capacity' => array( 'format' => '%d', 'default' => '1' ),
25
'padding_left' => array( 'format' => '%d', 'default' => '0' ),
lib/entities/StaffService.php CHANGED
@@ -15,7 +15,7 @@ class StaffService extends Lib\Base\Entity
15
'id' => array( 'format' => '%d' ),
16
'staff_id' => array( 'format' => '%d', 'reference' => array( 'entity' => 'Staff' ) ),
17
'service_id' => array( 'format' => '%d', 'reference' => array( 'entity' => 'Service' ) ),
18
- 'price' => array( 'format' => '%.2f', 'default' => '0' ),
19
'capacity' => array( 'format' => '%d', 'default' => '1' ),
20
'deposit' => array( 'format' => '%s', 'default' => '100%' ),
21
);
15
'id' => array( 'format' => '%d' ),
16
'staff_id' => array( 'format' => '%d', 'reference' => array( 'entity' => 'Staff' ) ),
17
'service_id' => array( 'format' => '%d', 'reference' => array( 'entity' => 'Service' ) ),
18
+ 'price' => array( 'format' => '%f', 'default' => '0' ),
19
'capacity' => array( 'format' => '%d', 'default' => '1' ),
20
'deposit' => array( 'format' => '%s', 'default' => '100%' ),
21
);
lib/utils/DateTime.php CHANGED
@@ -243,6 +243,8 @@ class DateTime
243
*/
244
public static function secondsToInterval( $duration )
245
{
246
$weeks = (int) ( $duration / WEEK_IN_SECONDS );
247
$days = (int) ( ( $duration % WEEK_IN_SECONDS ) / DAY_IN_SECONDS );
248
$hours = (int) ( ( $duration % DAY_IN_SECONDS ) / HOUR_IN_SECONDS );
243
*/
244
public static function secondsToInterval( $duration )
245
{
246
+ $duration = (int) $duration;
247
+
248
$weeks = (int) ( $duration / WEEK_IN_SECONDS );
249
$days = (int) ( ( $duration % WEEK_IN_SECONDS ) / DAY_IN_SECONDS );
250
$hours = (int) ( ( $duration % DAY_IN_SECONDS ) / HOUR_IN_SECONDS );
main.php CHANGED
@@ -3,7 +3,7 @@
3
Plugin Name: Bookly Lite
4
Plugin URI: http://booking-wp-plugin.com
5
Description: Bookly Plugin – is a great easy-to-use and easy-to-manage booking tool for service providers who think about their customers. The plugin supports a wide range of services provided by business and individuals who offer reservations through websites. Set up any reservation quickly, pleasantly and easily with Bookly!
6
- Version: 13.0
7
Author: Ladela Interactive
8
Author URI: http://booking-wp-plugin.com
9
Text Domain: bookly
3
Plugin Name: Bookly Lite
4
Plugin URI: http://booking-wp-plugin.com
5
Description: Bookly Plugin – is a great easy-to-use and easy-to-manage booking tool for service providers who think about their customers. The plugin supports a wide range of services provided by business and individuals who offer reservations through websites. Set up any reservation quickly, pleasantly and easily with Bookly!
6
+ Version: 13.1
7
Author: Ladela Interactive
8
Author URI: http://booking-wp-plugin.com
9
Text Domain: bookly
readme.txt CHANGED
@@ -3,9 +3,9 @@ Contributors: Ladela
3
Tags: 2checkout, appointment plugin, authorize.net, booking plugin, calendar, cart, google calendar, paypal, payson, reservation, responsive, stripe, woocommerce, wordpress, wpm
4
Donate link: http://booking-wp-plugin.com/
5
Requires at least: 3.7
6
- Tested up to: 4.7.5
7
Requires PHP: 5.3.7
8
- Stable tag: 13.0
9
License: GPLv3
10
License URI: http://www.gnu.org/licenses/gpl-3.0.html
11
@@ -205,6 +205,9 @@ Upon the completion of these steps, customers can book appointments. In the Cale
205
206
== Changelog ==
207
208
= 13.0 =
209
* Added support for <a href="https://codecanyon.net/item/bookly-recurring-appointments-addon/19497634?ref=ladela">Recurring Appointments (Add-on)</a>
210
* Added new status Rejected for appointments
3
Tags: 2checkout, appointment plugin, authorize.net, booking plugin, calendar, cart, google calendar, paypal, payson, reservation, responsive, stripe, woocommerce, wordpress, wpm
4
Donate link: http://booking-wp-plugin.com/
5
Requires at least: 3.7
6
+ Tested up to: 4.8.2
7
Requires PHP: 5.3.7
8
+ Stable tag: 13.1
9
License: GPLv3
10
License URI: http://www.gnu.org/licenses/gpl-3.0.html
11
205
206
== Changelog ==
207
208
+ = 13.1 =
209
+ * Added support for WordPress 4.8.2
210
+
211
= 13.0 =
212
* Added support for <a href="https://codecanyon.net/item/bookly-recurring-appointments-addon/19497634?ref=ladela">Recurring Appointments (Add-on)</a>
213
* Added new status Rejected for appointments