Tunnel loadbalancing policy: phase1 support
diff --git a/cli/desc/version200/core.py b/cli/desc/version200/core.py
index 0e0f3c1..9a8b8bc 100755
--- a/cli/desc/version200/core.py
+++ b/cli/desc/version200/core.py
@@ -2399,12 +2399,37 @@
 SHOW_TUNNEL_FORMAT = {
     'show_tunnel' : {
         'field-orderings' : {
-            'default' : [ 'Idx', 'tunnelId', 'policies','tunnelPath','labelStack',],
-            'details' : [ 'Idx', 'tunnelId', 'policies','tunnelPath','labelStack', 'dpidGroup',],
+            'default' : [ 'Idx', 'tunnelId', 'policies','tunnelset','tunnelPath','labelStack',],
+            'details' : [ 'Idx', 'tunnelId', 'policies','tunnelset','tunnelPath','labelStack', 'dpidGroup',],
             },
         'fields': {
             'tunnelId'         : { 'verbose-name' : 'Id',
                                },
+            'tunnelset'         : { 'verbose-name' : 'tunnelset',
+                               },
+            'dpidGroup'         : { 'verbose-name' : 'Dpid(Node Id)/Group',
+                               },
+            'labelStack'         : { 'verbose-name' : 'Label Stack [Outer-->Inner]',
+                               },
+            'tunnelPath'         : { 'verbose-name' : 'Tunnel Path [Head-->Tail]',
+                               },
+                   }
+        },
+}
+
+SHOW_TUNNELSET_FORMAT = {
+    'show_tunnelset' : {
+        'field-orderings' : {
+            'default' : [ 'Idx', 'tunnelsetId', 'policies','tunnelId','tunnelPath','labelStack',],
+            'details' : [ 'Idx', 'tunnelsetId', 'policies','tunnelId','tunnelPath','labelStack', 'dpidGroup',],
+            },
+        'fields': {
+            'tunnelsetId'         : { 'verbose-name' : 'Id',
+                               },
+            'tunnelId'         : { 'verbose-name' : 'tunnelId',
+                               },
+            'tunnelset'         : { 'verbose-name' : 'tunnelset',
+                               },
             'dpidGroup'         : { 'verbose-name' : 'Dpid(Node Id)/Group',
                                },
             'labelStack'         : { 'verbose-name' : 'Label Stack [Outer-->Inner]',
diff --git a/cli/desc/version200/policy.py b/cli/desc/version200/policy.py
index eac0209..ad99363 100644
--- a/cli/desc/version200/policy.py
+++ b/cli/desc/version200/policy.py
@@ -254,7 +254,7 @@
                                 'proc' : 'create-policy',
                             },
                          ),
-        'completion'   : 'tunnelid-completion',
+        'completion'   : 'tunnel-id-completion',
         'field'        : 'tunnel-id',
         'type'         : 'identifier',
         'syntax-help'  : 'Enter tunnel id',
@@ -263,6 +263,30 @@
     }
 }
 
+POLICY_TUNNELSET_ID_COMMAND_DESCRIPTION = {
+    'name'            : 'tunnelset',
+    'mode'            : 'config-policy',
+    #'obj-type'        : 'policy-config',
+    'command-type'    : 'config',
+    'short-help'      : 'Configure tunnelset id',
+    #'doc'             : 'policy|tunnel',
+    #'doc-example'     : 'policy|policy-tunnel-example',
+    'parent-field'    : 'policy',
+    'args' : {
+        'action'       : (
+                            {
+                                'proc' : 'create-policy',
+                            },
+                         ),
+        'completion'   : 'tunnelset-id-completion',
+        'field'        : 'tunnelset-id',
+        'type'         : 'identifier',
+        'syntax-help'  : 'Enter tunnelset id',
+        'doc'          : 'policy|tunnelset-id',
+        'doc-include'  : [ 'type-doc' ],
+    }
+}
+
 POLICY_PRIORITY_COMMAND_DESCRIPTION = {
     'name'            : 'priority',
     'mode'            : 'config-policy',
@@ -322,6 +346,19 @@
                                     'completions'  : '$completions',
                                     }})
 
+def tunnelset_id_completion(prefix, completions):
+    query_url = "http://127.0.0.1:8000/rest/v1/showtunnelset"
+    result = command.sdnsh.store.rest_simple_request(query_url)
+    entries = json.loads(result)
+    for entry in entries:
+        if entry['tunnelsetId'].startswith(prefix):
+            completions[entry['tunnelsetId']+' '] = entry['tunnelsetId']
+    return
+
+command.add_completion('tunnelset-id-completion', tunnelset_id_completion,
+                       {'kwargs': { 'prefix'       : '$text',
+                                    'completions'  : '$completions',
+                                    }})
 
 def policy_id_completion(prefix, completions):
     query_url = "http://127.0.0.1:8000/rest/v1/showpolicy"
diff --git a/cli/desc/version200/tunnel.py b/cli/desc/version200/tunnel.py
index d79b012..a2bc0cd 100644
--- a/cli/desc/version200/tunnel.py
+++ b/cli/desc/version200/tunnel.py
@@ -2,12 +2,56 @@
 import json
 import fmtcnv
 
+TUNNELSET_SUBMODE_COMMAND_DESCRIPTION = {
+    'name'          : 'tunnelset',
+    'short-help'    : 'Enter tunnelset submode, configure tunnelset details',
+    'mode'          : 'config',
+    'parent-field'  : None,
+    'command-type'  : 'config-submode',
+    'obj-type'      : 'tunnelset-config',
+    'submode-name'  : 'config-tunnelset',
+    'doc'           : 'tunnelset|tunnelset',
+    'doc-example'   : 'tunnelset|tunnelset-example',
+    'args' : (
+        {
+            'field'        : 'tunnelset-id',
+            'type'         : 'identifier',
+            #'completion'   : 'complete-object-field',
+            'syntax-help'  : 'Enter a tunnelset name',
+            'doc'          : 'tunnelset|tunnelset',
+            'doc-include'  : [ 'type-doc' ],
+            #'completion'   : 'tunnelset-id-completion',
+            'action'       : (
+                                {
+                                    'proc' : 'create-tunnelset',
+                                },
+                                {
+                                    'proc' : 'push-mode-stack',
+                                },
+                              ),
+            'no-action': (
+                {
+                    'proc' : 'remove-tunnelset',
+                }
+            ),
+        }
+    )
+}
+
+TUNNELSET_CONFIG_FORMAT = {
+    'tunnelset-config' : {
+        'field-orderings' : {
+            'default' : [
+                          'tunnelset-id',
+                        ],
+        },
+    },
+}
 
 TUNNEL_SUBMODE_COMMAND_DESCRIPTION = {
     'name'          : 'tunnel',
     'short-help'    : 'Enter tunnel submode, configure tunnel details',
-    'mode'          : 'config',
-    'parent-field'  : None,
+    'mode'          : ['config', 'config-tunnelset'],
     'command-type'  : 'config-submode',
     'obj-type'      : 'tunnel-config',
     'submode-name'  : 'config-tunnel',
@@ -115,7 +159,7 @@
 # obj_type flow-entry field hard-timeout
 TUNNEL_NODE_ENTRY_COMMAND_DESCRIPTION = {
     'name'                : 'node',
-    'mode'                : 'config-tunnel',
+    'mode'                : 'config-tunnel*',
     'short-help'          : 'Set node for this tunnel',
     'doc'                 : 'tunnel|node',
     'doc-example'         : 'tunnel|node',
@@ -143,7 +187,7 @@
     )
 }
 
-SWITCH_TUNNEL_COMMAND_DESCRIPTION = {
+SHOW_TUNNEL_COMMAND_DESCRIPTION = {
     'name'                : 'show',
     'mode'                : 'login',
     'command-type'        : 'display-table',
@@ -180,6 +224,42 @@
     )
 }
 
+SHOW_TUNNELSET_COMMAND_DESCRIPTION = {
+    'name'                : 'show',
+    'mode'                : 'login',
+    'command-type'        : 'display-table',
+    'all-help'            : 'Show tunnelset information',
+    'short-help'          : 'Show tunnelset summary',
+    #'obj-type'            : 'switches',
+    'doc'                 : 'tunnelset|show',
+    'doc-example'         : 'tunnelset|show-example',
+    'args' : (
+        {
+            'token'  : 'tunnelset',
+            'field'  : 'showtunnelset',
+            'sort'   : ['tunnelsetId',],
+            'action' : 'display-rest',
+            'doc'    : 'tunnelset|show',
+            'url'    : [
+                        'showtunnelset',
+                       ],
+            'format' : 'show_tunnelset',
+        },
+              { 
+            'optional'   : True,
+            'choices' : (
+                {
+                 'field'      : 'showtunnelset',
+                 'type'       : 'enum',
+                 'values'     : ('details',),
+                 'optional'   : True,
+                 'format' : 'show_tunnelset',
+                 'data'         : { 'detail' : 'details' },
+                },
+                         ),
+               }
+    )
+}
 
 def tunnel_id_completion(prefix, completions):
     query_url = "http://127.0.0.1:8000/rest/v1/showtunnel"