Title: WP_Customize_Manager::save_changeset_post
Published: December 7, 2016
Last modified: May 20, 2026

---

# WP_Customize_Manager::save_changeset_post( array $args = array() ): array|󠀁[WP_Error](https://developer.wordpress.org/reference/classes/wp_error/)󠁿

## In this article

 * [Parameters](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#parameters)
 * [Return](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#return)
 * [Source](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#source)
 * [Hooks](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#hooks)
 * [Related](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#related)
 * [Changelog](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#changelog)

[ Back to top](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#wp--skip-link--target)

Saves the post for the loaded changeset.

## 󠀁[Parameters](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#parameters)󠁿

 `$args`arrayoptional

Args for changeset post.

 * `data` array
 * Optional additional changeset data. Values will be merged on top of any existing
   post values.
 * `status` string
 * Post status. Optional. If supplied, the save will be transactional and a post
   revision will be allowed.
 * `title` string
 * Post title. Optional.
 * `date_gmt` string
 * Date in GMT. Optional.
 * `user_id` int
 * ID for user who is saving the changeset. Optional, defaults to the current user
   ID.
 * `starter_content` bool
 * Whether the data is starter content. If false (default), then $starter_content
   will be cleared for any $data being saved.
 * `autosave` bool
 * Whether this is a request to create an autosave revision.

Default:`array()`

## 󠀁[Return](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#return)󠁿

 array|[WP_Error](https://developer.wordpress.org/reference/classes/wp_error/) Returns
array on success and [WP_Error](https://developer.wordpress.org/reference/classes/wp_error/)
with array data on error.

## 󠀁[Source](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#source)󠁿

    ```php
    public function save_changeset_post( $args = array() ) {

    	$args = array_merge(
    		array(
    			'status'          => null,
    			'title'           => null,
    			'data'            => array(),
    			'date_gmt'        => null,
    			'user_id'         => get_current_user_id(),
    			'starter_content' => false,
    			'autosave'        => false,
    		),
    		$args
    	);

    	$changeset_post_id       = $this->changeset_post_id();
    	$existing_changeset_data = array();
    	if ( $changeset_post_id ) {
    		$existing_status = get_post_status( $changeset_post_id );
    		if ( 'publish' === $existing_status || 'trash' === $existing_status ) {
    			return new WP_Error(
    				'changeset_already_published',
    				__( 'The previous set of changes has already been published. Please try saving your current set of changes again.' ),
    				array(
    					'next_changeset_uuid' => wp_generate_uuid4(),
    				)
    			);
    		}

    		$existing_changeset_data = $this->get_changeset_post_data( $changeset_post_id );
    		if ( is_wp_error( $existing_changeset_data ) ) {
    			return $existing_changeset_data;
    		}
    	}

    	// Fail if attempting to publish but publish hook is missing.
    	if ( 'publish' === $args['status'] && false === has_action( 'transition_post_status', '_wp_customize_publish_changeset' ) ) {
    		return new WP_Error( 'missing_publish_callback' );
    	}

    	// Validate date.
    	$now = gmdate( 'Y-m-d H:i:59' );
    	if ( $args['date_gmt'] ) {
    		$is_future_dated = ( mysql2date( 'U', $args['date_gmt'], false ) > mysql2date( 'U', $now, false ) );
    		if ( ! $is_future_dated ) {
    			return new WP_Error( 'not_future_date', __( 'You must supply a future date to schedule.' ) ); // Only future dates are allowed.
    		}

    		if ( ! $this->is_theme_active() && ( 'future' === $args['status'] || $is_future_dated ) ) {
    			return new WP_Error( 'cannot_schedule_theme_switches' ); // This should be allowed in the future, when theme is a regular setting.
    		}
    		$will_remain_auto_draft = ( ! $args['status'] && ( ! $changeset_post_id || 'auto-draft' === get_post_status( $changeset_post_id ) ) );
    		if ( $will_remain_auto_draft ) {
    			return new WP_Error( 'cannot_supply_date_for_auto_draft_changeset' );
    		}
    	} elseif ( $changeset_post_id && 'future' === $args['status'] ) {

    		// Fail if the new status is future but the existing post's date is not in the future.
    		$changeset_post = get_post( $changeset_post_id );
    		if ( mysql2date( 'U', $changeset_post->post_date_gmt, false ) <= mysql2date( 'U', $now, false ) ) {
    			return new WP_Error( 'not_future_date', __( 'You must supply a future date to schedule.' ) );
    		}
    	}

    	if ( ! empty( $is_future_dated ) && 'publish' === $args['status'] ) {
    		$args['status'] = 'future';
    	}

    	// Validate autosave param. See _wp_post_revision_fields() for why these fields are disallowed.
    	if ( $args['autosave'] ) {
    		if ( $args['date_gmt'] ) {
    			return new WP_Error( 'illegal_autosave_with_date_gmt' );
    		} elseif ( $args['status'] ) {
    			return new WP_Error( 'illegal_autosave_with_status' );
    		} elseif ( $args['user_id'] && get_current_user_id() !== $args['user_id'] ) {
    			return new WP_Error( 'illegal_autosave_with_non_current_user' );
    		}
    	}

    	// The request was made via wp.customize.previewer.save().
    	$update_transactionally = (bool) $args['status'];
    	$allow_revision         = (bool) $args['status'];

    	// Amend post values with any supplied data.
    	foreach ( $args['data'] as $setting_id => $setting_params ) {
    		if ( is_array( $setting_params ) && array_key_exists( 'value', $setting_params ) ) {
    			$this->set_post_value( $setting_id, $setting_params['value'] ); // Add to post values so that they can be validated and sanitized.
    		}
    	}

    	// Note that in addition to post data, this will include any stashed theme mods.
    	$post_values = $this->unsanitized_post_values(
    		array(
    			'exclude_changeset' => true,
    			'exclude_post_data' => false,
    		)
    	);
    	$this->add_dynamic_settings( array_keys( $post_values ) ); // Ensure settings get created even if they lack an input value.

    	/*
    	 * Get list of IDs for settings that have values different from what is currently
    	 * saved in the changeset. By skipping any values that are already the same, the
    	 * subset of changed settings can be passed into validate_setting_values to prevent
    	 * an underprivileged modifying a single setting for which they have the capability
    	 * from being blocked from saving. This also prevents a user from touching of the
    	 * previous saved settings and overriding the associated user_id if they made no change.
    	 */
    	$changed_setting_ids = array();
    	foreach ( $post_values as $setting_id => $setting_value ) {
    		$setting = $this->get_setting( $setting_id );

    		if ( $setting && 'theme_mod' === $setting->type ) {
    			$prefixed_setting_id = $this->get_stylesheet() . '::' . $setting->id;
    		} else {
    			$prefixed_setting_id = $setting_id;
    		}

    		$is_value_changed = (
    			! isset( $existing_changeset_data[ $prefixed_setting_id ] )
    			||
    			! array_key_exists( 'value', $existing_changeset_data[ $prefixed_setting_id ] )
    			||
    			$existing_changeset_data[ $prefixed_setting_id ]['value'] !== $setting_value
    		);
    		if ( $is_value_changed ) {
    			$changed_setting_ids[] = $setting_id;
    		}
    	}

    	/**
    	 * Fires before save validation happens.
    	 *
    	 * Plugins can add just-in-time 'customize_validate_{$this->ID'} filters
    	 * at this point to catch any settings registered after `customize_register`.
    	 * The dynamic portion of the hook name, `$this->ID` refers to the setting ID.
    	 *
    	 * @since 4.6.0
    	 *
    	 * @param WP_Customize_Manager $manager WP_Customize_Manager instance.
    	 */
    	do_action( 'customize_save_validation_before', $this );

    	// Validate settings.
    	$validated_values      = array_merge(
    		array_fill_keys( array_keys( $args['data'] ), null ), // Make sure existence/capability checks are done on value-less setting updates.
    		$post_values
    	);
    	$setting_validities    = $this->validate_setting_values(
    		$validated_values,
    		array(
    			'validate_capability' => true,
    			'validate_existence'  => true,
    		)
    	);
    	$invalid_setting_count = count( array_filter( $setting_validities, 'is_wp_error' ) );

    	/*
    	 * Short-circuit if there are invalid settings the update is transactional.
    	 * A changeset update is transactional when a status is supplied in the request.
    	 */
    	if ( $update_transactionally && $invalid_setting_count > 0 ) {
    		$response = array(
    			'setting_validities' => $setting_validities,
    			/* translators: %s: Number of invalid settings. */
    			'message'            => sprintf( _n( 'Unable to save due to %s invalid setting.', 'Unable to save due to %s invalid settings.', $invalid_setting_count ), number_format_i18n( $invalid_setting_count ) ),
    		);
    		return new WP_Error( 'transaction_fail', '', $response );
    	}

    	// Obtain/merge data for changeset.
    	$original_changeset_data = $this->get_changeset_post_data( $changeset_post_id );
    	$data                    = $original_changeset_data;
    	if ( is_wp_error( $data ) ) {
    		$data = array();
    	}

    	// Ensure that all post values are included in the changeset data.
    	foreach ( $post_values as $setting_id => $post_value ) {
    		if ( ! isset( $args['data'][ $setting_id ] ) ) {
    			$args['data'][ $setting_id ] = array();
    		}
    		if ( ! isset( $args['data'][ $setting_id ]['value'] ) ) {
    			$args['data'][ $setting_id ]['value'] = $post_value;
    		}
    	}

    	foreach ( $args['data'] as $setting_id => $setting_params ) {
    		$setting = $this->get_setting( $setting_id );
    		if ( ! $setting || ! $setting->check_capabilities() ) {
    			continue;
    		}

    		// Skip updating changeset for invalid setting values.
    		if ( isset( $setting_validities[ $setting_id ] ) && is_wp_error( $setting_validities[ $setting_id ] ) ) {
    			continue;
    		}

    		$changeset_setting_id = $setting_id;
    		if ( 'theme_mod' === $setting->type ) {
    			$changeset_setting_id = sprintf( '%s::%s', $this->get_stylesheet(), $setting_id );
    		}

    		if ( null === $setting_params ) {
    			// Remove setting from changeset entirely.
    			unset( $data[ $changeset_setting_id ] );
    		} else {

    			if ( ! isset( $data[ $changeset_setting_id ] ) ) {
    				$data[ $changeset_setting_id ] = array();
    			}

    			// Merge any additional setting params that have been supplied with the existing params.
    			$merged_setting_params = array_merge( $data[ $changeset_setting_id ], $setting_params );

    			// Skip updating setting params if unchanged (ensuring the user_id is not overwritten).
    			if ( $data[ $changeset_setting_id ] === $merged_setting_params ) {
    				continue;
    			}

    			$data[ $changeset_setting_id ] = array_merge(
    				$merged_setting_params,
    				array(
    					'type'              => $setting->type,
    					'user_id'           => $args['user_id'],
    					'date_modified_gmt' => current_time( 'mysql', true ),
    				)
    			);

    			// Clear starter_content flag in data if changeset is not explicitly being updated for starter content.
    			if ( empty( $args['starter_content'] ) ) {
    				unset( $data[ $changeset_setting_id ]['starter_content'] );
    			}
    		}
    	}

    	$filter_context = array(
    		'uuid'          => $this->changeset_uuid(),
    		'title'         => $args['title'],
    		'status'        => $args['status'],
    		'date_gmt'      => $args['date_gmt'],
    		'post_id'       => $changeset_post_id,
    		'previous_data' => is_wp_error( $original_changeset_data ) ? array() : $original_changeset_data,
    		'manager'       => $this,
    	);

    	/**
    	 * Filters the settings' data that will be persisted into the changeset.
    	 *
    	 * Plugins may amend additional data (such as additional meta for settings) into the changeset with this filter.
    	 *
    	 * @since 4.7.0
    	 *
    	 * @param array $data Updated changeset data, mapping setting IDs to arrays containing a $value item and optionally other metadata.
    	 * @param array $context {
    	 *     Filter context.
    	 *
    	 *     @type string               $uuid          Changeset UUID.
    	 *     @type string               $title         Requested title for the changeset post.
    	 *     @type string               $status        Requested status for the changeset post.
    	 *     @type string               $date_gmt      Requested date for the changeset post in MySQL format and GMT timezone.
    	 *     @type int|false            $post_id       Post ID for the changeset, or false if it doesn't exist yet.
    	 *     @type array                $previous_data Previous data contained in the changeset.
    	 *     @type WP_Customize_Manager $manager       Manager instance.
    	 * }
    	 */
    	$data = apply_filters( 'customize_changeset_save_data', $data, $filter_context );

    	// Switch theme if publishing changes now.
    	if ( 'publish' === $args['status'] && ! $this->is_theme_active() ) {
    		// Temporarily stop previewing the theme to allow switch_themes() to operate properly.
    		$this->stop_previewing_theme();
    		switch_theme( $this->get_stylesheet() );
    		update_option( 'theme_switched_via_customizer', true );
    		$this->start_previewing_theme();
    	}

    	// Gather the data for wp_insert_post()/wp_update_post().
    	$post_array = array(
    		// JSON_UNESCAPED_SLASHES is only to improve readability as slashes needn't be escaped in storage.
    		'post_content' => wp_json_encode( $data, JSON_UNESCAPED_SLASHES | JSON_PRETTY_PRINT ),
    	);
    	if ( $args['title'] ) {
    		$post_array['post_title'] = $args['title'];
    	}
    	if ( $changeset_post_id ) {
    		$post_array['ID'] = $changeset_post_id;
    	} else {
    		$post_array['post_type']   = 'customize_changeset';
    		$post_array['post_name']   = $this->changeset_uuid();
    		$post_array['post_status'] = 'auto-draft';
    	}
    	if ( $args['status'] ) {
    		$post_array['post_status'] = $args['status'];
    	}

    	// Reset post date to now if we are publishing, otherwise pass post_date_gmt and translate for post_date.
    	if ( 'publish' === $args['status'] ) {
    		$post_array['post_date_gmt'] = '0000-00-00 00:00:00';
    		$post_array['post_date']     = '0000-00-00 00:00:00';
    	} elseif ( $args['date_gmt'] ) {
    		$post_array['post_date_gmt'] = $args['date_gmt'];
    		$post_array['post_date']     = get_date_from_gmt( $args['date_gmt'] );
    	} elseif ( $changeset_post_id && 'auto-draft' === get_post_status( $changeset_post_id ) ) {
    		/*
    		 * Keep bumping the date for the auto-draft whenever it is modified;
    		 * this extends its life, preserving it from garbage-collection via
    		 * wp_delete_auto_drafts().
    		 */
    		$post_array['post_date']     = current_time( 'mysql' );
    		$post_array['post_date_gmt'] = '';
    	}

    	$this->store_changeset_revision = $allow_revision;
    	add_filter( 'wp_save_post_revision_post_has_changed', array( $this, '_filter_revision_post_has_changed' ), 5, 3 );

    	/*
    	 * Update the changeset post. The publish_customize_changeset action will cause the settings in the
    	 * changeset to be saved via WP_Customize_Setting::save(). Updating a post with publish status will
    	 * trigger WP_Customize_Manager::publish_changeset_values().
    	 */
    	add_filter( 'wp_insert_post_data', array( $this, 'preserve_insert_changeset_post_content' ), 5, 3 );
    	if ( $changeset_post_id ) {
    		if ( $args['autosave'] && 'auto-draft' !== get_post_status( $changeset_post_id ) ) {
    			// See _wp_translate_postdata() for why this is required as it will use the edit_post meta capability.
    			add_filter( 'map_meta_cap', array( $this, 'grant_edit_post_capability_for_changeset' ), 10, 4 );

    			$post_array['post_ID']   = $post_array['ID'];
    			$post_array['post_type'] = 'customize_changeset';

    			$r = wp_create_post_autosave( wp_slash( $post_array ) );

    			remove_filter( 'map_meta_cap', array( $this, 'grant_edit_post_capability_for_changeset' ), 10 );
    		} else {
    			$post_array['edit_date'] = true; // Prevent date clearing.

    			$r = wp_update_post( wp_slash( $post_array ), true );

    			// Delete autosave revision for user when the changeset is updated.
    			if ( ! empty( $args['user_id'] ) ) {
    				$autosave_draft = wp_get_post_autosave( $changeset_post_id, $args['user_id'] );
    				if ( $autosave_draft ) {
    					wp_delete_post( $autosave_draft->ID, true );
    				}
    			}
    		}
    	} else {
    		$r = wp_insert_post( wp_slash( $post_array ), true );
    		if ( ! is_wp_error( $r ) ) {
    			$this->_changeset_post_id = $r; // Update cached post ID for the loaded changeset.
    		}
    	}
    	remove_filter( 'wp_insert_post_data', array( $this, 'preserve_insert_changeset_post_content' ), 5 );

    	$this->_changeset_data = null; // Reset so WP_Customize_Manager::changeset_data() will re-populate with updated contents.

    	remove_filter( 'wp_save_post_revision_post_has_changed', array( $this, '_filter_revision_post_has_changed' ) );

    	$response = array(
    		'setting_validities' => $setting_validities,
    	);

    	if ( is_wp_error( $r ) ) {
    		$response['changeset_post_save_failure'] = $r->get_error_code();
    		return new WP_Error( 'changeset_post_save_failure', '', $response );
    	}

    	return $response;
    }
    ```

[View all references](https://developer.wordpress.org/reference/files/wp-includes/class-wp-customize-manager.php/)
[View on Trac](https://core.trac.wordpress.org/browser/tags/7.0/src/wp-includes/class-wp-customize-manager.php#L2640)
[View on GitHub](https://github.com/WordPress/wordpress-develop/blob/7.0/src/wp-includes/class-wp-customize-manager.php#L2640-L3007)

## 󠀁[Hooks](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#hooks)󠁿

 [apply_filters( ‘customize_changeset_save_data’, array $data, array $context )](https://developer.wordpress.org/reference/hooks/customize_changeset_save_data/)

Filters the settings’ data that will be persisted into the changeset.

 [do_action( ‘customize_save_validation_before’, WP_Customize_Manager $manager )](https://developer.wordpress.org/reference/hooks/customize_save_validation_before/)

Fires before save validation happens.

## 󠀁[Related](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#related)󠁿

| Uses | Description | 
| [WP_Customize_Manager::changeset_post_id()](https://developer.wordpress.org/reference/classes/wp_customize_manager/changeset_post_id/)`wp-includes/class-wp-customize-manager.php` |

Gets the changeset post ID for the loaded changeset.

  | 
| [WP_Customize_Manager::get_changeset_post_data()](https://developer.wordpress.org/reference/classes/wp_customize_manager/get_changeset_post_data/)`wp-includes/class-wp-customize-manager.php` |

Gets the data stored in a changeset post.

  | 
| [WP_Customize_Manager::changeset_uuid()](https://developer.wordpress.org/reference/classes/wp_customize_manager/changeset_uuid/)`wp-includes/class-wp-customize-manager.php` |

Gets the changeset UUID.

  | 
| [wp_generate_uuid4()](https://developer.wordpress.org/reference/functions/wp_generate_uuid4/)`wp-includes/functions.php` |

Generates a random UUID (version 4).

  | 
| [WP_Customize_Manager::validate_setting_values()](https://developer.wordpress.org/reference/classes/wp_customize_manager/validate_setting_values/)`wp-includes/class-wp-customize-manager.php` |

Validates setting values.

  | 
| [WP_Customize_Manager::add_dynamic_settings()](https://developer.wordpress.org/reference/classes/wp_customize_manager/add_dynamic_settings/)`wp-includes/class-wp-customize-manager.php` |

Registers any dynamically-created settings, such as those from $_POST[‘customized’] that have no corresponding setting created.

  | 
| [WP_Customize_Manager::set_post_value()](https://developer.wordpress.org/reference/classes/wp_customize_manager/set_post_value/)`wp-includes/class-wp-customize-manager.php` |

Overrides a setting’s value in the current customized state.

  | 
| [WP_Customize_Manager::unsanitized_post_values()](https://developer.wordpress.org/reference/classes/wp_customize_manager/unsanitized_post_values/)`wp-includes/class-wp-customize-manager.php` |

Gets dirty pre-sanitized setting values in the current customized state.

  | 
| [wp_create_post_autosave()](https://developer.wordpress.org/reference/functions/wp_create_post_autosave/)`wp-admin/includes/post.php` |

Creates autosave data for the specified post from `$_POST` data.

  | 
| [WP_Customize_Manager::get_setting()](https://developer.wordpress.org/reference/classes/wp_customize_manager/get_setting/)`wp-includes/class-wp-customize-manager.php` |

Retrieves a customize setting.

  | 
| [WP_Customize_Manager::get_stylesheet()](https://developer.wordpress.org/reference/classes/wp_customize_manager/get_stylesheet/)`wp-includes/class-wp-customize-manager.php` |

Retrieves the stylesheet name of the previewed theme.

  | 
| [WP_Customize_Manager::is_theme_active()](https://developer.wordpress.org/reference/classes/wp_customize_manager/is_theme_active/)`wp-includes/class-wp-customize-manager.php` |

Checks if the current theme is active.

  | 
| [WP_Customize_Manager::stop_previewing_theme()](https://developer.wordpress.org/reference/classes/wp_customize_manager/stop_previewing_theme/)`wp-includes/class-wp-customize-manager.php` |

Stops previewing the selected theme.

  | 
| [WP_Customize_Manager::start_previewing_theme()](https://developer.wordpress.org/reference/classes/wp_customize_manager/start_previewing_theme/)`wp-includes/class-wp-customize-manager.php` |

If the theme to be previewed isn’t the active theme, add filter callbacks to swap it out at runtime.

  | 
| [switch_theme()](https://developer.wordpress.org/reference/functions/switch_theme/)`wp-includes/theme.php` |

Switches the theme.

  | 
| [_n()](https://developer.wordpress.org/reference/functions/_n/)`wp-includes/l10n.php` |

Translates and retrieves the singular or plural form based on the supplied number.

  | 
| [get_date_from_gmt()](https://developer.wordpress.org/reference/functions/get_date_from_gmt/)`wp-includes/formatting.php` |

Given a date in UTC or GMT timezone, returns that date in the timezone of the site.

  | 
| [mysql2date()](https://developer.wordpress.org/reference/functions/mysql2date/)`wp-includes/functions.php` |

Converts given MySQL date string into a different format.

  | 
| [current_time()](https://developer.wordpress.org/reference/functions/current_time/)`wp-includes/functions.php` |

Retrieves the current time based on specified type.

  | 
| [has_action()](https://developer.wordpress.org/reference/functions/has_action/)`wp-includes/plugin.php` |

Checks if any action has been registered for a hook.

  | 
| [wp_update_post()](https://developer.wordpress.org/reference/functions/wp_update_post/)`wp-includes/post.php` |

Updates a post with new post data.

  | 
| [wp_insert_post()](https://developer.wordpress.org/reference/functions/wp_insert_post/)`wp-includes/post.php` |

Inserts or updates a post in the database.

  | 
| [wp_delete_post()](https://developer.wordpress.org/reference/functions/wp_delete_post/)`wp-includes/post.php` |

Trashes or deletes a post or page.

  | 
| [get_post_status()](https://developer.wordpress.org/reference/functions/get_post_status/)`wp-includes/post.php` |

Retrieves the post status based on the post ID.

  | 
| [wp_get_post_autosave()](https://developer.wordpress.org/reference/functions/wp_get_post_autosave/)`wp-includes/revision.php` |

Retrieves the autosaved data of the specified post.

  | 
| [wp_json_encode()](https://developer.wordpress.org/reference/functions/wp_json_encode/)`wp-includes/functions.php` |

Encodes a variable into JSON, with some confidence checks.

  | 
| [__()](https://developer.wordpress.org/reference/functions/__/)`wp-includes/l10n.php` |

Retrieves the translation of $text.

  | 
| [wp_slash()](https://developer.wordpress.org/reference/functions/wp_slash/)`wp-includes/formatting.php` |

Adds slashes to a string or recursively adds slashes to strings within an array.

  | 
| [number_format_i18n()](https://developer.wordpress.org/reference/functions/number_format_i18n/)`wp-includes/functions.php` |

Converts float number to format based on the locale.

  | 
| [do_action()](https://developer.wordpress.org/reference/functions/do_action/)`wp-includes/plugin.php` |

Calls the callback functions that have been added to an action hook.

  | 
| [apply_filters()](https://developer.wordpress.org/reference/functions/apply_filters/)`wp-includes/plugin.php` |

Calls the callback functions that have been added to a filter hook.

  | 
| [add_filter()](https://developer.wordpress.org/reference/functions/add_filter/)`wp-includes/plugin.php` |

Adds a callback function to a filter hook.

  | 
| [remove_filter()](https://developer.wordpress.org/reference/functions/remove_filter/)`wp-includes/plugin.php` |

Removes a callback function from a filter hook.

  | 
| [update_option()](https://developer.wordpress.org/reference/functions/update_option/)`wp-includes/option.php` |

Updates the value of an option that was already added.

  | 
| [get_current_user_id()](https://developer.wordpress.org/reference/functions/get_current_user_id/)`wp-includes/user.php` |

Gets the current user’s ID.

  | 
| [get_post()](https://developer.wordpress.org/reference/functions/get_post/)`wp-includes/post.php` |

Retrieves post data given a post ID or post object.

  | 
| [is_wp_error()](https://developer.wordpress.org/reference/functions/is_wp_error/)`wp-includes/load.php` |

Checks whether the given variable is a WordPress Error.

  | 
| [WP_Error::__construct()](https://developer.wordpress.org/reference/classes/wp_error/__construct/)`wp-includes/class-wp-error.php` |

Initializes the error.

  |

[Show 33 more](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#)
[Show less](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#)

| Used by | Description | 
| [WP_Customize_Manager::_save_starter_content_changeset()](https://developer.wordpress.org/reference/classes/wp_customize_manager/_save_starter_content_changeset/)`wp-includes/class-wp-customize-manager.php` |

Saves starter content changeset.

  | 
| [WP_Customize_Manager::save()](https://developer.wordpress.org/reference/classes/wp_customize_manager/save/)`wp-includes/class-wp-customize-manager.php` |

Handles customize_save WP Ajax request to save/update a changeset.

  |

## 󠀁[Changelog](https://developer.wordpress.org/reference/classes/WP_Customize_Manager/save_changeset_post/?output_format=md#changelog)󠁿

| Version | Description | 
| [4.7.0](https://developer.wordpress.org/reference/since/4.7.0/) | Introduced. |

## User Contributed Notes

You must [log in](https://login.wordpress.org/?redirect_to=https%3A%2F%2Fdeveloper.wordpress.org%2Freference%2Fclasses%2Fwp_customize_manager%2Fsave_changeset_post%2F)
before being able to contribute a note or feedback.