6.15.4: Подзадачи в драфтах авто-выполнения
All checks were successful
Build and Push Docker Image / build-and-push (push) Successful in 1m28s
All checks were successful
Build and Push Docker Image / build-and-push (push) Successful in 1m28s
This commit is contained in:
@@ -3514,6 +3514,123 @@ func (a *App) getAutoCompleteDraftEntries(userID int) ([]TodayEntry, error) {
|
||||
entryText = taskName
|
||||
}
|
||||
|
||||
// Вычисляем следующий свободный индекс для нод подзадач
|
||||
nextNodeIndex := 0
|
||||
for _, node := range nodes {
|
||||
if node.Index >= nextNodeIndex {
|
||||
nextNodeIndex = node.Index + 1
|
||||
}
|
||||
}
|
||||
|
||||
// Получаем checked подзадачи из task_draft_subtasks для этого драфта
|
||||
subtaskRows, err := a.DB.Query(`
|
||||
SELECT t.id, t.name, COALESCE(t.reward_message, ''), t.progression_base
|
||||
FROM task_draft_subtasks tds
|
||||
JOIN task_drafts td ON tds.task_draft_id = td.id
|
||||
JOIN tasks t ON tds.subtask_id = t.id
|
||||
WHERE td.task_id = $1 AND td.user_id = $2 AND t.deleted = FALSE
|
||||
`, taskID, userID)
|
||||
if err != nil {
|
||||
log.Printf("Error querying draft subtasks for task %d: %v", taskID, err)
|
||||
} else {
|
||||
for subtaskRows.Next() {
|
||||
var subtaskID int
|
||||
var subtaskName string
|
||||
var subtaskRewardMsg string
|
||||
var subtaskProgressionBase sql.NullFloat64
|
||||
|
||||
if err := subtaskRows.Scan(&subtaskID, &subtaskName, &subtaskRewardMsg, &subtaskProgressionBase); err != nil {
|
||||
log.Printf("Error scanning subtask row for draft: %v", err)
|
||||
continue
|
||||
}
|
||||
|
||||
// Пропускаем подзадачи без reward_message
|
||||
if subtaskRewardMsg == "" {
|
||||
continue
|
||||
}
|
||||
|
||||
// Получаем ноды подзадачи
|
||||
subtaskRewardRows, err := a.DB.Query(`
|
||||
SELECT rc.position, p.name AS project_name, rc.value, rc.use_progression
|
||||
FROM reward_configs rc
|
||||
JOIN projects p ON rc.project_id = p.id
|
||||
WHERE rc.task_id = $1
|
||||
ORDER BY rc.position
|
||||
`, subtaskID)
|
||||
if err != nil {
|
||||
log.Printf("Error querying subtask rewards for draft subtask %d: %v", subtaskID, err)
|
||||
continue
|
||||
}
|
||||
|
||||
type subtaskRewardEntry struct {
|
||||
position int
|
||||
projectName string
|
||||
rewardValue float64
|
||||
useProgression bool
|
||||
}
|
||||
subtaskRewards := make([]subtaskRewardEntry, 0)
|
||||
for subtaskRewardRows.Next() {
|
||||
var sre subtaskRewardEntry
|
||||
if err := subtaskRewardRows.Scan(&sre.position, &sre.projectName, &sre.rewardValue, &sre.useProgression); err != nil {
|
||||
log.Printf("Error scanning subtask reward row for draft: %v", err)
|
||||
continue
|
||||
}
|
||||
subtaskRewards = append(subtaskRewards, sre)
|
||||
}
|
||||
subtaskRewardRows.Close()
|
||||
|
||||
// Определяем progression base для подзадачи
|
||||
var subtaskProgressionBasePtr *float64
|
||||
if subtaskProgressionBase.Valid {
|
||||
subtaskProgressionBasePtr = &subtaskProgressionBase.Float64
|
||||
} else if progressionBase.Valid {
|
||||
subtaskProgressionBasePtr = &progressionBase.Float64
|
||||
}
|
||||
|
||||
// Строим map позиция → новый глобальный индекс и добавляем ноды
|
||||
positionToIndex := make(map[int]int)
|
||||
for _, sre := range subtaskRewards {
|
||||
reward := Reward{
|
||||
Value: sre.rewardValue,
|
||||
UseProgression: sre.useProgression,
|
||||
}
|
||||
score := calculateRewardScore(reward, progressionValuePtr, subtaskProgressionBasePtr)
|
||||
positionToIndex[sre.position] = nextNodeIndex
|
||||
nodes = append(nodes, TodayEntryNode{
|
||||
ProjectName: sre.projectName,
|
||||
Score: score,
|
||||
Index: nextNodeIndex,
|
||||
})
|
||||
nextNodeIndex++
|
||||
}
|
||||
|
||||
// Переписываем reward_message подзадачи, заменяя $position на ${globalIndex}
|
||||
subtaskText := subtaskRewardMsg
|
||||
// Заменяем $subtaskName
|
||||
subtaskText = strings.ReplaceAll(subtaskText, "$subtaskName", subtaskName)
|
||||
// Заменяем $name
|
||||
subtaskText = strings.ReplaceAll(subtaskText, "$name", taskName)
|
||||
// Заменяем ${pos} и $pos на ${globalIndex}
|
||||
for pos, globalIdx := range positionToIndex {
|
||||
newPlaceholder := fmt.Sprintf("${%d}", globalIdx)
|
||||
subtaskText = strings.ReplaceAll(subtaskText, fmt.Sprintf("${%d}", pos), newPlaceholder)
|
||||
}
|
||||
for i := 99; i >= 0; i-- {
|
||||
if globalIdx, ok := positionToIndex[i]; ok {
|
||||
newPlaceholder := fmt.Sprintf("${%d}", globalIdx)
|
||||
re := regexp.MustCompile(fmt.Sprintf(`\$%d(\D|$)`, i))
|
||||
subtaskText = re.ReplaceAllStringFunc(subtaskText, func(match string) string {
|
||||
suffix := []rune(match)[len([]rune(fmt.Sprintf("$%d", i))):]
|
||||
return newPlaceholder + string(suffix)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
entryText += "\n + " + subtaskText
|
||||
}
|
||||
subtaskRows.Close()
|
||||
}
|
||||
|
||||
taskIDCopy := taskID
|
||||
entries = append(entries, TodayEntry{
|
||||
IsDraft: true,
|
||||
|
||||
Binary file not shown.
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "play-life-web",
|
||||
"version": "6.15.3",
|
||||
"version": "6.15.4",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"dev": "vite",
|
||||
|
||||
Reference in New Issue
Block a user