generated from VLADIMIR/template
up
This commit is contained in:
@@ -9,14 +9,14 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
func TestSafeFailure(t *testing.T) {
|
func TestSafeFailure(t *testing.T) {
|
||||||
validation := &game_package_service.ValidationError{Reason: "некорректная команда"}
|
validation := &game_package_service.ValidationError{Reason: "шаг экранов №2 — текст экрана не должен быть пустым"}
|
||||||
for _, tc := range []struct {
|
for _, tc := range []struct {
|
||||||
name string
|
name string
|
||||||
err error
|
err error
|
||||||
want string
|
want string
|
||||||
}{
|
}{
|
||||||
{"validation", validation, "Не удалось подготовить автономный пакет: некорректная команда"},
|
{"validation", validation, "Не удалось подготовить автономный пакет: шаг экранов №2 — текст экрана не должен быть пустым"},
|
||||||
{"wrapped validation", fmt.Errorf("private path: %w", validation), "Не удалось подготовить автономный пакет: некорректная команда"},
|
{"wrapped validation", fmt.Errorf("private path: %w", validation), "Не удалось подготовить автономный пакет: шаг экранов №2 — текст экрана не должен быть пустым"},
|
||||||
{"invalid package", errors.Join(game_package_service.ErrInvalidPackage, errors.New("private")), "Данные игры не подходят для автономного пакета."},
|
{"invalid package", errors.Join(game_package_service.ErrInvalidPackage, errors.New("private")), "Данные игры не подходят для автономного пакета."},
|
||||||
{"technical", errors.New("private password"), "Не удалось подготовить пакет. Запустите экспорт повторно."},
|
{"technical", errors.New("private password"), "Не удалось подготовить пакет. Запустите экспорт повторно."},
|
||||||
{"media", game_package_service.ErrMediaUnavailable, "Не удалось получить медиафайлы игры. Проверьте их доступность и повторите экспорт."},
|
{"media", game_package_service.ErrMediaUnavailable, "Не удалось получить медиафайлы игры. Проверьте их доступность и повторите экспорт."},
|
||||||
|
|||||||
@@ -882,3 +882,33 @@ func TestPackageValidatesScreenSteps(t *testing.T) {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestScreenStepFailureExplainsReason(t *testing.T) {
|
||||||
|
for _, tc := range []struct {
|
||||||
|
name string
|
||||||
|
step game_screen_plans_repo.Step
|
||||||
|
reason string
|
||||||
|
}{
|
||||||
|
{"mode", game_screen_plans_repo.Step{Mode: 11}, "неподдерживаемый режим экрана"},
|
||||||
|
{"timer type", game_screen_plans_repo.Step{Mode: 7, TimerType: 3}, "неизвестный тип таймера"},
|
||||||
|
{"duration", game_screen_plans_repo.Step{Mode: 7}, "длительность таймера должна быть от 1 до 86400 секунд"},
|
||||||
|
{"timer label", game_screen_plans_repo.Step{Mode: 7, TimerDurationSeconds: 1, TimerLabel: strings.Repeat("a", 201)}, "подпись таймера превышает 200 байт"},
|
||||||
|
{"empty text", game_screen_plans_repo.Step{Mode: 8, Text: " "}, "текст экрана не должен быть пустым"},
|
||||||
|
{"long text", game_screen_plans_repo.Step{Mode: 8, Text: strings.Repeat("a", 10001)}, "текст экрана превышает 10000 байт"},
|
||||||
|
{"QR URL", game_screen_plans_repo.Step{Mode: 9, QRURL: "javascript:private"}, "ссылка QR-кода должна использовать HTTP/HTTPS, содержать адрес сайта, не содержать логин, пароль и крайние пробелы и занимать не более 2048 байт"},
|
||||||
|
{"QR caption", game_screen_plans_repo.Step{Mode: 9, QRURL: "https://example.org", Text: strings.Repeat("a", 10001)}, "подпись QR-кода превышает 10000 байт"},
|
||||||
|
} {
|
||||||
|
t.Run(tc.name, func(t *testing.T) {
|
||||||
|
snapshot, _ := fixture()
|
||||||
|
snapshot.Data.ScreenPlan.Steps = []game_screen_plans_repo.Step{{Mode: 1}, tc.step}
|
||||||
|
err := validateData(&snapshot.Data)
|
||||||
|
var validation *ValidationError
|
||||||
|
if !errors.Is(err, ErrInvalidPackage) || !errors.As(err, &validation) {
|
||||||
|
t.Fatalf("expected validation error, got %v", err)
|
||||||
|
}
|
||||||
|
if want := "шаг экранов №2 — " + tc.reason; validation.Reason != want {
|
||||||
|
t.Fatalf("got %q, want %q", validation.Reason, want)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -156,13 +156,28 @@ func validateData(data *Data) error {
|
|||||||
(len(plan.Steps) > 0 && plan.CurrentStep >= len(plan.Steps)) {
|
(len(plan.Steps) > 0 && plan.CurrentStep >= len(plan.Steps)) {
|
||||||
return invalid("некорректный план экранов")
|
return invalid("некорректный план экранов")
|
||||||
}
|
}
|
||||||
for _, step := range plan.Steps {
|
for i, step := range plan.Steps {
|
||||||
if !screen_service.ValidMode(step.Mode) ||
|
var reason string
|
||||||
!screen_service.ValidTimerType(step.TimerType) ||
|
switch {
|
||||||
(step.Mode == 9 && !screen_service.ValidQR(step.QRURL, step.Text)) ||
|
case !screen_service.ValidMode(step.Mode):
|
||||||
(step.Mode == 7 && (step.TimerDurationSeconds <= 0 || step.TimerDurationSeconds > 86400 || len(step.TimerLabel) > 200)) ||
|
reason = "неподдерживаемый режим экрана"
|
||||||
(step.Mode == 8 && (strings.TrimSpace(step.Text) == "" || len(step.Text) > 10000)) {
|
case !screen_service.ValidTimerType(step.TimerType):
|
||||||
return invalid("некорректный шаг плана экранов")
|
reason = "неизвестный тип таймера"
|
||||||
|
case step.Mode == 7 && (step.TimerDurationSeconds <= 0 || step.TimerDurationSeconds > 86400):
|
||||||
|
reason = "длительность таймера должна быть от 1 до 86400 секунд"
|
||||||
|
case step.Mode == 7 && len(step.TimerLabel) > 200:
|
||||||
|
reason = "подпись таймера превышает 200 байт"
|
||||||
|
case step.Mode == 8 && strings.TrimSpace(step.Text) == "":
|
||||||
|
reason = "текст экрана не должен быть пустым"
|
||||||
|
case step.Mode == 8 && len(step.Text) > 10000:
|
||||||
|
reason = "текст экрана превышает 10000 байт"
|
||||||
|
case step.Mode == 9 && !screen_service.ValidQR(step.QRURL, ""):
|
||||||
|
reason = "ссылка QR-кода должна использовать HTTP/HTTPS, содержать адрес сайта, не содержать логин, пароль и крайние пробелы и занимать не более 2048 байт"
|
||||||
|
case step.Mode == 9 && len(step.Text) > 10000:
|
||||||
|
reason = "подпись QR-кода превышает 10000 байт"
|
||||||
|
}
|
||||||
|
if reason != "" {
|
||||||
|
return invalid(fmt.Sprintf("шаг экранов №%d — %s", i+1, reason))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user