test_rh_ip.py 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326
  1. # -*- coding: utf-8 -*-
  2. """
  3. :codeauthor: Jayesh Kariya <jayeshk@saltstack.com>
  4. """
  5. # Import Python libs
  6. from __future__ import absolute_import, print_function, unicode_literals
  7. import os
  8. # Import 3rd-party libs
  9. import jinja2.exceptions
  10. import salt.modules.rh_ip as rh_ip
  11. from salt.ext import six
  12. # Import Salt Libs
  13. from salt.ext.six.moves import range
  14. # Import Salt Testing Libs
  15. from tests.support.mixins import LoaderModuleMockMixin
  16. from tests.support.mock import MagicMock, patch
  17. from tests.support.unit import TestCase
  18. class RhipTestCase(TestCase, LoaderModuleMockMixin):
  19. """
  20. Test cases for salt.modules.rh_ip
  21. """
  22. def setup_loader_modules(self):
  23. return {rh_ip: {}}
  24. def test_error_message_iface_should_process_non_str_expected(self):
  25. values = [1, True, False, "no-kaboom"]
  26. iface = "ethtest"
  27. option = "test"
  28. msg = rh_ip._error_msg_iface(iface, option, values)
  29. self.assertTrue(msg.endswith("[1|True|False|no-kaboom]"), msg)
  30. def test_error_message_network_should_process_non_str_expected(self):
  31. values = [1, True, False, "no-kaboom"]
  32. msg = rh_ip._error_msg_network("fnord", values)
  33. self.assertTrue(msg.endswith("[1|True|False|no-kaboom]"), msg)
  34. def test_build_bond(self):
  35. """
  36. Test to create a bond script in /etc/modprobe.d with the passed
  37. settings and load the bonding kernel module.
  38. """
  39. with patch.dict(rh_ip.__grains__, {"osrelease": "osrelease"}):
  40. with patch.object(rh_ip, "_parse_settings_bond", MagicMock()):
  41. mock = jinja2.exceptions.TemplateNotFound("foo")
  42. with patch.object(
  43. jinja2.Environment, "get_template", MagicMock(side_effect=mock)
  44. ):
  45. self.assertEqual(rh_ip.build_bond("iface"), "")
  46. with patch.dict(
  47. rh_ip.__salt__, {"kmod.load": MagicMock(return_value=None)}
  48. ):
  49. with patch.object(rh_ip, "_write_file_iface", return_value=None):
  50. with patch.object(rh_ip, "_read_temp", return_value="A"):
  51. self.assertEqual(rh_ip.build_bond("iface", test="A"), "A")
  52. with patch.object(rh_ip, "_read_file", return_value="A"):
  53. self.assertEqual(rh_ip.build_bond("iface", test=None), "A")
  54. def test_build_interface(self):
  55. """
  56. Test to build an interface script for a network interface.
  57. """
  58. with patch.dict(rh_ip.__grains__, {"os": "Fedora", "osmajorrelease": 26}):
  59. with patch.object(rh_ip, "_raise_error_iface", return_value=None):
  60. self.assertRaises(
  61. AttributeError, rh_ip.build_interface, "iface", "slave", True
  62. )
  63. with patch.dict(
  64. rh_ip.__salt__, {"network.interfaces": lambda: {"eth": True}}
  65. ):
  66. self.assertRaises(
  67. AttributeError,
  68. rh_ip.build_interface,
  69. "iface",
  70. "eth",
  71. True,
  72. netmask="255.255.255.255",
  73. prefix=32,
  74. test=True,
  75. )
  76. self.assertRaises(
  77. AttributeError,
  78. rh_ip.build_interface,
  79. "iface",
  80. "eth",
  81. True,
  82. ipaddrs=["A"],
  83. test=True,
  84. )
  85. self.assertRaises(
  86. AttributeError,
  87. rh_ip.build_interface,
  88. "iface",
  89. "eth",
  90. True,
  91. ipv6addrs=["A"],
  92. test=True,
  93. )
  94. for osrelease in range(5, 8):
  95. with patch.dict(
  96. rh_ip.__grains__,
  97. {"os": "RedHat", "osrelease": six.text_type(osrelease)},
  98. ):
  99. with patch.object(rh_ip, "_raise_error_iface", return_value=None):
  100. with patch.object(rh_ip, "_parse_settings_bond", MagicMock()):
  101. mock = jinja2.exceptions.TemplateNotFound("foo")
  102. with patch.object(
  103. jinja2.Environment,
  104. "get_template",
  105. MagicMock(side_effect=mock),
  106. ):
  107. self.assertEqual(
  108. rh_ip.build_interface("iface", "vlan", True), ""
  109. )
  110. with patch.object(rh_ip, "_read_temp", return_value="A"):
  111. with patch.object(
  112. jinja2.Environment, "get_template", MagicMock()
  113. ):
  114. self.assertEqual(
  115. rh_ip.build_interface(
  116. "iface", "vlan", True, test="A"
  117. ),
  118. "A",
  119. )
  120. with patch.object(
  121. rh_ip, "_write_file_iface", return_value=None
  122. ):
  123. with patch.object(
  124. os.path, "join", return_value="A"
  125. ):
  126. with patch.object(
  127. rh_ip, "_read_file", return_value="A"
  128. ):
  129. self.assertEqual(
  130. rh_ip.build_interface(
  131. "iface", "vlan", True
  132. ),
  133. "A",
  134. )
  135. if osrelease > 6:
  136. with patch.dict(
  137. rh_ip.__salt__,
  138. {
  139. "network.interfaces": lambda: {
  140. "eth": True
  141. }
  142. },
  143. ):
  144. self.assertEqual(
  145. rh_ip.build_interface(
  146. "iface",
  147. "eth",
  148. True,
  149. ipaddrs=["127.0.0.1/8"],
  150. ),
  151. "A",
  152. )
  153. self.assertEqual(
  154. rh_ip.build_interface(
  155. "iface",
  156. "eth",
  157. True,
  158. ipv6addrs=["fc00::1/128"],
  159. ),
  160. "A",
  161. )
  162. def test_build_routes(self):
  163. """
  164. Test to build a route script for a network interface.
  165. """
  166. with patch.dict(rh_ip.__grains__, {"osrelease": "5.0"}):
  167. with patch.object(rh_ip, "_parse_routes", MagicMock()):
  168. mock = jinja2.exceptions.TemplateNotFound("foo")
  169. with patch.object(
  170. jinja2.Environment, "get_template", MagicMock(side_effect=mock)
  171. ):
  172. self.assertEqual(rh_ip.build_routes("iface"), "")
  173. with patch.object(jinja2.Environment, "get_template", MagicMock()):
  174. with patch.object(rh_ip, "_read_temp", return_value=["A"]):
  175. self.assertEqual(rh_ip.build_routes("i", test="t"), ["A", "A"])
  176. with patch.object(rh_ip, "_read_file", return_value=["A"]):
  177. with patch.object(os.path, "join", return_value="A"):
  178. with patch.object(
  179. rh_ip, "_write_file_iface", return_value=None
  180. ):
  181. self.assertEqual(
  182. rh_ip.build_routes("i", test=None), ["A", "A"]
  183. )
  184. def test_down(self):
  185. """
  186. Test to shutdown a network interface
  187. """
  188. with patch.dict(rh_ip.__salt__, {"cmd.run": MagicMock(return_value="A")}):
  189. self.assertEqual(rh_ip.down("iface", "iface_type"), "A")
  190. self.assertEqual(rh_ip.down("iface", "slave"), None)
  191. def test_get_bond(self):
  192. """
  193. Test to return the content of a bond script
  194. """
  195. with patch.object(os.path, "join", return_value="A"):
  196. with patch.object(rh_ip, "_read_file", return_value="A"):
  197. self.assertEqual(rh_ip.get_bond("iface"), "A")
  198. def test_get_interface(self):
  199. """
  200. Test to return the contents of an interface script
  201. """
  202. with patch.object(os.path, "join", return_value="A"):
  203. with patch.object(rh_ip, "_read_file", return_value="A"):
  204. self.assertEqual(rh_ip.get_interface("iface"), "A")
  205. def test__parse_settings_eth_hwaddr_and_macaddr(self):
  206. """
  207. Test that an AttributeError is thrown when hwaddr and macaddr are
  208. passed together. They cannot be used together
  209. """
  210. opts = {"hwaddr": 1, "macaddr": 2}
  211. self.assertRaises(
  212. AttributeError,
  213. rh_ip._parse_settings_eth,
  214. opts=opts,
  215. iface_type="eth",
  216. enabled=True,
  217. iface="eth0",
  218. )
  219. def test__parse_settings_eth_hwaddr(self):
  220. """
  221. Make sure hwaddr gets added when parsing opts
  222. """
  223. opts = {"hwaddr": "AA:BB:CC:11:22:33"}
  224. with patch.dict(rh_ip.__salt__, {"network.interfaces": MagicMock()}):
  225. results = rh_ip._parse_settings_eth(
  226. opts=opts, iface_type="eth", enabled=True, iface="eth0"
  227. )
  228. self.assertIn("hwaddr", results)
  229. self.assertEqual(results["hwaddr"], opts["hwaddr"])
  230. def test__parse_settings_eth_macaddr(self):
  231. """
  232. Make sure macaddr gets added when parsing opts
  233. """
  234. opts = {"macaddr": "AA:BB:CC:11:22:33"}
  235. with patch.dict(rh_ip.__salt__, {"network.interfaces": MagicMock()}):
  236. results = rh_ip._parse_settings_eth(
  237. opts=opts, iface_type="eth", enabled=True, iface="eth0"
  238. )
  239. self.assertIn("macaddr", results)
  240. self.assertEqual(results["macaddr"], opts["macaddr"])
  241. def test_up(self):
  242. """
  243. Test to start up a network interface
  244. """
  245. with patch.dict(rh_ip.__salt__, {"cmd.run": MagicMock(return_value="A")}):
  246. self.assertEqual(rh_ip.up("iface", "iface_type"), "A")
  247. self.assertEqual(rh_ip.up("iface", "slave"), None)
  248. def test_get_routes(self):
  249. """
  250. Test to return the contents of the interface routes script.
  251. """
  252. with patch.object(os.path, "join", return_value="A"):
  253. with patch.object(rh_ip, "_read_file", return_value=["A"]):
  254. self.assertEqual(rh_ip.get_routes("iface"), ["A", "A"])
  255. def test_get_network_settings(self):
  256. """
  257. Test to return the contents of the global network script.
  258. """
  259. with patch.object(rh_ip, "_read_file", return_value="A"):
  260. self.assertEqual(rh_ip.get_network_settings(), "A")
  261. def test_apply_network_settings(self):
  262. """
  263. Test to apply global network configuration.
  264. """
  265. with patch.dict(
  266. rh_ip.__salt__, {"service.restart": MagicMock(return_value=True)}
  267. ):
  268. self.assertTrue(rh_ip.apply_network_settings())
  269. def test_build_network_settings(self):
  270. """
  271. Test to build the global network script.
  272. """
  273. with patch.object(rh_ip, "_parse_rh_config", MagicMock()):
  274. with patch.object(rh_ip, "_parse_network_settings", MagicMock()):
  275. mock = jinja2.exceptions.TemplateNotFound("foo")
  276. with patch.object(
  277. jinja2.Environment, "get_template", MagicMock(side_effect=mock)
  278. ):
  279. self.assertEqual(rh_ip.build_network_settings(), "")
  280. with patch.object(jinja2.Environment, "get_template", MagicMock()):
  281. with patch.object(rh_ip, "_read_temp", return_value="A"):
  282. self.assertEqual(rh_ip.build_network_settings(test="t"), "A")
  283. with patch.object(
  284. rh_ip, "_write_file_network", return_value=None
  285. ):
  286. with patch.object(rh_ip, "_read_file", return_value="A"):
  287. self.assertEqual(
  288. rh_ip.build_network_settings(test=None), "A"
  289. )