Skip to content

Commit

Permalink
feat: allow configs from subdirectories
Browse files Browse the repository at this point in the history
  • Loading branch information
vkorbes authored and eysi09 committed Sep 5, 2018
1 parent 1631777 commit bb464c3
Show file tree
Hide file tree
Showing 4 changed files with 33 additions and 17 deletions.
5 changes: 3 additions & 2 deletions garden-cli/src/config/base.ts
Original file line number Diff line number Diff line change
Expand Up @@ -48,16 +48,17 @@ export const configSchema = Joi.object()

const baseModuleSchemaKeys = Object.keys(baseModuleSpecSchema.describe().children)

export async function loadConfig(projectRoot: string, path: string): Promise<GardenConfig> {
export async function loadConfig(projectRoot: string, path: string): Promise<GardenConfig | undefined> {
// TODO: nicer error messages when load/validation fails
const absPath = join(path, CONFIG_FILENAME)
let fileData
let spec: any

// loadConfig returns null if config file is not found in the given directory
try {
fileData = await readFile(absPath)
} catch (err) {
throw new ConfigurationError(`Could not find ${CONFIG_FILENAME} in directory ${path}`, err)
return undefined
}

try {
Expand Down
34 changes: 22 additions & 12 deletions garden-cli/src/garden.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@

import Bluebird = require("bluebird")
import {
join,
parse,
relative,
resolve,
Expand Down Expand Up @@ -185,37 +186,46 @@ export class Garden {
this.taskGraph = new TaskGraph(this.pluginContext)
}

static async factory(projectRoot: string, { env, config, logger, plugins = [] }: ContextOpts = {}) {
static async factory(currentDirectory: string, { env, config, logger, plugins = [] }: ContextOpts = {}) {
let parsedConfig: GardenConfig
let initialDirectory = currentDirectory || []
let projectRoot: string

if (config) {
parsedConfig = <GardenConfig>validate(config, configSchema, { context: "root configuration" })

if (!parsedConfig.project) {
throw new ConfigurationError(`Supplied config does not contain a project configuration`, {
projectRoot,
currentDirectory,
config,
})
}
} else {
config = await loadConfig(projectRoot, projectRoot)
parsedConfig = await resolveTemplateStrings(config, new ProjectConfigContext())

if (!parsedConfig.project) {
throw new ConfigurationError(`Path ${projectRoot} does not contain a project configuration`, {
projectRoot,
config,
})
let sepCount = (currentDirectory.match(new RegExp(sep, "g")) || []).length
for (let i = 0; i < sepCount; i++) {
config = await loadConfig(currentDirectory, currentDirectory)
if (!config || !config.project) {
currentDirectory = join(currentDirectory, "..")
} else if (config.project) {
break
}
}
if (!config || !config.project) {
throw new ConfigurationError(`Not a project directory (or any of the parent directories): ${initialDirectory}`,
{ initialDirectory })
}
}

projectRoot = currentDirectory
parsedConfig = await resolveTemplateStrings(config!, new ProjectConfigContext())

const {
defaultEnvironment,
environments,
name: projectName,
environmentDefaults,
sources: projectSources,
} = parsedConfig.project
} = parsedConfig.project!

if (!env) {
env = defaultEnvironment
Expand Down Expand Up @@ -782,7 +792,7 @@ export class Garden {
const path = resolve(this.projectRoot, nameOrLocation)
const config = await loadConfig(this.projectRoot, path)

if (!config.module) {
if (!config || !config.module) {
return null
}

Expand Down
9 changes: 7 additions & 2 deletions garden-cli/test/src/config/base.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ describe("loadConfig", async () => {
it("should load and parse a project config", async () => {
const parsed = await loadConfig(projectPathA, projectPathA)

expect(parsed.project).to.eql({
expect(parsed!.project).to.eql({
name: "test-project-a",
defaultEnvironment: "local",
sources: [],
Expand Down Expand Up @@ -41,7 +41,7 @@ describe("loadConfig", async () => {
it("should load and parse a module config", async () => {
const parsed = await loadConfig(projectPathA, modulePathA)

expect(parsed.module).to.eql({
expect(parsed!.module).to.eql({
name: "module-a",
type: "test",
description: undefined,
Expand All @@ -64,4 +64,9 @@ describe("loadConfig", async () => {
})
})

it("should return undefined if config file is not found", async () => {
const parsed = await loadConfig("/thisdoesnotexist", "/thisdoesnotexist")
expect(parsed).to.be.undefined
})

})
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -60,4 +60,4 @@
},
"snyk": true,
"dependencies": {}
}
}

0 comments on commit bb464c3

Please sign in to comment.