| package notifications |
| |
| import ( |
| "fmt" |
| "time" |
| |
| "github.com/docker/distribution" |
| ) |
| |
| // EventAction constants used in action field of Event. |
| const ( |
| EventActionPull = "pull" |
| EventActionPush = "push" |
| EventActionMount = "mount" |
| EventActionDelete = "delete" |
| ) |
| |
| const ( |
| // EventsMediaType is the mediatype for the json event envelope. If the |
| // Event, ActorRecord, SourceRecord or Envelope structs change, the version |
| // number should be incremented. |
| EventsMediaType = "application/vnd.docker.distribution.events.v1+json" |
| // LayerMediaType is the media type for image rootfs diffs (aka "layers") |
| // used by Docker. We don't expect this to change for quite a while. |
| layerMediaType = "application/vnd.docker.container.image.rootfs.diff+x-gtar" |
| ) |
| |
| // Envelope defines the fields of a json event envelope message that can hold |
| // one or more events. |
| type Envelope struct { |
| // Events make up the contents of the envelope. Events present in a single |
| // envelope are not necessarily related. |
| Events []Event `json:"events,omitempty"` |
| } |
| |
| // TODO(stevvooe): The event type should be separate from the json format. It |
| // should be defined as an interface. Leaving as is for now since we don't |
| // need that at this time. If we make this change, the struct below would be |
| // called "EventRecord". |
| |
| // Event provides the fields required to describe a registry event. |
| type Event struct { |
| // ID provides a unique identifier for the event. |
| ID string `json:"id,omitempty"` |
| |
| // Timestamp is the time at which the event occurred. |
| Timestamp time.Time `json:"timestamp,omitempty"` |
| |
| // Action indicates what action encompasses the provided event. |
| Action string `json:"action,omitempty"` |
| |
| // Target uniquely describes the target of the event. |
| Target struct { |
| // TODO(stevvooe): Use http.DetectContentType for layers, maybe. |
| |
| distribution.Descriptor |
| |
| // Length in bytes of content. Same as Size field in Descriptor. |
| // Provided for backwards compatibility. |
| Length int64 `json:"length,omitempty"` |
| |
| // Repository identifies the named repository. |
| Repository string `json:"repository,omitempty"` |
| |
| // FromRepository identifies the named repository which a blob was mounted |
| // from if appropriate. |
| FromRepository string `json:"fromRepository,omitempty"` |
| |
| // URL provides a direct link to the content. |
| URL string `json:"url,omitempty"` |
| |
| // Tag provides the tag |
| Tag string `json:"tag,omitempty"` |
| |
| // References provides the references descriptors. |
| References []distribution.Descriptor `json:"references,omitempty"` |
| } `json:"target,omitempty"` |
| |
| // Request covers the request that generated the event. |
| Request RequestRecord `json:"request,omitempty"` |
| |
| // Actor specifies the agent that initiated the event. For most |
| // situations, this could be from the authorization context of the request. |
| Actor ActorRecord `json:"actor,omitempty"` |
| |
| // Source identifies the registry node that generated the event. Put |
| // differently, while the actor "initiates" the event, the source |
| // "generates" it. |
| Source SourceRecord `json:"source,omitempty"` |
| } |
| |
| // ActorRecord specifies the agent that initiated the event. For most |
| // situations, this could be from the authorization context of the request. |
| // Data in this record can refer to both the initiating client and the |
| // generating request. |
| type ActorRecord struct { |
| // Name corresponds to the subject or username associated with the |
| // request context that generated the event. |
| Name string `json:"name,omitempty"` |
| |
| // TODO(stevvooe): Look into setting a session cookie to get this |
| // without docker daemon. |
| // SessionID |
| |
| // TODO(stevvooe): Push the "Docker-Command" header to replace cookie and |
| // get the actual command. |
| // Command |
| } |
| |
| // RequestRecord covers the request that generated the event. |
| type RequestRecord struct { |
| // ID uniquely identifies the request that initiated the event. |
| ID string `json:"id"` |
| |
| // Addr contains the ip or hostname and possibly port of the client |
| // connection that initiated the event. This is the RemoteAddr from |
| // the standard http request. |
| Addr string `json:"addr,omitempty"` |
| |
| // Host is the externally accessible host name of the registry instance, |
| // as specified by the http host header on incoming requests. |
| Host string `json:"host,omitempty"` |
| |
| // Method has the request method that generated the event. |
| Method string `json:"method"` |
| |
| // UserAgent contains the user agent header of the request. |
| UserAgent string `json:"useragent"` |
| } |
| |
| // SourceRecord identifies the registry node that generated the event. Put |
| // differently, while the actor "initiates" the event, the source "generates" |
| // it. |
| type SourceRecord struct { |
| // Addr contains the ip or hostname and the port of the registry node |
| // that generated the event. Generally, this will be resolved by |
| // os.Hostname() along with the running port. |
| Addr string `json:"addr,omitempty"` |
| |
| // InstanceID identifies a running instance of an application. Changes |
| // after each restart. |
| InstanceID string `json:"instanceID,omitempty"` |
| } |
| |
| var ( |
| // ErrSinkClosed is returned if a write is issued to a sink that has been |
| // closed. If encountered, the error should be considered terminal and |
| // retries will not be successful. |
| ErrSinkClosed = fmt.Errorf("sink: closed") |
| ) |
| |
| // Sink accepts and sends events. |
| type Sink interface { |
| // Write writes one or more events to the sink. If no error is returned, |
| // the caller will assume that all events have been committed and will not |
| // try to send them again. If an error is received, the caller may retry |
| // sending the event. The caller should cede the slice of memory to the |
| // sink and not modify it after calling this method. |
| Write(events ...Event) error |
| |
| // Close the sink, possibly waiting for pending events to flush. |
| Close() error |
| } |