Skip to content

Commit

Permalink
improvement(core): allow wildcard in first label in hostname
Browse files Browse the repository at this point in the history
  • Loading branch information
eysi09 committed Nov 18, 2020
1 parent 94947b6 commit 2a5f304
Show file tree
Hide file tree
Showing 6 changed files with 65 additions and 8 deletions.
39 changes: 39 additions & 0 deletions core/src/config/common.ts
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,7 @@ export interface Schema extends Joi.Root {
environment: () => Joi.StringSchema
gitUrl: () => GitUrlSchema
posixPath: () => PosixPathSchema
hostname: () => Joi.StringSchema
}

export let joi: Schema = Joi.extend({
Expand Down Expand Up @@ -354,6 +355,44 @@ joi = joi.extend({
},
})

/**
* Add a joi.hostname() type. Like joi.string().hostname() with the exception that it allows
* wildcards in the first DNS label and returns a custom error if it finds wildcards in labels
* other than the first.
*/
joi = joi.extend({
base: Joi.string(),
type: "hostname",
messages: {
base: "{{#label}} must be a valid hostname.",
wildcardLabel: "{{#label}} only first DNS label my contain a wildcard.",
},
validate(value: string, { error }) {
const baseSchema = joi.string().hostname()
const wildcardLabel = "*."
let result: Joi.ValidationResult

const labels = value.split(".")
// Hostname includes a wildcard label that is not the first label
if (!value.startsWith(wildcardLabel) && labels.includes("*")) {
return { value, errors: error("wildcardLabel") }
}

if (value.startsWith(wildcardLabel)) {
const restLabels = value.slice(wildcardLabel.length)
result = baseSchema.validate(restLabels)
} else {
result = baseSchema.validate(value)
}

if (result.error) {
return { value, errors: error("base") }
}

return { value }
},
})

export const joiPrimitive = () =>
joi
.alternatives()
Expand Down
2 changes: 1 addition & 1 deletion core/src/plugins/kubernetes/config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -264,7 +264,7 @@ const tlsCertificateSchema = () =>
.example("wildcard"),
hostnames: joi
.array()
.items(joi.string().hostname())
.items(joi.hostname())
.description(
"A list of hostnames that this certificate should be used for. " +
"If you don't specify these, they will be automatically read from the certificate."
Expand Down
2 changes: 1 addition & 1 deletion core/src/types/service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ export interface ServiceIngress extends ServiceIngressSpec {
}

export const ingressHostnameSchema = () =>
joi.string().hostname().description(dedent`
joi.hostname().description(dedent`
The hostname that should route to this service. Defaults to the default hostname configured in the provider configuration.
Note that if you're developing locally you may need to add this hostname to your hosts file.
Expand Down
18 changes: 18 additions & 0 deletions core/test/unit/src/config/common.ts
Original file line number Diff line number Diff line change
Expand Up @@ -276,6 +276,24 @@ describe("joi.posixPath", () => {
})
})

describe("joi.hostname", () => {
const schema = joi.hostname()

it("should accept valid hostnames", () => {
const result = schema.validate("foo.bar.bas")
expect(result.error).to.be.undefined
})
it("should accept hostnames with a wildcard in the first DNS label", () => {
const result = schema.validate("*.bar.bas")
expect(result.error).to.be.undefined
})
it("should reject hostnames with wildcard DNS labels that are not the first label", () => {
const result = schema.validate("foo.*.bas")
expect(result.error).to.exist
expect(result!.error!.message).to.eql(`"value" only first DNS label my contain a wildcard.`)
})
})

describe("joi.environment", () => {
const schema = joi.environment()

Expand Down
6 changes: 3 additions & 3 deletions docs/reference/module-types/container.md
Original file line number Diff line number Diff line change
Expand Up @@ -1030,9 +1030,9 @@ The hostname that should route to this service. Defaults to the default hostname

Note that if you're developing locally you may need to add this hostname to your hosts file.

| Type | Required |
| -------- | -------- |
| `string` | No |
| Type | Required |
| ---------- | -------- |
| `hostname` | No |

### `services[].ingresses[].linkUrl`

Expand Down
6 changes: 3 additions & 3 deletions docs/reference/module-types/maven-container.md
Original file line number Diff line number Diff line change
Expand Up @@ -1038,9 +1038,9 @@ The hostname that should route to this service. Defaults to the default hostname

Note that if you're developing locally you may need to add this hostname to your hosts file.

| Type | Required |
| -------- | -------- |
| `string` | No |
| Type | Required |
| ---------- | -------- |
| `hostname` | No |

### `services[].ingresses[].linkUrl`

Expand Down

0 comments on commit 2a5f304

Please sign in to comment.