github.com/aclisp/heapster@v0.19.2-0.20160613100040-51756f899a96/Godeps/_workspace/src/k8s.io/kubernetes/pkg/labels/selector.go (about)

     1  /*
     2  Copyright 2014 The Kubernetes Authors All rights reserved.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8      http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package labels
    18  
    19  import (
    20  	"bytes"
    21  	"fmt"
    22  	"sort"
    23  	"strconv"
    24  	"strings"
    25  
    26  	"github.com/golang/glog"
    27  	"k8s.io/kubernetes/pkg/util/sets"
    28  	"k8s.io/kubernetes/pkg/util/validation"
    29  )
    30  
    31  // Selector represents a label selector.
    32  type Selector interface {
    33  	// Matches returns true if this selector matches the given set of labels.
    34  	Matches(Labels) bool
    35  
    36  	// Empty returns true if this selector does not restrict the selection space.
    37  	Empty() bool
    38  
    39  	// String returns a human readable string that represents this selector.
    40  	String() string
    41  
    42  	// Add adds requirements to the Selector
    43  	Add(r ...Requirement) Selector
    44  }
    45  
    46  // Everything returns a selector that matches all labels.
    47  func Everything() Selector {
    48  	return internalSelector{}
    49  }
    50  
    51  type nothingSelector struct{}
    52  
    53  func (n nothingSelector) Matches(_ Labels) bool         { return false }
    54  func (n nothingSelector) Empty() bool                   { return false }
    55  func (n nothingSelector) String() string                { return "<null>" }
    56  func (n nothingSelector) Add(_ ...Requirement) Selector { return n }
    57  
    58  // Nothing returns a selector that matches no labels
    59  func Nothing() Selector {
    60  	return nothingSelector{}
    61  }
    62  
    63  // Operator represents a key's relationship
    64  // to a set of values in a Requirement.
    65  type Operator string
    66  
    67  const (
    68  	DoesNotExistOperator Operator = "!"
    69  	EqualsOperator       Operator = "="
    70  	DoubleEqualsOperator Operator = "=="
    71  	InOperator           Operator = "in"
    72  	NotEqualsOperator    Operator = "!="
    73  	NotInOperator        Operator = "notin"
    74  	ExistsOperator       Operator = "exists"
    75  	GreaterThanOperator  Operator = "gt"
    76  	LessThanOperator     Operator = "lt"
    77  )
    78  
    79  func NewSelector() Selector {
    80  	return internalSelector(nil)
    81  }
    82  
    83  type internalSelector []Requirement
    84  
    85  // Sort by key to obtain determisitic parser
    86  type ByKey []Requirement
    87  
    88  func (a ByKey) Len() int { return len(a) }
    89  
    90  func (a ByKey) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
    91  
    92  func (a ByKey) Less(i, j int) bool { return a[i].key < a[j].key }
    93  
    94  // Requirement is a selector that contains values, a key
    95  // and an operator that relates the key and values. The zero
    96  // value of Requirement is invalid.
    97  // Requirement implements both set based match and exact match
    98  // Requirement is initialized via NewRequirement constructor for creating a valid Requirement.
    99  type Requirement struct {
   100  	key       string
   101  	operator  Operator
   102  	strValues sets.String
   103  }
   104  
   105  // NewRequirement is the constructor for a Requirement.
   106  // If any of these rules is violated, an error is returned:
   107  // (1) The operator can only be In, NotIn, Equals, DoubleEquals, NotEquals, Exists, or DoesNotExist.
   108  // (2) If the operator is In or NotIn, the values set must be non-empty.
   109  // (3) If the operator is Equals, DoubleEquals, or NotEquals, the values set must contain one value.
   110  // (4) If the operator is Exists or DoesNotExist, the value set must be empty.
   111  // (5) If the operator is Gt or Lt, the values set must contain only one value.
   112  // (6) The key is invalid due to its length, or sequence
   113  //     of characters. See validateLabelKey for more details.
   114  //
   115  // The empty string is a valid value in the input values set.
   116  func NewRequirement(key string, op Operator, vals sets.String) (*Requirement, error) {
   117  	if err := validateLabelKey(key); err != nil {
   118  		return nil, err
   119  	}
   120  	switch op {
   121  	case InOperator, NotInOperator:
   122  		if len(vals) == 0 {
   123  			return nil, fmt.Errorf("for 'in', 'notin' operators, values set can't be empty")
   124  		}
   125  	case EqualsOperator, DoubleEqualsOperator, NotEqualsOperator:
   126  		if len(vals) != 1 {
   127  			return nil, fmt.Errorf("exact-match compatibility requires one single value")
   128  		}
   129  	case ExistsOperator, DoesNotExistOperator:
   130  		if len(vals) != 0 {
   131  			return nil, fmt.Errorf("values set must be empty for exists and does not exist")
   132  		}
   133  	case GreaterThanOperator, LessThanOperator:
   134  		if len(vals) != 1 {
   135  			return nil, fmt.Errorf("for 'Gt', 'Lt' operators, exactly one value is required")
   136  		}
   137  		for val := range vals {
   138  			if _, err := strconv.ParseFloat(val, 64); err != nil {
   139  				return nil, fmt.Errorf("for 'Gt', 'Lt' operators, the value must be a number")
   140  			}
   141  		}
   142  	default:
   143  		return nil, fmt.Errorf("operator '%v' is not recognized", op)
   144  	}
   145  
   146  	for v := range vals {
   147  		if err := validateLabelValue(v); err != nil {
   148  			return nil, err
   149  		}
   150  	}
   151  	return &Requirement{key: key, operator: op, strValues: vals}, nil
   152  }
   153  
   154  // Matches returns true if the Requirement matches the input Labels.
   155  // There is a match in the following cases:
   156  // (1) The operator is Exists and Labels has the Requirement's key.
   157  // (2) The operator is In, Labels has the Requirement's key and Labels'
   158  //     value for that key is in Requirement's value set.
   159  // (3) The operator is NotIn, Labels has the Requirement's key and
   160  //     Labels' value for that key is not in Requirement's value set.
   161  // (4) The operator is DoesNotExist or NotIn and Labels does not have the
   162  //     Requirement's key.
   163  func (r *Requirement) Matches(ls Labels) bool {
   164  	switch r.operator {
   165  	case InOperator, EqualsOperator, DoubleEqualsOperator:
   166  		if !ls.Has(r.key) {
   167  			return false
   168  		}
   169  		return r.strValues.Has(ls.Get(r.key))
   170  	case NotInOperator, NotEqualsOperator:
   171  		if !ls.Has(r.key) {
   172  			return true
   173  		}
   174  		return !r.strValues.Has(ls.Get(r.key))
   175  	case ExistsOperator:
   176  		return ls.Has(r.key)
   177  	case DoesNotExistOperator:
   178  		return !ls.Has(r.key)
   179  	case GreaterThanOperator, LessThanOperator:
   180  		if !ls.Has(r.key) {
   181  			return false
   182  		}
   183  		lsValue, err := strconv.ParseFloat(ls.Get(r.key), 64)
   184  		if err != nil {
   185  			glog.V(10).Infof("Parse float failed for value %+v in label %+v, %+v", ls.Get(r.key), ls, err)
   186  			return false
   187  		}
   188  
   189  		// There should be only one strValue in r.strValues, and can be converted to a float number.
   190  		if len(r.strValues) != 1 {
   191  			glog.V(10).Infof("Invalid values count %+v of requirement %+v, for 'Gt', 'Lt' operators, exactly one value is required", len(r.strValues), r)
   192  			return false
   193  		}
   194  
   195  		var rValue float64
   196  		for strValue := range r.strValues {
   197  			rValue, err = strconv.ParseFloat(strValue, 64)
   198  			if err != nil {
   199  				glog.V(10).Infof("Parse float failed for value %+v in requirement %+v, for 'Gt', 'Lt' operators, the value must be a number", strValue, r)
   200  				return false
   201  			}
   202  		}
   203  		return (r.operator == GreaterThanOperator && lsValue > rValue) || (r.operator == LessThanOperator && lsValue < rValue)
   204  	default:
   205  		return false
   206  	}
   207  }
   208  
   209  func (r *Requirement) Key() string {
   210  	return r.key
   211  }
   212  func (r *Requirement) Operator() Operator {
   213  	return r.operator
   214  }
   215  func (r *Requirement) Values() sets.String {
   216  	ret := sets.String{}
   217  	for k := range r.strValues {
   218  		ret.Insert(k)
   219  	}
   220  	return ret
   221  }
   222  
   223  // Return true if the internalSelector doesn't restrict selection space
   224  func (lsel internalSelector) Empty() bool {
   225  	if lsel == nil {
   226  		return true
   227  	}
   228  	return len(lsel) == 0
   229  }
   230  
   231  // String returns a human-readable string that represents this
   232  // Requirement. If called on an invalid Requirement, an error is
   233  // returned. See NewRequirement for creating a valid Requirement.
   234  func (r *Requirement) String() string {
   235  	var buffer bytes.Buffer
   236  	if r.operator == DoesNotExistOperator {
   237  		buffer.WriteString("!")
   238  	}
   239  	buffer.WriteString(r.key)
   240  
   241  	switch r.operator {
   242  	case EqualsOperator:
   243  		buffer.WriteString("=")
   244  	case DoubleEqualsOperator:
   245  		buffer.WriteString("==")
   246  	case NotEqualsOperator:
   247  		buffer.WriteString("!=")
   248  	case InOperator:
   249  		buffer.WriteString(" in ")
   250  	case NotInOperator:
   251  		buffer.WriteString(" notin ")
   252  	case GreaterThanOperator:
   253  		buffer.WriteString(">")
   254  	case LessThanOperator:
   255  		buffer.WriteString("<")
   256  	case ExistsOperator, DoesNotExistOperator:
   257  		return buffer.String()
   258  	}
   259  
   260  	switch r.operator {
   261  	case InOperator, NotInOperator:
   262  		buffer.WriteString("(")
   263  	}
   264  	if len(r.strValues) == 1 {
   265  		buffer.WriteString(r.strValues.List()[0])
   266  	} else { // only > 1 since == 0 prohibited by NewRequirement
   267  		buffer.WriteString(strings.Join(r.strValues.List(), ","))
   268  	}
   269  
   270  	switch r.operator {
   271  	case InOperator, NotInOperator:
   272  		buffer.WriteString(")")
   273  	}
   274  	return buffer.String()
   275  }
   276  
   277  // Add adds requirements to the selector. It copies the current selector returning a new one
   278  func (lsel internalSelector) Add(reqs ...Requirement) Selector {
   279  	var sel internalSelector
   280  	for ix := range lsel {
   281  		sel = append(sel, lsel[ix])
   282  	}
   283  	for _, r := range reqs {
   284  		sel = append(sel, r)
   285  	}
   286  	sort.Sort(ByKey(sel))
   287  	return sel
   288  }
   289  
   290  // Matches for a internalSelector returns true if all
   291  // its Requirements match the input Labels. If any
   292  // Requirement does not match, false is returned.
   293  func (lsel internalSelector) Matches(l Labels) bool {
   294  	for ix := range lsel {
   295  		if matches := lsel[ix].Matches(l); !matches {
   296  			return false
   297  		}
   298  	}
   299  	return true
   300  }
   301  
   302  // String returns a comma-separated string of all
   303  // the internalSelector Requirements' human-readable strings.
   304  func (lsel internalSelector) String() string {
   305  	var reqs []string
   306  	for ix := range lsel {
   307  		reqs = append(reqs, lsel[ix].String())
   308  	}
   309  	return strings.Join(reqs, ",")
   310  }
   311  
   312  // constants definition for lexer token
   313  type Token int
   314  
   315  const (
   316  	ErrorToken Token = iota
   317  	EndOfStringToken
   318  	ClosedParToken
   319  	CommaToken
   320  	DoesNotExistToken
   321  	DoubleEqualsToken
   322  	EqualsToken
   323  	GreaterThanToken
   324  	IdentifierToken // to represent keys and values
   325  	InToken
   326  	LessThanToken
   327  	NotEqualsToken
   328  	NotInToken
   329  	OpenParToken
   330  )
   331  
   332  // string2token contains the mapping between lexer Token and token literal
   333  // (except IdentifierToken, EndOfStringToken and ErrorToken since it makes no sense)
   334  var string2token = map[string]Token{
   335  	")":     ClosedParToken,
   336  	",":     CommaToken,
   337  	"!":     DoesNotExistToken,
   338  	"==":    DoubleEqualsToken,
   339  	"=":     EqualsToken,
   340  	">":     GreaterThanToken,
   341  	"in":    InToken,
   342  	"<":     LessThanToken,
   343  	"!=":    NotEqualsToken,
   344  	"notin": NotInToken,
   345  	"(":     OpenParToken,
   346  }
   347  
   348  // The item produced by the lexer. It contains the Token and the literal.
   349  type ScannedItem struct {
   350  	tok     Token
   351  	literal string
   352  }
   353  
   354  // isWhitespace returns true if the rune is a space, tab, or newline.
   355  func isWhitespace(ch byte) bool {
   356  	return ch == ' ' || ch == '\t' || ch == '\r' || ch == '\n'
   357  }
   358  
   359  // isSpecialSymbol detect if the character ch can be an operator
   360  func isSpecialSymbol(ch byte) bool {
   361  	switch ch {
   362  	case '=', '!', '(', ')', ',', '>', '<':
   363  		return true
   364  	}
   365  	return false
   366  }
   367  
   368  // Lexer represents the Lexer struct for label selector.
   369  // It contains necessary informationt to tokenize the input string
   370  type Lexer struct {
   371  	// s stores the string to be tokenized
   372  	s string
   373  	// pos is the position currently tokenized
   374  	pos int
   375  }
   376  
   377  // read return the character currently lexed
   378  // increment the position and check the buffer overflow
   379  func (l *Lexer) read() (b byte) {
   380  	b = 0
   381  	if l.pos < len(l.s) {
   382  		b = l.s[l.pos]
   383  		l.pos++
   384  	}
   385  	return b
   386  }
   387  
   388  // unread 'undoes' the last read character
   389  func (l *Lexer) unread() {
   390  	l.pos--
   391  }
   392  
   393  // scanIdOrKeyword scans string to recognize literal token (for example 'in') or an identifier.
   394  func (l *Lexer) scanIdOrKeyword() (tok Token, lit string) {
   395  	var buffer []byte
   396  IdentifierLoop:
   397  	for {
   398  		switch ch := l.read(); {
   399  		case ch == 0:
   400  			break IdentifierLoop
   401  		case isSpecialSymbol(ch) || isWhitespace(ch):
   402  			l.unread()
   403  			break IdentifierLoop
   404  		default:
   405  			buffer = append(buffer, ch)
   406  		}
   407  	}
   408  	s := string(buffer)
   409  	if val, ok := string2token[s]; ok { // is a literal token?
   410  		return val, s
   411  	}
   412  	return IdentifierToken, s // otherwise is an identifier
   413  }
   414  
   415  // scanSpecialSymbol scans string starting with special symbol.
   416  // special symbol identify non literal operators. "!=", "==", "="
   417  func (l *Lexer) scanSpecialSymbol() (Token, string) {
   418  	lastScannedItem := ScannedItem{}
   419  	var buffer []byte
   420  SpecialSymbolLoop:
   421  	for {
   422  		switch ch := l.read(); {
   423  		case ch == 0:
   424  			break SpecialSymbolLoop
   425  		case isSpecialSymbol(ch):
   426  			buffer = append(buffer, ch)
   427  			if token, ok := string2token[string(buffer)]; ok {
   428  				lastScannedItem = ScannedItem{tok: token, literal: string(buffer)}
   429  			} else if lastScannedItem.tok != 0 {
   430  				l.unread()
   431  				break SpecialSymbolLoop
   432  			}
   433  		default:
   434  			l.unread()
   435  			break SpecialSymbolLoop
   436  		}
   437  	}
   438  	if lastScannedItem.tok == 0 {
   439  		return ErrorToken, fmt.Sprintf("error expected: keyword found '%s'", buffer)
   440  	}
   441  	return lastScannedItem.tok, lastScannedItem.literal
   442  }
   443  
   444  // skipWhiteSpaces consumes all blank characters
   445  // returning the first non blank character
   446  func (l *Lexer) skipWhiteSpaces(ch byte) byte {
   447  	for {
   448  		if !isWhitespace(ch) {
   449  			return ch
   450  		}
   451  		ch = l.read()
   452  	}
   453  }
   454  
   455  // Lex returns a pair of Token and the literal
   456  // literal is meaningfull only for IdentifierToken token
   457  func (l *Lexer) Lex() (tok Token, lit string) {
   458  	switch ch := l.skipWhiteSpaces(l.read()); {
   459  	case ch == 0:
   460  		return EndOfStringToken, ""
   461  	case isSpecialSymbol(ch):
   462  		l.unread()
   463  		return l.scanSpecialSymbol()
   464  	default:
   465  		l.unread()
   466  		return l.scanIdOrKeyword()
   467  	}
   468  }
   469  
   470  // Parser data structure contains the label selector parser data strucutre
   471  type Parser struct {
   472  	l            *Lexer
   473  	scannedItems []ScannedItem
   474  	position     int
   475  }
   476  
   477  // Parser context represents context during parsing:
   478  // some literal for example 'in' and 'notin' can be
   479  // recognized as operator for example 'x in (a)' but
   480  // it can be recognized as value for example 'value in (in)'
   481  type ParserContext int
   482  
   483  const (
   484  	KeyAndOperator ParserContext = iota
   485  	Values
   486  )
   487  
   488  // lookahead func returns the current token and string. No increment of current position
   489  func (p *Parser) lookahead(context ParserContext) (Token, string) {
   490  	tok, lit := p.scannedItems[p.position].tok, p.scannedItems[p.position].literal
   491  	if context == Values {
   492  		switch tok {
   493  		case InToken, NotInToken:
   494  			tok = IdentifierToken
   495  		}
   496  	}
   497  	return tok, lit
   498  }
   499  
   500  // consume returns current token and string. Increments the the position
   501  func (p *Parser) consume(context ParserContext) (Token, string) {
   502  	p.position++
   503  	tok, lit := p.scannedItems[p.position-1].tok, p.scannedItems[p.position-1].literal
   504  	if context == Values {
   505  		switch tok {
   506  		case InToken, NotInToken:
   507  			tok = IdentifierToken
   508  		}
   509  	}
   510  	return tok, lit
   511  }
   512  
   513  // scan runs through the input string and stores the ScannedItem in an array
   514  // Parser can now lookahead and consume the tokens
   515  func (p *Parser) scan() {
   516  	for {
   517  		token, literal := p.l.Lex()
   518  		p.scannedItems = append(p.scannedItems, ScannedItem{token, literal})
   519  		if token == EndOfStringToken {
   520  			break
   521  		}
   522  	}
   523  }
   524  
   525  // parse runs the left recursive descending algorithm
   526  // on input string. It returns a list of Requirement objects.
   527  func (p *Parser) parse() (internalSelector, error) {
   528  	p.scan() // init scannedItems
   529  
   530  	var requirements internalSelector
   531  	for {
   532  		tok, lit := p.lookahead(Values)
   533  		switch tok {
   534  		case IdentifierToken, DoesNotExistToken:
   535  			r, err := p.parseRequirement()
   536  			if err != nil {
   537  				return nil, fmt.Errorf("unable to parse requirement: %v", err)
   538  			}
   539  			requirements = append(requirements, *r)
   540  			t, l := p.consume(Values)
   541  			switch t {
   542  			case EndOfStringToken:
   543  				return requirements, nil
   544  			case CommaToken:
   545  				t2, l2 := p.lookahead(Values)
   546  				if t2 != IdentifierToken && t2 != DoesNotExistToken {
   547  					return nil, fmt.Errorf("found '%s', expected: identifier after ','", l2)
   548  				}
   549  			default:
   550  				return nil, fmt.Errorf("found '%s', expected: ',' or 'end of string'", l)
   551  			}
   552  		case EndOfStringToken:
   553  			return requirements, nil
   554  		default:
   555  			return nil, fmt.Errorf("found '%s', expected: !, identifier, or 'end of string'", lit)
   556  		}
   557  	}
   558  }
   559  
   560  func (p *Parser) parseRequirement() (*Requirement, error) {
   561  	key, operator, err := p.parseKeyAndInferOperator()
   562  	if err != nil {
   563  		return nil, err
   564  	}
   565  	if operator == ExistsOperator || operator == DoesNotExistOperator { // operator found lookahead set checked
   566  		return NewRequirement(key, operator, nil)
   567  	}
   568  	operator, err = p.parseOperator()
   569  	if err != nil {
   570  		return nil, err
   571  	}
   572  	var values sets.String
   573  	switch operator {
   574  	case InOperator, NotInOperator:
   575  		values, err = p.parseValues()
   576  	case EqualsOperator, DoubleEqualsOperator, NotEqualsOperator, GreaterThanOperator, LessThanOperator:
   577  		values, err = p.parseExactValue()
   578  	}
   579  	if err != nil {
   580  		return nil, err
   581  	}
   582  	return NewRequirement(key, operator, values)
   583  
   584  }
   585  
   586  // parseKeyAndInferOperator parse literals.
   587  // in case of no operator '!, in, notin, ==, =, !=' are found
   588  // the 'exists' operator is inferred
   589  func (p *Parser) parseKeyAndInferOperator() (string, Operator, error) {
   590  	var operator Operator
   591  	tok, literal := p.consume(Values)
   592  	if tok == DoesNotExistToken {
   593  		operator = DoesNotExistOperator
   594  		tok, literal = p.consume(Values)
   595  	}
   596  	if tok != IdentifierToken {
   597  		err := fmt.Errorf("found '%s', expected: identifier", literal)
   598  		return "", "", err
   599  	}
   600  	if err := validateLabelKey(literal); err != nil {
   601  		return "", "", err
   602  	}
   603  	if t, _ := p.lookahead(Values); t == EndOfStringToken || t == CommaToken {
   604  		if operator != DoesNotExistOperator {
   605  			operator = ExistsOperator
   606  		}
   607  	}
   608  	return literal, operator, nil
   609  }
   610  
   611  // parseOperator return operator and eventually matchType
   612  // matchType can be exact
   613  func (p *Parser) parseOperator() (op Operator, err error) {
   614  	tok, lit := p.consume(KeyAndOperator)
   615  	switch tok {
   616  	// DoesNotExistToken shouldn't be here because it's a unary operator, not a binary operator
   617  	case InToken:
   618  		op = InOperator
   619  	case EqualsToken:
   620  		op = EqualsOperator
   621  	case DoubleEqualsToken:
   622  		op = DoubleEqualsOperator
   623  	case GreaterThanToken:
   624  		op = GreaterThanOperator
   625  	case LessThanToken:
   626  		op = LessThanOperator
   627  	case NotInToken:
   628  		op = NotInOperator
   629  	case NotEqualsToken:
   630  		op = NotEqualsOperator
   631  	default:
   632  		return "", fmt.Errorf("found '%s', expected: '=', '!=', '==', 'in', notin'", lit)
   633  	}
   634  	return op, nil
   635  }
   636  
   637  // parseValues parses the values for set based matching (x,y,z)
   638  func (p *Parser) parseValues() (sets.String, error) {
   639  	tok, lit := p.consume(Values)
   640  	if tok != OpenParToken {
   641  		return nil, fmt.Errorf("found '%s' expected: '('", lit)
   642  	}
   643  	tok, lit = p.lookahead(Values)
   644  	switch tok {
   645  	case IdentifierToken, CommaToken:
   646  		s, err := p.parseIdentifiersList() // handles general cases
   647  		if err != nil {
   648  			return s, err
   649  		}
   650  		if tok, _ = p.consume(Values); tok != ClosedParToken {
   651  			return nil, fmt.Errorf("found '%s', expected: ')'", lit)
   652  		}
   653  		return s, nil
   654  	case ClosedParToken: // handles "()"
   655  		p.consume(Values)
   656  		return sets.NewString(""), nil
   657  	default:
   658  		return nil, fmt.Errorf("found '%s', expected: ',', ')' or identifier", lit)
   659  	}
   660  }
   661  
   662  // parseIdentifiersList parses a (possibly empty) list of
   663  // of comma separated (possibly empty) identifiers
   664  func (p *Parser) parseIdentifiersList() (sets.String, error) {
   665  	s := sets.NewString()
   666  	for {
   667  		tok, lit := p.consume(Values)
   668  		switch tok {
   669  		case IdentifierToken:
   670  			s.Insert(lit)
   671  			tok2, lit2 := p.lookahead(Values)
   672  			switch tok2 {
   673  			case CommaToken:
   674  				continue
   675  			case ClosedParToken:
   676  				return s, nil
   677  			default:
   678  				return nil, fmt.Errorf("found '%s', expected: ',' or ')'", lit2)
   679  			}
   680  		case CommaToken: // handled here since we can have "(,"
   681  			if s.Len() == 0 {
   682  				s.Insert("") // to handle (,
   683  			}
   684  			tok2, _ := p.lookahead(Values)
   685  			if tok2 == ClosedParToken {
   686  				s.Insert("") // to handle ,)  Double "" removed by StringSet
   687  				return s, nil
   688  			}
   689  			if tok2 == CommaToken {
   690  				p.consume(Values)
   691  				s.Insert("") // to handle ,, Double "" removed by StringSet
   692  			}
   693  		default: // it can be operator
   694  			return s, fmt.Errorf("found '%s', expected: ',', or identifier", lit)
   695  		}
   696  	}
   697  }
   698  
   699  // parseExactValue parses the only value for exact match style
   700  func (p *Parser) parseExactValue() (sets.String, error) {
   701  	s := sets.NewString()
   702  	tok, lit := p.lookahead(Values)
   703  	if tok == EndOfStringToken || tok == CommaToken {
   704  		s.Insert("")
   705  		return s, nil
   706  	}
   707  	tok, lit = p.consume(Values)
   708  	if tok == IdentifierToken {
   709  		s.Insert(lit)
   710  		return s, nil
   711  	}
   712  	return nil, fmt.Errorf("found '%s', expected: identifier", lit)
   713  }
   714  
   715  // Parse takes a string representing a selector and returns a selector
   716  // object, or an error. This parsing function differs from ParseSelector
   717  // as they parse different selectors with different syntaxes.
   718  // The input will cause an error if it does not follow this form:
   719  //
   720  // <selector-syntax> ::= <requirement> | <requirement> "," <selector-syntax> ]
   721  // <requirement> ::= [!] KEY [ <set-based-restriction> | <exact-match-restriction> ]
   722  // <set-based-restriction> ::= "" | <inclusion-exclusion> <value-set>
   723  // <inclusion-exclusion> ::= <inclusion> | <exclusion>
   724  //           <exclusion> ::= "notin"
   725  //           <inclusion> ::= "in"
   726  //           <value-set> ::= "(" <values> ")"
   727  //              <values> ::= VALUE | VALUE "," <values>
   728  // <exact-match-restriction> ::= ["="|"=="|"!="] VALUE
   729  // KEY is a sequence of one or more characters following [ DNS_SUBDOMAIN "/" ] DNS_LABEL. Max length is 63 characters.
   730  // VALUE is a sequence of zero or more characters "([A-Za-z0-9_-\.])". Max length is 63 characters.
   731  // Delimiter is white space: (' ', '\t')
   732  // Example of valid syntax:
   733  //  "x in (foo,,baz),y,z notin ()"
   734  //
   735  // Note:
   736  //  (1) Inclusion - " in " - denotes that the KEY exists and is equal to any of the
   737  //      VALUEs in its requirement
   738  //  (2) Exclusion - " notin " - denotes that the KEY is not equal to any
   739  //      of the VALUEs in its requirement or does not exist
   740  //  (3) The empty string is a valid VALUE
   741  //  (4) A requirement with just a KEY - as in "y" above - denotes that
   742  //      the KEY exists and can be any VALUE.
   743  //  (5) A requirement with just !KEY requires that the KEY not exist.
   744  //
   745  func Parse(selector string) (Selector, error) {
   746  	parsedSelector, err := parse(selector)
   747  	if err == nil {
   748  		return parsedSelector, nil
   749  	}
   750  	return nil, err
   751  }
   752  
   753  // parse parses the string representation of the selector and returns the internalSelector struct.
   754  // The callers of this method can then decide how to return the internalSelector struct to their
   755  // callers. This function has two callers now, one returns a Selector interface and the other
   756  // returns a list of requirements.
   757  func parse(selector string) (internalSelector, error) {
   758  	p := &Parser{l: &Lexer{s: selector, pos: 0}}
   759  	items, err := p.parse()
   760  	if err != nil {
   761  		return nil, err
   762  	}
   763  	sort.Sort(ByKey(items)) // sort to grant determistic parsing
   764  	return internalSelector(items), err
   765  }
   766  
   767  var qualifiedNameErrorMsg string = fmt.Sprintf(`must be a qualified name (at most %d characters, matching regex %s), with an optional DNS subdomain prefix (at most %d characters, matching regex %s) and slash (/): e.g. "MyName" or "example.com/MyName"`, validation.QualifiedNameMaxLength, validation.QualifiedNameFmt, validation.DNS1123SubdomainMaxLength, validation.DNS1123SubdomainFmt)
   768  var labelValueErrorMsg string = fmt.Sprintf(`must have at most %d characters, matching regex %s: e.g. "MyValue" or ""`, validation.LabelValueMaxLength, validation.LabelValueFmt)
   769  
   770  func validateLabelKey(k string) error {
   771  	if !validation.IsQualifiedName(k) {
   772  		return fmt.Errorf("invalid label key: %s", qualifiedNameErrorMsg)
   773  	}
   774  	return nil
   775  }
   776  
   777  func validateLabelValue(v string) error {
   778  	if !validation.IsValidLabelValue(v) {
   779  		return fmt.Errorf("invalid label value: %s", labelValueErrorMsg)
   780  	}
   781  	return nil
   782  }
   783  
   784  // SelectorFromSet returns a Selector which will match exactly the given Set. A
   785  // nil and empty Sets are considered equivalent to Everything().
   786  func SelectorFromSet(ls Set) Selector {
   787  	if ls == nil {
   788  		return internalSelector{}
   789  	}
   790  	var requirements internalSelector
   791  	for label, value := range ls {
   792  		if r, err := NewRequirement(label, EqualsOperator, sets.NewString(value)); err != nil {
   793  			//TODO: double check errors when input comes from serialization?
   794  			return internalSelector{}
   795  		} else {
   796  			requirements = append(requirements, *r)
   797  		}
   798  	}
   799  	// sort to have deterministic string representation
   800  	sort.Sort(ByKey(requirements))
   801  	return internalSelector(requirements)
   802  }
   803  
   804  // ParseToRequirements takes a string representing a selector and returns a list of
   805  // requirements. This function is suitable for those callers that perform additional
   806  // processing on selector requirements.
   807  // See the documentation for Parse() function for more details.
   808  // TODO: Consider exporting the internalSelector type instead.
   809  func ParseToRequirements(selector string) ([]Requirement, error) {
   810  	return parse(selector)
   811  }