I built custom React/Gatsby multipart form with file upload and I want to send all form data to WordPress endpoint, upload files to specific folder and display all of the data in the WordPress backend.
This is how I send data:
const {
stepOne,
stepTwo,
} = useContext(FormStepProvider)
const steps = {
stepOne: stepOne,
stepTwo: stepTwo,
}
const postData = async () => {
const formData = new FormData()
formData.append("stepOne", JSON.stringify(stepOne))
formData.append("stepTwo", stepTwo.file)
await fetch(";, {
method: "POST",
headers: {
"Content-Type": "multipart/form-data",
},
body: formData,
})
.then(response => response)
.then(result => {
console.log("Success:", result)
})
.catch(error => {
console.error("Error:", error)
})
}
useEffect(() => {
postData()
console.log(steps)
}, [])
This is the response I get:
This is my endpoint:
add_action( 'rest_api_init', function () {
register_rest_route( 'test/v1', 'forms', array(
'methods' => 'POST',
'callback' => 'get_formdata_function',
'args' => array(),
) );
} );
function get_formdata_function(WP_REST_Request $request)
{
$data = $request->get_body();
print_r($data);
}
I'm new to WordPress and I want to know what's the best way to do this?
I built custom React/Gatsby multipart form with file upload and I want to send all form data to WordPress endpoint, upload files to specific folder and display all of the data in the WordPress backend.
This is how I send data:
const {
stepOne,
stepTwo,
} = useContext(FormStepProvider)
const steps = {
stepOne: stepOne,
stepTwo: stepTwo,
}
const postData = async () => {
const formData = new FormData()
formData.append("stepOne", JSON.stringify(stepOne))
formData.append("stepTwo", stepTwo.file)
await fetch("https://panel.domain.com/wp-json/test/v1/forms", {
method: "POST",
headers: {
"Content-Type": "multipart/form-data",
},
body: formData,
})
.then(response => response)
.then(result => {
console.log("Success:", result)
})
.catch(error => {
console.error("Error:", error)
})
}
useEffect(() => {
postData()
console.log(steps)
}, [])
This is the response I get:
This is my endpoint:
add_action( 'rest_api_init', function () {
register_rest_route( 'test/v1', 'forms', array(
'methods' => 'POST',
'callback' => 'get_formdata_function',
'args' => array(),
) );
} );
function get_formdata_function(WP_REST_Request $request)
{
$data = $request->get_body();
print_r($data);
}
I'm new to WordPress and I want to know what's the best way to do this?
Share Improve this question edited Feb 9, 2022 at 12:11 Andy Macaulay-Brook 3,8593 gold badges19 silver badges44 bronze badges asked Sep 10, 2021 at 6:53 FrostbournFrostbourn 1031 silver badge4 bronze badges1 Answer
Reset to default 2So I don't know what stepTwo.file
is, but I presumed it's a File
object instance, and I believe the issue here is that you're not aware that you didn't actually need to manually set the Content-Type
header because when the request body is a FormData
instance, then the content type header will always default to multipart/form-data
.
Therefore just get rid of that header from the headers
list in your fetch()
call and then in your endpoint callback, use WP_REST_Request::get_file_params()
to get the uploaded file data (name, temporary path, size, etc.). So for example, you could do $request->get_file_params()['stepTwo']
. ($_FILES['stepTwo']
would also work, but I'd use the class method)
As for the stepOne
parameter (which would be stored in the $_POST
array), you could simply do $request['stepOne']
to get the value, or you could also do $request->get_param( 'stepOne' )
.
See https://developer.wordpress.org/rest-api/extending-the-rest-api/adding-custom-endpoints/#arguments for more details.
Additionally, you should always set permission_callback
, so for example if your REST API endpoint is public, you could do 'permission_callback' => '__return_true'
.