parse.go 1.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283
  1. package filters
  2. import (
  3. "encoding/json"
  4. "errors"
  5. "regexp"
  6. "strings"
  7. )
  8. type Args map[string][]string
  9. // Parse the argument to the filter flag. Like
  10. //
  11. // `docker ps -f 'created=today' -f 'image.name=ubuntu*'`
  12. //
  13. // If prev map is provided, then it is appended to, and returned. By default a new
  14. // map is created.
  15. func ParseFlag(arg string, prev Args) (Args, error) {
  16. var filters Args = prev
  17. if prev == nil {
  18. filters = Args{}
  19. }
  20. if len(arg) == 0 {
  21. return filters, nil
  22. }
  23. if !strings.Contains(arg, "=") {
  24. return filters, ErrorBadFormat
  25. }
  26. f := strings.SplitN(arg, "=", 2)
  27. filters[f[0]] = append(filters[f[0]], f[1])
  28. return filters, nil
  29. }
  30. var ErrorBadFormat = errors.New("bad format of filter (expected name=value)")
  31. // packs the Args into an string for easy transport from client to server
  32. func ToParam(a Args) (string, error) {
  33. // this way we don't URL encode {}, just empty space
  34. if len(a) == 0 {
  35. return "", nil
  36. }
  37. buf, err := json.Marshal(a)
  38. if err != nil {
  39. return "", err
  40. }
  41. return string(buf), nil
  42. }
  43. // unpacks the filter Args
  44. func FromParam(p string) (Args, error) {
  45. args := Args{}
  46. if len(p) == 0 {
  47. return args, nil
  48. }
  49. err := json.Unmarshal([]byte(p), &args)
  50. if err != nil {
  51. return nil, err
  52. }
  53. return args, nil
  54. }
  55. func (filters Args) Match(field, source string) bool {
  56. fieldValues := filters[field]
  57. //do not filter if there is no filter set or cannot determine filter
  58. if len(fieldValues) == 0 {
  59. return true
  60. }
  61. for _, name2match := range fieldValues {
  62. match, err := regexp.MatchString(name2match, source)
  63. if err != nil {
  64. continue
  65. }
  66. if match {
  67. return true
  68. }
  69. }
  70. return false
  71. }