ADTRAN: Update to containerized adapters.
Loading and running but still needs about a week or so of work to
catch up to where the OpenOLT/ONU containerized adapters are
Change-Id: I5522232e21dd76b3f95b4698af6c7e4cef96753d
diff --git a/adapters/adtran_olt/adtran_olt.yml b/adapters/adtran_olt/adapters-adtran-olt.yml
similarity index 100%
rename from adapters/adtran_olt/adtran_olt.yml
rename to adapters/adtran_olt/adapters-adtran-olt.yml
diff --git a/adapters/adtran_olt/adtran_olt.py b/adapters/adtran_olt/adtran_olt.py
index c052b78..e25b42a 100644
--- a/adapters/adtran_olt/adtran_olt.py
+++ b/adapters/adtran_olt/adtran_olt.py
@@ -22,7 +22,7 @@
from pyvoltha.adapters.iadapter import OltAdapter
from pyvoltha.protos import third_party
from pyvoltha.protos.common_pb2 import AdminState
-
+from pyvoltha.protos.health_pb2 import HealthStatus
from adtran_olt_handler import AdtranOltHandler
@@ -43,7 +43,7 @@
version='2.0.0',
device_type=AdtranOltAdapter.name,
accepts_bulk_flow_update=True,
- accepts_add_remove_flow_updates=False) # TODO: Implement me
+ accepts_add_remove_flow_updates=True)
log.debug('adtran_olt.__init__')
@@ -55,7 +55,6 @@
"""
# TODO: Currently this is always healthy for every adapter.
# If we decide not to modify this, delete this method and use base class method
- from pyvoltha.protos.health_pb2 import HealthStatus
return HealthStatus(state=HealthStatus.HEALTHY)
def abandon_device(self, device):
@@ -75,8 +74,9 @@
is provisioned top-down and needs to be activated by the adapter.
:param device: A voltha.Device object, with possible device-type
- specific extensions. Such extensions shall be described as part of
- the device type specification returned by device_types().
+ specific extensions. Such extensions shall be described as part of
+ the device type specification returned by device_types().
+
:return: (Deferred) Shall be fired to acknowledge device ownership.
"""
log.info('adopt-device', device=device)
@@ -84,23 +84,36 @@
'adapter': self,
'device-id': device.id
}
- self.devices_handlers[device.id] = self.device_handler_class(**kwargs)
- d = defer.Deferred()
- reactor.callLater(0, self.devices_handlers[device.id].activate, d, False)
- return d
+ try:
+ self.devices_handlers[device.id] = self.device_handler_class(**kwargs)
+ d = defer.Deferred()
+ reactor.callLater(0, self.devices_handlers[device.id].activate, d, False)
+ return d
+
+ except Exception as _e:
+ raise
def reconcile_device(self, device):
+ """
+ Make sure the adapter looks after given device. Called when this
+ device has changed ownership from another Voltha instance to
+ this one (typically, this occurs when the previous voltha
+ instance went down).
+
+ :param device: A voltha.Device object, with possible device-type
+ specific extensions. Such extensions shall be described as part of
+ the device type specification returned by device_types().
+
+ :return: (Deferred) Shall be fired to acknowledge device ownership.
+ """
try:
- self.devices_handlers[device.id] = self.device_handler_class(self,
- device.id)
+ kwargs = {
+ 'adapter': self,
+ 'device-id': device.id
+ }
+ self.devices_handlers[device.id] = self.device_handler_class(**kwargs)
# Work only required for devices that are in ENABLED state
if device.admin_state == AdminState.ENABLED:
-
- kwargs = {
- 'adapter': self,
- 'device-id': device.id
- }
- self.devices_handlers[device.id] =self.device_handler_class(**kwargs)
d = defer.Deferred()
reactor.callLater(0, self.devices_handlers[device.id].activate, d, True)
diff --git a/adapters/adtran_olt/adtran_olt_handler.py b/adapters/adtran_olt/adtran_olt_handler.py
index ad32b84..92c3398 100644
--- a/adapters/adtran_olt/adtran_olt_handler.py
+++ b/adapters/adtran_olt/adtran_olt_handler.py
@@ -160,9 +160,6 @@
'startup-revision': 'unknown',
'software-images': []
}
- if self.is_virtual_olt:
- returnValue(device)
-
try:
pe_state = PhysicalEntitiesState(self.netconf_client)
self.startup = pe_state.get_state()
@@ -322,12 +319,8 @@
from nni_port import MockNniPort
ietf_interfaces = IetfInterfacesState(self.netconf_client)
-
- if self.is_virtual_olt:
- results = MockNniPort.get_nni_port_state_results()
- else:
- self.startup = ietf_interfaces.get_state()
- results = yield self.startup
+ self.startup = ietf_interfaces.get_state()
+ results = yield self.startup
ports = ietf_interfaces.get_port_entries(results, 'ethernet')
returnValue(ports)
@@ -355,10 +348,9 @@
# May already exist if device was not fully reachable when first enabled
if port_no not in self.northbound_ports:
self.log.info('processing-nni', port_no=port_no, name=port['port_no'])
- self.northbound_ports[port_no] = NniPort(self, **port) if not self.is_virtual_olt \
- else MockNniPort(self, **port)
+ self.northbound_ports[port_no] = NniPort(self, **port)
- if len(self.northbound_ports) >= self.max_nni_ports: # TODO: For now, limit number of NNI ports to make debugging easier
+ if len(self.northbound_ports) >= self.max_nni_ports: # TODO: For now, limit number of NNI ports to make debugging easier
break
self.num_northbound_ports = len(self.northbound_ports)
@@ -407,12 +399,8 @@
results = yield self.startup
ietf_interfaces = IetfInterfacesState(self.netconf_client)
-
- if self.is_virtual_olt:
- nc_results = MockNniPort.get_pon_port_state_results()
- else:
- self.startup = ietf_interfaces.get_state()
- nc_results = yield self.startup
+ self.startup = ietf_interfaces.get_state()
+ nc_results = yield self.startup
ports = ietf_interfaces.get_port_entries(nc_results, 'xpon')
if len(ports) == 0:
@@ -692,7 +680,7 @@
# Upstream direction?
if self.is_pon_port(port_no):
#TODO: Validate the evc-map name
- from python.adapters.adtran.adtran_common.flow.evc_map import EVCMap
+ from pyvoltha.adapters.adtran_common.flow.evc_map import EVCMap
map_info = EVCMap.decode_evc_map_name(evc_map)
logical_port_no = int(map_info.get('ingress-port'))
@@ -1162,6 +1150,7 @@
self.adapter_agent.update_image_download(request)
+ @inlineCallbacks
def start_download(self, device, request, done):
"""
This is called to request downloading a specified image into
@@ -1193,7 +1182,7 @@
self._downloads[download.name] = download
self._update_download_status(request, download)
done.callback('started')
- return done
+ returnValue(done)
except Exception:
request.additional_info = 'Download request startup failed due to exception'
@@ -1214,9 +1203,10 @@
# restore admin state to enabled
device.admin_state = AdminState.ENABLED
- self.adapter_agent.update_device(device)
+ yield self.adapter_agent.device_update(device)
raise
+ @inlineCallbacks
def download_status(self, device, request, done):
"""
This is called to inquire about a requested image download status based
@@ -1241,11 +1231,12 @@
ImageDownload.DOWNLOAD_FAILED]:
# restore admin state to enabled
device.admin_state = AdminState.ENABLED
- self.adapter_agent.update_device(device)
+ yield self.adapter_agent.device_update(device)
done.callback(request.state)
- return done
+ returnValue(done)
+ @inlineCallbacks
def cancel_download(self, device, request, done):
"""
This is called to cancel a requested image download based on a NBI
@@ -1273,10 +1264,11 @@
if device.admin_state == AdminState.DOWNLOADING_IMAGE:
device.admin_state = AdminState.ENABLED
- self.adapter_agent.update_device(device)
+ yield self.adapter_agent.device_update(device)
- return done
+ returnValue(done)
+ @inlineCallbacks
def activate_image(self, device, request, done):
"""
This is called to activate a downloaded image from a standby partition
@@ -1306,9 +1298,10 @@
# restore admin state to enabled
device.admin_state = AdminState.ENABLED
- self.adapter_agent.update_device(device)
- return done
+ yield self.adapter_agent.device_update(device)
+ returnValue(done)
+ @inlineCallbacks
def revert_image(self, device, request, done):
"""
This is called to deactivate the specified image at active partition,
@@ -1338,8 +1331,8 @@
# restore admin state to enabled
device.admin_state = AdminState.ENABLED
- self.adapter_agent.update_device(device)
- return done
+ yield self.adapter_agent.device_update(device)
+ returnValue(done)
def add_onu_device(self, pon_id, onu_id, serial_number):
onu_device = self.adapter_agent.get_child_device(self.device_id,
diff --git a/adapters/adtran_olt/main.py b/adapters/adtran_olt/main.py
index 07bcc07..bea91bf 100755
--- a/adapters/adtran_olt/main.py
+++ b/adapters/adtran_olt/main.py
@@ -49,9 +49,9 @@
_ = third_party
-defs = dict(
- version_file='./VERSION',
- config=os.environ.get('CONFIG', './adapters-adtran_olt.yml'),
+defs=dict(
+ version_file='/voltha/VERSION',
+ config=os.environ.get('CONFIG', './adapters-adtran-olt.yml'),
container_name_regex=os.environ.get('CONTAINER_NUMBER_EXTRACTOR', '^.*\.(['
'0-9]+)\..*$'),
consul=os.environ.get('CONSUL', 'localhost:8500'),
@@ -64,8 +64,8 @@
core_topic=os.environ.get('CORE_TOPIC', 'rwcore'),
interface=os.environ.get('INTERFACE', get_my_primary_interface()),
instance_id=os.environ.get('INSTANCE_ID', os.environ.get('HOSTNAME', '1')),
- kafka_adapter=os.environ.get('KAFKA_ADAPTER', '172.20.10.3:9092'),
- kafka_cluster=os.environ.get('KAFKA_CLUSTER', '172.20.10.3:9092'),
+ kafka_adapter=os.environ.get('KAFKA_ADAPTER', '192.168.0.20:9092'),
+ kafka_cluster=os.environ.get('KAFKA_CLUSTER', '10.100.198.220:9092'),
backend=os.environ.get('BACKEND', 'none'),
retry_interval=os.environ.get('RETRY_INTERVAL', 2),
heartbeat_topic=os.environ.get('HEARTBEAT_TOPIC', "adapters.heartbeat"),
@@ -74,7 +74,7 @@
debug_enabled=True,
debug_host='work.bcsw.net',
# debug_host='10.0.2.15',
- debug_port=8765,
+ debug_port=5678,
)
@@ -286,7 +286,7 @@
except:
import sys
logger.error("pydevd startup exception: %s" % sys.exc_info()[0])
- print('REMOTE DEBUGGING will not be supported in this run...')
+ logger.error('REMOTE DEBUGGING will not be supported in this run...')
def load_config(args):
@@ -295,6 +295,7 @@
dir = os.path.dirname(os.path.abspath(__file__))
path = os.path.join(dir, path)
path = os.path.abspath(path)
+
with open(path) as fd:
config = yaml.load(fd)
return config
@@ -308,6 +309,7 @@
log.info(" / ____ \| |__| | | | | | \ \ / ____ \| |\ | | |__| | |____| | ")
log.info(" /_/ \_\_____/ |_| |_| _\_\/_/ \_\_| \_| \____/|______|_| ")
log.info(" /\ | | | | ")
+ log.info(' _ _ _ ')
log.info(" / \ __| | __ _ _ __ | |_ ___ _ __ ")
log.info(" / /\ \ / _` |/ _` | '_ \| __/ _ \ '__| ")
log.info(" / ____ \ (_| | (_| | |_) | || __/ | ")
@@ -322,42 +324,45 @@
class Main(object):
def __init__(self):
+ try:
+ self.args = args = parse_args()
+ self.config = load_config(args)
- self.args = args = parse_args()
- self.config = load_config(args)
+ verbosity_adjust = (args.verbose or 0) - (args.quiet or 0)
+ self.log = setup_logging(self.config.get('logging', {}),
+ args.instance_id,
+ verbosity_adjust=verbosity_adjust)
+ self.log.info('container-number-extractor',
+ regex=args.container_name_regex)
- verbosity_adjust = (args.verbose or 0) - (args.quiet or 0)
- self.log = setup_logging(self.config.get('logging', {}),
- args.instance_id,
- verbosity_adjust=verbosity_adjust)
- self.log.info('container-number-extractor',
- regex=args.container_name_regex)
+ if args.debug_enabled:
+ setup_remote_debug(args.debug_host, args.debug_port, self.log)
- if args.debug_enabled:
- setup_remote_debug(args.debug_host, args.debug_port, self.log)
+ self.adtran_olt_adapter_version = self.get_version()
+ self.log.info('ADTRAN-OLT-Adapter-Version',
+ version=self.adtran_olt_adapter_version)
- self.adtran_olt_adapter_version = self.get_version()
- self.log.info('ADTRAN-OLT-Adapter-Version', version=self.adtran_olt_adapter_version)
+ if not args.no_banner:
+ print_banner(self.log)
- if not args.no_banner:
- print_banner(self.log)
+ self.adapter = None
- self.adapter = None
- self.core_proxy = None
- self.adapter_proxy = None
+ # Create a unique instance id using the passed-in instance id and
+ # UTC timestamp
+ current_time = arrow.utcnow().timestamp
+ self.instance_id = self.args.instance_id + '_' + str(current_time)
- # Create a unique instance id using the passed-in instance id and
- # UTC timestamp
- current_time = arrow.utcnow().timestamp
- self.instance_id = self.args.instance_id + '_' + str(current_time)
+ self.core_topic = args.core_topic
+ self.listening_topic = args.name
+ self.startup_components()
- self.core_topic = args.core_topic
- self.listening_topic = args.name
- self.startup_components()
+ if not args.no_heartbeat:
+ self.start_heartbeat()
+ self.start_kafka_cluster_heartbeat(self.instance_id)
- if not args.no_heartbeat:
- self.start_heartbeat()
- self.start_kafka_cluster_heartbeat(self.instance_id)
+ except Exception as e:
+ self.log.exception('unhandled-exception', e=e)
+ raise
def get_version(self):
path = defs['version_file']
@@ -442,6 +447,7 @@
kv_store=self.args.backend,
default_topic=self.args.name,
group_id_prefix=self.args.instance_id,
+ # Needs to assign a real class
target_cls=adtran_request_handler
)
).start()
@@ -543,8 +549,8 @@
kafka_cluster_proxy.send_message(topic, dumps(message))
else:
self.log.error('kafka-proxy-unavailable')
- except Exception, err:
- self.log.exception('failed-sending-message-heartbeat', e=err)
+ except Exception as e:
+ self.log.exception('failed-sending-message-heartbeat', e=e)
try:
t0 = time.time()
diff --git a/adapters/adtran_olt/resources/adtran_olt_resource_manager.py b/adapters/adtran_olt/resources/adtran_olt_resource_manager.py
index caf5a46..8cce46c 100644
--- a/adapters/adtran_olt/resources/adtran_olt_resource_manager.py
+++ b/adapters/adtran_olt/resources/adtran_olt_resource_manager.py
@@ -245,7 +245,7 @@
# we need to derive the ONU Id for which the packet arrived based
# on the pon_intf and gemport available in the packet_indication
# self.kv_store[str(pon_intf_gemport)] = ' '.join(map(str, (onu_id, uni_id)))
- self.kv_store.put(self._make_path(str(pon_intf_gemport)), ' '.join(map(str, (onu_id, uni_id)))
+ self.kv_store.put(self._make_path(str(pon_intf_gemport)), ' '.join(map(str, (onu_id, uni_id))))
def get_onu_uni_from_ponport_gemport(self, pon_port, gemport):
pon_intf_gemport = (pon_port, gemport)