@@ -506,6 +506,7 @@ def gw_set_log_level(self, args):
506
506
gw_actions .append ({"name" : "get_log_level" , "args" : [], "help" : "Get gateway's log level" })
507
507
gw_actions .append ({"name" : "set_log_level" , "args" : gw_set_log_level_args , "help" : "Set gateway's log level" })
508
508
gw_choices = get_actions (gw_actions )
509
+
509
510
@cli .cmd (gw_actions )
510
511
def gw (self , args ):
511
512
"""Gateway commands"""
@@ -596,8 +597,6 @@ def spdk_log_level_get(self, args):
596
597
597
598
def spdk_log_level_set (self , args ):
598
599
"""Set SPDK log levels and nvmf log flags"""
599
- rc = 0
600
- errmsg = ""
601
600
602
601
out_func , err_func = self .get_output_functions (args )
603
602
log_level = None
@@ -655,6 +654,7 @@ def spdk_log_level_set(self, args):
655
654
spdk_log_actions .append ({"name" : "set" , "args" : spdk_log_set_args , "help" : "Set SPDK log levels and nvmf log flags" })
656
655
spdk_log_actions .append ({"name" : "disable" , "args" : spdk_log_disable_args , "help" : "Disable SPDK nvmf log flags" })
657
656
spdk_log_choices = get_actions (spdk_log_actions )
657
+
658
658
@cli .cmd (spdk_log_actions )
659
659
def spdk_log_level (self , args ):
660
660
"""SPDK nvmf log level commands"""
@@ -691,7 +691,7 @@ def subsystem_add(self, args):
691
691
new_nqn = ""
692
692
try :
693
693
new_nqn = ret .nqn
694
- except Exception as ex : # In case of an old gateway the returned value wouldn't have the nqn field
694
+ except Exception : # In case of an old gateway the returned value wouldn't have the nqn field
695
695
pass
696
696
if not new_nqn :
697
697
new_nqn = args .subsystem
@@ -826,7 +826,6 @@ def subsystem_list(self, args):
826
826
def subsystem_change_key (self , args ):
827
827
"""Change subsystem's inband authentication key."""
828
828
829
- rc = 0
830
829
out_func , err_func = self .get_output_functions (args )
831
830
832
831
req = pb2 .change_subsystem_key_req (subsystem_nqn = args .subsystem , dhchap_key = args .dhchap_key )
@@ -884,6 +883,7 @@ def subsystem_change_key(self, args):
884
883
subsystem_actions .append ({"name" : "list" , "args" : subsys_list_args , "help" : "List subsystems" })
885
884
subsystem_actions .append ({"name" : "change_key" , "args" : subsys_change_key_args , "help" : "Change subsystem key" })
886
885
subsystem_choices = get_actions (subsystem_actions )
886
+
887
887
@cli .cmd (subsystem_actions )
888
888
def subsystem (self , args ):
889
889
"""Subsystem commands"""
@@ -1026,11 +1026,11 @@ def listener_list(self, args):
1026
1026
if args .format == "text" or args .format == "plain" :
1027
1027
if listeners_info .status == 0 :
1028
1028
listeners_list = []
1029
- for l in listeners_info .listeners :
1030
- adrfam = GatewayEnumUtils .get_key_from_value (pb2 .AddressFamily , l .adrfam )
1029
+ for lstnr in listeners_info .listeners :
1030
+ adrfam = GatewayEnumUtils .get_key_from_value (pb2 .AddressFamily , lstnr .adrfam )
1031
1031
adrfam = self .format_adrfam (adrfam )
1032
- secure = "Yes" if l .secure else "No"
1033
- listeners_list .append ([l .host_name , l .trtype , adrfam , f"{ l .traddr } :{ l .trsvcid } " , secure ])
1032
+ secure = "Yes" if lstnr .secure else "No"
1033
+ listeners_list .append ([lstnr .host_name , lstnr .trtype , adrfam , f"{ lstnr .traddr } :{ lstnr .trsvcid } " , secure ])
1034
1034
if len (listeners_list ) > 0 :
1035
1035
if args .format == "text" :
1036
1036
table_format = "fancy_grid"
@@ -1086,6 +1086,7 @@ def listener_list(self, args):
1086
1086
listener_actions .append ({"name" : "del" , "args" : listener_del_args , "help" : "Delete a listener" })
1087
1087
listener_actions .append ({"name" : "list" , "args" : listener_list_args , "help" : "List listeners" })
1088
1088
listener_choices = get_actions (listener_actions )
1089
+
1089
1090
@cli .cmd (listener_actions )
1090
1091
def listener (self , args ):
1091
1092
"""Listener commands"""
@@ -1216,7 +1217,6 @@ def host_del(self, args):
1216
1217
def host_change_key (self , args ):
1217
1218
"""Change host's inband authentication keys."""
1218
1219
1219
- rc = 0
1220
1220
out_func , err_func = self .get_output_functions (args )
1221
1221
1222
1222
if args .host_nqn == "*" :
@@ -1327,6 +1327,7 @@ def host_list(self, args):
1327
1327
host_actions .append ({"name" : "list" , "args" : host_list_args , "help" : "List subsystem's host access" })
1328
1328
host_actions .append ({"name" : "change_key" , "args" : host_change_key_args , "help" : "Change host's inband authentication keys" })
1329
1329
host_choices = get_actions (host_actions )
1330
+
1330
1331
@cli .cmd (host_actions )
1331
1332
def host (self , args ):
1332
1333
"""Host commands"""
@@ -1406,6 +1407,7 @@ def connection_list(self, args):
1406
1407
connection_actions = []
1407
1408
connection_actions .append ({"name" : "list" , "args" : connection_list_args , "help" : "List active connections" })
1408
1409
connection_choices = get_actions (connection_actions )
1410
+
1409
1411
@cli .cmd (connection_actions )
1410
1412
def connection (self , args ):
1411
1413
"""Connection commands"""
@@ -1601,7 +1603,7 @@ def get_size_in_bytes(self, sz):
1601
1603
try :
1602
1604
sz = sz .strip ()
1603
1605
int_size = int (sz )
1604
- except :
1606
+ except Exception :
1605
1607
self .cli .parser .error (f"Size { sz } must be numeric" )
1606
1608
1607
1609
int_size *= multiply
@@ -1638,14 +1640,15 @@ def ns_list(self, args):
1638
1640
lb_group = "<n/a>"
1639
1641
else :
1640
1642
lb_group = str (ns .load_balancing_group )
1641
- if ns .no_auto_visible :
1643
+ if ns .auto_visible :
1644
+ visibility = "All Hosts"
1645
+ else :
1642
1646
if len (ns .hosts ) > 0 :
1647
+ visibility = ""
1643
1648
for hst in ns .hosts :
1644
- visibility = break_string (hst , ":" , 2 ) + "\n "
1649
+ visibility += "· " + break_string (hst , ":" , 2 ) + "\n "
1645
1650
else :
1646
- visibility = "Selective"
1647
- else :
1648
- visibility = "All Hosts"
1651
+ visibility = "Restrictive"
1649
1652
1650
1653
namespaces_list .append ([ns .nsid ,
1651
1654
break_string (ns .bdev_name , "-" , 2 ),
@@ -1850,7 +1853,7 @@ def ns_change_load_balancing_group(self, args):
1850
1853
1851
1854
def get_qos_limit_str_value (self , qos_limit ):
1852
1855
if qos_limit == 0 :
1853
- return "unlimited "
1856
+ return "unset "
1854
1857
else :
1855
1858
return str (qos_limit )
1856
1859
@@ -1977,7 +1980,7 @@ def ns_del_host(self, args):
1977
1980
1978
1981
if args .format == "text" or args .format == "plain" :
1979
1982
if ret .status == 0 :
1980
- out_func (f"Deleting host { args . host_nqn } from namespace { args .nsid } on { args .subsystem } : Successful" )
1983
+ out_func (f"Deleting host { one_host_nqn } from namespace { args .nsid } on { args .subsystem } : Successful" )
1981
1984
else :
1982
1985
err_func (f"{ ret .error_message } " )
1983
1986
elif args .format == "json" or args .format == "yaml" :
@@ -2001,6 +2004,61 @@ def ns_del_host(self, args):
2001
2004
2002
2005
return rc
2003
2006
2007
+ def ns_change_visibility (self , args ):
2008
+ """Change namespace visibility."""
2009
+
2010
+ out_func , err_func = self .get_output_functions (args )
2011
+ if args .nsid <= 0 :
2012
+ self .cli .parser .error ("nsid value must be positive" )
2013
+
2014
+ if not args .auto_visible and not args .no_auto_visible :
2015
+ self .cli .parser .error ("Either --auto-visible or --no-auto-visible should be specified" )
2016
+
2017
+ if args .auto_visible and args .no_auto_visible :
2018
+ self .cli .parser .error ("--auto-visible and --no-auto-visible are mutually exclusive" )
2019
+
2020
+ if args .auto_visible :
2021
+ auto_visible = True
2022
+ elif args .no_auto_visible :
2023
+ auto_visible = False
2024
+ else :
2025
+ assert False
2026
+
2027
+ try :
2028
+ change_visibility_req = pb2 .namespace_change_visibility_req (subsystem_nqn = args .subsystem ,
2029
+ nsid = args .nsid , auto_visible = auto_visible ,
2030
+ force = args .force )
2031
+ ret = self .stub .namespace_change_visibility (change_visibility_req )
2032
+ except Exception as ex :
2033
+ ret = pb2 .req_status (status = errno .EINVAL , error_message = f"Failure changing namespace visibility:\n { ex } " )
2034
+
2035
+ if auto_visible :
2036
+ vis_text = "\" visible to all hosts\" "
2037
+ else :
2038
+ vis_text = "\" visible to selected hosts\" "
2039
+ if args .format == "text" or args .format == "plain" :
2040
+ if ret .status == 0 :
2041
+ out_func (f"Changing visibility of namespace { args .nsid } in { args .subsystem } to { vis_text } : Successful" )
2042
+ else :
2043
+ err_func (f"{ ret .error_message } " )
2044
+ elif args .format == "json" or args .format == "yaml" :
2045
+ ret_str = json_format .MessageToJson (
2046
+ ret ,
2047
+ indent = 4 ,
2048
+ including_default_value_fields = True ,
2049
+ preserving_proto_field_name = True )
2050
+ if args .format == "json" :
2051
+ out_func (f"{ ret_str } " )
2052
+ elif args .format == "yaml" :
2053
+ obj = json .loads (ret_str )
2054
+ out_func (yaml .dump (obj ))
2055
+ elif args .format == "python" :
2056
+ return ret
2057
+ else :
2058
+ assert False
2059
+
2060
+ return ret .status
2061
+
2004
2062
ns_common_args = [
2005
2063
argument ("--subsystem" , "-n" , help = "Subsystem NQN" , required = True ),
2006
2064
]
@@ -2034,6 +2092,12 @@ def ns_del_host(self, args):
2034
2092
argument ("--nsid" , help = "Namespace ID" , type = int , required = True ),
2035
2093
argument ("--load-balancing-group" , "-l" , help = "Load balancing group" , type = int , required = True ),
2036
2094
]
2095
+ ns_change_visibility_args_list = ns_common_args + [
2096
+ argument ("--nsid" , help = "Namespace ID" , type = int , required = True ),
2097
+ argument ("--auto-visible" , help = "Visible to all hosts" , action = 'store_true' , required = False ),
2098
+ argument ("--no-auto-visible" , help = "Visible to selected hosts only" , action = 'store_true' , required = False ),
2099
+ argument ("--force" , help = "Change visibility of namespace even if there hosts added to it or active connections on the subsystem" , action = 'store_true' , required = False ),
2100
+ ]
2037
2101
ns_set_qos_args_list = ns_common_args + [
2038
2102
argument ("--nsid" , help = "Namespace ID" , type = int , required = True ),
2039
2103
argument ("--rw-ios-per-second" , help = "R/W IOs per second limit, 0 means unlimited" , type = int ),
@@ -2059,7 +2123,9 @@ def ns_del_host(self, args):
2059
2123
ns_actions .append ({"name" : "set_qos" , "args" : ns_set_qos_args_list , "help" : "Set QOS limits for a namespace" })
2060
2124
ns_actions .append ({"name" : "add_host" , "args" : ns_add_host_args_list , "help" : "Add a host to a namespace" })
2061
2125
ns_actions .append ({"name" : "del_host" , "args" : ns_del_host_args_list , "help" : "Delete a host from a namespace" })
2126
+ ns_actions .append ({"name" : "change_visibility" , "args" : ns_change_visibility_args_list , "help" : "Change visibility for a namespace" })
2062
2127
ns_choices = get_actions (ns_actions )
2128
+
2063
2129
@cli .cmd (ns_actions , ["ns" ])
2064
2130
def namespace (self , args ):
2065
2131
"""Namespace commands"""
@@ -2081,6 +2147,8 @@ def namespace(self, args):
2081
2147
return self .ns_add_host (args )
2082
2148
elif args .action == "del_host" :
2083
2149
return self .ns_del_host (args )
2150
+ elif args .action == "change_visibility" :
2151
+ return self .ns_change_visibility (args )
2084
2152
if not args .action :
2085
2153
self .cli .parser .error (f"missing action for namespace command (choose from { GatewayClient .ns_choices } )" )
2086
2154
@@ -2135,5 +2203,6 @@ def main(args=None) -> int:
2135
2203
2136
2204
return main_common (client , parsed_args )
2137
2205
2206
+
2138
2207
if __name__ == "__main__" :
2139
2208
sys .exit (main ())
0 commit comments