Merge pull request #1760 from github/koesie10/filter-export-copy
Add filtering and sorting to exported repo list
This commit is contained in:
@@ -123,6 +123,7 @@ import { VSCodeMockGitHubApiServer } from './mocks/vscode-mock-gh-api-server';
|
|||||||
import { VariantAnalysisResultsManager } from './remote-queries/variant-analysis-results-manager';
|
import { VariantAnalysisResultsManager } from './remote-queries/variant-analysis-results-manager';
|
||||||
import { initializeDbModule } from './databases/db-module';
|
import { initializeDbModule } from './databases/db-module';
|
||||||
import { ExtensionApp } from './common/vscode/vscode-app';
|
import { ExtensionApp } from './common/vscode/vscode-app';
|
||||||
|
import { RepositoriesFilterSortState } from './pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* extension.ts
|
* extension.ts
|
||||||
@@ -962,8 +963,8 @@ async function activateWithInstalledDistribution(
|
|||||||
);
|
);
|
||||||
|
|
||||||
ctx.subscriptions.push(
|
ctx.subscriptions.push(
|
||||||
commandRunner('codeQL.copyVariantAnalysisRepoList', async (variantAnalysisId: number) => {
|
commandRunner('codeQL.copyVariantAnalysisRepoList', async (variantAnalysisId: number, filterSort?: RepositoriesFilterSortState) => {
|
||||||
await variantAnalysisManager.copyRepoListToClipboard(variantAnalysisId);
|
await variantAnalysisManager.copyRepoListToClipboard(variantAnalysisId, filterSort);
|
||||||
})
|
})
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import {
|
|||||||
VariantAnalysisScannedRepositoryResult,
|
VariantAnalysisScannedRepositoryResult,
|
||||||
VariantAnalysisScannedRepositoryState,
|
VariantAnalysisScannedRepositoryState,
|
||||||
} from '../remote-queries/shared/variant-analysis';
|
} from '../remote-queries/shared/variant-analysis';
|
||||||
|
import { RepositoriesFilterSortState } from './variant-analysis-filter-sort';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This module contains types and code that are shared between
|
* This module contains types and code that are shared between
|
||||||
@@ -474,6 +475,7 @@ export interface OpenQueryTextMessage {
|
|||||||
|
|
||||||
export interface CopyRepositoryListMessage {
|
export interface CopyRepositoryListMessage {
|
||||||
t: 'copyRepositoryList';
|
t: 'copyRepositoryList';
|
||||||
|
filterSort?: RepositoriesFilterSortState;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ExportResultsMessage {
|
export interface ExportResultsMessage {
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import { Repository, RepositoryWithMetadata } from '../../remote-queries/shared/repository';
|
import { Repository, RepositoryWithMetadata } from '../remote-queries/shared/repository';
|
||||||
import { parseDate } from '../../pure/date';
|
import { parseDate } from './date';
|
||||||
|
|
||||||
export enum SortKey {
|
export enum SortKey {
|
||||||
Name = 'name',
|
Name = 'name',
|
||||||
@@ -71,3 +71,17 @@ export function compareWithResults(filterSortState: RepositoriesFilterSortState
|
|||||||
return fallbackSort(left.repository, right.repository);
|
return fallbackSort(left.repository, right.repository);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// These define the behavior for undefined input values
|
||||||
|
export function filterAndSortRepositoriesWithResults<T extends SortableResult>(repositories: T[], filterSortState: RepositoriesFilterSortState | undefined): T[];
|
||||||
|
export function filterAndSortRepositoriesWithResults<T extends SortableResult>(repositories: T[] | undefined, filterSortState: RepositoriesFilterSortState | undefined): T[] | undefined;
|
||||||
|
|
||||||
|
export function filterAndSortRepositoriesWithResults<T extends SortableResult>(repositories: T[] | undefined, filterSortState: RepositoriesFilterSortState | undefined): T[] | undefined {
|
||||||
|
if (!repositories) {
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
|
||||||
|
return repositories
|
||||||
|
.filter(repo => matchesFilter(repo.repository, filterSortState))
|
||||||
|
.sort(compareWithResults(filterSortState));
|
||||||
|
}
|
||||||
@@ -32,6 +32,11 @@ import * as os from 'os';
|
|||||||
import { cancelVariantAnalysis } from './gh-api/gh-actions-api-client';
|
import { cancelVariantAnalysis } from './gh-api/gh-actions-api-client';
|
||||||
import { ProgressCallback, UserCancellationException } from '../commandRunner';
|
import { ProgressCallback, UserCancellationException } from '../commandRunner';
|
||||||
import { CodeQLCliServer } from '../cli';
|
import { CodeQLCliServer } from '../cli';
|
||||||
|
import {
|
||||||
|
defaultFilterSortState,
|
||||||
|
filterAndSortRepositoriesWithResults,
|
||||||
|
RepositoriesFilterSortState,
|
||||||
|
} from '../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
export class VariantAnalysisManager extends DisposableObject implements VariantAnalysisViewManager<VariantAnalysisView> {
|
export class VariantAnalysisManager extends DisposableObject implements VariantAnalysisViewManager<VariantAnalysisView> {
|
||||||
private static readonly REPO_STATES_FILENAME = 'repo_states.json';
|
private static readonly REPO_STATES_FILENAME = 'repo_states.json';
|
||||||
@@ -368,13 +373,15 @@ export class VariantAnalysisManager extends DisposableObject implements VariantA
|
|||||||
await cancelVariantAnalysis(credentials, variantAnalysis);
|
await cancelVariantAnalysis(credentials, variantAnalysis);
|
||||||
}
|
}
|
||||||
|
|
||||||
public async copyRepoListToClipboard(variantAnalysisId: number) {
|
public async copyRepoListToClipboard(variantAnalysisId: number, filterSort: RepositoriesFilterSortState = defaultFilterSortState) {
|
||||||
const variantAnalysis = this.variantAnalyses.get(variantAnalysisId);
|
const variantAnalysis = this.variantAnalyses.get(variantAnalysisId);
|
||||||
if (!variantAnalysis) {
|
if (!variantAnalysis) {
|
||||||
throw new Error(`No variant analysis with id: ${variantAnalysisId}`);
|
throw new Error(`No variant analysis with id: ${variantAnalysisId}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
const fullNames = variantAnalysis.scannedRepos?.filter(a => a.resultCount && a.resultCount > 0).map(a => a.repository.fullName);
|
const filteredRepositories = filterAndSortRepositoriesWithResults(variantAnalysis.scannedRepos, filterSort);
|
||||||
|
|
||||||
|
const fullNames = filteredRepositories?.filter(a => a.resultCount && a.resultCount > 0).map(a => a.repository.fullName);
|
||||||
if (!fullNames || fullNames.length === 0) {
|
if (!fullNames || fullNames.length === 0) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -104,7 +104,7 @@ export class VariantAnalysisView extends AbstractWebview<ToVariantAnalysisMessag
|
|||||||
await this.openQueryText();
|
await this.openQueryText();
|
||||||
break;
|
break;
|
||||||
case 'copyRepositoryList':
|
case 'copyRepositoryList':
|
||||||
void commands.executeCommand('codeQL.copyVariantAnalysisRepoList', this.variantAnalysisId);
|
void commands.executeCommand('codeQL.copyVariantAnalysisRepoList', this.variantAnalysisId, msg.filterSort);
|
||||||
break;
|
break;
|
||||||
case 'exportResults':
|
case 'exportResults':
|
||||||
void commands.executeCommand('codeQL.exportVariantAnalysisResults', this.variantAnalysisId);
|
void commands.executeCommand('codeQL.exportVariantAnalysisResults', this.variantAnalysisId);
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ import React, { useState } from 'react';
|
|||||||
import { ComponentMeta } from '@storybook/react';
|
import { ComponentMeta } from '@storybook/react';
|
||||||
|
|
||||||
import { RepositoriesSearchSortRow as RepositoriesSearchSortRowComponent } from '../../view/variant-analysis/RepositoriesSearchSortRow';
|
import { RepositoriesSearchSortRow as RepositoriesSearchSortRowComponent } from '../../view/variant-analysis/RepositoriesSearchSortRow';
|
||||||
import { defaultFilterSortState } from '../../view/variant-analysis/filterSort';
|
import { defaultFilterSortState } from '../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
title: 'Variant Analysis/Repositories Search and Sort Row',
|
title: 'Variant Analysis/Repositories Search and Sort Row',
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ import React, { useState } from 'react';
|
|||||||
import { ComponentMeta } from '@storybook/react';
|
import { ComponentMeta } from '@storybook/react';
|
||||||
|
|
||||||
import { RepositoriesSort as RepositoriesSortComponent } from '../../view/variant-analysis/RepositoriesSort';
|
import { RepositoriesSort as RepositoriesSortComponent } from '../../view/variant-analysis/RepositoriesSort';
|
||||||
import { SortKey } from '../../view/variant-analysis/filterSort';
|
import { SortKey } from '../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
title: 'Variant Analysis/Repositories Sort',
|
title: 'Variant Analysis/Repositories Sort',
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import React from 'react';
|
import React, { useState } from 'react';
|
||||||
|
|
||||||
import { ComponentMeta, ComponentStory } from '@storybook/react';
|
import { ComponentMeta, ComponentStory } from '@storybook/react';
|
||||||
|
|
||||||
@@ -8,6 +8,7 @@ import { VariantAnalysisRepoStatus, VariantAnalysisStatus } from '../../remote-q
|
|||||||
import { createMockScannedRepo } from '../../vscode-tests/factories/remote-queries/shared/scanned-repositories';
|
import { createMockScannedRepo } from '../../vscode-tests/factories/remote-queries/shared/scanned-repositories';
|
||||||
import { createMockVariantAnalysis } from '../../vscode-tests/factories/remote-queries/shared/variant-analysis';
|
import { createMockVariantAnalysis } from '../../vscode-tests/factories/remote-queries/shared/variant-analysis';
|
||||||
import { createMockRepositoryWithMetadata } from '../../vscode-tests/factories/remote-queries/shared/repository';
|
import { createMockRepositoryWithMetadata } from '../../vscode-tests/factories/remote-queries/shared/repository';
|
||||||
|
import { defaultFilterSortState, RepositoriesFilterSortState } from '../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
title: 'Variant Analysis/Variant Analysis Outcome Panels',
|
title: 'Variant Analysis/Variant Analysis Outcome Panels',
|
||||||
@@ -21,9 +22,13 @@ export default {
|
|||||||
],
|
],
|
||||||
} as ComponentMeta<typeof VariantAnalysisOutcomePanels>;
|
} as ComponentMeta<typeof VariantAnalysisOutcomePanels>;
|
||||||
|
|
||||||
const Template: ComponentStory<typeof VariantAnalysisOutcomePanels> = (args) => (
|
const Template: ComponentStory<typeof VariantAnalysisOutcomePanels> = (args) => {
|
||||||
<VariantAnalysisOutcomePanels {...args} />
|
const [filterSortState, setFilterSortState] = useState<RepositoriesFilterSortState>(defaultFilterSortState);
|
||||||
);
|
|
||||||
|
return (
|
||||||
|
<VariantAnalysisOutcomePanels {...args} filterSortState={filterSortState} setFilterSortState={setFilterSortState} />
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
export const WithoutSkippedRepos = Template.bind({});
|
export const WithoutSkippedRepos = Template.bind({});
|
||||||
WithoutSkippedRepos.args = {
|
WithoutSkippedRepos.args = {
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import * as React from 'react';
|
import * as React from 'react';
|
||||||
import { Dispatch, SetStateAction, useCallback } from 'react';
|
import { Dispatch, SetStateAction, useCallback } from 'react';
|
||||||
import styled from 'styled-components';
|
import styled from 'styled-components';
|
||||||
import { RepositoriesFilterSortState, SortKey } from './filterSort';
|
import { RepositoriesFilterSortState, SortKey } from '../../pure/variant-analysis-filter-sort';
|
||||||
import { RepositoriesSearch } from './RepositoriesSearch';
|
import { RepositoriesSearch } from './RepositoriesSearch';
|
||||||
import { RepositoriesSort } from './RepositoriesSort';
|
import { RepositoriesSort } from './RepositoriesSort';
|
||||||
|
|
||||||
|
|||||||
@@ -2,7 +2,7 @@ import * as React from 'react';
|
|||||||
import { useCallback } from 'react';
|
import { useCallback } from 'react';
|
||||||
import styled from 'styled-components';
|
import styled from 'styled-components';
|
||||||
import { VSCodeDropdown, VSCodeOption } from '@vscode/webview-ui-toolkit/react';
|
import { VSCodeDropdown, VSCodeOption } from '@vscode/webview-ui-toolkit/react';
|
||||||
import { SortKey } from './filterSort';
|
import { SortKey } from '../../pure/variant-analysis-filter-sort';
|
||||||
import { Codicon } from '../common';
|
import { Codicon } from '../common';
|
||||||
|
|
||||||
const Dropdown = styled(VSCodeDropdown)`
|
const Dropdown = styled(VSCodeDropdown)`
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import * as React from 'react';
|
import * as React from 'react';
|
||||||
import { useEffect, useState } from 'react';
|
import { useCallback, useEffect, useState } from 'react';
|
||||||
|
|
||||||
import {
|
import {
|
||||||
VariantAnalysis as VariantAnalysisDomainModel,
|
VariantAnalysis as VariantAnalysisDomainModel,
|
||||||
@@ -11,6 +11,7 @@ import { VariantAnalysisOutcomePanels } from './VariantAnalysisOutcomePanels';
|
|||||||
import { VariantAnalysisLoading } from './VariantAnalysisLoading';
|
import { VariantAnalysisLoading } from './VariantAnalysisLoading';
|
||||||
import { ToVariantAnalysisMessage } from '../../pure/interface-types';
|
import { ToVariantAnalysisMessage } from '../../pure/interface-types';
|
||||||
import { vscode } from '../vscode-api';
|
import { vscode } from '../vscode-api';
|
||||||
|
import { defaultFilterSortState, RepositoriesFilterSortState } from '../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
type Props = {
|
type Props = {
|
||||||
variantAnalysis?: VariantAnalysisDomainModel;
|
variantAnalysis?: VariantAnalysisDomainModel;
|
||||||
@@ -36,12 +37,6 @@ const stopQuery = () => {
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
const copyRepositoryList = () => {
|
|
||||||
vscode.postMessage({
|
|
||||||
t: 'copyRepositoryList',
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
const exportResults = () => {
|
const exportResults = () => {
|
||||||
vscode.postMessage({
|
vscode.postMessage({
|
||||||
t: 'exportResults',
|
t: 'exportResults',
|
||||||
@@ -64,6 +59,7 @@ export function VariantAnalysis({
|
|||||||
const [repoResults, setRepoResults] = useState<VariantAnalysisScannedRepositoryResult[]>(initialRepoResults);
|
const [repoResults, setRepoResults] = useState<VariantAnalysisScannedRepositoryResult[]>(initialRepoResults);
|
||||||
|
|
||||||
const [selectedRepositoryIds, setSelectedRepositoryIds] = useState<number[]>([]);
|
const [selectedRepositoryIds, setSelectedRepositoryIds] = useState<number[]>([]);
|
||||||
|
const [filterSortState, setFilterSortState] = useState<RepositoriesFilterSortState>(defaultFilterSortState);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const listener = (evt: MessageEvent) => {
|
const listener = (evt: MessageEvent) => {
|
||||||
@@ -98,6 +94,13 @@ export function VariantAnalysis({
|
|||||||
};
|
};
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
|
const copyRepositoryList = useCallback(() => {
|
||||||
|
vscode.postMessage({
|
||||||
|
t: 'copyRepositoryList',
|
||||||
|
filterSort: filterSortState,
|
||||||
|
});
|
||||||
|
}, [filterSortState]);
|
||||||
|
|
||||||
if (variantAnalysis?.actionsWorkflowRunId === undefined) {
|
if (variantAnalysis?.actionsWorkflowRunId === undefined) {
|
||||||
return <VariantAnalysisLoading />;
|
return <VariantAnalysisLoading />;
|
||||||
}
|
}
|
||||||
@@ -119,6 +122,8 @@ export function VariantAnalysis({
|
|||||||
repositoryResults={repoResults}
|
repositoryResults={repoResults}
|
||||||
selectedRepositoryIds={selectedRepositoryIds}
|
selectedRepositoryIds={selectedRepositoryIds}
|
||||||
setSelectedRepositoryIds={setSelectedRepositoryIds}
|
setSelectedRepositoryIds={setSelectedRepositoryIds}
|
||||||
|
filterSortState={filterSortState}
|
||||||
|
setFilterSortState={setFilterSortState}
|
||||||
/>
|
/>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -7,7 +7,10 @@ import {
|
|||||||
VariantAnalysisScannedRepositoryResult,
|
VariantAnalysisScannedRepositoryResult,
|
||||||
VariantAnalysisScannedRepositoryState
|
VariantAnalysisScannedRepositoryState
|
||||||
} from '../../remote-queries/shared/variant-analysis';
|
} from '../../remote-queries/shared/variant-analysis';
|
||||||
import { compareWithResults, matchesFilter, RepositoriesFilterSortState } from './filterSort';
|
import {
|
||||||
|
filterAndSortRepositoriesWithResults,
|
||||||
|
RepositoriesFilterSortState,
|
||||||
|
} from '../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
const Container = styled.div`
|
const Container = styled.div`
|
||||||
display: flex;
|
display: flex;
|
||||||
@@ -52,9 +55,7 @@ export const VariantAnalysisAnalyzedRepos = ({
|
|||||||
}, [repositoryResults]);
|
}, [repositoryResults]);
|
||||||
|
|
||||||
const repositories = useMemo(() => {
|
const repositories = useMemo(() => {
|
||||||
return variantAnalysis.scannedRepos?.filter((repoTask) => {
|
return filterAndSortRepositoriesWithResults(variantAnalysis.scannedRepos, filterSortState);
|
||||||
return matchesFilter(repoTask.repository, filterSortState);
|
|
||||||
})?.sort(compareWithResults(filterSortState));
|
|
||||||
}, [filterSortState, variantAnalysis.scannedRepos]);
|
}, [filterSortState, variantAnalysis.scannedRepos]);
|
||||||
|
|
||||||
const onSelectedChange = useCallback((repositoryId: number, selected: boolean) => {
|
const onSelectedChange = useCallback((repositoryId: number, selected: boolean) => {
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import * as React from 'react';
|
import * as React from 'react';
|
||||||
import { Dispatch, SetStateAction, useState } from 'react';
|
import { Dispatch, SetStateAction } from 'react';
|
||||||
import styled from 'styled-components';
|
import styled from 'styled-components';
|
||||||
import { VSCodeBadge, VSCodePanels, VSCodePanelTab, VSCodePanelView } from '@vscode/webview-ui-toolkit/react';
|
import { VSCodeBadge, VSCodePanels, VSCodePanelTab, VSCodePanelView } from '@vscode/webview-ui-toolkit/react';
|
||||||
import { formatDecimal } from '../../pure/number';
|
import { formatDecimal } from '../../pure/number';
|
||||||
@@ -12,7 +12,7 @@ import {
|
|||||||
import { VariantAnalysisAnalyzedRepos } from './VariantAnalysisAnalyzedRepos';
|
import { VariantAnalysisAnalyzedRepos } from './VariantAnalysisAnalyzedRepos';
|
||||||
import { Alert } from '../common';
|
import { Alert } from '../common';
|
||||||
import { VariantAnalysisSkippedRepositoriesTab } from './VariantAnalysisSkippedRepositoriesTab';
|
import { VariantAnalysisSkippedRepositoriesTab } from './VariantAnalysisSkippedRepositoriesTab';
|
||||||
import { defaultFilterSortState, RepositoriesFilterSortState } from './filterSort';
|
import { RepositoriesFilterSortState } from '../../pure/variant-analysis-filter-sort';
|
||||||
import { RepositoriesSearchSortRow } from './RepositoriesSearchSortRow';
|
import { RepositoriesSearchSortRow } from './RepositoriesSearchSortRow';
|
||||||
import { FailureReasonAlert } from './FailureReasonAlert';
|
import { FailureReasonAlert } from './FailureReasonAlert';
|
||||||
|
|
||||||
@@ -23,6 +23,9 @@ export type VariantAnalysisOutcomePanelProps = {
|
|||||||
|
|
||||||
selectedRepositoryIds?: number[];
|
selectedRepositoryIds?: number[];
|
||||||
setSelectedRepositoryIds?: Dispatch<SetStateAction<number[]>>;
|
setSelectedRepositoryIds?: Dispatch<SetStateAction<number[]>>;
|
||||||
|
|
||||||
|
filterSortState: RepositoriesFilterSortState;
|
||||||
|
setFilterSortState: Dispatch<SetStateAction<RepositoriesFilterSortState>>;
|
||||||
};
|
};
|
||||||
|
|
||||||
const Tab = styled(VSCodePanelTab)`
|
const Tab = styled(VSCodePanelTab)`
|
||||||
@@ -51,9 +54,9 @@ export const VariantAnalysisOutcomePanels = ({
|
|||||||
repositoryResults,
|
repositoryResults,
|
||||||
selectedRepositoryIds,
|
selectedRepositoryIds,
|
||||||
setSelectedRepositoryIds,
|
setSelectedRepositoryIds,
|
||||||
|
filterSortState,
|
||||||
|
setFilterSortState,
|
||||||
}: VariantAnalysisOutcomePanelProps) => {
|
}: VariantAnalysisOutcomePanelProps) => {
|
||||||
const [filterSortState, setFilterSortState] = useState<RepositoriesFilterSortState>(defaultFilterSortState);
|
|
||||||
|
|
||||||
const scannedReposCount = variantAnalysis.scannedRepos?.length ?? 0;
|
const scannedReposCount = variantAnalysis.scannedRepos?.length ?? 0;
|
||||||
const noCodeqlDbRepos = variantAnalysis.skippedRepos?.noCodeqlDbRepos;
|
const noCodeqlDbRepos = variantAnalysis.skippedRepos?.noCodeqlDbRepos;
|
||||||
const notFoundRepos = variantAnalysis.skippedRepos?.notFoundRepos;
|
const notFoundRepos = variantAnalysis.skippedRepos?.notFoundRepos;
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ import styled from 'styled-components';
|
|||||||
import { VariantAnalysisSkippedRepositoryGroup } from '../../remote-queries/shared/variant-analysis';
|
import { VariantAnalysisSkippedRepositoryGroup } from '../../remote-queries/shared/variant-analysis';
|
||||||
import { Alert } from '../common';
|
import { Alert } from '../common';
|
||||||
import { RepoRow } from './RepoRow';
|
import { RepoRow } from './RepoRow';
|
||||||
import { compareRepository, matchesFilter, RepositoriesFilterSortState } from './filterSort';
|
import { compareRepository, matchesFilter, RepositoriesFilterSortState } from '../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
export type VariantAnalysisSkippedRepositoriesTabProps = {
|
export type VariantAnalysisSkippedRepositoriesTabProps = {
|
||||||
alertTitle: string,
|
alertTitle: string,
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ import { VariantAnalysisAnalyzedRepos, VariantAnalysisAnalyzedReposProps } from
|
|||||||
import { createMockVariantAnalysis } from '../../../vscode-tests/factories/remote-queries/shared/variant-analysis';
|
import { createMockVariantAnalysis } from '../../../vscode-tests/factories/remote-queries/shared/variant-analysis';
|
||||||
import { createMockRepositoryWithMetadata } from '../../../vscode-tests/factories/remote-queries/shared/repository';
|
import { createMockRepositoryWithMetadata } from '../../../vscode-tests/factories/remote-queries/shared/repository';
|
||||||
import { createMockScannedRepo } from '../../../vscode-tests/factories/remote-queries/shared/scanned-repositories';
|
import { createMockScannedRepo } from '../../../vscode-tests/factories/remote-queries/shared/scanned-repositories';
|
||||||
import { defaultFilterSortState, SortKey } from '../filterSort';
|
import { defaultFilterSortState, SortKey } from '../../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
describe(VariantAnalysisAnalyzedRepos.name, () => {
|
describe(VariantAnalysisAnalyzedRepos.name, () => {
|
||||||
const defaultVariantAnalysis = createMockVariantAnalysis({
|
const defaultVariantAnalysis = createMockVariantAnalysis({
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ import {
|
|||||||
createMockScannedRepo,
|
createMockScannedRepo,
|
||||||
createMockScannedRepos
|
createMockScannedRepos
|
||||||
} from '../../../vscode-tests/factories/remote-queries/shared/scanned-repositories';
|
} from '../../../vscode-tests/factories/remote-queries/shared/scanned-repositories';
|
||||||
|
import { defaultFilterSortState } from '../../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
describe(VariantAnalysisOutcomePanels.name, () => {
|
describe(VariantAnalysisOutcomePanels.name, () => {
|
||||||
const defaultVariantAnalysis = {
|
const defaultVariantAnalysis = {
|
||||||
@@ -81,6 +82,8 @@ describe(VariantAnalysisOutcomePanels.name, () => {
|
|||||||
...defaultVariantAnalysis,
|
...defaultVariantAnalysis,
|
||||||
...variantAnalysis,
|
...variantAnalysis,
|
||||||
}}
|
}}
|
||||||
|
filterSortState={defaultFilterSortState}
|
||||||
|
setFilterSortState={jest.fn()}
|
||||||
{...props}
|
{...props}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import * as React from 'react';
|
import * as React from 'react';
|
||||||
import { render as reactRender, screen } from '@testing-library/react';
|
import { render as reactRender, screen } from '@testing-library/react';
|
||||||
import { VariantAnalysisSkippedRepositoriesTab, VariantAnalysisSkippedRepositoriesTabProps } from '../VariantAnalysisSkippedRepositoriesTab';
|
import { VariantAnalysisSkippedRepositoriesTab, VariantAnalysisSkippedRepositoriesTabProps } from '../VariantAnalysisSkippedRepositoriesTab';
|
||||||
import { defaultFilterSortState, SortKey } from '../filterSort';
|
import { defaultFilterSortState, SortKey } from '../../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
describe(VariantAnalysisSkippedRepositoriesTab.name, () => {
|
describe(VariantAnalysisSkippedRepositoriesTab.name, () => {
|
||||||
const render = (props: VariantAnalysisSkippedRepositoriesTabProps) =>
|
const render = (props: VariantAnalysisSkippedRepositoriesTabProps) =>
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
import { compareRepository, compareWithResults, defaultFilterSortState, matchesFilter, SortKey } from '../filterSort';
|
import { compareRepository, compareWithResults, defaultFilterSortState, matchesFilter, SortKey } from '../../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
|
// TODO: Move this file to the "pure" tests once it has been switched to Jest
|
||||||
describe(matchesFilter.name, () => {
|
describe(matchesFilter.name, () => {
|
||||||
const repository = {
|
const repository = {
|
||||||
fullName: 'github/codeql'
|
fullName: 'github/codeql'
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import { CancellationTokenSource, commands, env, extensions, QuickPickItem, Uri,
|
|||||||
import { CodeQLExtensionInterface } from '../../../extension';
|
import { CodeQLExtensionInterface } from '../../../extension';
|
||||||
import { logger } from '../../../logging';
|
import { logger } from '../../../logging';
|
||||||
import * as config from '../../../config';
|
import * as config from '../../../config';
|
||||||
|
import { setRemoteControllerRepo, setRemoteRepositoryLists } from '../../../config';
|
||||||
import * as ghApiClient from '../../../remote-queries/gh-api/gh-api-client';
|
import * as ghApiClient from '../../../remote-queries/gh-api/gh-api-client';
|
||||||
import * as ghActionsApiClient from '../../../remote-queries/gh-api/gh-actions-api-client';
|
import * as ghActionsApiClient from '../../../remote-queries/gh-api/gh-actions-api-client';
|
||||||
import { Credentials } from '../../../authentication';
|
import { Credentials } from '../../../authentication';
|
||||||
@@ -35,7 +36,7 @@ import {
|
|||||||
import { createMockApiResponse } from '../../factories/remote-queries/gh-api/variant-analysis-api-response';
|
import { createMockApiResponse } from '../../factories/remote-queries/gh-api/variant-analysis-api-response';
|
||||||
import { UserCancellationException } from '../../../commandRunner';
|
import { UserCancellationException } from '../../../commandRunner';
|
||||||
import { Repository } from '../../../remote-queries/gh-api/repository';
|
import { Repository } from '../../../remote-queries/gh-api/repository';
|
||||||
import { setRemoteControllerRepo, setRemoteRepositoryLists } from '../../../config';
|
import { defaultFilterSortState, SortKey } from '../../../pure/variant-analysis-filter-sort';
|
||||||
|
|
||||||
describe('Variant Analysis Manager', async function() {
|
describe('Variant Analysis Manager', async function() {
|
||||||
let sandbox: sinon.SinonSandbox;
|
let sandbox: sinon.SinonSandbox;
|
||||||
@@ -766,23 +767,23 @@ describe('Variant Analysis Manager', async function() {
|
|||||||
describe('when the variant analysis has repositories with results', () => {
|
describe('when the variant analysis has repositories with results', () => {
|
||||||
const scannedRepos = [
|
const scannedRepos = [
|
||||||
{
|
{
|
||||||
...createMockScannedRepo(),
|
...createMockScannedRepo('pear'),
|
||||||
resultCount: 100,
|
resultCount: 100,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
...createMockScannedRepo(),
|
...createMockScannedRepo('apple'),
|
||||||
resultCount: 0,
|
resultCount: 0,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
...createMockScannedRepo(),
|
...createMockScannedRepo('citrus'),
|
||||||
resultCount: 200,
|
resultCount: 200,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
...createMockScannedRepo(),
|
...createMockScannedRepo('sky'),
|
||||||
resultCount: undefined,
|
resultCount: undefined,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
...createMockScannedRepo(),
|
...createMockScannedRepo('banana'),
|
||||||
resultCount: 5,
|
resultCount: 5,
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
@@ -809,8 +810,44 @@ describe('Variant Analysis Manager', async function() {
|
|||||||
|
|
||||||
expect(parsed).to.deep.eq({
|
expect(parsed).to.deep.eq({
|
||||||
'new-repo-list': [
|
'new-repo-list': [
|
||||||
scannedRepos[0].repository.fullName,
|
scannedRepos[4].repository.fullName,
|
||||||
scannedRepos[2].repository.fullName,
|
scannedRepos[2].repository.fullName,
|
||||||
|
scannedRepos[0].repository.fullName,
|
||||||
|
],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should use the sort key', async () => {
|
||||||
|
await variantAnalysisManager.copyRepoListToClipboard(variantAnalysis.id, {
|
||||||
|
...defaultFilterSortState,
|
||||||
|
sortKey: SortKey.ResultsCount,
|
||||||
|
});
|
||||||
|
|
||||||
|
const text = writeTextStub.getCalls()[0].lastArg;
|
||||||
|
|
||||||
|
const parsed = JSON.parse('{' + text + '}');
|
||||||
|
|
||||||
|
expect(parsed).to.deep.eq({
|
||||||
|
'new-repo-list': [
|
||||||
|
scannedRepos[2].repository.fullName,
|
||||||
|
scannedRepos[0].repository.fullName,
|
||||||
|
scannedRepos[4].repository.fullName,
|
||||||
|
],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should use the search value', async () => {
|
||||||
|
await variantAnalysisManager.copyRepoListToClipboard(variantAnalysis.id, {
|
||||||
|
...defaultFilterSortState,
|
||||||
|
searchValue: 'ban',
|
||||||
|
});
|
||||||
|
|
||||||
|
const text = writeTextStub.getCalls()[0].lastArg;
|
||||||
|
|
||||||
|
const parsed = JSON.parse('{' + text + '}');
|
||||||
|
|
||||||
|
expect(parsed).to.deep.eq({
|
||||||
|
'new-repo-list': [
|
||||||
scannedRepos[4].repository.fullName,
|
scannedRepos[4].repository.fullName,
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
|||||||
Reference in New Issue
Block a user