以前提交数据的两种方式:
- 直接使用form表单(缺点:提交页面会刷新)
- ajax、fetch(缺点:需要塞东西)
表单:
所有向服务器提交的HTTP数据,其实都是一个表单
FormData是一种容器,用于模拟表单,向服务器提交数据,有两种使用方法
- 创建空白FormData对象,然后向其中添加数据
- 将<form>标签直接转换为一个FormData对象
服务端:
和处理普通表单一样
服务器端代码:
const Koa = require("koa");
const Router = require("koa-router");
const body = require("koa-better-body");
const convert = require("koa-convert");
const static = require("koa-static");
const path = require("path");
const opn = require("opn");
let router = new Router();
let server = new Koa();
server.listen(8000);
// post
server.use(convert(
body({
uploadDir: path.resolve(__dirname, 'upload')
})
));
// router
router.post('/a', async ctx=>{
console.log(ctx.request.fields);
ctx.body="ok";
})
server.use(router.routes());
// static
server.use(static('./static'));
opn("http://localhost:8000/1.html")
第一种用法:创建空白FormData对象,然后向其中添加数据
1.html
使用原生:
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>FormData</title>
</head>
<body>
I'm FormData.
<script>
// 1. 构建容器 并向容器添加东西
let form = new FormData();
form.append('name', 'enoch');
form.append('password', 'yuxi0000');
// 2. 使用ajax发送
let xhr = new XMLHttpRequest();
xhr.open('POST', '/a'); // method and address
xhr.send(form); // 直接使用form即可
// 3. 等待返回
xhr.onreadystatechange=function() {
if(xhr.readyState==4){
if(xhr.status >= 200 && xhr.status < 300 || xhr.status == 304) {
alert(xhr.responseText)
}else{
alert("失败");
}
}
}
</script>
</body>
</html>
实现了,也接受到内容了。
使用fetch:
代码:
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>FormData</title>
</head>
<body>
I'm FormData.
<script>
// 1. 构建容器 并向容器添加东西
let form = new FormData();
form.append('name', 'enoch');
form.append('password', 'yuxi0000');
// 2. 使用fetch发送
(async ()=>{
let res = await fetch('/a', {
method: 'post',
body: form
});
let data = await res.text(); // 返回的服务器的respone对象
alert(data)
})();
</script>
</body>
</html>
也成功了。
$.ajax:
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>FormData</title>
</head>
<body>
I'm FormData.
<script src="http://code.jquery.com/jquery-3.4.1.js"></script>
<script>
// 1. 构建容器 并向容器添加东西
let form = new FormData();
form.append('name', 'enoch');
form.append('password', 'yuxi0000');
// 2. 使用jquery的ajax发送
( async () =>{
let data = await $.ajax({
url: '/a',
type: 'post',
data: form,
processData: false, // 不要处理数据 , jq默认会按json方式处理数据
contentType: false, // 提交类型 默认会使用urlencoding提交数据
})
alert(data);
})();
</script>
</body>
</html>
也成功了。
axios也成功了:
// 1. 构建容器 并向容器添加东西
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>FormData</title>
</head>
<body>
I'm FormData.
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
<script>
// 1. 构建容器 并向容器添加东西
let form = new FormData();
form.append('name', 'enoch');
form.append('password', 'yuxi0000');
// 2. 使用axios
(async () =>{
let {data} = await axios({
url: '/a',
method: 'post',
data: form,
});
// 结果很多,需要解构赋值
alert(data);
})();
</script>
</body>
</html>
FormData的两大好处:
- 不需要频繁的处理数据
- 跟主流的东西都搭
第二种用法: 将<form>标签直接转换为一个FormData对象
使用fetch和FormData的结合:
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>FormData</title>
</head>
<body>
<p>I'm FormData.</p>
<form id="form1">
用户名:<input type="text" name="name"/><br/>
密码:<input type="password" name="pass"><br />
<input type="button" value="提交" id="btn1">
</form>
<script>
let oBtn = document.getElementById("btn1");
oBtn.onclick = async function() {
let form = new FormData(document.getElementById('form1'));
let res = await fetch('/a', {
method: 'post',
body: form
});
let data = await res.text();
alert(data);
}
</script>
</body>
</html>
成功
input选择文件要在后面加.files