Skip to content

Commit

Permalink
Merge pull request #3558 from hashicorp/b-nomad-validate-with-defaults
Browse files Browse the repository at this point in the history
Make validate command ignore environment variables in service name
  • Loading branch information
Preetha authored Nov 17, 2017
2 parents c446e4c + 800f5cb commit 7bf4d34
Show file tree
Hide file tree
Showing 4 changed files with 25 additions and 7 deletions.
5 changes: 5 additions & 0 deletions helper/args/args.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,3 +21,8 @@ func ReplaceEnv(arg string, environments ...map[string]string) string {
return arg
})
}

// ReplaceEnvWithPlaceHolder replaces all occurrences of environment variables with the placeholder string.
func ReplaceEnvWithPlaceHolder(arg string, placeholder string) string {
return envRe.ReplaceAllString(arg, placeholder)
}
11 changes: 5 additions & 6 deletions nomad/structs/structs.go
Original file line number Diff line number Diff line change
Expand Up @@ -3074,12 +3074,11 @@ func (s *Service) Validate() error {
var mErr multierror.Error

// Ensure the service name is valid per the below RFCs but make an exception
// for our interpolation syntax
// RFC-952 §1 (https://tools.ietf.org/html/rfc952), RFC-1123 §2.1
// (https://tools.ietf.org/html/rfc1123), and RFC-2782
// (https://tools.ietf.org/html/rfc2782).
re := regexp.MustCompile(`^(?i:[a-z0-9]|[a-z0-9\$][a-zA-Z0-9\-\$\{\}\_\.]*[a-z0-9\}])$`)
if !re.MatchString(s.Name) {
// for our interpolation syntax by first stripping any environment variables from the name

serviceNameStripped := args.ReplaceEnvWithPlaceHolder(s.Name, "ENV-VAR")

if err := s.ValidateName(serviceNameStripped); err != nil {
mErr.Errors = append(mErr.Errors, fmt.Errorf("service name must be valid per RFC 1123 and can contain only alphanumeric characters or dashes: %q", s.Name))
}

Expand Down
8 changes: 8 additions & 0 deletions nomad/structs/structs_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1681,6 +1681,14 @@ func TestInvalidServiceCheck(t *testing.T) {
t.Fatalf("Service should be valid: %v", err)
}

s = Service{
Name: "my_service-${NOMAD_META_FOO}",
PortLabel: "bar",
}
if err := s.Validate(); err == nil {
t.Fatalf("Service should be invalid (contains underscore but not in a variable name): %v", err)
}

s = Service{
Name: "abcdef0123456789-abcdef0123456789-abcdef0123456789-abcdef0123456",
PortLabel: "bar",
Expand Down
8 changes: 7 additions & 1 deletion website/source/docs/job-specification/service.html.md
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,13 @@ does not automatically enable service discovery.
- `${GROUP}` - the name of the group
- `${TASK}` - the name of the task
- `${BASE}` - shorthand for `${JOB}-${GROUP}-${TASK}`


Validation of the name occurs in two parts. When the job is registered, an initial validation pass checks that
the service name adheres to RFC-1123 §2.1 and the length limit, excluding any variables requiring interpolation.
Once the client receives the service and all interpretable values are available, the service name will be
interpolated and revalidated. This can cause certain service names to pass validation at submit time but fail
at runtime.

- `port` `(string: <required>)` - Specifies the label of the port on which this
service is running. Note this is the _label_ of the port and not the port
number. The port label must match one defined in the [`network`][network]
Expand Down

0 comments on commit 7bf4d34

Please sign in to comment.