Repository: kumahq/kuma
Pull request #1291 (2020-12-11 09:34:28)

feat(kuma-dp): Kuma DP + Envoy version in Dataplane Insights (#1112) (bp #1192)
This is an automated backport of pull request #1192 done by Mergify

Cherry-pick of 8efb495018a517e0cb96e61f374e858dbc465ea4 has failed:
```
On branch mergify/bp/release-1.0/pr-1192
Your branch is up to date with 'origin/release-1.0'.

You are currently cherry-picking commit 8efb4950.
  (fix conflicts and run "git cherry-pick --continue")
  (use "git cherry-pick --abort" to cancel the cherry-pick operation)

Changes to be committed:

	modified:   api/mesh/v1alpha1/dataplane_insight.proto
	modified:   api/mesh/v1alpha1/dataplane_insight_helpers.go
	modified:   app/kuma-dp/cmd/run_test.go
	modified:   app/kuma-dp/cmd/testdata/envoy-mock.sleep.sh
	modified:   app/kuma-dp/pkg/dataplane/envoy/envoy.go
	modified:   app/kuma-dp/pkg/dataplane/envoy/envoy_test.go
	modified:   app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap.go
	modified:   app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap_test.go
	modified:   app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-0.sh
	modified:   app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-1.sh
	modified:   pkg/xds/bootstrap/generator.go
	modified:   pkg/xds/bootstrap/generator_test.go
	modified:   pkg/xds/bootstrap/server_test.go
	modified:   pkg/xds/bootstrap/template.go
	modified:   pkg/xds/bootstrap/testdata/bootstrap.k8s.golden.yaml
	modified:   pkg/xds/bootstrap/testdata/bootstrap.overridden.golden.yaml
	modified:   pkg/xds/bootstrap/testdata/bootstrap.universal.golden.yaml
	modified:   pkg/xds/bootstrap/testdata/generator.custom-config-minimal-request.golden.yaml
	modified:   pkg/xds/bootstrap/testdata/generator.custom-config.golden.yaml
	modified:   pkg/xds/bootstrap/testdata/generator.default-config-minimal-request.golden.yaml
	modified:   pkg/xds/bootstrap/testdata/generator.default-config.golden.yaml
	modified:   pkg/xds/bootstrap/types/bootstrap_request.go
	modified:   pkg/xds/server/dataplane_status_tracker.go
	modified:   pkg/xds/server/dataplane_status_tracker_test.go

Unmerged paths:
  (use "git add <file>..." to mark resolution)

	both modified:   api/mesh/v1alpha1/dataplane_insight.pb.go

```

To fixup this pull request, you can check out it locally. See documentation: https://help.github.com/articles/checking-out-pull-requests-locally/
---


<details>
<summary>Mergify commands and options</summary>

<br />

More conditions and actions can be found in the [documentation](https://docs.mergify.io/).

You can also trigger Mergify actions by commenting on this pull request:

- `@Mergifyio refresh` will re-evaluate the rules
- `@Mergifyio rebase` will rebase this PR on its base branch
- `@Mergifyio update` will merge the base branch into this PR
- `@Mergifyio backport <destination>` will backport this PR on `<destination>` branch

Additionally, on Mergify [dashboard](https://dashboard.mergify.io/) you can:

- look at your merge queues
- generate the Mergify configuration with the config editor.

Finally, you can contact us on https://mergify.io/
</details>



Patch:
diff --git a/api/mesh/v1alpha1/dataplane_insight.pb.go b/api/mesh/v1alpha1/dataplane_insight.pb.go
index d491ac9cf..4a39eb45e 100644
--- a/api/mesh/v1alpha1/dataplane_insight.pb.go
+++ b/api/mesh/v1alpha1/dataplane_insight.pb.go
@@ -109,6 +109,8 @@ type DiscoverySubscription struct {
 	DisconnectTime *timestamp.Timestamp `protobuf:"bytes,4,opt,name=disconnect_time,json=disconnectTime,proto3" json:"disconnect_time,omitempty"`
 	// Status of the ADS subscription.
 	Status *DiscoverySubscriptionStatus `protobuf:"bytes,5,opt,name=status,proto3" json:"status,omitempty"`
+	// Version of Envoy and Kuma dataplane
+	Version *Version `protobuf:"bytes,6,opt,name=version,proto3" json:"version,omitempty"`
 }
 
 func (x *DiscoverySubscription) Reset() {
@@ -178,6 +180,13 @@ func (x *DiscoverySubscription) GetStatus() *DiscoverySubscriptionStatus {
 	return nil
 }
 
+func (x *DiscoverySubscription) GetVersion() *Version {
+	if x != nil {
+		return x.Version
+	}
+	return nil
+}
+
 // DiscoverySubscriptionStatus defines status of an ADS subscription.
 type DiscoverySubscriptionStatus struct {
 	state         protoimpl.MessageState
@@ -339,6 +348,198 @@ func (x *DiscoveryServiceStats) GetResponsesRejected() uint64 {
 	return 0
 }
 
+// Version defines version of Kuma Dataplane and Envoy
+type Version struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	// Version of Kuma Dataplane
+	DpVersion *KumaDpVersion `protobuf:"bytes,1,opt,name=dpVersion,proto3" json:"dpVersion,omitempty"`
+	// Version of Envoy
+	Envoy *EnvoyVersion `protobuf:"bytes,2,opt,name=envoy,proto3" json:"envoy,omitempty"`
+}
+
+func (x *Version) Reset() {
+	*x = Version{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[4]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *Version) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Version) ProtoMessage() {}
+
+func (x *Version) ProtoReflect() protoreflect.Message {
+	mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[4]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use Version.ProtoReflect.Descriptor instead.
+func (*Version) Descriptor() ([]byte, []int) {
+	return file_mesh_v1alpha1_dataplane_insight_proto_rawDescGZIP(), []int{4}
+}
+
+func (x *Version) GetDpVersion() *KumaDpVersion {
+	if x != nil {
+		return x.DpVersion
+	}
+	return nil
+}
+
+func (x *Version) GetEnvoy() *EnvoyVersion {
+	if x != nil {
+		return x.Envoy
+	}
+	return nil
+}
+
+// KumaDpVersion describes details of Kuma Dataplane version
+type KumaDpVersion struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	// Version number of Kuma Dataplane
+	Version string `protobuf:"bytes,1,opt,name=version,proto3" json:"version,omitempty"`
+	// Git tag of Kuma Dataplane version
+	GitTag string `protobuf:"bytes,2,opt,name=gitTag,proto3" json:"gitTag,omitempty"`
+	// Git commit of Kuma Dataplane version
+	GitCommit string `protobuf:"bytes,3,opt,name=gitCommit,proto3" json:"gitCommit,omitempty"`
+	// Build date of Kuma Dataplane version
+	BuildDate string `protobuf:"bytes,4,opt,name=buildDate,proto3" json:"buildDate,omitempty"`
+}
+
+func (x *KumaDpVersion) Reset() {
+	*x = KumaDpVersion{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[5]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *KumaDpVersion) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*KumaDpVersion) ProtoMessage() {}
+
+func (x *KumaDpVersion) ProtoReflect() protoreflect.Message {
+	mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[5]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use KumaDpVersion.ProtoReflect.Descriptor instead.
+func (*KumaDpVersion) Descriptor() ([]byte, []int) {
+	return file_mesh_v1alpha1_dataplane_insight_proto_rawDescGZIP(), []int{5}
+}
+
+func (x *KumaDpVersion) GetVersion() string {
+	if x != nil {
+		return x.Version
+	}
+	return ""
+}
+
+func (x *KumaDpVersion) GetGitTag() string {
+	if x != nil {
+		return x.GitTag
+	}
+	return ""
+}
+
+func (x *KumaDpVersion) GetGitCommit() string {
+	if x != nil {
+		return x.GitCommit
+	}
+	return ""
+}
+
+func (x *KumaDpVersion) GetBuildDate() string {
+	if x != nil {
+		return x.BuildDate
+	}
+	return ""
+}
+
+// EnvoyVersion describes details of Envoy version
+type EnvoyVersion struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	// Version number of Envoy
+	Version string `protobuf:"bytes,1,opt,name=version,proto3" json:"version,omitempty"`
+	// Full build tag of Envoy version
+	Build string `protobuf:"bytes,2,opt,name=build,proto3" json:"build,omitempty"`
+}
+
+func (x *EnvoyVersion) Reset() {
+	*x = EnvoyVersion{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[6]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *EnvoyVersion) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*EnvoyVersion) ProtoMessage() {}
+
+func (x *EnvoyVersion) ProtoReflect() protoreflect.Message {
+	mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[6]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use EnvoyVersion.ProtoReflect.Descriptor instead.
+func (*EnvoyVersion) Descriptor() ([]byte, []int) {
+	return file_mesh_v1alpha1_dataplane_insight_proto_rawDescGZIP(), []int{6}
+}
+
+func (x *EnvoyVersion) GetVersion() string {
+	if x != nil {
+		return x.Version
+	}
+	return ""
+}
+
+func (x *EnvoyVersion) GetBuild() string {
+	if x != nil {
+		return x.Build
+	}
+	return ""
+}
+
 // MTLS defines insights for mTLS
 type DataplaneInsight_MTLS struct {
 	state         protoimpl.MessageState
@@ -357,7 +558,7 @@ type DataplaneInsight_MTLS struct {
 func (x *DataplaneInsight_MTLS) Reset() {
 	*x = DataplaneInsight_MTLS{}
 	if protoimpl.UnsafeEnabled {
-		mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[4]
+		mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[7]
 		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
 		ms.StoreMessageInfo(mi)
 	}
@@ -370,7 +571,7 @@ func (x *DataplaneInsight_MTLS) String() string {
 func (*DataplaneInsight_MTLS) ProtoMessage() {}
 
 func (x *DataplaneInsight_MTLS) ProtoReflect() protoreflect.Message {
-	mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[4]
+	mi := &file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[7]
 	if protoimpl.UnsafeEnabled && x != nil {
 		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
 		if ms.LoadMessageInfo() == nil {
@@ -443,7 +644,7 @@ var file_mesh_v1alpha1_dataplane_insight_proto_rawDesc = []byte{
 	0x3b, 0x0a, 0x19, 0x63, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x5f, 0x72,
 	0x65, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x18, 0x03, 0x20, 0x01,
 	0x28, 0x0d, 0x52, 0x18, 0x63, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x52,
-	0x65, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x22, 0xd5, 0x02, 0x0a,
+	0x65, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x22, 0x8c, 0x03, 0x0a,
 	0x15, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x75, 0x62, 0x73, 0x63, 0x72,
 	0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x17, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01,
 	0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x10, 0x01, 0x52, 0x02, 0x69, 0x64, 0x12,
@@ -465,46 +666,70 @@ var file_mesh_v1alpha1_dataplane_insight_proto_rawDesc = []byte{
 	0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79,
 	0x53, 0x75, 0x62, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x53, 0x74, 0x61, 0x74,
 	0x75, 0x73, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x8a, 0x01, 0x02, 0x10, 0x01, 0x52, 0x06, 0x73, 0x74,
-	0x61, 0x74, 0x75, 0x73, 0x22, 0x98, 0x03, 0x0a, 0x1b, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65,
-	0x72, 0x79, 0x53, 0x75, 0x62, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x53, 0x74,
-	0x61, 0x74, 0x75, 0x73, 0x12, 0x44, 0x0a, 0x10, 0x6c, 0x61, 0x73, 0x74, 0x5f, 0x75, 0x70, 0x64,
-	0x61, 0x74, 0x65, 0x5f, 0x74, 0x69, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1a,
-	0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66,
-	0x2e, 0x54, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x52, 0x0e, 0x6c, 0x61, 0x73, 0x74,
-	0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x54, 0x69, 0x6d, 0x65, 0x12, 0x3f, 0x0a, 0x05, 0x74, 0x6f,
-	0x74, 0x61, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61,
+	0x61, 0x74, 0x75, 0x73, 0x12, 0x35, 0x0a, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18,
+	0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1b, 0x2e, 0x6b, 0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65, 0x73,
+	0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x56, 0x65, 0x72, 0x73, 0x69,
+	0x6f, 0x6e, 0x52, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x22, 0x98, 0x03, 0x0a, 0x1b,
+	0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x75, 0x62, 0x73, 0x63, 0x72, 0x69,
+	0x70, 0x74, 0x69, 0x6f, 0x6e, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x44, 0x0a, 0x10, 0x6c,
+	0x61, 0x73, 0x74, 0x5f, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x5f, 0x74, 0x69, 0x6d, 0x65, 0x18,
+	0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1a, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70,
+	0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x54, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d,
+	0x70, 0x52, 0x0e, 0x6c, 0x61, 0x73, 0x74, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x54, 0x69, 0x6d,
+	0x65, 0x12, 0x3f, 0x0a, 0x05, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b,
+	0x32, 0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76, 0x31, 0x61,
+	0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53,
+	0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x05, 0x74, 0x6f, 0x74,
+	0x61, 0x6c, 0x12, 0x3b, 0x0a, 0x03, 0x63, 0x64, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32,
+	0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c,
+	0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x65,
+	0x72, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x03, 0x63, 0x64, 0x73, 0x12,
+	0x3b, 0x0a, 0x03, 0x65, 0x64, 0x73, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x6b,
+	0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+	0x31, 0x2e, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x65, 0x72, 0x76, 0x69,
+	0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x03, 0x65, 0x64, 0x73, 0x12, 0x3b, 0x0a, 0x03,
+	0x6c, 0x64, 0x73, 0x18, 0x05, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61,
 	0x2e, 0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x44,
 	0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x53,
-	0x74, 0x61, 0x74, 0x73, 0x52, 0x05, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x12, 0x3b, 0x0a, 0x03, 0x63,
-	0x64, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61, 0x2e,
-	0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x69,
-	0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74,
-	0x61, 0x74, 0x73, 0x52, 0x03, 0x63, 0x64, 0x73, 0x12, 0x3b, 0x0a, 0x03, 0x65, 0x64, 0x73, 0x18,
-	0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65, 0x73,
-	0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x69, 0x73, 0x63, 0x6f,
+	0x74, 0x61, 0x74, 0x73, 0x52, 0x03, 0x6c, 0x64, 0x73, 0x12, 0x3b, 0x0a, 0x03, 0x72, 0x64, 0x73,
+	0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65,
+	0x73, 0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x69, 0x73, 0x63,
+	0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74,
+	0x73, 0x52, 0x03, 0x72, 0x64, 0x73, 0x22, 0xa4, 0x01, 0x0a, 0x15, 0x44, 0x69, 0x73, 0x63, 0x6f,
 	0x76, 0x65, 0x72, 0x79, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x73,
-	0x52, 0x03, 0x65, 0x64, 0x73, 0x12, 0x3b, 0x0a, 0x03, 0x6c, 0x64, 0x73, 0x18, 0x05, 0x20, 0x01,
-	0x28, 0x0b, 0x32, 0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76,
-	0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72,
-	0x79, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x03, 0x6c,
-	0x64, 0x73, 0x12, 0x3b, 0x0a, 0x03, 0x72, 0x64, 0x73, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32,
-	0x29, 0x2e, 0x6b, 0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c,
-	0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x65,
-	0x72, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x03, 0x72, 0x64, 0x73, 0x22,
-	0xa4, 0x01, 0x0a, 0x15, 0x44, 0x69, 0x73, 0x63, 0x6f, 0x76, 0x65, 0x72, 0x79, 0x53, 0x65, 0x72,
-	0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x73, 0x12, 0x25, 0x0a, 0x0e, 0x72, 0x65, 0x73,
-	0x70, 0x6f, 0x6e, 0x73, 0x65, 0x73, 0x5f, 0x73, 0x65, 0x6e, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28,
-	0x04, 0x52, 0x0d, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x73, 0x53, 0x65, 0x6e, 0x74,
-	0x12, 0x35, 0x0a, 0x16, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x73, 0x5f, 0x61, 0x63,
-	0x6b, 0x6e, 0x6f, 0x77, 0x6c, 0x65, 0x64, 0x67, 0x65, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04,
-	0x52, 0x15, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x73, 0x41, 0x63, 0x6b, 0x6e, 0x6f,
-	0x77, 0x6c, 0x65, 0x64, 0x67, 0x65, 0x64, 0x12, 0x2d, 0x0a, 0x12, 0x72, 0x65, 0x73, 0x70, 0x6f,
-	0x6e, 0x73, 0x65, 0x73, 0x5f, 0x72, 0x65, 0x6a, 0x65, 0x63, 0x74, 0x65, 0x64, 0x18, 0x03, 0x20,
-	0x01, 0x28, 0x04, 0x52, 0x11, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x73, 0x52, 0x65,
-	0x6a, 0x65, 0x63, 0x74, 0x65, 0x64, 0x42, 0x2a, 0x5a, 0x28, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62,
-	0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6b, 0x75, 0x6d, 0x61, 0x68, 0x71, 0x2f, 0x6b, 0x75, 0x6d, 0x61,
-	0x2f, 0x61, 0x70, 0x69, 0x2f, 0x6d, 0x65, 0x73, 0x68, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68,
-	0x61, 0x31, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
+	0x12, 0x25, 0x0a, 0x0e, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x73, 0x5f, 0x73, 0x65,
+	0x6e, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x0d, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e,
+	0x73, 0x65, 0x73, 0x53, 0x65, 0x6e, 0x74, 0x12, 0x35, 0x0a, 0x16, 0x72, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x73, 0x5f, 0x61, 0x63, 0x6b, 0x6e, 0x6f, 0x77, 0x6c, 0x65, 0x64, 0x67, 0x65,
+	0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04, 0x52, 0x15, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73,
+	0x65, 0x73, 0x41, 0x63, 0x6b, 0x6e, 0x6f, 0x77, 0x6c, 0x65, 0x64, 0x67, 0x65, 0x64, 0x12, 0x2d,
+	0x0a, 0x12, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x73, 0x5f, 0x72, 0x65, 0x6a, 0x65,
+	0x63, 0x74, 0x65, 0x64, 0x18, 0x03, 0x20, 0x01, 0x28, 0x04, 0x52, 0x11, 0x72, 0x65, 0x73, 0x70,
+	0x6f, 0x6e, 0x73, 0x65, 0x73, 0x52, 0x65, 0x6a, 0x65, 0x63, 0x74, 0x65, 0x64, 0x22, 0x82, 0x01,
+	0x0a, 0x07, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x3f, 0x0a, 0x09, 0x64, 0x70, 0x56,
+	0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x21, 0x2e, 0x6b,
+	0x75, 0x6d, 0x61, 0x2e, 0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+	0x31, 0x2e, 0x4b, 0x75, 0x6d, 0x61, 0x44, 0x70, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x52,
+	0x09, 0x64, 0x70, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x36, 0x0a, 0x05, 0x65, 0x6e,
+	0x76, 0x6f, 0x79, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e, 0x6b, 0x75, 0x6d, 0x61,
+	0x2e, 0x6d, 0x65, 0x73, 0x68, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45,
+	0x6e, 0x76, 0x6f, 0x79, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x52, 0x05, 0x65, 0x6e, 0x76,
+	0x6f, 0x79, 0x22, 0x7d, 0x0a, 0x0d, 0x4b, 0x75, 0x6d, 0x61, 0x44, 0x70, 0x56, 0x65, 0x72, 0x73,
+	0x69, 0x6f, 0x6e, 0x12, 0x18, 0x0a, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x01,
+	0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x16, 0x0a,
+	0x06, 0x67, 0x69, 0x74, 0x54, 0x61, 0x67, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x67,
+	0x69, 0x74, 0x54, 0x61, 0x67, 0x12, 0x1c, 0x0a, 0x09, 0x67, 0x69, 0x74, 0x43, 0x6f, 0x6d, 0x6d,
+	0x69, 0x74, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x67, 0x69, 0x74, 0x43, 0x6f, 0x6d,
+	0x6d, 0x69, 0x74, 0x12, 0x1c, 0x0a, 0x09, 0x62, 0x75, 0x69, 0x6c, 0x64, 0x44, 0x61, 0x74, 0x65,
+	0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x62, 0x75, 0x69, 0x6c, 0x64, 0x44, 0x61, 0x74,
+	0x65, 0x22, 0x3e, 0x0a, 0x0c, 0x45, 0x6e, 0x76, 0x6f, 0x79, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f,
+	0x6e, 0x12, 0x18, 0x0a, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x01, 0x20, 0x01,
+	0x28, 0x09, 0x52, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x14, 0x0a, 0x05, 0x62,
+	0x75, 0x69, 0x6c, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x62, 0x75, 0x69, 0x6c,
+	0x64, 0x42, 0x2a, 0x5a, 0x28, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f,
+	0x6b, 0x75, 0x6d, 0x61, 0x68, 0x71, 0x2f, 0x6b, 0x75, 0x6d, 0x61, 0x2f, 0x61, 0x70, 0x69, 0x2f,
+	0x6d, 0x65, 0x73, 0x68, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x62, 0x06, 0x70,
+	0x72, 0x6f, 0x74, 0x6f, 0x33,
 }
 
 var (
@@ -519,34 +744,40 @@ func file_mesh_v1alpha1_dataplane_insight_proto_rawDescGZIP() []byte {
 	return file_mesh_v1alpha1_dataplane_insight_proto_rawDescData
 }
 
-var file_mesh_v1alpha1_dataplane_insight_proto_msgTypes = make([]protoimpl.MessageInfo, 5)
+var file_mesh_v1alpha1_dataplane_insight_proto_msgTypes = make([]protoimpl.MessageInfo, 8)
 var file_mesh_v1alpha1_dataplane_insight_proto_goTypes = []interface{}{
 	(*DataplaneInsight)(nil),            // 0: kuma.mesh.v1alpha1.DataplaneInsight
 	(*DiscoverySubscription)(nil),       // 1: kuma.mesh.v1alpha1.DiscoverySubscription
 	(*DiscoverySubscriptionStatus)(nil), // 2: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus
 	(*DiscoveryServiceStats)(nil),       // 3: kuma.mesh.v1alpha1.DiscoveryServiceStats
-	(*DataplaneInsight_MTLS)(nil),       // 4: kuma.mesh.v1alpha1.DataplaneInsight.MTLS
-	(*timestamp.Timestamp)(nil),         // 5: google.protobuf.Timestamp
+	(*Version)(nil),                     // 4: kuma.mesh.v1alpha1.Version
+	(*KumaDpVersion)(nil),               // 5: kuma.mesh.v1alpha1.KumaDpVersion
+	(*EnvoyVersion)(nil),                // 6: kuma.mesh.v1alpha1.EnvoyVersion
+	(*DataplaneInsight_MTLS)(nil),       // 7: kuma.mesh.v1alpha1.DataplaneInsight.MTLS
+	(*timestamp.Timestamp)(nil),         // 8: google.protobuf.Timestamp
 }
 var file_mesh_v1alpha1_dataplane_insight_proto_depIdxs = []int32{
 	1,  // 0: kuma.mesh.v1alpha1.DataplaneInsight.subscriptions:type_name -> kuma.mesh.v1alpha1.DiscoverySubscription
-	4,  // 1: kuma.mesh.v1alpha1.DataplaneInsight.mTLS:type_name -> kuma.mesh.v1alpha1.DataplaneInsight.MTLS
-	5,  // 2: kuma.mesh.v1alpha1.DiscoverySubscription.connect_time:type_name -> google.protobuf.Timestamp
-	5,  // 3: kuma.mesh.v1alpha1.DiscoverySubscription.disconnect_time:type_name -> google.protobuf.Timestamp
+	7,  // 1: kuma.mesh.v1alpha1.DataplaneInsight.mTLS:type_name -> kuma.mesh.v1alpha1.DataplaneInsight.MTLS
+	8,  // 2: kuma.mesh.v1alpha1.DiscoverySubscription.connect_time:type_name -> google.protobuf.Timestamp
+	8,  // 3: kuma.mesh.v1alpha1.DiscoverySubscription.disconnect_time:type_name -> google.protobuf.Timestamp
 	2,  // 4: kuma.mesh.v1alpha1.DiscoverySubscription.status:type_name -> kuma.mesh.v1alpha1.DiscoverySubscriptionStatus
-	5,  // 5: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.last_update_time:type_name -> google.protobuf.Timestamp
-	3,  // 6: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.total:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
-	3,  // 7: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.cds:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
-	3,  // 8: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.eds:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
-	3,  // 9: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.lds:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
-	3,  // 10: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.rds:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
-	5,  // 11: kuma.mesh.v1alpha1.DataplaneInsight.MTLS.certificate_expiration_time:type_name -> google.protobuf.Timestamp
-	5,  // 12: kuma.mesh.v1alpha1.DataplaneInsight.MTLS.last_certificate_regeneration:type_name -> google.protobuf.Timestamp
-	13, // [13:13] is the sub-list for method output_type
-	13, // [13:13] is the sub-list for method input_type
-	13, // [13:13] is the sub-list for extension type_name
-	13, // [13:13] is the sub-list for extension extendee
-	0,  // [0:13] is the sub-list for field type_name
+	4,  // 5: kuma.mesh.v1alpha1.DiscoverySubscription.version:type_name -> kuma.mesh.v1alpha1.Version
+	8,  // 6: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.last_update_time:type_name -> google.protobuf.Timestamp
+	3,  // 7: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.total:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
+	3,  // 8: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.cds:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
+	3,  // 9: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.eds:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
+	3,  // 10: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.lds:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
+	3,  // 11: kuma.mesh.v1alpha1.DiscoverySubscriptionStatus.rds:type_name -> kuma.mesh.v1alpha1.DiscoveryServiceStats
+	5,  // 12: kuma.mesh.v1alpha1.Version.dpVersion:type_name -> kuma.mesh.v1alpha1.KumaDpVersion
+	6,  // 13: kuma.mesh.v1alpha1.Version.envoy:type_name -> kuma.mesh.v1alpha1.EnvoyVersion
+	8,  // 14: kuma.mesh.v1alpha1.DataplaneInsight.MTLS.certificate_expiration_time:type_name -> google.protobuf.Timestamp
+	8,  // 15: kuma.mesh.v1alpha1.DataplaneInsight.MTLS.last_certificate_regeneration:type_name -> google.protobuf.Timestamp
+	16, // [16:16] is the sub-list for method output_type
+	16, // [16:16] is the sub-list for method input_type
+	16, // [16:16] is the sub-list for extension type_name
+	16, // [16:16] is the sub-list for extension extendee
+	0,  // [0:16] is the sub-list for field type_name
 }
 
 func init() { file_mesh_v1alpha1_dataplane_insight_proto_init() }
@@ -604,6 +835,42 @@ func file_mesh_v1alpha1_dataplane_insight_proto_init() {
 			}
 		}
 		file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*Version); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*KumaDpVersion); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*EnvoyVersion); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_mesh_v1alpha1_dataplane_insight_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} {
 			switch v := v.(*DataplaneInsight_MTLS); i {
 			case 0:
 				return &v.state
@@ -622,7 +889,7 @@ func file_mesh_v1alpha1_dataplane_insight_proto_init() {
 			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
 			RawDescriptor: file_mesh_v1alpha1_dataplane_insight_proto_rawDesc,
 			NumEnums:      0,
-			NumMessages:   5,
+			NumMessages:   8,
 			NumExtensions: 0,
 			NumServices:   0,
 		},
diff --git a/api/mesh/v1alpha1/dataplane_insight.proto b/api/mesh/v1alpha1/dataplane_insight.proto
index 02df0e2c9..90b7f3765 100644
--- a/api/mesh/v1alpha1/dataplane_insight.proto
+++ b/api/mesh/v1alpha1/dataplane_insight.proto
@@ -57,6 +57,9 @@ message DiscoverySubscription {
   // Status of the ADS subscription.
   DiscoverySubscriptionStatus status = 5
       [ (validate.rules).message.required = true ];
+
+  // Version of Envoy and Kuma dataplane
+  Version version = 6;
 }
 
 // DiscoverySubscriptionStatus defines status of an ADS subscription.
@@ -93,3 +96,39 @@ message DiscoveryServiceStats {
   // Number of xDS responses NACKed by the Dataplane.
   uint64 responses_rejected = 3;
 }
+
+// Version defines version of Kuma Dataplane and Envoy
+message Version {
+
+  // Version of Kuma Dataplane
+  KumaDpVersion dpVersion = 1;
+
+  // Version of Envoy
+  EnvoyVersion envoy = 2;
+}
+
+// KumaDpVersion describes details of Kuma Dataplane version
+message KumaDpVersion {
+
+  // Version number of Kuma Dataplane
+  string version = 1;
+
+  // Git tag of Kuma Dataplane version
+  string gitTag = 2;
+
+  // Git commit of Kuma Dataplane version
+  string gitCommit = 3;
+
+  // Build date of Kuma Dataplane version
+  string buildDate = 4;
+}
+
+// EnvoyVersion describes details of Envoy version
+message EnvoyVersion {
+
+  // Version number of Envoy
+  string version = 1;
+
+  // Full build tag of Envoy version
+  string build = 2;
+}
diff --git a/api/mesh/v1alpha1/dataplane_insight_helpers.go b/api/mesh/v1alpha1/dataplane_insight_helpers.go
index e3431830e..47f093aec 100644
--- a/api/mesh/v1alpha1/dataplane_insight_helpers.go
+++ b/api/mesh/v1alpha1/dataplane_insight_helpers.go
@@ -17,6 +17,21 @@ func NewSubscriptionStatus() *DiscoverySubscriptionStatus {
 	}
 }
 
+func NewVersion() *Version {
+	return &Version{
+		DpVersion: &KumaDpVersion{
+			Version:   "",
+			GitTag:    "",
+			GitCommit: "",
+			BuildDate: "",
+		},
+		Envoy: &EnvoyVersion{
+			Version: "",
+			Build:   "",
+		},
+	}
+}
+
 func (ds *DataplaneInsight) IsOnline() bool {
 	for _, s := range ds.GetSubscriptions() {
 		if s.ConnectTime != nil && s.DisconnectTime == nil {
diff --git a/app/kuma-dp/pkg/dataplane/envoy/envoy.go b/app/kuma-dp/pkg/dataplane/envoy/envoy.go
index bf4fabb2a..af2bf4d5b 100644
--- a/app/kuma-dp/pkg/dataplane/envoy/envoy.go
+++ b/app/kuma-dp/pkg/dataplane/envoy/envoy.go
@@ -7,6 +7,8 @@ import (
 	"os"
 	"os/exec"
 	"path/filepath"
+	"regexp"
+	"strings"
 	"time"
 
 	"github.com/kumahq/kuma/pkg/core/resources/model/rest"
@@ -23,7 +25,7 @@ var (
 	runLog = core.Log.WithName("kuma-dp").WithName("run").WithName("envoy")
 )
 
-type BootstrapConfigFactoryFunc func(url string, cfg kuma_dp.Config, dp *rest.Resource) (proto.Message, error)
+type BootstrapConfigFactoryFunc func(url string, cfg kuma_dp.Config, dp *rest.Resource, ev EnvoyVersion) (proto.Message, error)
 
 type Opts struct {
 	Config    kuma_dp.Config
@@ -47,6 +49,11 @@ type Envoy struct {
 	opts Opts
 }
 
+type EnvoyVersion struct {
+	Build   string
+	Version string
+}
+
 func (e *Envoy) NeedLeaderElection() bool {
 	return false
 }
@@ -95,8 +102,13 @@ func lookupEnvoyPath(configuredPath string) (string, error) {
 }
 
 func (e *Envoy) Start(stop <-chan struct{}) error {
+	envoyVersion, err := e.version()
+	if err != nil {
+		return errors.Wrap(err, "failed to get Envoy version")
+	}
+	runLog.Info("fetched Envoy version", "version", envoyVersion)
 	runLog.Info("generating bootstrap configuration")
-	bootstrapConfig, err := e.opts.Generator(e.opts.Config.ControlPlane.URL, e.opts.Config, e.opts.Dataplane)
+	bootstrapConfig, err := e.opts.Generator(e.opts.Config.ControlPlane.URL, e.opts.Config, e.opts.Dataplane, *envoyVersion)
 	if err != nil {
 		return errors.Errorf("Failed to generate Envoy bootstrap config. %v", err)
 	}
@@ -156,3 +168,27 @@ func (e *Envoy) Start(stop <-chan struct{}) error {
 		return err
 	}
 }
+
+func (e *Envoy) version() (*EnvoyVersion, error) {
+	binaryPathConfig := e.opts.Config.DataplaneRuntime.BinaryPath
+	resolvedPath, err := lookupEnvoyPath(binaryPathConfig)
+	if err != nil {
+		return nil, err
+	}
+	arg := "--version"
+	command := exec.Command(resolvedPath, arg)
+	output, err := command.Output()
+	if err != nil {
+		return nil, errors.Wrap(err, fmt.Sprintf("the envoy excutable was found at %s but an error occurred when executing it with arg %s", resolvedPath, arg))
+	}
+	build := strings.Trim(string(output), "\n")
+	build = regexp.MustCompile(`:(.*)`).FindString(build)
+	build = strings.Trim(build, ":")
+	build = strings.Trim(build, " ")
+	version := regexp.MustCompile(`/([0-9.]+)/`).FindString(build)
+	version = strings.Trim(version, "/")
+	return &EnvoyVersion{
+		Build:   build,
+		Version: version,
+	}, nil
+}
diff --git a/app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap.go b/app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap.go
index 29562f599..087857efd 100644
--- a/app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap.go
+++ b/app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap.go
@@ -23,6 +23,7 @@ import (
 	"github.com/kumahq/kuma/pkg/core"
 	rest_types "github.com/kumahq/kuma/pkg/core/resources/model/rest"
 	util_proto "github.com/kumahq/kuma/pkg/util/proto"
+	kuma_version "github.com/kumahq/kuma/pkg/version"
 	"github.com/kumahq/kuma/pkg/xds/bootstrap/types"
 )
 
@@ -48,7 +49,7 @@ func IsInvalidRequestErr(err error) bool {
 	return strings.HasPrefix(err.Error(), "Invalid request: ")
 }
 
-func (b *remoteBootstrap) Generate(url string, cfg kuma_dp.Config, dp *rest_types.Resource) (proto.Message, error) {
+func (b *remoteBootstrap) Generate(url string, cfg kuma_dp.Config, dp *rest_types.Resource, ev EnvoyVersion) (proto.Message, error) {
 	bootstrapUrl, err := net_url.Parse(url)
 	if err != nil {
 		return nil, err
@@ -78,7 +79,7 @@ func (b *remoteBootstrap) Generate(url string, cfg kuma_dp.Config, dp *rest_type
 	var respBytes []byte
 	err = retry.Do(context.Background(), backoff, func(ctx context.Context) error {
 		log.Info("trying to fetch bootstrap configuration from the Control Plane")
-		respBytes, err = b.requestForBootstrap(bootstrapUrl, cfg, dp)
+		respBytes, err = b.requestForBootstrap(bootstrapUrl, cfg, dp, ev)
 		if err == nil {
 			return nil
 		}
@@ -105,7 +106,7 @@ func (b *remoteBootstrap) Generate(url string, cfg kuma_dp.Config, dp *rest_type
 	return &bootstrap, nil
 }
 
-func (b *remoteBootstrap) requestForBootstrap(url *net_url.URL, cfg kuma_dp.Config, dp *rest_types.Resource) ([]byte, error) {
+func (b *remoteBootstrap) requestForBootstrap(url *net_url.URL, cfg kuma_dp.Config, dp *rest_types.Resource, ev EnvoyVersion) ([]byte, error) {
 	url.Path = "/bootstrap"
 	var dataplaneResource string
 	if dp != nil {
@@ -123,6 +124,18 @@ func (b *remoteBootstrap) requestForBootstrap(url *net_url.URL, cfg kuma_dp.Conf
 		AdminPort:          cfg.Dataplane.AdminPort.Lowest(),
 		DataplaneTokenPath: cfg.DataplaneRuntime.TokenPath,
 		DataplaneResource:  dataplaneResource,
+		Version: types.Version{
+			KumaDp: types.KumaDpVersion{
+				Version:   kuma_version.Build.Version,
+				GitTag:    kuma_version.Build.GitTag,
+				GitCommit: kuma_version.Build.GitCommit,
+				BuildDate: kuma_version.Build.BuildDate,
+			},
+			Envoy: types.EnvoyVersion{
+				Version: ev.Version,
+				Build:   ev.Build,
+			},
+		},
 	}
 	jsonBytes, err := json.Marshal(request)
 	if err != nil {
diff --git a/go.sum b/go.sum
index c8770c98c..574fde868 100644
--- a/go.sum
+++ b/go.sum
@@ -379,6 +379,7 @@ github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk=
 github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY=
 github.com/gobuffalo/envy v1.7.0/go.mod h1:n7DRkBerg/aorDM8kbduw5dN3oXGswK5liaSCx4T5NI=
 github.com/gobuffalo/envy v1.7.1/go.mod h1:FurDp9+EDPE4aIUS3ZLyD+7/9fpx7YRt/ukY6jIHf0w=
+github.com/gobuffalo/flect v0.2.0/go.mod h1:W3K3X9ksuZfir8f/LrfVtWmCDQFfayuylOJ7sz/Fj80=
 github.com/gobuffalo/logger v1.0.1/go.mod h1:2zbswyIUa45I+c+FLXuWl9zSWEiVuthsk8ze5s8JvPs=
 github.com/gobuffalo/packd v0.3.0/go.mod h1:zC7QkmNkYVGKPw4tHpBQ+ml7W/3tIebgeo1b36chA3Q=
 github.com/gobuffalo/packr/v2 v2.7.1/go.mod h1:qYEvAazPaVxy7Y7KR0W8qYEE+RymX74kETFqjFoFlOc=
@@ -701,6 +702,7 @@ github.com/onsi/gomega v1.4.3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1Cpa
 github.com/onsi/gomega v1.5.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY=
 github.com/onsi/gomega v1.7.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY=
 github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY=
+github.com/onsi/gomega v1.8.1/go.mod h1:Ho0h+IUsWyvy1OpqCwxlQ/21gkhVunqlU8fDGcoTdcA=
 github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo=
 github.com/onsi/gomega v1.10.3 h1:gph6h/qe9GSUw1NhH1gp+qb+h8rXD8Cy60Z32Qw3ELA=
 github.com/onsi/gomega v1.10.3/go.mod h1:V9xEwhxec5O8UDM77eCW8vLymOMltsqPVYWrpDsH8xc=
@@ -1271,6 +1273,7 @@ gopkg.in/yaml.v2 v2.2.5/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
 gopkg.in/yaml.v2 v2.2.8/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
 gopkg.in/yaml.v2 v2.3.0 h1:clyUAQHOM3G0M3f5vQj7LuJrETvjVot3Z5el9nffUtU=
 gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
+gopkg.in/yaml.v3 v3.0.0-20190905181640-827449938966/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
 gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo=
 gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
 gotest.tools v2.2.0+incompatible h1:VsBPFP1AI068pPrMxtb/S8Zkgf9xEmTLJjfM+P5UIEo=
@@ -1286,22 +1289,26 @@ honnef.co/go/tools v0.0.1-2019.2.3 h1:3JgtbtFHMiCmsznwGVTUWbgGov+pVqnlf1dEJTNAXe
 honnef.co/go/tools v0.0.1-2019.2.3/go.mod h1:a3bituU0lyd329TUQxRnasdCoJDkEUEAqEt0JzvZhAg=
 k8s.io/api v0.0.0-20190222213804-5cb15d344471/go.mod h1:iuAfoD4hCxJ8Onx9kaTIt30j7jUFS00AXQi6QMi99vA=
 k8s.io/api v0.17.0/go.mod h1:npsyOePkeP0CPwyGfXDHxvypiYMJxBWAMpQxCaJ4ZxI=
+k8s.io/api v0.18.2/go.mod h1:SJCWI7OLzhZSvbY7U8zwNl9UA4o1fizoug34OV/2r78=
 k8s.io/api v0.18.3/go.mod h1:UOaMwERbqJMfeeeHc8XJKawj4P9TgDRnViIqqBeH2QA=
 k8s.io/api v0.18.4/go.mod h1:lOIQAKYgai1+vz9J7YcDZwC26Z0zQewYOGWdyIPUUQ4=
 k8s.io/api v0.18.8/go.mod h1:d/CXqwWv+Z2XEG1LgceeDmHQwpUJhROPx16SlxJgERY=
 k8s.io/api v0.18.9 h1:7VDtivqwbvLOf8hmXSd/PDSSbpCBq49MELg84EYBYiQ=
 k8s.io/api v0.18.9/go.mod h1:9u/h6sUh6FxfErv7QqetX1EB3yBMIYOBXzdcf0Gf0rc=
+k8s.io/apiextensions-apiserver v0.18.2/go.mod h1:q3faSnRGmYimiocj6cHQ1I3WpLqmDgJFlKL37fC4ZvY=
 k8s.io/apiextensions-apiserver v0.18.4/go.mod h1:NYeyeYq4SIpFlPxSAB6jHPIdvu3hL0pc36wuRChybio=
 k8s.io/apiextensions-apiserver v0.18.8 h1:pkqYPKTHa0/3lYwH7201RpF9eFm0lmZDFBNzhN+k/sA=
 k8s.io/apiextensions-apiserver v0.18.8/go.mod h1:7f4ySEkkvifIr4+BRrRWriKKIJjPyg9mb/p63dJKnlM=
 k8s.io/apimachinery v0.0.0-20190221213512-86fb29eff628/go.mod h1:ccL7Eh7zubPUSh9A3USN90/OzHNSVN6zxzde07TDCL0=
 k8s.io/apimachinery v0.17.0/go.mod h1:b9qmWdKlLuU9EBh+06BtLcSf/Mu89rWL33naRxs1uZg=
+k8s.io/apimachinery v0.18.2/go.mod h1:9SnR/e11v5IbyPCGbvJViimtJ0SwHG4nfZFjU77ftcA=
 k8s.io/apimachinery v0.18.3/go.mod h1:OaXp26zu/5J7p0f92ASynJa1pZo06YlV9fG7BoWbCko=
 k8s.io/apimachinery v0.18.4/go.mod h1:OaXp26zu/5J7p0f92ASynJa1pZo06YlV9fG7BoWbCko=
 k8s.io/apimachinery v0.18.8/go.mod h1:6sQd+iHEqmOtALqOFjSWp2KZ9F0wlU/nWm0ZgsYWMig=
 k8s.io/apimachinery v0.18.9 h1:3ZABKQx3F3xPWlsGhCfUl8W+JXRRblV6Wo2A3zn0pvY=
 k8s.io/apimachinery v0.18.9/go.mod h1:PF5taHbXgTEJLU+xMypMmYTXTWPJ5LaW8bfsisxnEXk=
 k8s.io/apiserver v0.17.0/go.mod h1:ABM+9x/prjINN6iiffRVNCBR2Wk7uY4z+EtEGZD48cg=
+k8s.io/apiserver v0.18.2/go.mod h1:Xbh066NqrZO8cbsoenCwyDJ1OSi8Ag8I2lezeHxzwzw=
 k8s.io/apiserver v0.18.4/go.mod h1:q+zoFct5ABNnYkGIaGQ3bcbUNdmPyOCoEBcg51LChY8=
 k8s.io/apiserver v0.18.8/go.mod h1:12u5FuGql8Cc497ORNj79rhPdiXQC4bf53X/skR/1YM=
 k8s.io/cli-runtime v0.18.8/go.mod h1:7EzWiDbS9PFd0hamHHVoCY4GrokSTPSL32MA4rzIu0M=
@@ -1309,9 +1316,11 @@ k8s.io/client-go v0.18.9 h1:sPHX49yOtUqv1fl49TwV3f8cC0N3etSnwgFGsIsXnZc=
 k8s.io/client-go v0.18.9/go.mod h1:UjkEetDmr40P9NX0Ok3Idt08FCf2I4mIHgjFsot77uY=
 k8s.io/cloud-provider v0.17.0/go.mod h1:Ze4c3w2C0bRsjkBUoHpFi+qWe3ob1wI2/7cUn+YQIDE=
 k8s.io/code-generator v0.0.0-20191121015212-c4c8f8345c7e/go.mod h1:DVmfPQgxQENqDIzVR2ddLXMH34qeszkKSdH/N+s+38s=
+k8s.io/code-generator v0.18.2/go.mod h1:+UHX5rSbxmR8kzS+FAv7um6dtYrZokQvjHpDSYRVkTc=
 k8s.io/code-generator v0.18.4/go.mod h1:TgNEVx9hCyPGpdtCWA34olQYLkh3ok9ar7XfSsr8b6c=
 k8s.io/code-generator v0.18.8/go.mod h1:TgNEVx9hCyPGpdtCWA34olQYLkh3ok9ar7XfSsr8b6c=
 k8s.io/component-base v0.17.0/go.mod h1:rKuRAokNMY2nn2A6LP/MiwpoaMRHpfRnrPaUJJj1Yoc=
+k8s.io/component-base v0.18.2/go.mod h1:kqLlMuhJNHQ9lz8Z7V5bxUUtjFZnrypArGl58gmDfUM=
 k8s.io/component-base v0.18.4/go.mod h1:7jr/Ef5PGmKwQhyAz/pjByxJbC58mhKAhiaDu0vXfPk=
 k8s.io/component-base v0.18.8/go.mod h1:00frPRDas29rx58pPCxNkhUfPbwajlyyvu8ruNgSErU=
 k8s.io/csi-translation-lib v0.17.0/go.mod h1:HEF7MEz7pOLJCnxabi45IPkhSsE/KmxPQksuCrHKWls=
@@ -1325,6 +1334,7 @@ k8s.io/klog v1.0.0/go.mod h1:4Bi6QPql/J/LkTDqv7R/cd3hPo4k2DG6Ptcz060Ez5I=
 k8s.io/klog/v2 v2.0.0 h1:Foj74zO6RbjjP4hBEKjnYtjjAhGg4jNynUdYF6fJrok=
 k8s.io/klog/v2 v2.0.0/go.mod h1:PBfzABfn139FHAV07az/IF9Wp1bkk3vpT2XSJ76fSDE=
 k8s.io/kube-openapi v0.0.0-20191107075043-30be4d16710a/go.mod h1:1TqjTSzOxsLGIKfj0lK8EeCP7K1iUG65v09OM0/WG5E=
+k8s.io/kube-openapi v0.0.0-20200121204235-bf4fb3bd569c/go.mod h1:GRQhZsXIAJ1xR0C9bd8UpWHZ5plfAS9fzPjJuQ6JL3E=
 k8s.io/kube-openapi v0.0.0-20200410145947-61e04a5be9a6 h1:Oh3Mzx5pJ+yIumsAD0MOECPVeXsVot0UkiaCGVyfGQY=
 k8s.io/kube-openapi v0.0.0-20200410145947-61e04a5be9a6/go.mod h1:GRQhZsXIAJ1xR0C9bd8UpWHZ5plfAS9fzPjJuQ6JL3E=
 k8s.io/kubectl v0.18.8/go.mod h1:PlEgIAjOMua4hDFTEkVf+W5M0asHUKfE4y7VDZkpLHM=
@@ -1354,6 +1364,7 @@ rsc.io/binaryregexp v0.2.0/go.mod h1:qTv7/COck+e2FymRvadv62gMdZztPaShugOCi3I+8D8
 sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.0.7/go.mod h1:PHgbrJT7lCHcxMU+mDHEm+nx46H4zuuHZkDP6icnhu0=
 sigs.k8s.io/controller-runtime v0.6.1 h1:LcK2+nk0kmaOnKGN+vBcWHqY5WDJNJNB/c5pW+sU8fc=
 sigs.k8s.io/controller-runtime v0.6.1/go.mod h1:XRYBPdbf5XJu9kpS84VJiZ7h/u1hF3gEORz0efEja7A=
+sigs.k8s.io/controller-tools v0.3.0/go.mod h1:enhtKGfxZD1GFEoMgP8Fdbu+uKQ/cq1/WGJhdVChfvI=
 sigs.k8s.io/kustomize v2.0.3+incompatible/go.mod h1:MkjgH3RdOWrievjo6c9T245dYlB5QeXV4WCbnt/PEpU=
 sigs.k8s.io/structured-merge-diff v0.0.0-20190525122527-15d366b2352e/go.mod h1:wWxsB5ozmmv/SG7nM11ayaAW51xMvak/t1r0CSlcokI=
 sigs.k8s.io/structured-merge-diff v1.0.1-0.20191108220359-b1b620dd3f06 h1:zD2IemQ4LmOcAumeiyDWXKUI2SO0NYDe3H6QGvPOVgU=
diff --git a/pkg/plugins/resources/k8s/native/go.mod b/pkg/plugins/resources/k8s/native/go.mod
index d4daebce3..273ceff49 100644
--- a/pkg/plugins/resources/k8s/native/go.mod
+++ b/pkg/plugins/resources/k8s/native/go.mod
@@ -13,7 +13,6 @@ require (
 	k8s.io/apimachinery v0.18.9
 	k8s.io/client-go v0.18.9
 	sigs.k8s.io/controller-runtime v0.6.1
-	sigs.k8s.io/controller-tools v0.3.0 // indirect
 )
 
 replace github.com/kumahq/kuma/api => ../../../../../api
diff --git a/pkg/plugins/resources/k8s/native/go.sum b/pkg/plugins/resources/k8s/native/go.sum
index 32ecd030f..0dc17db43 100644
--- a/pkg/plugins/resources/k8s/native/go.sum
+++ b/pkg/plugins/resources/k8s/native/go.sum
@@ -74,7 +74,6 @@ github.com/evanphx/json-patch v4.2.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLi
 github.com/evanphx/json-patch v4.5.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk=
 github.com/evanphx/json-patch v4.9.0+incompatible h1:kLcOMZeuLAJvL2BPWLMIj5oaZQobrkAqrL+WFZwQses=
 github.com/evanphx/json-patch v4.9.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk=
-github.com/fatih/color v1.7.0 h1:DkWD4oS2D8LGGgTQ6IvwJJXSL5Vp2ffcQg58nFV38Ys=
 github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4=
 github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
 github.com/fsnotify/fsnotify v1.4.9 h1:hsms1Qyu0jgnwNXIxa+/V/PDsU6CfLf6CNO8H7IWoS4=
@@ -134,8 +133,6 @@ github.com/go-openapi/validate v0.18.0/go.mod h1:Uh4HdOzKt19xGIGm1qHf/ofbX1YQ4Y+
 github.com/go-openapi/validate v0.19.2/go.mod h1:1tRCw7m3jtI8eNWEEliiAqUIcBztB2KDnRCRMUi7GTA=
 github.com/go-openapi/validate v0.19.5/go.mod h1:8DJv2CVJQ6kGNpFW6eV9N3JviE1C85nY1c2z52x1Gk4=
 github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY=
-github.com/gobuffalo/flect v0.2.0 h1:EWCvMGGxOjsgwlWaP+f4+Hh6yrrte7JeFL2S6b+0hdM=
-github.com/gobuffalo/flect v0.2.0/go.mod h1:W3K3X9ksuZfir8f/LrfVtWmCDQFfayuylOJ7sz/Fj80=
 github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
 github.com/gogo/protobuf v1.2.1/go.mod h1:hp+jE20tsWTFYpLwKvXlhS1hjn+gTNwPg2I6zVXpSg4=
 github.com/gogo/protobuf v1.3.1 h1:DqDEcV5aeaTmdFBePNpYsp3FlcVH/2ISVVM9Qf8PSls=
@@ -195,7 +192,6 @@ github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpO
 github.com/imdario/mergo v0.3.5/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA=
 github.com/imdario/mergo v0.3.9 h1:UauaLniWCFHWd+Jp9oCEkTBj8VO/9DKg3PV3VCNMDIg=
 github.com/imdario/mergo v0.3.9/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA=
-github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM=
 github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8=
 github.com/jonboulle/clockwork v0.1.0/go.mod h1:Ii8DK3G1RaLaWxj9trq07+26W01tbo22gdxWY5EU2bo=
 github.com/json-iterator/go v1.1.6/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU=
@@ -224,11 +220,7 @@ github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN
 github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
 github.com/mailru/easyjson v0.7.0/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs=
 github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
-github.com/mattn/go-colorable v0.1.2 h1:/bC9yWikZXAL9uJdulbSfyVNIR3n3trXl+v8+1sx8mU=
-github.com/mattn/go-colorable v0.1.2/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE=
 github.com/mattn/go-isatty v0.0.4/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=
-github.com/mattn/go-isatty v0.0.8 h1:HLtExJ+uU2HOZ+wI0Tt5DtUDrx8yhUqDcp7fYERX4CE=
-github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s=
 github.com/mattn/go-runewidth v0.0.2/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU=
 github.com/matttproud/golang_protobuf_extensions v1.0.1 h1:4hp9jkHxhMHkqkrB3Ix0jegS5sx/RkqARlsWZ6pIwiU=
 github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0=
@@ -256,7 +248,6 @@ github.com/onsi/ginkgo v1.14.2/go.mod h1:iSB4RoI2tjJc9BBv4NKIKWKya62Rps+oPG/Lv9k
 github.com/onsi/gomega v0.0.0-20170829124025-dcabb60a477c/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA=
 github.com/onsi/gomega v1.7.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY=
 github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY=
-github.com/onsi/gomega v1.8.1/go.mod h1:Ho0h+IUsWyvy1OpqCwxlQ/21gkhVunqlU8fDGcoTdcA=
 github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo=
 github.com/onsi/gomega v1.10.3 h1:gph6h/qe9GSUw1NhH1gp+qb+h8rXD8Cy60Z32Qw3ELA=
 github.com/onsi/gomega v1.10.3/go.mod h1:V9xEwhxec5O8UDM77eCW8vLymOMltsqPVYWrpDsH8xc=
@@ -294,7 +285,6 @@ github.com/spf13/afero v1.1.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B
 github.com/spf13/afero v1.2.2/go.mod h1:9ZxEEn6pIJ8Rxe320qSDBk6AsU0r9pR7Q4OcevTdifk=
 github.com/spf13/cast v1.3.0/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE=
 github.com/spf13/cobra v0.0.3/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ=
-github.com/spf13/cobra v0.0.5 h1:f0B+LkLX6DtmRH1isoNA9VTtNUK9K8xYd28JNNfOv/s=
 github.com/spf13/cobra v0.0.5/go.mod h1:3K3wKZymM7VvHMDS9+Akkh4K60UwM26emMESw8tLCHU=
 github.com/spf13/jwalterweatherman v1.0.0/go.mod h1:cQK4TGJAtQXfYWX+Ddv3mKDzgVb68N+wFjFa4jdeBTo=
 github.com/spf13/pflag v0.0.0-20170130214245-9ff6c6923cff/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
@@ -384,7 +374,6 @@ golang.org/x/sys v0.0.0-20181116152217-5ac8a444bdc5/go.mod h1:STP8DvDyc/dI5b8T5h
 golang.org/x/sys v0.0.0-20181205085412-a5c9d58dba9a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/sys v0.0.0-20190209173611-3b5209105503/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
-golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/sys v0.0.0-20190321052220-f7bb7a8bee54/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
@@ -421,7 +410,6 @@ golang.org/x/tools v0.0.0-20190312170243-e65039ee4138/go.mod h1:LCzVGOaR6xXOjkQ3
 golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q=
 golang.org/x/tools v0.0.0-20190614205625-5aca471b1d59/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc=
 golang.org/x/tools v0.0.0-20190617190820-da514acc4774/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc=
-golang.org/x/tools v0.0.0-20190920225731-5eefd052ad72 h1:bw9doJza/SFBEweII/rHQh338oozWyiFsBRHtrflcws=
 golang.org/x/tools v0.0.0-20190920225731-5eefd052ad72/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
 golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
 golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4=
@@ -474,32 +462,23 @@ gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
 gopkg.in/yaml.v2 v2.2.8/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
 gopkg.in/yaml.v2 v2.3.0 h1:clyUAQHOM3G0M3f5vQj7LuJrETvjVot3Z5el9nffUtU=
 gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
-gopkg.in/yaml.v3 v3.0.0-20190905181640-827449938966 h1:B0J02caTR6tpSJozBJyiAzT6CtBzjclw4pgm9gg8Ys0=
-gopkg.in/yaml.v3 v3.0.0-20190905181640-827449938966/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
 gotest.tools v2.2.0+incompatible/go.mod h1:DsYFclhRJ6vuDpmuTbkuFWG+y2sxOXAzmJt81HFBacw=
 honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
 honnef.co/go/tools v0.0.0-20190106161140-3f1c8253044a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
 honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
-k8s.io/api v0.18.2/go.mod h1:SJCWI7OLzhZSvbY7U8zwNl9UA4o1fizoug34OV/2r78=
 k8s.io/api v0.18.4/go.mod h1:lOIQAKYgai1+vz9J7YcDZwC26Z0zQewYOGWdyIPUUQ4=
 k8s.io/api v0.18.9 h1:7VDtivqwbvLOf8hmXSd/PDSSbpCBq49MELg84EYBYiQ=
 k8s.io/api v0.18.9/go.mod h1:9u/h6sUh6FxfErv7QqetX1EB3yBMIYOBXzdcf0Gf0rc=
-k8s.io/apiextensions-apiserver v0.18.2/go.mod h1:q3faSnRGmYimiocj6cHQ1I3WpLqmDgJFlKL37fC4ZvY=
 k8s.io/apiextensions-apiserver v0.18.4 h1:Y3HGERmS8t9u12YNUFoOISqefaoGRuTc43AYCLzWmWE=
 k8s.io/apiextensions-apiserver v0.18.4/go.mod h1:NYeyeYq4SIpFlPxSAB6jHPIdvu3hL0pc36wuRChybio=
-k8s.io/apimachinery v0.18.2/go.mod h1:9SnR/e11v5IbyPCGbvJViimtJ0SwHG4nfZFjU77ftcA=
 k8s.io/apimachinery v0.18.4/go.mod h1:OaXp26zu/5J7p0f92ASynJa1pZo06YlV9fG7BoWbCko=
 k8s.io/apimachinery v0.18.9 h1:3ZABKQx3F3xPWlsGhCfUl8W+JXRRblV6Wo2A3zn0pvY=
 k8s.io/apimachinery v0.18.9/go.mod h1:PF5taHbXgTEJLU+xMypMmYTXTWPJ5LaW8bfsisxnEXk=
-k8s.io/apiserver v0.18.2/go.mod h1:Xbh066NqrZO8cbsoenCwyDJ1OSi8Ag8I2lezeHxzwzw=
 k8s.io/apiserver v0.18.4/go.mod h1:q+zoFct5ABNnYkGIaGQ3bcbUNdmPyOCoEBcg51LChY8=
-k8s.io/client-go v0.18.2/go.mod h1:Xcm5wVGXX9HAA2JJ2sSBUn3tCJ+4SVlCbl2MNNv+CIU=
 k8s.io/client-go v0.18.4/go.mod h1:f5sXwL4yAZRkAtzOxRWUhA/N8XzGCb+nPZI8PfobZ9g=
 k8s.io/client-go v0.18.9 h1:sPHX49yOtUqv1fl49TwV3f8cC0N3etSnwgFGsIsXnZc=
 k8s.io/client-go v0.18.9/go.mod h1:UjkEetDmr40P9NX0Ok3Idt08FCf2I4mIHgjFsot77uY=
-k8s.io/code-generator v0.18.2/go.mod h1:+UHX5rSbxmR8kzS+FAv7um6dtYrZokQvjHpDSYRVkTc=
 k8s.io/code-generator v0.18.4/go.mod h1:TgNEVx9hCyPGpdtCWA34olQYLkh3ok9ar7XfSsr8b6c=
-k8s.io/component-base v0.18.2/go.mod h1:kqLlMuhJNHQ9lz8Z7V5bxUUtjFZnrypArGl58gmDfUM=
 k8s.io/component-base v0.18.4/go.mod h1:7jr/Ef5PGmKwQhyAz/pjByxJbC58mhKAhiaDu0vXfPk=
 k8s.io/gengo v0.0.0-20190128074634-0689ccc1d7d6/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0=
 k8s.io/gengo v0.0.0-20200114144118-36b2048a9120/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0=
@@ -509,7 +488,6 @@ k8s.io/klog v1.0.0 h1:Pt+yjF5aB1xDSVbau4VsWe+dQNzA0qv1LlXdC2dF6Q8=
 k8s.io/klog v1.0.0/go.mod h1:4Bi6QPql/J/LkTDqv7R/cd3hPo4k2DG6Ptcz060Ez5I=
 k8s.io/klog/v2 v2.0.0 h1:Foj74zO6RbjjP4hBEKjnYtjjAhGg4jNynUdYF6fJrok=
 k8s.io/klog/v2 v2.0.0/go.mod h1:PBfzABfn139FHAV07az/IF9Wp1bkk3vpT2XSJ76fSDE=
-k8s.io/kube-openapi v0.0.0-20200121204235-bf4fb3bd569c/go.mod h1:GRQhZsXIAJ1xR0C9bd8UpWHZ5plfAS9fzPjJuQ6JL3E=
 k8s.io/kube-openapi v0.0.0-20200410145947-61e04a5be9a6 h1:Oh3Mzx5pJ+yIumsAD0MOECPVeXsVot0UkiaCGVyfGQY=
 k8s.io/kube-openapi v0.0.0-20200410145947-61e04a5be9a6/go.mod h1:GRQhZsXIAJ1xR0C9bd8UpWHZ5plfAS9fzPjJuQ6JL3E=
 k8s.io/utils v0.0.0-20200324210504-a9aa75ae1b89/go.mod h1:sZAwmy6armz5eXlNoLmJcl4F1QuKu7sr+mFQ0byX7Ew=
@@ -518,8 +496,6 @@ k8s.io/utils v0.0.0-20200603063816-c1c6865ac451/go.mod h1:jPW/WVKK9YHAvNhRxK0md/
 sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.0.7/go.mod h1:PHgbrJT7lCHcxMU+mDHEm+nx46H4zuuHZkDP6icnhu0=
 sigs.k8s.io/controller-runtime v0.6.1 h1:LcK2+nk0kmaOnKGN+vBcWHqY5WDJNJNB/c5pW+sU8fc=
 sigs.k8s.io/controller-runtime v0.6.1/go.mod h1:XRYBPdbf5XJu9kpS84VJiZ7h/u1hF3gEORz0efEja7A=
-sigs.k8s.io/controller-tools v0.3.0 h1:y3YD99XOyWaXkiF1kd41uRvfp/64teWcrEZFuHxPhJ4=
-sigs.k8s.io/controller-tools v0.3.0/go.mod h1:enhtKGfxZD1GFEoMgP8Fdbu+uKQ/cq1/WGJhdVChfvI=
 sigs.k8s.io/structured-merge-diff/v3 v3.0.0-20200116222232-67a7b8c61874/go.mod h1:PlARxl6Hbt/+BC80dRLi1qAmnMqwqDg62YvvVkZjemw=
 sigs.k8s.io/structured-merge-diff/v3 v3.0.0 h1:dOmIZBMfhcHS09XZkMyUgkq5trg3/jRyJYFZUiaOp8E=
 sigs.k8s.io/structured-merge-diff/v3 v3.0.0/go.mod h1:PlARxl6Hbt/+BC80dRLi1qAmnMqwqDg62YvvVkZjemw=
diff --git a/pkg/xds/bootstrap/generator.go b/pkg/xds/bootstrap/generator.go
index f779a883c..05ee08f5f 100644
--- a/pkg/xds/bootstrap/generator.go
+++ b/pkg/xds/bootstrap/generator.go
@@ -197,6 +197,12 @@ func (b *bootstrapGenerator) generateFor(proxyId core_xds.ProxyId, dataplane *co
 		DataplaneTokenPath: request.DataplaneTokenPath,
 		DataplaneResource:  request.DataplaneResource,
 		CertBytes:          certBytes,
+		KumaDpVersion:      request.Version.KumaDp.Version,
+		KumaDpGitTag:       request.Version.KumaDp.GitTag,
+		KumaDpGitCommit:    request.Version.KumaDp.GitCommit,
+		KumaDpBuildDate:    request.Version.KumaDp.BuildDate,
+		EnvoyVersion:       request.Version.Envoy.Version,
+		EnvoyBuild:         request.Version.Envoy.Build,
 	}
 	log.WithValues("params", params).Info("Generating bootstrap config")
 	return b.configForParameters(params)
diff --git a/pkg/xds/bootstrap/template.go b/pkg/xds/bootstrap/template.go
index 946b559dd..a4da6ff7f 100644
--- a/pkg/xds/bootstrap/template.go
+++ b/pkg/xds/bootstrap/template.go
@@ -15,6 +15,12 @@ type configParameters struct {
 	DataplaneTokenPath string
 	DataplaneResource  string
 	CertBytes          string
+	KumaDpVersion      string
+	KumaDpGitTag       string
+	KumaDpGitCommit    string
+	KumaDpBuildDate    string
+	EnvoyVersion       string
+	EnvoyBuild         string
 }
 
 const configTemplate string = `
@@ -31,6 +37,15 @@ node:
 {{if .AdminPort }}
     dataplane.admin.port: "{{ .AdminPort }}"
 {{ end }}
+    version:
+      kumaDp:
+        version: "{{ .KumaDpVersion }}"
+        gitTag: "{{ .KumaDpGitTag }}"
+        gitCommit: "{{ .KumaDpGitCommit }}"
+        buildDate: "{{ .KumaDpBuildDate }}"
+      envoy:
+        version: "{{ .EnvoyVersion }}"
+        build: "{{ .EnvoyBuild }}"
 
 {{if .AdminPort }}
 admin:
diff --git a/pkg/xds/bootstrap/types/bootstrap_request.go b/pkg/xds/bootstrap/types/bootstrap_request.go
index a1829f98b..c3d326a18 100644
--- a/pkg/xds/bootstrap/types/bootstrap_request.go
+++ b/pkg/xds/bootstrap/types/bootstrap_request.go
@@ -1,10 +1,28 @@
 package types
 
 type BootstrapRequest struct {
-	Mesh               string `json:"mesh"`
-	Name               string `json:"name"`
-	AdminPort          uint32 `json:"adminPort,omitempty"`
-	DataplaneTokenPath string `json:"dataplaneTokenPath,omitempty"`
-	DataplaneResource  string `json:"dataplaneResource,omitempty"`
-	Host               string `json:"-"`
+	Mesh               string  `json:"mesh"`
+	Name               string  `json:"name"`
+	AdminPort          uint32  `json:"adminPort,omitempty"`
+	DataplaneTokenPath string  `json:"dataplaneTokenPath,omitempty"`
+	DataplaneResource  string  `json:"dataplaneResource,omitempty"`
+	Host               string  `json:"-"`
+	Version            Version `json:"version"`
+}
+
+type Version struct {
+	KumaDp KumaDpVersion `json:"kumaDp"`
+	Envoy  EnvoyVersion  `json:"envoy"`
+}
+
+type KumaDpVersion struct {
+	Version   string `json:"version"`
+	GitTag    string `json:"gitTag"`
+	GitCommit string `json:"gitCommit"`
+	BuildDate string `json:"buildDate"`
+}
+
+type EnvoyVersion struct {
+	Version string `json:"version"`
+	Build   string `json:"build"`
 }
diff --git a/pkg/xds/server/dataplane_status_tracker.go b/pkg/xds/server/dataplane_status_tracker.go
index c3af7ed7f..ba5867fa4 100644
--- a/pkg/xds/server/dataplane_status_tracker.go
+++ b/pkg/xds/server/dataplane_status_tracker.go
@@ -5,6 +5,8 @@ import (
 	"sync"
 	"time"
 
+	pstruct "github.com/golang/protobuf/ptypes/struct"
+
 	envoy "github.com/envoyproxy/go-control-plane/envoy/api/v2"
 	envoy_xds "github.com/envoyproxy/go-control-plane/pkg/server/v2"
 	"github.com/golang/protobuf/proto"
@@ -71,6 +73,7 @@ func (c *dataplaneStatusTracker) OnStreamOpen(ctx context.Context, streamID int6
 		ControlPlaneInstanceId: c.runtimeInfo.GetInstanceId(),
 		ConnectTime:            util_proto.MustTimestampProto(now()),
 		Status:                 mesh_proto.NewSubscriptionStatus(),
+		Version:                mesh_proto.NewVersion(),
 	}
 	// initialize state per ADS stream
 	state := &streamState{
@@ -120,6 +123,9 @@ func (c *dataplaneStatusTracker) OnStreamRequest(streamID int64, req *envoy.Disc
 	if state.dataplaneId == (core_model.ResourceKey{}) {
 		if id, err := core_xds.ParseProxyId(req.Node); err == nil {
 			state.dataplaneId = core_model.ResourceKey{Mesh: id.Mesh, Name: id.Name}
+			if err := readVersion(req.Node.Metadata, state.subscription.Version); err != nil {
+				xdsServerLog.Error(err, "failed to extract version out of the Envoy metadata", "streamid", streamID, "metadata", req.Node.Metadata)
+			}
 			// kick off async Dataplane status flusher
 			go c.createStatusSink(state).Start(state.stop)
 		} else {
@@ -188,3 +194,14 @@ func (s *streamState) GetStatus() (core_model.ResourceKey, *mesh_proto.Discovery
 func (s *streamState) Close() {
 	close(s.stop)
 }
+
+func readVersion(metadata *pstruct.Struct, version *mesh_proto.Version) error {
+	rawVersion := metadata.Fields["version"].GetStructValue()
+	if rawVersion != nil {
+		err := util_proto.ToTyped(rawVersion, version)
+		if err != nil {
+			return err
+		}
+	}
+	return nil
+}


Test patch:
diff --git a/app/kuma-dp/cmd/run_test.go b/app/kuma-dp/cmd/run_test.go
index 75098fccf..cb9a54e28 100644
--- a/app/kuma-dp/cmd/run_test.go
+++ b/app/kuma-dp/cmd/run_test.go
@@ -36,7 +36,7 @@ var _ = Describe("run", func() {
 	BeforeEach(func() {
 		backupSetupSignalHandler = core.SetupSignalHandler
 		backupBootstrapGenerator = bootstrapGenerator
-		bootstrapGenerator = func(_ string, cfg kumadp.Config, _ *rest.Resource) (proto.Message, error) {
+		bootstrapGenerator = func(_ string, cfg kumadp.Config, _ *rest.Resource, version envoy.EnvoyVersion) (proto.Message, error) {
 			bootstrap := envoy_bootstrap.Bootstrap{}
 			respBytes, err := ioutil.ReadFile(filepath.Join("testdata", "bootstrap-config.golden.yaml"))
 			Expect(err).ToNot(HaveOccurred())
@@ -152,13 +152,14 @@ var _ = Describe("run", func() {
 			Expect(err).ToNot(HaveOccurred())
 			// and
 			actualArgs := strings.Split(string(cmdline), "\n")
-			Expect(actualArgs[0]).To(Equal("-c"))
-			actualConfigFile := actualArgs[1]
+			Expect(actualArgs[0]).To(Equal("--version"))
+			Expect(actualArgs[1]).To(Equal("-c"))
+			actualConfigFile := actualArgs[2]
 			Expect(actualConfigFile).To(BeARegularFile())
 
 			// then
 			if given.expectedFile != "" {
-				Expect(actualArgs[1]).To(Equal(given.expectedFile))
+				Expect(actualArgs[2]).To(Equal(given.expectedFile))
 			}
 
 			// when
diff --git a/app/kuma-dp/cmd/testdata/envoy-mock.sleep.sh b/app/kuma-dp/cmd/testdata/envoy-mock.sleep.sh
index eca65192c..208bf00b7 100755
--- a/app/kuma-dp/cmd/testdata/envoy-mock.sleep.sh
+++ b/app/kuma-dp/cmd/testdata/envoy-mock.sleep.sh
@@ -1,9 +1,19 @@
 #!/bin/sh
 
-touch ${ENVOY_MOCK_CMDLINE_FILE}
-for arg in "$@"; do
-    echo $arg >> ${ENVOY_MOCK_CMDLINE_FILE}
-done
+if [ ! -e ${ENVOY_MOCK_CMDLINE_FILE} ]; then
+    touch ${ENVOY_MOCK_CMDLINE_FILE}
+fi
+
+if [ "$1" = "--version" ];
+then
+    echo $1 >> ${ENVOY_MOCK_CMDLINE_FILE}
+    printf "\n50ef0945fa2c5da4bff7627c3abf41fdd3b7cffd/1.15.0/clean-getenvoy-2aa564b-envoy/RELEASE/BoringSSL\n"
+    exit 0
+else
+    for arg in "$@"; do
+        echo $arg >> ${ENVOY_MOCK_CMDLINE_FILE}
+    done
+fi
 
 echo $$ >${ENVOY_MOCK_PID_FILE}
 
diff --git a/app/kuma-dp/pkg/dataplane/envoy/envoy_test.go b/app/kuma-dp/pkg/dataplane/envoy/envoy_test.go
index a5b68d047..f48d4af5f 100644
--- a/app/kuma-dp/pkg/dataplane/envoy/envoy_test.go
+++ b/app/kuma-dp/pkg/dataplane/envoy/envoy_test.go
@@ -73,7 +73,7 @@ var _ = Describe("Envoy", func() {
 					ConfigDir:  configDir,
 				},
 			}
-			sampleConfig := func(string, kuma_dp.Config, *rest.Resource) (proto.Message, error) {
+			sampleConfig := func(string, kuma_dp.Config, *rest.Resource, EnvoyVersion) (proto.Message, error) {
 				return &envoy_bootstrap.Bootstrap{
 					Node: &envoy_core.Node{
 						Id: "example",
@@ -144,7 +144,7 @@ var _ = Describe("Envoy", func() {
 					ConfigDir:  configDir,
 				},
 			}
-			sampleConfig := func(string, kuma_dp.Config, *rest.Resource) (proto.Message, error) {
+			sampleConfig := func(string, kuma_dp.Config, *rest.Resource, EnvoyVersion) (proto.Message, error) {
 				return &envoy_bootstrap.Bootstrap{}, nil
 			}
 
@@ -186,7 +186,7 @@ var _ = Describe("Envoy", func() {
 					ConfigDir:  configDir,
 				},
 			}
-			sampleConfig := func(string, kuma_dp.Config, *rest.Resource) (proto.Message, error) {
+			sampleConfig := func(string, kuma_dp.Config, *rest.Resource, EnvoyVersion) (proto.Message, error) {
 				return &envoy_bootstrap.Bootstrap{}, nil
 			}
 
@@ -207,4 +207,30 @@ var _ = Describe("Envoy", func() {
 			close(done)
 		}, 10)
 	})
+
+	Describe("Parse version", func() {
+		It("should properly read envoy version", func() {
+			// given
+			cfg := kuma_dp.Config{
+				DataplaneRuntime: kuma_dp.DataplaneRuntime{
+					BinaryPath: filepath.Join("testdata", "envoy-mock.exit-0.sh"),
+					ConfigDir:  configDir,
+				},
+			}
+
+			// when
+			dataplane, err := New(Opts{
+				Config: cfg,
+				Stdout: &bytes.Buffer{},
+				Stderr: &bytes.Buffer{},
+			})
+			Expect(err).ToNot(HaveOccurred())
+			version, err := dataplane.version()
+
+			// then
+			Expect(err).ToNot(HaveOccurred())
+			Expect(version.Version).To(Equal("1.15.0"))
+			Expect(version.Build).To(Equal("50ef0945fa2c5da4bff7627c3abf41fdd3b7cffd/1.15.0/clean-getenvoy-2aa564b-envoy/RELEASE/BoringSSL"))
+		})
+	})
 })
diff --git a/app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap_test.go b/app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap_test.go
index 1c9cbbd9b..065150c98 100644
--- a/app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap_test.go
+++ b/app/kuma-dp/pkg/dataplane/envoy/remote_bootstrap_test.go
@@ -10,6 +10,8 @@ import (
 	"strings"
 	"time"
 
+	kuma_version "github.com/kumahq/kuma/pkg/version"
+
 	. "github.com/onsi/ginkgo"
 	. "github.com/onsi/ginkgo/extensions/table"
 	. "github.com/onsi/gomega"
@@ -28,6 +30,15 @@ var _ = Describe("Remote Bootstrap", func() {
 		expectedBootstrapRequest string
 	}
 
+	BeforeEach(func() {
+		kuma_version.Build = kuma_version.BuildInfo{
+			Version:   "0.0.1",
+			GitTag:    "v0.0.1",
+			GitCommit: "91ce236824a9d875601679aa80c63783fb0e8725",
+			BuildDate: "2019-08-07T11:26:06Z",
+		}
+	})
+
 	DescribeTable("should generate bootstrap configuration", func(given testCase) {
 		// given
 		mux := http.NewServeMux()
@@ -51,7 +62,10 @@ var _ = Describe("Remote Bootstrap", func() {
 		generator := NewRemoteBootstrapGenerator(http.DefaultClient)
 
 		// when
-		config, err := generator(fmt.Sprintf("http://localhost:%d", port), given.config, given.dataplane)
+		config, err := generator(fmt.Sprintf("http://localhost:%d", port), given.config, given.dataplane, EnvoyVersion{
+			Build:   "hash/1.15.0/RELEASE",
+			Version: "1.15.0",
+		})
 
 		// then
 		Expect(err).ToNot(HaveOccurred())
@@ -75,14 +89,25 @@ var _ = Describe("Remote Bootstrap", func() {
 						},
 					},
 					expectedBootstrapRequest: `
-                    {
-                      "mesh": "demo",
-                      "name": "sample",
-                      "adminPort": 4321,
-                      "dataplaneTokenPath": "/tmp/token",
-                      "dataplaneResource": "{\"type\":\"Dataplane\",\"mesh\":\"demo\",\"name\":\"sample\",\"creationTime\":\"0001-01-01T00:00:00Z\",\"modificationTime\":\"0001-01-01T00:00:00Z\"}"
-                    }
-`,
+					{
+					  "mesh": "demo",
+					  "name": "sample",
+					  "adminPort": 4321,
+					  "dataplaneTokenPath": "/tmp/token",
+					  "dataplaneResource": "{\"type\":\"Dataplane\",\"mesh\":\"demo\",\"name\":\"sample\",\"creationTime\":\"0001-01-01T00:00:00Z\",\"modificationTime\":\"0001-01-01T00:00:00Z\"}",
+					  "version": {
+						"kumaDp": {
+						  "version": "0.0.1",
+						  "gitTag": "v0.0.1",
+						  "gitCommit": "91ce236824a9d875601679aa80c63783fb0e8725",
+						  "buildDate": "2019-08-07T11:26:06Z"
+						},
+						"envoy": {
+						  "version": "1.15.0",
+						  "build": "hash/1.15.0/RELEASE"
+						}
+					  }
+					}`,
 				}
 			}()),
 
@@ -109,9 +134,20 @@ var _ = Describe("Remote Bootstrap", func() {
                       "name": "sample",
                       "adminPort": 4321,
                       "dataplaneTokenPath": "/tmp/token",
-                      "dataplaneResource": "{\"type\":\"Dataplane\",\"mesh\":\"demo\",\"name\":\"sample\",\"creationTime\":\"0001-01-01T00:00:00Z\",\"modificationTime\":\"0001-01-01T00:00:00Z\"}"
-                    }
-`,
+                      "dataplaneResource": "{\"type\":\"Dataplane\",\"mesh\":\"demo\",\"name\":\"sample\",\"creationTime\":\"0001-01-01T00:00:00Z\",\"modificationTime\":\"0001-01-01T00:00:00Z\"}",
+                      "version": {
+                        "kumaDp": {
+                          "version": "0.0.1",
+                          "gitTag": "v0.0.1",
+                          "gitCommit": "91ce236824a9d875601679aa80c63783fb0e8725",
+                          "buildDate": "2019-08-07T11:26:06Z"
+                        },
+                        "envoy": {
+                          "version": "1.15.0",
+                          "build": "hash/1.15.0/RELEASE"
+                        }
+                      }
+                    }`,
 				}
 			}()),
 		Entry("should support empty port range",
@@ -136,9 +172,20 @@ var _ = Describe("Remote Bootstrap", func() {
                       "mesh": "demo",
                       "name": "sample",
                       "dataplaneTokenPath": "/tmp/token",
-                      "dataplaneResource": "{\"type\":\"Dataplane\",\"mesh\":\"demo\",\"name\":\"sample\",\"creationTime\":\"0001-01-01T00:00:00Z\",\"modificationTime\":\"0001-01-01T00:00:00Z\"}"
-                    }
-`,
+                      "dataplaneResource": "{\"type\":\"Dataplane\",\"mesh\":\"demo\",\"name\":\"sample\",\"creationTime\":\"0001-01-01T00:00:00Z\",\"modificationTime\":\"0001-01-01T00:00:00Z\"}",
+                      "version": {
+                        "kumaDp": {
+                          "version": "0.0.1",
+                          "gitTag": "v0.0.1",
+                          "gitCommit": "91ce236824a9d875601679aa80c63783fb0e8725",
+                          "buildDate": "2019-08-07T11:26:06Z"
+                        },
+                        "envoy": {
+                          "version": "1.15.0",
+                          "build": "hash/1.15.0/RELEASE"
+                        }
+                      }
+                    }`,
 				}
 			}()),
 	)
@@ -176,7 +223,7 @@ var _ = Describe("Remote Bootstrap", func() {
 				Mesh: "default",
 				Name: "dp-1",
 			},
-		})
+		}, EnvoyVersion{})
 
 		// then
 		Expect(err).ToNot(HaveOccurred())
@@ -204,7 +251,7 @@ var _ = Describe("Remote Bootstrap", func() {
 		config.ControlPlane.Retry.MaxDuration = 100 * time.Millisecond
 		_, err = generator(fmt.Sprintf("http://localhost:%d", port), config, &rest.Resource{
 			Meta: rest.ResourceMeta{Mesh: "default", Name: "dp-1"},
-		})
+		}, EnvoyVersion{})
 
 		// then
 		Expect(err).To(MatchError("retryable: Dataplane entity not found. If you are running on Universal please create a Dataplane entity on kuma-cp before starting kuma-dp. If you are running on Kubernetes, please check the kuma-cp logs to determine why the Dataplane entity could not be created by the automatic sidecar injection."))
diff --git a/app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-0.sh b/app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-0.sh
index 238f1bd8d..52a969318 100755
--- a/app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-0.sh
+++ b/app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-0.sh
@@ -1,4 +1,10 @@
 #!/bin/sh
 
+if [ "$1" = "--version" ];
+then
+  printf "\nenvoy  version: 50ef0945fa2c5da4bff7627c3abf41fdd3b7cffd/1.15.0/clean-getenvoy-2aa564b-envoy/RELEASE/BoringSSL\n\n"
+  exit 0
+fi
+
 # print arguments to verify in the test
 echo $@
diff --git a/app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-1.sh b/app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-1.sh
index ed6febbe9..bf21a5259 100755
--- a/app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-1.sh
+++ b/app/kuma-dp/pkg/dataplane/envoy/testdata/envoy-mock.exit-1.sh
@@ -1,5 +1,11 @@
 #!/bin/sh
 
+if [ "$1" = "--version" ];
+then
+  printf "\nenvoy  version: 50ef0945fa2c5da4bff7627c3abf41fdd3b7cffd/1.15.0/clean-getenvoy-2aa564b-envoy/RELEASE/BoringSSL\n\n"
+  exit 0
+fi
+
 >&2 echo Envoy crashed
 
 # simulate crash of Envoy process
diff --git a/pkg/xds/bootstrap/generator_test.go b/pkg/xds/bootstrap/generator_test.go
index 6b257e85d..53f55a022 100644
--- a/pkg/xds/bootstrap/generator_test.go
+++ b/pkg/xds/bootstrap/generator_test.go
@@ -29,6 +29,19 @@ var _ = Describe("bootstrapGenerator", func() {
 
 	var resManager core_manager.ResourceManager
 
+	defaultVersion := types.Version{
+		KumaDp: types.KumaDpVersion{
+			Version:   "0.0.1",
+			GitTag:    "v0.0.1",
+			GitCommit: "91ce236824a9d875601679aa80c63783fb0e8725",
+			BuildDate: "2019-08-07T11:26:06Z",
+		},
+		Envoy: types.EnvoyVersion{
+			Build:   "hash/1.15.0/RELEASE",
+			Version: "1.15.0",
+		},
+	}
+
 	BeforeEach(func() {
 		resManager = core_manager.NewResourceManager(memory.NewStore())
 		core.Now = func() time.Time {
@@ -106,8 +119,9 @@ var _ = Describe("bootstrapGenerator", func() {
 				return cfg
 			},
 			request: types.BootstrapRequest{
-				Mesh: "mesh",
-				Name: "name.namespace",
+				Mesh:    "mesh",
+				Name:    "name.namespace",
+				Version: defaultVersion,
 			},
 			expectedConfigFile: "generator.default-config-minimal-request.golden.yaml",
 		}),
@@ -124,6 +138,7 @@ var _ = Describe("bootstrapGenerator", func() {
 				Name:               "name.namespace",
 				AdminPort:          1234,
 				DataplaneTokenPath: "/tmp/token",
+				Version:            defaultVersion,
 			},
 			expectedConfigFile: "generator.default-config.golden.yaml",
 		}),
@@ -140,8 +155,9 @@ var _ = Describe("bootstrapGenerator", func() {
 				}
 			},
 			request: types.BootstrapRequest{
-				Mesh: "mesh",
-				Name: "name.namespace",
+				Mesh:    "mesh",
+				Name:    "name.namespace",
+				Version: defaultVersion,
 			},
 			expectedConfigFile: "generator.custom-config-minimal-request.golden.yaml",
 		}),
@@ -183,6 +199,7 @@ var _ = Describe("bootstrapGenerator", func() {
     ]
   }
 }`,
+				Version: defaultVersion,
 			},
 			expectedConfigFile: "generator.custom-config.golden.yaml",
 		}),
diff --git a/pkg/xds/bootstrap/server_test.go b/pkg/xds/bootstrap/server_test.go
index bd1c98c42..aad81b9d2 100644
--- a/pkg/xds/bootstrap/server_test.go
+++ b/pkg/xds/bootstrap/server_test.go
@@ -3,6 +3,7 @@ package bootstrap_test
 import (
 	"context"
 	"crypto/tls"
+	"fmt"
 	"io/ioutil"
 	"net/http"
 	"path/filepath"
@@ -38,6 +39,20 @@ var _ = Describe("Bootstrap Server", func() {
 	var baseUrl string
 	var metrics core_metrics.Metrics
 
+	version := `
+	"version": {
+	  "kumaDp": {
+	    "version": "0.0.1",
+	    "gitTag": "v0.0.1",
+	    "gitCommit": "91ce236824a9d875601679aa80c63783fb0e8725",
+	    "buildDate": "2019-08-07T11:26:06Z"
+	  },
+	  "envoy": {
+	    "version": "1.15.0",
+	    "build": "hash/1.15.0/RELEASE"
+	  }
+	}`
+
 	httpClient := &http.Client{
 		Transport: &http.Transport{TLSClientConfig: &tls.Config{InsecureSkipVerify: true}},
 	}
@@ -142,17 +157,17 @@ var _ = Describe("Bootstrap Server", func() {
 		},
 		Entry("minimal data provided (universal)", testCase{
 			dataplaneName:      "dp-1",
-			body:               `{ "mesh": "default", "name": "dp-1", "dataplaneTokenPath": "/tmp/token" }`,
+			body:               fmt.Sprintf(`{ "mesh": "default", "name": "dp-1", "dataplaneTokenPath": "/tmp/token", %s }`, version),
 			expectedConfigFile: "bootstrap.universal.golden.yaml",
 		}),
 		Entry("minimal data provided (k8s)", testCase{
 			dataplaneName:      "dp-1.default",
-			body:               `{ "mesh": "default", "name": "dp-1.default", "dataplaneTokenPath": "/tmp/token" }`,
+			body:               fmt.Sprintf(`{ "mesh": "default", "name": "dp-1.default", "dataplaneTokenPath": "/tmp/token", %s }`, version),
 			expectedConfigFile: "bootstrap.k8s.golden.yaml",
 		}),
 		Entry("full data provided", testCase{
 			dataplaneName:      "dp-1.default",
-			body:               `{ "mesh": "default", "name": "dp-1.default", "adminPort": 1234, "dataplaneTokenPath": "/tmp/token" }`,
+			body:               fmt.Sprintf(`{ "mesh": "default", "name": "dp-1.default", "adminPort": 1234, "dataplaneTokenPath": "/tmp/token", %s }`, version),
 			expectedConfigFile: "bootstrap.overridden.golden.yaml",
 		}),
 	)
diff --git a/pkg/xds/bootstrap/testdata/bootstrap.k8s.golden.yaml b/pkg/xds/bootstrap/testdata/bootstrap.k8s.golden.yaml
index 64414a480..da6dfcc34 100644
--- a/pkg/xds/bootstrap/testdata/bootstrap.k8s.golden.yaml
+++ b/pkg/xds/bootstrap/testdata/bootstrap.k8s.golden.yaml
@@ -26,6 +26,15 @@ node:
   id: default.dp-1.default
   metadata:
     dataplaneTokenPath: /tmp/token
+    version:
+      kumaDp:
+        version: 0.0.1
+        gitTag: v0.0.1
+        gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+        buildDate: 2019-08-07T11:26:06Z
+      envoy:
+        version: 1.15.0
+        build: hash/1.15.0/RELEASE
 staticResources:
   clusters:
     - connectTimeout: 1s
diff --git a/pkg/xds/bootstrap/testdata/bootstrap.overridden.golden.yaml b/pkg/xds/bootstrap/testdata/bootstrap.overridden.golden.yaml
index a1202c8f8..81c676046 100644
--- a/pkg/xds/bootstrap/testdata/bootstrap.overridden.golden.yaml
+++ b/pkg/xds/bootstrap/testdata/bootstrap.overridden.golden.yaml
@@ -33,6 +33,15 @@ node:
   metadata:
     dataplane.admin.port: "1234"
     dataplaneTokenPath: /tmp/token
+    version:
+      kumaDp:
+        version: 0.0.1
+        gitTag: v0.0.1
+        gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+        buildDate: 2019-08-07T11:26:06Z
+      envoy:
+        version: 1.15.0
+        build: hash/1.15.0/RELEASE
 staticResources:
   clusters:
     - connectTimeout: 1s
diff --git a/pkg/xds/bootstrap/testdata/bootstrap.universal.golden.yaml b/pkg/xds/bootstrap/testdata/bootstrap.universal.golden.yaml
index e7e788e80..83c8fe19d 100644
--- a/pkg/xds/bootstrap/testdata/bootstrap.universal.golden.yaml
+++ b/pkg/xds/bootstrap/testdata/bootstrap.universal.golden.yaml
@@ -26,6 +26,15 @@ node:
   id: default.dp-1
   metadata:
     dataplaneTokenPath: /tmp/token
+    version:
+      kumaDp:
+        version: 0.0.1
+        gitTag: v0.0.1
+        gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+        buildDate: 2019-08-07T11:26:06Z
+      envoy:
+        version: 1.15.0
+        build: hash/1.15.0/RELEASE
 staticResources:
   clusters:
     - connectTimeout: 1s
diff --git a/pkg/xds/bootstrap/testdata/generator.custom-config-minimal-request.golden.yaml b/pkg/xds/bootstrap/testdata/generator.custom-config-minimal-request.golden.yaml
index b3864710d..7dc9299c6 100644
--- a/pkg/xds/bootstrap/testdata/generator.custom-config-minimal-request.golden.yaml
+++ b/pkg/xds/bootstrap/testdata/generator.custom-config-minimal-request.golden.yaml
@@ -24,6 +24,15 @@ node:
   id: mesh.name.namespace
   metadata:
     dataplane.admin.port: "9902"
+    version:
+      kumaDp:
+        version: 0.0.1
+        gitTag: v0.0.1
+        gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+        buildDate: 2019-08-07T11:26:06Z
+      envoy:
+        version: 1.15.0
+        build: hash/1.15.0/RELEASE
 staticResources:
   clusters:
     - connectTimeout: 2s
diff --git a/pkg/xds/bootstrap/testdata/generator.custom-config.golden.yaml b/pkg/xds/bootstrap/testdata/generator.custom-config.golden.yaml
index 297b0f883..42c37570b 100644
--- a/pkg/xds/bootstrap/testdata/generator.custom-config.golden.yaml
+++ b/pkg/xds/bootstrap/testdata/generator.custom-config.golden.yaml
@@ -34,6 +34,15 @@ node:
     dataplane.admin.port: "1234"
     dataplane.resource: ' { "type": "Dataplane", "mesh": "mesh", "name": "name.namespace", "creationTime": "1970-01-01T00:00:00Z", "modificationTime": "1970-01-01T00:00:00Z", "networking": { "address": "127.0.0.1", "inbound": [ { "port": 22022, "servicePort": 8443, "tags": { "kuma.io/protocol": "http2", "kuma.io/service": "backend" } }, ] } }'
     dataplaneTokenPath: /tmp/token
+    version:
+      kumaDp:
+        version: 0.0.1
+        gitTag: v0.0.1
+        gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+        buildDate: 2019-08-07T11:26:06Z
+      envoy:
+        version: 1.15.0
+        build: hash/1.15.0/RELEASE
 staticResources:
   clusters:
     - connectTimeout: 2s
diff --git a/pkg/xds/bootstrap/testdata/generator.default-config-minimal-request.golden.yaml b/pkg/xds/bootstrap/testdata/generator.default-config-minimal-request.golden.yaml
index 61064d539..5395f3bfe 100644
--- a/pkg/xds/bootstrap/testdata/generator.default-config-minimal-request.golden.yaml
+++ b/pkg/xds/bootstrap/testdata/generator.default-config-minimal-request.golden.yaml
@@ -16,6 +16,16 @@ dynamicResources:
 node:
   cluster: backend
   id: mesh.name.namespace
+  metadata:
+    version:
+      kumaDp:
+        version: 0.0.1
+        gitTag: v0.0.1
+        gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+        buildDate: 2019-08-07T11:26:06Z
+      envoy:
+        version: 1.15.0
+        build: hash/1.15.0/RELEASE
 staticResources:
   clusters:
     - connectTimeout: 1s
diff --git a/pkg/xds/bootstrap/testdata/generator.default-config.golden.yaml b/pkg/xds/bootstrap/testdata/generator.default-config.golden.yaml
index c1e4ccbde..23ab19ef6 100644
--- a/pkg/xds/bootstrap/testdata/generator.default-config.golden.yaml
+++ b/pkg/xds/bootstrap/testdata/generator.default-config.golden.yaml
@@ -33,6 +33,15 @@ node:
   metadata:
     dataplane.admin.port: "1234"
     dataplaneTokenPath: /tmp/token
+    version:
+      kumaDp:
+        version: 0.0.1
+        gitTag: v0.0.1
+        gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+        buildDate: 2019-08-07T11:26:06Z
+      envoy:
+        version: 1.15.0
+        build: hash/1.15.0/RELEASE
 staticResources:
   clusters:
     - connectTimeout: 1s
diff --git a/pkg/xds/server/dataplane_status_tracker_test.go b/pkg/xds/server/dataplane_status_tracker_test.go
index 370b40ebe..e5350ca79 100644
--- a/pkg/xds/server/dataplane_status_tracker_test.go
+++ b/pkg/xds/server/dataplane_status_tracker_test.go
@@ -4,6 +4,10 @@ import (
 	"context"
 	"time"
 
+	pstruct "github.com/golang/protobuf/ptypes/struct"
+
+	mesh_proto "github.com/kumahq/kuma/api/mesh/v1alpha1"
+
 	. "github.com/onsi/ginkgo"
 	. "github.com/onsi/ginkgo/extensions/table"
 	. "github.com/onsi/gomega"
@@ -89,6 +93,9 @@ var _ = Describe("DataplaneStatusTracker", func() {
               lds: {}
               rds: {}
               total: {}
+            version:
+              dpVersion: {}
+              envoy: {}
 `))
 
 		By("simulating end of ADS subscription")
@@ -111,6 +118,9 @@ var _ = Describe("DataplaneStatusTracker", func() {
               lds: {}
               rds: {}
               total: {}
+            version:
+              dpVersion: {}
+              envoy: {}
 `))
 	})
 
@@ -153,6 +163,9 @@ var _ = Describe("DataplaneStatusTracker", func() {
           lds: {}
           rds: {}
           total: {}
+        version:
+          dpVersion: {}
+          envoy: {}
 `))
 	})
 
@@ -167,6 +180,18 @@ var _ = Describe("DataplaneStatusTracker", func() {
 		func(given testCase) {
 			// given
 			streamID := int64(1)
+			version := util_proto.MustToStruct(&mesh_proto.Version{
+				DpVersion: &mesh_proto.KumaDpVersion{
+					Version:   "0.0.1",
+					GitTag:    "v0.0.1",
+					GitCommit: "91ce236824a9d875601679aa80c63783fb0e8725",
+					BuildDate: "2019-08-07T11:26:06Z",
+				},
+				Envoy: &mesh_proto.EnvoyVersion{
+					Version: "1.15.0",
+					Build:   "hash/1.15.0/RELEASE",
+				},
+			})
 
 			By("simulating start of subscription")
 			// when
@@ -184,6 +209,20 @@ var _ = Describe("DataplaneStatusTracker", func() {
 			discoveryRequest := &envoy.DiscoveryRequest{
 				Node: &envoy_core.Node{
 					Id: "default.example-001",
+					Metadata: &pstruct.Struct{
+						Fields: map[string]*pstruct.Value{
+							"dataplaneTokenPath": {
+								Kind: &pstruct.Value_StringValue{
+									StringValue: "/tmp/token",
+								},
+							},
+							"version": {
+								Kind: &pstruct.Value_StructValue{
+									StructValue: version,
+								},
+							},
+						},
+					},
 				},
 				TypeUrl: given.TypeUrl,
 			}
@@ -209,6 +248,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
           lds: {}
           rds: {}
           total: {}
+        version:
+          dpVersion:
+            buildDate: "2019-08-07T11:26:06Z"
+            gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+            gitTag: v0.0.1
+            version: 0.0.1
+          envoy:
+            build: hash/1.15.0/RELEASE
+            version: 1.15.0
 `))
 
 			By("simulating initial xDS response")
@@ -285,6 +333,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
               rds: {}
               total:
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 			ExpectedStatsAfterACK: `
             connectTime: "2019-07-01T00:00:00Z"
@@ -301,6 +358,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
               total:
                 responsesAcknowledged: "1"
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 			ExpectedStatsAfterNACK: `
             connectTime: "2019-07-01T00:00:00Z"
@@ -319,6 +385,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
                 responsesAcknowledged: "1"
                 responsesRejected: "1"
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 		}),
 		Entry("should properly handle RDS flow", testCase{
@@ -336,6 +411,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
                 responsesSent: "1"
               total:
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 			ExpectedStatsAfterACK: `
             connectTime: "2019-07-01T00:00:00Z"
@@ -352,6 +436,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
               total:
                 responsesAcknowledged: "1"
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 			ExpectedStatsAfterNACK: `
             connectTime: "2019-07-01T00:00:00Z"
@@ -370,6 +463,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
                 responsesAcknowledged: "1"
                 responsesRejected: "1"
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 		}),
 		Entry("should properly handle CDS flow", testCase{
@@ -387,6 +489,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
               rds: {}
               total:
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 			ExpectedStatsAfterACK: `
             connectTime: "2019-07-01T00:00:00Z"
@@ -403,6 +514,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
               total:
                 responsesAcknowledged: "1"
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 			ExpectedStatsAfterNACK: `
             connectTime: "2019-07-01T00:00:00Z"
@@ -421,6 +541,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
                 responsesAcknowledged: "1"
                 responsesRejected: "1"
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 		}),
 		Entry("should properly handle EDS flow", testCase{
@@ -438,6 +567,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
               rds: {}
               total:
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 			ExpectedStatsAfterACK: `
             connectTime: "2019-07-01T00:00:00Z"
@@ -454,6 +592,15 @@ var _ = Describe("DataplaneStatusTracker", func() {
               total:
                 responsesAcknowledged: "1"
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 			ExpectedStatsAfterNACK: `
             connectTime: "2019-07-01T00:00:00Z"
@@ -472,9 +619,62 @@ var _ = Describe("DataplaneStatusTracker", func() {
                 responsesAcknowledged: "1"
                 responsesRejected: "1"
                 responsesSent: "1"
+            version:
+              dpVersion:
+                buildDate: "2019-08-07T11:26:06Z"
+                gitCommit: 91ce236824a9d875601679aa80c63783fb0e8725
+                gitTag: v0.0.1
+                version: 0.0.1
+              envoy:
+                build: hash/1.15.0/RELEASE
+                version: 1.15.0
 `,
 		}),
 	)
+
+	type versionTestCase struct {
+		version *pstruct.Value
+	}
+
+	DescribeTable("should read node.metadata without error",
+		func(given versionTestCase) {
+			// given
+			version := mesh_proto.NewVersion()
+			node := &envoy_core.Node{
+				Metadata: &pstruct.Struct{
+					Fields: map[string]*pstruct.Value{
+						"dataplaneTokenPath": {
+							Kind: &pstruct.Value_StringValue{
+								StringValue: "/tmp/token",
+							},
+						},
+						"version": given.version,
+					},
+				},
+			}
+
+			// when
+			err := readVersion(node.Metadata, version)
+
+			// then
+			Expect(err).To(BeNil())
+			Expect(version).To(Equal(mesh_proto.NewVersion()))
+		},
+		Entry("when version is a nil struct", versionTestCase{
+			version: &pstruct.Value{
+				Kind: &pstruct.Value_StructValue{
+					StructValue: nil,
+				},
+			},
+		}),
+		Entry("when version is not a struct", versionTestCase{
+			version: &pstruct.Value{
+				Kind: &pstruct.Value_StringValue{
+					StringValue: "v1.0.0",
+				},
+			},
+		}),
+	)
 })
 
 type DataplaneInsightSinkFunc func(stop <-chan struct{})