Daniel Park
Committed by Gerrit Code Review

[ONOS-4797] Implement the Driver for handling Arista switch

Arista switch with its recent network OS, EOS, supports remote configuration & control. The protocol for this is Arista's proprietary but REST style.
Since ONOS has already REST southbound protocol, the control of Arista switch can be easily done by using this.

- Implemnted driver Loader for Arista switch
- Implemented DeviceDescriptionDiscovery for Arista switch
- [Deleted] Implemented the method sending post to Arista switch and return the result as a String

Change-Id: I9d4b8f0d707361949ff530ff414adb0437ae87d9
...@@ -55,6 +55,7 @@ CORE = [ ...@@ -55,6 +55,7 @@ CORE = [
55 '//drivers/netconf:onos-drivers-netconf-oar', 55 '//drivers/netconf:onos-drivers-netconf-oar',
56 '//drivers/ovsdb:onos-drivers-ovsdb-oar', 56 '//drivers/ovsdb:onos-drivers-ovsdb-oar',
57 '//drivers/optical:onos-drivers-optical-oar', 57 '//drivers/optical:onos-drivers-optical-oar',
58 + '//drivers/arista:onos-drivers-arista-oar',
58 59
59 '//providers/netconf/device:onos-providers-netconf-device', 60 '//providers/netconf/device:onos-providers-netconf-device',
60 '//providers/openflow/device:onos-providers-openflow-device', 61 '//providers/openflow/device:onos-providers-openflow-device',
......
1 +COMPILE_DEPS = [
2 + '//lib:CORE_DEPS',
3 + '//lib:javax.ws.rs-api',
4 + '//incubator/api:onos-incubator-api',
5 + '//utils/rest:onlab-rest',
6 + '//drivers/utilities:onos-drivers-utilities',
7 + '//protocols/rest/api:onos-protocols-rest-api',
8 +]
9 +
10 +TEST_DEPS = [
11 + '//lib:TEST_ADAPTERS',
12 + '//core/api:onos-api-tests',
13 +]
14 +
15 +osgi_jar_with_tests (
16 + deps = COMPILE_DEPS,
17 + test_deps = TEST_DEPS,
18 + resources_root = 'src/main/resources',
19 + resources = glob(['src/main/resources/**']),
20 +)
21 +
22 +onos_app (
23 + title = 'Arista Device Drivers',
24 + category = 'Drivers',
25 + url = 'http://onosproject.org',
26 + description = 'ONOS Arista Device Drivers application.',
27 + required_apps = [ 'org.onosproject.restsb' ],
28 +)
...\ No newline at end of file ...\ No newline at end of file
1 +<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
2 +<!--
3 + ~ Copyright 2016 Open Networking Laboratory
4 + ~
5 + ~ Licensed under the Apache License, Version 2.0 (the "License");
6 + ~ you may not use this file except in compliance with the License.
7 + ~ You may obtain a copy of the License at
8 + ~
9 + ~ http://www.apache.org/licenses/LICENSE-2.0
10 + ~
11 + ~ Unless required by applicable law or agreed to in writing, software
12 + ~ distributed under the License is distributed on an "AS IS" BASIS,
13 + ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 + ~ See the License for the specific language governing permissions and
15 + ~ limitations under the License.
16 + -->
17 +<features xmlns="http://karaf.apache.org/xmlns/features/v1.2.0" name="${project.artifactId}-${project.version}">
18 + <feature name="${project.artifactId}" version="${project.version}"
19 + description="${project.description}">
20 + <feature>onos-api</feature>
21 + <bundle>mvn:${project.groupId}/${project.artifactId}/${project.version}</bundle>
22 + <bundle>mvn:${project.groupId}/onos-drivers-utilities/${project.version}</bundle>
23 + </feature>
24 +</features>
1 +<?xml version="1.0" encoding="UTF-8"?>
2 +<!--
3 + ~ Copyright 2016 Open Networking Laboratory
4 + ~
5 + ~ Licensed under the Apache License, Version 2.0 (the "License");
6 + ~ you may not use this file except in compliance with the License.
7 + ~ You may obtain a copy of the License at
8 + ~
9 + ~ http://www.apache.org/licenses/LICENSE-2.0
10 + ~
11 + ~ Unless required by applicable law or agreed to in writing, software
12 + ~ distributed under the License is distributed on an "AS IS" BASIS,
13 + ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 + ~ See the License for the specific language governing permissions and
15 + ~ limitations under the License.
16 + -->
17 +
18 +<project xmlns="http://maven.apache.org/POM/4.0.0"
19 + xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
20 + xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
21 + <parent>
22 + <artifactId>onos-drivers-general</artifactId>
23 + <groupId>org.onosproject</groupId>
24 + <version>1.7.0-SNAPSHOT</version>
25 + </parent>
26 + <modelVersion>4.0.0</modelVersion>
27 +
28 + <artifactId>onos-drivers-arista</artifactId>
29 + <packaging>bundle</packaging>
30 +
31 + <description>Arista device drivers</description>
32 +
33 + <properties>
34 + <onos.app.name>org.onosproject.drivers.arista</onos.app.name>
35 + <onos.app.title>Arista Device Drivers</onos.app.title>
36 + <onos.app.category>Drivers</onos.app.category>
37 + <onos.app.url>https://eos.arista.com/arista-eapi-101</onos.app.url>
38 + <onos.app.requires>
39 + org.onosproject.restsb
40 + </onos.app.requires>
41 + </properties>
42 +
43 + <dependencies>
44 + <dependency>
45 + <groupId>org.onosproject</groupId>
46 + <artifactId>onos-drivers-utilities</artifactId>
47 + <version>${project.version}</version>
48 + </dependency>
49 + <dependency>
50 + <groupId>org.onosproject</groupId>
51 + <artifactId>onos-restsb-api</artifactId>
52 + <version>${project.version}</version>
53 + </dependency>
54 + </dependencies>
55 +
56 +</project>
...\ No newline at end of file ...\ No newline at end of file
1 +/*
2 + * Copyright 2016 Open Networking Laboratory
3 + *
4 + * Licensed under the Apache License, Version 2.0 (the "License");
5 + * you may not use this file except in compliance with the License.
6 + * You may obtain a copy of the License at
7 + *
8 + * http://www.apache.org/licenses/LICENSE-2.0
9 + *
10 + * Unless required by applicable law or agreed to in writing, software
11 + * distributed under the License is distributed on an "AS IS" BASIS,
12 + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 + * See the License for the specific language governing permissions and
14 + * limitations under the License.
15 + */
16 +
17 +package org.onosproject.drivers.arista;
18 +
19 +import org.apache.felix.scr.annotations.Component;
20 +import org.onosproject.net.driver.AbstractDriverLoader;
21 +
22 +/**
23 + * Loader for Arista device drivers.
24 + */
25 +@Component(immediate = true)
26 +public class AristaDriversLoader extends AbstractDriverLoader {
27 + public AristaDriversLoader() {
28 + super("/arista-drivers.xml");
29 + }
30 +}
1 +/*
2 + * Copyright 2016 Open Networking Laboratory
3 + *
4 + * Licensed under the Apache License, Version 2.0 (the "License");
5 + * you may not use this file except in compliance with the License.
6 + * You may obtain a copy of the License at
7 + *
8 + * http://www.apache.org/licenses/LICENSE-2.0
9 + *
10 + * Unless required by applicable law or agreed to in writing, software
11 + * distributed under the License is distributed on an "AS IS" BASIS,
12 + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 + * See the License for the specific language governing permissions and
14 + * limitations under the License.
15 + */
16 +
17 +package org.onosproject.drivers.arista;
18 +
19 +import java.io.ByteArrayInputStream;
20 +import java.io.IOException;
21 +import com.fasterxml.jackson.databind.JsonNode;
22 +import com.fasterxml.jackson.databind.ObjectMapper;
23 +import com.fasterxml.jackson.databind.node.ArrayNode;
24 +import com.fasterxml.jackson.databind.node.ObjectNode;
25 +import com.google.common.collect.Lists;
26 +import org.onosproject.net.AnnotationKeys;
27 +import org.onosproject.net.DefaultAnnotations;
28 +import org.onosproject.net.DeviceId;
29 +import org.onosproject.net.Port;
30 +import org.onosproject.net.PortNumber;
31 +import org.onosproject.net.SparseAnnotations;
32 +import org.onosproject.net.device.DefaultPortDescription;
33 +import org.onosproject.net.device.DeviceDescription;
34 +import org.onosproject.net.device.DeviceDescriptionDiscovery;
35 +import org.onosproject.net.device.PortDescription;
36 +import org.onosproject.net.driver.AbstractHandlerBehaviour;
37 +import org.onosproject.net.driver.DriverHandler;
38 +import org.onosproject.protocol.rest.RestSBController;
39 +import javax.ws.rs.core.MediaType;
40 +import org.slf4j.Logger;
41 +
42 +import java.util.List;
43 +
44 +import static com.google.common.base.Preconditions.checkNotNull;
45 +import static org.slf4j.LoggerFactory.getLogger;
46 +
47 +/**
48 + * Discovers the ports from Arista EOS device.
49 + */
50 +public class DeviceDescriptionDiscoveryAristaImpl extends AbstractHandlerBehaviour
51 + implements DeviceDescriptionDiscovery {
52 +
53 + private static final String JSON = "json";
54 + private static final String RESULT = "result";
55 + private static final String INTERFACE_STATUSES = "interfaceStatuses";
56 + private static final String LINK_STATUS = "linkStatus";
57 + private static final String LINE_PROTOCOL_STATUS = "lineProtocolStatus";
58 + private static final String BANDWIDTH = "bandwidth";
59 + private static final String ETHERNET = "Ethernet";
60 + private static final String MANAGEMENT = "Management";
61 + private static final String INTERFACE_TYPE = "interfaceType";
62 + private static final int WEIGHTING_FACTOR_MANAGEMENT_INTERFACE = 100;
63 + private static final String JSONRPC = "jsonrpc";
64 + private static final String METHOD = "method";
65 + private static final String RUN_CMDS = "runCmds";
66 + private static final String VERSION = "version";
67 + private static final String ID = "id";
68 + private static final String GET_PORT = "GetPort";
69 + private static final String PARAMS = "params";
70 + private static final String FORMAT = "format";
71 + private static final String TIMESTAMPS = "timestamps";
72 + private static final String CMDS = "cmds";
73 + private static final String SHOW_INTERFACES_STATUS = "show interfaces status";
74 + private static final String TWO_POINT_ZERO = "2.0";
75 + private static final long MBPS = 1000000;
76 +
77 + private final Logger log = getLogger(getClass());
78 +
79 + private static final String API_ENDPOINT = "/command-api/";
80 +
81 + @Override
82 + public DeviceDescription discoverDeviceDetails() {
83 + log.info("No description to be added for device");
84 + //TODO to be implemented if needed.
85 + return null;
86 + }
87 +
88 + @Override
89 + public List<PortDescription> discoverPortDetails() {
90 + List<PortDescription> ports = Lists.newArrayList();
91 + DriverHandler handler = handler();
92 + RestSBController controller = checkNotNull(handler.get(RestSBController.class));
93 + DeviceId deviceId = handler.data().deviceId();
94 +
95 + ObjectMapper mapper = new ObjectMapper();
96 +
97 + ObjectNode sendObjNode = mapper.createObjectNode();
98 +
99 + sendObjNode.put(JSONRPC, TWO_POINT_ZERO)
100 + .put(METHOD, RUN_CMDS)
101 + .put(ID, GET_PORT)
102 + .putObject(PARAMS)
103 + .put(FORMAT, JSON)
104 + .put(TIMESTAMPS, false)
105 + .put(VERSION, 1)
106 + .putArray(CMDS).add(SHOW_INTERFACES_STATUS);
107 +
108 + String response = controller.post(deviceId, API_ENDPOINT,
109 + new ByteArrayInputStream(sendObjNode.toString().getBytes()),
110 + MediaType.APPLICATION_JSON, String.class);
111 +
112 + try {
113 + ObjectNode node = (ObjectNode) mapper.readTree(response);
114 + ArrayNode arrayNode = (ArrayNode) node.get(RESULT);
115 +
116 + JsonNode jsonNode = arrayNode.iterator().next().get(INTERFACE_STATUSES);
117 +
118 + jsonNode.fieldNames().forEachRemaining(name -> {
119 + JsonNode interfaceNode = jsonNode.get(name);
120 +
121 + Long bandwidth = interfaceNode.path(BANDWIDTH).asLong() / MBPS;
122 +
123 + SparseAnnotations annotations = DefaultAnnotations.builder()
124 + .set(AnnotationKeys.BANDWIDTH, bandwidth.toString())
125 + .set(AnnotationKeys.NAME, name)
126 + .set(LINK_STATUS, interfaceNode.path(LINK_STATUS).asText())
127 + .set(LINE_PROTOCOL_STATUS, interfaceNode.path(LINE_PROTOCOL_STATUS).asText())
128 + .set(INTERFACE_TYPE, interfaceNode.path(INTERFACE_TYPE).asText())
129 + .build();
130 +
131 + PortDescription portDescription = new DefaultPortDescription(PortNumber
132 + .portNumber(getPortNumber(name)),
133 + true, Port.Type.FIBER, bandwidth, annotations);
134 + ports.add(portDescription);
135 +
136 + });
137 +
138 + } catch (IOException e) {
139 + log.warn("IO exception occured because of ", e);
140 + }
141 + return ports;
142 + }
143 +
144 + private int getPortNumber(String interfaceName) {
145 + if (interfaceName.startsWith(ETHERNET)) {
146 + return Integer.valueOf(interfaceName.substring(ETHERNET.length()));
147 + } else {
148 + return Integer.valueOf(interfaceName.substring(MANAGEMENT.length())).intValue()
149 + + WEIGHTING_FACTOR_MANAGEMENT_INTERFACE;
150 + }
151 + }
152 +}
153 +
1 +/*
2 + * Copyright 2016 Open Networking Laboratory
3 + *
4 + * Licensed under the Apache License, Version 2.0 (the "License");
5 + * you may not use this file except in compliance with the License.
6 + * You may obtain a copy of the License at
7 + *
8 + * http://www.apache.org/licenses/LICENSE-2.0
9 + *
10 + * Unless required by applicable law or agreed to in writing, software
11 + * distributed under the License is distributed on an "AS IS" BASIS,
12 + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 + * See the License for the specific language governing permissions and
14 + * limitations under the License.
15 + */
16 +
17 +/**
18 + * Package for Arista EOS device drivers.
19 + */
20 +package org.onosproject.drivers.arista;
...\ No newline at end of file ...\ No newline at end of file
1 +<?xml version="1.0" encoding="UTF-8"?>
2 +<!--
3 + ~ Copyright 2016 Open Networking Laboratory
4 + ~
5 + ~ Licensed under the Apache License, Version 2.0 (the "License");
6 + ~ you may not use this file except in compliance with the License.
7 + ~ You may obtain a copy of the License at
8 + ~
9 + ~ http://www.apache.org/licenses/LICENSE-2.0
10 + ~
11 + ~ Unless required by applicable law or agreed to in writing, software
12 + ~ distributed under the License is distributed on an "AS IS" BASIS,
13 + ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 + ~ See the License for the specific language governing permissions and
15 + ~ limitations under the License.
16 + -->
17 +<drivers>
18 + <driver name="restArista" manufacturer="Arista Networks" hwVersion="1.0.0" swVersion="1.0.0">
19 + <behaviour api="org.onosproject.net.device.DeviceDescriptionDiscovery"
20 + impl="org.onosproject.drivers.arista.DeviceDescriptionDiscoveryAristaImpl"/>
21 + </driver>
22 +</drivers>
23 +
...@@ -43,6 +43,7 @@ ...@@ -43,6 +43,7 @@
43 <module>bmv2</module> 43 <module>bmv2</module>
44 <module>corsa</module> 44 <module>corsa</module>
45 <module>optical</module> 45 <module>optical</module>
46 + <module>arista</module>
46 </modules> 47 </modules>
47 48
48 <!--<properties> 49 <!--<properties>
......