Skip to content

Commit

Permalink
fix(cli): provide PROXY agent to ruleset reader
Browse files Browse the repository at this point in the history
  • Loading branch information
P0lip committed Feb 25, 2021
1 parent e27fccc commit 0c134e5
Show file tree
Hide file tree
Showing 3 changed files with 75 additions and 7 deletions.
59 changes: 59 additions & 0 deletions src/cli/services/__tests__/linter.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,10 @@ import { ValidationError } from '../../../ruleset/validation';
import { ILintConfig } from '../../../types/config';
import lintCommand from '../../commands/lint';
import { lint } from '../linter';
import * as http from 'http';
import * as url from 'url';
import { DEFAULT_REQUEST_OPTIONS } from '../../../request';
import * as ProxyAgent from 'proxy-agent';

jest.mock('../output');

Expand Down Expand Up @@ -803,4 +807,59 @@ describe('Linter service', () => {
);
});
});

describe('proxy', () => {
let server: http.Server;
const PORT = 4001;

beforeAll(() => {
// nock cannot mock proxied requests
server = http
.createServer((req, res) => {
const { pathname } = url.parse(String(req.url));
if (pathname === '/custom-ruleset') {
res.writeHead(403);
} else if (pathname === '/ok.json') {
res.writeHead(200, { 'Content-Type': 'application/json' });
res.write(
JSON.stringify({
info: {
title: '',
description: 'Foo',
},
}),
);
} else {
res.writeHead(404);
}

res.end();
})
.listen(PORT, '0.0.0.0');
});

afterAll(() => {
server.close();
});

describe('when agent is set', () => {
beforeEach(() => {
DEFAULT_REQUEST_OPTIONS.agent = new ProxyAgent(`http://localhost:${PORT}`) as any;
});

afterEach(() => {
delete DEFAULT_REQUEST_OPTIONS.agent;
});

describe('loading a ruleset', () => {
it('proxies the request', async () => {
await expect(
run(`lint --ruleset http://localhost:4000/custom-ruleset src/__tests__/__fixtures__/petstore.oas3.json`),
).rejects.toThrowErrorMatchingInlineSnapshot(
`"Could not parse http://localhost:4000/custom-ruleset: Forbidden"`,
);
});
});
});
});
});
8 changes: 7 additions & 1 deletion src/cli/services/linter/linter.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,19 @@ import { ILintConfig } from '../../../types/config';
import { getRuleset, listFiles, skipRules, segregateEntriesPerKind, readFileDescriptor } from './utils';
import { getResolver } from './utils/getResolver';
import { YamlParserResult } from '@stoplight/yaml';
import { DEFAULT_REQUEST_OPTIONS } from '../../../request';
import type { Agent } from 'https';

export async function lint(documents: Array<number | string>, flags: ILintConfig): Promise<IRuleResult[]> {
const spectral = new Spectral({
resolver: getResolver(flags.resolver),
proxyUri: process.env.PROXY,
});

const ruleset = await getRuleset(flags.ruleset, {
agent: DEFAULT_REQUEST_OPTIONS.agent as Agent,
});

const ruleset = await getRuleset(flags.ruleset);
spectral.setRuleset(ruleset);

for (const [format, lookup, prettyName] of KNOWN_FORMATS) {
Expand Down
15 changes: 9 additions & 6 deletions src/cli/services/linter/utils/getRuleset.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
import { isAbsolute, resolve } from '@stoplight/path';
import { Optional } from '@stoplight/types';
import { readRuleset } from '../../../../ruleset';
import { IRulesetReadOptions, readRuleset } from '../../../../ruleset';
import { getDefaultRulesetFile } from '../../../../ruleset/utils';
import { IRuleset } from '../../../../types/ruleset';
import { KNOWN_RULESETS } from '../../../../formats';

async function loadRulesets(cwd: string, rulesetFiles: string[]): Promise<IRuleset> {
async function loadRulesets(cwd: string, rulesetFiles: string[], opts: IRulesetReadOptions): Promise<IRuleset> {
if (rulesetFiles.length === 0) {
return {
functions: {},
Expand All @@ -14,13 +14,16 @@ async function loadRulesets(cwd: string, rulesetFiles: string[]): Promise<IRules
};
}

return readRuleset(rulesetFiles.map(file => (isAbsolute(file) ? file : resolve(cwd, file))));
return readRuleset(
rulesetFiles.map(file => (isAbsolute(file) ? file : resolve(cwd, file))),
opts,
);
}

export async function getRuleset(rulesetFile: Optional<string[]>): Promise<IRuleset> {
export async function getRuleset(rulesetFile: Optional<string[]>, opts: IRulesetReadOptions): Promise<IRuleset> {
const rulesetFiles = rulesetFile ?? (await getDefaultRulesetFile(process.cwd()));

return await (rulesetFiles !== null
? loadRulesets(process.cwd(), Array.isArray(rulesetFiles) ? rulesetFiles : [rulesetFiles])
: readRuleset(KNOWN_RULESETS));
? loadRulesets(process.cwd(), Array.isArray(rulesetFiles) ? rulesetFiles : [rulesetFiles], opts)
: readRuleset(KNOWN_RULESETS, opts));
}

0 comments on commit 0c134e5

Please sign in to comment.