refactor: test run case status messages duplication
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
import { TestTypeType } from '@/types/testType';
|
||||
import { PriorityType } from '@/types/priority';
|
||||
import { TestStatusType } from '@/types/testStatus';
|
||||
|
||||
const roles = [{ uid: 'administrator' }, { uid: 'user' }];
|
||||
|
||||
@@ -12,6 +13,18 @@ const locales = [
|
||||
{ code: 'ja', name: '日本語' },
|
||||
];
|
||||
|
||||
const testRunCaseStatus: TestStatusType[] = [
|
||||
{
|
||||
uid: 'untested',
|
||||
color: 'primary',
|
||||
chartColor: '#3ac6e1',
|
||||
},
|
||||
{ uid: 'passed', color: 'success', chartColor: '#6ea56c' },
|
||||
{ uid: 'failed', color: 'danger', chartColor: '#f15f47' },
|
||||
{ uid: 'retest', color: 'warning', chartColor: '#fba91e' },
|
||||
{ uid: 'skipped', color: 'primary', chartColor: '#805aab' },
|
||||
];
|
||||
|
||||
const priorities: PriorityType[] = [
|
||||
{ uid: 'critical', color: '#bb3e03', chartColor: '#bb3e03' },
|
||||
{ uid: 'high', color: '#ca6702', chartColor: '#ca6702' },
|
||||
@@ -53,18 +66,6 @@ const testRunStatus = [
|
||||
{ uid: 'closed' },
|
||||
];
|
||||
|
||||
const testRunCaseStatus = [
|
||||
{
|
||||
uid: 'untested',
|
||||
color: 'primary',
|
||||
chartColor: '#3ac6e1',
|
||||
},
|
||||
{ uid: 'passed', color: 'success', chartColor: '#6ea56c' },
|
||||
{ uid: 'failed', color: 'danger', chartColor: '#f15f47' },
|
||||
{ uid: 'retest', color: 'warning', chartColor: '#fba91e' },
|
||||
{ uid: 'skipped', color: 'primary', chartColor: '#805aab' },
|
||||
];
|
||||
|
||||
export {
|
||||
roles,
|
||||
memberRoles,
|
||||
|
||||
@@ -1,4 +1,11 @@
|
||||
{
|
||||
"Status": {
|
||||
"untested": "Untested",
|
||||
"passed": "Passed",
|
||||
"failed": "Failed",
|
||||
"retest": "Retest",
|
||||
"skipped": "Skipped"
|
||||
},
|
||||
"Priority": {
|
||||
"critical": "Critical",
|
||||
"high": "High",
|
||||
@@ -128,11 +135,6 @@
|
||||
"test_cases": "Test Cases",
|
||||
"test_runs": "Test Runs",
|
||||
"progress": "Progress",
|
||||
"untested": "Untested",
|
||||
"passed": "Passed",
|
||||
"failed": "Failed",
|
||||
"retest": "Retest",
|
||||
"skipped": "Skipped",
|
||||
"test_classification": "Test Classification",
|
||||
"by_type": "By test type",
|
||||
"by_priority": "By test priority"
|
||||
@@ -241,11 +243,6 @@
|
||||
"priority": "Priority",
|
||||
"status": "Status",
|
||||
"actions": "Actions",
|
||||
"untested": "Untested",
|
||||
"passed": "Passed",
|
||||
"failed": "Failed",
|
||||
"retest": "Retest",
|
||||
"skipped": "Skipped",
|
||||
"select_test_case": "Select test cases",
|
||||
"test_case_selection": "Test case selection",
|
||||
"include_in_run": "Include in run",
|
||||
|
||||
@@ -1,4 +1,11 @@
|
||||
{
|
||||
"Status": {
|
||||
"untested": "未実行",
|
||||
"passed": "成功",
|
||||
"failed": "失敗",
|
||||
"retest": "再テスト",
|
||||
"skipped": "スキップ"
|
||||
},
|
||||
"Priority": {
|
||||
"priority": "優先度",
|
||||
"critical": "致",
|
||||
@@ -129,11 +136,6 @@
|
||||
"test_cases": "テストケース",
|
||||
"test_runs": "テストラン",
|
||||
"progress": "進捗",
|
||||
"untested": "未実行",
|
||||
"passed": "成功",
|
||||
"failed": "失敗",
|
||||
"retest": "再テスト",
|
||||
"skipped": "スキップ",
|
||||
"test_classification": "テスト分類",
|
||||
"by_type": "タイプ別",
|
||||
"by_priority": "優先度別"
|
||||
@@ -242,11 +244,6 @@
|
||||
"priority": "優先度",
|
||||
"status": "ステータス",
|
||||
"actions": "アクション",
|
||||
"untested": "未実行",
|
||||
"passed": "成功",
|
||||
"failed": "失敗",
|
||||
"retest": "再テスト",
|
||||
"skipped": "スキップ",
|
||||
"select_test_case": "テストケースを選択",
|
||||
"test_case_selection": "テストケース選択",
|
||||
"include_in_run": "テストランに含める",
|
||||
|
||||
@@ -10,11 +10,13 @@ import { TokenContext } from '@/utils/TokenProvider';
|
||||
import { aggregateBasicInfo, aggregateTestPriority, aggregateTestType, aggregateProgress } from './aggregate';
|
||||
import Config from '@/config/config';
|
||||
import { useTheme } from 'next-themes';
|
||||
import { PriorityMessages } from '@/types/priority';
|
||||
import { TestTypeMessages } from '@/types/testType';
|
||||
import TestTypesChart from './TestTypesDonutChart';
|
||||
import TestPriorityChart from './TestPriorityDonutChart';
|
||||
import TestProgressBarChart from './TestProgressColumnChart';
|
||||
import { TestStatusMessages } from '@/types/testStatus';
|
||||
import { TestTypeMessages } from '@/types/testType';
|
||||
import { PriorityMessages } from '@/types/priority';
|
||||
|
||||
const apiServer = Config.apiServer;
|
||||
|
||||
async function fetchProject(jwt: string, projectId: number) {
|
||||
@@ -43,11 +45,12 @@ async function fetchProject(jwt: string, projectId: number) {
|
||||
type Props = {
|
||||
projectId: string;
|
||||
messages: HomeMessages;
|
||||
statusMessages: TestStatusMessages;
|
||||
testTypeMessages: TestTypeMessages;
|
||||
priorityMessages: PriorityMessages;
|
||||
};
|
||||
|
||||
export function ProjectHome({ projectId, messages, testTypeMessages, priorityMessages }: Props) {
|
||||
export function ProjectHome({ projectId, messages, statusMessages, testTypeMessages, priorityMessages }: Props) {
|
||||
const context = useContext(TokenContext);
|
||||
const { theme, setTheme } = useTheme();
|
||||
const [project, setProject] = useState({
|
||||
@@ -71,7 +74,7 @@ export function ProjectHome({ projectId, messages, testTypeMessages, priorityMes
|
||||
}
|
||||
|
||||
try {
|
||||
const data = await fetchProject(context.token.access_token, projectId);
|
||||
const data = await fetchProject(context.token.access_token, Number(projectId));
|
||||
setProject(data);
|
||||
} catch (error: any) {
|
||||
console.error('Error in effect:', error.message);
|
||||
@@ -94,7 +97,7 @@ export function ProjectHome({ projectId, messages, testTypeMessages, priorityMes
|
||||
const priorityRet = aggregateTestPriority(project);
|
||||
setPriorityCounts([...priorityRet]);
|
||||
|
||||
const { series, categories } = aggregateProgress(project, messages);
|
||||
const { series, categories } = aggregateProgress(project, statusMessages);
|
||||
setProgressSeries([...series]);
|
||||
setProgressCategories([...categories]);
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import { ProjectType } from '@/types/project';
|
||||
import { testTypes, priorities, testRunCaseStatus } from '@/config/selection';
|
||||
import { HomeMessages } from './page';
|
||||
import { TestStatusMessages } from '@/types/testStatus';
|
||||
|
||||
// aggregate folder, case, run mum
|
||||
function aggregateBasicInfo(project: ProjectType) {
|
||||
@@ -50,9 +50,9 @@ function aggregateTestPriority(project: ProjectType) {
|
||||
return result;
|
||||
}
|
||||
|
||||
function aggregateProgress(project: ProjectType, messages: HomeMessages) {
|
||||
function aggregateProgress(project: ProjectType, statusMessages: TestStatusMessages) {
|
||||
let series = testRunCaseStatus.map((status) => {
|
||||
return { name: messages[status.uid], data: [] };
|
||||
return { name: statusMessages[status.uid], data: [] };
|
||||
});
|
||||
let categories = [];
|
||||
|
||||
|
||||
@@ -2,17 +2,13 @@ import { ProjectHome } from './ProjectHome';
|
||||
import { useTranslations } from 'next-intl';
|
||||
import { PriorityMessages } from '@/types/priority';
|
||||
import { TestTypeMessages } from '@/types/testType';
|
||||
import { TestStatusMessages } from '@/types/testStatus';
|
||||
|
||||
export type HomeMessages = {
|
||||
folders: string;
|
||||
testCases: string;
|
||||
testRuns: string;
|
||||
progress: string;
|
||||
untested: string;
|
||||
passed: string;
|
||||
failed: string;
|
||||
retest: string;
|
||||
skipped: string;
|
||||
testClassification: string;
|
||||
byType: string;
|
||||
byPriority: string;
|
||||
@@ -25,16 +21,20 @@ export default function Page({ params }: { params: { projectId: string } }) {
|
||||
testCases: t('test_cases'),
|
||||
testRuns: t('test_runs'),
|
||||
progress: t('progress'),
|
||||
untested: t('untested'),
|
||||
passed: t('passed'),
|
||||
failed: t('failed'),
|
||||
retest: t('retest'),
|
||||
skipped: t('skipped'),
|
||||
testClassification: t('test_classification'),
|
||||
byType: t('by_type'),
|
||||
byPriority: t('by_priority'),
|
||||
};
|
||||
|
||||
const st = useTranslations('Status');
|
||||
const statusMessages: TestStatusMessages = {
|
||||
untested: st('untested'),
|
||||
passed: st('passed'),
|
||||
failed: st('failed'),
|
||||
retest: st('retest'),
|
||||
skipped: st('skipped'),
|
||||
};
|
||||
|
||||
const tt = useTranslations('Type');
|
||||
const testTypeMessages: TestTypeMessages = {
|
||||
other: tt('other'),
|
||||
@@ -65,6 +65,7 @@ export default function Page({ params }: { params: { projectId: string } }) {
|
||||
<ProjectHome
|
||||
projectId={params.projectId}
|
||||
messages={messages}
|
||||
statusMessages={statusMessages}
|
||||
testTypeMessages={testTypeMessages}
|
||||
priorityMessages={priorityMessages}
|
||||
/>
|
||||
|
||||
@@ -38,6 +38,7 @@ import { TokenContext } from '@/utils/TokenProvider';
|
||||
import { useTheme } from 'next-themes';
|
||||
import { useFormGuard } from '@/utils/formGuard';
|
||||
import { PriorityMessages } from '@/types/priority';
|
||||
import { TestStatusMessages } from '@/types/testStatus';
|
||||
|
||||
const defaultTestRun = {
|
||||
id: 0,
|
||||
@@ -54,11 +55,12 @@ type Props = {
|
||||
projectId: string;
|
||||
runId: string;
|
||||
messages: RunMessages;
|
||||
statusMessages: TestStatusMessages;
|
||||
priorityMessages: PriorityMessages;
|
||||
locale: string;
|
||||
};
|
||||
|
||||
export default function RunEditor({ projectId, runId, messages, priorityMessages, locale }: Props) {
|
||||
export default function RunEditor({ projectId, runId, messages, statusMessages, priorityMessages, locale }: Props) {
|
||||
const context = useContext(TokenContext);
|
||||
const { theme, setTheme } = useTheme();
|
||||
const [testRun, setTestRun] = useState<RunType>(defaultTestRun);
|
||||
@@ -204,7 +206,7 @@ export default function RunEditor({ projectId, runId, messages, priorityMessages
|
||||
</Tooltip>
|
||||
</div>
|
||||
|
||||
<RunProgressChart statusCounts={runStatusCounts} messages={messages} theme={theme} />
|
||||
<RunProgressChart statusCounts={runStatusCounts} statusMessages={statusMessages} theme={theme} />
|
||||
</div>
|
||||
</div>
|
||||
<div className="flex-grow">
|
||||
@@ -316,6 +318,7 @@ export default function RunEditor({ projectId, runId, messages, priorityMessages
|
||||
onIncludeCase={(includeTestId) => handleIncludeExcludeCase(true, includeTestId)}
|
||||
onExcludeCase={(excludeCaseId) => handleIncludeExcludeCase(false, excludeCaseId)}
|
||||
messages={messages}
|
||||
statusMessages={statusMessages}
|
||||
priorityMessages={priorityMessages}
|
||||
/>
|
||||
</div>
|
||||
|
||||
@@ -2,16 +2,17 @@ import React from 'react';
|
||||
import { useState, useEffect } from 'react';
|
||||
import dynamic from 'next/dynamic';
|
||||
import { testRunCaseStatus } from '@/config/selection';
|
||||
import { RunStatusCountType, RunMessages } from '@/types/run';
|
||||
import { RunStatusCountType } from '@/types/run';
|
||||
import { TestStatusMessages } from '@/types/testStatus';
|
||||
const Chart = dynamic(() => import('react-apexcharts'), { ssr: false });
|
||||
|
||||
type Props = {
|
||||
statusCounts: RunStatusCountType[];
|
||||
messages: RunMessages;
|
||||
statusMessages: TestStatusMessages;
|
||||
theme: string | undefined;
|
||||
};
|
||||
|
||||
export default function RunProgressDounut({ statusCounts, messages, theme }: Props) {
|
||||
export default function RunProgressDounut({ statusCounts, statusMessages, theme }: Props) {
|
||||
const [chartData, setChartData] = useState({
|
||||
series: [],
|
||||
options: {
|
||||
@@ -28,7 +29,7 @@ export default function RunProgressDounut({ statusCounts, messages, theme }: Pro
|
||||
return found ? found.count : 0;
|
||||
});
|
||||
|
||||
const labels = testRunCaseStatus.map((entry) => messages[entry.uid]);
|
||||
const labels = testRunCaseStatus.map((entry) => statusMessages[entry.uid]);
|
||||
const colors = testRunCaseStatus.map((entry) => entry.chartColor);
|
||||
const legend = {
|
||||
labels: {
|
||||
|
||||
@@ -32,6 +32,7 @@ import { RunMessages } from '@/types/run';
|
||||
import TestCaseDetailDialog from './TestCaseDetailDialog';
|
||||
import { PriorityMessages } from '@/types/priority';
|
||||
import TestCasePriority from '@/components/TestCasePriority';
|
||||
import { TestStatusMessages } from '@/types/testStatus';
|
||||
|
||||
type Props = {
|
||||
cases: CaseType[];
|
||||
@@ -42,6 +43,7 @@ type Props = {
|
||||
onIncludeCase: (includeCaseId: number) => {};
|
||||
onExcludeCase: (excludeCaseId: number) => {};
|
||||
messages: RunMessages;
|
||||
statusMessages: TestStatusMessages;
|
||||
priorityMessages: PriorityMessages;
|
||||
};
|
||||
|
||||
@@ -54,6 +56,7 @@ export default function TestCaseSelector({
|
||||
onIncludeCase,
|
||||
onExcludeCase,
|
||||
messages,
|
||||
statusMessages,
|
||||
priorityMessages,
|
||||
}: Props) {
|
||||
const headerColumns = [
|
||||
@@ -157,7 +160,7 @@ export default function TestCaseSelector({
|
||||
startContent={isIncluded && renderStatusIcon(testRunCaseStatus[runStatus].uid)}
|
||||
endContent={isIncluded && <ChevronDown size={16} />}
|
||||
>
|
||||
<span className="w-12">{isIncluded && messages[testRunCaseStatus[runStatus].uid]}</span>
|
||||
<span className="w-12">{isIncluded && statusMessages[testRunCaseStatus[runStatus].uid]}</span>
|
||||
</Button>
|
||||
</DropdownTrigger>
|
||||
<DropdownMenu disabledKeys={disabledStatusKeys} aria-label="test case actions">
|
||||
@@ -167,7 +170,7 @@ export default function TestCaseSelector({
|
||||
startContent={renderStatusIcon(runCaseStatus.uid)}
|
||||
onPress={() => onChangeStatus(testCase.id, index)}
|
||||
>
|
||||
{messages[runCaseStatus.uid]}
|
||||
{statusMessages[runCaseStatus.uid]}
|
||||
</DropdownItem>
|
||||
))}
|
||||
</DropdownMenu>
|
||||
|
||||
@@ -2,6 +2,7 @@ import RunEditor from './RunEditor';
|
||||
import { useTranslations } from 'next-intl';
|
||||
import { RunMessages } from '@/types/run';
|
||||
import { PriorityMessages } from '@/types/priority';
|
||||
import { TestStatusMessages } from '@/types/testStatus';
|
||||
|
||||
export default function Page({ params }: { params: { projectId: string; runId: string; locale: string } }) {
|
||||
const t = useTranslations('Run');
|
||||
@@ -24,11 +25,6 @@ export default function Page({ params }: { params: { projectId: string; runId: s
|
||||
priority: t('priority'),
|
||||
actions: t('actions'),
|
||||
status: t('status'),
|
||||
untested: t('untested'),
|
||||
passed: t('passed'),
|
||||
failed: t('failed'),
|
||||
retest: t('retest'),
|
||||
skipped: t('skipped'),
|
||||
selectTestCase: t('select_test_case'),
|
||||
testCaseSelection: t('test_case_selection'),
|
||||
includeInRun: t('include_in_run'),
|
||||
@@ -36,25 +32,21 @@ export default function Page({ params }: { params: { projectId: string; runId: s
|
||||
noCasesFound: t('no_cases_found'),
|
||||
areYouSureLeave: t('are_you_sure_leave'),
|
||||
type: t('type'),
|
||||
other: t('other'),
|
||||
security: t('security'),
|
||||
performance: t('performance'),
|
||||
accessibility: t('accessibility'),
|
||||
functional: t('functional'),
|
||||
acceptance: t('acceptance'),
|
||||
usability: t('usability'),
|
||||
smokeSanity: t('smoke_sanity'),
|
||||
compatibility: t('compatibility'),
|
||||
destructive: t('destructive'),
|
||||
regression: t('regression'),
|
||||
automated: t('automated'),
|
||||
manual: t('manual'),
|
||||
preconditions: t('preconditions'),
|
||||
expectedResult: t('expected_result'),
|
||||
detailsOfTheStep: t('details_of_the_step'),
|
||||
close: t('close'),
|
||||
};
|
||||
|
||||
const st = useTranslations('Status');
|
||||
const statusMessages: TestStatusMessages = {
|
||||
untested: st('untested'),
|
||||
passed: st('passed'),
|
||||
failed: st('failed'),
|
||||
retest: st('retest'),
|
||||
skipped: st('skipped'),
|
||||
};
|
||||
|
||||
const pt = useTranslations('Priority');
|
||||
const priorityMessages: PriorityMessages = {
|
||||
critical: pt('critical'),
|
||||
@@ -68,6 +60,7 @@ export default function Page({ params }: { params: { projectId: string; runId: s
|
||||
projectId={params.projectId}
|
||||
runId={params.runId}
|
||||
messages={messages}
|
||||
statusMessages={statusMessages}
|
||||
priorityMessages={priorityMessages}
|
||||
locale={params.locale}
|
||||
/>
|
||||
|
||||
17
frontend/types/testStatus.ts
Normal file
17
frontend/types/testStatus.ts
Normal file
@@ -0,0 +1,17 @@
|
||||
type TestStatusUidType = 'untested' | 'passed' | 'failed' | 'retest' | 'skipped';
|
||||
|
||||
type TestStatusType = {
|
||||
uid: TestStatusUidType;
|
||||
color: string;
|
||||
chartColor: string;
|
||||
};
|
||||
|
||||
type TestStatusMessages = {
|
||||
untested: string;
|
||||
passed: string;
|
||||
failed: string;
|
||||
retest: string;
|
||||
skipped: string;
|
||||
};
|
||||
|
||||
export type { TestStatusUidType, TestStatusType, TestStatusMessages };
|
||||
Reference in New Issue
Block a user