Skip to content
This repository was archived by the owner on Jun 16, 2022. It is now read-only.

Go list implementation for detecting dependencies #5

Merged
merged 23 commits into from
May 24, 2022
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
More lint
  • Loading branch information
lseppala authored May 14, 2022
commit c66a139385291e5fef7ecc7efb404f95d59797ab
50 changes: 25 additions & 25 deletions src/go_mod_parser.ts
Original file line number Diff line number Diff line change
@@ -1,45 +1,45 @@
import {
Entry,
ParsedDependencies,
} from "@github/dependency-submission-toolkit/dist/processor";
ParsedDependencies
} from '@github/dependency-submission-toolkit/dist/processor'

export function parseDependents(contents: string) {
const stdoutArr: string[] = contents.split("\n");
export function parseDependents (contents: string) {
const stdoutArr: string[] = contents.split('\n')
const splitStdoutArr: string[][] = stdoutArr.map(function (line) {
return line.split(" ");
});
return line.split(' ')
})

const entries: ParsedDependencies = {};
const repoName = splitStdoutArr[0][0];
const entries: ParsedDependencies = {}
const repoName = splitStdoutArr[0][0]
splitStdoutArr.forEach((line: string[]) => {
if (line === undefined || line.length < 2) return; // skip empty lines
if (line === undefined || line.length < 2) return // skip empty lines

let targetEntry: Entry;
const targetPkg = `pkg:golang/${line[0]}`;
let dependencyEntry: Entry;
const dependencyPkg = `pkg:golang/${line[1]}`;
let targetEntry: Entry
const targetPkg = `pkg:golang/${line[0]}`
let dependencyEntry: Entry
const dependencyPkg = `pkg:golang/${line[1]}`

const matchFound = line[0].match(repoName);
const matchFound = line[0].match(repoName)
if (matchFound && matchFound.index != null) {
entries[dependencyPkg] = new Entry(dependencyPkg, "direct");
return;
entries[dependencyPkg] = new Entry(dependencyPkg, 'direct')
return
}

if (targetPkg in entries) {
targetEntry = entries[targetPkg];
targetEntry = entries[targetPkg]
} else {
targetEntry = new Entry(targetPkg, "indirect");
entries[targetPkg] = targetEntry;
targetEntry = new Entry(targetPkg, 'indirect')
entries[targetPkg] = targetEntry
}

if (dependencyPkg in entries) {
dependencyEntry = entries[dependencyPkg];
dependencyEntry = entries[dependencyPkg]
} else {
dependencyEntry = new Entry(dependencyPkg, "indirect");
entries[dependencyPkg] = dependencyEntry;
dependencyEntry = new Entry(dependencyPkg, 'indirect')
entries[dependencyPkg] = dependencyEntry
}

targetEntry.addDependency(dependencyEntry);
});
return entries;
targetEntry.addDependency(dependencyEntry)
})
return entries
}
58 changes: 29 additions & 29 deletions src/index.ts
Original file line number Diff line number Diff line change
@@ -1,57 +1,57 @@
import * as core from "@actions/core";
import { run } from "@github/dependency-submission-toolkit";
import { ProcessDependenciesContent } from "@github/dependency-submission-toolkit/dist/processor";
import { parseDependents } from "./go_mod_parser";
import * as path from "path";
import * as process from "process";
import execa from "execa";
import * as core from '@actions/core'
import { run } from '@github/dependency-submission-toolkit'
import { ProcessDependenciesContent } from '@github/dependency-submission-toolkit/dist/processor'
import { parseDependents } from './go_mod_parser'
import * as path from 'path'
import * as process from 'process'
import execa from 'execa'

const parseDependentsFunc: ProcessDependenciesContent = parseDependents;
const parseDependentsFunc: ProcessDependenciesContent = parseDependents

// Set the detector information provided from the action workflow input
const detector = {
name: core.getInput("detector-name"),
url: core.getInput("detector-url"),
version: core.getInput("detector-version"),
};
name: core.getInput('detector-name'),
url: core.getInput('detector-url'),
version: core.getInput('detector-version')
}

async function searchForFile(filename: string) {
console.log(`searching for ${filename} in ${process.cwd()}`);
async function searchForFile (filename: string) {
console.log(`searching for ${filename} in ${process.cwd()}`)

const { stdout } = await execa("find", [process.cwd(), "-name", filename]);
const { stdout } = await execa('find', [process.cwd(), '-name', filename])

const dirs = stdout
.split("\n")
.split('\n')
.filter((s) => s.length > 0)
// remove the file name
.map((filename) => path.dirname(filename))
// map to absolute path
.map((pathname) => path.resolve(process.cwd(), pathname));
.map((pathname) => path.resolve(process.cwd(), pathname))

return dirs;
return dirs
}

// Enumerate directories
async function detect() {
const goModPaths = await searchForFile("go.mod");
async function detect () {
const goModPaths = await searchForFile('go.mod')

// If provided, set the metadata provided from the action workflow input
const metadataInput = core.getInput("metadata");
const metadataInput = core.getInput('metadata')

goModPaths.forEach((path) => {
process.chdir(path);
console.log(`Running go mod graph in ${path}`);
process.chdir(path)
console.log(`Running go mod graph in ${path}`)
if (metadataInput.length < 1) {
run(parseDependentsFunc, { command: "go mod graph" }, { detector });
run(parseDependentsFunc, { command: 'go mod graph' }, { detector })
} else {
const metadata = JSON.parse(metadataInput);
const metadata = JSON.parse(metadataInput)
run(
parseDependentsFunc,
{ command: "go mod graph" },
{ command: 'go mod graph' },
{ metadata, detector }
);
)
}
});
})
}

detect();
detect()
30 changes: 15 additions & 15 deletions test/go_mod_parser.test.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { describe, expect, test } from "@jest/globals";
import { parseDependents } from "../src/go_mod_parser";
import { describe, expect, test } from '@jest/globals'
import { parseDependents } from '../src/go_mod_parser'

/*
Expected dependency tree:
Expand All @@ -22,26 +22,26 @@ github.com/jaffee/[email protected] github.com/spf13/[email protected]
github.com/jaffee/[email protected] github.com/spf13/[email protected]
github.com/spf13/[email protected] github.com/armon/[email protected]
github.com/spf13/[email protected] github.com/coreos/[email protected]
`;
`

describe("test go mod graph dependenciesProcessorFunc", () => {
test("parses output of go mod graph into dependencies", async () => {
const dependencies = parseDependents(GO_MOD_GRAPH);
describe('test go mod graph dependenciesProcessorFunc', () => {
test('parses output of go mod graph into dependencies', async () => {
const dependencies = parseDependents(GO_MOD_GRAPH)

// Should have 7 total dependencies: 2 direct, 5 indirect
expect(Object.values(dependencies).length).toEqual(7);
expect(Object.values(dependencies).length).toEqual(7)

expect(
dependencies["pkg:golang/github.com/jaffee/[email protected]"]
dependencies['pkg:golang/github.com/jaffee/[email protected]']
.relationship
).toEqual("direct");
).toEqual('direct')

expect(
dependencies["pkg:golang/github.com/spf13/[email protected]"].relationship
).toEqual("direct");
dependencies['pkg:golang/github.com/spf13/[email protected]'].relationship
).toEqual('direct')

expect(
dependencies["pkg:golang/github.com/spf13/[email protected]"].dependencies
).toContainEqual(dependencies["pkg:golang/github.com/coreos/[email protected]"]);
});
});
dependencies['pkg:golang/github.com/spf13/[email protected]'].dependencies
).toContainEqual(dependencies['pkg:golang/github.com/coreos/[email protected]'])
})
})