如何在 React 组件中显示来自使用 AWS S3 的后端的字节数组图像?
How do I display a byte array image from a backend that uses AWS S3, in a React component?
我正在尝试使用 React 从 SpringBoot API 后端显示存储在 AWS 中的图像。我在进行以下提取时从服务器得到的响应是:
‰PNG
IHDRäX³N•jsRGB®ÎégAMA±üa pHYs.#.#x¥?vf/IDATx^íÝ|]wyÿqï!Ë–eÙ–myÊ#vlg'„=É2«u M¡@hšBÛ?´Ð2úé eh˜„$$…ã@2IÂÊ"‹loËS–lI–,K¶¼þÏ÷ÜóK99’îÒ½çJŸ÷ëõ¼î¹º×¶|ÇyÎo=¿A²18¼Pš.³—:Ôjñ‹Ô!(¤W-Ž„ñ’~ 4
o@‘H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !
§øc‹±žõãÿø篿þzÔ=}……ª|Ž÷
}6´ÌŠ®lèJ®J²ÝuMk‰Œê%Ÿe1`¨e|ùå—?tå•W~;üÑ@¡Õײ(½÷qŸ }VþÈ"Ÿ»oÀ€¦¥1O[Ät5QKu‘U[yÀùú׿^}Ægì¾è¢‹ž²ä<PæüÜ"îó¡PkZKÚ€DãÊI6ßâÇÚÊO“{|JÄ?³ÐæÚB3rœ;v,mmm×ÑÑqô·¾õºFW3çµ|MŸ%f}6|
etc
我认为我必须将其转换为如下所示的 blob,但图像没有出现在配置文件中。
Profile.js:
const GET_SINGLE_USER_URL = 'http://localhost:8080/users/get-user-by-username'
const USER_IMG_URL = 'http://localhost:8080/image-files/'
class Profile extends Component {
constructor(props) {
super(props);
this.state = {user: '', token: '', img: ''};
}
componentDidMount() {
const imgUrl = USER_IMG_URL + localStorage.getItem("username");
const payload = {
"username": localStorage.getItem("username"),
"password": localStorage.getItem("password")
};
fetch(GET_SINGLE_USER_URL, {
method: 'POST',
headers: {
"Accept": "application/json",
"Content-Type": "application/json",
"Authorization": localStorage.getItem("token")
},
body: JSON.stringify(payload)
})
.then(response => response.json())
.then(data => this.setState({user: data}));
fetch(imgUrl, {
method: 'GET',
headers: {
"Authorization": localStorage.getItem("token")
}
})
.then(r => r.arrayBuffer())
.then(buffer => {
const blob = new Blob([buffer]);
this.state.img = URL.createObjectURL(blob);
});
}
render() {
const {user, img, isLoading} = this.state;
if (isLoading) {
return <p>Loading...</p>;
}
return (
<div className="outer-div-container">
<div>
<AppNavbar/>
<Container fluid>
<div id="flexbox-container">
<div className="card-container" id="profile-card-container">
<Card className="profile-card">
<CardImg src={img} />
<CardText className="profile-data">{user.name}</CardText>
<CardText className="profile-data">{user.username}</CardText>
<CardText className="profile-data">{user.location}</CardText>
</Card>
</div>
</div>
</Container>
</div>
</div>
我不确定如何在 React 组件中将字节数组转换为可显示的图像。
非常感谢任何帮助,谢谢。
我也试过:
async getImage() {
const imgUrl = USER_IMG_URL + localStorage.getItem("username");
fetch(imgUrl,{
method: 'GET',
headers: {
"Authorization": localStorage.getItem("token")
}
})
.then(response => response.json())
.then(data => {
console.log(data)
this.setState({
image: "data:image/png;base64," + data
})
})
console.log(this.state.image) // *1
}
现在它在 'PNG' 响应行上显示意外的 JSON 输入。
此外,当我上传 jpeg 时,我得到的是“ÿØÿàJFIFHHÿÛ”
您可以将图像响应作为数据 URL 嵌入到 img 标签的 src 属性中。
将 ArrayBuffer 转换为数据 URL:
export function toDataURL(img:ArrayBuffer, contentType:string) {
const image = btoa(
new Uint8Array(img)
.reduce((data, byte) => data + String.fromCharCode(byte), '')
);
return `data:${contentType};base64,${image}`;
}
此方法下载图像,获取字节数组,将其转换为 Blob
并将二进制数据填充到可用于图像源的魔术 url。
const IMAGE_URL = "https://placekitten.com/200/300";
const fetchImage = async (url) => {
try {
const response = await fetch(url);
const imageBytes = await response.arrayBuffer();
var blob = new Blob([imageBytes], { type: "image/jpeg" });
var imageUrl = URL.createObjectURL(blob);
return imageUrl;
} catch (error) {
console.log("ERROR:", error);
}
};
(async () => {
const imageSrc = await fetchImage(IMAGE_URL);
console.log(imageSrc);
document.getElementById("kittenImage").src = imageSrc;
})();
document.getElementById("app").innerHTML = `
<h1>Kitty!</h1>
<image id='kittenImage'>
`;
<!DOCTYPE html>
<html>
<head>
<title>Parcel Sandbox</title>
<meta charset="UTF-8" />
</head>
<body>
<div id="app"></div>
<script src="src/index.js">
</script>
</body>
</html>
我正在尝试使用 React 从 SpringBoot API 后端显示存储在 AWS 中的图像。我在进行以下提取时从服务器得到的响应是:
‰PNG
IHDRäX³N•jsRGB®ÎégAMA±üa pHYs.#.#x¥?vf/IDATx^íÝ|]wyÿqï!Ë–eÙ–myÊ#vlg'„=É2«u M¡@hšBÛ?´Ð2úé eh˜„$$…ã@2IÂÊ"‹loËS–lI–,K¶¼þÏ÷ÜóK99’îÒ½çJŸ÷ëõ¼î¹º×¶|ÇyÎo=¿A²18¼Pš.³—:Ôjñ‹Ô!(¤W-Ž„ñ’~ 4
o@‘H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !$d€„@H2 @B HÈ$ € !
§øc‹±žõãÿø篿þzÔ=}……ª|Ž÷
}6´ÌŠ®lèJ®J²ÝuMk‰Œê%Ÿe1`¨e|ùå—?tå•W~;üÑ@¡Õײ(½÷qŸ }VþÈ"Ÿ»oÀ€¦¥1O[Ät5QKu‘U[yÀùú׿^}Ægì¾è¢‹ž²ä<PæüÜ"îó¡PkZKÚ€DãÊI6ßâÇÚÊO“{|JÄ?³ÐæÚB3rœ;v,mmm×ÑÑqô·¾õºFW3çµ|MŸ%f}6|
etc
我认为我必须将其转换为如下所示的 blob,但图像没有出现在配置文件中。
Profile.js:
const GET_SINGLE_USER_URL = 'http://localhost:8080/users/get-user-by-username'
const USER_IMG_URL = 'http://localhost:8080/image-files/'
class Profile extends Component {
constructor(props) {
super(props);
this.state = {user: '', token: '', img: ''};
}
componentDidMount() {
const imgUrl = USER_IMG_URL + localStorage.getItem("username");
const payload = {
"username": localStorage.getItem("username"),
"password": localStorage.getItem("password")
};
fetch(GET_SINGLE_USER_URL, {
method: 'POST',
headers: {
"Accept": "application/json",
"Content-Type": "application/json",
"Authorization": localStorage.getItem("token")
},
body: JSON.stringify(payload)
})
.then(response => response.json())
.then(data => this.setState({user: data}));
fetch(imgUrl, {
method: 'GET',
headers: {
"Authorization": localStorage.getItem("token")
}
})
.then(r => r.arrayBuffer())
.then(buffer => {
const blob = new Blob([buffer]);
this.state.img = URL.createObjectURL(blob);
});
}
render() {
const {user, img, isLoading} = this.state;
if (isLoading) {
return <p>Loading...</p>;
}
return (
<div className="outer-div-container">
<div>
<AppNavbar/>
<Container fluid>
<div id="flexbox-container">
<div className="card-container" id="profile-card-container">
<Card className="profile-card">
<CardImg src={img} />
<CardText className="profile-data">{user.name}</CardText>
<CardText className="profile-data">{user.username}</CardText>
<CardText className="profile-data">{user.location}</CardText>
</Card>
</div>
</div>
</Container>
</div>
</div>
我不确定如何在 React 组件中将字节数组转换为可显示的图像。
非常感谢任何帮助,谢谢。
我也试过:
async getImage() {
const imgUrl = USER_IMG_URL + localStorage.getItem("username");
fetch(imgUrl,{
method: 'GET',
headers: {
"Authorization": localStorage.getItem("token")
}
})
.then(response => response.json())
.then(data => {
console.log(data)
this.setState({
image: "data:image/png;base64," + data
})
})
console.log(this.state.image) // *1
}
现在它在 'PNG' 响应行上显示意外的 JSON 输入。
此外,当我上传 jpeg 时,我得到的是“ÿØÿàJFIFHHÿÛ”
您可以将图像响应作为数据 URL 嵌入到 img 标签的 src 属性中。
将 ArrayBuffer 转换为数据 URL:
export function toDataURL(img:ArrayBuffer, contentType:string) {
const image = btoa(
new Uint8Array(img)
.reduce((data, byte) => data + String.fromCharCode(byte), '')
);
return `data:${contentType};base64,${image}`;
}
此方法下载图像,获取字节数组,将其转换为 Blob
并将二进制数据填充到可用于图像源的魔术 url。
const IMAGE_URL = "https://placekitten.com/200/300";
const fetchImage = async (url) => {
try {
const response = await fetch(url);
const imageBytes = await response.arrayBuffer();
var blob = new Blob([imageBytes], { type: "image/jpeg" });
var imageUrl = URL.createObjectURL(blob);
return imageUrl;
} catch (error) {
console.log("ERROR:", error);
}
};
(async () => {
const imageSrc = await fetchImage(IMAGE_URL);
console.log(imageSrc);
document.getElementById("kittenImage").src = imageSrc;
})();
document.getElementById("app").innerHTML = `
<h1>Kitty!</h1>
<image id='kittenImage'>
`;
<!DOCTYPE html>
<html>
<head>
<title>Parcel Sandbox</title>
<meta charset="UTF-8" />
</head>
<body>
<div id="app"></div>
<script src="src/index.js">
</script>
</body>
</html>