github.com/marunai/moby@v1.13.1/daemon/events/testutils/testutils.go (about)

     1  package testutils
     2  
     3  import (
     4  	"fmt"
     5  	"regexp"
     6  	"strings"
     7  	"time"
     8  
     9  	"github.com/docker/docker/api/types/events"
    10  	timetypes "github.com/docker/docker/api/types/time"
    11  )
    12  
    13  var (
    14  	reTimestamp  = `(?P<timestamp>\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}.\d{9}(:?(:?(:?-|\+)\d{2}:\d{2})|Z))`
    15  	reEventType  = `(?P<eventType>\w+)`
    16  	reAction     = `(?P<action>\w+)`
    17  	reID         = `(?P<id>[^\s]+)`
    18  	reAttributes = `(\s\((?P<attributes>[^\)]+)\))?`
    19  	reString     = fmt.Sprintf(`\A%s\s%s\s%s\s%s%s\z`, reTimestamp, reEventType, reAction, reID, reAttributes)
    20  
    21  	// eventCliRegexp is a regular expression that matches all possible event outputs in the cli
    22  	eventCliRegexp = regexp.MustCompile(reString)
    23  )
    24  
    25  // ScanMap turns an event string like the default ones formatted in the cli output
    26  // and turns it into map.
    27  func ScanMap(text string) map[string]string {
    28  	matches := eventCliRegexp.FindAllStringSubmatch(text, -1)
    29  	md := map[string]string{}
    30  	if len(matches) == 0 {
    31  		return md
    32  	}
    33  
    34  	names := eventCliRegexp.SubexpNames()
    35  	for i, n := range matches[0] {
    36  		md[names[i]] = n
    37  	}
    38  	return md
    39  }
    40  
    41  // Scan turns an event string like the default ones formatted in the cli output
    42  // and turns it into an event message.
    43  func Scan(text string) (*events.Message, error) {
    44  	md := ScanMap(text)
    45  	if len(md) == 0 {
    46  		return nil, fmt.Errorf("text is not an event: %s", text)
    47  	}
    48  
    49  	f, err := timetypes.GetTimestamp(md["timestamp"], time.Now())
    50  	if err != nil {
    51  		return nil, err
    52  	}
    53  
    54  	t, tn, err := timetypes.ParseTimestamps(f, -1)
    55  	if err != nil {
    56  		return nil, err
    57  	}
    58  
    59  	attrs := make(map[string]string)
    60  	for _, a := range strings.SplitN(md["attributes"], ", ", -1) {
    61  		kv := strings.SplitN(a, "=", 2)
    62  		attrs[kv[0]] = kv[1]
    63  	}
    64  
    65  	tu := time.Unix(t, tn)
    66  	return &events.Message{
    67  		Time:     t,
    68  		TimeNano: tu.UnixNano(),
    69  		Type:     md["eventType"],
    70  		Action:   md["action"],
    71  		Actor: events.Actor{
    72  			ID:         md["id"],
    73  			Attributes: attrs,
    74  		},
    75  	}, nil
    76  }