~wallyworld/juju-core/1304742-backport-1.18

« back to all changes in this revision

Viewing changes to state/util.go

  • Committer: Roger Peppe
  • Date: 2012-09-19 13:40:41 UTC
  • mto: This revision was merged to the branch mainline in revision 527.
  • Revision ID: roger.peppe@canonical.com-20120919134041-1rt4cg7ox52pt4os
mstate: rename to state

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
package state
2
 
 
3
 
import (
4
 
        "errors"
5
 
        "launchpad.net/gozk/zookeeper"
6
 
        "launchpad.net/juju-core/trivial"
7
 
        pathpkg "path"
8
 
        "sort"
9
 
)
10
 
 
11
 
var (
12
 
        // stateChanged is a common error inside the state processing.
13
 
        stateChanged = errors.New("environment state has changed")
14
 
        // zkPermAll is a convenience variable for creating new nodes.
15
 
        zkPermAll = zookeeper.WorldACL(zookeeper.PERM_ALL)
16
 
)
17
 
 
18
 
// zkRemoveTree recursively removes a zookeeper node and all its
19
 
// children.  It does not delete "/zookeeper" or the root node itself
20
 
// and it does not consider deleting a nonexistent node to be an error.
21
 
func zkRemoveTree(zk *zookeeper.Conn, path string) (err error) {
22
 
        defer trivial.ErrorContextf(&err, "cannot clean up data")
23
 
        // If we try to delete the zookeeper node (for example when
24
 
        // calling ZkRemoveTree(zk, "/")) we silently ignore it.
25
 
        if path == "/zookeeper" {
26
 
                return
27
 
        }
28
 
        // First recursively delete the children.
29
 
        children, _, err := zk.Children(path)
30
 
        if err != nil {
31
 
                if zookeeper.IsError(err, zookeeper.ZNONODE) {
32
 
                        return nil
33
 
                }
34
 
                return
35
 
        }
36
 
        for _, child := range children {
37
 
                if err = zkRemoveTree(zk, pathpkg.Join(path, child)); err != nil {
38
 
                        return
39
 
                }
40
 
        }
41
 
        // Now delete the path itself unless it's the root node.
42
 
        if path == "/" {
43
 
                return nil
44
 
        }
45
 
        err = zk.Delete(path, -1)
46
 
        if err != nil && !zookeeper.IsError(err, zookeeper.ZNONODE) {
47
 
                return err
48
 
        }
49
 
        return nil
50
 
}
51
 
 
52
 
// diff returns all the elements that exist in A but not B.
53
 
func diff(A, B []string) (missing []string) {
54
 
next:
55
 
        for _, a := range A {
56
 
                for _, b := range B {
57
 
                        if a == b {
58
 
                                continue next
59
 
                        }
60
 
                }
61
 
                missing = append(missing, a)
62
 
        }
63
 
        return
64
 
}
65
 
 
66
 
type portSlice []Port
67
 
 
68
 
func (p portSlice) Len() int      { return len(p) }
69
 
func (p portSlice) Swap(i, j int) { p[i], p[j] = p[j], p[i] }
70
 
func (p portSlice) Less(i, j int) bool {
71
 
        p1 := p[i]
72
 
        p2 := p[j]
73
 
        if p1.Protocol != p2.Protocol {
74
 
                return p1.Protocol < p2.Protocol
75
 
        }
76
 
        return p1.Number < p2.Number
77
 
}
78
 
 
79
 
// SortPorts sorts the given ports, first by protocol,
80
 
// then by number.
81
 
func SortPorts(ports []Port) {
82
 
        sort.Sort(portSlice(ports))
83
 
}