• 实验7:基于REST API的SDN北向应用实践


    基本要求

    • 构建拓扑sudo mn --topo=single,3 --mac --controller=remote,ip=127.0.0.1,port=6633 --switch ovsk,protocols=OpenFlow13

    ODL操作

    • 删除流表Python代码:
          #!/usr/bin/python
          import requests
          from requests.auth import HTTPBasicAuth
    
          if __name__ == "__main__":
              url = 'http://127.0.0.1:8181/restconf/config/opendaylight-inventory:nodes/node/openflow:1/'
              headers = {'Content-Type': 'application/json'}
              res = requests.delete(url, headers=headers, auth=HTTPBasicAuth('admin', 'admin'))
              print (res.content)
    
    • 下发流表Python代码:
          #!/usr/bin/python
          import requests
          from requests.auth import HTTPBasicAuth
    
          if __name__ == "__main__":
              url = 'http://127.0.0.1:8181/restconf/config/opendaylight-inventory:nodes/node/openflow:1/flow-node-inventory:table/0/flow/1'
              with open("./flowtable.json") as f:
                  jstr = f.read()
              headers = {'Content-Type': 'application/json'}
              res = requests.put(url, jstr, headers=headers, auth=HTTPBasicAuth('admin', 'admin'))
              print (res.content)
    
    
    • flowtable.json文件:
          {
            "flow": [
              {
                "id": "1",
                "match": {
                  "in-port": "1",
                  "ethernet-match": {
                    "ethernet-type": {
                      "type": "0x0800"
                    }
                  },
                  "ipv4-destination": "10.0.0.3/32"
                },
                "instructions": {
                  "instruction": [
                    {
                      "order": "0",
                      "apply-actions": {
                        "action": [
                          {
                            "order": "0",
                            "drop-action": {}
                          }
                        ]
                      }
                    }
                  ]
                },
                "flow-name": "flow1",
                "priority": "65535",
                "hard-timeout": "20",
                "cookie": "2",
                "table_id": "0"
              }
            ]
          }
    

    • 获取流表信息Python代码:
          #!/usr/bin/python
          import requests
          from requests.auth import HTTPBasicAuth
    
          if __name__ == "__main__":
              url = 'http://127.0.0.1:8181/restconf/operational/opendaylight-inventory:nodes/node/openflow:1/flow-node-inventory:table/0/opendaylight-flow-table-statistics:flow-table-statistics'
              headers = {'Content-Type': 'application/json'}
              res = requests.get(url,headers=headers, auth=HTTPBasicAuth('admin', 'admin'))
              print (res.content)
    
    
    

    Ryu操作

    • 下发流表Python代码
          #!/usr/bin/python
          import requests
    
          if __name__ == "__main__":
              url = 'http://127.0.0.1:8080/stats/flowentry/add'
              with open("./flowtable.json") as f:
                  jstr = f.read()
              headers = {'Content-Type': 'application/json'}
              res = requests.put(url, jstr, headers=headers)
              print (res.content)
    
    
    
    • flowtable.json文件:
          {
              "dpid": 1,
              "cookie": 1,
              "cookie_mask": 1,
              "table_id": 0,
              "hard_timeout": 20,
              "priority": 65535,
              "flags": 1,
              "match":{
                  "in_port":1
              },
              "actions":[
    
              ]
           }
    
    

    执行结果

    Vlan划分

    • 搭建拓扑,使用openflow13协议,Python代码:
          #!/usr/bin/env python
          from mininet.topo import Topo
    
          class MyTopo(Topo):
              def __init__(self):
                  # initilaize topology
                  Topo.__init__(self)
    
                  self.addSwitch("s1")
                  self.addSwitch("s2")
    
                  self.addHost("h1")
                  self.addHost("h2")
                  self.addHost("h3")
                  self.addHost("h4")
    
                  self.addLink("s1", "h1")
                  self.addLink("s1", "h2")
                  self.addLink("s2", "h3")
                  self.addLink("s2", "h4")
                  self.addLink("s1", "s2")
    
          topos = {'mytopo': (lambda: MyTopo())}
    
    
    • 创建拓扑命令:
          sudo sudo mn  --custom mytopo.py --topo mytopo --mac --controller=remote,ip=127.0.0.1,port=6633 --switch ovsk,protocols=OpenFlow13
    
    

    • 脚本:
          # 将主机1,2发送来的包打上vlan标记
          curl -X POST -d '{
              "dpid": 1,
              "priority": 1,
              "match":{
                  "in_port": 1
              },
              "actions":[
                  {
                      "type": "PUSH_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                      "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                  },
                  {
                      "type": "SET_FIELD",
                      "field": "vlan_vid",     # Set VLAN ID
                      "value": 4096            # Describe sum of vlan_id(e.g. 6) | OFPVID_PRESENT(0x1000=4096)
                  },
                  {
                      "type": "OUTPUT",
                      "port": 3
                  }
              ]
           }' http://localhost:8080/stats/flowentry/add
    
           curl -X POST -d '{
              "dpid": 1,
              "priority": 1,
              "match":{
                  "in_port": 2
              },
              "actions":[
                  {
                      "type": "PUSH_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                      "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                  },
                  {
                      "type": "SET_FIELD",
                      "field": "vlan_vid",     # Set VLAN ID
                      "value": 4097            # Describe sum of vlan_id(e.g. 6) | OFPVID_PRESENT(0x1000=4096)
                  },
                  {
                      "type": "OUTPUT",
                      "port": 3
                  }
              ]
           }' http://localhost:8080/stats/flowentry/add
    
          # 将主机3,4发送来的包取出vlan标记
           curl -X POST -d '{
              "dpid": 1,
              "priority": 1,
              "match":{
                  "vlan_vid": 0
              },
              "actions":[
                  {
                      "type": "POP_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                      "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                  },
                  {
                      "type": "OUTPUT",
                      "port": 1
                  }
              ]
           }' http://localhost:8080/stats/flowentry/add
    
           curl -X POST -d '{
              "dpid": 1,
              "priority": 1,
              "match":{
                  "vlan_vid": 1
              },
              "actions":[
                  {
                      "type": "POP_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                      "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                  },
                  {
                      "type": "OUTPUT",
                      "port": 2
                  }
              ]
           }' http://localhost:8080/stats/flowentry/add
    
          # 将主机3,4发送来的包打上vlan标记
           curl -X POST -d '{
              "dpid": 2,
              "priority": 1,
              "match":{
                  "in_port": 1
              },
              "actions":[
                  {
                      "type": "PUSH_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                      "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                  },
                  {
                      "type": "SET_FIELD",
                      "field": "vlan_vid",     # Set VLAN ID
                      "value": 4096            # Describe sum of vlan_id(e.g. 6) | OFPVID_PRESENT(0x1000=4096)
                  },
                  {
                      "type": "OUTPUT",
                      "port": 3
                  }
              ]
           }' http://localhost:8080/stats/flowentry/add
    
           curl -X POST -d '{
              "dpid": 2,
              "priority": 1,
              "match":{
                  "in_port": 2
              },
              "actions":[
                  {
                      "type": "PUSH_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                      "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                  },
                  {
                      "type": "SET_FIELD",
                      "field": "vlan_vid",     # Set VLAN ID
                      "value": 4097            # Describe sum of vlan_id(e.g. 6) | OFPVID_PRESENT(0x1000=4096)
                  },
                  {
                      "type": "OUTPUT",
                      "port": 3
                  }
              ]
           }' http://localhost:8080/stats/flowentry/add
    
           curl -X POST -d '{
              "dpid": 2,
              "priority": 1,
              "match":{
                  "vlan_vid": 0
              },
              "actions":[
                  {
                      "type": "POP_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                      "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                  },
                  {
                      "type": "OUTPUT",
                      "port": 1
                  }
              ]
           }' http://localhost:8080/stats/flowentry/add
    
           curl -X POST -d '{
              "dpid": 2,
              "priority": 1,
              "match":{
                  "vlan_vid": 1
              },
              "actions":[
                  {
                      "type": "POP_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                      "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                  },
                  {
                      "type": "OUTPUT",
                      "port": 2
                  }
              ]
           }' http://localhost:8080/stats/flowentry/add
    
    

    进阶要求

    • 将上述以python代码实现,首先删除s1和s2上的流表:
          curl -X DELETE http://localhost:8080/stats/flowentry/clear/1
          curl -X DELETE http://localhost:8080/stats/flowentry/clear/2
    
    
    • 编程代码:
          #!/usr/bin/python
          import json
    
          import requests
    
          if __name__ == "__main__":
              url = 'http://127.0.0.1:8080/stats/flowentry/add'
              headers = {'Content-Type': 'application/json'}
              flow1 = {
                  "dpid": 1,
                  "priority": 1,
                  "match":{
                      "in_port": 1
                  },
                  "actions":[
                      {
                          "type": "PUSH_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                          "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                      },
                      {
                          "type": "SET_FIELD",
                          "field": "vlan_vid",     # Set VLAN ID
                          "value": 4096            # Describe sum of vlan_id(e.g. 6) | OFPVID_PRESENT(0x1000=4096)
                      },
                      {
                          "type": "OUTPUT",
                          "port": 3
                      }
                  ]
              }
              flow2 = {
                  "dpid": 1,
                  "priority": 1,
                  "match":{
                      "in_port": 2
                  },
                  "actions":[
                      {
                          "type": "PUSH_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                          "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                      },
                      {
                          "type": "SET_FIELD",
                          "field": "vlan_vid",     # Set VLAN ID
                          "value": 4097            # Describe sum of vlan_id(e.g. 6) | OFPVID_PRESENT(0x1000=4096)
                      },
                      {
                          "type": "OUTPUT",
                          "port": 3
                      }
                  ]
              }
              flow3 = {
                  "dpid": 1,
                  "priority": 1,
                  "match":{
                      "vlan_vid": 0
                  },
                  "actions":[
                      {
                          "type": "POP_VLAN",     # Push a new VLAN tag if a input frame is non-VLAN-tagged
                          "ethertype": 33024       # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                      },
                      {
                          "type": "OUTPUT",
                          "port": 1
                      }
                  ]
              }
              flow4 = {
                  "dpid": 1,
                  "priority": 1,
                  "match": {
                      "vlan_vid": 1
                  },
                  "actions": [
                      {
                          "type": "POP_VLAN",  # Push a new VLAN tag if a input frame is non-VLAN-tagged
                          "ethertype": 33024  # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                      },
                      {
                          "type": "OUTPUT",
                          "port": 2
                      }
                  ]
              }
              flow5 = {
                  "dpid": 2,
                  "priority": 1,
                  "match": {
                      "in_port": 1
                  },
                  "actions": [
                      {
                          "type": "PUSH_VLAN",  # Push a new VLAN tag if a input frame is non-VLAN-tagged
                          "ethertype": 33024  # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                      },
                      {
                          "type": "SET_FIELD",
                          "field": "vlan_vid",  # Set VLAN ID
                          "value": 4096  # Describe sum of vlan_id(e.g. 6) | OFPVID_PRESENT(0x1000=4096)
                      },
                      {
                          "type": "OUTPUT",
                          "port": 3
                      }
                  ]
              }
              flow6 = {
                  "dpid": 2,
                  "priority": 1,
                  "match": {
                      "in_port": 2
                  },
                  "actions": [
                      {
                          "type": "PUSH_VLAN",  # Push a new VLAN tag if a input frame is non-VLAN-tagged
                          "ethertype": 33024  # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                      },
                      {
                          "type": "SET_FIELD",
                          "field": "vlan_vid",  # Set VLAN ID
                          "value": 4097  # Describe sum of vlan_id(e.g. 6) | OFPVID_PRESENT(0x1000=4096)
                      },
                      {
                          "type": "OUTPUT",
                          "port": 3
                      }
                  ]
              }
              flow7 = {
                  "dpid": 2,
                  "priority": 1,
                  "match": {
                      "vlan_vid": 0
                  },
                  "actions": [
                      {
                          "type": "POP_VLAN",  # Push a new VLAN tag if a input frame is non-VLAN-tagged
                          "ethertype": 33024  # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                      },
                      {
                          "type": "OUTPUT",
                          "port": 1
                      }
                  ]
              }
              flow8 = {
                  "dpid": 2,
                  "priority": 1,
                  "match": {
                      "vlan_vid": 0
                  },
                  "actions": [
                      {
                          "type": "POP_VLAN",  # Push a new VLAN tag if a input frame is non-VLAN-tagged
                          "ethertype": 33024  # Ethertype 0x8100(=33024): IEEE 802.1Q VLAN-tagged frame
                      },
                      {
                          "type": "OUTPUT",
                          "port": 1
                      }
                  ]
              }
              res1 = requests.post(url, json.dumps(flow1), headers=headers)
              res2 = requests.post(url, json.dumps(flow2), headers=headers)
              res3 = requests.post(url, json.dumps(flow3), headers=headers)
              res4 = requests.post(url, json.dumps(flow4), headers=headers)
              res5 = requests.post(url, json.dumps(flow5), headers=headers)
              res6 = requests.post(url, json.dumps(flow6), headers=headers)
              res7 = requests.post(url, json.dumps(flow7), headers=headers)
              res8 = requests.post(url, json.dumps(flow8), headers=headers)
    
    

    总结

    这次作业难度中等,主要在熟悉ODL和Ryu的RestfulAPI使用。本次实验所耗费时间相对较久。但同时对ODL 和 Ryu的使用和有了深刻了解。 遇到了一些问题,这边做一下记录:

    • requests的请求类型需要时刻注意,由于请求类型不对,而Ryu一直报错404,所以一时没有定位到错误
    • 流表残留
      解决方法:记得在实验开始之前删除流表避免残余流表的影响,需要下载curl
    • 在实验前要先清空已有流表,防止先前实验残余流表造成影响
  • 相关阅读:
    egret-使用URLLoader 设置不同的dataFormat 加载不同的资源
    egret新手指南--自定义组件
    事件的三个阶段
    事件派发,事件机制
    屏幕适配
    断线重连机制
    电影屏幕字从天上掉下来的效果
    使用select2 实现select多选与初始化数据。
    ul高度为0 li高度为0
    php生成json文件,以zip压缩包批量下载。
  • 原文地址:https://www.cnblogs.com/xiao-qingjiang/p/15456771.html
Copyright © 2020-2023  润新知