基于Angular与Spring Boot的图片上传、展示及数据库取回实现
Angular + Spring Boot 实现 Person 图片上传与展示方案
一、Spring Boot 后端实现
1. 调整 Person 实体类
添加图片字段,用@Lob标注大对象类型,适配数据库存储二进制图片数据:
import jakarta.persistence.*; @Entity public class Person { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Long id; private String name; // 其他Person业务字段... @Lob private byte[] profileImage; // 存储图片二进制数据 // Getter、Setter方法 public Long getId() { return id; } public void setId(Long id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public byte[] getProfileImage() { return profileImage; } public void setProfileImage(byte[] profileImage) { this.profileImage = profileImage; } }
2. 编写 Repository 层
继承JpaRepository实现基础CRUD:
import org.springframework.data.jpa.repository.JpaRepository; public interface PersonRepository extends JpaRepository<Person, Long> { }
3. 编写 Service 层
处理图片转换与实体保存逻辑:
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.web.multipart.MultipartFile; import java.io.IOException; @Service public class PersonService { @Autowired private PersonRepository personRepository; public Person savePersonWithImage(String name, MultipartFile image) throws IOException { Person person = new Person(); person.setName(name); if (image != null && !image.isEmpty()) { person.setProfileImage(image.getBytes()); } return personRepository.save(person); } public byte[] getPersonImageById(Long id) { return personRepository.findById(id) .map(Person::getProfileImage) .orElse(null); } }
4. 编写 Controller 层
提供上传和图片获取接口:
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.http.HttpHeaders; import org.springframework.http.HttpStatus; import org.springframework.http.MediaType; import org.springframework.http.ResponseEntity; import org.springframework.web.bind.annotation.*; import org.springframework.web.multipart.MultipartFile; import java.io.IOException; @RestController @RequestMapping("/api/persons") public class PersonController { @Autowired private PersonService personService; // 上传Person信息与图片 @PostMapping(consumes = MediaType.MULTIPART_FORM_DATA_VALUE) public ResponseEntity<Person> uploadPerson( @RequestParam("name") String name, @RequestParam("profileImage") MultipartFile profileImage) throws IOException { Person savedPerson = personService.savePersonWithImage(name, profileImage); return new ResponseEntity<>(savedPerson, HttpStatus.CREATED); } // 根据ID获取图片,用于前端展示 @GetMapping("/{id}/image") public ResponseEntity<byte[]> getPersonImage(@PathVariable Long id) { byte[] imageBytes = personService.getPersonImageById(id); if (imageBytes == null) { return new ResponseEntity<>(HttpStatus.NOT_FOUND); } HttpHeaders headers = new HttpHeaders(); headers.setContentType(MediaType.IMAGE_JPEG); // 可根据实际图片类型调整 return new ResponseEntity<>(imageBytes, headers, HttpStatus.OK); } }
5. 配置文件调整
在application.properties中设置文件上传大小限制:
spring.servlet.multipart.max-file-size=10MB spring.servlet.multipart.max-request-size=10MB
二、Angular 前端实现
1. 上传组件模板(person-upload.component.html)
<form (ngSubmit)="onSubmit()" #personForm="ngForm"> <div> <label>姓名:</label> <input type="text" name="name" [(ngModel)]="personName" required> </div> <div> <label>头像:</label> <input type="file" accept="image/*" (change)="onFileSelected($event)"> </div> <button type="submit" [disabled]="!personForm.valid || !selectedFile">提交</button> </form> <!-- 图片预览 --> <div *ngIf="previewUrl"> <h3>预览:</h3> <img [src]="previewUrl" alt="Person Image" style="width: 200px;"> </div>
2. 上传组件逻辑(person-upload.component.ts)
import { Component } from '@angular/core'; import { HttpClient } from '@angular/common/http'; @Component({ selector: 'app-person-upload', templateUrl: './person-upload.component.html', styleUrls: ['./person-upload.component.css'] }) export class PersonUploadComponent { personName: string = ''; selectedFile: File | null = null; previewUrl: string | null = null; constructor(private http: HttpClient) {} onFileSelected(event: any) { this.selectedFile = event.target.files[0]; if (this.selectedFile) { this.previewUrl = URL.createObjectURL(this.selectedFile); } } onSubmit() { if (!this.selectedFile || !this.personName) return; const formData = new FormData(); formData.append('name', this.personName); formData.append('profileImage', this.selectedFile); this.http.post('http://localhost:8080/api/persons', formData) .subscribe({ next: (res) => { console.log('上传成功', res); // 可添加上传成功后的逻辑,如跳转列表页 }, error: (err) => { console.error('上传失败', err); } }); } }
3. 图片展示组件(person-image.component.ts)
直接调用后端接口展示图片:
import { Component, Input, OnInit } from '@angular/core'; @Component({ selector: 'app-person-image', template: `<img [src]="imageUrl" alt="Person Profile" style="width: 200px;">` }) export class PersonImageComponent implements OnInit { @Input() personId: number | null = null; imageUrl: string | null = null; ngOnInit() { if (this.personId) { this.imageUrl = `http://localhost:8080/api/persons/${this.personId}/image`; } } }
4. 模块配置(app.module.ts)
确保导入必要模块:
import { NgModule } from '@angular/core'; import { BrowserModule } from '@angular/platform-browser'; import { HttpClientModule } from '@angular/common/http'; import { FormsModule } from '@angular/forms'; import { AppComponent } from './app.component'; import { PersonUploadComponent } from './person-upload/person-upload.component'; import { PersonImageComponent } from './person-image/person-image.component'; @NgModule({ declarations: [ AppComponent, PersonUploadComponent, PersonImageComponent ], imports: [ BrowserModule, HttpClientModule, FormsModule ], providers: [], bootstrap: [AppComponent] }) export class AppModule { }
内容的提问来源于stack exchange,提问作者prabin chand
相关产品推荐
相关产品推荐

