我正在尝试从Angular 2前端上传文件和其他表单字段内容到Spring后端。但不知怎的,我无法做到。这是我的代码:
app.component.ts
fileChange(e){
this.fileList = e.target.files;
}
uploadPdf(){
if(this.fileList.length>0){
let file: File = this.fileList[0];
let formData:FormData = new FormData();
formData.append('uploadFile', file, file.name);
formData.append('info',this.model);
console.log(file.size);
let headers = new Headers();
headers.append('Accept', 'application/json');
let options = new RequestOptions({ headers: headers });
this.http.post(this.url,formData, options)
/*.map((res: Response) => res.json())*/
.catch(error => Observable.throw(error))
.subscribe(
data =>{
this.data = data;
console.log(this.data);
}
,
error => console.log(error)
)
}
}
app.cmoponent.html
<h1 class="text-center">
PDF Viewer and Uploader Example
</h1>
<div class="text-center">
<form enctype="multipart/form-data">
<div class="form-group">
<label for="name">Name: </label>
<input type="text" id="name" class="form-control" name="name" [(ngModel)]="model.name">
</div>
<div class="form-group">
<label for="email">Email: </label>
<input type="email" id="email" class="form-control" name="email" [(ngModel)]="model.email">
</div>
<div class="form-group">
<label for="pdfInput">Select File: </label>
<input type="file" id="pdfInput" class="form-control" name="pdfInput" (change)="fileChange($event)">
</div>
<div class="form-group">
<button type="button" class="btn btn-success" (click)="uploadPdf()">Upload File!</button><span> </span>
<button type="button" class="btn btn-success" (click)="printData()">Print to Console!</button>
</div>
</form>
</div>
model.ts
export class Model{
name: string;
email: string;
}
现在在后端:
ExampleModel.java
public class ExampleModel {
private String name;
private String email;
//Getters and Setters
MainController.java
@RequestMapping(value = "/file",method = RequestMethod.POST)
@ResponseBody
public ResponseEntity<String> addUser(@RequestParam("uploadFile") MultipartFile file, @RequestParam("info") ExampleModel model){}
那么,如何在弹簧控制器中获得info
标记数据?上面我已经展示了我的错误尝试,获取其他表单字段数据的正确方法是什么?
如何定义带注释的Controller方法,或者是否有其他方式从Angular 2发送数据(文件+表单字段)?
答案 0 :(得分:6)
您需要使用@RequestPart
代替@RequestParam
并设置consumes
属性:
@RequestMapping(value = "/file",method = RequestMethod.POST, consumes = "multipart/form-data")
@ResponseBody
public ResponseEntity<String> addUser(@RequestPart("uploadFile") MultipartFile file, @RequestPart("info") ExampleModel model){}
您还需要调整FormData
对象:
formData.append('uploadFile', file, file.name);
formData.append('info', new Blob([JSON.stringify(this.model)],
{
type: "application/json"
}));
答案 1 :(得分:1)
我正在尝试使用formData将myobject和一个文件形式的角度2发送到websphere上的spring mvc deploed:
ao.component.ts是:
let input=new FormData();
input.append('appelOffre', new Blob([JSON.stringify(appelOffre)],
{
type: "application/json"
}));
input.append('compteRendu',file);
this._aoService.uploadAppelOffre(input)
.subscribe(
data => console.log('success'),
error => console.log(error)
);
服务是:
uploadAppelOffre(input : FormData): Observable<number>{
const headers = new Headers();
const cpHeaders = new Headers({ 'Content-Type': 'application/json' });
const options = new RequestOptions({ headers: cpHeaders });
return this.http.post(this.uploadUrl, input, options)
.map(this.extractData)
.catch(error => Observable.throw(error))
}
我的春季服务是:@RequestMapping(value="uploadfile", method=RequestMethod.POST, consumes={"multipart/form-data"} )
@ResponseBody
public ResponseEntity<Void> addFile(@RequestPart("compteRendu") MultipartFile file, @RequestPart("appelOffre") AppelOffre ao){
if(!file.isEmpty()){
System.out.println("accepted: "+file.getOriginalFilename());
File convFile = new File( file.getOriginalFilename());
try {
file.transferTo(convFile);
ao.setLien_alfresco_cr(convFile.getAbsolutePath());
// service.addAppelOffre(ao);
} catch (IOException e) {
e.printStackTrace();
}
}
return new ResponseEntity<Void>(HttpStatus.CREATED);
}
现在使用tomcat和mysql它运行正常,但是一旦在web领域发现我得到了问题:[03/01/18 10:21:50:148 GMT] 0000008c srt W com.ibm.ws.webcontainer.srt .SRTServletResponse setHeader SRVE8094W:AVERTISSEMENT:Impossiblededéfinirl'en-tête。 LaRéponseadéjàétévalidée。
并在控制台中: POST http://localhost:4200/gtaows/services/uploadfile 415(不支持的媒体类型)
THX,
答案 2 :(得分:0)
这是我的解决方案:
将 Content-Type 留空是非常重要。如果您设置了“内容类型”&#39;到&#39; multipart / form-data&#39;上传无效!
upload.component.html
<input type="file" (change)="fileChange($event)" name="file" />
<强> upload.component.ts 强>
fileChange(event): void {
const fileList: FileList = event.target.files;
if (fileList.length > 0) {
const file = fileList[0];
const formData = new FormData();
formData.append('file', file, file.name);
const headers = new Headers();
// It is very important to leave the Content-Type empty
// do not use headers.append('Content-Type', 'multipart/form-data');
headers.append('Authorization', 'Bearer ' + 'eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9....');
const options = new RequestOptions({headers: headers});
this.http.post('https://api.mysite.com/uploadfile', formData, options)
.map(res => res.json())
.catch(error => Observable.throw(error))
.subscribe(
data => console.log('success'),
error => console.log(error)
);
}
}