mirror of https://github.com/caddyserver/caddy.git
caddyfile: Copy input before parsing (fix #4422)
This commit is contained in:
parent
e81369e220
commit
b47af6ef04
|
@ -179,6 +179,11 @@ d {
|
||||||
{$F}
|
{$F}
|
||||||
}`,
|
}`,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
description: "env var placeholders with port",
|
||||||
|
input: `:{$PORT}`,
|
||||||
|
expect: `:{$PORT}`,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
description: "comments",
|
description: "comments",
|
||||||
input: `#a "\n"
|
input: `#a "\n"
|
||||||
|
|
|
@ -37,7 +37,13 @@ import (
|
||||||
// Environment variables in {$ENVIRONMENT_VARIABLE} notation
|
// Environment variables in {$ENVIRONMENT_VARIABLE} notation
|
||||||
// will be replaced before parsing begins.
|
// will be replaced before parsing begins.
|
||||||
func Parse(filename string, input []byte) ([]ServerBlock, error) {
|
func Parse(filename string, input []byte) ([]ServerBlock, error) {
|
||||||
tokens, err := allTokens(filename, input)
|
// unfortunately, we must copy the input because parsing must
|
||||||
|
// remain a read-only operation, but we have to expand environment
|
||||||
|
// variables before we parse, which changes the underlying array (#4422)
|
||||||
|
inputCopy := make([]byte, len(input))
|
||||||
|
copy(inputCopy, input)
|
||||||
|
|
||||||
|
tokens, err := allTokens(filename, inputCopy)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
@ -51,7 +57,23 @@ func Parse(filename string, input []byte) ([]ServerBlock, error) {
|
||||||
return p.parseAll()
|
return p.parseAll()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// allTokens lexes the entire input, but does not parse it.
|
||||||
|
// It returns all the tokens from the input, unstructured
|
||||||
|
// and in order. It may mutate input as it expands env vars.
|
||||||
|
func allTokens(filename string, input []byte) ([]Token, error) {
|
||||||
|
inputCopy, err := replaceEnvVars(input)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
tokens, err := Tokenize(inputCopy, filename)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return tokens, nil
|
||||||
|
}
|
||||||
|
|
||||||
// replaceEnvVars replaces all occurrences of environment variables.
|
// replaceEnvVars replaces all occurrences of environment variables.
|
||||||
|
// It mutates the underlying array and returns the updated slice.
|
||||||
func replaceEnvVars(input []byte) ([]byte, error) {
|
func replaceEnvVars(input []byte) ([]byte, error) {
|
||||||
var offset int
|
var offset int
|
||||||
for {
|
for {
|
||||||
|
@ -96,21 +118,6 @@ func replaceEnvVars(input []byte) ([]byte, error) {
|
||||||
return input, nil
|
return input, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// allTokens lexes the entire input, but does not parse it.
|
|
||||||
// It returns all the tokens from the input, unstructured
|
|
||||||
// and in order.
|
|
||||||
func allTokens(filename string, input []byte) ([]Token, error) {
|
|
||||||
input, err := replaceEnvVars(input)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
tokens, err := Tokenize(input, filename)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
return tokens, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
type parser struct {
|
type parser struct {
|
||||||
*Dispenser
|
*Dispenser
|
||||||
block ServerBlock // current server block being parsed
|
block ServerBlock // current server block being parsed
|
||||||
|
|
Loading…
Reference in New Issue