使用 FormData 将数据从 Vue 传递到 Laravel 的整数问题
Issue with Integers passing data from Vue to Laravel using FormData
我成功地将使用 Vue 2 的数据库更新为使用 Axios 的 Laravel 8 控制器。但是,我在尝试将整数传递到我的数据库时卡住了。
我的数据库有一列,'number_of_searches',它必须是一个整数。
Laravel 迁移看起来像这样:
$table->integer('number_of_searches')->nullable();
模型看起来像这样:
class Product extends Model
{
protected $fillable = [
'product_title',
'number_of_searches' => 'integer',
];
}
我的 Vue updateProduct() 函数使用了 FormData 并附加了来自表单的值。它看起来像这样:
updateProduct(product){
let data = new FormData();
data.append('_method', 'PATCH');
data.append('product_title', product.product_title);
data.append('number_of_searches', product.number_of_searches);
axios.post('/api-route-to-update/product_id/', data)
.then(function (response) {
console.log(response);
})
.catch(function (error) {
console.log(error);
});
}
我的更新控制器是这样的:
public function update(Request $request, $product_id){
$product = Product::findOrFail($product_id);
$product->update($request->all());
$product->save();
}
我可以有任意多的输入字段,只要它们是字符串,它就可以完美地工作。但是,当我在组件中使用数字输入字段时,例如:
<input v-model="product.number_of_searches" type="number" min="1" max="999">
将从 axios 传递到我的控制器的生成的 json 如下所示:
{ "id": 5, "product_title": "The Product Title will work great", "number_of_searches": "222"}
您会注意到 'number_of_searches' 作为字符串传递,因此我的数据库失败,因为它是错误的数据类型,它需要一个整数。阅读文档和其他线程后,FormData 似乎总是 return 字符串,我必须在服务器端处理它。
所以我所做的是进入后端 updateProduct() 方法并尝试修改请求。
首先我尝试了一些方法,例如:
//this one
$requestData = $request->all();
$requestData['number_of_searches'] = 123;
//also this one
$request->merge(['number_of_searches' => 123]);
//and this
$data = $request->all();
$data['number_of_searches'] = 123;
无数小时后,我无法修改原始请求。经过一番研究,似乎请求是受保护的,不能修改,这是有道理的。因此,我尝试创建一个克隆 $request->all() 的新请求,如下所示:
$new_request = new Request($request->all());
$new_request->merge(['number_of_searches' => 123]);
但是我强制覆盖失败了'number_of_searched'
我的问题是:
在这种情况下我应该完全远离 FormData 吗?您建议使用什么方法通过 axios 或 fetch 传递具有整数或浮点数或其他数据类型的表单?或者我做错了什么?我很难相信 FormData 只会发送字符串(在使用 axios 之前使 parseInt 无用)。我确定我从一开始就做错了。
另一方面,也许我需要在接收数据时完全改变我在控制器中的方法。我正在开发一个包含很多字段的应用程序,我喜欢 $request->all() 因为它简化了我想做的事情。我不介意在服务器端使用 intval,仅此而已,但它似乎过于复杂。
在 Vue 方面,您可以在 v-model
上使用 number
修饰符以确保它不会将值转换为字符串:
v-model.number="product.number_of_searches"
在请求端,您可以使用$request->merge
覆盖请求中的值
$request->merge([
'number_of_searches' => (int) $request->get('number_of_searches');
]);
在 boot
方法中 updating
挂钩的模型端,您可以确保在保存时将值转换为 int:
static::updating(function ($model) {
$model->number_of_searches = (int) $model->number_of_searches;
});
这应该给你一个完整的结尾。
我成功地将使用 Vue 2 的数据库更新为使用 Axios 的 Laravel 8 控制器。但是,我在尝试将整数传递到我的数据库时卡住了。
我的数据库有一列,'number_of_searches',它必须是一个整数。
Laravel 迁移看起来像这样:
$table->integer('number_of_searches')->nullable();
模型看起来像这样:
class Product extends Model
{
protected $fillable = [
'product_title',
'number_of_searches' => 'integer',
];
}
我的 Vue updateProduct() 函数使用了 FormData 并附加了来自表单的值。它看起来像这样:
updateProduct(product){
let data = new FormData();
data.append('_method', 'PATCH');
data.append('product_title', product.product_title);
data.append('number_of_searches', product.number_of_searches);
axios.post('/api-route-to-update/product_id/', data)
.then(function (response) {
console.log(response);
})
.catch(function (error) {
console.log(error);
});
}
我的更新控制器是这样的:
public function update(Request $request, $product_id){
$product = Product::findOrFail($product_id);
$product->update($request->all());
$product->save();
}
我可以有任意多的输入字段,只要它们是字符串,它就可以完美地工作。但是,当我在组件中使用数字输入字段时,例如:
<input v-model="product.number_of_searches" type="number" min="1" max="999">
将从 axios 传递到我的控制器的生成的 json 如下所示:
{ "id": 5, "product_title": "The Product Title will work great", "number_of_searches": "222"}
您会注意到 'number_of_searches' 作为字符串传递,因此我的数据库失败,因为它是错误的数据类型,它需要一个整数。阅读文档和其他线程后,FormData 似乎总是 return 字符串,我必须在服务器端处理它。
所以我所做的是进入后端 updateProduct() 方法并尝试修改请求。
首先我尝试了一些方法,例如:
//this one
$requestData = $request->all();
$requestData['number_of_searches'] = 123;
//also this one
$request->merge(['number_of_searches' => 123]);
//and this
$data = $request->all();
$data['number_of_searches'] = 123;
无数小时后,我无法修改原始请求。经过一番研究,似乎请求是受保护的,不能修改,这是有道理的。因此,我尝试创建一个克隆 $request->all() 的新请求,如下所示:
$new_request = new Request($request->all());
$new_request->merge(['number_of_searches' => 123]);
但是我强制覆盖失败了'number_of_searched'
我的问题是:
在这种情况下我应该完全远离 FormData 吗?您建议使用什么方法通过 axios 或 fetch 传递具有整数或浮点数或其他数据类型的表单?或者我做错了什么?我很难相信 FormData 只会发送字符串(在使用 axios 之前使 parseInt 无用)。我确定我从一开始就做错了。
另一方面,也许我需要在接收数据时完全改变我在控制器中的方法。我正在开发一个包含很多字段的应用程序,我喜欢 $request->all() 因为它简化了我想做的事情。我不介意在服务器端使用 intval,仅此而已,但它似乎过于复杂。
在 Vue 方面,您可以在 v-model
上使用 number
修饰符以确保它不会将值转换为字符串:
v-model.number="product.number_of_searches"
在请求端,您可以使用$request->merge
覆盖请求中的值
$request->merge([
'number_of_searches' => (int) $request->get('number_of_searches');
]);
在 boot
方法中 updating
挂钩的模型端,您可以确保在保存时将值转换为 int:
static::updating(function ($model) {
$model->number_of_searches = (int) $model->number_of_searches;
});
这应该给你一个完整的结尾。