2025. 1. 14. 00:11ㆍCalender Website
프로필 사진을 User 테이블에 저장해야 한다. 우선 사용자가 로컬 컴퓨터에서 이미지를 선택하면 선택된 이미지가 미리보기에 나타나고, 이를 데이터 베이스에 저장해야 한다.
보톤 이미지를 저장하는 방식은 이미지 파일을 텍스트 형식으로 인코딩하여 저장하거나, 이미지 경로만 데이터 베이스에 저장하는 두가지 방식이 있다. 이미지 파일을 직접 저장하는 방법은 데이터베이스의 용량이 커지므로, 이미지 경로를 데이터 베이스에 저장하겠다.
<HTML>
HTML의 form에는 미리보기 이미지와 type="file"인 입력 필드를 만들어준다. 이 때 입력 필드는 display:none으로 설정하여 파일 선택 창이 안보이도록 설정한다.
<div class="form-group">
<div class="image-div">
<img src="{{ url_for('static', filename='images/woman.png') }}" class="profile-image" id="profile-image">
</div>
<input type="file" id="image-input" name="user-image" style="display: none;" accept="image/*">
</div>
<Javascript>
우선 미리보기 이미지를 클릭하면 입력 필드도 같이 클릭되게 설정한다. 이렇게 하면 미리보기를 클릭했을 때 파일 선택 창이 뜨게 될 것이다.
document.getElementById('profile-image').onclick = function() {
document.getElementById('image-input').click(); // 파일 선택 창을 프로그램matically 열기
};
다음으로 이미지를 선택하면 미리보기에 해당 이미지가 뜨도록 해준다.
// select image file and update image
document.getElementById('image-input').addEventListener('change', function(event) {
const file = event.target.files[0];
if (file) {
const reader = new FileReader();
reader.onload = function(e) {
document.getElementById('profile-image').src = e.target.result;
};
reader.readAsDataURL(file);
}
});
이제 HTML form을 AXIOS 통신으로 Flask에 보내준다. 따로 전처리할 필요없이 FormData는 파일과 같은 복잡한 형식의 데이터도 보낼 수 있다.
document.addEventListener('DOMContentLoaded', function() {
document.querySelector('.signup-form').addEventListener('submit', function(e) {
e.preventDefault();
const formData = new FormData(this);
axios.post('/register', formData)
.then(function(response) {
document.querySelector('.form-container').style.display = 'none';
document.querySelector('.welcome-message').style.display = 'block';
document.getElementById('welcome-name').textContent = response.data.name;
})
.catch(function(error) {
console.error('Error: ', error);
});
});
});
<Flask>
formData로 전달받은 데이터에서 user-image를 확인한다.
만약 이미지 파일이 없으면 데이터베이스에 저장할 경로인 db_file_path를 공백으로 처리하고
이미지 파일이 있으면 secure_filename으로 다른 유저가 파일을 확인할 수 없도록 처리한 다음, 저장할 폴더인('app/static/images/profile')과 파일 이름을 합쳐f file_path를 만들어 파일을 저장한다.
데이터 베이스에 저장할 경로인 db_file_path는 static 이후의 경로만 저장하므로 문자열을 사용하여 저장해주면 된다.
해당 경로를 데이터 베이스에 전달해주면 다음에 이미지를 사용할 일이 있을 때 파일 경로를 참조하여 이미지를 불러올 수 있다.
@api.route('/register', methods=['POST'])
def register():
user_image = request.files['user-image']
if user_image.filename == '':
db_file_path = ''
else:
file_name = secure_filename(user_image.filename)
file_path = os.path.join('app/static/images/profile', file_name)
user_image.save(file_path)
# db에 저장할 경로는 static 이후부터
db_file_path = f'images/profile/{file_name}'
new_user = User(...,
image_path=db_file_path)
db.session.add(new_user)
db.session.commit()
return jsonify ({
'name': user_name
})
'Calender Website' 카테고리의 다른 글
[Flask] 회원 정보 수정, 탈퇴, 로그아웃 (0) | 2025.01.23 |
---|---|
[Flask] Flask-login을 사용한 로그인 시스템 구현 (0) | 2025.01.16 |
[Flask] Blueprint로 웹 애플리케이션 구조화 (0) | 2025.01.14 |
[Flask] 플라스크로 회원가입 구현하기 (0) | 2025.01.14 |
투두리스트, 캘린더, 다이어리 웹사이트 개발 - Flask 개발 환경 준비 (0) | 2024.12.30 |