Summernote는 Bootstrap 4 기반의 위지윅 에디터이다. 위지윅 에디터란, 에디터에서 보이는 모습을 그대로 HTML 태그를 추가하여 결과물로 보여주는 에디터이다.
그냥 input Textarea 태그를 통해 제목 - 글을 제공하는 방법도 있었지만, 위지윅 에디터를 통해 좀 더 다채로운 모습의 글을 서비스 할 수 있도록 적용하였다. 그리고 무엇보다도 일반 input Textarea 태그만 사용하게 되면 이미지를 삽입하는 것이 사실상 불가능할 정도로 어려운 과제가 되어버린다. 따라서 위지윅 에디터를 적용하게 되었다.
postWrite.ejs의 Head부분
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>summernote</title>
<!-- CDN 추가 시작 -->
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@4.6.1/dist/css/bootstrap.min.css" integrity="sha384-zCbKRCUGaJDkqS1kPbPd7TveP5iyJE0EjAuZQTgFLD2ylzuqKfdKlfG/eSrtxUkn" crossorigin="anonymous">
<script
src="https://code.jquery.com/jquery-3.5.1.min.js"
integrity="sha256-9/aliU8dGd2tb6OSsuzixeV4y/faTqgFtohetphbbj0="
crossorigin="anonymous"></script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@4.6.1/dist/js/bootstrap.bundle.min.js" integrity="sha384-fQybjgWLrvvRgtW6bFlB7jaZrFsaBXjsOMm/tB9LTS58ONXgqbR9W8oWht/amnpF" crossorigin="anonymous"></script>
<link href="https://cdn.jsdelivr.net/npm/summernote@0.8.18/dist/summernote.min.css" rel="stylesheet">
<script src="https://cdn.jsdelivr.net/npm/summernote@0.8.18/dist/summernote.min.js"></script>
<!-- CDN 추가 부분 끝 -->
</head>
...
postWrite.ejs의 Body 부분
<body>
<form method="post" action="/insertPost">
<textarea id="summernote" name="editordata"></textarea>
<button type="submit">등록</button>
</form>
</body>
postWrite.ejs의 script부분 (1)
<script>
// summernote init
$(function(){
$('#summernote').summernote({
placeholder: '내용',
tabsize: 2,
focus: true,
callbacks:{
// onImageUpload를 통해 이미지 업로드시 동작 개조 가능
// 개조하지 않으면 Base64로 이미지가 전환돼서 img태그로 바뀐뒤 본문에 추가된다.
onImageUpload: function(files){ // 이미지 업로드시
sendFile(files[0], this); // sendFile함수 동작
}
}
});
});
...
postWrite.ejs의 script부분(2)
function sendFile(file, editor){
data = new FormData()
data.append("img", file)
$.ajax({ // ajax사용시 웹 페이지를 갱신하지 않고도 request가 가능하다.
data: data,
type: "POST",
url: "/api/insertImage", // 이미지 업로드를 위한 api url
cache: false,
contentType: false,
enctype: "multipart/form-data",
processData: false,
success: function (response) { // 성공시 img태그 생성
var imgurl = $('<img>').attr({
'src': response,
'crossorigin': 'anonymous',
'class': 'img-fluid',
});
$("#summernote").summernote("insertNode", imgurl[0]); // editor 내용에 삽입
},
})
}
routes/api.js
...
const upload = require('../lib/multer');
const router = express.Router();
router.post('/insertImage', upload.single('img'), insertImage);
...
apiController.js
// @post
// /api/insertImage
const insertImage = async(req, res) => {
imgurl = '';
if(req.file !== undefined) {
var imgurl = req.file.location; // router에서 붙인 multer가 반환한 url (aws s3 object url)
}
res.json(imgurl);
}
이미지 업로드에 대한 자세한 내용은 이전 포스트 참고.
위지윅 에디터가 성공적으로 적용된 모습이다.
위지윅 에디터로 편집한 글이 블로그 글 보기에 그대로 출력되는 모습이다.