예약 발행 기능 추가

This commit is contained in:
2026-05-03 09:58:27 +09:00
parent db87542096
commit 60f9fd52f0
11 changed files with 151 additions and 9 deletions

View File

@@ -28,6 +28,46 @@ const autosaveNotice = ref(null)
const autosaveStatus = ref('')
const isRestoringAutosave = ref(false)
/**
* ISO 날짜를 datetime-local 입력값으로 변환
* @param {string} value - ISO 날짜 문자열
* @returns {string} datetime-local 입력값
*/
function toDateTimeLocalValue(value) {
if (!value) {
return ''
}
const date = new Date(value)
if (Number.isNaN(date.getTime())) {
return ''
}
const offsetDate = new Date(date.getTime() - date.getTimezoneOffset() * 60000)
return offsetDate.toISOString().slice(0, 16)
}
/**
* datetime-local 입력값을 ISO 문자열로 변환
* @param {string} value - datetime-local 입력값
* @returns {string | null} ISO 날짜 문자열
*/
function toIsoDateTime(value) {
if (!value) {
return null
}
const date = new Date(value)
if (Number.isNaN(date.getTime())) {
return null
}
return date.toISOString()
}
const form = reactive({
title: props.initialPost.title || '',
slug: props.initialPost.slug || '',
@@ -35,6 +75,7 @@ const form = reactive({
content: props.initialPost.content || '',
featuredImage: props.initialPost.featuredImage || '',
status: props.initialPost.status || 'draft',
publishedAt: toDateTimeLocalValue(props.initialPost.publishedAt),
tagsText: props.initialPost.tags?.join(', ') || ''
})
@@ -78,13 +119,23 @@ const parseTags = (value) => [...new Set(value
.map((tag) => toSlug(tag))
.filter(Boolean))]
/**
* 예약 발행 여부 확인
* @returns {boolean} 예약 발행 여부
*/
const isScheduledPost = () => {
const publishedAt = toIsoDateTime(form.publishedAt)
return form.status === 'published' && Boolean(publishedAt) && new Date(publishedAt) > new Date()
}
/**
* 게시물 입력값 생성
* @returns {Object} 게시물 입력값
*/
const createPostPayload = () => {
const publishedAt = form.status === 'published'
? props.initialPost.publishedAt || new Date().toISOString()
? toIsoDateTime(form.publishedAt) || props.initialPost.publishedAt || new Date().toISOString()
: null
return {
@@ -110,6 +161,7 @@ const createAutosavePayload = () => ({
content: form.content,
featuredImage: form.featuredImage,
status: form.status,
publishedAt: form.publishedAt,
tagsText: form.tagsText
})
@@ -381,6 +433,20 @@ defineExpose({
</select>
</label>
<label v-if="form.status === 'published'" class="admin-post-form__field grid gap-2 text-sm">
<span class="admin-post-form__label font-medium">
발행 시각
</span>
<input
v-model="form.publishedAt"
class="admin-post-form__input rounded border border-line bg-white px-3 py-2"
type="datetime-local"
>
<span class="admin-post-form__hint text-xs text-muted">
{{ isScheduledPost() ? '미래 시각이면 예약 발행으로 저장됩니다.' : '비워두면 저장 시점으로 발행됩니다.' }}
</span>
</label>
<label class="admin-post-form__field grid gap-2 text-sm">
<span class="admin-post-form__label font-medium">슬러그</span>
<input