このコミットが含まれているのは:
2026-07-18 00:31:02 +09:00
コミット c31d84115d
3個のファイルの変更58行の追加24行の削除
+1 -1
ファイルの表示
@@ -128,7 +128,6 @@ class PostsController < ApplicationController
provenance: { }, provenance: { },
tag_sources: { } }], tag_sources: { } }],
fetch_metadata: true).first fetch_metadata: true).first
return render_validation_error fields: preview[:validation_errors] if preview[:validation_errors].present?
render json: { render json: {
url: preview[:url], url: preview[:url],
@@ -141,6 +140,7 @@ class PostsController < ApplicationController
video_ms: preview[:attributes]['video_ms'], video_ms: preview[:attributes]['video_ms'],
field_warnings: preview[:field_warnings], field_warnings: preview[:field_warnings],
base_warnings: preview[:base_warnings], base_warnings: preview[:base_warnings],
validation_errors: preview[:validation_errors],
existing_post: compact_post(preview[:existing_post_id]) } existing_post: compact_post(preview[:existing_post_id]) }
rescue ArgumentError => e rescue ArgumentError => e
render_bad_request e.message render_bad_request e.message
+13 -4
ファイルの表示
@@ -74,6 +74,7 @@ type PreviewResponse = {
tags?: string tags?: string
fieldWarnings?: Record<string, string[]> fieldWarnings?: Record<string, string[]>
baseWarnings?: string[] baseWarnings?: string[]
validationErrors?: Record<string, string[]>
existingPost?: { existingPost?: {
id: number id: number
title: string title: string
@@ -249,7 +250,13 @@ const mergePreviewRow = (
): PostImportRow => { ): PostImportRow => {
const fieldWarnings = preview.fieldWarnings ?? { } const fieldWarnings = preview.fieldWarnings ?? { }
const baseWarnings = preview.baseWarnings ?? [] const baseWarnings = preview.baseWarnings ?? []
const validationErrors = preview.validationErrors ?? { }
const metadataChanged = currentRow.metadataUrl !== preview.url const metadataChanged = currentRow.metadataUrl !== preview.url
const hasWarnings =
Object.values (fieldWarnings).some (messages => messages.length > 0)
|| baseWarnings.length > 0
const hasErrors =
Object.values (validationErrors).some (messages => messages.length > 0)
const nextRow: PostImportRow = { const nextRow: PostImportRow = {
...currentRow, ...currentRow,
attributes: { ...currentRow.attributes }, attributes: { ...currentRow.attributes },
@@ -260,6 +267,7 @@ const mergePreviewRow = (
url: preview.url, url: preview.url,
fieldWarnings, fieldWarnings,
baseWarnings, baseWarnings,
validationErrors,
existingPostId: preview.existingPost?.id, existingPostId: preview.existingPost?.id,
existingPost: preview.existingPost ?? undefined, existingPost: preview.existingPost ?? undefined,
skipReason: skipReason:
@@ -274,10 +282,11 @@ const mergePreviewRow = (
? buildPreviewResetSnapshot (preview) ? buildPreviewResetSnapshot (preview)
: currentRow.resetSnapshot, : currentRow.resetSnapshot,
status: status:
Object.keys (fieldWarnings).length > 0 hasErrors
|| baseWarnings.length > 0 ? 'error'
? 'warning' : hasWarnings
: 'ready' } ? 'warning'
: 'ready' }
if (currentRow.provenance.title !== 'manual') if (currentRow.provenance.title !== 'manual')
nextRow.attributes.title = preview.title ?? '' nextRow.attributes.title = preview.title ?? ''
+44 -19
ファイルの表示
@@ -48,6 +48,7 @@ type PreviewResponse = {
tags?: string tags?: string
fieldWarnings?: Record<string, string[]> fieldWarnings?: Record<string, string[]>
baseWarnings?: string[] baseWarnings?: string[]
validationErrors?: Record<string, string[]>
existingPost?: { existingPost?: {
id: number id: number
title: string title: string
@@ -75,6 +76,12 @@ const previewRowFromResult = (
): PostImportRow => { ): PostImportRow => {
const fieldWarnings = result.fieldWarnings ?? { } const fieldWarnings = result.fieldWarnings ?? { }
const baseWarnings = result.baseWarnings ?? [] const baseWarnings = result.baseWarnings ?? []
const validationErrors = result.validationErrors ?? { }
const hasWarnings =
Object.values (fieldWarnings).some (messages => messages.length > 0)
|| baseWarnings.length > 0
const hasErrors =
Object.values (validationErrors).some (messages => messages.length > 0)
const row: PostImportRow = { const row: PostImportRow = {
sourceRow, sourceRow,
url: result.url, url: result.url,
@@ -89,7 +96,7 @@ const previewRowFromResult = (
parentPostIds: '' }, parentPostIds: '' },
fieldWarnings, fieldWarnings,
baseWarnings, baseWarnings,
validationErrors: { }, validationErrors,
provenance: { provenance: {
url: 'manual', url: 'manual',
title: 'automatic', title: 'automatic',
@@ -104,9 +111,11 @@ const previewRowFromResult = (
automatic: result.tags ?? '', automatic: result.tags ?? '',
manual: '' }, manual: '' },
status: status:
Object.keys (fieldWarnings).length > 0 || baseWarnings.length > 0 hasErrors
? 'warning' ? 'error'
: 'ready', : hasWarnings
? 'warning'
: 'ready',
skipReason: result.existingPost?.id != null ? 'existing' : undefined, skipReason: result.existingPost?.id != null ? 'existing' : undefined,
existingPostId: result.existingPost?.id, existingPostId: result.existingPost?.id,
existingPost: result.existingPost ?? undefined, existingPost: result.existingPost ?? undefined,
@@ -155,6 +164,36 @@ const fetchPreviewRows = async (
message: string message: string
url: string }> = [] url: string }> = []
let nextIndex = 0 let nextIndex = 0
const previewIssues = (
sourceRow: number,
url: string,
requestError: unknown,
): Array<{ sourceRow: number
message: string
url: string }> => {
if (!(isApiError<{
message?: string
errors?: Record<string, string[]>
baseErrors?: string[]
}> (requestError)))
{
return [{
sourceRow,
message: '入力を確認してください.',
url }]
}
const fieldMessages = Object.values (requestError.response?.data?.errors ?? { }).flat ()
const baseMessages = requestError.response?.data?.baseErrors ?? []
const messages = [...new Set ([...fieldMessages, ...baseMessages])]
return (messages.length > 0 ? messages : [requestError.response?.data?.message ?? '入力を確認してください.'])
.map (message => ({
sourceRow,
message,
url }))
}
const worker = async () => { const worker = async () => {
while (nextIndex < rows.length) while (nextIndex < rows.length)
{ {
@@ -172,21 +211,7 @@ const fetchPreviewRows = async (
{ {
if (signal.aborted) if (signal.aborted)
return return
issues.push (...previewIssues (row.sourceRow, row.url, requestError))
const apiMessage =
isApiError<{
message?: string
errors?: Record<string, string[]>
baseErrors?: string[]
}> (requestError)
? (requestError.response?.data?.errors?.url?.[0]
?? requestError.response?.data?.message
?? requestError.response?.data?.baseErrors?.[0])
: undefined
issues.push ({
sourceRow: row.sourceRow,
message: apiMessage ?? '入力を確認してください.',
url: row.url })
} }
} }
} }