您好我是React.js和typescript的新手。我正在尝试上传一个简单的文件以及简单的输入。
我查看了与网络上的文件上传或输入元素事件相关的一些示例(ex1,ex2,ex3),但我无法使其中任何一个工作。< / p>
这是我的tsx文件。
import * as React from 'react';
//import * as $ from "jquery";
import { RouteComponentProps } from 'react-router';
import { Button, Form, FormGroup, Label, Input, FormText } from 'reactstrap';
interface UploadContainerState {
tcknVkn: number;
proclamationYear: number;
file: FileList|null;
}
export default class UploadContainer extends React.Component<{}, UploadContainerState> {
constructor(props: any) {
super(props);
this.state = {
proclamationYear: 0,
tcknVkn: 0,
file: null
}
this.proclamationYearChange = this.proclamationYearChange.bind(this);
this.tcknVknChange = this.tcknVknChange.bind(this);
this.uploadFile = this.uploadFile.bind(this);
this.fileChange = this.fileChange.bind(this);
}
proclamationYearChange(event: any) {
this.setState({ proclamationYear: event.target.value });
}
tcknVknChange(event: any) {
this.setState({ tcknVkn: event.target.value });
}
fileChange(event: any) {
this.setState({ file: event.target.files[0] });
}
render() {
return (
<div>
<form className="uploader" encType="multipart/form-data" >
<br />
<FormGroup>
<Label for="proclamationYear">Beyanname Yılı</Label>
<Input type="text" name="proclamationYear" id="proclamationYear" placeholder="Beyanname Yılını Giriniz." onChange={this.proclamationYearChange} value={this.state.proclamationYear} />
</FormGroup>
<FormGroup>
<Label for="tcknVkn">Tckn/Vkn</Label>
<Input type="text" name="tcknVkn" id="tcknVkn" placeholder="Tckn/Vkn Giriniz." onChange={this.tcknVknChange} value={this.state.tcknVkn} />
</FormGroup>
<input type="file" name="file" className="upload-file" onChange={this.fileChange} value={this.state.file} />
<input type="button" value="Beyanname Yükle" onClick={this.uploadFile} />
</form>
</div>
);
}
uploadFile(event: any) {
event.preventDefault();
let formData = new FormData();
formData.append('file', event.target.myimage.files[0]);
formData.append('tcknVkn', event.target.tcknVkn.value);
formData.append('proclamationYear', event.target.proclamationYear.value);
fetch('ProposalData/UploadFile', {
method: 'POST',
credentials: 'include',
headers: {
'Content-Type': 'multipart/form-data',
'Accept': 'application/json'
},
body: formData
})
}
};
我收到以下错误。
ERROR in [at-loader] ./ClientApp/components/UploadContainer.tsx:50:29
TS2322: Type '{ type: "file"; name: "file"; className: "upload-file"; onChange: (event: any) => void; value: Fi...' is not assignable to type 'DetailedHTMLProps<InputHTMLAttributes<HTMLInputElement>, HTMLInputElement>'.
Type '{ type: "file"; name: "file"; className: "upload-file"; onChange: (event: any) => void; value: Fi...' is not assignable to type 'InputHTMLAttributes<HTMLInputElement>'.
Types of property 'value' are incompatible.
Type 'FileList | null' is not assignable to type 'string | number | string[] | undefined'.
Type 'null' is not assignable to type 'string | number | string[] | undefined'.
这是我的打字稿版本5.6.0
我无法理解这样轻松的任务怎么会成为一场噩梦。
答案 0 :(得分:1)
您的值属性类型不匹配。您在传递string | number | string[] | undefined
FileList
由于安全原因,您无法设置文件输入的值。设置文件输入值的唯一方法是通过浏览器中的用户操作。删除value={this.state.file}
,它将编译。
除此之外,州字段的类型应为File
答案 1 :(得分:1)
我知道这不是最佳解决方案。但这里是完整的后端和前端代码,适合那些尝试使用.net core,react.js和typescript完成相同任务的人。
这是我的tsx文件说明我在界面中注释了文件属性并将其设为公共属性。
import * as React from 'react';
import { RouteComponentProps } from 'react-router';
import { Button, Form, FormGroup, Label, Input, FormText } from 'reactstrap';
import ListGroup from 'reactstrap/lib/ListGroup';
interface UploadContainerState {
tcknVkn: number;
proclamationYear: number;
alertVisible: boolean;
//file: FileList
}
export default class UploadContainer extends React.Component<{}, UploadContainerState> {
public file: File;
constructor(props: any) {
super(props);
this.state = {
proclamationYear: 0,
tcknVkn: 0,
alertVisible: false
}
this.proclamationYearChange = this.proclamationYearChange.bind(this);
this.tcknVknChange = this.tcknVknChange.bind(this);
this.uploadFile = this.uploadFile.bind(this);
this.fileChange = this.fileChange.bind(this);
}
proclamationYearChange(event: any) {
this.setState({ proclamationYear: event.target.value });
}
tcknVknChange(event: any) {
this.setState({ tcknVkn: event.target.value });
}
onDismiss() {
this.setState({ alertVisible: false });
}
fileChange(event: any) {
this.file = event.target.files[0];
event.preventDefault();
}
render() {
return (
<div>
<form onSubmit={this.uploadFile} className="uploader" encType="multipart/form-data" >
<FormGroup>
<Label for="proclamationYear">Year</Label>
<Input type="text" name="proclamationYear" id="proclamationYear" onChange={this.proclamationYearChange} value={this.state.proclamationYear} />
</FormGroup>
<FormGroup>
<Label for="tcknVkn">Tckn/Vkn</Label>
<Input type="text" name="tcknVkn" id="tcknVkn" onChange={this.tcknVknChange} value={this.state.tcknVkn} />
</FormGroup>
<input type="file" name="file" accept=".pdf" className="upload-file" onChange={this.fileChange} />
<input type="submit" value="Submit" />
</form>
</div>
);
}
uploadFile(event: any) {
let that = this;
event.preventDefault();
let formData = new FormData();
formData.append('file', this.file);
formData.append('tcknVkn', event.target.tcknVkn.value);
formData.append('proclamationYear', event.target.proclamationYear.value);
fetch("ProposalData/UploadFile", {
method: 'POST',
credentials: 'include',
headers: {
'Accept': 'application/json, */*',
},
body: formData
})
.then(handleErrors)
.then(function (response) {
console.log("ok");
}).catch(function (error) {
console.log(error);
});
}
};
function handleErrors(response: any) {
if (!response.ok) {
throw Error(response.statusText);
}
return response;
}
这是我的控制器
public class FileUploadModel
{
public string ProclamationYear { get; set; }
public string TcknVkn { get; set; }
public IFormFile File { get; set; }
}
[HttpPost]
public async Task<IActionResult> UploadFile([FromForm]FileUploadModel vm)
{
var file = vm.File;