Skip to content

Commit

Permalink
Merge pull request #186 from snyk/feat/gradle-reachability-feature-pa…
Browse files Browse the repository at this point in the history
…rity

Feat/gradle reachability feature parity
  • Loading branch information
Dar Malovani authored May 25, 2021
2 parents 98b48cf + 6dd3192 commit 5a0c895
Show file tree
Hide file tree
Showing 3 changed files with 87 additions and 7 deletions.
42 changes: 37 additions & 5 deletions lib/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import debugModule = require('debug');

type ScannedProject = legacyCommon.ScannedProject;
type CallGraph = legacyCommon.CallGraph;
type CallGraphResult = legacyCommon.CallGraphResult;

// To enable debugging output, use `snyk -d`
let logger: debugModule.Debugger | null = null;
Expand Down Expand Up @@ -63,6 +64,7 @@ export interface GradleInspectOptions {
// Leaving default usage `--no-daemon`, because of backwards compatibility
daemon?: boolean;
reachableVulns?: boolean;
callGraphBuilderTimeout?: number;
initScript?: string;
}

Expand Down Expand Up @@ -111,7 +113,7 @@ export async function inspect(
meta: {},
};

let callGraph: CallGraph | undefined;
let callGraph: CallGraphResult | undefined;
const targetPath = path.join(root, targetFile);

if (options.reachableVulns) {
Expand All @@ -131,14 +133,17 @@ export async function inspect(
confAttrs = options['configuration-attributes'];
}

debugLog(`getting call graph from path ${targetPath}`);
callGraph = await javaCallGraphBuilder.getCallGraphGradle(
path.dirname(targetPath),
const timeout = options?.callGraphBuilderTimeout
? options?.callGraphBuilderTimeout * 1000
: undefined;

callGraph = await getCallGraph(
targetPath,
command,
initScriptPath,
confAttrs,
timeout,
);
debugLog('got call graph successfully');
}

if (api.isMultiSubProject(options)) {
Expand Down Expand Up @@ -765,6 +770,33 @@ function buildArgs(
return args;
}

async function getCallGraph(
targetPath: string,
command: string,
initScriptPath?: string,
confAttrs?: string,
timeout?: number,
): Promise<CallGraphResult> {
try {
debugLog(`getting call graph from path ${targetPath}`);
const callGraph: CallGraph = await javaCallGraphBuilder.getCallGraphGradle(
path.dirname(targetPath),
command,
initScriptPath,
confAttrs,
timeout,
);
debugLog('got call graph successfully');
return callGraph;
} catch (e) {
debugLog('call graph error: ' + e);
return {
message: e.message,
innerError: e.innerError || e,
};
}
}

export const exportsForTests = {
buildArgs,
extractJsonFromScriptOutput,
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@
"dependencies": {
"@snyk/cli-interface": "2.11.0",
"@snyk/dep-graph": "^1.28.0",
"@snyk/java-call-graph-builder": "1.22.0",
"@snyk/java-call-graph-builder": "1.23.0",
"@types/debug": "^4.1.4",
"chalk": "^3.0.0",
"debug": "^4.1.1",
Expand Down
50 changes: 49 additions & 1 deletion test/system/reachability.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import { inspect, formatArgWithWhiteSpace } from '../../lib';
import * as fs from 'fs';
import * as sinon from 'sinon';
import * as javaCallGraphBuilder from '@snyk/java-call-graph-builder';
import { CallGraph } from '@snyk/cli-interface/legacy/common';
import { CallGraph, CallGraphError } from '@snyk/cli-interface/legacy/common';

const rootNoWrapper = fixtureDir('no wrapper');

Expand Down Expand Up @@ -113,7 +113,55 @@ test('reachableVulns', async (t) => {
);
});

t.test('with timeout', async (t) => {
const result = await inspect(
'.',
path.join(rootNoWrapper, 'build.gradle'),
{
reachableVulns: true,
callGraphBuilderTimeout: 20,
},
);

t.ok(
javaCallGraphBuilderStub.calledWith(
path.join('.', rootNoWrapper),
'gradle',
undefined,
undefined,
20000,
),
'call graph builder was called with timeout',
);
t.same(gradleCallGraph, result.callGraph, 'returns expected callgraph');
});

t.teardown(() => {
javaCallGraphBuilderStub.restore();
});
});

test('failure modes', async (t) => {
t.test('gracefully fails', async (t) => {
const errorMessage = 'Call graph error';
const javaCallGraphBuilderFailedStub = sinon
.stub(javaCallGraphBuilder, 'getCallGraphGradle')
.rejects(new Error(errorMessage));

const result = await inspect(
'.',
path.join(rootNoWrapper, 'build.gradle'),
{
reachableVulns: true,
},
);

t.same(
errorMessage,
(result.callGraph as CallGraphError).message,
'get correct error message',
);

javaCallGraphBuilderFailedStub.restore();
});
});

0 comments on commit 5a0c895

Please sign in to comment.