run:R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:52
R W Run
DIR
2026-03-11 16:18:51
R W Run
DIR
2026-03-11 16:18:51
R W Run
23.8 KB
2026-03-11 16:18:51
R W Run
7.8 KB
2026-03-11 16:18:52
R W Run
36.1 KB
2026-03-11 16:18:51
R W Run
11.9 KB
2026-03-11 16:18:52
R W Run
18.94 KB
2026-03-11 16:18:52
R W Run
7.35 KB
2026-03-11 16:18:52
R W Run
28.6 KB
2026-03-11 16:18:51
R W Run
316 By
2026-03-11 16:18:51
R W Run
12.9 KB
2026-03-11 16:18:51
R W Run
61.02 KB
2026-03-11 16:18:52
R W Run
15 KB
2026-03-11 16:18:51
R W Run
112.05 KB
2026-03-11 16:18:51
R W Run
12.47 KB
2026-03-11 16:18:51
R W Run
15.07 KB
2026-03-11 16:18:52
R W Run
9.84 KB
2026-03-11 16:18:52
R W Run
13.17 KB
2026-03-11 16:18:52
R W Run
33.83 KB
2026-03-11 16:18:51
R W Run
42.63 KB
2026-03-11 16:18:51
R W Run
55.71 KB
2026-03-11 16:18:52
R W Run
12.53 KB
2026-03-11 16:18:51
R W Run
2.55 KB
2026-03-11 16:18:52
R W Run
28.92 KB
2026-03-11 16:18:52
R W Run
539 By
2026-03-11 16:18:51
R W Run
367 By
2026-03-11 16:18:52
R W Run
42.65 KB
2026-03-11 16:18:51
R W Run
401 By
2026-03-11 16:18:51
R W Run
6.61 KB
2026-03-11 16:18:51
R W Run
664 By
2026-03-11 16:18:52
R W Run
20.63 KB
2026-03-11 16:18:51
R W Run
2.18 KB
2026-03-11 16:18:52
R W Run
453 By
2026-03-11 16:18:52
R W Run
457 By
2026-03-11 16:18:51
R W Run
36.83 KB
2026-03-11 16:18:52
R W Run
2.41 KB
2026-03-11 16:18:52
R W Run
8.28 KB
2026-03-11 16:18:51
R W Run
13.89 KB
2026-03-11 16:18:51
R W Run
11.76 KB
2026-03-11 16:18:51
R W Run
2.65 KB
2026-03-11 16:18:51
R W Run
7.43 KB
2026-03-11 16:18:51
R W Run
17.46 KB
2026-03-11 16:18:51
R W Run
5.14 KB
2026-03-11 16:18:52
R W Run
16.7 KB
2026-03-11 16:18:51
R W Run
8.28 KB
2026-03-11 16:18:52
R W Run
2.92 KB
2026-03-11 16:18:52
R W Run
1.32 KB
2026-03-11 16:18:51
R W Run
4.6 KB
2026-03-11 16:18:52
R W Run
11.62 KB
2026-03-11 16:18:52
R W Run
2.5 KB
2026-03-11 16:18:51
R W Run
1.97 KB
2026-03-11 16:18:51
R W Run
11.25 KB
2026-03-11 16:18:52
R W Run
5.32 KB
2026-03-11 16:18:51
R W Run
10.99 KB
2026-03-11 16:18:52
R W Run
68.32 KB
2026-03-11 16:18:51
R W Run
6.34 KB
2026-03-11 16:18:51
R W Run
5.49 KB
2026-03-11 16:18:51
R W Run
1.99 KB
2026-03-11 16:18:52
R W Run
7.02 KB
2026-03-11 16:18:51
R W Run
4.91 KB
2026-03-11 16:18:52
R W Run
16.86 KB
2026-03-11 16:18:51
R W Run
24.23 KB
2026-03-11 16:18:51
R W Run
3.97 KB
2026-03-11 16:18:51
R W Run
47.66 KB
2026-03-11 16:18:51
R W Run
9.22 KB
2026-03-11 16:18:51
R W Run
25.51 KB
2026-03-11 16:18:51
R W Run
198.38 KB
2026-03-11 16:18:52
R W Run
56.65 KB
2026-03-11 16:18:51
R W Run
10.46 KB
2026-03-11 16:18:51
R W Run
10.95 KB
2026-03-11 16:18:52
R W Run
29.26 KB
2026-03-11 16:18:51
R W Run
70.91 KB
2026-03-11 16:18:52
R W Run
35.3 KB
2026-03-11 16:18:52
R W Run
16.61 KB
2026-03-11 16:18:52
R W Run
2.57 KB
2026-03-11 16:18:52
R W Run
39.83 KB
2026-03-11 16:18:51
R W Run
70.64 KB
2026-03-11 16:18:51
R W Run
15.56 KB
2026-03-11 16:18:52
R W Run
7.33 KB
2026-03-11 16:18:52
R W Run
253 By
2026-03-11 16:18:51
R W Run
7.96 KB
2026-03-11 16:18:52
R W Run
3.23 KB
2026-03-11 16:18:52
R W Run
969 By
2026-03-11 16:18:52
R W Run
16.28 KB
2026-03-11 16:18:51
R W Run
7.22 KB
2026-03-11 16:18:51
R W Run
12.95 KB
2026-03-11 16:18:51
R W Run
6.53 KB
2026-03-11 16:18:51
R W Run
3.42 KB
2026-03-11 16:18:52
R W Run
5.84 KB
2026-03-11 16:18:51
R W Run
1.97 KB
2026-03-11 16:18:51
R W Run
4.3 KB
2026-03-11 16:18:52
R W Run
2.91 KB
2026-03-11 16:18:51
R W Run
16.46 KB
2026-03-11 16:18:52
R W Run
40.6 KB
2026-03-11 16:18:51
R W Run
20.22 KB
2026-03-11 16:18:51
R W Run
36.11 KB
2026-03-11 16:18:52
R W Run
17.01 KB
2026-03-11 16:18:51
R W Run
7.27 KB
2026-03-11 16:18:52
R W Run
6.62 KB
2026-03-11 16:18:52
R W Run
16.49 KB
2026-03-11 16:18:52
R W Run
1.79 KB
2026-03-11 16:18:52
R W Run
29.82 KB
2026-03-11 16:18:51
R W Run
6.67 KB
2026-03-11 16:18:52
R W Run
8.98 KB
2026-03-11 16:18:52
R W Run
19.42 KB
2026-03-11 16:18:51
R W Run
12.01 KB
2026-03-11 16:18:51
R W Run
17.11 KB
2026-03-11 16:18:51
R W Run
6.74 KB
2026-03-11 16:18:52
R W Run
30.93 KB
2026-03-11 16:18:51
R W Run
4.99 KB
2026-03-11 16:18:51
R W Run
4.25 KB
2026-03-11 16:18:51
R W Run
24.72 KB
2026-03-11 16:18:51
R W Run
29.96 KB
2026-03-11 16:18:52
R W Run
6.41 KB
2026-03-11 16:18:51
R W Run
160 KB
2026-03-11 16:18:51
R W Run
6.72 KB
2026-03-11 16:18:52
R W Run
10.92 KB
2026-03-11 16:18:51
R W Run
4.77 KB
2026-03-11 16:18:51
R W Run
3.38 KB
2026-03-11 16:18:51
R W Run
11.18 KB
2026-03-11 16:18:51
R W Run
62.19 KB
2026-03-11 16:18:51
R W Run
2.46 KB
2026-03-11 16:18:51
R W Run
9.17 KB
2026-03-11 16:18:51
R W Run
32.15 KB
2026-03-11 16:18:51
R W Run
34.05 KB
2026-03-11 16:18:52
R W Run
7.15 KB
2026-03-11 16:18:51
R W Run
3.47 KB
2026-03-11 16:18:52
R W Run
1.87 KB
2026-03-11 16:18:52
R W Run
30.91 KB
2026-03-11 16:18:51
R W Run
7.29 KB
2026-03-11 16:18:52
R W Run
7.35 KB
2026-03-11 16:18:51
R W Run
12.54 KB
2026-03-11 16:18:51
R W Run
19.12 KB
2026-03-11 16:18:51
R W Run
18.12 KB
2026-03-11 16:18:52
R W Run
39.99 KB
2026-03-11 16:18:52
R W Run
5.17 KB
2026-03-11 16:18:52
R W Run
979 By
2026-03-11 16:18:51
R W Run
18.44 KB
2026-03-11 16:18:52
R W Run
10.24 KB
2026-03-11 16:18:51
R W Run
1.77 KB
2026-03-11 16:18:52
R W Run
34.9 KB
2026-03-11 16:18:51
R W Run
7.19 KB
2026-03-11 16:18:52
R W Run
160.5 KB
2026-03-11 16:18:51
R W Run
64.27 KB
2026-03-11 16:18:51
R W Run
27.95 KB
2026-03-11 16:18:51
R W Run
4.69 KB
2026-03-11 16:18:51
R W Run
2.94 KB
2026-03-11 16:18:51
R W Run
43.13 KB
2026-03-11 16:18:52
R W Run
2.25 KB
2026-03-11 16:18:52
R W Run
22.5 KB
2026-03-11 16:18:51
R W Run
13.01 KB
2026-03-11 16:18:52
R W Run
3.27 KB
2026-03-11 16:18:51
R W Run
18 KB
2026-03-11 16:18:51
R W Run
210.4 KB
2026-03-11 16:18:52
R W Run
25.86 KB
2026-03-11 16:18:52
R W Run
115.85 KB
2026-03-11 16:18:51
R W Run
373 By
2026-03-11 16:18:52
R W Run
343 By
2026-03-11 16:18:52
R W Run
338 By
2026-03-11 16:18:51
R W Run
100.73 KB
2026-03-11 16:18:52
R W Run
130.93 KB
2026-03-11 16:18:51
R W Run
19.1 KB
2026-03-11 16:18:51
R W Run
17.41 KB
2026-03-11 16:18:52
R W Run
41.98 KB
2026-03-11 16:18:52
R W Run
400 By
2026-03-11 16:18:52
R W Run
11.1 KB
2026-03-11 16:18:52
R W Run
37.02 KB
2026-03-11 16:18:51
R W Run
2.24 KB
2026-03-11 16:18:51
R W Run
188.13 KB
2026-03-11 16:18:51
R W Run
338 By
2026-03-11 16:18:51
R W Run
38 KB
2026-03-11 16:18:51
R W Run
4.02 KB
2026-03-11 16:18:52
R W Run
5.38 KB
2026-03-11 16:18:51
R W Run
3.05 KB
2026-03-11 16:18:52
R W Run
2.61 KB
2026-03-11 16:18:51
R W Run
1.16 KB
2026-03-11 16:18:52
R W Run
4.04 KB
2026-03-11 16:18:51
R W Run
3.71 KB
2026-03-11 16:18:51
R W Run
24.6 KB
2026-03-11 16:18:51
R W Run
9.56 KB
2026-03-11 16:18:51
R W Run
346.43 KB
2026-03-11 16:18:52
R W Run
281.84 KB
2026-03-11 16:18:52
R W Run
14.95 KB
2026-03-11 16:18:51
R W Run
8.44 KB
2026-03-11 16:18:52
R W Run
168.95 KB
2026-03-11 16:18:52
R W Run
20.71 KB
2026-03-11 16:18:52
R W Run
25.27 KB
2026-03-11 16:18:51
R W Run
5.72 KB
2026-03-11 16:18:51
R W Run
4.63 KB
2026-03-11 16:18:52
R W Run
81.73 KB
2026-03-11 16:18:51
R W Run
67.18 KB
2026-03-11 16:18:51
R W Run
156.36 KB
2026-03-11 16:18:52
R W Run
55.19 KB
2026-03-11 16:18:51
R W Run
162 By
2026-03-11 16:18:51
R W Run
61.72 KB
2026-03-11 16:18:51
R W Run
216.06 KB
2026-03-11 16:18:52
R W Run
65.09 KB
2026-03-11 16:18:51
R W Run
25.24 KB
2026-03-11 16:18:52
R W Run
4.81 KB
2026-03-11 16:18:51
R W Run
6.48 KB
2026-03-11 16:18:52
R W Run
21.25 KB
2026-03-11 16:18:51
R W Run
2.79 KB
2026-03-11 16:18:52
R W Run
89.69 KB
2026-03-11 16:18:52
R W Run
19.42 KB
2026-03-11 16:18:52
R W Run
3.69 KB
2026-03-11 16:18:52
R W Run
4.11 KB
2026-03-11 16:18:51
R W Run
40.74 KB
2026-03-11 16:18:51
R W Run
25.38 KB
2026-03-11 16:18:51
R W Run
43.31 KB
2026-03-11 16:18:52
R W Run
102.57 KB
2026-03-11 16:18:52
R W Run
6.18 KB
2026-03-11 16:18:51
R W Run
124.47 KB
2026-03-11 16:18:52
R W Run
35.65 KB
2026-03-11 16:18:52
R W Run
6.94 KB
2026-03-11 16:18:52
R W Run
67.04 KB
2026-03-11 16:18:52
R W Run
10.62 KB
2026-03-11 16:18:51
R W Run
289.35 KB
2026-03-11 16:18:52
R W Run
36.23 KB
2026-03-11 16:18:51
R W Run
200 By
2026-03-11 16:18:52
R W Run
200 By
2026-03-11 16:18:52
R W Run
98.29 KB
2026-03-11 16:18:52
R W Run
30.02 KB
2026-03-11 16:18:52
R W Run
19.03 KB
2026-03-11 16:18:52
R W Run
5.06 KB
2026-03-11 16:18:52
R W Run
255 By
2026-03-11 16:18:51
R W Run
22.66 KB
2026-03-11 16:18:52
R W Run
154.63 KB
2026-03-11 16:18:51
R W Run
9.68 KB
2026-03-11 16:18:51
R W Run
258 By
2026-03-11 16:18:51
R W Run
23.49 KB
2026-03-11 16:18:51
R W Run
3.16 KB
2026-03-11 16:18:51
R W Run
8.4 KB
2026-03-11 16:18:52
R W Run
441 By
2026-03-11 16:18:51
R W Run
7.39 KB
2026-03-11 16:18:51
R W Run
173 KB
2026-03-11 16:18:52
R W Run
544 By
2026-03-11 16:18:52
R W Run
4.17 KB
2026-03-11 16:18:51
R W Run
35.97 KB
2026-03-11 16:18:52
R W Run
1.69 KB
2026-03-11 16:18:51
R W Run
2.84 KB
2026-03-11 16:18:52
R W Run
6.09 KB
2026-03-11 16:18:51
R W Run
8.71 KB
2026-03-11 16:18:51
R W Run
131.84 KB
2026-03-11 16:18:51
R W Run
37.45 KB
2026-03-11 16:18:51
R W Run
173.89 KB
2026-03-11 16:18:51
R W Run
7.09 KB
2026-03-11 16:18:51
R W Run
6.41 KB
2026-03-11 16:18:51
R W Run
1.08 KB
2026-03-11 16:18:51
R W Run
69.46 KB
2026-03-11 16:18:52
R W Run
445 By
2026-03-11 16:18:51
R W Run
799 By
2026-03-11 16:18:52
R W Run
error_log
📄ms-site.php
1<?php
2/**
3 * Site API
4 *
5 * @package WordPress
6 * @subpackage Multisite
7 * @since 5.1.0
8 */
9
10/**
11 * Inserts a new site into the database.
12 *
13 * @since 5.1.0
14 *
15 * @global wpdb $wpdb WordPress database abstraction object.
16 *
17 * @param array $data {
18 * Data for the new site that should be inserted.
19 *
20 * @type string $domain Site domain. Default empty string.
21 * @type string $path Site path. Default '/'.
22 * @type int $network_id The site's network ID. Default is the current network ID.
23 * @type string $registered When the site was registered, in SQL datetime format. Default is
24 * the current time.
25 * @type string $last_updated When the site was last updated, in SQL datetime format. Default is
26 * the value of $registered.
27 * @type int $public Whether the site is public. Default 1.
28 * @type int $archived Whether the site is archived. Default 0.
29 * @type int $mature Whether the site is mature. Default 0.
30 * @type int $spam Whether the site is spam. Default 0.
31 * @type int $deleted Whether the site is deleted. Default 0.
32 * @type int $lang_id The site's language ID. Currently unused. Default 0.
33 * @type int $user_id User ID for the site administrator. Passed to the
34 * `wp_initialize_site` hook.
35 * @type string $title Site title. Default is 'Site %d' where %d is the site ID. Passed
36 * to the `wp_initialize_site` hook.
37 * @type array $options Custom option $key => $value pairs to use. Default empty array. Passed
38 * to the `wp_initialize_site` hook.
39 * @type array $meta Custom site metadata $key => $value pairs to use. Default empty array.
40 * Passed to the `wp_initialize_site` hook.
41 * }
42 * @return int|WP_Error The new site's ID on success, or error object on failure.
43 */
44function wp_insert_site( array $data ) {
45 global $wpdb;
46
47 $now = current_time( 'mysql', true );
48
49 $defaults = array(
50 'domain' => '',
51 'path' => '/',
52 'network_id' => get_current_network_id(),
53 'registered' => $now,
54 'last_updated' => $now,
55 'public' => 1,
56 'archived' => 0,
57 'mature' => 0,
58 'spam' => 0,
59 'deleted' => 0,
60 'lang_id' => 0,
61 );
62
63 $prepared_data = wp_prepare_site_data( $data, $defaults );
64 if ( is_wp_error( $prepared_data ) ) {
65 return $prepared_data;
66 }
67
68 if ( false === $wpdb->insert( $wpdb->blogs, $prepared_data ) ) {
69 return new WP_Error( 'db_insert_error', __( 'Could not insert site into the database.' ), $wpdb->last_error );
70 }
71
72 $site_id = (int) $wpdb->insert_id;
73
74 clean_blog_cache( $site_id );
75
76 $new_site = get_site( $site_id );
77
78 if ( ! $new_site ) {
79 return new WP_Error( 'get_site_error', __( 'Could not retrieve site data.' ) );
80 }
81
82 /**
83 * Fires once a site has been inserted into the database.
84 *
85 * @since 5.1.0
86 *
87 * @param WP_Site $new_site New site object.
88 */
89 do_action( 'wp_insert_site', $new_site );
90
91 // Extract the passed arguments that may be relevant for site initialization.
92 $args = array_diff_key( $data, $defaults );
93 if ( isset( $args['site_id'] ) ) {
94 unset( $args['site_id'] );
95 }
96
97 /**
98 * Fires when a site's initialization routine should be executed.
99 *
100 * @since 5.1.0
101 *
102 * @param WP_Site $new_site New site object.
103 * @param array $args Arguments for the initialization.
104 */
105 do_action( 'wp_initialize_site', $new_site, $args );
106
107 // Only compute extra hook parameters if the deprecated hook is actually in use.
108 if ( has_action( 'wpmu_new_blog' ) ) {
109 $user_id = ! empty( $args['user_id'] ) ? $args['user_id'] : 0;
110 $meta = ! empty( $args['options'] ) ? $args['options'] : array();
111
112 // WPLANG was passed with `$meta` to the `wpmu_new_blog` hook prior to 5.1.0.
113 if ( ! array_key_exists( 'WPLANG', $meta ) ) {
114 $meta['WPLANG'] = get_network_option( $new_site->network_id, 'WPLANG' );
115 }
116
117 /*
118 * Rebuild the data expected by the `wpmu_new_blog` hook prior to 5.1.0 using allowed keys.
119 * The `$allowed_data_fields` matches the one used in `wpmu_create_blog()`.
120 */
121 $allowed_data_fields = array( 'public', 'archived', 'mature', 'spam', 'deleted', 'lang_id' );
122 $meta = array_merge( array_intersect_key( $data, array_flip( $allowed_data_fields ) ), $meta );
123
124 /**
125 * Fires immediately after a new site is created.
126 *
127 * @since MU (3.0.0)
128 * @deprecated 5.1.0 Use {@see 'wp_initialize_site'} instead.
129 *
130 * @param int $site_id Site ID.
131 * @param int $user_id User ID.
132 * @param string $domain Site domain.
133 * @param string $path Site path.
134 * @param int $network_id Network ID. Only relevant on multi-network installations.
135 * @param array $meta Meta data. Used to set initial site options.
136 */
137 do_action_deprecated(
138 'wpmu_new_blog',
139 array( $new_site->id, $user_id, $new_site->domain, $new_site->path, $new_site->network_id, $meta ),
140 '5.1.0',
141 'wp_initialize_site'
142 );
143 }
144
145 return (int) $new_site->id;
146}
147
148/**
149 * Updates a site in the database.
150 *
151 * @since 5.1.0
152 *
153 * @global wpdb $wpdb WordPress database abstraction object.
154 *
155 * @param int $site_id ID of the site that should be updated.
156 * @param array $data Site data to update. See {@see wp_insert_site()} for the list of supported keys.
157 * @return int|WP_Error The updated site's ID on success, or error object on failure.
158 */
159function wp_update_site( $site_id, array $data ) {
160 global $wpdb;
161
162 if ( empty( $site_id ) ) {
163 return new WP_Error( 'site_empty_id', __( 'Site ID must not be empty.' ) );
164 }
165
166 $old_site = get_site( $site_id );
167 if ( ! $old_site ) {
168 return new WP_Error( 'site_not_exist', __( 'Site does not exist.' ) );
169 }
170
171 $defaults = $old_site->to_array();
172 $defaults['network_id'] = (int) $defaults['site_id'];
173 $defaults['last_updated'] = current_time( 'mysql', true );
174 unset( $defaults['blog_id'], $defaults['site_id'] );
175
176 $data = wp_prepare_site_data( $data, $defaults, $old_site );
177 if ( is_wp_error( $data ) ) {
178 return $data;
179 }
180
181 if ( false === $wpdb->update( $wpdb->blogs, $data, array( 'blog_id' => $old_site->id ) ) ) {
182 return new WP_Error( 'db_update_error', __( 'Could not update site in the database.' ), $wpdb->last_error );
183 }
184
185 clean_blog_cache( $old_site );
186
187 $new_site = get_site( $old_site->id );
188
189 /**
190 * Fires once a site has been updated in the database.
191 *
192 * @since 5.1.0
193 *
194 * @param WP_Site $new_site New site object.
195 * @param WP_Site $old_site Old site object.
196 */
197 do_action( 'wp_update_site', $new_site, $old_site );
198
199 return (int) $new_site->id;
200}
201
202/**
203 * Deletes a site from the database.
204 *
205 * @since 5.1.0
206 *
207 * @global wpdb $wpdb WordPress database abstraction object.
208 *
209 * @param int $site_id ID of the site that should be deleted.
210 * @return WP_Site|WP_Error The deleted site object on success, or error object on failure.
211 */
212function wp_delete_site( $site_id ) {
213 global $wpdb;
214
215 if ( empty( $site_id ) ) {
216 return new WP_Error( 'site_empty_id', __( 'Site ID must not be empty.' ) );
217 }
218
219 $old_site = get_site( $site_id );
220 if ( ! $old_site ) {
221 return new WP_Error( 'site_not_exist', __( 'Site does not exist.' ) );
222 }
223
224 $errors = new WP_Error();
225
226 /**
227 * Fires before a site should be deleted from the database.
228 *
229 * Plugins should amend the `$errors` object via its `WP_Error::add()` method. If any errors
230 * are present, the site will not be deleted.
231 *
232 * @since 5.1.0
233 *
234 * @param WP_Error $errors Error object to add validation errors to.
235 * @param WP_Site $old_site The site object to be deleted.
236 */
237 do_action( 'wp_validate_site_deletion', $errors, $old_site );
238
239 if ( ! empty( $errors->errors ) ) {
240 return $errors;
241 }
242
243 /**
244 * Fires before a site is deleted.
245 *
246 * @since MU (3.0.0)
247 * @deprecated 5.1.0
248 *
249 * @param int $site_id The site ID.
250 * @param bool $drop True if site's table should be dropped. Default false.
251 */
252 do_action_deprecated( 'delete_blog', array( $old_site->id, true ), '5.1.0' );
253
254 /**
255 * Fires when a site's uninitialization routine should be executed.
256 *
257 * @since 5.1.0
258 *
259 * @param WP_Site $old_site Deleted site object.
260 */
261 do_action( 'wp_uninitialize_site', $old_site );
262
263 if ( is_site_meta_supported() ) {
264 $blog_meta_ids = $wpdb->get_col( $wpdb->prepare( "SELECT meta_id FROM $wpdb->blogmeta WHERE blog_id = %d ", $old_site->id ) );
265 foreach ( $blog_meta_ids as $mid ) {
266 delete_metadata_by_mid( 'blog', $mid );
267 }
268 }
269
270 if ( false === $wpdb->delete( $wpdb->blogs, array( 'blog_id' => $old_site->id ) ) ) {
271 return new WP_Error( 'db_delete_error', __( 'Could not delete site from the database.' ), $wpdb->last_error );
272 }
273
274 clean_blog_cache( $old_site );
275
276 /**
277 * Fires once a site has been deleted from the database.
278 *
279 * @since 5.1.0
280 *
281 * @param WP_Site $old_site Deleted site object.
282 */
283 do_action( 'wp_delete_site', $old_site );
284
285 /**
286 * Fires after the site is deleted from the network.
287 *
288 * @since 4.8.0
289 * @deprecated 5.1.0
290 *
291 * @param int $site_id The site ID.
292 * @param bool $drop True if site's tables should be dropped. Default false.
293 */
294 do_action_deprecated( 'deleted_blog', array( $old_site->id, true ), '5.1.0' );
295
296 return $old_site;
297}
298
299/**
300 * Retrieves site data given a site ID or site object.
301 *
302 * Site data will be cached and returned after being passed through a filter.
303 * If the provided site is empty, the current site global will be used.
304 *
305 * @since 4.6.0
306 *
307 * @param WP_Site|int|null $site Optional. Site to retrieve. Default is the current site.
308 * @return WP_Site|null The site object or null if not found.
309 */
310function get_site( $site = null ) {
311 if ( empty( $site ) ) {
312 $site = get_current_blog_id();
313 }
314
315 if ( $site instanceof WP_Site ) {
316 $_site = $site;
317 } elseif ( is_object( $site ) ) {
318 $_site = new WP_Site( $site );
319 } else {
320 $_site = WP_Site::get_instance( $site );
321 }
322
323 if ( ! $_site ) {
324 return null;
325 }
326
327 /**
328 * Fires after a site is retrieved.
329 *
330 * @since 4.6.0
331 *
332 * @param WP_Site $_site Site data.
333 */
334 $_site = apply_filters( 'get_site', $_site );
335
336 return $_site;
337}
338
339/**
340 * Adds any sites from the given IDs to the cache that do not already exist in cache.
341 *
342 * @since 4.6.0
343 * @since 5.1.0 Introduced the `$update_meta_cache` parameter.
344 * @since 6.1.0 This function is no longer marked as "private".
345 * @since 6.3.0 Use wp_lazyload_site_meta() for lazy-loading of site meta.
346 *
347 * @see update_site_cache()
348 * @global wpdb $wpdb WordPress database abstraction object.
349 *
350 * @param array $ids ID list.
351 * @param bool $update_meta_cache Optional. Whether to update the meta cache. Default true.
352 */
353function _prime_site_caches( $ids, $update_meta_cache = true ) {
354 global $wpdb;
355
356 $non_cached_ids = _get_non_cached_ids( $ids, 'sites' );
357 if ( ! empty( $non_cached_ids ) ) {
358 $fresh_sites = $wpdb->get_results( sprintf( "SELECT * FROM $wpdb->blogs WHERE blog_id IN (%s)", implode( ',', array_map( 'intval', $non_cached_ids ) ) ) ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared
359
360 update_site_cache( $fresh_sites, false );
361 }
362
363 if ( $update_meta_cache ) {
364 wp_lazyload_site_meta( $ids );
365 }
366}
367
368/**
369 * Queue site meta for lazy-loading.
370 *
371 * @since 6.3.0
372 *
373 * @param array $site_ids List of site IDs.
374 */
375function wp_lazyload_site_meta( array $site_ids ) {
376 if ( empty( $site_ids ) ) {
377 return;
378 }
379 $lazyloader = wp_metadata_lazyloader();
380 $lazyloader->queue_objects( 'blog', $site_ids );
381}
382
383/**
384 * Updates sites in cache.
385 *
386 * @since 4.6.0
387 * @since 5.1.0 Introduced the `$update_meta_cache` parameter.
388 *
389 * @param array $sites Array of site objects.
390 * @param bool $update_meta_cache Whether to update site meta cache. Default true.
391 */
392function update_site_cache( $sites, $update_meta_cache = true ) {
393 if ( ! $sites ) {
394 return;
395 }
396 $site_ids = array();
397 $site_data = array();
398 $blog_details_data = array();
399 foreach ( $sites as $site ) {
400 $site_ids[] = $site->blog_id;
401 $site_data[ $site->blog_id ] = $site;
402 $blog_details_data[ $site->blog_id . 'short' ] = $site;
403
404 }
405 wp_cache_add_multiple( $site_data, 'sites' );
406 wp_cache_add_multiple( $blog_details_data, 'blog-details' );
407
408 if ( $update_meta_cache ) {
409 update_sitemeta_cache( $site_ids );
410 }
411}
412
413/**
414 * Updates metadata cache for list of site IDs.
415 *
416 * Performs SQL query to retrieve all metadata for the sites matching `$site_ids` and stores them in the cache.
417 * Subsequent calls to `get_site_meta()` will not need to query the database.
418 *
419 * @since 5.1.0
420 *
421 * @param array $site_ids List of site IDs.
422 * @return array|false An array of metadata on success, false if there is nothing to update.
423 */
424function update_sitemeta_cache( $site_ids ) {
425 // Ensure this filter is hooked in even if the function is called early.
426 if ( ! has_filter( 'update_blog_metadata_cache', 'wp_check_site_meta_support_prefilter' ) ) {
427 add_filter( 'update_blog_metadata_cache', 'wp_check_site_meta_support_prefilter' );
428 }
429 return update_meta_cache( 'blog', $site_ids );
430}
431
432/**
433 * Retrieves a list of sites matching requested arguments.
434 *
435 * @since 4.6.0
436 * @since 4.8.0 Introduced the 'lang_id', 'lang__in', and 'lang__not_in' parameters.
437 *
438 * @see WP_Site_Query::parse_query()
439 *
440 * @param string|array $args Optional. Array or string of arguments. See WP_Site_Query::__construct()
441 * for information on accepted arguments. Default empty array.
442 * @return WP_Site[]|int[]|int List of WP_Site objects, a list of site IDs when 'fields' is set to 'ids',
443 * or the number of sites when 'count' is passed as a query var.
444 */
445function get_sites( $args = array() ) {
446 $query = new WP_Site_Query();
447
448 return $query->query( $args );
449}
450
451/**
452 * Prepares site data for insertion or update in the database.
453 *
454 * @since 5.1.0
455 *
456 * @param array $data Associative array of site data passed to the respective function.
457 * See {@see wp_insert_site()} for the possibly included data.
458 * @param array $defaults Site data defaults to parse $data against.
459 * @param WP_Site|null $old_site Optional. Old site object if an update, or null if an insertion.
460 * Default null.
461 * @return array|WP_Error Site data ready for a database transaction, or WP_Error in case a validation
462 * error occurred.
463 */
464function wp_prepare_site_data( $data, $defaults, $old_site = null ) {
465
466 // Maintain backward-compatibility with `$site_id` as network ID.
467 if ( isset( $data['site_id'] ) ) {
468 if ( ! empty( $data['site_id'] ) && empty( $data['network_id'] ) ) {
469 $data['network_id'] = $data['site_id'];
470 }
471 unset( $data['site_id'] );
472 }
473
474 /**
475 * Filters passed site data in order to normalize it.
476 *
477 * @since 5.1.0
478 *
479 * @param array $data Associative array of site data passed to the respective function.
480 * See {@see wp_insert_site()} for the possibly included data.
481 */
482 $data = apply_filters( 'wp_normalize_site_data', $data );
483
484 $allowed_data_fields = array( 'domain', 'path', 'network_id', 'registered', 'last_updated', 'public', 'archived', 'mature', 'spam', 'deleted', 'lang_id' );
485 $data = array_intersect_key( wp_parse_args( $data, $defaults ), array_flip( $allowed_data_fields ) );
486
487 $errors = new WP_Error();
488
489 /**
490 * Fires when data should be validated for a site prior to inserting or updating in the database.
491 *
492 * Plugins should amend the `$errors` object via its `WP_Error::add()` method.
493 *
494 * @since 5.1.0
495 *
496 * @param WP_Error $errors Error object to add validation errors to.
497 * @param array $data Associative array of complete site data. See {@see wp_insert_site()}
498 * for the included data.
499 * @param WP_Site|null $old_site The old site object if the data belongs to a site being updated,
500 * or null if it is a new site being inserted.
501 */
502 do_action( 'wp_validate_site_data', $errors, $data, $old_site );
503
504 if ( ! empty( $errors->errors ) ) {
505 return $errors;
506 }
507
508 // Prepare for database.
509 $data['site_id'] = $data['network_id'];
510 unset( $data['network_id'] );
511
512 return $data;
513}
514
515/**
516 * Normalizes data for a site prior to inserting or updating in the database.
517 *
518 * @since 5.1.0
519 *
520 * @param array $data Associative array of site data passed to the respective function.
521 * See {@see wp_insert_site()} for the possibly included data.
522 * @return array Normalized site data.
523 */
524function wp_normalize_site_data( $data ) {
525 // Sanitize domain if passed.
526 if ( array_key_exists( 'domain', $data ) ) {
527 $data['domain'] = preg_replace( '/[^a-z0-9\-.:]+/i', '', $data['domain'] );
528 }
529
530 // Sanitize path if passed.
531 if ( array_key_exists( 'path', $data ) ) {
532 $data['path'] = trailingslashit( '/' . trim( $data['path'], '/' ) );
533 }
534
535 // Sanitize network ID if passed.
536 if ( array_key_exists( 'network_id', $data ) ) {
537 $data['network_id'] = (int) $data['network_id'];
538 }
539
540 // Sanitize status fields if passed.
541 $status_fields = array( 'public', 'archived', 'mature', 'spam', 'deleted' );
542 foreach ( $status_fields as $status_field ) {
543 if ( array_key_exists( $status_field, $data ) ) {
544 $data[ $status_field ] = (int) $data[ $status_field ];
545 }
546 }
547
548 // Strip date fields if empty.
549 $date_fields = array( 'registered', 'last_updated' );
550 foreach ( $date_fields as $date_field ) {
551 if ( ! array_key_exists( $date_field, $data ) ) {
552 continue;
553 }
554
555 if ( empty( $data[ $date_field ] ) || '0000-00-00 00:00:00' === $data[ $date_field ] ) {
556 unset( $data[ $date_field ] );
557 }
558 }
559
560 return $data;
561}
562
563/**
564 * Validates data for a site prior to inserting or updating in the database.
565 *
566 * @since 5.1.0
567 *
568 * @param WP_Error $errors Error object, passed by reference. Will contain validation errors if
569 * any occurred.
570 * @param array $data Associative array of complete site data. See {@see wp_insert_site()}
571 * for the included data.
572 * @param WP_Site|null $old_site The old site object if the data belongs to a site being updated,
573 * or null if it is a new site being inserted.
574 */
575function wp_validate_site_data( $errors, $data, $old_site = null ) {
576 // A domain must always be present.
577 if ( empty( $data['domain'] ) ) {
578 $errors->add( 'site_empty_domain', __( 'Site domain must not be empty.' ) );
579 }
580
581 // A path must always be present.
582 if ( empty( $data['path'] ) ) {
583 $errors->add( 'site_empty_path', __( 'Site path must not be empty.' ) );
584 }
585
586 // A network ID must always be present.
587 if ( empty( $data['network_id'] ) ) {
588 $errors->add( 'site_empty_network_id', __( 'Site network ID must be provided.' ) );
589 }
590
591 // Both registration and last updated dates must always be present and valid.
592 $date_fields = array( 'registered', 'last_updated' );
593 foreach ( $date_fields as $date_field ) {
594 if ( empty( $data[ $date_field ] ) ) {
595 $errors->add( 'site_empty_' . $date_field, __( 'Both registration and last updated dates must be provided.' ) );
596 break;
597 }
598
599 // Allow '0000-00-00 00:00:00', although it be stripped out at this point.
600 if ( '0000-00-00 00:00:00' !== $data[ $date_field ] ) {
601 $month = substr( $data[ $date_field ], 5, 2 );
602 $day = substr( $data[ $date_field ], 8, 2 );
603 $year = substr( $data[ $date_field ], 0, 4 );
604 $valid_date = wp_checkdate( $month, $day, $year, $data[ $date_field ] );
605 if ( ! $valid_date ) {
606 $errors->add( 'site_invalid_' . $date_field, __( 'Both registration and last updated dates must be valid dates.' ) );
607 break;
608 }
609 }
610 }
611
612 if ( ! empty( $errors->errors ) ) {
613 return;
614 }
615
616 // If a new site, or domain/path/network ID have changed, ensure uniqueness.
617 if ( ! $old_site
618 || $data['domain'] !== $old_site->domain
619 || $data['path'] !== $old_site->path
620 || $data['network_id'] !== $old_site->network_id
621 ) {
622 if ( domain_exists( $data['domain'], $data['path'], $data['network_id'] ) ) {
623 $errors->add( 'site_taken', __( 'Sorry, that site already exists!' ) );
624 }
625 }
626}
627
628/**
629 * Runs the initialization routine for a given site.
630 *
631 * This process includes creating the site's database tables and
632 * populating them with defaults.
633 *
634 * @since 5.1.0
635 *
636 * @global wpdb $wpdb WordPress database abstraction object.
637 * @global WP_Roles $wp_roles WordPress role management object.
638 *
639 * @param int|WP_Site $site_id Site ID or object.
640 * @param array $args {
641 * Optional. Arguments to modify the initialization behavior.
642 *
643 * @type int $user_id Required. User ID for the site administrator.
644 * @type string $title Site title. Default is 'Site %d' where %d is the
645 * site ID.
646 * @type array $options Custom option $key => $value pairs to use. Default
647 * empty array.
648 * @type array $meta Custom site metadata $key => $value pairs to use.
649 * Default empty array.
650 * }
651 * @return true|WP_Error True on success, or error object on failure.
652 */
653function wp_initialize_site( $site_id, array $args = array() ) {
654 global $wpdb, $wp_roles;
655
656 if ( empty( $site_id ) ) {
657 return new WP_Error( 'site_empty_id', __( 'Site ID must not be empty.' ) );
658 }
659
660 $site = get_site( $site_id );
661 if ( ! $site ) {
662 return new WP_Error( 'site_invalid_id', __( 'Site with the ID does not exist.' ) );
663 }
664
665 if ( wp_is_site_initialized( $site ) ) {
666 return new WP_Error( 'site_already_initialized', __( 'The site appears to be already initialized.' ) );
667 }
668
669 $network = get_network( $site->network_id );
670 if ( ! $network ) {
671 $network = get_network();
672 }
673
674 $args = wp_parse_args(
675 $args,
676 array(
677 'user_id' => 0,
678 /* translators: %d: Site ID. */
679 'title' => sprintf( __( 'Site %d' ), $site->id ),
680 'options' => array(),
681 'meta' => array(),
682 )
683 );
684
685 /**
686 * Filters the arguments for initializing a site.
687 *
688 * @since 5.1.0
689 *
690 * @param array $args Arguments to modify the initialization behavior.
691 * @param WP_Site $site Site that is being initialized.
692 * @param WP_Network $network Network that the site belongs to.
693 */
694 $args = apply_filters( 'wp_initialize_site_args', $args, $site, $network );
695
696 $orig_installing = wp_installing();
697 if ( ! $orig_installing ) {
698 wp_installing( true );
699 }
700
701 $switch = false;
702 if ( get_current_blog_id() !== $site->id ) {
703 $switch = true;
704 switch_to_blog( $site->id );
705 }
706
707 require_once ABSPATH . 'wp-admin/includes/upgrade.php';
708
709 // Set up the database tables.
710 make_db_current_silent( 'blog' );
711
712 $home_scheme = 'http';
713 $siteurl_scheme = 'http';
714 if ( ! is_subdomain_install() ) {
715 if ( 'https' === parse_url( get_home_url( $network->site_id ), PHP_URL_SCHEME ) ) {
716 $home_scheme = 'https';
717 }
718 if ( 'https' === parse_url( get_network_option( $network->id, 'siteurl' ), PHP_URL_SCHEME ) ) {
719 $siteurl_scheme = 'https';
720 }
721 }
722
723 // Populate the site's options.
724 populate_options(
725 array_merge(
726 array(
727 'home' => untrailingslashit( $home_scheme . '://' . $site->domain . $site->path ),
728 'siteurl' => untrailingslashit( $siteurl_scheme . '://' . $site->domain . $site->path ),
729 'blogname' => wp_unslash( $args['title'] ),
730 'admin_email' => '',
731 'upload_path' => get_network_option( $network->id, 'ms_files_rewriting' ) ? UPLOADBLOGSDIR . "/{$site->id}/files" : get_blog_option( $network->site_id, 'upload_path' ),
732 'blog_public' => (int) $site->public,
733 'WPLANG' => get_network_option( $network->id, 'WPLANG' ),
734 ),
735 $args['options']
736 )
737 );
738
739 // Clean blog cache after populating options.
740 clean_blog_cache( $site );
741
742 // Populate the site's roles.
743 populate_roles();
744 $wp_roles = new WP_Roles();
745
746 // Populate metadata for the site.
747 populate_site_meta( $site->id, $args['meta'] );
748
749 // Remove all permissions that may exist for the site.
750 $table_prefix = $wpdb->get_blog_prefix();
751 delete_metadata( 'user', 0, $table_prefix . 'user_level', null, true ); // Delete all.
752 delete_metadata( 'user', 0, $table_prefix . 'capabilities', null, true ); // Delete all.
753
754 // Install default site content.
755 wp_install_defaults( $args['user_id'] );
756
757 // Set the site administrator.
758 add_user_to_blog( $site->id, $args['user_id'], 'administrator' );
759 if ( ! user_can( $args['user_id'], 'manage_network' ) && ! get_user_meta( $args['user_id'], 'primary_blog', true ) ) {
760 update_user_meta( $args['user_id'], 'primary_blog', $site->id );
761 }
762
763 if ( $switch ) {
764 restore_current_blog();
765 }
766
767 wp_installing( $orig_installing );
768
769 return true;
770}
771
772/**
773 * Runs the uninitialization routine for a given site.
774 *
775 * This process includes dropping the site's database tables and deleting its uploads directory.
776 *
777 * @since 5.1.0
778 *
779 * @global wpdb $wpdb WordPress database abstraction object.
780 *
781 * @param int|WP_Site $site_id Site ID or object.
782 * @return true|WP_Error True on success, or error object on failure.
783 */
784function wp_uninitialize_site( $site_id ) {
785 global $wpdb;
786
787 if ( empty( $site_id ) ) {
788 return new WP_Error( 'site_empty_id', __( 'Site ID must not be empty.' ) );
789 }
790
791 $site = get_site( $site_id );
792 if ( ! $site ) {
793 return new WP_Error( 'site_invalid_id', __( 'Site with the ID does not exist.' ) );
794 }
795
796 if ( ! wp_is_site_initialized( $site ) ) {
797 return new WP_Error( 'site_already_uninitialized', __( 'The site appears to be already uninitialized.' ) );
798 }
799
800 $users = get_users(
801 array(
802 'blog_id' => $site->id,
803 'fields' => 'ids',
804 )
805 );
806
807 // Remove users from the site.
808 if ( ! empty( $users ) ) {
809 foreach ( $users as $user_id ) {
810 remove_user_from_blog( $user_id, $site->id );
811 }
812 }
813
814 $switch = false;
815 if ( get_current_blog_id() !== $site->id ) {
816 $switch = true;
817 switch_to_blog( $site->id );
818 }
819
820 $uploads = wp_get_upload_dir();
821
822 $tables = $wpdb->tables( 'blog' );
823
824 /**
825 * Filters the tables to drop when the site is deleted.
826 *
827 * @since MU (3.0.0)
828 *
829 * @param string[] $tables Array of names of the site tables to be dropped.
830 * @param int $site_id The ID of the site to drop tables for.
831 */
832 $drop_tables = apply_filters( 'wpmu_drop_tables', $tables, $site->id );
833
834 foreach ( (array) $drop_tables as $table ) {
835 $wpdb->query( "DROP TABLE IF EXISTS `$table`" ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared
836 }
837
838 /**
839 * Filters the upload base directory to delete when the site is deleted.
840 *
841 * @since MU (3.0.0)
842 *
843 * @param string $basedir Uploads path without subdirectory. See {@see wp_upload_dir()}.
844 * @param int $site_id The site ID.
845 */
846 $dir = apply_filters( 'wpmu_delete_blog_upload_dir', $uploads['basedir'], $site->id );
847 $dir = rtrim( $dir, DIRECTORY_SEPARATOR );
848 $top_dir = $dir;
849 $stack = array( $dir );
850 $index = 0;
851
852 while ( $index < count( $stack ) ) {
853 // Get indexed directory from stack.
854 $dir = $stack[ $index ];
855
856 // phpcs:disable WordPress.PHP.NoSilencedErrors.Discouraged
857 $dh = @opendir( $dir );
858 if ( $dh ) {
859 $file = @readdir( $dh );
860 while ( false !== $file ) {
861 if ( '.' === $file || '..' === $file ) {
862 $file = @readdir( $dh );
863 continue;
864 }
865
866 if ( @is_dir( $dir . DIRECTORY_SEPARATOR . $file ) ) {
867 $stack[] = $dir . DIRECTORY_SEPARATOR . $file;
868 } elseif ( @is_file( $dir . DIRECTORY_SEPARATOR . $file ) ) {
869 @unlink( $dir . DIRECTORY_SEPARATOR . $file );
870 }
871
872 $file = @readdir( $dh );
873 }
874 @closedir( $dh );
875 }
876 ++$index;
877 }
878
879 $stack = array_reverse( $stack ); // Last added directories are deepest.
880 foreach ( (array) $stack as $dir ) {
881 if ( $dir !== $top_dir ) {
882 @rmdir( $dir );
883 }
884 }
885
886 // phpcs:enable WordPress.PHP.NoSilencedErrors.Discouraged
887 if ( $switch ) {
888 restore_current_blog();
889 }
890
891 return true;
892}
893
894/**
895 * Checks whether a site is initialized.
896 *
897 * A site is considered initialized when its database tables are present.
898 *
899 * @since 5.1.0
900 *
901 * @global wpdb $wpdb WordPress database abstraction object.
902 *
903 * @param int|WP_Site $site_id Site ID or object.
904 * @return bool True if the site is initialized, false otherwise.
905 */
906function wp_is_site_initialized( $site_id ) {
907 global $wpdb;
908
909 if ( is_object( $site_id ) ) {
910 $site_id = $site_id->blog_id;
911 }
912 $site_id = (int) $site_id;
913
914 /**
915 * Filters the check for whether a site is initialized before the database is accessed.
916 *
917 * Returning a non-null value will effectively short-circuit the function, returning
918 * that value instead.
919 *
920 * @since 5.1.0
921 *
922 * @param bool|null $pre The value to return instead. Default null
923 * to continue with the check.
924 * @param int $site_id The site ID that is being checked.
925 */
926 $pre = apply_filters( 'pre_wp_is_site_initialized', null, $site_id );
927 if ( null !== $pre ) {
928 return (bool) $pre;
929 }
930
931 $switch = false;
932 if ( get_current_blog_id() !== $site_id ) {
933 $switch = true;
934 remove_action( 'switch_blog', 'wp_switch_roles_and_user', 1 );
935 switch_to_blog( $site_id );
936 }
937
938 $suppress = $wpdb->suppress_errors();
939 $result = (bool) $wpdb->get_results( "DESCRIBE {$wpdb->posts}" );
940 $wpdb->suppress_errors( $suppress );
941
942 if ( $switch ) {
943 restore_current_blog();
944 add_action( 'switch_blog', 'wp_switch_roles_and_user', 1, 2 );
945 }
946
947 return $result;
948}
949
950/**
951 * Clean the blog cache
952 *
953 * @since 3.5.0
954 *
955 * @global bool $_wp_suspend_cache_invalidation
956 *
957 * @param WP_Site|int $blog The site object or ID to be cleared from cache.
958 */
959function clean_blog_cache( $blog ) {
960 global $_wp_suspend_cache_invalidation;
961
962 if ( ! empty( $_wp_suspend_cache_invalidation ) ) {
963 return;
964 }
965
966 if ( empty( $blog ) ) {
967 return;
968 }
969
970 $blog_id = $blog;
971 $blog = get_site( $blog_id );
972 if ( ! $blog ) {
973 if ( ! is_numeric( $blog_id ) ) {
974 return;
975 }
976
977 // Make sure a WP_Site object exists even when the site has been deleted.
978 $blog = new WP_Site(
979 (object) array(
980 'blog_id' => $blog_id,
981 'domain' => null,
982 'path' => null,
983 )
984 );
985 }
986
987 $blog_id = $blog->blog_id;
988 $domain_path_key = md5( $blog->domain . $blog->path );
989
990 wp_cache_delete( $blog_id, 'sites' );
991 wp_cache_delete( $blog_id, 'site-details' );
992 wp_cache_delete( $blog_id, 'blog-details' );
993 wp_cache_delete( $blog_id . 'short', 'blog-details' );
994 wp_cache_delete( $domain_path_key, 'blog-lookup' );
995 wp_cache_delete( $domain_path_key, 'blog-id-cache' );
996 wp_cache_delete( $blog_id, 'blog_meta' );
997
998 /**
999 * Fires immediately after a site has been removed from the object cache.
1000 *
1001 * @since 4.6.0
1002 *
1003 * @param string $id Site ID as a numeric string.
1004 * @param WP_Site $blog Site object.
1005 * @param string $domain_path_key md5 hash of domain and path.
1006 */
1007 do_action( 'clean_site_cache', $blog_id, $blog, $domain_path_key );
1008
1009 wp_cache_set_sites_last_changed();
1010
1011 /**
1012 * Fires after the blog details cache is cleared.
1013 *
1014 * @since 3.4.0
1015 * @deprecated 4.9.0 Use {@see 'clean_site_cache'} instead.
1016 *
1017 * @param int $blog_id Blog ID.
1018 */
1019 do_action_deprecated( 'refresh_blog_details', array( $blog_id ), '4.9.0', 'clean_site_cache' );
1020}
1021
1022/**
1023 * Adds metadata to a site.
1024 *
1025 * For historical reasons both the meta key and the meta value are expected to be "slashed" (slashes escaped) on input.
1026 *
1027 * @since 5.1.0
1028 *
1029 * @param int $site_id Site ID.
1030 * @param string $meta_key Metadata name.
1031 * @param mixed $meta_value Metadata value. Arrays and objects are stored as serialized data and
1032 * will be returned as the same type when retrieved. Other data types will
1033 * be stored as strings in the database:
1034 * - false is stored and retrieved as an empty string ('')
1035 * - true is stored and retrieved as '1'
1036 * - numbers (both integer and float) are stored and retrieved as strings
1037 * Must be serializable if non-scalar.
1038 * @param bool $unique Optional. Whether the same key should not be added.
1039 * Default false.
1040 * @return int|false Meta ID on success, false on failure.
1041 */
1042function add_site_meta( $site_id, $meta_key, $meta_value, $unique = false ) {
1043 return add_metadata( 'blog', $site_id, $meta_key, $meta_value, $unique );
1044}
1045
1046/**
1047 * Removes metadata matching criteria from a site.
1048 *
1049 * You can match based on the key, or key and value. Removing based on key and
1050 * value, will keep from removing duplicate metadata with the same key. It also
1051 * allows removing all metadata matching key, if needed.
1052 *
1053 * For historical reasons both the meta key and the meta value are expected to be "slashed" (slashes escaped) on input.
1054 *
1055 * @since 5.1.0
1056 *
1057 * @param int $site_id Site ID.
1058 * @param string $meta_key Metadata name.
1059 * @param mixed $meta_value Optional. Metadata value. If provided,
1060 * rows will only be removed that match the value.
1061 * Must be serializable if non-scalar. Default empty.
1062 * @return bool True on success, false on failure.
1063 */
1064function delete_site_meta( $site_id, $meta_key, $meta_value = '' ) {
1065 return delete_metadata( 'blog', $site_id, $meta_key, $meta_value );
1066}
1067
1068/**
1069 * Retrieves metadata for a site.
1070 *
1071 * @since 5.1.0
1072 *
1073 * @param int $site_id Site ID.
1074 * @param string $key Optional. The meta key to retrieve. By default,
1075 * returns data for all keys. Default empty.
1076 * @param bool $single Optional. Whether to return a single value.
1077 * This parameter has no effect if `$key` is not specified.
1078 * Default false.
1079 * @return mixed An array of values if `$single` is false.
1080 * The value of meta data field if `$single` is true.
1081 * False for an invalid `$site_id` (non-numeric, zero, or negative value).
1082 * An empty array if a valid but non-existing site ID is passed and `$single` is false.
1083 * An empty string if a valid but non-existing site ID is passed and `$single` is true.
1084 * Note: Non-serialized values are returned as strings:
1085 * - false values are returned as empty strings ('')
1086 * - true values are returned as '1'
1087 * - numbers (both integer and float) are returned as strings
1088 * Arrays and objects retain their original type.
1089 */
1090function get_site_meta( $site_id, $key = '', $single = false ) {
1091 return get_metadata( 'blog', $site_id, $key, $single );
1092}
1093
1094/**
1095 * Updates metadata for a site.
1096 *
1097 * Use the `$prev_value` parameter to differentiate between meta fields with the
1098 * same key and site ID.
1099 *
1100 * If the meta field for the site does not exist, it will be added.
1101 *
1102 * For historical reasons both the meta key and the meta value are expected to be "slashed" (slashes escaped) on input.
1103 *
1104 * @since 5.1.0
1105 *
1106 * @param int $site_id Site ID.
1107 * @param string $meta_key Metadata key.
1108 * @param mixed $meta_value Metadata value. Must be serializable if non-scalar.
1109 * @param mixed $prev_value Optional. Previous value to check before updating.
1110 * If specified, only update existing metadata entries with
1111 * this value. Otherwise, update all entries. Default empty.
1112 * @return int|bool Meta ID if the key didn't exist, true on successful update,
1113 * false on failure or if the value passed to the function
1114 * is the same as the one that is already in the database.
1115 */
1116function update_site_meta( $site_id, $meta_key, $meta_value, $prev_value = '' ) {
1117 return update_metadata( 'blog', $site_id, $meta_key, $meta_value, $prev_value );
1118}
1119
1120/**
1121 * Deletes everything from site meta matching meta key.
1122 *
1123 * @since 5.1.0
1124 *
1125 * @param string $meta_key Metadata key to search for when deleting.
1126 * @return bool Whether the site meta key was deleted from the database.
1127 */
1128function delete_site_meta_by_key( $meta_key ) {
1129 return delete_metadata( 'blog', null, $meta_key, '', true );
1130}
1131
1132/**
1133 * Updates the count of sites for a network based on a changed site.
1134 *
1135 * @since 5.1.0
1136 *
1137 * @param WP_Site $new_site The site object that has been inserted, updated or deleted.
1138 * @param WP_Site|null $old_site Optional. If $new_site has been updated, this must be the previous
1139 * state of that site. Default null.
1140 */
1141function wp_maybe_update_network_site_counts_on_update( $new_site, $old_site = null ) {
1142 if ( null === $old_site ) {
1143 wp_maybe_update_network_site_counts( $new_site->network_id );
1144 return;
1145 }
1146
1147 if ( $new_site->network_id !== $old_site->network_id ) {
1148 wp_maybe_update_network_site_counts( $new_site->network_id );
1149 wp_maybe_update_network_site_counts( $old_site->network_id );
1150 }
1151}
1152
1153/**
1154 * Triggers actions on site status updates.
1155 *
1156 * @since 5.1.0
1157 *
1158 * @param WP_Site $new_site The site object after the update.
1159 * @param WP_Site|null $old_site Optional. If $new_site has been updated, this must be the previous
1160 * state of that site. Default null.
1161 */
1162function wp_maybe_transition_site_statuses_on_update( $new_site, $old_site = null ) {
1163 $site_id = $new_site->id;
1164
1165 // Use the default values for a site if no previous state is given.
1166 if ( ! $old_site ) {
1167 $old_site = new WP_Site( new stdClass() );
1168 }
1169
1170 if ( $new_site->spam !== $old_site->spam ) {
1171 if ( '1' === $new_site->spam ) {
1172
1173 /**
1174 * Fires when the 'spam' status is added to a site.
1175 *
1176 * @since MU (3.0.0)
1177 *
1178 * @param int $site_id Site ID.
1179 */
1180 do_action( 'make_spam_blog', $site_id );
1181 } else {
1182
1183 /**
1184 * Fires when the 'spam' status is removed from a site.
1185 *
1186 * @since MU (3.0.0)
1187 *
1188 * @param int $site_id Site ID.
1189 */
1190 do_action( 'make_ham_blog', $site_id );
1191 }
1192 }
1193
1194 if ( $new_site->mature !== $old_site->mature ) {
1195 if ( '1' === $new_site->mature ) {
1196
1197 /**
1198 * Fires when the 'mature' status is added to a site.
1199 *
1200 * @since 3.1.0
1201 *
1202 * @param int $site_id Site ID.
1203 */
1204 do_action( 'mature_blog', $site_id );
1205 } else {
1206
1207 /**
1208 * Fires when the 'mature' status is removed from a site.
1209 *
1210 * @since 3.1.0
1211 *
1212 * @param int $site_id Site ID.
1213 */
1214 do_action( 'unmature_blog', $site_id );
1215 }
1216 }
1217
1218 if ( $new_site->archived !== $old_site->archived ) {
1219 if ( '1' === $new_site->archived ) {
1220
1221 /**
1222 * Fires when the 'archived' status is added to a site.
1223 *
1224 * @since MU (3.0.0)
1225 *
1226 * @param int $site_id Site ID.
1227 */
1228 do_action( 'archive_blog', $site_id );
1229 } else {
1230
1231 /**
1232 * Fires when the 'archived' status is removed from a site.
1233 *
1234 * @since MU (3.0.0)
1235 *
1236 * @param int $site_id Site ID.
1237 */
1238 do_action( 'unarchive_blog', $site_id );
1239 }
1240 }
1241
1242 if ( $new_site->deleted !== $old_site->deleted ) {
1243 if ( '1' === $new_site->deleted ) {
1244
1245 /**
1246 * Fires when the 'flagged for deletion' status is added to a site.
1247 *
1248 * @since 3.5.0
1249 *
1250 * @param int $site_id Site ID.
1251 */
1252 do_action( 'make_delete_blog', $site_id );
1253 } else {
1254
1255 /**
1256 * Fires when the 'flagged for deletion' status is removed from a site.
1257 *
1258 * @since 3.5.0
1259 *
1260 * @param int $site_id Site ID.
1261 */
1262 do_action( 'make_undelete_blog', $site_id );
1263 }
1264 }
1265
1266 if ( $new_site->public !== $old_site->public ) {
1267
1268 /**
1269 * Fires after the current blog's 'public' setting is updated.
1270 *
1271 * @since MU (3.0.0)
1272 *
1273 * @param int $site_id Site ID.
1274 * @param string $is_public Whether the site is public. A numeric string,
1275 * for compatibility reasons. Accepts '1' or '0'.
1276 */
1277 do_action( 'update_blog_public', $site_id, $new_site->public );
1278 }
1279}
1280
1281/**
1282 * Cleans the necessary caches after specific site data has been updated.
1283 *
1284 * @since 5.1.0
1285 *
1286 * @param WP_Site $new_site The site object after the update.
1287 * @param WP_Site $old_site The site object prior to the update.
1288 */
1289function wp_maybe_clean_new_site_cache_on_update( $new_site, $old_site ) {
1290 if ( $old_site->domain !== $new_site->domain || $old_site->path !== $new_site->path ) {
1291 clean_blog_cache( $new_site );
1292 }
1293}
1294
1295/**
1296 * Updates the `blog_public` option for a given site ID.
1297 *
1298 * @since 5.1.0
1299 *
1300 * @param int $site_id Site ID.
1301 * @param string $is_public Whether the site is public. A numeric string,
1302 * for compatibility reasons. Accepts '1' or '0'.
1303 */
1304function wp_update_blog_public_option_on_site_update( $site_id, $is_public ) {
1305
1306 // Bail if the site's database tables do not exist (yet).
1307 if ( ! wp_is_site_initialized( $site_id ) ) {
1308 return;
1309 }
1310
1311 update_blog_option( $site_id, 'blog_public', $is_public );
1312}
1313
1314/**
1315 * Sets the last changed time for the 'sites' cache group.
1316 *
1317 * @since 5.1.0
1318 */
1319function wp_cache_set_sites_last_changed() {
1320 wp_cache_set_last_changed( 'sites' );
1321}
1322
1323/**
1324 * Aborts calls to site meta if it is not supported.
1325 *
1326 * @since 5.1.0
1327 *
1328 * @global wpdb $wpdb WordPress database abstraction object.
1329 *
1330 * @param mixed $check Skip-value for whether to proceed site meta function execution.
1331 * @return mixed Original value of $check, or false if site meta is not supported.
1332 */
1333function wp_check_site_meta_support_prefilter( $check ) {
1334 if ( ! is_site_meta_supported() ) {
1335 /* translators: %s: Database table name. */
1336 _doing_it_wrong( __FUNCTION__, sprintf( __( 'The %s table is not installed. Please run the network database upgrade.' ), $GLOBALS['wpdb']->blogmeta ), '5.1.0' );
1337 return false;
1338 }
1339
1340 return $check;
1341}
1342
Ui Ux Design – Teachers Night Out https://cardgames4educators.com Wed, 16 Oct 2024 22:24:18 +0000 en-US hourly 1 https://wordpress.org/?v=6.9.4 https://cardgames4educators.com/wp-content/uploads/2024/06/cropped-Card-4-Educators-logo-32x32.png Ui Ux Design – Teachers Night Out https://cardgames4educators.com 32 32 Masters In English How English Speaker https://cardgames4educators.com/masters-in-english-how-english-speaker/ https://cardgames4educators.com/masters-in-english-how-english-speaker/#comments Mon, 27 May 2024 08:54:45 +0000 https://themexriver.com/wp/kadu/?p=1

Erat himenaeos neque id sagittis massa. Hac suscipit pulvinar dignissim platea magnis eu. Don tellus a pharetra inceptos efficitur dui pulvinar. Feugiat facilisis penatibus pulvinar nunc dictumst donec odio platea habitasse. Lacus porta dolor purus elit ante bibendum tortor netus taciti nullam cubilia. Erat per suspendisse placerat morbi egestas pulvinar bibendum sollicitudin nec. Euismod cubilia eleifend velit himenaeos sodales lectus. Leo maximus cras ac porttitor aliquam torquent pulvinar odio volutpat parturient. Quisque risus finibus suspendisse mus purus magnis facilisi condimentum consectetur dui. Curae elit suspendisse cursus vehicula.

Turpis taciti class non vel pretium quis pulvinar tempor lobortis nunc. Libero phasellus parturient sapien volutpat malesuada ornare. Cubilia dignissim sollicitudin rhoncus lacinia maximus. Cras lorem fermentum bibendum pellentesque nisl etiam ligula enim cubilia. Vulputate pede sapien torquent montes tempus malesuada in mattis dis turpis vitae. Porta est tempor ex eget feugiat vulputate ipsum. Justo nec iaculis habitant diam arcu fermentum.

We offer comprehen sive emplo ment services such as assistance wit employer compliance.Our company is your strategic HR partner as instead of HR. john smithson

Cubilia dignissim sollicitudin rhoncus lacinia maximus. Cras lorem fermentum bibendum pellentesque nisl etiam ligula enim cubilia. Vulputate pede sapien torquent montes tempus malesuada in mattis dis turpis vitae.

Exploring Learning Landscapes in Academic

Feugiat facilisis penatibus pulvinar nunc dictumst donec odio platea habitasse. Lacus porta dolor purus elit ante bibendum tortor netus taciti nullam cubilia. Erat per suspendisse placerat morbi egestas pulvinar bibendum sollicitudin nec. Euismod cubilia eleifend velit himenaeos sodales lectus. Leo maximus cras ac porttitor aliquam torquent.

]]>
https://cardgames4educators.com/masters-in-english-how-english-speaker/feed/ 1