Browse code

pluggable secret backend

This commit extends SwarmKit secret management with pluggable secret
backends support.

Updating the work in
[swarmkit](docker/swarmkit@eebac27434d34708fac993f9f5181d106c5c2fae) for
pluggable secret backend and adding the
driver parameter to `SecretSpec`.

Remaining work:
- [ ] CLI support (docker/cli)
- [ ] api in [plugin helpers](docker/go-plugins-helpers))
- [ ] Reference plugin
- [ ] Documenation (after cli work)

Signed-off-by: Liron Levin <liron@twistlock.com>

Liron Levin authored on 2017/07/15 22:03:17
Showing 14 changed files
... ...
@@ -12,7 +12,8 @@ type Secret struct {
12 12
 // SecretSpec represents a secret specification from a secret in swarm
13 13
 type SecretSpec struct {
14 14
 	Annotations
15
-	Data []byte `json:",omitempty"`
15
+	Data   []byte  `json:",omitempty"`
16
+	Driver *Driver `json:"omitempty"` // name of the secrets driver used to fetch the secret's value from an external secret store
16 17
 }
17 18
 
18 19
 // SecretReferenceFileTarget is a file target in a secret reference
... ...
@@ -13,6 +13,7 @@ func SecretFromGRPC(s *swarmapi.Secret) swarmtypes.Secret {
13 13
 		Spec: swarmtypes.SecretSpec{
14 14
 			Annotations: annotationsFromGRPC(s.Spec.Annotations),
15 15
 			Data:        s.Spec.Data,
16
+			Driver:      driverFromGRPC(s.Spec.Driver),
16 17
 		},
17 18
 	}
18 19
 
... ...
@@ -31,7 +32,8 @@ func SecretSpecToGRPC(s swarmtypes.SecretSpec) swarmapi.SecretSpec {
31 31
 			Name:   s.Name,
32 32
 			Labels: s.Labels,
33 33
 		},
34
-		Data: s.Data,
34
+		Data:   s.Data,
35
+		Driver: driverToGRPC(s.Driver),
35 36
 	}
36 37
 }
37 38
 
... ...
@@ -106,7 +106,7 @@ github.com/stevvooe/continuity cd7a8e21e2b6f84799f5dd4b65faf49c8d3ee02d
106 106
 github.com/tonistiigi/fsutil 0ac4c11b053b9c5c7c47558f81f96c7100ce50fb
107 107
 
108 108
 # cluster
109
-github.com/docker/swarmkit a3d96fe13e30e46c3d4cfc3f316ebdd8446a079d
109
+github.com/docker/swarmkit 3e2dd3c0a76149b1620b42d28dd6ff48270404e5
110 110
 github.com/gogo/protobuf v0.4
111 111
 github.com/cloudflare/cfssl 7fb22c8cba7ecaf98e4082d22d65800cf45e042a
112 112
 github.com/google/certificate-transparency d90e65c3a07988180c5b1ece71791c0b6506826e
... ...
@@ -766,6 +766,8 @@ type SecretSpec struct {
766 766
 	// The currently recognized values are:
767 767
 	// - golang: Go templating
768 768
 	Templating *Driver `protobuf:"bytes,3,opt,name=templating" json:"templating,omitempty"`
769
+	// Driver is the the secret driver that is used to store the specified secret
770
+	Driver *Driver `protobuf:"bytes,4,opt,name=driver" json:"driver,omitempty"`
769 771
 }
770 772
 
771 773
 func (m *SecretSpec) Reset()                    { *m = SecretSpec{} }
... ...
@@ -1240,6 +1242,10 @@ func (m *SecretSpec) CopyFrom(src interface{}) {
1240 1240
 		m.Templating = &Driver{}
1241 1241
 		github_com_docker_swarmkit_api_deepcopy.Copy(m.Templating, o.Templating)
1242 1242
 	}
1243
+	if o.Driver != nil {
1244
+		m.Driver = &Driver{}
1245
+		github_com_docker_swarmkit_api_deepcopy.Copy(m.Driver, o.Driver)
1246
+	}
1243 1247
 }
1244 1248
 
1245 1249
 func (m *ConfigSpec) Copy() *ConfigSpec {
... ...
@@ -2257,6 +2263,16 @@ func (m *SecretSpec) MarshalTo(dAtA []byte) (int, error) {
2257 2257
 		}
2258 2258
 		i += n37
2259 2259
 	}
2260
+	if m.Driver != nil {
2261
+		dAtA[i] = 0x22
2262
+		i++
2263
+		i = encodeVarintSpecs(dAtA, i, uint64(m.Driver.Size()))
2264
+		n38, err := m.Driver.MarshalTo(dAtA[i:])
2265
+		if err != nil {
2266
+			return 0, err
2267
+		}
2268
+		i += n38
2269
+	}
2260 2270
 	return i, nil
2261 2271
 }
2262 2272
 
... ...
@@ -2278,11 +2294,11 @@ func (m *ConfigSpec) MarshalTo(dAtA []byte) (int, error) {
2278 2278
 	dAtA[i] = 0xa
2279 2279
 	i++
2280 2280
 	i = encodeVarintSpecs(dAtA, i, uint64(m.Annotations.Size()))
2281
-	n38, err := m.Annotations.MarshalTo(dAtA[i:])
2281
+	n39, err := m.Annotations.MarshalTo(dAtA[i:])
2282 2282
 	if err != nil {
2283 2283
 		return 0, err
2284 2284
 	}
2285
-	i += n38
2285
+	i += n39
2286 2286
 	if len(m.Data) > 0 {
2287 2287
 		dAtA[i] = 0x12
2288 2288
 		i++
... ...
@@ -2293,11 +2309,11 @@ func (m *ConfigSpec) MarshalTo(dAtA []byte) (int, error) {
2293 2293
 		dAtA[i] = 0x1a
2294 2294
 		i++
2295 2295
 		i = encodeVarintSpecs(dAtA, i, uint64(m.Templating.Size()))
2296
-		n39, err := m.Templating.MarshalTo(dAtA[i:])
2296
+		n40, err := m.Templating.MarshalTo(dAtA[i:])
2297 2297
 		if err != nil {
2298 2298
 			return 0, err
2299 2299
 		}
2300
-		i += n39
2300
+		i += n40
2301 2301
 	}
2302 2302
 	return i, nil
2303 2303
 }
... ...
@@ -2729,6 +2745,10 @@ func (m *SecretSpec) Size() (n int) {
2729 2729
 		l = m.Templating.Size()
2730 2730
 		n += 1 + l + sovSpecs(uint64(l))
2731 2731
 	}
2732
+	if m.Driver != nil {
2733
+		l = m.Driver.Size()
2734
+		n += 1 + l + sovSpecs(uint64(l))
2735
+	}
2732 2736
 	return n
2733 2737
 }
2734 2738
 
... ...
@@ -3022,6 +3042,7 @@ func (this *SecretSpec) String() string {
3022 3022
 		`Annotations:` + strings.Replace(strings.Replace(this.Annotations.String(), "Annotations", "Annotations", 1), `&`, ``, 1) + `,`,
3023 3023
 		`Data:` + fmt.Sprintf("%v", this.Data) + `,`,
3024 3024
 		`Templating:` + strings.Replace(fmt.Sprintf("%v", this.Templating), "Driver", "Driver", 1) + `,`,
3025
+		`Driver:` + strings.Replace(fmt.Sprintf("%v", this.Driver), "Driver", "Driver", 1) + `,`,
3025 3026
 		`}`,
3026 3027
 	}, "")
3027 3028
 	return s
... ...
@@ -5883,6 +5904,39 @@ func (m *SecretSpec) Unmarshal(dAtA []byte) error {
5883 5883
 				return err
5884 5884
 			}
5885 5885
 			iNdEx = postIndex
5886
+		case 4:
5887
+			if wireType != 2 {
5888
+				return fmt.Errorf("proto: wrong wireType = %d for field Driver", wireType)
5889
+			}
5890
+			var msglen int
5891
+			for shift := uint(0); ; shift += 7 {
5892
+				if shift >= 64 {
5893
+					return ErrIntOverflowSpecs
5894
+				}
5895
+				if iNdEx >= l {
5896
+					return io.ErrUnexpectedEOF
5897
+				}
5898
+				b := dAtA[iNdEx]
5899
+				iNdEx++
5900
+				msglen |= (int(b) & 0x7F) << shift
5901
+				if b < 0x80 {
5902
+					break
5903
+				}
5904
+			}
5905
+			if msglen < 0 {
5906
+				return ErrInvalidLengthSpecs
5907
+			}
5908
+			postIndex := iNdEx + msglen
5909
+			if postIndex > l {
5910
+				return io.ErrUnexpectedEOF
5911
+			}
5912
+			if m.Driver == nil {
5913
+				m.Driver = &Driver{}
5914
+			}
5915
+			if err := m.Driver.Unmarshal(dAtA[iNdEx:postIndex]); err != nil {
5916
+				return err
5917
+			}
5918
+			iNdEx = postIndex
5886 5919
 		default:
5887 5920
 			iNdEx = preIndex
5888 5921
 			skippy, err := skipSpecs(dAtA[iNdEx:])
... ...
@@ -6156,122 +6210,123 @@ var (
6156 6156
 func init() { proto.RegisterFile("specs.proto", fileDescriptorSpecs) }
6157 6157
 
6158 6158
 var fileDescriptorSpecs = []byte{
6159
-	// 1867 bytes of a gzipped FileDescriptorProto
6159
+	// 1880 bytes of a gzipped FileDescriptorProto
6160 6160
 	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xcc, 0x57, 0xcf, 0x73, 0x1b, 0x49,
6161
-	0x15, 0xb6, 0x6c, 0x59, 0x3f, 0xde, 0xc8, 0x89, 0xd2, 0x24, 0x61, 0xa2, 0xb0, 0xb2, 0xa2, 0x0d,
6161
+	0x15, 0xb6, 0x6c, 0x59, 0x3f, 0xde, 0xc8, 0x89, 0xdc, 0x24, 0x61, 0xac, 0xb0, 0xb2, 0xa2, 0x0d,
6162 6162
 	0xc1, 0xcb, 0x16, 0x72, 0x61, 0xa8, 0x25, 0xbb, 0x61, 0x01, 0xc9, 0x12, 0x8e, 0x31, 0x76, 0x54,
6163
-	0x6d, 0x6f, 0x20, 0x27, 0x55, 0x7b, 0xa6, 0x3d, 0x9a, 0xf2, 0xa8, 0x7b, 0xe8, 0xe9, 0xd1, 0x96,
6164
-	0x6e, 0x1c, 0xb7, 0x72, 0xe5, 0xec, 0xe2, 0x40, 0xf1, 0xbf, 0xe4, 0x48, 0x71, 0xe2, 0xe4, 0x62,
6165
-	0xfd, 0x2f, 0x70, 0xe3, 0x02, 0xd5, 0x3d, 0x3d, 0xd2, 0x28, 0x19, 0x27, 0xa9, 0x22, 0x07, 0x6e,
6166
-	0xdd, 0xaf, 0xbf, 0xef, 0xcd, 0xeb, 0xd7, 0x5f, 0xf7, 0x7b, 0x03, 0x56, 0x14, 0x52, 0x27, 0xea,
6167
-	0x84, 0x82, 0x4b, 0x8e, 0x90, 0xcb, 0x9d, 0x73, 0x2a, 0x3a, 0xd1, 0xd7, 0x44, 0x4c, 0xce, 0x7d,
6168
-	0xd9, 0x99, 0xfe, 0xb8, 0x61, 0xc9, 0x59, 0x48, 0x0d, 0xa0, 0x71, 0xdb, 0xe3, 0x1e, 0xd7, 0xc3,
6169
-	0x6d, 0x35, 0x32, 0xd6, 0xa6, 0xc7, 0xb9, 0x17, 0xd0, 0x6d, 0x3d, 0x3b, 0x8d, 0xcf, 0xb6, 0xdd,
6170
-	0x58, 0x10, 0xe9, 0x73, 0x66, 0xd6, 0xef, 0xbd, 0xbe, 0x4e, 0xd8, 0x2c, 0x59, 0x6a, 0x5f, 0x14,
6171
-	0xa1, 0x72, 0xc4, 0x5d, 0x7a, 0x1c, 0x52, 0x07, 0xed, 0x81, 0x45, 0x18, 0xe3, 0x52, 0x73, 0x23,
6172
-	0xbb, 0xd0, 0x2a, 0x6c, 0x59, 0x3b, 0x9b, 0x9d, 0x37, 0x83, 0xea, 0x74, 0x17, 0xb0, 0x5e, 0xf1,
6173
-	0xd5, 0xe5, 0xe6, 0x0a, 0xce, 0x32, 0xd1, 0x2f, 0xa1, 0xe6, 0xd2, 0xc8, 0x17, 0xd4, 0x1d, 0x09,
6174
-	0x1e, 0x50, 0x7b, 0xb5, 0x55, 0xd8, 0xba, 0xb1, 0xf3, 0xbd, 0x3c, 0x4f, 0xea, 0xe3, 0x98, 0x07,
6175
-	0x14, 0x5b, 0x86, 0xa1, 0x26, 0x68, 0x0f, 0x60, 0x42, 0x27, 0xa7, 0x54, 0x44, 0x63, 0x3f, 0xb4,
6176
-	0xd7, 0x34, 0xfd, 0x07, 0xd7, 0xd1, 0x55, 0xec, 0x9d, 0xc3, 0x39, 0x1c, 0x67, 0xa8, 0xe8, 0x10,
6177
-	0x6a, 0x64, 0x4a, 0xfc, 0x80, 0x9c, 0xfa, 0x81, 0x2f, 0x67, 0x76, 0x51, 0xbb, 0xfa, 0xe4, 0xad,
6178
-	0xae, 0xba, 0x19, 0x02, 0x5e, 0xa2, 0xb7, 0x5d, 0x80, 0xc5, 0x87, 0xd0, 0x23, 0x28, 0x0f, 0x07,
6179
-	0x47, 0xfd, 0xfd, 0xa3, 0xbd, 0xfa, 0x4a, 0xe3, 0xde, 0xcb, 0x8b, 0xd6, 0x1d, 0xe5, 0x63, 0x01,
6180
-	0x18, 0x52, 0xe6, 0xfa, 0xcc, 0x43, 0x5b, 0x50, 0xe9, 0xee, 0xee, 0x0e, 0x86, 0x27, 0x83, 0x7e,
6181
-	0xbd, 0xd0, 0x68, 0xbc, 0xbc, 0x68, 0xdd, 0x5d, 0x06, 0x76, 0x1d, 0x87, 0x86, 0x92, 0xba, 0x8d,
6182
-	0xe2, 0x37, 0x7f, 0x69, 0xae, 0xb4, 0xbf, 0x29, 0x40, 0x2d, 0x1b, 0x04, 0x7a, 0x04, 0xa5, 0xee,
6183
-	0xee, 0xc9, 0xfe, 0xf3, 0x41, 0x7d, 0x65, 0x41, 0xcf, 0x22, 0xba, 0x8e, 0xf4, 0xa7, 0x14, 0x3d,
6184
-	0x84, 0xf5, 0x61, 0xf7, 0xab, 0xe3, 0x41, 0xbd, 0xb0, 0x08, 0x27, 0x0b, 0x1b, 0x92, 0x38, 0xd2,
6185
-	0xa8, 0x3e, 0xee, 0xee, 0x1f, 0xd5, 0x57, 0xf3, 0x51, 0x7d, 0x41, 0x7c, 0x66, 0x42, 0xf9, 0x73,
6186
-	0x11, 0xac, 0x63, 0x2a, 0xa6, 0xbe, 0xf3, 0x81, 0x25, 0xf2, 0x19, 0x14, 0x25, 0x89, 0xce, 0xb5,
6187
-	0x34, 0xac, 0x7c, 0x69, 0x9c, 0x90, 0xe8, 0x5c, 0x7d, 0xd4, 0xd0, 0x35, 0x5e, 0x29, 0x43, 0xd0,
6188
-	0x30, 0xf0, 0x1d, 0x22, 0xa9, 0xab, 0x95, 0x61, 0xed, 0x7c, 0x3f, 0x8f, 0x8d, 0xe7, 0x28, 0x13,
6189
-	0xff, 0xd3, 0x15, 0x9c, 0xa1, 0xa2, 0x27, 0x50, 0xf2, 0x02, 0x7e, 0x4a, 0x02, 0xad, 0x09, 0x6b,
6190
-	0xe7, 0x41, 0x9e, 0x93, 0x3d, 0x8d, 0x58, 0x38, 0x30, 0x14, 0xf4, 0x18, 0x4a, 0x71, 0xe8, 0x12,
6191
-	0x49, 0xed, 0x92, 0x26, 0xb7, 0xf2, 0xc8, 0x5f, 0x69, 0xc4, 0x2e, 0x67, 0x67, 0xbe, 0x87, 0x0d,
6192
-	0x1e, 0x1d, 0x40, 0x85, 0x51, 0xf9, 0x35, 0x17, 0xe7, 0x91, 0x5d, 0x6e, 0xad, 0x6d, 0x59, 0x3b,
6193
-	0x9f, 0xe6, 0x8a, 0x31, 0xc1, 0x74, 0xa5, 0x24, 0xce, 0x78, 0x42, 0x99, 0x4c, 0xdc, 0xf4, 0x56,
6194
-	0xed, 0x02, 0x9e, 0x3b, 0x40, 0x3f, 0x87, 0x0a, 0x65, 0x6e, 0xc8, 0x7d, 0x26, 0xed, 0xca, 0xf5,
6195
-	0x81, 0x0c, 0x0c, 0x46, 0x25, 0x13, 0xcf, 0x19, 0x8a, 0x2d, 0x78, 0x10, 0x9c, 0x12, 0xe7, 0xdc,
6196
-	0xae, 0xbe, 0xe7, 0x36, 0xe6, 0x8c, 0x5e, 0x09, 0x8a, 0x13, 0xee, 0xd2, 0xf6, 0x36, 0xdc, 0x7a,
6197
-	0x23, 0xd5, 0xa8, 0x01, 0x15, 0x93, 0xea, 0x44, 0x23, 0x45, 0x3c, 0x9f, 0xb7, 0x6f, 0xc2, 0xc6,
6198
-	0x52, 0x5a, 0xdb, 0x7f, 0x2f, 0x42, 0x25, 0x3d, 0x6b, 0xd4, 0x85, 0xaa, 0xc3, 0x99, 0x24, 0x3e,
6199
-	0xa3, 0xc2, 0xc8, 0x2b, 0xf7, 0x64, 0x76, 0x53, 0x90, 0x62, 0x3d, 0x5d, 0xc1, 0x0b, 0x16, 0xfa,
6200
-	0x35, 0x54, 0x05, 0x8d, 0x78, 0x2c, 0x1c, 0x1a, 0x19, 0x7d, 0x6d, 0xe5, 0x2b, 0x24, 0x01, 0x61,
6201
-	0xfa, 0x87, 0xd8, 0x17, 0x54, 0x65, 0x39, 0xc2, 0x0b, 0x2a, 0x7a, 0x02, 0x65, 0x41, 0x23, 0x49,
6202
-	0x84, 0x7c, 0x9b, 0x44, 0x70, 0x02, 0x19, 0xf2, 0xc0, 0x77, 0x66, 0x38, 0x65, 0xa0, 0x27, 0x50,
6203
-	0x0d, 0x03, 0xe2, 0x68, 0xaf, 0xf6, 0xba, 0xa6, 0x7f, 0x94, 0x47, 0x1f, 0xa6, 0x20, 0xbc, 0xc0,
6204
-	0xa3, 0xcf, 0x01, 0x02, 0xee, 0x8d, 0x5c, 0xe1, 0x4f, 0xa9, 0x30, 0x12, 0x6b, 0xe4, 0xb1, 0xfb,
6205
-	0x1a, 0x81, 0xab, 0x01, 0xf7, 0x92, 0x21, 0xda, 0xfb, 0x9f, 0xf4, 0x95, 0xd1, 0xd6, 0x01, 0x00,
6206
-	0x99, 0xaf, 0x1a, 0x75, 0x7d, 0xf2, 0x5e, 0xae, 0xcc, 0x89, 0x64, 0xe8, 0xe8, 0x01, 0xd4, 0xce,
6207
-	0xb8, 0x70, 0xe8, 0xc8, 0xdc, 0x9a, 0xaa, 0xd6, 0x84, 0xa5, 0x6d, 0x89, 0xbe, 0x50, 0x0f, 0xca,
6208
-	0x1e, 0x65, 0x54, 0xf8, 0x8e, 0x0d, 0xfa, 0x63, 0x8f, 0x72, 0x2f, 0x64, 0x02, 0xc1, 0x31, 0x93,
6209
-	0xfe, 0x84, 0x9a, 0x2f, 0xa5, 0xc4, 0x5e, 0x15, 0xca, 0x22, 0x59, 0x69, 0xff, 0x1e, 0xd0, 0x9b,
6210
-	0x58, 0x84, 0xa0, 0x78, 0xee, 0x33, 0x57, 0x0b, 0xab, 0x8a, 0xf5, 0x18, 0x75, 0xa0, 0x1c, 0x92,
6211
-	0x59, 0xc0, 0x89, 0x6b, 0xc4, 0x72, 0xbb, 0x93, 0xd4, 0xcb, 0x4e, 0x5a, 0x2f, 0x3b, 0x5d, 0x36,
6212
-	0xc3, 0x29, 0xa8, 0x7d, 0x00, 0x77, 0x72, 0xb7, 0x8c, 0x76, 0xa0, 0x36, 0x17, 0xe1, 0xc8, 0x37,
6213
-	0x1f, 0xe9, 0xdd, 0xbc, 0xba, 0xdc, 0xb4, 0xe6, 0x6a, 0xdd, 0xef, 0x63, 0x6b, 0x0e, 0xda, 0x77,
6214
-	0xdb, 0x7f, 0xaa, 0xc2, 0xc6, 0x92, 0x94, 0xd1, 0x6d, 0x58, 0xf7, 0x27, 0xc4, 0xa3, 0x26, 0xc6,
6215
-	0x64, 0x82, 0x06, 0x50, 0x0a, 0xc8, 0x29, 0x0d, 0x94, 0xa0, 0xd5, 0xa1, 0xfe, 0xe8, 0x9d, 0x77,
6216
-	0xa2, 0xf3, 0x5b, 0x8d, 0x1f, 0x30, 0x29, 0x66, 0xd8, 0x90, 0x91, 0x0d, 0x65, 0x87, 0x4f, 0x26,
6217
-	0x84, 0xa9, 0xa7, 0x73, 0x6d, 0xab, 0x8a, 0xd3, 0xa9, 0xca, 0x0c, 0x11, 0x5e, 0x64, 0x17, 0xb5,
6218
-	0x59, 0x8f, 0x51, 0x1d, 0xd6, 0x28, 0x9b, 0xda, 0xeb, 0xda, 0xa4, 0x86, 0xca, 0xe2, 0xfa, 0x89,
6219
-	0x22, 0xab, 0x58, 0x0d, 0x15, 0x2f, 0x8e, 0xa8, 0xb0, 0xcb, 0x49, 0x46, 0xd5, 0x18, 0xfd, 0x0c,
6220
-	0x4a, 0x13, 0x1e, 0x33, 0x19, 0xd9, 0x15, 0x1d, 0xec, 0xbd, 0xbc, 0x60, 0x0f, 0x15, 0xc2, 0x3c,
6221
-	0xed, 0x06, 0x8e, 0x06, 0x70, 0x2b, 0x92, 0x3c, 0x1c, 0x79, 0x82, 0x38, 0x74, 0x14, 0x52, 0xe1,
6222
-	0x73, 0xd7, 0x3c, 0x4d, 0xf7, 0xde, 0x38, 0x94, 0xbe, 0x69, 0x72, 0xf0, 0x4d, 0xc5, 0xd9, 0x53,
6223
-	0x94, 0xa1, 0x66, 0xa0, 0x21, 0xd4, 0xc2, 0x38, 0x08, 0x46, 0x3c, 0x4c, 0xaa, 0x54, 0xa2, 0xa7,
6224
-	0xf7, 0x48, 0xd9, 0x30, 0x0e, 0x82, 0x67, 0x09, 0x09, 0x5b, 0xe1, 0x62, 0x82, 0xee, 0x42, 0xc9,
6225
-	0x13, 0x3c, 0x0e, 0x23, 0xdb, 0xd2, 0xc9, 0x30, 0x33, 0xf4, 0x25, 0x94, 0x23, 0xea, 0x08, 0x2a,
6226
-	0x23, 0xbb, 0xa6, 0xb7, 0xfa, 0x71, 0xde, 0x47, 0x8e, 0x35, 0x04, 0xd3, 0x33, 0x2a, 0x28, 0x73,
6227
-	0x28, 0x4e, 0x39, 0xe8, 0x1e, 0xac, 0x49, 0x39, 0xb3, 0x37, 0x5a, 0x85, 0xad, 0x4a, 0xaf, 0x7c,
6228
-	0x75, 0xb9, 0xb9, 0x76, 0x72, 0xf2, 0x02, 0x2b, 0x9b, 0x7a, 0x41, 0xc7, 0x3c, 0x92, 0x8c, 0x4c,
6229
-	0xa8, 0x7d, 0x43, 0xe7, 0x76, 0x3e, 0x47, 0x2f, 0x00, 0x5c, 0x16, 0x8d, 0x1c, 0x7d, 0x65, 0xed,
6230
-	0x9b, 0x7a, 0x77, 0x9f, 0xbe, 0x7b, 0x77, 0xfd, 0xa3, 0x63, 0x53, 0x45, 0x36, 0xae, 0x2e, 0x37,
6231
-	0xab, 0xf3, 0x29, 0xae, 0xba, 0x2c, 0x4a, 0x86, 0xa8, 0x07, 0xd6, 0x98, 0x92, 0x40, 0x8e, 0x9d,
6232
-	0x31, 0x75, 0xce, 0xed, 0xfa, 0xf5, 0x65, 0xe1, 0xa9, 0x86, 0x19, 0x0f, 0x59, 0x92, 0x52, 0xb0,
6233
-	0x0a, 0x35, 0xb2, 0x6f, 0xe9, 0x5c, 0x25, 0x13, 0xf4, 0x11, 0x00, 0x0f, 0x29, 0x1b, 0x45, 0xd2,
6234
-	0xf5, 0x99, 0x8d, 0xd4, 0x96, 0x71, 0x55, 0x59, 0x8e, 0x95, 0x01, 0xdd, 0x57, 0x8f, 0x36, 0x71,
6235
-	0x47, 0x9c, 0x05, 0x33, 0xfb, 0x3b, 0x7a, 0xb5, 0xa2, 0x0c, 0xcf, 0x58, 0x30, 0x43, 0x9b, 0x60,
6236
-	0x69, 0x5d, 0x44, 0xbe, 0xc7, 0x48, 0x60, 0xdf, 0xd6, 0xf9, 0x00, 0x65, 0x3a, 0xd6, 0x16, 0x75,
6237
-	0x0e, 0x49, 0x36, 0x22, 0xfb, 0xce, 0xf5, 0xe7, 0x60, 0x82, 0x5d, 0x9c, 0x83, 0xe1, 0xa0, 0x5f,
6238
-	0x00, 0x84, 0xc2, 0x9f, 0xfa, 0x01, 0xf5, 0x68, 0x64, 0xdf, 0xd5, 0x9b, 0x6e, 0xe6, 0xbe, 0xd6,
6239
-	0x73, 0x14, 0xce, 0x30, 0x1a, 0x9f, 0x83, 0x95, 0xb9, 0x6d, 0xea, 0x96, 0x9c, 0xd3, 0x99, 0xb9,
6240
-	0xc0, 0x6a, 0xa8, 0x52, 0x32, 0x25, 0x41, 0x9c, 0x74, 0xc2, 0x55, 0x9c, 0x4c, 0xbe, 0x58, 0x7d,
6241
-	0x5c, 0x68, 0xec, 0x80, 0x95, 0x51, 0x1d, 0xfa, 0x18, 0x36, 0x04, 0xf5, 0xfc, 0x48, 0x8a, 0xd9,
6242
-	0x88, 0xc4, 0x72, 0x6c, 0xff, 0x4a, 0x13, 0x6a, 0xa9, 0xb1, 0x1b, 0xcb, 0x71, 0x63, 0x04, 0x8b,
6243
-	0xc3, 0x43, 0x2d, 0xb0, 0x94, 0x28, 0x22, 0x2a, 0xa6, 0x54, 0xa8, 0x6a, 0xab, 0x72, 0x9e, 0x35,
6244
-	0x29, 0xf1, 0x46, 0x94, 0x08, 0x67, 0xac, 0xdf, 0x8e, 0x2a, 0x36, 0x33, 0xf5, 0x18, 0xa4, 0x37,
6245
-	0xc4, 0x3c, 0x06, 0x66, 0xda, 0xfe, 0x57, 0x01, 0x6a, 0xd9, 0xa6, 0x01, 0xed, 0x26, 0xc5, 0x5e,
6246
-	0x6f, 0xe9, 0xc6, 0xce, 0xf6, 0xbb, 0x9a, 0x0c, 0x5d, 0x5a, 0x83, 0x58, 0x39, 0x3b, 0x54, 0xfd,
6247
-	0xbd, 0x26, 0xa3, 0x9f, 0xc2, 0x7a, 0xc8, 0x85, 0x4c, 0x9f, 0xb0, 0xfc, 0x04, 0x73, 0x91, 0x96,
6248
-	0xa2, 0x04, 0xdc, 0x1e, 0xc3, 0x8d, 0x65, 0x6f, 0xe8, 0x21, 0xac, 0x3d, 0xdf, 0x1f, 0xd6, 0x57,
6249
-	0x1a, 0xf7, 0x5f, 0x5e, 0xb4, 0xbe, 0xbb, 0xbc, 0xf8, 0xdc, 0x17, 0x32, 0x26, 0xc1, 0xfe, 0x10,
6250
-	0xfd, 0x10, 0xd6, 0xfb, 0x47, 0xc7, 0x18, 0xd7, 0x0b, 0x8d, 0xcd, 0x97, 0x17, 0xad, 0xfb, 0xcb,
6251
-	0x38, 0xb5, 0xc4, 0x63, 0xe6, 0x62, 0x7e, 0x3a, 0xef, 0x75, 0xff, 0xbd, 0x0a, 0x96, 0x79, 0xd9,
6252
-	0x3f, 0xf4, 0xef, 0xd0, 0x46, 0x52, 0xca, 0xd3, 0x2b, 0xbb, 0xfa, 0xce, 0x8a, 0x5e, 0x4b, 0x08,
6253
-	0xe6, 0x8c, 0x1f, 0x40, 0xcd, 0x0f, 0xa7, 0x9f, 0x8d, 0x28, 0x23, 0xa7, 0x81, 0x69, 0x7b, 0x2b,
6254
-	0xd8, 0x52, 0xb6, 0x41, 0x62, 0x52, 0xef, 0x85, 0xcf, 0x24, 0x15, 0xcc, 0x34, 0xb4, 0x15, 0x3c,
6255
-	0x9f, 0xa3, 0x2f, 0xa1, 0xe8, 0x87, 0x64, 0x62, 0xda, 0x90, 0xdc, 0x1d, 0xec, 0x0f, 0xbb, 0x87,
6256
-	0x46, 0x83, 0xbd, 0xca, 0xd5, 0xe5, 0x66, 0x51, 0x19, 0xb0, 0xa6, 0xa1, 0x66, 0xda, 0x09, 0xa8,
6257
-	0x2f, 0xe9, 0xb7, 0xbf, 0x82, 0x33, 0x16, 0xa5, 0x23, 0x9f, 0x79, 0x82, 0x46, 0x91, 0xae, 0x02,
6258
-	0x15, 0x9c, 0x4e, 0x51, 0x03, 0xca, 0xa6, 0x9f, 0xd0, 0x0d, 0x44, 0x55, 0xd5, 0x6a, 0x63, 0xe8,
6259
-	0x6d, 0x80, 0x95, 0x64, 0x63, 0x74, 0x26, 0xf8, 0xa4, 0xfd, 0x9f, 0x22, 0x58, 0xbb, 0x41, 0x1c,
6260
-	0x49, 0x53, 0x06, 0x3f, 0x58, 0xf2, 0x5f, 0xc0, 0x2d, 0xa2, 0x7f, 0xaf, 0x08, 0x53, 0x35, 0x45,
6261
-	0xb7, 0x69, 0xe6, 0x00, 0x1e, 0xe6, 0xba, 0x9b, 0x83, 0x93, 0x96, 0xae, 0x57, 0x52, 0x3e, 0xed,
6262
-	0x02, 0xae, 0x93, 0xd7, 0x56, 0xd0, 0x31, 0x6c, 0x70, 0xe1, 0x8c, 0x69, 0x24, 0x93, 0x4a, 0x64,
6263
-	0x7e, 0x47, 0x72, 0x7f, 0x54, 0x9f, 0x65, 0x81, 0xe6, 0x19, 0x4e, 0xa2, 0x5d, 0xf6, 0x81, 0x1e,
6264
-	0x43, 0x51, 0x90, 0xb3, 0xb4, 0xe5, 0xcc, 0xbd, 0x24, 0x98, 0x9c, 0xc9, 0x25, 0x17, 0x9a, 0x81,
6265
-	0x7e, 0x03, 0xe0, 0xfa, 0x51, 0x48, 0xa4, 0x33, 0xa6, 0xc2, 0x1c, 0x76, 0xee, 0x16, 0xfb, 0x73,
6266
-	0xd4, 0x92, 0x97, 0x0c, 0x1b, 0x1d, 0x40, 0xd5, 0x21, 0xa9, 0x5c, 0x4b, 0xd7, 0xff, 0xa3, 0xed,
6267
-	0x76, 0x8d, 0x8b, 0xba, 0x72, 0x71, 0x75, 0xb9, 0x59, 0x49, 0x2d, 0xb8, 0xe2, 0x10, 0x23, 0xdf,
6268
-	0x03, 0xd8, 0x50, 0xff, 0x6e, 0x23, 0x97, 0x9e, 0x91, 0x38, 0x90, 0x89, 0x4c, 0xae, 0x29, 0x2b,
6269
-	0xea, 0x47, 0xa0, 0x6f, 0x70, 0x26, 0xae, 0x9a, 0xcc, 0xd8, 0xd0, 0xef, 0xe0, 0x16, 0x65, 0x8e,
6270
-	0x98, 0x69, 0xb1, 0xa6, 0x11, 0x56, 0xae, 0xdf, 0xec, 0x60, 0x0e, 0x5e, 0xda, 0x6c, 0x9d, 0xbe,
6271
-	0x66, 0x6f, 0xff, 0xb5, 0x00, 0x90, 0x54, 0xea, 0x0f, 0x2b, 0x40, 0x04, 0x45, 0x97, 0x48, 0xa2,
6272
-	0x35, 0x57, 0xc3, 0x7a, 0x8c, 0xbe, 0x00, 0x90, 0x74, 0x12, 0x06, 0x44, 0xfa, 0xcc, 0x33, 0xb2,
6273
-	0x79, 0xdb, 0x73, 0x90, 0x41, 0xeb, 0x38, 0x93, 0x90, 0xff, 0xaf, 0xe3, 0xec, 0xd9, 0xaf, 0xbe,
6274
-	0x6d, 0xae, 0xfc, 0xe3, 0xdb, 0xe6, 0xca, 0x1f, 0xaf, 0x9a, 0x85, 0x57, 0x57, 0xcd, 0xc2, 0xdf,
6275
-	0xae, 0x9a, 0x85, 0x7f, 0x5e, 0x35, 0x0b, 0xa7, 0x25, 0xdd, 0xc3, 0xfd, 0xe4, 0xbf, 0x01, 0x00,
6276
-	0x00, 0xff, 0xff, 0x06, 0x93, 0x6e, 0xba, 0xfc, 0x12, 0x00, 0x00,
6163
+	0x6d, 0x6f, 0x20, 0x27, 0x55, 0x7b, 0xa6, 0x2d, 0x4d, 0x79, 0xd4, 0x3d, 0xf4, 0xf4, 0x68, 0x4b,
6164
+	0x37, 0x8e, 0x5b, 0xb9, 0x72, 0x76, 0x71, 0xa0, 0xf8, 0x5f, 0x72, 0xa4, 0x38, 0xc1, 0xc5, 0x45,
6165
+	0xfc, 0x2f, 0x70, 0xe3, 0x02, 0xd5, 0x3d, 0x3d, 0xd2, 0x28, 0x19, 0xc7, 0xa9, 0x22, 0x87, 0xbd,
6166
+	0x75, 0xbf, 0xfe, 0xbe, 0xd7, 0xdd, 0xaf, 0xbf, 0xee, 0xf7, 0x1a, 0xac, 0x30, 0xa0, 0x4e, 0xd8,
6167
+	0x0a, 0x04, 0x97, 0x1c, 0x21, 0x97, 0x3b, 0xe7, 0x54, 0xb4, 0xc2, 0xaf, 0x89, 0x18, 0x9f, 0x7b,
6168
+	0xb2, 0x35, 0xf9, 0x71, 0xcd, 0x92, 0xd3, 0x80, 0x1a, 0x40, 0xed, 0xce, 0x90, 0x0f, 0xb9, 0x6e,
6169
+	0x6e, 0xab, 0x96, 0xb1, 0xd6, 0x87, 0x9c, 0x0f, 0x7d, 0xba, 0xad, 0x7b, 0xa7, 0xd1, 0xd9, 0xb6,
6170
+	0x1b, 0x09, 0x22, 0x3d, 0xce, 0xcc, 0xf8, 0xc6, 0x9b, 0xe3, 0x84, 0x4d, 0xe3, 0xa1, 0xe6, 0x45,
6171
+	0x1e, 0x4a, 0x47, 0xdc, 0xa5, 0xc7, 0x01, 0x75, 0xd0, 0x1e, 0x58, 0x84, 0x31, 0x2e, 0x35, 0x37,
6172
+	0xb4, 0x73, 0x8d, 0xdc, 0x96, 0xb5, 0xb3, 0xd9, 0x7a, 0x7b, 0x51, 0xad, 0xf6, 0x1c, 0xd6, 0xc9,
6173
+	0xbf, 0xba, 0xdc, 0x5c, 0xc2, 0x69, 0x26, 0xfa, 0x25, 0x54, 0x5c, 0x1a, 0x7a, 0x82, 0xba, 0x03,
6174
+	0xc1, 0x7d, 0x6a, 0x2f, 0x37, 0x72, 0x5b, 0xb7, 0x76, 0xbe, 0x97, 0xe5, 0x49, 0x4d, 0x8e, 0xb9,
6175
+	0x4f, 0xb1, 0x65, 0x18, 0xaa, 0x83, 0xf6, 0x00, 0xc6, 0x74, 0x7c, 0x4a, 0x45, 0x38, 0xf2, 0x02,
6176
+	0x7b, 0x45, 0xd3, 0x7f, 0x70, 0x1d, 0x5d, 0xad, 0xbd, 0x75, 0x38, 0x83, 0xe3, 0x14, 0x15, 0x1d,
6177
+	0x42, 0x85, 0x4c, 0x88, 0xe7, 0x93, 0x53, 0xcf, 0xf7, 0xe4, 0xd4, 0xce, 0x6b, 0x57, 0x9f, 0xbc,
6178
+	0xd3, 0x55, 0x3b, 0x45, 0xc0, 0x0b, 0xf4, 0xa6, 0x0b, 0x30, 0x9f, 0x08, 0x3d, 0x82, 0x62, 0xbf,
6179
+	0x77, 0xd4, 0xdd, 0x3f, 0xda, 0xab, 0x2e, 0xd5, 0x36, 0x5e, 0x5e, 0x34, 0xee, 0x2a, 0x1f, 0x73,
6180
+	0x40, 0x9f, 0x32, 0xd7, 0x63, 0x43, 0xb4, 0x05, 0xa5, 0xf6, 0xee, 0x6e, 0xaf, 0x7f, 0xd2, 0xeb,
6181
+	0x56, 0x73, 0xb5, 0xda, 0xcb, 0x8b, 0xc6, 0xbd, 0x45, 0x60, 0xdb, 0x71, 0x68, 0x20, 0xa9, 0x5b,
6182
+	0xcb, 0x7f, 0xf3, 0x97, 0xfa, 0x52, 0xf3, 0x9b, 0x1c, 0x54, 0xd2, 0x8b, 0x40, 0x8f, 0xa0, 0xd0,
6183
+	0xde, 0x3d, 0xd9, 0x7f, 0xde, 0xab, 0x2e, 0xcd, 0xe9, 0x69, 0x44, 0xdb, 0x91, 0xde, 0x84, 0xa2,
6184
+	0x87, 0xb0, 0xda, 0x6f, 0x7f, 0x75, 0xdc, 0xab, 0xe6, 0xe6, 0xcb, 0x49, 0xc3, 0xfa, 0x24, 0x0a,
6185
+	0x35, 0xaa, 0x8b, 0xdb, 0xfb, 0x47, 0xd5, 0xe5, 0x6c, 0x54, 0x57, 0x10, 0x8f, 0x99, 0xa5, 0xfc,
6186
+	0x39, 0x0f, 0xd6, 0x31, 0x15, 0x13, 0xcf, 0xf9, 0xc0, 0x12, 0xf9, 0x0c, 0xf2, 0x92, 0x84, 0xe7,
6187
+	0x5a, 0x1a, 0x56, 0xb6, 0x34, 0x4e, 0x48, 0x78, 0xae, 0x26, 0x35, 0x74, 0x8d, 0x57, 0xca, 0x10,
6188
+	0x34, 0xf0, 0x3d, 0x87, 0x48, 0xea, 0x6a, 0x65, 0x58, 0x3b, 0xdf, 0xcf, 0x62, 0xe3, 0x19, 0xca,
6189
+	0xac, 0xff, 0xe9, 0x12, 0x4e, 0x51, 0xd1, 0x13, 0x28, 0x0c, 0x7d, 0x7e, 0x4a, 0x7c, 0xad, 0x09,
6190
+	0x6b, 0xe7, 0x41, 0x96, 0x93, 0x3d, 0x8d, 0x98, 0x3b, 0x30, 0x14, 0xf4, 0x18, 0x0a, 0x51, 0xe0,
6191
+	0x12, 0x49, 0xed, 0x82, 0x26, 0x37, 0xb2, 0xc8, 0x5f, 0x69, 0xc4, 0x2e, 0x67, 0x67, 0xde, 0x10,
6192
+	0x1b, 0x3c, 0x3a, 0x80, 0x12, 0xa3, 0xf2, 0x6b, 0x2e, 0xce, 0x43, 0xbb, 0xd8, 0x58, 0xd9, 0xb2,
6193
+	0x76, 0x3e, 0xcd, 0x14, 0x63, 0x8c, 0x69, 0x4b, 0x49, 0x9c, 0xd1, 0x98, 0x32, 0x19, 0xbb, 0xe9,
6194
+	0x2c, 0xdb, 0x39, 0x3c, 0x73, 0x80, 0x7e, 0x0e, 0x25, 0xca, 0xdc, 0x80, 0x7b, 0x4c, 0xda, 0xa5,
6195
+	0xeb, 0x17, 0xd2, 0x33, 0x18, 0x15, 0x4c, 0x3c, 0x63, 0x28, 0xb6, 0xe0, 0xbe, 0x7f, 0x4a, 0x9c,
6196
+	0x73, 0xbb, 0xfc, 0x9e, 0xdb, 0x98, 0x31, 0x3a, 0x05, 0xc8, 0x8f, 0xb9, 0x4b, 0x9b, 0xdb, 0xb0,
6197
+	0xfe, 0x56, 0xa8, 0x51, 0x0d, 0x4a, 0x26, 0xd4, 0xb1, 0x46, 0xf2, 0x78, 0xd6, 0x6f, 0xde, 0x86,
6198
+	0xb5, 0x85, 0xb0, 0x36, 0xff, 0x9e, 0x87, 0x52, 0x72, 0xd6, 0xa8, 0x0d, 0x65, 0x87, 0x33, 0x49,
6199
+	0x3c, 0x46, 0x85, 0x91, 0x57, 0xe6, 0xc9, 0xec, 0x26, 0x20, 0xc5, 0x7a, 0xba, 0x84, 0xe7, 0x2c,
6200
+	0xf4, 0x6b, 0x28, 0x0b, 0x1a, 0xf2, 0x48, 0x38, 0x34, 0x34, 0xfa, 0xda, 0xca, 0x56, 0x48, 0x0c,
6201
+	0xc2, 0xf4, 0x0f, 0x91, 0x27, 0xa8, 0x8a, 0x72, 0x88, 0xe7, 0x54, 0xf4, 0x04, 0x8a, 0x82, 0x86,
6202
+	0x92, 0x08, 0xf9, 0x2e, 0x89, 0xe0, 0x18, 0xd2, 0xe7, 0xbe, 0xe7, 0x4c, 0x71, 0xc2, 0x40, 0x4f,
6203
+	0xa0, 0x1c, 0xf8, 0xc4, 0xd1, 0x5e, 0xed, 0x55, 0x4d, 0xff, 0x28, 0x8b, 0xde, 0x4f, 0x40, 0x78,
6204
+	0x8e, 0x47, 0x9f, 0x03, 0xf8, 0x7c, 0x38, 0x70, 0x85, 0x37, 0xa1, 0xc2, 0x48, 0xac, 0x96, 0xc5,
6205
+	0xee, 0x6a, 0x04, 0x2e, 0xfb, 0x7c, 0x18, 0x37, 0xd1, 0xde, 0xff, 0xa5, 0xaf, 0x94, 0xb6, 0x0e,
6206
+	0x00, 0xc8, 0x6c, 0xd4, 0xa8, 0xeb, 0x93, 0xf7, 0x72, 0x65, 0x4e, 0x24, 0x45, 0x47, 0x0f, 0xa0,
6207
+	0x72, 0xc6, 0x85, 0x43, 0x07, 0xe6, 0xd6, 0x94, 0xb5, 0x26, 0x2c, 0x6d, 0x8b, 0xf5, 0x85, 0x3a,
6208
+	0x50, 0x1c, 0x52, 0x46, 0x85, 0xe7, 0xd8, 0xa0, 0x27, 0x7b, 0x94, 0x79, 0x21, 0x63, 0x08, 0x8e,
6209
+	0x98, 0xf4, 0xc6, 0xd4, 0xcc, 0x94, 0x10, 0x3b, 0x65, 0x28, 0x8a, 0x78, 0xa4, 0xf9, 0x7b, 0x40,
6210
+	0x6f, 0x63, 0x11, 0x82, 0xfc, 0xb9, 0xc7, 0x5c, 0x2d, 0xac, 0x32, 0xd6, 0x6d, 0xd4, 0x82, 0x62,
6211
+	0x40, 0xa6, 0x3e, 0x27, 0xae, 0x11, 0xcb, 0x9d, 0x56, 0x9c, 0x2f, 0x5b, 0x49, 0xbe, 0x6c, 0xb5,
6212
+	0xd9, 0x14, 0x27, 0xa0, 0xe6, 0x01, 0xdc, 0xcd, 0xdc, 0x32, 0xda, 0x81, 0xca, 0x4c, 0x84, 0x03,
6213
+	0xcf, 0x4c, 0xd2, 0xb9, 0x7d, 0x75, 0xb9, 0x69, 0xcd, 0xd4, 0xba, 0xdf, 0xc5, 0xd6, 0x0c, 0xb4,
6214
+	0xef, 0x36, 0xff, 0x54, 0x86, 0xb5, 0x05, 0x29, 0xa3, 0x3b, 0xb0, 0xea, 0x8d, 0xc9, 0x90, 0x9a,
6215
+	0x35, 0xc6, 0x1d, 0xd4, 0x83, 0x82, 0x4f, 0x4e, 0xa9, 0xaf, 0x04, 0xad, 0x0e, 0xf5, 0x47, 0x37,
6216
+	0xde, 0x89, 0xd6, 0x6f, 0x35, 0xbe, 0xc7, 0xa4, 0x98, 0x62, 0x43, 0x46, 0x36, 0x14, 0x1d, 0x3e,
6217
+	0x1e, 0x13, 0xa6, 0x9e, 0xce, 0x95, 0xad, 0x32, 0x4e, 0xba, 0x2a, 0x32, 0x44, 0x0c, 0x43, 0x3b,
6218
+	0xaf, 0xcd, 0xba, 0x8d, 0xaa, 0xb0, 0x42, 0xd9, 0xc4, 0x5e, 0xd5, 0x26, 0xd5, 0x54, 0x16, 0xd7,
6219
+	0x8b, 0x15, 0x59, 0xc6, 0xaa, 0xa9, 0x78, 0x51, 0x48, 0x85, 0x5d, 0x8c, 0x23, 0xaa, 0xda, 0xe8,
6220
+	0x67, 0x50, 0x18, 0xf3, 0x88, 0xc9, 0xd0, 0x2e, 0xe9, 0xc5, 0x6e, 0x64, 0x2d, 0xf6, 0x50, 0x21,
6221
+	0xcc, 0xd3, 0x6e, 0xe0, 0xa8, 0x07, 0xeb, 0xa1, 0xe4, 0xc1, 0x60, 0x28, 0x88, 0x43, 0x07, 0x01,
6222
+	0x15, 0x1e, 0x77, 0xcd, 0xd3, 0xb4, 0xf1, 0xd6, 0xa1, 0x74, 0x4d, 0x91, 0x83, 0x6f, 0x2b, 0xce,
6223
+	0x9e, 0xa2, 0xf4, 0x35, 0x03, 0xf5, 0xa1, 0x12, 0x44, 0xbe, 0x3f, 0xe0, 0x41, 0x9c, 0xa5, 0x62,
6224
+	0x3d, 0xbd, 0x47, 0xc8, 0xfa, 0x91, 0xef, 0x3f, 0x8b, 0x49, 0xd8, 0x0a, 0xe6, 0x1d, 0x74, 0x0f,
6225
+	0x0a, 0x43, 0xc1, 0xa3, 0x20, 0xb4, 0x2d, 0x1d, 0x0c, 0xd3, 0x43, 0x5f, 0x42, 0x31, 0xa4, 0x8e,
6226
+	0xa0, 0x32, 0xb4, 0x2b, 0x7a, 0xab, 0x1f, 0x67, 0x4d, 0x72, 0xac, 0x21, 0x98, 0x9e, 0x51, 0x41,
6227
+	0x99, 0x43, 0x71, 0xc2, 0x41, 0x1b, 0xb0, 0x22, 0xe5, 0xd4, 0x5e, 0x6b, 0xe4, 0xb6, 0x4a, 0x9d,
6228
+	0xe2, 0xd5, 0xe5, 0xe6, 0xca, 0xc9, 0xc9, 0x0b, 0xac, 0x6c, 0xea, 0x05, 0x1d, 0xf1, 0x50, 0x32,
6229
+	0x32, 0xa6, 0xf6, 0x2d, 0x1d, 0xdb, 0x59, 0x1f, 0xbd, 0x00, 0x70, 0x59, 0x38, 0x70, 0xf4, 0x95,
6230
+	0xb5, 0x6f, 0xeb, 0xdd, 0x7d, 0x7a, 0xf3, 0xee, 0xba, 0x47, 0xc7, 0x26, 0x8b, 0xac, 0x5d, 0x5d,
6231
+	0x6e, 0x96, 0x67, 0x5d, 0x5c, 0x76, 0x59, 0x18, 0x37, 0x51, 0x07, 0xac, 0x11, 0x25, 0xbe, 0x1c,
6232
+	0x39, 0x23, 0xea, 0x9c, 0xdb, 0xd5, 0xeb, 0xd3, 0xc2, 0x53, 0x0d, 0x33, 0x1e, 0xd2, 0x24, 0xa5,
6233
+	0x60, 0xb5, 0xd4, 0xd0, 0x5e, 0xd7, 0xb1, 0x8a, 0x3b, 0xe8, 0x23, 0x00, 0x1e, 0x50, 0x36, 0x08,
6234
+	0xa5, 0xeb, 0x31, 0x1b, 0xa9, 0x2d, 0xe3, 0xb2, 0xb2, 0x1c, 0x2b, 0x03, 0xba, 0xaf, 0x1e, 0x6d,
6235
+	0xe2, 0x0e, 0x38, 0xf3, 0xa7, 0xf6, 0x77, 0xf4, 0x68, 0x49, 0x19, 0x9e, 0x31, 0x7f, 0x8a, 0x36,
6236
+	0xc1, 0xd2, 0xba, 0x08, 0xbd, 0x21, 0x23, 0xbe, 0x7d, 0x47, 0xc7, 0x03, 0x94, 0xe9, 0x58, 0x5b,
6237
+	0xd4, 0x39, 0xc4, 0xd1, 0x08, 0xed, 0xbb, 0xd7, 0x9f, 0x83, 0x59, 0xec, 0xfc, 0x1c, 0x0c, 0x07,
6238
+	0xfd, 0x02, 0x20, 0x10, 0xde, 0xc4, 0xf3, 0xe9, 0x90, 0x86, 0xf6, 0x3d, 0xbd, 0xe9, 0x7a, 0xe6,
6239
+	0x6b, 0x3d, 0x43, 0xe1, 0x14, 0xa3, 0xf6, 0x39, 0x58, 0xa9, 0xdb, 0xa6, 0x6e, 0xc9, 0x39, 0x9d,
6240
+	0x9a, 0x0b, 0xac, 0x9a, 0x2a, 0x24, 0x13, 0xe2, 0x47, 0x71, 0x25, 0x5c, 0xc6, 0x71, 0xe7, 0x8b,
6241
+	0xe5, 0xc7, 0xb9, 0xda, 0x0e, 0x58, 0x29, 0xd5, 0xa1, 0x8f, 0x61, 0x4d, 0xd0, 0xa1, 0x17, 0x4a,
6242
+	0x31, 0x1d, 0x90, 0x48, 0x8e, 0xec, 0x5f, 0x69, 0x42, 0x25, 0x31, 0xb6, 0x23, 0x39, 0xaa, 0x0d,
6243
+	0x60, 0x7e, 0x78, 0xa8, 0x01, 0x96, 0x12, 0x45, 0x48, 0xc5, 0x84, 0x0a, 0x95, 0x6d, 0x55, 0xcc,
6244
+	0xd3, 0x26, 0x25, 0xde, 0x90, 0x12, 0xe1, 0x8c, 0xf4, 0xdb, 0x51, 0xc6, 0xa6, 0xa7, 0x1e, 0x83,
6245
+	0xe4, 0x86, 0x98, 0xc7, 0xc0, 0x74, 0x9b, 0xff, 0xce, 0x41, 0x25, 0x5d, 0x34, 0xa0, 0xdd, 0x38,
6246
+	0xd9, 0xeb, 0x2d, 0xdd, 0xda, 0xd9, 0xbe, 0xa9, 0xc8, 0xd0, 0xa9, 0xd5, 0x8f, 0x94, 0xb3, 0x43,
6247
+	0x55, 0xdf, 0x6b, 0x32, 0xfa, 0x29, 0xac, 0x06, 0x5c, 0xc8, 0xe4, 0x09, 0xcb, 0x0e, 0x30, 0x17,
6248
+	0x49, 0x2a, 0x8a, 0xc1, 0xcd, 0x11, 0xdc, 0x5a, 0xf4, 0x86, 0x1e, 0xc2, 0xca, 0xf3, 0xfd, 0x7e,
6249
+	0x75, 0xa9, 0x76, 0xff, 0xe5, 0x45, 0xe3, 0xbb, 0x8b, 0x83, 0xcf, 0x3d, 0x21, 0x23, 0xe2, 0xef,
6250
+	0xf7, 0xd1, 0x0f, 0x61, 0xb5, 0x7b, 0x74, 0x8c, 0x71, 0x35, 0x57, 0xdb, 0x7c, 0x79, 0xd1, 0xb8,
6251
+	0xbf, 0x88, 0x53, 0x43, 0x3c, 0x62, 0x2e, 0xe6, 0xa7, 0xb3, 0x5a, 0xf7, 0x3f, 0xcb, 0x60, 0x99,
6252
+	0x97, 0xfd, 0x43, 0x7f, 0x87, 0xd6, 0xe2, 0x54, 0x9e, 0x5c, 0xd9, 0xe5, 0x1b, 0x33, 0x7a, 0x25,
6253
+	0x26, 0x98, 0x33, 0x7e, 0x00, 0x15, 0x2f, 0x98, 0x7c, 0x36, 0xa0, 0x8c, 0x9c, 0xfa, 0xa6, 0xec,
6254
+	0x2d, 0x61, 0x4b, 0xd9, 0x7a, 0xb1, 0x49, 0xbd, 0x17, 0x1e, 0x93, 0x54, 0x30, 0x53, 0xd0, 0x96,
6255
+	0xf0, 0xac, 0x8f, 0xbe, 0x84, 0xbc, 0x17, 0x90, 0xb1, 0x29, 0x43, 0x32, 0x77, 0xb0, 0xdf, 0x6f,
6256
+	0x1f, 0x1a, 0x0d, 0x76, 0x4a, 0x57, 0x97, 0x9b, 0x79, 0x65, 0xc0, 0x9a, 0x86, 0xea, 0x49, 0x25,
6257
+	0xa0, 0x66, 0xd2, 0x6f, 0x7f, 0x09, 0xa7, 0x2c, 0x4a, 0x47, 0x1e, 0x1b, 0x0a, 0x1a, 0x86, 0x3a,
6258
+	0x0b, 0x94, 0x70, 0xd2, 0x45, 0x35, 0x28, 0x9a, 0x7a, 0x42, 0x17, 0x10, 0x65, 0x95, 0xab, 0x8d,
6259
+	0xa1, 0xb3, 0x06, 0x56, 0x1c, 0x8d, 0xc1, 0x99, 0xe0, 0xe3, 0xe6, 0x7f, 0xf3, 0x60, 0xed, 0xfa,
6260
+	0x51, 0x28, 0x4d, 0x1a, 0xfc, 0x60, 0xc1, 0x7f, 0x01, 0xeb, 0x44, 0x7f, 0xaf, 0x08, 0x53, 0x39,
6261
+	0x45, 0x97, 0x69, 0xe6, 0x00, 0x1e, 0x66, 0xba, 0x9b, 0x81, 0xe3, 0x92, 0xae, 0x53, 0x50, 0x3e,
6262
+	0xed, 0x1c, 0xae, 0x92, 0x37, 0x46, 0xd0, 0x31, 0xac, 0x71, 0xe1, 0x8c, 0x68, 0x28, 0xe3, 0x4c,
6263
+	0x64, 0xbe, 0x23, 0x99, 0x1f, 0xd5, 0x67, 0x69, 0xa0, 0x79, 0x86, 0xe3, 0xd5, 0x2e, 0xfa, 0x40,
6264
+	0x8f, 0x21, 0x2f, 0xc8, 0x59, 0x52, 0x72, 0x66, 0x5e, 0x12, 0x4c, 0xce, 0xe4, 0x82, 0x0b, 0xcd,
6265
+	0x40, 0xbf, 0x01, 0x70, 0xbd, 0x30, 0x20, 0xd2, 0x19, 0x51, 0x61, 0x0e, 0x3b, 0x73, 0x8b, 0xdd,
6266
+	0x19, 0x6a, 0xc1, 0x4b, 0x8a, 0x8d, 0x0e, 0xa0, 0xec, 0x90, 0x44, 0xae, 0x85, 0xeb, 0xff, 0x68,
6267
+	0xbb, 0x6d, 0xe3, 0xa2, 0xaa, 0x5c, 0x5c, 0x5d, 0x6e, 0x96, 0x12, 0x0b, 0x2e, 0x39, 0xc4, 0xc8,
6268
+	0xf7, 0x00, 0xd6, 0xd4, 0xdf, 0x6d, 0xe0, 0xd2, 0x33, 0x12, 0xf9, 0x32, 0x96, 0xc9, 0x35, 0x69,
6269
+	0x45, 0x7d, 0x04, 0xba, 0x06, 0x67, 0xd6, 0x55, 0x91, 0x29, 0x1b, 0xfa, 0x1d, 0xac, 0x53, 0xe6,
6270
+	0x88, 0xa9, 0x16, 0x6b, 0xb2, 0xc2, 0xd2, 0xf5, 0x9b, 0xed, 0xcd, 0xc0, 0x0b, 0x9b, 0xad, 0xd2,
6271
+	0x37, 0xec, 0xcd, 0x7f, 0xe6, 0x00, 0xe2, 0x4c, 0xfd, 0x61, 0x05, 0x88, 0x20, 0xef, 0x12, 0x49,
6272
+	0xb4, 0xe6, 0x2a, 0x58, 0xb7, 0xd1, 0x17, 0x00, 0x92, 0x8e, 0x03, 0x9f, 0x48, 0x8f, 0x0d, 0x8d,
6273
+	0x6c, 0xde, 0xf5, 0x1c, 0xa4, 0xd0, 0x68, 0x07, 0x0a, 0xe6, 0x63, 0x90, 0xbf, 0x91, 0x67, 0x90,
6274
+	0xcd, 0xbf, 0xe6, 0x00, 0xe2, 0x6d, 0x7e, 0xab, 0xf7, 0xd6, 0xb1, 0x5f, 0xbd, 0xae, 0x2f, 0xfd,
6275
+	0xe3, 0x75, 0x7d, 0xe9, 0x8f, 0x57, 0xf5, 0xdc, 0xab, 0xab, 0x7a, 0xee, 0x6f, 0x57, 0xf5, 0xdc,
6276
+	0xbf, 0xae, 0xea, 0xb9, 0xd3, 0x82, 0xae, 0xfb, 0x7e, 0xf2, 0xbf, 0x00, 0x00, 0x00, 0xff, 0xff,
6277
+	0xc1, 0xd8, 0x19, 0x9e, 0x30, 0x13, 0x00, 0x00,
6277 6278
 }
... ...
@@ -393,6 +393,9 @@ message SecretSpec {
393 393
 	// The currently recognized values are:
394 394
 	// - golang: Go templating
395 395
 	Driver templating = 3;
396
+
397
+	// Driver is the the secret driver that is used to store the specified secret
398
+	Driver driver = 4;
396 399
 }
397 400
 
398 401
 // ConfigSpec specifies user-provided configuration files.
399 402
new file mode 100644
... ...
@@ -0,0 +1,14 @@
0
+package validation
1
+
2
+import "fmt"
3
+
4
+// MaxSecretSize is the maximum byte length of the `Secret.Spec.Data` field.
5
+const MaxSecretSize = 500 * 1024 // 500KB
6
+
7
+// ValidateSecretPayload validates the secret payload size
8
+func ValidateSecretPayload(data []byte) error {
9
+	if len(data) >= MaxSecretSize || len(data) < 1 {
10
+		return fmt.Errorf("secret data must be larger than 0 and less than %d bytes", MaxSecretSize)
11
+	}
12
+	return nil
13
+}
... ...
@@ -6,6 +6,7 @@ import (
6 6
 
7 7
 	"github.com/Sirupsen/logrus"
8 8
 	"github.com/docker/swarmkit/api"
9
+	"github.com/docker/swarmkit/api/validation"
9 10
 	"github.com/docker/swarmkit/identity"
10 11
 	"github.com/docker/swarmkit/log"
11 12
 	"github.com/docker/swarmkit/manager/state/store"
... ...
@@ -14,9 +15,6 @@ import (
14 14
 	"google.golang.org/grpc/codes"
15 15
 )
16 16
 
17
-// MaxSecretSize is the maximum byte length of the `Secret.Spec.Data` field.
18
-const MaxSecretSize = 500 * 1024 // 500KB
19
-
20 17
 // assumes spec is not nil
21 18
 func secretFromSecretSpec(spec *api.SecretSpec) *api.Secret {
22 19
 	return &api.Secret{
... ...
@@ -56,7 +54,6 @@ func (s *Server) UpdateSecret(ctx context.Context, request *api.UpdateSecretRequ
56 56
 	if request.SecretID == "" || request.SecretVersion == nil {
57 57
 		return nil, grpc.Errorf(codes.InvalidArgument, errInvalidArgument.Error())
58 58
 	}
59
-
60 59
 	var secret *api.Secret
61 60
 	err := s.store.Update(func(tx store.Tx) error {
62 61
 		secret = store.GetSecret(tx, request.SecretID)
... ...
@@ -245,9 +242,16 @@ func validateSecretSpec(spec *api.SecretSpec) error {
245 245
 	if err := validateConfigOrSecretAnnotations(spec.Annotations); err != nil {
246 246
 		return err
247 247
 	}
248
-
249
-	if len(spec.Data) >= MaxSecretSize || len(spec.Data) < 1 {
250
-		return grpc.Errorf(codes.InvalidArgument, "secret data must be larger than 0 and less than %d bytes", MaxSecretSize)
248
+	// Check if secret driver is defined
249
+	if spec.Driver != nil {
250
+		// Ensure secret driver has a name
251
+		if spec.Driver.Name == "" {
252
+			return grpc.Errorf(codes.InvalidArgument, "secret driver must have a name")
253
+		}
254
+		return nil
255
+	}
256
+	if err := validation.ValidateSecretPayload(spec.Data); err != nil {
257
+		return grpc.Errorf(codes.InvalidArgument, "%s", err.Error())
251 258
 	}
252 259
 	return nil
253 260
 }
... ...
@@ -10,7 +10,6 @@ import (
10 10
 )
11 11
 
12 12
 var (
13
-	errNotImplemented  = errors.New("not implemented")
14 13
 	errInvalidArgument = errors.New("invalid argument")
15 14
 )
16 15
 
... ...
@@ -1,9 +1,13 @@
1 1
 package dispatcher
2 2
 
3 3
 import (
4
+	"fmt"
5
+
4 6
 	"github.com/Sirupsen/logrus"
5 7
 	"github.com/docker/swarmkit/api"
6 8
 	"github.com/docker/swarmkit/api/equality"
9
+	"github.com/docker/swarmkit/api/validation"
10
+	"github.com/docker/swarmkit/manager/drivers"
7 11
 	"github.com/docker/swarmkit/manager/state/store"
8 12
 )
9 13
 
... ...
@@ -24,15 +28,16 @@ type typeAndID struct {
24 24
 }
25 25
 
26 26
 type assignmentSet struct {
27
+	dp                   *drivers.DriverProvider
27 28
 	tasksMap             map[string]*api.Task
28 29
 	tasksUsingDependency map[typeAndID]map[string]struct{}
29 30
 	changes              map[typeAndID]*api.AssignmentChange
30
-
31
-	log *logrus.Entry
31
+	log                  *logrus.Entry
32 32
 }
33 33
 
34
-func newAssignmentSet(log *logrus.Entry) *assignmentSet {
34
+func newAssignmentSet(log *logrus.Entry, dp *drivers.DriverProvider) *assignmentSet {
35 35
 	return &assignmentSet{
36
+		dp:                   dp,
36 37
 		changes:              make(map[typeAndID]*api.AssignmentChange),
37 38
 		tasksMap:             make(map[string]*api.Task),
38 39
 		tasksUsingDependency: make(map[typeAndID]map[string]struct{}),
... ...
@@ -53,12 +58,13 @@ func (a *assignmentSet) addTaskDependencies(readTx store.ReadTx, t *api.Task) {
53 53
 		if len(a.tasksUsingDependency[mapKey]) == 0 {
54 54
 			a.tasksUsingDependency[mapKey] = make(map[string]struct{})
55 55
 
56
-			secret := store.GetSecret(readTx, secretID)
57
-			if secret == nil {
56
+			secret, err := a.secret(readTx, secretID)
57
+			if err != nil {
58 58
 				a.log.WithFields(logrus.Fields{
59 59
 					"secret.id":   secretID,
60 60
 					"secret.name": secretRef.SecretName,
61
-				}).Debug("secret not found")
61
+					"error":       err,
62
+				}).Error("failed to fetch secret")
62 63
 				continue
63 64
 			}
64 65
 
... ...
@@ -245,3 +251,29 @@ func (a *assignmentSet) message() api.AssignmentsMessage {
245 245
 
246 246
 	return message
247 247
 }
248
+
249
+// secret populates the secret value from raft store. For external secrets, the value is populated
250
+// from the secret driver.
251
+func (a *assignmentSet) secret(readTx store.ReadTx, secretID string) (*api.Secret, error) {
252
+	secret := store.GetSecret(readTx, secretID)
253
+	if secret == nil {
254
+		return nil, fmt.Errorf("secret not found")
255
+	}
256
+	if secret.Spec.Driver == nil {
257
+		return secret, nil
258
+	}
259
+	d, err := a.dp.NewSecretDriver(secret.Spec.Driver)
260
+	if err != nil {
261
+		return nil, err
262
+	}
263
+	value, err := d.Get(&secret.Spec)
264
+	if err != nil {
265
+		return nil, err
266
+	}
267
+	if err := validation.ValidateSecretPayload(value); err != nil {
268
+		return nil, err
269
+	}
270
+	// Assign the secret
271
+	secret.Spec.Data = value
272
+	return secret, nil
273
+}
... ...
@@ -17,6 +17,7 @@ import (
17 17
 	"github.com/docker/swarmkit/api/equality"
18 18
 	"github.com/docker/swarmkit/ca"
19 19
 	"github.com/docker/swarmkit/log"
20
+	"github.com/docker/swarmkit/manager/drivers"
20 21
 	"github.com/docker/swarmkit/manager/state/store"
21 22
 	"github.com/docker/swarmkit/remotes"
22 23
 	"github.com/docker/swarmkit/watch"
... ...
@@ -125,6 +126,7 @@ type Dispatcher struct {
125 125
 	ctx                  context.Context
126 126
 	cancel               context.CancelFunc
127 127
 	clusterUpdateQueue   *watch.Queue
128
+	dp                   *drivers.DriverProvider
128 129
 
129 130
 	taskUpdates     map[string]*api.TaskStatus // indexed by task ID
130 131
 	taskUpdatesLock sync.Mutex
... ...
@@ -142,8 +144,9 @@ type Dispatcher struct {
142 142
 }
143 143
 
144 144
 // New returns Dispatcher with cluster interface(usually raft.Node).
145
-func New(cluster Cluster, c *Config) *Dispatcher {
145
+func New(cluster Cluster, c *Config, dp *drivers.DriverProvider) *Dispatcher {
146 146
 	d := &Dispatcher{
147
+		dp:                    dp,
147 148
 		nodes:                 newNodeStore(c.HeartbeatPeriod, c.HeartbeatEpsilon, c.GracePeriodMultiplier, c.RateLimitPeriod),
148 149
 		downNodes:             newNodeStore(defaultNodeDownPeriod, 0, 1, 0),
149 150
 		store:                 cluster.MemoryStore(),
... ...
@@ -836,7 +839,7 @@ func (d *Dispatcher) Assignments(r *api.AssignmentsRequest, stream api.Dispatche
836 836
 	var (
837 837
 		sequence    int64
838 838
 		appliesTo   string
839
-		assignments = newAssignmentSet(log)
839
+		assignments = newAssignmentSet(log, d.dp)
840 840
 	)
841 841
 
842 842
 	sendMessage := func(msg api.AssignmentsMessage, assignmentType api.AssignmentsMessage_Type) error {
843 843
new file mode 100644
... ...
@@ -0,0 +1,34 @@
0
+package drivers
1
+
2
+import (
3
+	"fmt"
4
+
5
+	"github.com/docker/docker/pkg/plugingetter"
6
+	"github.com/docker/swarmkit/api"
7
+)
8
+
9
+// DriverProvider provides external drivers
10
+type DriverProvider struct {
11
+	pluginGetter plugingetter.PluginGetter
12
+}
13
+
14
+// New returns a new driver provider
15
+func New(pluginGetter plugingetter.PluginGetter) *DriverProvider {
16
+	return &DriverProvider{pluginGetter: pluginGetter}
17
+}
18
+
19
+// NewSecretDriver creates a new driver for fetching secrets
20
+func (m *DriverProvider) NewSecretDriver(driver *api.Driver) (*SecretDriver, error) {
21
+	if m.pluginGetter == nil {
22
+		return nil, fmt.Errorf("plugin getter is nil")
23
+	}
24
+	if driver == nil && driver.Name == "" {
25
+		return nil, fmt.Errorf("driver specification is nil")
26
+	}
27
+	// Search for the specified plugin
28
+	plugin, err := m.pluginGetter.Get(driver.Name, SecretsProviderCapability, plugingetter.Lookup)
29
+	if err != nil {
30
+		return nil, err
31
+	}
32
+	return NewSecretDriver(plugin), nil
33
+}
0 34
new file mode 100644
... ...
@@ -0,0 +1,55 @@
0
+package drivers
1
+
2
+import (
3
+	"fmt"
4
+
5
+	"github.com/docker/docker/pkg/plugingetter"
6
+	"github.com/docker/swarmkit/api"
7
+)
8
+
9
+const (
10
+	// SecretsProviderAPI is the endpoint for fetching secrets from plugins
11
+	SecretsProviderAPI = "/SecretProvider.GetSecret"
12
+
13
+	// SecretsProviderCapability is the secrets provider plugin capability identification
14
+	SecretsProviderCapability = "secretprovider"
15
+)
16
+
17
+// SecretDriver provides secrets from different stores
18
+type SecretDriver struct {
19
+	plugin plugingetter.CompatPlugin
20
+}
21
+
22
+// NewSecretDriver creates a new driver that provides third party secrets
23
+func NewSecretDriver(plugin plugingetter.CompatPlugin) *SecretDriver {
24
+	return &SecretDriver{plugin: plugin}
25
+}
26
+
27
+// Get gets a secret from the secret provider
28
+func (d *SecretDriver) Get(spec *api.SecretSpec) ([]byte, error) {
29
+	if spec == nil {
30
+		return nil, fmt.Errorf("spec is nil")
31
+	}
32
+	var secretResp SecretsProviderResponse
33
+	secretReq := &SecretsProviderRequest{Name: spec.Annotations.Name}
34
+	err := d.plugin.Client().Call(SecretsProviderAPI, secretReq, &secretResp)
35
+	if err != nil {
36
+		return nil, err
37
+	}
38
+	if secretResp.Err != "" {
39
+		return nil, fmt.Errorf(secretResp.Err)
40
+	}
41
+	// Assign the secret value
42
+	return []byte(secretResp.Value), nil
43
+}
44
+
45
+// SecretsProviderRequest is the secrets provider request.
46
+type SecretsProviderRequest struct {
47
+	Name string `json:"name"` // Name is the name of the secret plugin
48
+}
49
+
50
+// SecretsProviderResponse is the secrets provider response.
51
+type SecretsProviderResponse struct {
52
+	Value string `json:"value"` // Value is the value of the secret
53
+	Err   string `json:"err"`   // Err is the error response of the plugin
54
+}
... ...
@@ -26,6 +26,7 @@ import (
26 26
 	"github.com/docker/swarmkit/manager/allocator/networkallocator"
27 27
 	"github.com/docker/swarmkit/manager/controlapi"
28 28
 	"github.com/docker/swarmkit/manager/dispatcher"
29
+	"github.com/docker/swarmkit/manager/drivers"
29 30
 	"github.com/docker/swarmkit/manager/health"
30 31
 	"github.com/docker/swarmkit/manager/keymanager"
31 32
 	"github.com/docker/swarmkit/manager/logbroker"
... ...
@@ -218,7 +219,7 @@ func New(config *Config) (*Manager, error) {
218 218
 	m := &Manager{
219 219
 		config:          *config,
220 220
 		caserver:        ca.NewServer(raftNode.MemoryStore(), config.SecurityConfig, config.RootCAPaths),
221
-		dispatcher:      dispatcher.New(raftNode, dispatcher.DefaultConfig()),
221
+		dispatcher:      dispatcher.New(raftNode, dispatcher.DefaultConfig(), drivers.New(config.PluginGetter)),
222 222
 		logbroker:       logbroker.New(raftNode.MemoryStore()),
223 223
 		server:          grpc.NewServer(opts...),
224 224
 		localserver:     grpc.NewServer(opts...),
... ...
@@ -20,10 +20,7 @@ type decisionTree struct {
20 20
 // (lowest) first according to the sorting function. Must be called on a leaf
21 21
 // of the decision tree.
22 22
 //
23
-// The caller may modify the nodes in the returned slice. This has the effect
24
-// of changing the nodes in the decision tree entry. The next node to
25
-// findBestNodes on this decisionTree entry will take into account the changes
26
-// that were made to the nodes.
23
+// The caller may modify the nodes in the returned slice.
27 24
 func (dt *decisionTree) orderedNodes(meetsConstraints func(*NodeInfo) bool, nodeLess func(*NodeInfo, *NodeInfo) bool) []NodeInfo {
28 25
 	if dt.nodeHeap.length != len(dt.nodeHeap.nodes) {
29 26
 		// We already collapsed the heap into a sorted slice, so