VOL-1910
Added unit test cases for openolt_flowmgr.go

Change-Id: If7b87ce2760a9eff81a2a77545fa39573190625b
diff --git a/adaptercore/openolt_flowmgr.go b/adaptercore/openolt_flowmgr.go
index 7baabb1..7fb968f 100644
--- a/adaptercore/openolt_flowmgr.go
+++ b/adaptercore/openolt_flowmgr.go
@@ -1394,10 +1394,10 @@
 func (f *OpenOltFlowMgr) addGemPortToOnuInfoMap(intfID uint32, onuID uint32, gemPort uint32) {
 	onuIDkey := onuIDKey{intfID: intfID, onuID: onuID}
 	if val, ok := f.onuIds[onuIDkey]; ok {
-		onuInfo := val
+		onuInf := val
 		gemportKey := gemPortKey{intfID: intfID, gemPort: gemPort}
-		f.onuGemPortIds[gemportKey] = onuInfo
-		log.Debugw("Cached Gemport to Onuinfo map", log.Fields{"GemPort": gemPort, "intfId": onuInfo.intfID, "onuId": onuInfo.onuID})
+		f.onuGemPortIds[gemportKey] = onuInf
+		log.Debugw("Cached Gemport to Onuinfo map", log.Fields{"GemPort": gemPort, "intfId": onuInf.intfID, "onuId": onuInf.onuID})
 		return
 	}
 	log.Errorw("OnuInfo not found", log.Fields{"intfId": intfID, "onuId": onuID, "gemPort": gemPort})
@@ -1409,14 +1409,14 @@
 func (f *OpenOltFlowMgr) getOnuIDfromGemPortMap(serialNumber string, intfID uint32, gemPortID uint32) (uint32, error) {
 	log.Debugw("Getting ONU ID from GEM port and PON port", log.Fields{"serialNumber": serialNumber, "intfId": intfID, "gemPortId": gemPortID})
 	if serialNumber != "" {
-		if onuInfo, ok := f.onuSerialNumbers[serialNumber]; ok {
-			return onuInfo.onuID, nil
+		if onuInf, ok := f.onuSerialNumbers[serialNumber]; ok {
+			return onuInf.onuID, nil
 		}
 	} else {
 		gemportKey := gemPortKey{intfID: intfID, gemPort: gemPortID}
-		if onuInfo, ok := f.onuGemPortIds[gemportKey]; ok {
-			log.Debugw("Retrieved onu info from access", log.Fields{"intfId": intfID, "gemPortId": gemPortID, "onuId": onuInfo.onuID})
-			return onuInfo.onuID, nil
+		if onuInf, ok := f.onuGemPortIds[gemportKey]; ok {
+			log.Debugw("Retrieved onu info from access", log.Fields{"intfId": intfID, "gemPortId": gemPortID, "onuId": onuInf.onuID})
+			return onuInf.onuID, nil
 		}
 	}
 	log.Errorw("onuid is not found", log.Fields{"serialNumber": serialNumber, "intfId": intfID, "gemPort": gemPortID})
diff --git a/adaptercore/openolt_flowmgr_test.go b/adaptercore/openolt_flowmgr_test.go
new file mode 100644
index 0000000..93a2e0e
--- /dev/null
+++ b/adaptercore/openolt_flowmgr_test.go
@@ -0,0 +1,393 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+
+ * http://www.apache.org/licenses/LICENSE-2.0
+
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+//Package adaptercore provides the utility for olt devices, flows and statistics
+package adaptercore
+
+import (
+	"fmt"
+	"testing"
+
+	"github.com/opencord/voltha-go/common/log"
+	tp "github.com/opencord/voltha-go/common/techprofile"
+	"github.com/opencord/voltha-go/db/model"
+	fu "github.com/opencord/voltha-go/rw_core/utils"
+	"github.com/opencord/voltha-openolt-adapter/adaptercore/resourcemanager"
+	"github.com/opencord/voltha-openolt-adapter/mocks"
+	ofp "github.com/opencord/voltha-protos/go/openflow_13"
+	"github.com/opencord/voltha-protos/go/openolt"
+	openoltpb2 "github.com/opencord/voltha-protos/go/openolt"
+	tp_pb "github.com/opencord/voltha-protos/go/tech_profile"
+	"github.com/opencord/voltha-protos/go/voltha"
+)
+
+func init() {
+	log.SetDefaultLogger(log.JSON, log.DebugLevel, nil)
+}
+func newMockResourceMgr() *resourcemanager.OpenOltResourceMgr {
+	ranges := []*openolt.DeviceInfo_DeviceResourceRanges{
+		{IntfIds: []uint32{0, 1, 2}}}
+
+	deviceinfo := &openolt.DeviceInfo{Vendor: "openolt", Model: "openolt", HardwareVersion: "1.0", FirmwareVersion: "1.0",
+		DeviceId: "olt", DeviceSerialNumber: "openolt", PonPorts: 3, Technology: "Default",
+		OnuIdStart: 1, OnuIdEnd: 1, AllocIdStart: 1, AllocIdEnd: 1,
+		GemportIdStart: 1, GemportIdEnd: 1, FlowIdStart: 1, FlowIdEnd: 1,
+		Ranges: ranges,
+	}
+	rsrMgr := resourcemanager.NewResourceMgr("olt", "127.0.0.1:2379", "etcd", "olt", deviceinfo)
+	return rsrMgr
+}
+
+func newMockFlowmgr() *OpenOltFlowMgr {
+	rsrMgr := newMockResourceMgr()
+	dh := newMockDeviceHandler()
+
+	rsrMgr.KVStore = &model.Backend{}
+	rsrMgr.KVStore.Client = &mocks.MockKVClient{}
+
+	dh.resourceMgr = rsrMgr
+	flwMgr := NewFlowManager(dh, rsrMgr)
+	onuIds := make(map[onuIDKey]onuInfo)
+	onuIds[onuIDKey{intfID: 1, onuID: 1}] = onuInfo{intfID: 1, onuID: 1, serialNumber: "1"}
+	onuIds[onuIDKey{intfID: 2, onuID: 2}] = onuInfo{intfID: 2, onuID: 2, serialNumber: "2"}
+	flwMgr.onuIds = onuIds
+
+	onuSerialNumbers := make(map[string]onuInfo)
+	onuSerialNumbers["1"] = onuInfo{intfID: 1, onuID: 1, serialNumber: "1"}
+	onuSerialNumbers["2"] = onuInfo{intfID: 2, onuID: 1, serialNumber: "2"}
+	flwMgr.onuSerialNumbers = onuSerialNumbers
+
+	onuGemPortIds := make(map[gemPortKey]onuInfo)
+	onuGemPortIds[gemPortKey{intfID: 1, gemPort: 1}] = onuInfo{intfID: 1, onuID: 1, serialNumber: "1"}
+	onuGemPortIds[gemPortKey{intfID: 2, gemPort: 2}] = onuInfo{intfID: 2, onuID: 2, serialNumber: "2"}
+	flwMgr.onuGemPortIds = onuGemPortIds
+
+	packetInGemPort := make(map[packetInInfoKey]uint32)
+	packetInGemPort[packetInInfoKey{intfID: 1, onuID: 1, logicalPort: 1}] = 1
+	packetInGemPort[packetInInfoKey{intfID: 2, onuID: 2, logicalPort: 2}] = 2
+
+	flwMgr.packetInGemPort = packetInGemPort
+	tps := make([]*tp.TechProfileMgr, len(rsrMgr.ResourceMgrs))
+	for key, val := range rsrMgr.ResourceMgrs {
+		tps[key] = val.TechProfileMgr
+	}
+	flwMgr.techprofile = tps
+	return flwMgr
+}
+func TestOpenOltFlowMgr_CreateSchedulerQueues(t *testing.T) {
+	flowMgr := newMockFlowmgr()
+
+	tprofile := &tp.TechProfile{Name: "tp1", SubscriberIdentifier: "subscriber1",
+		ProfileType: "pt1", NumGemPorts: 1, NumTconts: 1, Version: 1,
+		InstanceCtrl: tp.InstanceControl{Onu: "1", Uni: "1", MaxGemPayloadSize: "1"},
+	}
+	tprofile.UsScheduler.Direction = "UPSTREAM"
+	tprofile.UsScheduler.AdditionalBw = "AdditionalBW_None"
+	tprofile.UsScheduler.QSchedPolicy = "WRR"
+
+	tprofile2 := tprofile
+	tprofile2.DsScheduler.Direction = "DOWNSTREAM"
+	tprofile2.DsScheduler.AdditionalBw = "AdditionalBW_None"
+	tprofile2.DsScheduler.QSchedPolicy = "WRR"
+	bands := make([]*ofp.OfpMeterBandHeader, 2)
+	bands[0] = &ofp.OfpMeterBandHeader{Type: ofp.OfpMeterBandType_OFPMBT_DROP, Rate: 1000, BurstSize: 5000, Data: &ofp.OfpMeterBandHeader_Drop{}}
+	bands[1] = &ofp.OfpMeterBandHeader{Type: ofp.OfpMeterBandType_OFPMBT_DROP, Rate: 2000, BurstSize: 5000, Data: &ofp.OfpMeterBandHeader_Drop{}}
+	ofpMeterConfig := &ofp.OfpMeterConfig{Flags: 1, MeterId: 1, Bands: bands}
+	flowmetadata := &voltha.FlowMetadata{
+		Meters: []*ofp.OfpMeterConfig{ofpMeterConfig},
+	}
+	type args struct {
+		Dir          tp_pb.Direction
+		IntfID       uint32
+		OnuID        uint32
+		UniID        uint32
+		UniPort      uint32
+		TpInst       *tp.TechProfile
+		MeterID      uint32
+		flowMetadata *voltha.FlowMetadata
+	}
+	tests := []struct {
+		name    string
+		args    args
+		wantErr bool
+	}{
+		// TODO: Add test cases.
+		{"CreateSchedulerQueues-1", args{Dir: tp_pb.Direction_UPSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile, MeterID: 1, flowMetadata: flowmetadata}, false},
+		{"CreateSchedulerQueues-2", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2, MeterID: 1, flowMetadata: flowmetadata}, false},
+		{"CreateSchedulerQueues-3", args{Dir: tp_pb.Direction_UPSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile, MeterID: 2, flowMetadata: flowmetadata}, true},
+		{"CreateSchedulerQueues-4", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2, MeterID: 2, flowMetadata: flowmetadata}, true},
+		{"CreateSchedulerQueues-5", args{Dir: tp_pb.Direction_UPSTREAM, IntfID: 2, OnuID: 2, UniID: 2, UniPort: 2, TpInst: tprofile, MeterID: 2, flowMetadata: flowmetadata}, true},
+		{"CreateSchedulerQueues-6", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 2, OnuID: 2, UniID: 2, UniPort: 2, TpInst: tprofile2, MeterID: 2, flowMetadata: flowmetadata}, true},
+		{"CreateSchedulerQueues-13", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2, MeterID: 1, flowMetadata: flowmetadata}, false},
+		//Negative testcases
+		{"CreateSchedulerQueues-7", args{Dir: tp_pb.Direction_UPSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile, MeterID: 1, flowMetadata: &voltha.FlowMetadata{}}, true},
+		{"CreateSchedulerQueues-8", args{Dir: tp_pb.Direction_UPSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile, MeterID: 0, flowMetadata: &voltha.FlowMetadata{}}, true},
+		{"CreateSchedulerQueues-9", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2, MeterID: 1, flowMetadata: &voltha.FlowMetadata{}}, true},
+		{"CreateSchedulerQueues-10", args{Dir: tp_pb.Direction_UPSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile, MeterID: 2, flowMetadata: &voltha.FlowMetadata{}}, true},
+		{"CreateSchedulerQueues-11", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2, MeterID: 2, flowMetadata: &voltha.FlowMetadata{}}, true},
+		{"CreateSchedulerQueues-12", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2, MeterID: 2}, true},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+			if err := flowMgr.CreateSchedulerQueues(tt.args.Dir, tt.args.IntfID, tt.args.OnuID, tt.args.UniID, tt.args.UniPort, tt.args.TpInst, tt.args.MeterID, tt.args.flowMetadata); (err != nil) != tt.wantErr {
+				t.Errorf("OpenOltFlowMgr.CreateSchedulerQueues() error = %v, wantErr %v", err, tt.wantErr)
+			}
+		})
+	}
+}
+
+func TestOpenOltFlowMgr_RemoveSchedulerQueues(t *testing.T) {
+
+	flowMgr := newMockFlowmgr()
+	tprofile := &tp.TechProfile{Name: "tp1", SubscriberIdentifier: "subscriber1",
+		ProfileType: "pt1", NumGemPorts: 1, NumTconts: 1, Version: 1,
+		InstanceCtrl: tp.InstanceControl{Onu: "1", Uni: "1", MaxGemPayloadSize: "1"},
+	}
+	tprofile.UsScheduler.Direction = "UPSTREAM"
+	tprofile.UsScheduler.AdditionalBw = "AdditionalBW_None"
+	tprofile.UsScheduler.QSchedPolicy = "WRR"
+
+	tprofile2 := tprofile
+	tprofile2.DsScheduler.Direction = "DOWNSTREAM"
+	tprofile2.DsScheduler.AdditionalBw = "AdditionalBW_None"
+	tprofile2.DsScheduler.QSchedPolicy = "WRR"
+	//defTprofile := &tp.DefaultTechProfile{}
+	type args struct {
+		Dir     tp_pb.Direction
+		IntfID  uint32
+		OnuID   uint32
+		UniID   uint32
+		UniPort uint32
+		TpInst  *tp.TechProfile
+	}
+	tests := []struct {
+		name    string
+		args    args
+		wantErr bool
+	}{
+		// TODO: Add test cases.
+		{"RemoveSchedulerQueues", args{Dir: tp_pb.Direction_UPSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile}, false},
+		{"RemoveSchedulerQueues", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2}, false},
+		// negative test cases
+		{"RemoveSchedulerQueues", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2}, false},
+		{"RemoveSchedulerQueues", args{Dir: tp_pb.Direction_DOWNSTREAM, IntfID: 1, OnuID: 1, UniID: 1, UniPort: 1, TpInst: tprofile2}, false},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+
+			if err := flowMgr.RemoveSchedulerQueues(tt.args.Dir, tt.args.IntfID, tt.args.OnuID, tt.args.UniID, tt.args.UniPort, tt.args.TpInst); (err != nil) != tt.wantErr {
+				t.Errorf("OpenOltFlowMgr.RemoveSchedulerQueues() error = %v, wantErr %v", err, tt.wantErr)
+			}
+		})
+	}
+}
+
+func TestOpenOltFlowMgr_RemoveFlow(t *testing.T) {
+	flowMgr := newMockFlowmgr()
+
+	fa := &fu.FlowArgs{
+		MatchFields: []*ofp.OfpOxmOfbField{
+			fu.InPort(2),
+			fu.Metadata_ofp(2),
+			fu.VlanVid(uint32(ofp.OfpVlanId_OFPVID_PRESENT) | 0),
+		},
+		Actions: []*ofp.OfpAction{
+			fu.SetField(fu.Metadata_ofp(uint64(ofp.OfpInstructionType_OFPIT_WRITE_METADATA | 2))),
+			fu.SetField(fu.VlanVid(uint32(ofp.OfpVlanId_OFPVID_PRESENT) | 101)),
+			fu.Output(1),
+		},
+	}
+	ofpstats := fu.MkFlowStat(fa)
+	type args struct {
+		flow *ofp.OfpFlowStats
+	}
+	tests := []struct {
+		name string
+		args args
+	}{
+		// TODO: Add test cases.
+		{"RemoveFlow", args{flow: ofpstats}},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+			flowMgr.RemoveFlow(tt.args.flow)
+		})
+	}
+}
+
+func TestOpenOltFlowMgr_AddFlow(t *testing.T) {
+
+	flowMgr := newMockFlowmgr()
+	kw := make(map[string]uint64)
+	kw["table_id"] = 1
+	kw["meter_id"] = 1
+	kw["write_metadata"] = 2
+	fa := &fu.FlowArgs{
+		MatchFields: []*ofp.OfpOxmOfbField{
+			fu.InPort(1000),
+			fu.Metadata_ofp(1),
+			fu.VlanVid(uint32(ofp.OfpVlanId_OFPVID_PRESENT) | 0),
+		},
+		Actions: []*ofp.OfpAction{
+			//fu.SetField(fu.Metadata_ofp(uint64(ofp.OfpInstructionType_OFPIT_WRITE_METADATA | 2))),
+			fu.SetField(fu.VlanVid(uint32(ofp.OfpVlanId_OFPVID_PRESENT) | 101)),
+			fu.Output(65533),
+		},
+		KV: kw,
+	}
+
+	ofpstats := fu.MkFlowStat(fa)
+	fmt.Println("ofpstats ", ofpstats)
+	//ofpstats.Dat
+	ofpMeterConfig := &ofp.OfpMeterConfig{Flags: 1, MeterId: 1}
+	//ofpWritemetaData := &ofp.ofp
+	flowMetadata := &voltha.FlowMetadata{
+		Meters: []*ofp.OfpMeterConfig{ofpMeterConfig},
+	}
+	type args struct {
+		flow         *ofp.OfpFlowStats
+		flowMetadata *voltha.FlowMetadata
+	}
+	tests := []struct {
+		name string
+		args args
+	}{
+		// TODO: Add test cases.
+		{"AddFlow", args{flow: ofpstats, flowMetadata: flowMetadata}},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+			flowMgr.AddFlow(tt.args.flow, tt.args.flowMetadata)
+		})
+	}
+}
+
+func TestOpenOltFlowMgr_UpdateOnuInfo(t *testing.T) {
+	flowMgr := newMockFlowmgr()
+	type args struct {
+		intfID    uint32
+		onuID     uint32
+		serialNum string
+	}
+	tests := []struct {
+		name string
+		args args
+	}{
+		// TODO: Add test cases.
+		{"UpdateOnuInfo", args{1, 1, "onu1"}},
+		{"UpdateOnuInfo", args{2, 3, "onu1"}},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+
+			flowMgr.UpdateOnuInfo(tt.args.intfID, tt.args.onuID, tt.args.serialNum)
+		})
+	}
+}
+
+func TestOpenOltFlowMgr_GetLogicalPortFromPacketIn(t *testing.T) {
+	flowMgr := newMockFlowmgr()
+	type args struct {
+		packetIn *openoltpb2.PacketIndication
+	}
+	tests := []struct {
+		name    string
+		args    args
+		want    uint32
+		wantErr bool
+	}{
+		// TODO: Add test cases.
+		{"GetLogicalPortFromPacketIn", args{packetIn: &openoltpb2.PacketIndication{IntfType: "pon", IntfId: 1, GemportId: 1, FlowId: 100, PortNo: 1, Cookie: 100, Pkt: []byte("GetLogicalPortFromPacketIn")}}, 1, false},
+		{"GetLogicalPortFromPacketIn", args{packetIn: &openoltpb2.PacketIndication{IntfType: "nni", IntfId: 1, GemportId: 1, FlowId: 100, PortNo: 1, Cookie: 100, Pkt: []byte("GetLogicalPortFromPacketIn")}}, 65537, false},
+		// Negative Test cases.
+		{"GetLogicalPortFromPacketIn", args{packetIn: &openoltpb2.PacketIndication{IntfType: "pon", IntfId: 2, GemportId: 1, FlowId: 100, PortNo: 1, Cookie: 100, Pkt: []byte("GetLogicalPortFromPacketIn")}}, 0, true},
+		{"GetLogicalPortFromPacketIn", args{packetIn: &openoltpb2.PacketIndication{IntfType: "pon", IntfId: 1, GemportId: 1, FlowId: 100, PortNo: 0, Cookie: 100, Pkt: []byte("GetLogicalPortFromPacketIn")}}, 2064, false},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+
+			got, err := flowMgr.GetLogicalPortFromPacketIn(tt.args.packetIn)
+			if (err != nil) != tt.wantErr {
+				t.Errorf("OpenOltFlowMgr.GetLogicalPortFromPacketIn() error = %v, wantErr %v", err, tt.wantErr)
+				return
+			}
+			if got != tt.want {
+				t.Errorf("OpenOltFlowMgr.GetLogicalPortFromPacketIn() = %v, want %v", got, tt.want)
+			}
+		})
+	}
+}
+
+func TestOpenOltFlowMgr_GetPacketOutGemPortID(t *testing.T) {
+	flwMgr := newMockFlowmgr()
+
+	type args struct {
+		intfID  uint32
+		onuID   uint32
+		portNum uint32
+	}
+	tests := []struct {
+		name    string
+		args    args
+		want    uint32
+		wantErr bool
+	}{
+		// TODO: Add test cases.
+		{"GetPacketOutGemPortID", args{intfID: 1, onuID: 1, portNum: 1}, 1, false},
+		{"GetPacketOutGemPortID", args{intfID: 2, onuID: 2, portNum: 2}, 2, false},
+		{"GetPacketOutGemPortID", args{intfID: 1, onuID: 2, portNum: 2}, 0, true},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+
+			got, err := flwMgr.GetPacketOutGemPortID(tt.args.intfID, tt.args.onuID, tt.args.portNum)
+			if (err != nil) != tt.wantErr {
+				t.Errorf("OpenOltFlowMgr.GetPacketOutGemPortID() error = %v, wantErr %v", err, tt.wantErr)
+				return
+			}
+			if got != tt.want {
+				t.Errorf("OpenOltFlowMgr.GetPacketOutGemPortID() = %v, want %v", got, tt.want)
+			}
+
+		})
+	}
+}
+
+func TestOpenOltFlowMgr_DeleteTechProfileInstance(t *testing.T) {
+	flwMgr := newMockFlowmgr()
+	type args struct {
+		intfID uint32
+		onuID  uint32
+		uniID  uint32
+		sn     string
+	}
+	tests := []struct {
+		name    string
+		args    args
+		wantErr bool
+	}{
+		// TODO: Add test cases.
+		{"DeleteTechProfileInstance", args{intfID: 0, onuID: 1, uniID: 1, sn: ""}, true},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+
+			if err := flwMgr.DeleteTechProfileInstance(tt.args.intfID, tt.args.onuID, tt.args.uniID, tt.args.sn); (err != nil) != tt.wantErr {
+				t.Errorf("OpenOltFlowMgr.DeleteTechProfileInstance() error = %v, wantErr %v", err, tt.wantErr)
+			}
+		})
+	}
+}
diff --git a/mocks/mockKVClient.go b/mocks/mockKVClient.go
new file mode 100644
index 0000000..e11a756
--- /dev/null
+++ b/mocks/mockKVClient.go
@@ -0,0 +1,172 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+
+ * http://www.apache.org/licenses/LICENSE-2.0
+
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+//Package mocks provides the mocks for openolt-adapter.
+package mocks
+
+import (
+	"encoding/json"
+	"errors"
+	"strconv"
+	"strings"
+
+	"github.com/opencord/voltha-go/db/kvstore"
+	ofp "github.com/opencord/voltha-protos/go/openflow_13"
+)
+
+const (
+	// MeterConfig meter to extarct meter
+	MeterConfig = "meter_id"
+	// TpIDPathSuffix to extract Techprofile
+	TpIDPathSuffix = "tp_id"
+)
+
+// MockKVClient mocks the AdapterProxy interface.
+type MockKVClient struct {
+}
+
+// List mock function implementation for KVClient
+func (kvclient *MockKVClient) List(key string, timeout int, lock ...bool) (map[string]*kvstore.KVPair, error) {
+	if key != "" {
+		maps := make(map[string]*kvstore.KVPair)
+		maps[key] = &kvstore.KVPair{Key: key}
+		return maps, nil
+	}
+	return nil, errors.New("key didn't find")
+}
+
+// Get mock function implementation for KVClient
+func (kvclient *MockKVClient) Get(key string, timeout int, lock ...bool) (*kvstore.KVPair, error) {
+	if key != "" {
+
+		if strings.Contains(key, MeterConfig) {
+			var bands []*ofp.OfpMeterBandHeader
+			bands = append(bands, &ofp.OfpMeterBandHeader{Type: ofp.OfpMeterBandType_OFPMBT_DSCP_REMARK,
+				Rate: 1024, Data: &ofp.OfpMeterBandHeader_DscpRemark{DscpRemark: &ofp.OfpMeterBandDscpRemark{PrecLevel: 2}}})
+
+			bands = append(bands, &ofp.OfpMeterBandHeader{Type: ofp.OfpMeterBandType_OFPMBT_DSCP_REMARK,
+				Rate: 1024, Data: &ofp.OfpMeterBandHeader_DscpRemark{DscpRemark: &ofp.OfpMeterBandDscpRemark{PrecLevel: 3}}})
+
+			//	bands = append(bands, &ofp.OfpMeterBandHeader{})
+			// Data: &ofp.OfpMeterBandHeader_Drop{Drop: &ofp.OfpMeterBandDrop{}}
+			sep := strings.Split(key, "/")[2]
+			val, _ := strconv.ParseInt(strings.Split(sep, ",")[1], 10, 32)
+			if uint32(val) > 1 {
+				meterConfig := &ofp.OfpMeterConfig{MeterId: uint32(val), Bands: bands}
+				str, _ := json.Marshal(meterConfig)
+				//json.marshall()
+				return kvstore.NewKVPair(key, string(str), "mock", 3000, 1), nil
+			}
+			if uint32(val) == 1 {
+				return nil, nil
+			}
+			return nil, errors.New("invalid meter")
+		}
+		if strings.Contains(key, TpIDPathSuffix) {
+			str, _ := json.Marshal(1)
+			return kvstore.NewKVPair(key, str, "mock", 3000, 1), nil
+		}
+		maps := make(map[string]*kvstore.KVPair)
+		maps[key] = &kvstore.KVPair{Key: key}
+		return maps[key], nil
+	}
+	return nil, errors.New("key didn't find")
+}
+
+// Put mock function implementation for KVClient
+func (kvclient *MockKVClient) Put(key string, value interface{}, timeout int, lock ...bool) error {
+	if key != "" {
+
+		return nil
+	}
+	return errors.New("key didn't find")
+}
+
+// Delete mock function implementation for KVClient
+func (kvclient *MockKVClient) Delete(key string, timeout int, lock ...bool) error {
+	if key == "" {
+		return errors.New("key didn't find")
+	}
+	return nil
+}
+
+// Reserve mock function implementation for KVClient
+func (kvclient *MockKVClient) Reserve(key string, value interface{}, ttl int64) (interface{}, error) {
+	if key != "" {
+		maps := make(map[string]*kvstore.KVPair)
+		maps[key] = &kvstore.KVPair{Key: key}
+		return maps[key], nil
+	}
+	return nil, errors.New("key didn't find")
+}
+
+// ReleaseReservation mock function implementation for KVClient
+func (kvclient *MockKVClient) ReleaseReservation(key string) error {
+	// return nil
+	if key == "" {
+		return errors.New("key didn't find")
+	}
+	return nil
+}
+
+// ReleaseAllReservations mock function implementation for KVClient
+func (kvclient *MockKVClient) ReleaseAllReservations() error {
+	return nil
+}
+
+// RenewReservation mock function implementation for KVClient
+func (kvclient *MockKVClient) RenewReservation(key string) error {
+	// return nil
+	if key == "" {
+		return errors.New("key didn't find")
+	}
+	return nil
+}
+
+// Watch mock function implementation for KVClient
+func (kvclient *MockKVClient) Watch(key string) chan *kvstore.Event {
+	return nil
+	// if key == "" {
+	// 	return nil
+	// }
+	// return &kvstore.Event{EventType: 1, Key: key}
+}
+
+// AcquireLock mock function implementation for KVClient
+func (kvclient *MockKVClient) AcquireLock(lockName string, timeout int) error {
+	return nil
+}
+
+// ReleaseLock mock function implementation for KVClient
+func (kvclient *MockKVClient) ReleaseLock(lockName string) error {
+	return nil
+}
+
+// IsConnectionUp mock function implementation for KVClient
+func (kvclient *MockKVClient) IsConnectionUp(timeout int) bool { // timeout in second
+	if timeout < 1 {
+		return false
+	}
+	return true
+}
+
+// CloseWatch mock function implementation for KVClient
+func (kvclient *MockKVClient) CloseWatch(key string, ch chan *kvstore.Event) {
+}
+
+// Close mock function implementation for KVClient
+func (kvclient *MockKVClient) Close() {
+}