~ubuntu-branches/ubuntu/saucy/juju-core/saucy

« back to all changes in this revision

Viewing changes to src/launchpad.net/juju-core/state/apiserver/common/watch.go

  • Committer: Package Import Robot
  • Author(s): James Page
  • Date: 2013-08-20 16:02:16 UTC
  • mfrom: (1.1.5)
  • Revision ID: package-import@ubuntu.com-20130820160216-5yu1llasa2e2youn
Tags: 1.13.1-0ubuntu1
* New upstream release.
  - Build and install juju metadata plugin.
  - d/NEWS: Add some guidance on upgrading environments from 1.11.x
    to 1.13.x.
* d/NEWS: Add details about lack of upgrade path from juju < 1.11
  and how to interact with older juju environments.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
// Copyright 2013 Canonical Ltd.
 
2
// Licensed under the AGPLv3, see LICENCE file for details.
 
3
 
 
4
package common
 
5
 
 
6
import (
 
7
        "launchpad.net/juju-core/state"
 
8
        "launchpad.net/juju-core/state/api/params"
 
9
        "launchpad.net/juju-core/state/watcher"
 
10
)
 
11
 
 
12
// AgentEntityWatcher implements a common Watch method for use by
 
13
// various facades.
 
14
type AgentEntityWatcher struct {
 
15
        st          state.EntityFinder
 
16
        resources   *Resources
 
17
        getCanWatch GetAuthFunc
 
18
}
 
19
 
 
20
// NewAgentEntityWatcher returns a new AgentEntityWatcher. The
 
21
// GetAuthFunc will be used on each invocation of Watch to determine
 
22
// current permissions.
 
23
func NewAgentEntityWatcher(st state.EntityFinder, resources *Resources, getCanWatch GetAuthFunc) *AgentEntityWatcher {
 
24
        return &AgentEntityWatcher{
 
25
                st:          st,
 
26
                resources:   resources,
 
27
                getCanWatch: getCanWatch,
 
28
        }
 
29
}
 
30
 
 
31
func (a *AgentEntityWatcher) watchEntity(tag string) (string, error) {
 
32
        entity0, err := a.st.FindEntity(tag)
 
33
        if err != nil {
 
34
                return "", err
 
35
        }
 
36
        entity, ok := entity0.(state.NotifyWatcherFactory)
 
37
        if !ok {
 
38
                return "", NotSupportedError(tag, "watching")
 
39
        }
 
40
        watch := entity.Watch()
 
41
        // Consume the initial event. Technically, API
 
42
        // calls to Watch 'transmit' the initial event
 
43
        // in the Watch response. But NotifyWatchers
 
44
        // have no state to transmit.
 
45
        if _, ok := <-watch.Changes(); ok {
 
46
                return a.resources.Register(watch), nil
 
47
        }
 
48
        return "", watcher.MustErr(watch)
 
49
}
 
50
 
 
51
// Watch starts an NotifyWatcher for each given entity.
 
52
func (a *AgentEntityWatcher) Watch(args params.Entities) (params.NotifyWatchResults, error) {
 
53
        result := params.NotifyWatchResults{
 
54
                Results: make([]params.NotifyWatchResult, len(args.Entities)),
 
55
        }
 
56
        if len(args.Entities) == 0 {
 
57
                return result, nil
 
58
        }
 
59
        canWatch, err := a.getCanWatch()
 
60
        if err != nil {
 
61
                return params.NotifyWatchResults{}, err
 
62
        }
 
63
        for i, entity := range args.Entities {
 
64
                err := ErrPerm
 
65
                watcherId := ""
 
66
                if canWatch(entity.Tag) {
 
67
                        watcherId, err = a.watchEntity(entity.Tag)
 
68
                }
 
69
                result.Results[i].NotifyWatcherId = watcherId
 
70
                result.Results[i].Error = ServerError(err)
 
71
        }
 
72
        return result, nil
 
73
}