283 lines
11 KiB
TypeScript
283 lines
11 KiB
TypeScript
import { BookType, OperateBookType, TagDefineType } from '../../../define/enum/bookEnum'
|
|
import { errorMessage, successMessage } from '../../Public/generalTools'
|
|
import { BookService } from '../../../define/db/service/Book/bookService'
|
|
import { BookTaskService } from '../../../define/db/service/Book/bookTaskService'
|
|
import { BookTaskDetailService } from '../../../define/db/service/Book/bookTaskDetailService'
|
|
import { CopyImageType } from '../../../define/enum/bookEnum'
|
|
const { v4: uuidv4 } = require('uuid')
|
|
import { define } from '../../../define/define'
|
|
import path from 'path'
|
|
import { CheckFileOrDirExist, CheckFolderExistsOrCreate, CopyFileOrFolder } from '../../../define/Tools/file'
|
|
import { Book } from '../../../model/book'
|
|
import { GeneralResponse } from '../../../model/generalResponse'
|
|
import { cloneDeep, isEmpty } from 'lodash'
|
|
|
|
export class BookBasic {
|
|
constructor() { }
|
|
bookTaskService: BookTaskService
|
|
bookTaskDetailService: BookTaskDetailService
|
|
|
|
async InitService() {
|
|
if (!this.bookTaskService) {
|
|
this.bookTaskService = await BookTaskService.getInstance()
|
|
}
|
|
if (!this.bookTaskDetailService) {
|
|
this.bookTaskDetailService = await BookTaskDetailService.getInstance()
|
|
}
|
|
}
|
|
|
|
//#region 小说相关操作
|
|
/**
|
|
* 新增或者是修小说数据
|
|
* @param {*} book 小说信息
|
|
* @returns
|
|
*/
|
|
async AddOrModifyBook(book) {
|
|
try {
|
|
if (book == null) {
|
|
return errorMessage('小说数据为空,无法修改')
|
|
}
|
|
// 处理一下数据,处理文件地址(删除前缀,转换为默认地址)
|
|
// 当前的小说的名字是不是在数据库中以存在
|
|
let _bookService = await BookService.getInstance()
|
|
let res = await _bookService.AddOrModifyBook(book)
|
|
return res
|
|
} catch (error) {
|
|
return errorMessage(
|
|
'修改数据错误,错误信息如下:' + error.message,
|
|
'BookBasic_AddOrModifyBook'
|
|
)
|
|
}
|
|
}
|
|
|
|
// 小说类型返回
|
|
GetBookType() {
|
|
return successMessage(
|
|
[
|
|
{
|
|
label: 'SD反推',
|
|
value: BookType.SD_REVERSE
|
|
},
|
|
{
|
|
label: 'MJ反推',
|
|
value: BookType.MJ_REVERSE
|
|
},
|
|
{
|
|
label: '原创',
|
|
value: BookType.ORIGINAL
|
|
}
|
|
],
|
|
'获取小说类型成功'
|
|
)
|
|
}
|
|
|
|
//#endregion
|
|
|
|
//#region 小说批次任务相关操作
|
|
|
|
|
|
async OneToFourBookTask(bookTaskId: string) {
|
|
try {
|
|
console.log(bookTaskId)
|
|
await this.InitService();
|
|
let copyCount = 100
|
|
let bookTask = this.bookTaskService.GetBookTaskDataById(bookTaskId)
|
|
if (bookTask == null) {
|
|
throw new Error("没有找到对应的数小说任务,请检查数据")
|
|
}
|
|
// 获取所有的出图中最少的
|
|
let bookTaskDetail = this.bookTaskDetailService.GetBookTaskData({
|
|
bookTaskId: bookTaskId
|
|
}).data as Book.SelectBookTaskDetail[]
|
|
if (bookTaskDetail == null || bookTaskDetail.length <= 0) {
|
|
throw new Error("没有对应的小说分镜任务,请先添加分镜任务")
|
|
}
|
|
|
|
for (let i = 0; i < bookTaskDetail.length; i++) {
|
|
const element = bookTaskDetail[i];
|
|
if (isEmpty(element.subImagePath)) {
|
|
throw new Error("检测到图片没有出完,请先检查出图")
|
|
}
|
|
if (element.subImagePath == null || element.subImagePath.length <= 0) {
|
|
throw new Error("检测到图片没有出完,请先检查出图")
|
|
}
|
|
if (element.subImagePath.length < copyCount) {
|
|
copyCount = element.subImagePath.length
|
|
}
|
|
}
|
|
if (copyCount <= 0) {
|
|
throw new Error("批次设置错误,无法进行一拆四")
|
|
}
|
|
// 开始复制
|
|
let res = await this.CopyNewBookTask(bookTask, bookTaskDetail, copyCount - 1, CopyImageType.ONE)
|
|
if (res.code == 0) {
|
|
throw new Error(res.message)
|
|
}
|
|
return successMessage(res.data, "一拆四成功", "BookBasic_OneToFourBookTask")
|
|
} catch (error) {
|
|
return errorMessage("一拆四失败,失败信息如下:" + error.message, "BookBasic_OneToFourBookTask")
|
|
}
|
|
}
|
|
|
|
/**
|
|
* 复制一个小说批次任务,创建新的小说批次任务
|
|
* @param oldBookTaskId
|
|
* @param copyCount 复制的数量
|
|
* @param isCopyImage 是否复制图片
|
|
*/
|
|
async CopyNewBookTask(sourceBookTask: Book.SelectBookTask, sourceBookTaskDetail: Book.SelectBookTaskDetail[], copyCount: number, copyImageType: CopyImageType) {
|
|
try {
|
|
await this.InitService();
|
|
let addBookTask = [] as Book.SelectBookTask[]
|
|
let addBookTaskDetail = [] as Book.SelectBookTaskDetail[]
|
|
|
|
// 先处理文件夹的创建,包括小说任务的和小说任务分镜的
|
|
for (let i = 0; i < copyCount; i++) {
|
|
let maxNo = this.bookTaskService.realm
|
|
.objects('BookTask')
|
|
.filtered('bookId = $0', sourceBookTask.bookId)
|
|
.max('no')
|
|
let no = maxNo == null ? 1 : Number(maxNo) + 1 + i
|
|
let name = 'output_0000' + no
|
|
let imageFolder = path.join(define.project_path, `${sourceBookTask.bookId}/tmp/${name}`)
|
|
await CheckFolderExistsOrCreate(imageFolder)
|
|
// 创建对应的文件夹
|
|
let addOneBookTask = {
|
|
id: uuidv4(),
|
|
bookId: sourceBookTask.bookId,
|
|
no: no,
|
|
name: name,
|
|
generateVideoPath: sourceBookTask.generateVideoPath,
|
|
srtPath: sourceBookTask.srtPath,
|
|
audioPath: sourceBookTask.audioPath,
|
|
draftSrtStyle: sourceBookTask.draftSrtStyle,
|
|
backgroundMusic: sourceBookTask.backgroundMusic,
|
|
friendlyReminder: sourceBookTask.friendlyReminder,
|
|
imageFolder: path.relative(define.project_path, imageFolder),
|
|
status: sourceBookTask.status,
|
|
errorMsg: sourceBookTask.errorMsg,
|
|
updateTime: new Date(),
|
|
createTime: new Date(),
|
|
isAuto: sourceBookTask.isAuto,
|
|
imageStyle: sourceBookTask.imageStyle,
|
|
autoAnalyzeCharacter: sourceBookTask.autoAnalyzeCharacter,
|
|
customizeImageStyle: sourceBookTask.customizeImageStyle,
|
|
videoConfig: sourceBookTask.videoConfig,
|
|
prefixPrompt: sourceBookTask.prefixPrompt,
|
|
suffixPrompt: sourceBookTask.suffixPrompt,
|
|
version: sourceBookTask.version,
|
|
imageCategory: sourceBookTask.imageCategory,
|
|
} as Book.SelectBookTask
|
|
|
|
addBookTask.push(addOneBookTask)
|
|
|
|
for (let j = 0; j < sourceBookTaskDetail.length; j++) {
|
|
const element = sourceBookTaskDetail[j];
|
|
|
|
let outImagePath = undefined as string
|
|
let subImagePath = [] as string[]
|
|
|
|
if (copyImageType == CopyImageType.ALL) { // 直接全部复制
|
|
outImagePath = element.outImagePath
|
|
subImagePath = element.subImagePath
|
|
} else if (copyImageType == CopyImageType.ONE) { // 只复制对应的
|
|
let oldImage = element.subImagePath[i + 1]
|
|
outImagePath = path.join(imageFolder, path.basename(element.outImagePath))
|
|
await CopyFileOrFolder(oldImage, outImagePath)
|
|
|
|
subImagePath = []
|
|
}
|
|
else if (copyImageType == CopyImageType.NONE) {
|
|
outImagePath = undefined
|
|
subImagePath = []
|
|
} else {
|
|
throw new Error("无效的图片复制类型")
|
|
}
|
|
if (outImagePath) {
|
|
// 单独处理一下显示的图片
|
|
let imageBaseName = path.basename(element.outImagePath);
|
|
let newImageBaseName = path.join(define.project_path, `${sourceBookTask.bookId}/tmp/${name}/${imageBaseName}`)
|
|
await CopyFileOrFolder(outImagePath, newImageBaseName)
|
|
}
|
|
// 处理SD设置
|
|
let sdConifg = undefined
|
|
if (element.sdConifg) {
|
|
let sdConifg = cloneDeep(element.sdConifg)
|
|
if (sdConifg.webuiConfig) {
|
|
let tempSdConfig = cloneDeep(sdConifg.webuiConfig);
|
|
tempSdConfig.id = uuidv4()
|
|
sdConifg.webuiConfig = tempSdConfig
|
|
}
|
|
}
|
|
|
|
let reverseId = uuidv4()
|
|
// 处理反推数据
|
|
let reverseMessage = [] as Book.ReversePrompt[]
|
|
if (element.reversePrompt && element.reversePrompt.length > 0) {
|
|
reverseMessage = cloneDeep(element.reversePrompt)
|
|
for (let k = 0; k < reverseMessage.length; k++) {
|
|
reverseMessage[k].id = uuidv4()
|
|
reverseMessage[k].bookTaskDetailId = reverseId
|
|
}
|
|
}
|
|
|
|
let addOneBookTaskDetail = {
|
|
id: reverseId,
|
|
no: element.no,
|
|
name: element.name,
|
|
bookId: sourceBookTask.bookId,
|
|
bookTaskId: addOneBookTask.id,
|
|
videoPath: path.relative(define.project_path, element.videoPath),
|
|
word: element.word,
|
|
oldImage: path.relative(define.project_path, element.oldImage),
|
|
afterGpt: element.afterGpt,
|
|
startTime: element.startTime,
|
|
endTime: element.endTime,
|
|
timeLimit: element.timeLimit,
|
|
subValue: element.subValue,
|
|
characterTags: element.characterTags && element.characterTags.length > 0 ? cloneDeep(element.characterTags) : [],
|
|
gptPrompt: element.gptPrompt,
|
|
outImagePath: path.relative(define.project_path, outImagePath),
|
|
subImagePath: subImagePath || [],
|
|
prompt: element.prompt,
|
|
adetailer: element.adetailer,
|
|
sdConifg: sdConifg,
|
|
createTime: new Date(),
|
|
updateTime: new Date(),
|
|
audioPath: element.audioPath,
|
|
subtitlePosition: element.subtitlePosition,
|
|
status: element.status,
|
|
reversePrompt: reverseMessage,
|
|
imageLock: element.imageLock
|
|
} as Book.SelectBookTaskDetail
|
|
addBookTaskDetail.push(addOneBookTaskDetail)
|
|
}
|
|
}
|
|
|
|
// 数据处理完毕,开始新增数据
|
|
// 将所有的复制才做,全部放在一个事务中
|
|
this.bookTaskService.transaction(() => {
|
|
for (let i = 0; i < addBookTask.length; i++) {
|
|
const element = addBookTask[i];
|
|
this.bookTaskService.realm.create('BookTask', element)
|
|
}
|
|
for (let i = 0; i < addBookTaskDetail.length; i++) {
|
|
const element = addBookTaskDetail[i];
|
|
this.bookTaskDetailService.realm.create('BookTaskDetail', element)
|
|
}
|
|
})
|
|
// 全部创建完成
|
|
// 查找到数据,然后全部返回
|
|
let returnBookTask = this.bookTaskService.GetBookTaskData({
|
|
bookId: sourceBookTask.bookId
|
|
}).data as Book.SelectBookTask[]
|
|
|
|
return successMessage(returnBookTask, "复制小说任务成功", "BookBasic_CopyNewBookTask")
|
|
} catch (error) {
|
|
console.log(error)
|
|
throw error
|
|
}
|
|
}
|
|
|
|
//#endregion
|
|
} |