mtncloud-cli 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (499) hide show
  1. checksums.yaml +7 -0
  2. data/.dockerignore +20 -0
  3. data/.github/pull_request_template.md +14 -0
  4. data/.github/workflows/ci.yml +56 -0
  5. data/.github/workflows/release.yml +46 -0
  6. data/.gitignore +25 -0
  7. data/CLAUDE.md +24 -0
  8. data/CONTRIBUTING.md +91 -0
  9. data/Dockerfile +19 -0
  10. data/Gemfile +4 -0
  11. data/LICENSE.txt +23 -0
  12. data/README.md +187 -0
  13. data/Rakefile +26 -0
  14. data/bin/mcs +3 -0
  15. data/bin/mtncloud +27 -0
  16. data/lib/mtncloud/api/account_groups_interface.rb +48 -0
  17. data/lib/mtncloud/api/account_users_interface.rb +68 -0
  18. data/lib/mtncloud/api/accounts_interface.rb +9 -0
  19. data/lib/mtncloud/api/activity_interface.rb +9 -0
  20. data/lib/mtncloud/api/affinity_groups_interface.rb +46 -0
  21. data/lib/mtncloud/api/api_client.rb +1091 -0
  22. data/lib/mtncloud/api/appliance_settings_interface.rb +49 -0
  23. data/lib/mtncloud/api/approvals_interface.rb +32 -0
  24. data/lib/mtncloud/api/apps_interface.rb +180 -0
  25. data/lib/mtncloud/api/archive_buckets_interface.rb +116 -0
  26. data/lib/mtncloud/api/archive_files_interface.rb +173 -0
  27. data/lib/mtncloud/api/audit_interface.rb +9 -0
  28. data/lib/mtncloud/api/auth_interface.rb +58 -0
  29. data/lib/mtncloud/api/backup_jobs_interface.rb +13 -0
  30. data/lib/mtncloud/api/backup_restores_interface.rb +27 -0
  31. data/lib/mtncloud/api/backup_results_interface.rb +32 -0
  32. data/lib/mtncloud/api/backup_service_types_interface.rb +9 -0
  33. data/lib/mtncloud/api/backup_services_interface.rb +9 -0
  34. data/lib/mtncloud/api/backup_settings_interface.rb +20 -0
  35. data/lib/mtncloud/api/backup_types_interface.rb +9 -0
  36. data/lib/mtncloud/api/backups_interface.rb +21 -0
  37. data/lib/mtncloud/api/billing_interface.rb +34 -0
  38. data/lib/mtncloud/api/blueprints_interface.rb +70 -0
  39. data/lib/mtncloud/api/body_io.rb +22 -0
  40. data/lib/mtncloud/api/budgets_interface.rb +48 -0
  41. data/lib/mtncloud/api/catalog_item_types_interface.rb +29 -0
  42. data/lib/mtncloud/api/certificate_types_interface.rb +14 -0
  43. data/lib/mtncloud/api/certificates_interface.rb +9 -0
  44. data/lib/mtncloud/api/clients_interface.rb +41 -0
  45. data/lib/mtncloud/api/cloud_datastores_interface.rb +48 -0
  46. data/lib/mtncloud/api/cloud_folders_interface.rb +41 -0
  47. data/lib/mtncloud/api/cloud_policies_interface.rb +41 -0
  48. data/lib/mtncloud/api/cloud_resource_pools_interface.rb +66 -0
  49. data/lib/mtncloud/api/clouds_interface.rb +217 -0
  50. data/lib/mtncloud/api/clusters_interface.rb +471 -0
  51. data/lib/mtncloud/api/containers_interface.rb +145 -0
  52. data/lib/mtncloud/api/credential_types_interface.rb +9 -0
  53. data/lib/mtncloud/api/credentials_interface.rb +9 -0
  54. data/lib/mtncloud/api/custom_instance_types_interface.rb +99 -0
  55. data/lib/mtncloud/api/cypher_interface.rb +51 -0
  56. data/lib/mtncloud/api/dashboard_interface.rb +14 -0
  57. data/lib/mtncloud/api/datastores_interface.rb +21 -0
  58. data/lib/mtncloud/api/deploy_interface.rb +44 -0
  59. data/lib/mtncloud/api/deployments_interface.rb +79 -0
  60. data/lib/mtncloud/api/distributed_workers_interface.rb +41 -0
  61. data/lib/mtncloud/api/email_templates_interface.rb +53 -0
  62. data/lib/mtncloud/api/environments_interface.rb +48 -0
  63. data/lib/mtncloud/api/execute_schedules_interface.rb +71 -0
  64. data/lib/mtncloud/api/execution_request_interface.rb +27 -0
  65. data/lib/mtncloud/api/file_copy_request_interface.rb +68 -0
  66. data/lib/mtncloud/api/forgot_password_interface.rb +17 -0
  67. data/lib/mtncloud/api/group_policies_interface.rb +41 -0
  68. data/lib/mtncloud/api/groups_interface.rb +73 -0
  69. data/lib/mtncloud/api/guidance_interface.rb +44 -0
  70. data/lib/mtncloud/api/guidance_settings_interface.rb +17 -0
  71. data/lib/mtncloud/api/health_interface.rb +100 -0
  72. data/lib/mtncloud/api/host_vm_groups_interface.rb +37 -0
  73. data/lib/mtncloud/api/hub_interface.rb +25 -0
  74. data/lib/mtncloud/api/image_builder_boot_scripts_interface.rb +41 -0
  75. data/lib/mtncloud/api/image_builder_image_builds_interface.rb +73 -0
  76. data/lib/mtncloud/api/image_builder_interface.rb +20 -0
  77. data/lib/mtncloud/api/image_builder_preseed_scripts_interface.rb +41 -0
  78. data/lib/mtncloud/api/instance_types_interface.rb +20 -0
  79. data/lib/mtncloud/api/instances_interface.rb +453 -0
  80. data/lib/mtncloud/api/integration_types_interface.rb +14 -0
  81. data/lib/mtncloud/api/integrations_interface.rb +74 -0
  82. data/lib/mtncloud/api/invoice_line_items_interface.rb +9 -0
  83. data/lib/mtncloud/api/invoices_interface.rb +28 -0
  84. data/lib/mtncloud/api/jobs_interface.rb +83 -0
  85. data/lib/mtncloud/api/key_pairs_interface.rb +57 -0
  86. data/lib/mtncloud/api/library_cluster_layouts_interface.rb +47 -0
  87. data/lib/mtncloud/api/library_cluster_packages_interface.rb +60 -0
  88. data/lib/mtncloud/api/library_container_scripts_interface.rb +43 -0
  89. data/lib/mtncloud/api/library_container_templates_interface.rb +43 -0
  90. data/lib/mtncloud/api/library_container_types_interface.rb +59 -0
  91. data/lib/mtncloud/api/library_container_upgrades_interface.rb +60 -0
  92. data/lib/mtncloud/api/library_instance_types_interface.rb +74 -0
  93. data/lib/mtncloud/api/library_layouts_interface.rb +69 -0
  94. data/lib/mtncloud/api/library_operating_systems_interface.rb +63 -0
  95. data/lib/mtncloud/api/library_spec_template_types_interface.rb +43 -0
  96. data/lib/mtncloud/api/library_spec_templates_interface.rb +43 -0
  97. data/lib/mtncloud/api/license_interface.rb +30 -0
  98. data/lib/mtncloud/api/load_balancer_monitors_interface.rb +9 -0
  99. data/lib/mtncloud/api/load_balancer_pool_nodes_interface.rb +8 -0
  100. data/lib/mtncloud/api/load_balancer_pools_interface.rb +9 -0
  101. data/lib/mtncloud/api/load_balancer_pools_secondary_interface.rb +9 -0
  102. data/lib/mtncloud/api/load_balancer_profiles_interface.rb +9 -0
  103. data/lib/mtncloud/api/load_balancer_types_interface.rb +9 -0
  104. data/lib/mtncloud/api/load_balancer_virtual_servers_interface.rb +18 -0
  105. data/lib/mtncloud/api/load_balancers_interface.rb +14 -0
  106. data/lib/mtncloud/api/log_settings_interface.rb +44 -0
  107. data/lib/mtncloud/api/logs_interface.rb +37 -0
  108. data/lib/mtncloud/api/migrations_interface.rb +49 -0
  109. data/lib/mtncloud/api/monitoring_alerts_interface.rb +39 -0
  110. data/lib/mtncloud/api/monitoring_apps_interface.rb +69 -0
  111. data/lib/mtncloud/api/monitoring_checks_interface.rb +103 -0
  112. data/lib/mtncloud/api/monitoring_contacts_interface.rb +41 -0
  113. data/lib/mtncloud/api/monitoring_groups_interface.rb +77 -0
  114. data/lib/mtncloud/api/monitoring_incidents_interface.rb +107 -0
  115. data/lib/mtncloud/api/monitoring_interface.rb +35 -0
  116. data/lib/mtncloud/api/monitoring_settings_interface.rb +21 -0
  117. data/lib/mtncloud/api/network_dhcp_relays_interface.rb +36 -0
  118. data/lib/mtncloud/api/network_dhcp_servers_interface.rb +36 -0
  119. data/lib/mtncloud/api/network_domain_records_interface.rb +41 -0
  120. data/lib/mtncloud/api/network_domains_interface.rb +41 -0
  121. data/lib/mtncloud/api/network_edge_clusters_interface.rb +26 -0
  122. data/lib/mtncloud/api/network_floating_ips_interface.rb +40 -0
  123. data/lib/mtncloud/api/network_groups_interface.rb +41 -0
  124. data/lib/mtncloud/api/network_pool_ips_interface.rb +41 -0
  125. data/lib/mtncloud/api/network_pool_server_types_interface.rb +9 -0
  126. data/lib/mtncloud/api/network_pool_servers_interface.rb +48 -0
  127. data/lib/mtncloud/api/network_pools_interface.rb +41 -0
  128. data/lib/mtncloud/api/network_proxies_interface.rb +41 -0
  129. data/lib/mtncloud/api/network_routers_interface.rb +181 -0
  130. data/lib/mtncloud/api/network_security_server_types_interface.rb +9 -0
  131. data/lib/mtncloud/api/network_security_servers_interface.rb +27 -0
  132. data/lib/mtncloud/api/network_server_groups_interface.rb +7 -0
  133. data/lib/mtncloud/api/network_server_types_interface.rb +9 -0
  134. data/lib/mtncloud/api/network_servers_interface.rb +102 -0
  135. data/lib/mtncloud/api/network_services_interface.rb +63 -0
  136. data/lib/mtncloud/api/network_static_routes_interface.rb +36 -0
  137. data/lib/mtncloud/api/network_subnets_interface.rb +42 -0
  138. data/lib/mtncloud/api/network_types_interface.rb +20 -0
  139. data/lib/mtncloud/api/networks_interface.rb +48 -0
  140. data/lib/mtncloud/api/option_type_forms_interface.rb +9 -0
  141. data/lib/mtncloud/api/option_type_lists_interface.rb +53 -0
  142. data/lib/mtncloud/api/option_types_interface.rb +41 -0
  143. data/lib/mtncloud/api/options_interface.rb +17 -0
  144. data/lib/mtncloud/api/packages_interface.rb +112 -0
  145. data/lib/mtncloud/api/ping_interface.rb +22 -0
  146. data/lib/mtncloud/api/plugins_interface.rb +22 -0
  147. data/lib/mtncloud/api/policies_interface.rb +56 -0
  148. data/lib/mtncloud/api/power_schedules_interface.rb +71 -0
  149. data/lib/mtncloud/api/price_sets_interface.rb +39 -0
  150. data/lib/mtncloud/api/prices_interface.rb +71 -0
  151. data/lib/mtncloud/api/processes_interface.rb +40 -0
  152. data/lib/mtncloud/api/projects_interface.rb +33 -0
  153. data/lib/mtncloud/api/provision_types_interface.rb +24 -0
  154. data/lib/mtncloud/api/provisioning_license_types_interface.rb +31 -0
  155. data/lib/mtncloud/api/provisioning_licenses_interface.rb +60 -0
  156. data/lib/mtncloud/api/provisioning_settings_interface.rb +26 -0
  157. data/lib/mtncloud/api/read_interface.rb +24 -0
  158. data/lib/mtncloud/api/reports_interface.rb +70 -0
  159. data/lib/mtncloud/api/resource_pool_groups_interface.rb +51 -0
  160. data/lib/mtncloud/api/rest_interface.rb +37 -0
  161. data/lib/mtncloud/api/roles_interface.rb +151 -0
  162. data/lib/mtncloud/api/scale_thresholds_interface.rb +9 -0
  163. data/lib/mtncloud/api/search_interface.rb +13 -0
  164. data/lib/mtncloud/api/secondary_read_interface.rb +25 -0
  165. data/lib/mtncloud/api/secondary_rest_interface.rb +42 -0
  166. data/lib/mtncloud/api/security_group_rules_interface.rb +35 -0
  167. data/lib/mtncloud/api/security_groups_interface.rb +56 -0
  168. data/lib/mtncloud/api/security_package_types_interface.rb +9 -0
  169. data/lib/mtncloud/api/security_packages_interface.rb +9 -0
  170. data/lib/mtncloud/api/security_scans_interface.rb +9 -0
  171. data/lib/mtncloud/api/server_devices_interface.rb +30 -0
  172. data/lib/mtncloud/api/server_types_interface.rb +20 -0
  173. data/lib/mtncloud/api/servers_interface.rb +230 -0
  174. data/lib/mtncloud/api/service_catalog_interface.rb +89 -0
  175. data/lib/mtncloud/api/service_plans_interface.rb +62 -0
  176. data/lib/mtncloud/api/setup_interface.rb +46 -0
  177. data/lib/mtncloud/api/snapshots_interface.rb +19 -0
  178. data/lib/mtncloud/api/storage_datastores_interface.rb +44 -0
  179. data/lib/mtncloud/api/storage_providers_interface.rb +151 -0
  180. data/lib/mtncloud/api/storage_server_types_interface.rb +14 -0
  181. data/lib/mtncloud/api/storage_servers_interface.rb +9 -0
  182. data/lib/mtncloud/api/storage_volume_types_interface.rb +9 -0
  183. data/lib/mtncloud/api/storage_volumes_interface.rb +24 -0
  184. data/lib/mtncloud/api/subnet_types_interface.rb +20 -0
  185. data/lib/mtncloud/api/subnets_interface.rb +41 -0
  186. data/lib/mtncloud/api/support_bundles_interface.rb +46 -0
  187. data/lib/mtncloud/api/system_types_interface.rb +13 -0
  188. data/lib/mtncloud/api/systems_interface.rb +55 -0
  189. data/lib/mtncloud/api/task_sets_interface.rb +52 -0
  190. data/lib/mtncloud/api/tasks_interface.rb +66 -0
  191. data/lib/mtncloud/api/tokens_interface.rb +39 -0
  192. data/lib/mtncloud/api/usage_interface.rb +18 -0
  193. data/lib/mtncloud/api/user_groups_interface.rb +59 -0
  194. data/lib/mtncloud/api/user_settings_interface.rb +90 -0
  195. data/lib/mtncloud/api/user_sources_interface.rb +99 -0
  196. data/lib/mtncloud/api/users_interface.rb +33 -0
  197. data/lib/mtncloud/api/vdi_allocations_interface.rb +9 -0
  198. data/lib/mtncloud/api/vdi_apps_interface.rb +9 -0
  199. data/lib/mtncloud/api/vdi_gateways_interface.rb +9 -0
  200. data/lib/mtncloud/api/vdi_interface.rb +28 -0
  201. data/lib/mtncloud/api/vdi_pools_interface.rb +19 -0
  202. data/lib/mtncloud/api/virtual_images_interface.rb +210 -0
  203. data/lib/mtncloud/api/virtual_servers_interface.rb +9 -0
  204. data/lib/mtncloud/api/virtual_switches_interface.rb +9 -0
  205. data/lib/mtncloud/api/whitelabel_settings_interface.rb +57 -0
  206. data/lib/mtncloud/api/whoami_interface.rb +13 -0
  207. data/lib/mtncloud/api/wiki_interface.rb +48 -0
  208. data/lib/mtncloud/api.rb +12 -0
  209. data/lib/mtncloud/benchmarking.rb +259 -0
  210. data/lib/mtncloud/cli/cli_command.rb +2281 -0
  211. data/lib/mtncloud/cli/cli_registry.rb +337 -0
  212. data/lib/mtncloud/cli/commands/access_token_command.rb +201 -0
  213. data/lib/mtncloud/cli/commands/account_groups_command.rb +530 -0
  214. data/lib/mtncloud/cli/commands/activity_command.rb +149 -0
  215. data/lib/mtncloud/cli/commands/affinity_groups_command.rb +554 -0
  216. data/lib/mtncloud/cli/commands/alias_command.rb +278 -0
  217. data/lib/mtncloud/cli/commands/appliance_settings_command.rb +382 -0
  218. data/lib/mtncloud/cli/commands/approvals_command.rb +236 -0
  219. data/lib/mtncloud/cli/commands/apps.rb +2549 -0
  220. data/lib/mtncloud/cli/commands/archives_command.rb +2161 -0
  221. data/lib/mtncloud/cli/commands/audit.rb +188 -0
  222. data/lib/mtncloud/cli/commands/backup_jobs_command.rb +366 -0
  223. data/lib/mtncloud/cli/commands/backup_restores_command.rb +144 -0
  224. data/lib/mtncloud/cli/commands/backup_results_command.rb +149 -0
  225. data/lib/mtncloud/cli/commands/backup_services_command.rb +44 -0
  226. data/lib/mtncloud/cli/commands/backup_settings_command.rb +184 -0
  227. data/lib/mtncloud/cli/commands/backup_types_command.rb +53 -0
  228. data/lib/mtncloud/cli/commands/backups_command.rb +674 -0
  229. data/lib/mtncloud/cli/commands/benchmark_command.rb +458 -0
  230. data/lib/mtncloud/cli/commands/blueprints_command.rb +2297 -0
  231. data/lib/mtncloud/cli/commands/boot_scripts_command.rb +379 -0
  232. data/lib/mtncloud/cli/commands/budgets_command.rb +754 -0
  233. data/lib/mtncloud/cli/commands/cat_command.rb +45 -0
  234. data/lib/mtncloud/cli/commands/catalog_item_types_command.rb +858 -0
  235. data/lib/mtncloud/cli/commands/certificates_command.rb +575 -0
  236. data/lib/mtncloud/cli/commands/change_password_command.rb +132 -0
  237. data/lib/mtncloud/cli/commands/clients_command.rb +331 -0
  238. data/lib/mtncloud/cli/commands/cloud_datastores_command.rb +543 -0
  239. data/lib/mtncloud/cli/commands/cloud_folders_command.rb +512 -0
  240. data/lib/mtncloud/cli/commands/cloud_resource_pools_command.rb +870 -0
  241. data/lib/mtncloud/cli/commands/clouds.rb +2037 -0
  242. data/lib/mtncloud/cli/commands/clouds_types.rb +140 -0
  243. data/lib/mtncloud/cli/commands/cluster_types.rb +179 -0
  244. data/lib/mtncloud/cli/commands/clusters.rb +5855 -0
  245. data/lib/mtncloud/cli/commands/coloring_command.rb +82 -0
  246. data/lib/mtncloud/cli/commands/containers_command.rb +967 -0
  247. data/lib/mtncloud/cli/commands/credential_types_command.rb +36 -0
  248. data/lib/mtncloud/cli/commands/credentials_command.rb +124 -0
  249. data/lib/mtncloud/cli/commands/curl_command.rb +168 -0
  250. data/lib/mtncloud/cli/commands/cypher_command.rb +587 -0
  251. data/lib/mtncloud/cli/commands/dashboard_command.rb +300 -0
  252. data/lib/mtncloud/cli/commands/debug_command.rb +75 -0
  253. data/lib/mtncloud/cli/commands/deploy.rb +485 -0
  254. data/lib/mtncloud/cli/commands/deployments.rb +923 -0
  255. data/lib/mtncloud/cli/commands/deploys.rb +485 -0
  256. data/lib/mtncloud/cli/commands/distributed_workers_command.rb +282 -0
  257. data/lib/mtncloud/cli/commands/echo_command.rb +61 -0
  258. data/lib/mtncloud/cli/commands/edit_profile_command.rb +57 -0
  259. data/lib/mtncloud/cli/commands/edit_rc_command.rb +77 -0
  260. data/lib/mtncloud/cli/commands/email_templates_command.rb +373 -0
  261. data/lib/mtncloud/cli/commands/environments_command.rb +401 -0
  262. data/lib/mtncloud/cli/commands/execute_schedules_command.rb +735 -0
  263. data/lib/mtncloud/cli/commands/execution_request_command.rb +333 -0
  264. data/lib/mtncloud/cli/commands/exit_command.rb +34 -0
  265. data/lib/mtncloud/cli/commands/file_copy_request_command.rb +352 -0
  266. data/lib/mtncloud/cli/commands/forgot_password.rb +133 -0
  267. data/lib/mtncloud/cli/commands/get_prompt_command.rb +36 -0
  268. data/lib/mtncloud/cli/commands/groups.rb +818 -0
  269. data/lib/mtncloud/cli/commands/guidance_command.rb +529 -0
  270. data/lib/mtncloud/cli/commands/guidance_settings.rb +148 -0
  271. data/lib/mtncloud/cli/commands/health_command.rb +1046 -0
  272. data/lib/mtncloud/cli/commands/history_command.rb +60 -0
  273. data/lib/mtncloud/cli/commands/host_vm_groups_command.rb +423 -0
  274. data/lib/mtncloud/cli/commands/hosts.rb +2986 -0
  275. data/lib/mtncloud/cli/commands/hub.rb +215 -0
  276. data/lib/mtncloud/cli/commands/image_builder_command.rb +1197 -0
  277. data/lib/mtncloud/cli/commands/instance_types.rb +163 -0
  278. data/lib/mtncloud/cli/commands/instances.rb +5813 -0
  279. data/lib/mtncloud/cli/commands/integrations_command.rb +1412 -0
  280. data/lib/mtncloud/cli/commands/invoices_command.rb +1151 -0
  281. data/lib/mtncloud/cli/commands/jobs_command.rb +998 -0
  282. data/lib/mtncloud/cli/commands/key_pairs.rb +470 -0
  283. data/lib/mtncloud/cli/commands/library_cluster_layouts_command.rb +901 -0
  284. data/lib/mtncloud/cli/commands/library_cluster_packages_command.rb +552 -0
  285. data/lib/mtncloud/cli/commands/library_container_scripts_command.rb +446 -0
  286. data/lib/mtncloud/cli/commands/library_container_templates_command.rb +526 -0
  287. data/lib/mtncloud/cli/commands/library_container_types_command.rb +698 -0
  288. data/lib/mtncloud/cli/commands/library_forms_command.rb +625 -0
  289. data/lib/mtncloud/cli/commands/library_instance_types_command.rb +668 -0
  290. data/lib/mtncloud/cli/commands/library_layouts_command.rb +849 -0
  291. data/lib/mtncloud/cli/commands/library_operating_systems_command.rb +671 -0
  292. data/lib/mtncloud/cli/commands/library_option_lists_command.rb +503 -0
  293. data/lib/mtncloud/cli/commands/library_option_types_command.rb +329 -0
  294. data/lib/mtncloud/cli/commands/library_spec_templates_command.rb +547 -0
  295. data/lib/mtncloud/cli/commands/library_upgrades_command.rb +596 -0
  296. data/lib/mtncloud/cli/commands/license.rb +475 -0
  297. data/lib/mtncloud/cli/commands/load_balancer_monitors.rb +70 -0
  298. data/lib/mtncloud/cli/commands/load_balancer_pool_nodes.rb +87 -0
  299. data/lib/mtncloud/cli/commands/load_balancer_pools.rb +129 -0
  300. data/lib/mtncloud/cli/commands/load_balancer_profiles.rb +64 -0
  301. data/lib/mtncloud/cli/commands/load_balancer_types.rb +38 -0
  302. data/lib/mtncloud/cli/commands/load_balancer_virtual_servers.rb +147 -0
  303. data/lib/mtncloud/cli/commands/load_balancers.rb +189 -0
  304. data/lib/mtncloud/cli/commands/log_level_command.rb +54 -0
  305. data/lib/mtncloud/cli/commands/log_settings_command.rb +443 -0
  306. data/lib/mtncloud/cli/commands/login.rb +148 -0
  307. data/lib/mtncloud/cli/commands/logout.rb +63 -0
  308. data/lib/mtncloud/cli/commands/logs_command.rb +140 -0
  309. data/lib/mtncloud/cli/commands/man_command.rb +409 -0
  310. data/lib/mtncloud/cli/commands/migrations.rb +453 -0
  311. data/lib/mtncloud/cli/commands/monitoring_alerts_command.rb +791 -0
  312. data/lib/mtncloud/cli/commands/monitoring_apps_command.rb +716 -0
  313. data/lib/mtncloud/cli/commands/monitoring_checks_command.rb +766 -0
  314. data/lib/mtncloud/cli/commands/monitoring_contacts_command.rb +339 -0
  315. data/lib/mtncloud/cli/commands/monitoring_groups_command.rb +674 -0
  316. data/lib/mtncloud/cli/commands/monitoring_incidents_command.rb +835 -0
  317. data/lib/mtncloud/cli/commands/monitoring_settings.rb +212 -0
  318. data/lib/mtncloud/cli/commands/network_dhcp_relays_command.rb +375 -0
  319. data/lib/mtncloud/cli/commands/network_dhcp_servers_command.rb +366 -0
  320. data/lib/mtncloud/cli/commands/network_domains_command.rb +896 -0
  321. data/lib/mtncloud/cli/commands/network_edge_clusters_command.rb +288 -0
  322. data/lib/mtncloud/cli/commands/network_firewalls_command.rb +783 -0
  323. data/lib/mtncloud/cli/commands/network_floating_ips.rb +147 -0
  324. data/lib/mtncloud/cli/commands/network_groups_command.rb +654 -0
  325. data/lib/mtncloud/cli/commands/network_pool_server_types.rb +20 -0
  326. data/lib/mtncloud/cli/commands/network_pool_servers_command.rb +318 -0
  327. data/lib/mtncloud/cli/commands/network_pools_command.rb +903 -0
  328. data/lib/mtncloud/cli/commands/network_proxies_command.rb +578 -0
  329. data/lib/mtncloud/cli/commands/network_routers_command.rb +2628 -0
  330. data/lib/mtncloud/cli/commands/network_security_server_types.rb +20 -0
  331. data/lib/mtncloud/cli/commands/network_server_groups_command.rb +222 -0
  332. data/lib/mtncloud/cli/commands/network_server_types_command.rb +20 -0
  333. data/lib/mtncloud/cli/commands/network_servers_command.rb +398 -0
  334. data/lib/mtncloud/cli/commands/network_services_command.rb +198 -0
  335. data/lib/mtncloud/cli/commands/network_static_routes_command.rb +451 -0
  336. data/lib/mtncloud/cli/commands/network_transport_zones_command.rb +412 -0
  337. data/lib/mtncloud/cli/commands/networks_command.rb +1692 -0
  338. data/lib/mtncloud/cli/commands/open_command.rb +30 -0
  339. data/lib/mtncloud/cli/commands/options.rb +231 -0
  340. data/lib/mtncloud/cli/commands/packages_command.rb +822 -0
  341. data/lib/mtncloud/cli/commands/ping.rb +242 -0
  342. data/lib/mtncloud/cli/commands/plugins.rb +214 -0
  343. data/lib/mtncloud/cli/commands/policies_command.rb +990 -0
  344. data/lib/mtncloud/cli/commands/power_schedules_command.rb +731 -0
  345. data/lib/mtncloud/cli/commands/preseed_scripts_command.rb +378 -0
  346. data/lib/mtncloud/cli/commands/price_sets_command.rb +557 -0
  347. data/lib/mtncloud/cli/commands/prices_command.rb +692 -0
  348. data/lib/mtncloud/cli/commands/processes_command.rb +469 -0
  349. data/lib/mtncloud/cli/commands/projects_command.rb +537 -0
  350. data/lib/mtncloud/cli/commands/provisioning_licenses_command.rb +509 -0
  351. data/lib/mtncloud/cli/commands/provisioning_settings_command.rb +238 -0
  352. data/lib/mtncloud/cli/commands/recent_activity_command.rb +171 -0
  353. data/lib/mtncloud/cli/commands/remote.rb +1818 -0
  354. data/lib/mtncloud/cli/commands/reports_command.rb +724 -0
  355. data/lib/mtncloud/cli/commands/resource_pool_groups_command.rb +586 -0
  356. data/lib/mtncloud/cli/commands/rm_command.rb +14 -0
  357. data/lib/mtncloud/cli/commands/roles.rb +3120 -0
  358. data/lib/mtncloud/cli/commands/scale_thresholds.rb +103 -0
  359. data/lib/mtncloud/cli/commands/search_command.rb +184 -0
  360. data/lib/mtncloud/cli/commands/security_group_rules.rb +230 -0
  361. data/lib/mtncloud/cli/commands/security_groups.rb +1294 -0
  362. data/lib/mtncloud/cli/commands/security_package_types.rb +32 -0
  363. data/lib/mtncloud/cli/commands/security_packages.rb +84 -0
  364. data/lib/mtncloud/cli/commands/security_scans.rb +107 -0
  365. data/lib/mtncloud/cli/commands/self_service_command.rb +17 -0
  366. data/lib/mtncloud/cli/commands/server_devices_command.rb +207 -0
  367. data/lib/mtncloud/cli/commands/service_catalog_command.rb +1528 -0
  368. data/lib/mtncloud/cli/commands/service_plans_command.rb +895 -0
  369. data/lib/mtncloud/cli/commands/set_prompt_command.rb +51 -0
  370. data/lib/mtncloud/cli/commands/setup.rb +423 -0
  371. data/lib/mtncloud/cli/commands/shell.rb +717 -0
  372. data/lib/mtncloud/cli/commands/sleep_command.rb +43 -0
  373. data/lib/mtncloud/cli/commands/snapshots.rb +156 -0
  374. data/lib/mtncloud/cli/commands/source_command.rb +30 -0
  375. data/lib/mtncloud/cli/commands/ssl_verification_command.rb +47 -0
  376. data/lib/mtncloud/cli/commands/storage_datastores.rb +457 -0
  377. data/lib/mtncloud/cli/commands/storage_providers_command.rb +1401 -0
  378. data/lib/mtncloud/cli/commands/storage_server_types.rb +45 -0
  379. data/lib/mtncloud/cli/commands/storage_servers.rb +116 -0
  380. data/lib/mtncloud/cli/commands/storage_volume_types.rb +45 -0
  381. data/lib/mtncloud/cli/commands/storage_volumes.rb +236 -0
  382. data/lib/mtncloud/cli/commands/subnets_command.rb +819 -0
  383. data/lib/mtncloud/cli/commands/support_bundles_command.rb +606 -0
  384. data/lib/mtncloud/cli/commands/systems.rb +1203 -0
  385. data/lib/mtncloud/cli/commands/tasks.rb +1391 -0
  386. data/lib/mtncloud/cli/commands/tee_command.rb +14 -0
  387. data/lib/mtncloud/cli/commands/tenants_command.rb +315 -0
  388. data/lib/mtncloud/cli/commands/tokens_command.rb +391 -0
  389. data/lib/mtncloud/cli/commands/update_command.rb +46 -0
  390. data/lib/mtncloud/cli/commands/usage_command.rb +203 -0
  391. data/lib/mtncloud/cli/commands/user_groups_command.rb +512 -0
  392. data/lib/mtncloud/cli/commands/user_settings_command.rb +849 -0
  393. data/lib/mtncloud/cli/commands/user_sources_command.rb +1065 -0
  394. data/lib/mtncloud/cli/commands/users.rb +897 -0
  395. data/lib/mtncloud/cli/commands/vdi_allocations_command.rb +159 -0
  396. data/lib/mtncloud/cli/commands/vdi_apps_command.rb +317 -0
  397. data/lib/mtncloud/cli/commands/vdi_command.rb +359 -0
  398. data/lib/mtncloud/cli/commands/vdi_gateways_command.rb +290 -0
  399. data/lib/mtncloud/cli/commands/vdi_pools_command.rb +574 -0
  400. data/lib/mtncloud/cli/commands/version_command.rb +38 -0
  401. data/lib/mtncloud/cli/commands/view.rb +107 -0
  402. data/lib/mtncloud/cli/commands/virtual_images.rb +1362 -0
  403. data/lib/mtncloud/cli/commands/virtual_switches_command.rb +336 -0
  404. data/lib/mtncloud/cli/commands/whitelabel_settings_command.rb +653 -0
  405. data/lib/mtncloud/cli/commands/whoami.rb +323 -0
  406. data/lib/mtncloud/cli/commands/wiki_command.rb +448 -0
  407. data/lib/mtncloud/cli/commands/workflows.rb +1022 -0
  408. data/lib/mtncloud/cli/credentials.rb +482 -0
  409. data/lib/mtncloud/cli/dot_file.rb +180 -0
  410. data/lib/mtncloud/cli/error_handler.rb +307 -0
  411. data/lib/mtncloud/cli/errors.rb +53 -0
  412. data/lib/mtncloud/cli/expression_parser.rb +153 -0
  413. data/lib/mtncloud/cli/mixins/accounts_helper.rb +484 -0
  414. data/lib/mtncloud/cli/mixins/affinity_helper.rb +118 -0
  415. data/lib/mtncloud/cli/mixins/backups_helper.rb +200 -0
  416. data/lib/mtncloud/cli/mixins/deployments_helper.rb +163 -0
  417. data/lib/mtncloud/cli/mixins/execution_request_helper.rb +50 -0
  418. data/lib/mtncloud/cli/mixins/infrastructure_helper.rb +966 -0
  419. data/lib/mtncloud/cli/mixins/jobs_helper.rb +202 -0
  420. data/lib/mtncloud/cli/mixins/library_helper.rb +539 -0
  421. data/lib/mtncloud/cli/mixins/load_balancers_helper.rb +176 -0
  422. data/lib/mtncloud/cli/mixins/logs_helper.rb +131 -0
  423. data/lib/mtncloud/cli/mixins/monitoring_helper.rb +876 -0
  424. data/lib/mtncloud/cli/mixins/networks_helper.rb +62 -0
  425. data/lib/mtncloud/cli/mixins/operations_helper.rb +41 -0
  426. data/lib/mtncloud/cli/mixins/option_source_helper.rb +254 -0
  427. data/lib/mtncloud/cli/mixins/print_helper.rb +1631 -0
  428. data/lib/mtncloud/cli/mixins/processes_helper.rb +286 -0
  429. data/lib/mtncloud/cli/mixins/prompt_helper.rb +136 -0
  430. data/lib/mtncloud/cli/mixins/provisioning_helper.rb +2963 -0
  431. data/lib/mtncloud/cli/mixins/remote_helper.rb +139 -0
  432. data/lib/mtncloud/cli/mixins/rest_command.rb +994 -0
  433. data/lib/mtncloud/cli/mixins/secondary_rest_command.rb +700 -0
  434. data/lib/mtncloud/cli/mixins/storage_servers_helper.rb +93 -0
  435. data/lib/mtncloud/cli/mixins/storage_volumes_helper.rb +76 -0
  436. data/lib/mtncloud/cli/mixins/vdi_helper.rb +246 -0
  437. data/lib/mtncloud/cli/mixins/whoami_helper.rb +73 -0
  438. data/lib/mtncloud/cli/option_parser.rb +127 -0
  439. data/lib/mtncloud/cli/option_types.rb +1622 -0
  440. data/lib/mtncloud/cli/version.rb +6 -0
  441. data/lib/mtncloud/cli.rb +105 -0
  442. data/lib/mtncloud/currency.rb +184 -0
  443. data/lib/mtncloud/ext/hash.rb +109 -0
  444. data/lib/mtncloud/ext/nil_class.rb +5 -0
  445. data/lib/mtncloud/ext/rest_client.rb +37 -0
  446. data/lib/mtncloud/ext/string.rb +66 -0
  447. data/lib/mtncloud/formatters.rb +511 -0
  448. data/lib/mtncloud/logging.rb +185 -0
  449. data/lib/mtncloud/morpkg.rb +119 -0
  450. data/lib/mtncloud/rest_client.rb +104 -0
  451. data/lib/mtncloud/routes.rb +304 -0
  452. data/lib/mtncloud/terminal.rb +528 -0
  453. data/lib/mtncloud/util.rb +29 -0
  454. data/lib/mtncloud.rb +5 -0
  455. data/mtncloud-cli.gemspec +38 -0
  456. data/test/api/affinity_groups_interface_test.rb +43 -0
  457. data/test/api/clients_interface_test.rb +23 -0
  458. data/test/api/clouds_interface_test.rb +67 -0
  459. data/test/api/containers_interface_test.rb +68 -0
  460. data/test/api/host_vm_groups_interface_test.rb +35 -0
  461. data/test/api/instances_interface_test.rb +22 -0
  462. data/test/api/network_routers_interface_test.rb +22 -0
  463. data/test/api/systems_interface_test.rb +26 -0
  464. data/test/api/whoami_interface_test.rb +14 -0
  465. data/test/branding_test.rb +160 -0
  466. data/test/cli/access_token_test.rb +36 -0
  467. data/test/cli/affinity_groups_cloud_cluster_scope_test.rb +270 -0
  468. data/test/cli/affinity_groups_cluster_scope_test.rb +171 -0
  469. data/test/cli/affinity_groups_test.rb +57 -0
  470. data/test/cli/affinity_groups_violations_scope_test.rb +141 -0
  471. data/test/cli/affinity_helper_test.rb +367 -0
  472. data/test/cli/auth_test.rb +88 -0
  473. data/test/cli/backups_test.rb +212 -0
  474. data/test/cli/cli_test.rb +48 -0
  475. data/test/cli/clients_test.rb +45 -0
  476. data/test/cli/clusters_uuid_test.rb +146 -0
  477. data/test/cli/containers_test.rb +92 -0
  478. data/test/cli/distributed_workers_test.rb +68 -0
  479. data/test/cli/help_test.rb +25 -0
  480. data/test/cli/host_vm_groups_cluster_scope_test.rb +187 -0
  481. data/test/cli/host_vm_groups_test.rb +63 -0
  482. data/test/cli/infrastructure_helper_cluster_resolver_test.rb +250 -0
  483. data/test/cli/instances_test.rb +37 -0
  484. data/test/cli/man_test.rb +14 -0
  485. data/test/cli/migrations_test.rb +39 -0
  486. data/test/cli/network_routers_test.rb +65 -0
  487. data/test/cli/remote_test.rb +89 -0
  488. data/test/cli/roles_test.rb +47 -0
  489. data/test/cli/shell_test.rb +81 -0
  490. data/test/cli/storage_volumes_test.rb +79 -0
  491. data/test/cli/systems_test.rb +206 -0
  492. data/test/cli/version_test.rb +23 -0
  493. data/test/cli/view_test.rb +55 -0
  494. data/test/cli/whoami_test.rb +17 -0
  495. data/test/mtncloud_test.rb +16 -0
  496. data/test/test_case.rb +342 -0
  497. data/test/test_config.rb +137 -0
  498. data/test/test_data_helper.rb +97 -0
  499. metadata +807 -0
@@ -0,0 +1,2628 @@
1
+ require 'mtncloud/cli/cli_command'
2
+
3
+ class MtnCloud::Cli::NetworkRoutersCommand
4
+ include MtnCloud::Cli::CliCommand
5
+ include MtnCloud::Cli::InfrastructureHelper
6
+ include MtnCloud::Cli::ProvisioningHelper
7
+ include MtnCloud::Cli::WhoamiHelper
8
+
9
+ set_command_name :'network-routers'
10
+ register_subcommands :list, :get, :firewall, :dhcp, :types, :type, :add, :update, :remove
11
+ register_subcommands :add_firewall_rule_group, :update_firewall_rule_group, :remove_firewall_rule_group, :firewall_rule_groups, :firewall_rule_group
12
+ register_subcommands :add_firewall_rule, :update_firewall_rule, :remove_firewall_rule, :firewall_rules, :firewall_rule
13
+ register_subcommands :add_route, :remove_route, :routes
14
+ register_subcommands :update_permissions
15
+ register_subcommands :add_nat, :update_nat, :remove_nat, :nats, :nat
16
+ register_subcommands :add_bgp_neighbor, :update_bgp_neighbor, :remove_bgp_neighbor, :bgp_neighbors, :bgp_neighbor
17
+
18
+ def initialize()
19
+ end
20
+
21
+ def connect(opts)
22
+ @api_client = establish_remote_appliance_connection(opts)
23
+ @network_routers_interface = @api_client.network_routers
24
+ @network_services_interface = @api_client.network_services
25
+ @clouds_interface = @api_client.clouds
26
+ @options_interface = @api_client.options
27
+ @accounts_interface = @api_client.accounts
28
+ end
29
+
30
+ def handle(args)
31
+ handle_subcommand(args)
32
+ end
33
+
34
+ def list(args)
35
+ options = {}
36
+ params = {}
37
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
38
+ opts.banner = subcommand_usage()
39
+ build_common_options(opts, options, [:list, :query, :json, :yaml, :csv, :fields, :dry_run, :remote])
40
+ opts.footer = "List network routers."
41
+ end
42
+ optparse.parse!(args)
43
+ connect(options)
44
+ begin
45
+ params.merge!(parse_list_options(options))
46
+ @network_routers_interface.setopts(options)
47
+ if options[:dry_run]
48
+ print_dry_run @network_routers_interface.dry.list(params)
49
+ return
50
+ end
51
+ json_response = @network_routers_interface.list(params)
52
+ routers = json_response["networkRouters"]
53
+ if options[:json]
54
+ puts as_json(json_response, options, "networkRouters")
55
+ return 0
56
+ elsif options[:yaml]
57
+ puts as_yaml(json_response, options, "networkRouters")
58
+ return 0
59
+ elsif options[:csv]
60
+ puts records_as_csv(routers, options)
61
+ return 0
62
+ end
63
+ title = "Network Routers"
64
+ subtitles = []
65
+ subtitles += parse_list_subtitles(options)
66
+ print_h1 title, subtitles
67
+ if routers.empty?
68
+ print cyan,"No network routers found.",reset,"\n"
69
+ else
70
+ # STATUS NAME ROUTER TYPE SERVICE NETWORKS EXTERNAL IP
71
+ rows = routers.collect {|router|
72
+ row = {
73
+ id: router['id'],
74
+ name: router['name'],
75
+ status: format_router_status(router),
76
+ router_type: (router['type'] || {})['name'],
77
+ group: router['site'] ? router['site']['name'] : 'Shared',
78
+ service: (router['networkServer'] || {})['name'],
79
+ networks: (router['externalNetwork'] || {})['name'],
80
+ external_ip: router['externalIp']
81
+ }
82
+ row
83
+ }
84
+ columns = [:id, :name, :status, :router_type, :group, :service, :networks, :external_ip]
85
+ if options[:include_fields]
86
+ columns = options[:include_fields]
87
+ end
88
+ print cyan
89
+ print as_pretty_table(rows, columns, options)
90
+ print reset
91
+ if json_response['meta']
92
+ print_results_pagination(json_response, {:label => "network routers", :n_label => "network routers"})
93
+ else
94
+ print_results_pagination({'meta'=>{'total'=>rows.size,'size'=>rows.size,'max'=>options[:max] || rows.size,'offset'=>0}}, {:label => "network routers", :n_label => "network routers"})
95
+ end
96
+ end
97
+ print reset,"\n"
98
+ return 0
99
+ rescue RestClient::Exception => e
100
+ print_rest_exception(e, options)
101
+ exit 1
102
+ end
103
+ end
104
+
105
+ def get(args)
106
+ options = {}
107
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
108
+ opts.banner = subcommand_usage("[router]")
109
+ opts.on('--details', "Display details: firewall, DHCP, routing, and NATs." ) do
110
+ options[:details] = true
111
+ end
112
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
113
+ opts.footer = "Display network router details." + "\n" +
114
+ "[router] is required. This is the name or id of a network router."
115
+ end
116
+ optparse.parse!(args)
117
+ if args.count < 1
118
+ puts optparse
119
+ return 1
120
+ end
121
+ connect(options)
122
+ id_list = parse_id_list(args)
123
+ return run_command_for_each_arg(id_list) do |arg|
124
+ _get(arg, options)
125
+ end
126
+ end
127
+
128
+ def _get(id, options)
129
+ begin
130
+ @network_routers_interface.setopts(options)
131
+ if options[:dry_run]
132
+ if arg.to_s =~ /\A\d{1,}\Z/
133
+ print_dry_run @network_routers_interface.dry.get(arg.to_i)
134
+ else
135
+ print_dry_run @network_routers_interface.dry.list({name:arg})
136
+ end
137
+ return
138
+ end
139
+ router = find_router(id)
140
+ if router.nil?
141
+ return 1
142
+ end
143
+
144
+ json_response = {'networkRouter' => router}
145
+
146
+ if options[:json]
147
+ puts as_json(json_response, options, "networkRouter")
148
+ return 0
149
+ elsif options[:yaml]
150
+ puts as_yaml(json_response, options, "networkRouter")
151
+ return 0
152
+ elsif options[:csv]
153
+ puts records_as_csv([json_response['networkRouter']], options)
154
+ return 0
155
+ end
156
+
157
+ print_h1 "Network Router Details"
158
+ print cyan
159
+ description_cols = {
160
+ "ID" => lambda {|it| it['id'] },
161
+ "Name" => lambda {|it| it['name'] },
162
+ "Status" => lambda {|it| format_router_status(it)},
163
+ "Type" => lambda {|it| it['type']['name']},
164
+ "Service" => lambda {|it| it['networkServer'] ? it['networkServer']['name'] : nil},
165
+ "Group" => lambda {|it| it['site'] ? it['site']['name'] : 'Shared'},
166
+ # "Integration" => lambda {|it| router_integration_label(it)},
167
+ "Provider ID" => lambda {|it| it['providerId'] || it['externalId']},
168
+ "Created" => lambda {|it| format_local_dt(it['dateCreated']) },
169
+ "Updated" => lambda {|it| format_local_dt(it['lastUpdated']) }
170
+ }
171
+
172
+ print_description_list(description_cols, router)
173
+
174
+ if (router['interfaces'] || []).count > 0
175
+ rows = router['interfaces'].sort_by{|it| it['networkPosition']}.collect do |it|
176
+ {
177
+ position: it['networkPosition'],
178
+ name: it['name'],
179
+ type: it['interfaceType'],
180
+ network: (it['network'] || {})['name'],
181
+ link: it['externalLink'],
182
+ ip_address: it['ipAddress'],
183
+ subnet: it['cidr'],
184
+ enabled: format_boolean(it['enabled'])
185
+ }
186
+ end
187
+ print_h2 "Interfaces"
188
+ puts as_pretty_table(rows, [:position, :name, :type, :link, :network, :ip_address, :subnet, :enabled])
189
+ end
190
+
191
+ if router['type']['hasFirewall']
192
+ print_h2 "Firewall"
193
+ print cyan
194
+ print_firewall(router, options)
195
+ end
196
+ if router['type']['hasDhcp']
197
+ print_h2 "DHCP"
198
+ print cyan
199
+ print_dhcp(router, options[:details])
200
+ end
201
+ if router['type']['hasRouting'] && options[:details]
202
+ print_h2 "Routes"
203
+ print cyan
204
+ print_routes(router)
205
+ end
206
+ if router['type']['hasNat'] && options[:details]
207
+ print_h2 "NATs"
208
+ print cyan
209
+ print_nats(router)
210
+ end
211
+ if router['permissions'] && options[:details]
212
+ print_h2 "Tenant Permissions"
213
+ print cyan
214
+ description_cols = {
215
+ "Visibility" => lambda{|it| (it['permissions']['visibility'] || '').capitalize},
216
+ "Tenants" => lambda{|it|
217
+ accounts = (it['permissions']['tenantPermissions'] || {})['accounts'] || []
218
+ accounts.count > 0 ? accounts.join(', ') : ''
219
+ }
220
+ }
221
+ print_description_list(description_cols, router)
222
+ println
223
+ end
224
+ print reset
225
+ rescue RestClient::Exception => e
226
+ print_rest_exception(e, options)
227
+ return 1
228
+ end
229
+ end
230
+
231
+ def add(args)
232
+ options = {:options=>{}}
233
+ params = {}
234
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
235
+ opts.banner = subcommand_usage("[type] [name] [options]")
236
+ opts.on( '-g', '--group GROUP', "Group Name or ID" ) do |val|
237
+ options[:group] = val
238
+ end
239
+ opts.on('-t', '--type VALUE', String, "Name or ID of router type") do |val|
240
+ options[:options]['routerType'] = val
241
+ end
242
+ opts.on('-n', '--name VALUE', String, "Name for this network router") do |val|
243
+ options[:options]['name'] = val
244
+ end
245
+ opts.on('-D', '--description VALUE', String, "Description") do |val|
246
+ options[:options]['description'] = val
247
+ end
248
+ opts.on('-s', '--server VALUE', String, "Network server") do |val|
249
+ options[:network_server] = val
250
+ end
251
+ opts.on( '-c', '--cloud CLOUD', "Cloud Name or ID" ) do |val|
252
+ options[:cloud] = val
253
+ end
254
+ opts.on('--enabled [on|off]', String, "Can be used to enable / disable the network router. Default is on") do |val|
255
+ options[:enabled] = val.to_s == 'on' || val.to_s == 'true' || val.to_s == '1' || val.to_s == ''
256
+ end
257
+ opts.on('--hostname VALUE', String, "Hostname for this network pool IP") do |val|
258
+ options[:options]['hostname'] = val
259
+ end
260
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
261
+ opts.footer = "Create a network router."
262
+ end
263
+ optparse.parse!(args)
264
+ connect(options)
265
+ if args.count > 2
266
+ print_error MtnCloud::Terminal.angry_prompt
267
+ puts_error "wrong number of arguments, expected 0-2 and got (#{args.count}) #{args.inspect}\n#{optparse}"
268
+ return 1
269
+ end
270
+ if args.count > 0
271
+ options[:options]['routerType'] = args[0]
272
+ end
273
+ if args.count > 1
274
+ params['name'] = args[1]
275
+ end
276
+ begin
277
+ if options[:payload]
278
+ payload = options[:payload]
279
+ else
280
+ router_type = prompt_router_type(options)
281
+ router = {'type' => {'id' => router_type['id']}, 'enabled' => options[:enabled].nil? || options[:enabled] }
282
+
283
+ group_options = available_groups
284
+
285
+ if options[:group]
286
+ group = available_groups.find {|it| it['name'] == options[:group] || "#{it['value']}" == "#{options[:group]}".downcase}
287
+
288
+ if group.nil?
289
+ print_red_alert "Group #{options[:group]} not found"
290
+ exit 1
291
+ end
292
+ router['site'] = {'id' => group['value']}
293
+ else
294
+ default_group = group_options.find {|it| it['value'] == 'shared'} ? 'shared' : nil
295
+ group_id = MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'group', 'type' => 'select', 'fieldLabel' => 'Group', 'required' => true, 'selectOptions' => group_options, 'defaultValue' => default_group}], options[:options], @api_client, params, nil, true)['group']
296
+ router['site'] = {'id' => group_id}
297
+ end
298
+
299
+ # add router type to be used for option prompts
300
+ params = {'router' => {'site' => router['site']}, 'routerType' => {'id' => router_type['id']}}
301
+
302
+ if router_type['hasNetworkServer']
303
+ if options[:network_server]
304
+ # This is using network_services instead of network_servers though, hrmm
305
+ # server = find_network_server(options[:network_server])
306
+ services = @network_services_interface.list()['networkServices']
307
+ server = (options[:network_server].to_s =~ /\A\d{1,}\Z/) ? services.find {|it| it['id'].to_i == options[:network_server].to_i} : services.find {|it| it['name'] == options[:network_server]}
308
+ if server.nil?
309
+ print_red_alert "Network server #{options[:network_server]} not found"
310
+ exit 1
311
+ end
312
+ else
313
+ server_id = MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'networkServer', 'type' => 'select', 'fieldLabel' => 'Network Server', 'required' => true, 'optionSource' => 'networkServer'}], options[:options], @api_client, params, nil, true)['networkServer']
314
+ server = {'id' => server_id}
315
+ end
316
+ params['router']['networkServer'] = router['networkServer'] = {'id' => server['id']}
317
+ params['networkServerId'] = server['id']
318
+ else
319
+ # prompt cloud
320
+ if options[:cloud]
321
+ cloud = find_cloud_by_name_or_id(options[:cloud])
322
+ if cloud.nil?
323
+ print_red_alert "Cloud #{options[:cloud]} not found"
324
+ exit 1
325
+ end
326
+ else
327
+ cloud_id = MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'zone', 'type' => 'select', 'fieldLabel' => 'Cloud', 'required' => true, 'optionSource' => 'routerTypeCloud'}], options[:options], @api_client, params, nil, true)['zone']
328
+ cloud = {'id' => cloud_id}
329
+ end
330
+ router['zone'] = params['zone'] = {'id' => cloud['id']}
331
+ # add router type to be used for option prompts
332
+ params['router']['zone'] = {'id' => cloud['id']}
333
+ end
334
+
335
+ # prompt for enabled
336
+ router['enabled'] = options[:enabled].nil? ? MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'enabled', 'fieldLabel' => 'Enabled', 'type' => 'checkbox', 'description' => 'Enable Router.', 'defaultValue' => true, 'required' => false}], options, @api_client, {})['enabled'] == 'on' : options[:enabled]
337
+
338
+ option_types = router_type['optionTypes'].reject {|it| ['enabled'].include?(it['fieldName']) || it['showOnCreate'] === false}.sort {|it| it['displayOrder']}
339
+
340
+ # prompt options
341
+ option_opts = options[:options].deep_merge!({'config' => options[:options].clone})
342
+ # option types are mixing context router and networkRouter, so we need to copy these to avoid prompt for router.name if passed in
343
+ if option_opts['name'] || option_opts['description']
344
+ option_opts['router'] ||= {}
345
+ option_opts['router']['name'] = option_opts['name'] if option_opts['name']
346
+ option_opts['router']['description'] = option_opts['description'] if option_opts['description']
347
+ end
348
+ option_result = MtnCloud::Cli::OptionTypes.prompt(option_types, option_opts.merge({:context_map => {'networkRouter' => 'router'}}), @api_client, params)
349
+ # option types are mixing context router and networkRouter, so we need to clean up the payload
350
+ router_params = option_result.delete('router')
351
+ if router_params.is_a?(Hash)
352
+ option_result = router_params.deep_merge(option_result)
353
+ end
354
+ payload = {'networkRouter' => router.deep_merge(option_result)}
355
+ payload['networkRouter']['config'] = option_result['config'] if option_result['config']
356
+ end
357
+
358
+ @network_routers_interface.setopts(options)
359
+ if options[:dry_run]
360
+ print_dry_run @network_routers_interface.dry.create(payload)
361
+ return
362
+ end
363
+
364
+ json_response = @network_routers_interface.create(payload)
365
+
366
+ if options[:json]
367
+ print JSON.pretty_generate(json_response), "\n"
368
+ return
369
+ end
370
+ print_green_success "Added Network Router #{payload['networkRouter']['name']}"
371
+ _get(json_response['id'], options)
372
+ rescue RestClient::Exception => e
373
+ print_rest_exception(e, options)
374
+ exit 1
375
+ end
376
+ end
377
+
378
+ def update(args)
379
+ options = {:options=>{}}
380
+ params = {}
381
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
382
+ opts.banner = subcommand_usage("[router]")
383
+ opts.on('-n', '--name VALUE', String, "Name for this network") do |val|
384
+ params['name'] = val
385
+ end
386
+ opts.on('-D', '--description VALUE', String, "Description for this network") do |val|
387
+ params['description'] = val
388
+ end
389
+ opts.on('--enabled [on|off]', String, "Can be used to enable / disable the network router. Default is on") do |val|
390
+ options[:enabled] = val.to_s == 'on' || val.to_s == 'true' || val.to_s == '1' || val.to_s == ''
391
+ end
392
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
393
+ opts.footer = "Update a network router."
394
+ end
395
+ optparse.parse!(args)
396
+ connect(options)
397
+ if args.count != 1
398
+ print_error MtnCloud::Terminal.angry_prompt
399
+ puts_error "wrong number of arguments, expected 1 and got (#{args.count}) #{args.inspect}\n#{optparse}"
400
+ return 1
401
+ end
402
+
403
+ begin
404
+ router = find_router(args[0])
405
+ if router.nil?
406
+ return 1
407
+ end
408
+
409
+ payload = parse_payload(options)
410
+
411
+ if payload.nil?
412
+ if !options[:enabled].nil?
413
+ params['enabled'] = options[:enabled]
414
+ end
415
+
416
+ if options[:options]
417
+ params.deep_merge!(options[:options].reject {|k,v| k.is_a?(Symbol) || ['name', 'routerType', 'enabled', 'description'].include?(k)})
418
+ end
419
+ payload = {'networkRouter' => params}
420
+ end
421
+
422
+ if payload['networkRouter'].empty?
423
+ print_green_success "Nothing to update"
424
+ return
425
+ end
426
+
427
+ @network_routers_interface.setopts(options)
428
+ if options[:dry_run]
429
+ print_dry_run @network_routers_interface.dry.update(router['id'], payload)
430
+ return
431
+ end
432
+
433
+ json_response = @network_routers_interface.update(router['id'], payload)
434
+
435
+ if options[:json]
436
+ puts as_json(json_response, options)
437
+ elsif !options[:quiet]
438
+ if json_response['success']
439
+ print_green_success "Network router updated"
440
+ _get(router['id'], options)
441
+ else
442
+ print_red_alert "Error updating network router: #{json_response['msg'] || json_response['errors']}"
443
+ end
444
+ end
445
+ return 0
446
+ rescue RestClient::Exception => e
447
+ print_rest_exception(e, options)
448
+ exit 1
449
+ end
450
+ end
451
+
452
+ def remove(args)
453
+ options = {}
454
+ query_params = {}
455
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
456
+ opts.banner = subcommand_usage("[router]")
457
+ build_common_options(opts, options, [:auto_confirm, :json, :dry_run, :quiet, :remote])
458
+ opts.footer = "Delete a network router.\n" +
459
+ "[router] is required. This is the name or id of an existing network router."
460
+ end
461
+ optparse.parse!(args)
462
+ if args.count != 1
463
+ raise_command_error "wrong number of arguments, expected 1 and got (#{args.count}) #{args}\n#{optparse}"
464
+ end
465
+ connect(options)
466
+
467
+ begin
468
+ router = find_router(args[0])
469
+
470
+ return if !router
471
+
472
+ unless options[:yes] || ::MtnCloud::Cli::OptionTypes::confirm("Are you sure you would like to remove the network router '#{router['name']}'?", options)
473
+ return 9, "aborted command"
474
+ end
475
+ @network_routers_interface.setopts(options)
476
+ if options[:dry_run]
477
+ print_dry_run @network_routers_interface.dry.destroy(router['id'], query_params)
478
+ return
479
+ end
480
+ json_response = @network_routers_interface.destroy(router['id'], query_params)
481
+ if options[:json]
482
+ print JSON.pretty_generate(json_response)
483
+ print "\n"
484
+ elsif !options[:quiet]
485
+ print_green_success "Network router #{router['name']} is being removed..."
486
+ end
487
+ rescue RestClient::Exception => e
488
+ print_rest_exception(e, options)
489
+ exit 1
490
+ end
491
+ end
492
+
493
+ def firewall(args)
494
+ options = {}
495
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
496
+ opts.banner = subcommand_usage("[router]")
497
+ opts.on('--details', "Display details." ) do
498
+ options[:details] = true
499
+ end
500
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
501
+ opts.footer = "Display network router firewall details." + "\n" +
502
+ "[router] is required. This is the name or id of a network router."
503
+ end
504
+
505
+ optparse.parse!(args)
506
+ connect(options)
507
+
508
+ if args.count < 1
509
+ puts optparse
510
+ return 1
511
+ end
512
+
513
+ begin
514
+ @network_routers_interface.setopts(options)
515
+ if options[:dry_run]
516
+ if args[0].to_s =~ /\A\d{1,}\Z/
517
+ print_dry_run @network_routers_interface.dry.get(args[0].to_i)
518
+ else
519
+ print_dry_run @network_routers_interface.dry.list({name:args[0]})
520
+ end
521
+ return
522
+ end
523
+ router = find_router(args[0])
524
+ if router.nil?
525
+ return 1
526
+ end
527
+
528
+ json_response = {'networkRouter' => router}
529
+
530
+ if options[:json]
531
+ puts as_json(json_response, options, "networkRouter")
532
+ return 0
533
+ elsif options[:yaml]
534
+ puts as_yaml(json_response, options, "networkRouter")
535
+ return 0
536
+ elsif options[:csv]
537
+ puts records_as_csv([json_response['networkRouter']], options)
538
+ return 0
539
+ end
540
+
541
+ print_h1 "Network Router Firewall Details For: #{router['name']}"
542
+ print cyan
543
+
544
+ if router['type']['hasFirewall']
545
+ print_firewall(router, options)
546
+ else
547
+ print_red_alert "Firewall not supported for #{router['type']['name']}"
548
+ end
549
+ println reset
550
+ rescue RestClient::Exception => e
551
+ print_rest_exception(e, options)
552
+ return 1
553
+ end
554
+ end
555
+
556
+ def firewall_rule_groups(args)
557
+ options = {}
558
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
559
+ opts.banner = subcommand_usage("[router]")
560
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
561
+ opts.footer = "Display network router firewall rule groups.\n" +
562
+ "[router] is required. This is the name or id of a network router."
563
+ end
564
+
565
+ optparse.parse!(args)
566
+ connect(options)
567
+
568
+ if args.count < 1
569
+ puts optparse
570
+ return 1
571
+ end
572
+
573
+ begin
574
+ @network_routers_interface.setopts(options)
575
+ if options[:dry_run]
576
+ if router_id.to_s =~ /\A\d{1,}\Z/
577
+ print_dry_run @network_routers_interface.dry.get(router_id.to_i)
578
+ else
579
+ print_dry_run @network_routers_interface.dry.list({name:router_id})
580
+ end
581
+ return
582
+ end
583
+
584
+ router = find_router(args[0])
585
+ if router.nil?
586
+ return 1
587
+ end
588
+ _firewall_rule_groups(router, options)
589
+ rescue RestClient::Exception => e
590
+ print_rest_exception(e, options)
591
+ return 1
592
+ end
593
+ end
594
+
595
+ def _firewall_rule_groups(router, options)
596
+ if router['type']['hasFirewallGroups']
597
+ json_response = {'ruleGroups' => router['firewall']['ruleGroups'] || []}
598
+
599
+ if options[:json]
600
+ puts as_json(json_response, options, "ruleGroups")
601
+ return 0
602
+ elsif options[:yaml]
603
+ puts as_yaml(json_response, options, "ruleGroups")
604
+ return 0
605
+ elsif options[:csv]
606
+ puts records_as_csv(json_response['ruleGroups'], options)
607
+ return 0
608
+ end
609
+
610
+ if (router['firewall']['ruleGroups'] || []).count > 0
611
+ print_h1 "Firewall Rule Groups For: #{router['name']}"
612
+ rows = router['firewall']['ruleGroups'].collect do |rule_group|
613
+ {
614
+ id: rule_group['id'],
615
+ name: rule_group['name'],
616
+ description: rule_group['description'],
617
+ priority: rule_group['priority'],
618
+ category: rule_group['groupLayer']
619
+ }
620
+ end
621
+ rows = rows.reject {|it| it[:id].to_s != options[:rule_group_id].to_s} if options[:rule_group_id]
622
+ puts as_pretty_table(rows, [:id, :name, :description, :priority, :category])
623
+ else
624
+ print_h1 "No Firewall Rule Groups"
625
+ end
626
+ else
627
+ print_red_alert "Firewall rule groups not supported for #{router['type']['name']}"
628
+ end
629
+ println reset
630
+ end
631
+
632
+ def firewall_rule_group(args)
633
+ options = {}
634
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
635
+ opts.banner = subcommand_usage("[router]")
636
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
637
+ opts.footer = "Display network router firewall rule group details." + "\n" +
638
+ "[router] is required. This is the name or id of a network router.\n" +
639
+ "[group] is required. This is the name or id of a firewall rule group.\n"
640
+ end
641
+
642
+ optparse.parse!(args)
643
+ connect(options)
644
+
645
+ if args.count < 2
646
+ puts optparse
647
+ return 1
648
+ end
649
+ _firewall_rule_group(args[0], args[1], options)
650
+ end
651
+
652
+ def _firewall_rule_group(router_id, group_id, options)
653
+ @network_routers_interface.setopts(options)
654
+ if options[:dry_run]
655
+ if router_id.to_s =~ /\A\d{1,}\Z/
656
+ print_dry_run @network_routers_interface.dry.list({name:router_id})
657
+ else
658
+ if group_id.to_s =~ /\A\d{1,}\Z/
659
+ print_dry_run @network_routers_interface.dry.get_firewall_rule_group(router_id.to_i, group_id)
660
+ else
661
+ print_dry_run @network_routers_interface.dry.list_firewall_rule_groups(router_id.to_i, {phrase:router_id})
662
+ end
663
+ end
664
+ return
665
+ end
666
+ router = find_router(router_id)
667
+ if router.nil?
668
+ return 1
669
+ end
670
+
671
+ if router['type']['hasFirewallGroups']
672
+ group = find_firewall_rule_group(router['id'], group_id)
673
+ return 1 if group.nil?
674
+
675
+ render_response({ruleGroup: group}, options, 'ruleGroup') do
676
+ print_h1 "Firewall Rule Group Details"
677
+ print cyan
678
+ description_cols = {
679
+ "ID" => lambda {|it| it['id'] },
680
+ "Name" => lambda {|it| it['name'] },
681
+ "Description" => lambda {|it| it['description']},
682
+ "Priority" => lambda {|it| it['priority']},
683
+ "Category" => lambda {|it| it['groupLayer']}
684
+ }
685
+ print_description_list(description_cols, group)
686
+
687
+ if is_master_account
688
+ description_cols["Visibility"] = lambda {|it| it['visibility']}
689
+ description_cols["Tenants"] = lambda {|it| it['tenants'].collect {|tenant| tenant['name']}.join(', ')}
690
+ end
691
+ print_description_list(description_cols, group)
692
+ end
693
+ else
694
+ print_red_alert "Firewall rule groups not supported for #{router['type']['name']}"
695
+ return 1
696
+ end
697
+ println reset
698
+ end
699
+
700
+ def add_firewall_rule_group(args)
701
+ options = {:options=>{}}
702
+ params = {}
703
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
704
+ opts.banner = subcommand_usage("[router] [name]")
705
+ opts.on('-n', '--name VALUE', String, "Name for this firewall rule group") do |val|
706
+ params['name'] = val
707
+ end
708
+ opts.on('-D', '--description VALUE', String, "Description for this firewall rule group") do |val|
709
+ params['description'] = val
710
+ end
711
+ opts.on('--priority VALUE', Integer, "Priority for this firewall rule group (not applicable to all firewall types)") do |val|
712
+ params['priority'] = val
713
+ end
714
+ add_perms_options(opts, options, ['plans', 'groups'])
715
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
716
+ opts.footer = "Create a network router firewall rule group."
717
+ end
718
+ optparse.parse!(args)
719
+ connect(options)
720
+ if args.count < 1 || args.count > 2
721
+ print_error MtnCloud::Terminal.angry_prompt
722
+ puts_error "wrong number of arguments, expected 1-2 and got (#{args.count}) #{args.inspect}\n#{optparse}"
723
+ return 1
724
+ end
725
+ if args.count > 1
726
+ params['name'] = args[1]
727
+ end
728
+ begin
729
+ router = find_router(args[0])
730
+
731
+ if router.nil?
732
+ return 1
733
+ end
734
+
735
+ if !router['type']['hasFirewallGroups']
736
+ print_red_alert "Firewall rule groups not supported for #{router['type']['name']}"
737
+ return 1
738
+ end
739
+
740
+ if options[:payload]
741
+ payload = options[:payload]
742
+ else
743
+ params['name'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'name', 'type' => 'text', 'fieldLabel' => 'Group Name', 'required' => true}], options[:options], @api_client, params)['name']
744
+ params['description'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'description', 'type' => 'text', 'fieldLabel' => 'Description', 'required' => false}], options[:options], @api_client, params)['description']
745
+
746
+ if router['type']['hasSecurityGroupPriority']
747
+ params['priority'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'priority', 'type' => 'number', 'fieldLabel' => 'Priority', 'required' => false}], options[:options], @api_client, params)['priority']
748
+ end
749
+
750
+ option_types = router['type']['ruleGroupOptionTypes'].reject {|it| ['name'].include?(it['fieldName'])}.sort {|it| it['displayOrder']}
751
+
752
+ # prompt options
753
+ option_result = MtnCloud::Cli::OptionTypes.prompt(option_types, options[:options].deep_merge({:context_map => {'group' => ''}}), @api_client, {}, nil, true)
754
+
755
+ rule_group = params.deep_merge(option_result)
756
+
757
+ # prompt perms
758
+ if is_master_account
759
+ rule_group.merge!(prompt_permissions_v2(options, ['plans', 'groups']))
760
+ end
761
+ payload = {'ruleGroup' => rule_group}
762
+ end
763
+
764
+ @network_routers_interface.setopts(options)
765
+ if options[:dry_run]
766
+ print_dry_run @network_routers_interface.dry.create_firewall_rule_group(router['id'], payload)
767
+ return
768
+ end
769
+
770
+ json_response = @network_routers_interface.create_firewall_rule_group(router['id'], payload)
771
+
772
+ if options[:json]
773
+ print JSON.pretty_generate(json_response), "\n"
774
+ return
775
+ end
776
+ print_green_success "\nAdded Network Router Firewall Rule Group #{payload['ruleGroup']['name']}\n"
777
+ _firewall_rule_group(router['id'], json_response['id'], options)
778
+ rescue RestClient::Exception => e
779
+ print_rest_exception(e, options)
780
+ exit 1
781
+ end
782
+ end
783
+
784
+ def update_firewall_rule_group(args)
785
+ options = {:options=>{}}
786
+ params = {}
787
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
788
+ opts.banner = subcommand_usage("[router] [name]")
789
+ opts.on('-n', '--name VALUE', String, "Name for this firewall rule group") do |val|
790
+ params['name'] = val
791
+ end
792
+ opts.on('-D', '--description VALUE', String, "Description for this firewall rule group") do |val|
793
+ params['description'] = val
794
+ end
795
+ opts.on('--priority VALUE', Integer, "Priority for this firewall rule group (not applicable to all firewall types)") do |val|
796
+ params['priority'] = val
797
+ end
798
+ add_perms_options(opts, options, ['plans', 'groups'])
799
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
800
+ opts.footer = "Update a network router firewall rule group.\n" +
801
+ "[router] is required. This is the name or id of an existing network router.\n" +
802
+ "[name] is required. This is the name or id of an existing network router firewall rule group."
803
+ end
804
+
805
+ optparse.parse!(args)
806
+ if args.count != 2
807
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
808
+ end
809
+ connect(options)
810
+
811
+ begin
812
+ router = find_router(args[0])
813
+
814
+ if router.nil?
815
+ return 1
816
+ end
817
+
818
+ if !router['type']['hasFirewallGroups']
819
+ print_red_alert "Firewall rule group not supported for #{router['type']['name']}"
820
+ return 1
821
+ end
822
+
823
+ group = router['firewall'] && router['firewall']['ruleGroups'] ? router['firewall']['ruleGroups'].find {|it| it['name'] == args[1] || it['id'] == args[1].to_i} : nil
824
+
825
+ if !group
826
+ print_red_alert "Firewall rule group #{args[1]} not found for router #{router['name']}"
827
+ exit 1
828
+ end
829
+
830
+ if is_master_account
831
+ params['visibility'] = options[:visibility] if !options[:visibility].nil?
832
+ params['tenants'] = options[:tenants].collect {|it| {'id' => it}} if !options[:tenants].nil?
833
+ end
834
+
835
+ payload = parse_payload(options) || {'ruleGroup' => params}
836
+ payload['ruleGroup'].deep_merge!(options[:options].reject {|k,v| k.is_a?(Symbol) }) if options[:options]
837
+
838
+ if payload['ruleGroup'].empty?
839
+ print_green_success "Nothing to update"
840
+ exit 1
841
+ end
842
+
843
+ @network_routers_interface.setopts(options)
844
+ if options[:dry_run]
845
+ print_dry_run @network_routers_interface.dry.update_firewall_rule_group(router['id'], group['id'], payload)
846
+ return
847
+ end
848
+
849
+ json_response = @network_routers_interface.update_firewall_rule_group(router['id'], group['id'], payload)
850
+
851
+ if options[:json]
852
+ print JSON.pretty_generate(json_response), "\n"
853
+ return
854
+ end
855
+ print_green_success "\nUpdated Network Router Firewall Rule Group #{payload['ruleGroup']['name']}\n"
856
+ _firewall_rule_group(router['id'], args[1], options)
857
+ rescue RestClient::Exception => e
858
+ print_rest_exception(e, options)
859
+ exit 1
860
+ end
861
+ end
862
+
863
+ def remove_firewall_rule_group(args)
864
+ options = {}
865
+ query_params = {}
866
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
867
+ opts.banner = subcommand_usage("[router] [group]")
868
+ build_common_options(opts, options, [:auto_confirm, :json, :dry_run, :quiet, :remote])
869
+ opts.footer = "Delete a network router firewall rule group.\n" +
870
+ "[router] is required. This is the name or id of an existing network router."
871
+ "[group] is required. This is the name or id of an existing network router firewall rule group."
872
+ end
873
+ optparse.parse!(args)
874
+ if args.count != 2
875
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
876
+ end
877
+ connect(options)
878
+
879
+ begin
880
+ router = find_router(args[0])
881
+ return if !router
882
+
883
+ group = router['firewall'] && router['firewall']['ruleGroups'] ? router['firewall']['ruleGroups'].find {|it| it['name'] == args[1] || it['id'] == args[1].to_i} : nil
884
+
885
+ if !group
886
+ print_red_alert "Firewall rule group #{args[1]} not found for router #{router['name']}"
887
+ exit 1
888
+ end
889
+
890
+ unless options[:yes] || ::MtnCloud::Cli::OptionTypes::confirm("Are you sure you would like to remove the firewall rule group '#{group['name']}' from router '#{router['name']}'?", options)
891
+ return 9, "aborted command"
892
+ end
893
+ @network_routers_interface.setopts(options)
894
+ if options[:dry_run]
895
+ print_dry_run @network_routers_interface.dry.destroy_firewall_rule_group(router['id'], group['id'])
896
+ return
897
+ end
898
+ json_response = @network_routers_interface.destroy_firewall_rule_group(router['id'], group['id'])
899
+ if options[:json]
900
+ print JSON.pretty_generate(json_response)
901
+ print "\n"
902
+ elsif !options[:quiet]
903
+ print_green_success "\nFirewall rule group #{group['name']} for router #{router['name']} is being removed...\n"
904
+ _firewall_rule_groups(find_router(router['id']), options)
905
+ end
906
+ rescue RestClient::Exception => e
907
+ print_rest_exception(e, options)
908
+ exit 1
909
+ end
910
+ end
911
+
912
+ def firewall_rules(args)
913
+ options = {}
914
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
915
+ opts.banner = subcommand_usage("[router]")
916
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
917
+ opts.footer = "Display network router firewall rules.\n" +
918
+ "[router] is required. This is the name or id of a network router."
919
+ end
920
+
921
+ optparse.parse!(args)
922
+ connect(options)
923
+
924
+ if args.count < 1
925
+ puts optparse
926
+ return 1
927
+ end
928
+
929
+ begin
930
+ @network_routers_interface.setopts(options)
931
+ if options[:dry_run]
932
+ if args[0].to_s =~ /\A\d{1,}\Z/
933
+ print_dry_run @network_routers_interface.dry.get(args[0].to_i)
934
+ else
935
+ print_dry_run @network_routers_interface.dry.list({name:args[0]})
936
+ end
937
+ return
938
+ end
939
+ router = find_router(args[0])
940
+ if router.nil?
941
+ return 1
942
+ end
943
+
944
+ _firewall_rules(router, options)
945
+ rescue RestClient::Exception => e
946
+ print_rest_exception(e, options)
947
+ return 1
948
+ end
949
+ end
950
+
951
+ def _firewall_rules(router, options)
952
+ if router['type']['hasFirewall']
953
+ rules = router['type']['hasFirewallGroups'] ? (router['firewall']['ruleGroups'] || []).collect {|it| it['rules']}.flatten : router['firewall']['rules']
954
+
955
+ json_response = {'rules' => rules}
956
+
957
+ if options[:json]
958
+ puts as_json(json_response, options, "rules")
959
+ return 0
960
+ elsif options[:yaml]
961
+ puts as_yaml(json_response, options, "rules")
962
+ return 0
963
+ elsif options[:csv]
964
+ puts records_as_csv(json_response['rules'], options)
965
+ return 0
966
+ end
967
+
968
+ if router['type']['hasFirewallGroups']
969
+ rules = []
970
+ (router['firewall']['ruleGroups'] || []).each do |rule_group|
971
+ (rule_group['rules'] || []).each do |rule|
972
+ rule['groupId'] = rule_group['id']
973
+ rule['groupName'] ||= rule_group['name']
974
+ rules << rule
975
+ end
976
+ end
977
+ end
978
+
979
+ if rules.count > 0
980
+ print_h1 "Firewall Rules For: #{router['name']}"
981
+ rows = rules.collect do |it|
982
+ {
983
+ id: it['id'],
984
+ group_name: it['groupName'],
985
+ name: it['name'],
986
+ type: it['ruleType'],
987
+ policy: it['policy'],
988
+ direction: it['direction'] || 'any',
989
+ source: it['source'].kind_of?(Array) && it['source'].count > 0 ? it['source'].join(', ') : (it['source'].nil? || it['source'].empty? ? 'any' : it['source']),
990
+ destination: it['destination'].kind_of?(Array) && it['destination'].count > 0 ? it['destination'].join(', ') : (it['destination'].nil? || it['destination'].empty? ? 'any' : it['destination']),
991
+ application: it['applications'].count > 0 ? it['applications'][0]['name'] : "#{(it['protocol'] || 'any')} #{it['portRange'] || ''}"
992
+ }
993
+ end
994
+
995
+ if router['type']['hasFirewallGroups']
996
+ puts as_pretty_table(rows, [:id, :group_name, :name, :type, :policy, :direction, :source, :destination, :application])
997
+ else
998
+ puts as_pretty_table(rows, [:id, :name, :type, :policy, :direction, :source, :destination, :application])
999
+ end
1000
+ else
1001
+ print_h1 "No Firewall Rules"
1002
+ end
1003
+ else
1004
+ print_red_alert "Firewall not supported for #{router['type']['name']}"
1005
+ end
1006
+ println reset
1007
+ end
1008
+
1009
+ def firewall_rule(args)
1010
+ options = {}
1011
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1012
+ opts.banner = subcommand_usage("[router] [rule]")
1013
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
1014
+ opts.footer = "Display network router firewall rule details." + "\n" +
1015
+ "[router] is required. This is the name or id of a network router.\n" +
1016
+ "[rule] is required. This is the name or id of a firewall rule.\n"
1017
+ end
1018
+
1019
+ optparse.parse!(args)
1020
+ connect(options)
1021
+
1022
+ if args.count < 2
1023
+ puts optparse
1024
+ return 1
1025
+ end
1026
+ @network_routers_interface.setopts(options)
1027
+ if options[:dry_run]
1028
+ if args[0].to_s =~ /\A\d{1,}\Z/
1029
+ print_dry_run @network_routers_interface.dry.get(args[0].to_i)
1030
+ else
1031
+ print_dry_run @network_routers_interface.dry.list({name:args[0]})
1032
+ end
1033
+ return
1034
+ end
1035
+ _firewall_rule(args[0], args[1], options)
1036
+ end
1037
+
1038
+ def _firewall_rule(router_id, rule_id, options)
1039
+ router = find_router(router_id)
1040
+ if router.nil?
1041
+ return 1
1042
+ end
1043
+
1044
+ if router['type']['hasFirewall']
1045
+ rule = find_firewall_rule(router, rule_id)
1046
+
1047
+ if rule
1048
+ json_response = {'rule' => rule}
1049
+
1050
+ if options[:json]
1051
+ puts as_json(json_response, options, "rule")
1052
+ return 0
1053
+ elsif options[:yaml]
1054
+ puts as_yaml(json_response, options, "rule")
1055
+ return 0
1056
+ elsif options[:csv]
1057
+ puts records_as_csv([json_response['rule']], options)
1058
+ return 0
1059
+ end
1060
+
1061
+ print_h1 "Firewall Rule Details"
1062
+ print cyan
1063
+ description_cols = {
1064
+ "ID" => lambda {|it| it['id'] },
1065
+ "Enabled" => lambda {|it| format_boolean(it['enabled'])},
1066
+ "Priority" => lambda {|it| it['priority']},
1067
+ "Name" => lambda {|it| it['name'] },
1068
+ "Type" => lambda {|it| it['ruleType'] },
1069
+ "Policy" => lambda {|it| it['policy'] },
1070
+ "Direction" => lambda {|it| it['direction'] || 'any' },
1071
+ "Source" => lambda {|it| it['source'].kind_of?(Array) && it['source'].count > 0 ? it['source'].join(', ') : (it['source'].nil? || it['source'].empty? ? 'any' : it['source']) },
1072
+ "Destination" => lambda {|it| it['destination'].kind_of?(Array) && it['destination'].count > 0 ? it['destination'].join(', ') : (it['destination'].nil? || it['destination'].empty? ? 'any' : it['destination'])},
1073
+ "Application" => lambda {|it| it['applications'].count > 0 ? it['applications'][0]['name'] : "#{(it['protocol'] || 'any')} #{it['portRange'] || ''}"}
1074
+ }
1075
+ print_description_list(description_cols, rule)
1076
+ else
1077
+ print_red_alert "Firewall rule #{rule_id} not found for router #{router['name']}"
1078
+ end
1079
+ else
1080
+ print_red_alert "Firewall not supported for #{router['type']['name']}"
1081
+ end
1082
+ println reset
1083
+ end
1084
+
1085
+ def add_firewall_rule(args)
1086
+ options = {:options=>{}}
1087
+ params = {}
1088
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
1089
+ opts.banner = subcommand_usage("[router] [name]")
1090
+ opts.on('-n', '--name VALUE', String, "Name for this firewall rule") do |val|
1091
+ params['name'] = val
1092
+ end
1093
+ opts.on('--enabled [on|off]', String, "Can be used to enable / disable the rule. Default is on") do |val|
1094
+ params['enabled'] = val.to_s == 'on' || val.to_s == 'true' || val.to_s == '1' || val.to_s == ''
1095
+ end
1096
+ opts.on( '-g', '--group GROUP', "Firewall rule group name or ID (not applicable to all firewall types)" ) do |val|
1097
+ options[:group] = val
1098
+ end
1099
+ opts.on('--priority VALUE', Integer, "Priority for this rule (not applicable to all firewall types)") do |val|
1100
+ params['priority'] = val
1101
+ end
1102
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
1103
+ opts.footer = "Create a network router firewall rule."
1104
+ end
1105
+ optparse.parse!(args)
1106
+ connect(options)
1107
+ if args.count < 1 || args.count > 2
1108
+ print_error MtnCloud::Terminal.angry_prompt
1109
+ puts_error "wrong number of arguments, expected 1-2 and got (#{args.count}) #{args.inspect}\n#{optparse}"
1110
+ return 1
1111
+ end
1112
+ if args.count > 1
1113
+ params['name'] = args[1]
1114
+ end
1115
+ begin
1116
+ router = find_router(args[0])
1117
+
1118
+ if router.nil?
1119
+ return 1
1120
+ end
1121
+
1122
+ if !router['type']['hasFirewall']
1123
+ print_red_alert "Firewall not supported for #{router['type']['name']}"
1124
+ return 1
1125
+ end
1126
+
1127
+ if options[:payload]
1128
+ payload = options[:payload]
1129
+ else
1130
+ params['name'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'name', 'type' => 'text', 'fieldLabel' => 'Rule Name', 'required' => true}], options[:options], @api_client, params)['name']
1131
+
1132
+ if router['type']['hasFirewallGroups']
1133
+ if !router['firewall']['ruleGroups'].count
1134
+ print_red_alert "No firewall rule group found for #{router['type']['name']}"
1135
+ return 1
1136
+ end
1137
+
1138
+ if options[:group]
1139
+ group = router['firewall']['ruleGroups'].find {|it| it['name'] == options[:group] || it['id'] == options[:group].to_i}
1140
+ if !group
1141
+ print_red_alert "Firewall rule group #{options[:group]} not found for #{router['type']['name']}"
1142
+ return 1
1143
+ end
1144
+ group_id = group['id']
1145
+ else
1146
+ group_id = MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'group', 'type' => 'select', 'fieldLabel' => 'Rule Group', 'required' => true, 'selectOptions' => router['firewall']['ruleGroups'].collect {|it| {'name' => it['name'], 'value' => it['id']}}}])['group']
1147
+ end
1148
+
1149
+ params['config'] = {} if params['config'].nil?
1150
+ params['config']['parentId'] = "group-#{group_id}"
1151
+ end
1152
+
1153
+ params['enabled'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'enabled', 'fieldLabel' => 'Enabled', 'type' => 'checkbox', 'description' => 'Enable Rule.', 'defaultValue' => true, 'required' => false}], options, @api_client, {})['enabled'] == 'on'
1154
+
1155
+ if router['type']['code'].start_with?('nsx-t')
1156
+ params['priority'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'priority', 'type' => 'number', 'fieldLabel' => 'Priority', 'required' => false}], options[:options], @api_client, params)['priority']
1157
+ end
1158
+
1159
+ option_types = router['type']['ruleOptionTypes'].reject {|it| ['name'].include?(it['fieldName'])}.sort {|it| it['displayOrder']}
1160
+
1161
+ # prompt options
1162
+ api_params = {}
1163
+ api_params['networkServerId'] = router['networkServer']['id'] if router['networkServer']
1164
+ api_params['zoneId'] = router['zone']['id'] if router['networkServer'].nil?
1165
+ option_result = MtnCloud::Cli::OptionTypes.prompt(option_types, options[:options].deep_merge({:context_map => {'rule' => ''}}), @api_client, api_params, nil, true)
1166
+ payload = {'rule' => params.deep_merge(option_result)}
1167
+ end
1168
+
1169
+ @network_routers_interface.setopts(options)
1170
+ if options[:dry_run]
1171
+ print_dry_run @network_routers_interface.dry.create_firewall_rule(router['id'], payload)
1172
+ return
1173
+ end
1174
+
1175
+ json_response = @network_routers_interface.create_firewall_rule(router['id'], payload)
1176
+
1177
+ if options[:json]
1178
+ print JSON.pretty_generate(json_response), "\n"
1179
+ return
1180
+ end
1181
+ print_green_success "\nAdded Network Router Firewall Rule #{payload['rule']['name']}\n"
1182
+ _firewall_rule(router['id'], json_response['id'], options)
1183
+ rescue RestClient::Exception => e
1184
+ print_rest_exception(e, options)
1185
+ exit 1
1186
+ end
1187
+ end
1188
+
1189
+ def update_firewall_rule(args)
1190
+ options = {:options=>{}}
1191
+ params = {}
1192
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
1193
+ opts.banner = subcommand_usage("[router] [name]")
1194
+ opts.on('-n', '--name VALUE', String, "Name for this firewall rule") do |val|
1195
+ params['name'] = val
1196
+ end
1197
+ opts.on('--enabled [on|off]', String, "Can be used to enable / disable the rule. Default is on") do |val|
1198
+ params['enabled'] = val.to_s == 'on' || val.to_s == 'true' || val.to_s == '1' || val.to_s == ''
1199
+ end
1200
+ opts.on('--priority VALUE', Integer, "Priority for this rule (not applicable to all firewall types)") do |val|
1201
+ params['priority'] = val
1202
+ end
1203
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
1204
+ opts.footer = "Update a network router firewall rule.\n" +
1205
+ "[router] is required. This is the name or id of an existing network router.\n" +
1206
+ "[name] is required. This is the name or id of an existing network router firewall rule."
1207
+ end
1208
+
1209
+ optparse.parse!(args)
1210
+ if args.count != 2
1211
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
1212
+ end
1213
+ connect(options)
1214
+
1215
+ begin
1216
+ router = find_router(args[0])
1217
+
1218
+ if router.nil?
1219
+ return 1
1220
+ end
1221
+
1222
+ if !router['type']['hasFirewall']
1223
+ print_red_alert "Firewall not supported for #{router['type']['name']}"
1224
+ return 1
1225
+ end
1226
+
1227
+ rule = find_firewall_rule(router, args[1])
1228
+
1229
+ if !rule
1230
+ print_red_alert "Firewall rule #{args[1]} not found for router #{router['name']}"
1231
+ exit 1
1232
+ end
1233
+
1234
+ payload = parse_payload(options) || {'rule' => params}
1235
+ payload['rule'].deep_merge!(options[:options].reject {|k,v| k.is_a?(Symbol) }) if options[:options]
1236
+
1237
+ if payload['rule'].empty?
1238
+ print_green_success "Nothing to update"
1239
+ exit 1
1240
+ end
1241
+
1242
+ @network_routers_interface.setopts(options)
1243
+ if options[:dry_run]
1244
+ print_dry_run @network_routers_interface.dry.update_firewall_rule(router['id'], rule['id'], payload)
1245
+ return
1246
+ end
1247
+
1248
+ json_response = @network_routers_interface.update_firewall_rule(router['id'], rule['id'], payload)
1249
+
1250
+ if options[:json]
1251
+ print JSON.pretty_generate(json_response), "\n"
1252
+ return
1253
+ end
1254
+ print_green_success "\nUpdated Network Router Firewall Rule #{payload['rule']['name']}\n"
1255
+ _firewall_rule(router['id'], args[1], options)
1256
+ rescue RestClient::Exception => e
1257
+ print_rest_exception(e, options)
1258
+ exit 1
1259
+ end
1260
+ end
1261
+
1262
+ def remove_firewall_rule(args)
1263
+ options = {}
1264
+ query_params = {}
1265
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1266
+ opts.banner = subcommand_usage("[router] [rule]")
1267
+ build_common_options(opts, options, [:auto_confirm, :json, :dry_run, :quiet, :remote])
1268
+ opts.footer = "Delete a network router firewall rule.\n" +
1269
+ "[router] is required. This is the name or id of an existing network router."
1270
+ "[rule] is required. This is the name or id of an existing network router firewall rule."
1271
+ end
1272
+ optparse.parse!(args)
1273
+ if args.count != 2
1274
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
1275
+ end
1276
+ connect(options)
1277
+
1278
+ begin
1279
+ router = find_router(args[0])
1280
+ return if !router
1281
+
1282
+ rule = find_firewall_rule(router, args[1])
1283
+
1284
+ if !rule
1285
+ print_red_alert "Firewall rule #{args[1]} not found for router #{router['name']}"
1286
+ exit 1
1287
+ end
1288
+
1289
+ unless options[:yes] || ::MtnCloud::Cli::OptionTypes::confirm("Are you sure you would like to remove the firewall rule '#{rule['name']}' from router '#{router['name']}'?", options)
1290
+ return 9, "aborted command"
1291
+ end
1292
+ @network_routers_interface.setopts(options)
1293
+ if options[:dry_run]
1294
+ print_dry_run @network_routers_interface.dry.destroy_firewall_rule(router['id'], rule['id'])
1295
+ return
1296
+ end
1297
+ json_response = @network_routers_interface.destroy_firewall_rule(router['id'], rule['id'])
1298
+ if options[:json]
1299
+ print JSON.pretty_generate(json_response)
1300
+ print "\n"
1301
+ elsif !options[:quiet]
1302
+ print_green_success "\nFirewall rule #{rule['name']} for router #{router['name']} is being removed...\n"
1303
+ _firewall_rules(find_router(router['id']), options)
1304
+ end
1305
+ rescue RestClient::Exception => e
1306
+ print_rest_exception(e, options)
1307
+ exit 1
1308
+ end
1309
+ end
1310
+
1311
+ def dhcp(args)
1312
+ options = {}
1313
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1314
+ opts.banner = subcommand_usage("[router]")
1315
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
1316
+ opts.footer = "Display network router DHCP details." + "\n" +
1317
+ "[router] is required. This is the name or id of a network router."
1318
+ end
1319
+
1320
+ optparse.parse!(args)
1321
+ connect(options)
1322
+
1323
+ if args.count < 1
1324
+ puts optparse
1325
+ return 1
1326
+ end
1327
+
1328
+ begin
1329
+ @network_routers_interface.setopts(options)
1330
+ if options[:dry_run]
1331
+ if args[0].to_s =~ /\A\d{1,}\Z/
1332
+ print_dry_run @network_routers_interface.dry.get(args[0].to_i)
1333
+ else
1334
+ print_dry_run @network_routers_interface.dry.list({name:args[0]})
1335
+ end
1336
+ return
1337
+ end
1338
+ router = find_router(args[0])
1339
+ if router.nil?
1340
+ return 1
1341
+ end
1342
+
1343
+ json_response = {'networkRouter' => router}
1344
+
1345
+ if options[:json]
1346
+ puts as_json(json_response, options, "networkRouter")
1347
+ return 0
1348
+ elsif options[:yaml]
1349
+ puts as_yaml(json_response, options, "networkRouter")
1350
+ return 0
1351
+ elsif options[:csv]
1352
+ puts records_as_csv([json_response['networkRouter']], options)
1353
+ return 0
1354
+ end
1355
+
1356
+ print_h1 "Network Router DHCP Details For: #{router['name']}"
1357
+ print cyan
1358
+
1359
+ if router['type']['hasDhcp']
1360
+ print_dhcp(router, true)
1361
+ else
1362
+ print_red_alert "DHCP not supported for #{router['type']['name']}"
1363
+ end
1364
+ println reset
1365
+ rescue RestClient::Exception => e
1366
+ print_rest_exception(e, options)
1367
+ return 1
1368
+ end
1369
+ end
1370
+
1371
+ def routes(args)
1372
+ options = {}
1373
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1374
+ opts.banner = subcommand_usage("[router]")
1375
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
1376
+ opts.footer = "List network router routes." + "\n" +
1377
+ "[router] is required. This is the name or id of a network router."
1378
+ end
1379
+
1380
+ optparse.parse!(args)
1381
+ connect(options)
1382
+
1383
+ if args.count < 1
1384
+ puts optparse
1385
+ return 1
1386
+ end
1387
+ _routes(args[0], options)
1388
+ end
1389
+
1390
+ def _routes(router_id, options)
1391
+ begin
1392
+ @network_routers_interface.setopts(options)
1393
+ if options[:dry_run]
1394
+ if args[0].to_s =~ /\A\d{1,}\Z/
1395
+ print_dry_run @network_routers_interface.dry.get(router_id.to_i)
1396
+ else
1397
+ print_dry_run @network_routers_interface.dry.list({name:router_id})
1398
+ end
1399
+ return
1400
+ end
1401
+ router = find_router(router_id)
1402
+ if router.nil?
1403
+ return 1
1404
+ end
1405
+
1406
+ json_response = {'networkRoutes' => router['routes']}
1407
+
1408
+ if options[:json]
1409
+ puts as_json(json_response, options, "networkRoutes")
1410
+ return 0
1411
+ elsif options[:yaml]
1412
+ puts as_yaml(json_response, options, "networkRoutes")
1413
+ return 0
1414
+ elsif options[:csv]
1415
+ puts records_as_csv(json_response['networkRoutes'], options)
1416
+ return 0
1417
+ end
1418
+
1419
+ print_h1 "Network Router Routes For: #{router['name']}"
1420
+ print cyan
1421
+
1422
+ if router['type']['hasRouting']
1423
+ print_routes(router)
1424
+ else
1425
+ print_red_alert "Routes not supported for #{router['type']['name']}"
1426
+ end
1427
+ print reset
1428
+ rescue RestClient::Exception => e
1429
+ print_rest_exception(e, options)
1430
+ return 1
1431
+ end
1432
+ end
1433
+
1434
+ def add_route(args)
1435
+ options = {:options=>{}}
1436
+ params = {}
1437
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
1438
+ opts.banner = subcommand_usage("[router] [name]")
1439
+ opts.on('-n', '--name VALUE', String, "Name for this route") do |val|
1440
+ params['name'] = val
1441
+ end
1442
+ opts.on('-D', '--description VALUE', String, "Description") do |val|
1443
+ params['description'] = val
1444
+ end
1445
+ opts.on('--enabled [on|off]', String, "Can be used to enable / disable the route. Default is on") do |val|
1446
+ options[:enabled] = val.to_s == 'on' || val.to_s == 'true' || val.to_s == '1' || val.to_s == ''
1447
+ end
1448
+ opts.on('--default [on|off]', String, "Can be used to enable / disable as default route. Default is off") do |val|
1449
+ options[:defaultRoute] = val.to_s == 'on' || val.to_s == 'true' || val.to_s == '1' || val.to_s == ''
1450
+ end
1451
+ opts.on('--source VALUE', String, "Network for this route") do |val|
1452
+ params['source'] = val
1453
+ end
1454
+ opts.on('--destination VALUE', String, "Next hop for this route") do |val|
1455
+ params['destination'] = val
1456
+ end
1457
+ opts.on('--mtu VALUE', String, "MTU for this route") do |val|
1458
+ params['networkMtu'] = val
1459
+ end
1460
+ opts.on('--priority VALUE', Integer, "Priority for this route") do |val|
1461
+ params['priority'] = val
1462
+ end
1463
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
1464
+ opts.footer = "Create a network router route."
1465
+ end
1466
+ optparse.parse!(args)
1467
+ connect(options)
1468
+ if args.count < 1 || args.count > 2
1469
+ print_error MtnCloud::Terminal.angry_prompt
1470
+ puts_error "wrong number of arguments, expected 1-2 and got (#{args.count}) #{args.inspect}\n#{optparse}"
1471
+ return 1
1472
+ end
1473
+ if args.count > 1
1474
+ params['name'] = args[1]
1475
+ end
1476
+ begin
1477
+ router = find_router(args[0])
1478
+
1479
+ if router.nil?
1480
+ return 1
1481
+ end
1482
+
1483
+ if !router['type']['hasRouting']
1484
+ print_red_alert "Routes not supported for #{router['type']['name']}"
1485
+ return 1
1486
+ end
1487
+
1488
+ if options[:payload]
1489
+ payload = options[:payload]
1490
+ payload = {'networkRoute' => payload['route']} if payload['route']
1491
+ else
1492
+ params['name'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'name', 'type' => 'text', 'fieldLabel' => 'Name', 'required' => true}], options[:options], @api_client, params)['name']
1493
+ params['description'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'description', 'type' => 'text', 'fieldLabel' => 'Description', 'required' => false}], options[:options], @api_client, params)['description']
1494
+
1495
+ # prompt for enabled if not set
1496
+ params['enabled'] = options[:enabled].nil? ? MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'enabled', 'fieldLabel' => 'Enabled', 'type' => 'checkbox', 'description' => 'Enabling Route.', 'defaultValue' => true, 'required' => false}], options, @api_client, {})['enabled'] == 'on' : options[:enabled]
1497
+
1498
+ # default route
1499
+ params['defaultRoute'] = options[:defaultRoute].nil? ? MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'defaultRoute', 'fieldLabel' => 'Default Route', 'type' => 'checkbox', 'description' => 'Default Route.', 'defaultValue' => false, 'required' => false}], options, @api_client, {})['defaultRoute'] == 'on' : options[:defaultRoute]
1500
+
1501
+ params['source'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'source', 'type' => 'text', 'fieldLabel' => 'Network', 'required' => true}], options[:options], @api_client, params)['source']
1502
+ params['destination'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'destination', 'type' => 'text', 'fieldLabel' => 'Next Hop', 'required' => true}], options[:options], @api_client, params)['destination']
1503
+ params['networkMtu'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'networkMtu', 'type' => 'text', 'fieldLabel' => 'MTU', 'required' => false}], options[:options], @api_client, params)['networkMtu']
1504
+ params['priority'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'priority', 'type' => 'number', 'fieldLabel' => 'Priority', 'required' => false}], options[:options], @api_client, params)['priority']
1505
+
1506
+ payload = {'networkRoute' => params}
1507
+ end
1508
+
1509
+ @network_routers_interface.setopts(options)
1510
+ if options[:dry_run]
1511
+ print_dry_run @network_routers_interface.dry.create_route(router['id'], payload)
1512
+ return
1513
+ end
1514
+
1515
+ json_response = @network_routers_interface.create_route(router['id'], payload)
1516
+
1517
+ if options[:json]
1518
+ print JSON.pretty_generate(json_response), "\n"
1519
+ return
1520
+ end
1521
+ print_green_success "\nAdded Network Router Route #{payload['networkRoute']['name']}"
1522
+ _routes(router['id'], options)
1523
+ rescue RestClient::Exception => e
1524
+ print_rest_exception(e, options)
1525
+ exit 1
1526
+ end
1527
+ end
1528
+
1529
+ def remove_route(args)
1530
+ options = {}
1531
+ query_params = {}
1532
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1533
+ opts.banner = subcommand_usage("[router] [route]")
1534
+ build_common_options(opts, options, [:auto_confirm, :json, :dry_run, :quiet, :remote])
1535
+ opts.footer = "Delete a network router route.\n" +
1536
+ "[router] is required. This is the name or id of an existing network router."
1537
+ "[route] is required. This is the name or id of an existing network router route."
1538
+ end
1539
+ optparse.parse!(args)
1540
+ if args.count != 2
1541
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
1542
+ end
1543
+ connect(options)
1544
+
1545
+ begin
1546
+ router = find_router(args[0])
1547
+ return if !router
1548
+
1549
+ route = router['routes'] ? router['routes'].find {|it| it['name'] == args[1] || it['id'] == args[1].to_i} : nil
1550
+
1551
+ if !route
1552
+ print_red_alert "Route #{args[1]} not found for router #{router['name']}"
1553
+ exit 1
1554
+ end
1555
+
1556
+ unless options[:yes] || ::MtnCloud::Cli::OptionTypes::confirm("Are you sure you would like to remove the route '#{route['name']}' from router '#{router['name']}'?", options)
1557
+ return 9, "aborted command"
1558
+ end
1559
+ @network_routers_interface.setopts(options)
1560
+ if options[:dry_run]
1561
+ print_dry_run @network_routers_interface.dry.destroy_route(router['id'], route['id'])
1562
+ return
1563
+ end
1564
+ json_response = @network_routers_interface.destroy_route(router['id'], route['id'])
1565
+ if options[:json]
1566
+ print JSON.pretty_generate(json_response)
1567
+ print "\n"
1568
+ elsif !options[:quiet]
1569
+ print_green_success "\nRoute #{route['name']} for router #{router['name']} is being removed..."
1570
+ _routes(router['id'], options)
1571
+ end
1572
+ rescue RestClient::Exception => e
1573
+ print_rest_exception(e, options)
1574
+ exit 1
1575
+ end
1576
+ end
1577
+
1578
+ def nats(args)
1579
+ options = {}
1580
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1581
+ opts.banner = subcommand_usage("[router]")
1582
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
1583
+ opts.footer = "List network router NATs." + "\n" +
1584
+ "[router] is required. This is the name or id of a network router."
1585
+ end
1586
+
1587
+ optparse.parse!(args)
1588
+ connect(options)
1589
+
1590
+ if args.count < 1
1591
+ puts optparse
1592
+ return 1
1593
+ end
1594
+ _nats(args[0], options)
1595
+ end
1596
+
1597
+ def _nats(router_id, options)
1598
+ begin
1599
+ @network_routers_interface.setopts(options)
1600
+ if options[:dry_run]
1601
+ if args[0].to_s =~ /\A\d{1,}\Z/
1602
+ print_dry_run @network_routers_interface.dry.get(router_id.to_i)
1603
+ else
1604
+ print_dry_run @network_routers_interface.dry.list({name:router_id})
1605
+ end
1606
+ return
1607
+ end
1608
+ router = find_router(router_id)
1609
+ if router.nil?
1610
+ return 1
1611
+ end
1612
+
1613
+ json_response = {'networkRouterNATs' => router['nats']}
1614
+
1615
+ if options[:json]
1616
+ puts as_json(json_response, options, "networkRouterNATs")
1617
+ return 0
1618
+ elsif options[:yaml]
1619
+ puts as_yaml(json_response, options, "networkRouterNATs")
1620
+ return 0
1621
+ elsif options[:csv]
1622
+ puts records_as_csv(json_response['networkRouterNATs'], options)
1623
+ return 0
1624
+ end
1625
+
1626
+ print_h1 "Network Router NATs For: #{router['name']}"
1627
+ print cyan
1628
+
1629
+ if router['type']['hasNat']
1630
+ print_nats(router)
1631
+ else
1632
+ print_red_alert "NATs not supported for #{router['type']['name']}"
1633
+ end
1634
+ print reset
1635
+ rescue RestClient::Exception => e
1636
+ print_rest_exception(e, options)
1637
+ return 1
1638
+ end
1639
+ end
1640
+
1641
+ def nat(args)
1642
+ options = {}
1643
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1644
+ opts.banner = subcommand_usage("[router] [nat]")
1645
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
1646
+ opts.footer = "Display network router firewall rule details." + "\n" +
1647
+ "[router] is required. This is the name or id of a network router.\n" +
1648
+ "[nat] is required. This is the name or id of a NAT.\n"
1649
+ end
1650
+
1651
+ optparse.parse!(args)
1652
+ connect(options)
1653
+
1654
+ if args.count < 2
1655
+ puts optparse
1656
+ return 1
1657
+ end
1658
+
1659
+ begin
1660
+ @network_routers_interface.setopts(options)
1661
+ if options[:dry_run]
1662
+ if args[0].to_s =~ /\A\d{1,}\Z/
1663
+ print_dry_run @network_routers_interface.dry.get(args[0].to_i)
1664
+ else
1665
+ print_dry_run @network_routers_interface.dry.list({name:args[0]})
1666
+ end
1667
+ return
1668
+ end
1669
+ router = find_router(args[0])
1670
+ if router.nil?
1671
+ return 1
1672
+ end
1673
+
1674
+ if router['type']['hasNat']
1675
+ nat = (router['nats'] || []).find {|it| it['id'] == args[1].to_i || it['name'] == args[1]}
1676
+
1677
+ if nat
1678
+ json_response = {'networkRouterNAT' => nat}
1679
+
1680
+ if options[:json]
1681
+ puts as_json(json_response, options, "networkRouterNAT")
1682
+ return 0
1683
+ elsif options[:yaml]
1684
+ puts as_yaml(json_response, options, "networkRouterNAT")
1685
+ return 0
1686
+ elsif options[:csv]
1687
+ puts records_as_csv([json_response['networkRouterNAT']], options)
1688
+ return 0
1689
+ end
1690
+
1691
+ print_h1 "Network Router NAT Details"
1692
+ print cyan
1693
+
1694
+ description_cols = {
1695
+ "ID" => lambda {|it| it['id'] },
1696
+ "Name" => lambda {|it| it['name'] },
1697
+ "Description" => lambda {|it| it['description'] },
1698
+ "Enabled" => lambda {|it| format_boolean(it['enabled'])},
1699
+ "Source Network" => lambda {|it| it['sourceNetwork']},
1700
+ "Destination Network" => lambda {|it| it['destinationNetwork']},
1701
+ "Translated Network" => lambda {|it| it['translatedNetwork']},
1702
+ "Translated Port" => lambda {|it| it['translatedPorts']},
1703
+ "Priority" => lambda {|it| it['priority'] }
1704
+ }
1705
+ print_description_list(description_cols, nat)
1706
+ else
1707
+ print_red_alert "NAT #{args[1]} not found for router #{router['name']}"
1708
+ end
1709
+ else
1710
+ print_red_alert "NATs not supported for #{router['type']['name']}"
1711
+ end
1712
+ println reset
1713
+ rescue RestClient::Exception => e
1714
+ print_rest_exception(e, options)
1715
+ return 1
1716
+ end
1717
+ end
1718
+
1719
+ def add_nat(args)
1720
+ options = {:options=>{}}
1721
+ params = {}
1722
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
1723
+ opts.banner = subcommand_usage("[router] [name]")
1724
+ opts.on('-n', '--name VALUE', String, "Name for this NAT") do |val|
1725
+ params['name'] = val
1726
+ end
1727
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
1728
+ opts.footer = "Create a network router NAT."
1729
+ end
1730
+ optparse.parse!(args)
1731
+ connect(options)
1732
+ if args.count < 1 || args.count > 2
1733
+ print_error MtnCloud::Terminal.angry_prompt
1734
+ puts_error "wrong number of arguments, expected 1-2 and got (#{args.count}) #{args.inspect}\n#{optparse}"
1735
+ return 1
1736
+ end
1737
+ if args.count > 1
1738
+ params['name'] = args[1]
1739
+ end
1740
+ begin
1741
+ router = find_router(args[0])
1742
+
1743
+ if router.nil?
1744
+ return 1
1745
+ end
1746
+
1747
+ if !router['type']['hasNat']
1748
+ print_red_alert "NATs not supported for #{router['type']['name']}"
1749
+ return 1
1750
+ end
1751
+
1752
+ if options[:payload]
1753
+ payload = options[:payload]
1754
+ else
1755
+ params['name'] ||= MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'name', 'type' => 'text', 'fieldLabel' => 'Name', 'required' => true}], options[:options], @api_client, params)['name']
1756
+
1757
+ option_types = router['type']['natOptionTypes'].reject {|it| ['name'].include?(it['fieldName'])}.sort {|it| it['displayOrder']}
1758
+
1759
+ # prompt options
1760
+ option_result = MtnCloud::Cli::OptionTypes.prompt(option_types, options[:options].deep_merge({:context_map => {'nat' => ''}}), @api_client, {'networkServer' => {'id' => router['networkServer']['id']}}, nil, true)
1761
+ payload = {'networkRouterNAT' => params.deep_merge(option_result)}
1762
+ end
1763
+
1764
+ @network_routers_interface.setopts(options)
1765
+ if options[:dry_run]
1766
+ print_dry_run @network_routers_interface.dry.create_nat(router['id'], payload)
1767
+ return
1768
+ end
1769
+
1770
+ json_response = @network_routers_interface.create_nat(router['id'], payload)
1771
+
1772
+ if options[:json]
1773
+ print JSON.pretty_generate(json_response), "\n"
1774
+ return
1775
+ end
1776
+ print_green_success "\nAdded Network Router NAT #{payload['networkRouterNAT']['name']}\n"
1777
+ _nats(router['id'], options)
1778
+ rescue RestClient::Exception => e
1779
+ print_rest_exception(e, options)
1780
+ exit 1
1781
+ end
1782
+ end
1783
+
1784
+ def update_nat(args)
1785
+ options = {:options=>{}}
1786
+ params = {}
1787
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
1788
+ opts.banner = subcommand_usage("[router] [NAT]")
1789
+ opts.on('-n', '--name VALUE', String, "Name for this NAT") do |val|
1790
+ params['name'] = val
1791
+ end
1792
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
1793
+ opts.footer = "Update a network router NAT.\n" +
1794
+ "[router] is required. This is the name or id of an existing network router.\n" +
1795
+ "[NAT] is required. This is the name or id of an existing network router NAT."
1796
+ end
1797
+ optparse.parse!(args)
1798
+ if args.count != 2
1799
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
1800
+ end
1801
+ connect(options)
1802
+ begin
1803
+ router = find_router(args[0])
1804
+
1805
+ if router.nil?
1806
+ return 1
1807
+ end
1808
+
1809
+ if !router['type']['hasNat']
1810
+ print_red_alert "NATs not supported for #{router['type']['name']}"
1811
+ return 1
1812
+ end
1813
+
1814
+ nat = router['firewall'] && router['nats'] ? router['nats'].find {|it| it['name'] == args[1] || it['id'] == args[1].to_i} : nil
1815
+
1816
+ if !nat
1817
+ print_red_alert "NAT #{args[1]} not found for router #{router['name']}"
1818
+ exit 1
1819
+ end
1820
+
1821
+ payload = parse_payload(options) || {'networkRouterNAT' => params}
1822
+ payload['networkRouterNAT'].deep_merge!(options[:options].reject {|k,v| k.is_a?(Symbol) }) if options[:options] && !payload['networkRouterNAT'].nil?
1823
+
1824
+ if payload['networkRouterNAT'].empty?
1825
+ print_green_success "Nothing to update"
1826
+ exit 1
1827
+ end
1828
+
1829
+ @network_routers_interface.setopts(options)
1830
+ if options[:dry_run]
1831
+ print_dry_run @network_routers_interface.dry.update_nat(router['id'], nat['id'], payload)
1832
+ return
1833
+ end
1834
+
1835
+ json_response = @network_routers_interface.update_nat(router['id'], nat['id'], payload)
1836
+
1837
+ if options[:json]
1838
+ print JSON.pretty_generate(json_response), "\n"
1839
+ return
1840
+ end
1841
+ print_green_success "\nUpdated Network Router NAT #{nat['name']}\n"
1842
+ _nats(router['id'], options)
1843
+ rescue RestClient::Exception => e
1844
+ print_rest_exception(e, options)
1845
+ exit 1
1846
+ end
1847
+ end
1848
+
1849
+ def remove_nat(args)
1850
+ options = {}
1851
+ query_params = {}
1852
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1853
+ opts.banner = subcommand_usage("[router] [NAT]")
1854
+ build_common_options(opts, options, [:auto_confirm, :json, :dry_run, :quiet, :remote])
1855
+ opts.footer = "Delete a network router NAT.\n" +
1856
+ "[router] is required. This is the name or id of an existing network router."
1857
+ "[NAT] is required. This is the name or id of an existing network router NAT."
1858
+ end
1859
+ optparse.parse!(args)
1860
+ if args.count != 2
1861
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
1862
+ end
1863
+ connect(options)
1864
+
1865
+ begin
1866
+ router = find_router(args[0])
1867
+ return if !router
1868
+
1869
+ if !router['type']['hasNat']
1870
+ print_red_alert "NATs not supported for #{router['type']['name']}"
1871
+ return 1
1872
+ end
1873
+
1874
+ nat = router['nats'] ? router['nats'].find {|it| it['name'] == args[1] || it['id'] == args[1].to_i} : nil
1875
+
1876
+ if !nat
1877
+ print_red_alert "NAT #{args[1]} not found for router #{router['name']}"
1878
+ exit 1
1879
+ end
1880
+
1881
+ unless options[:yes] || ::MtnCloud::Cli::OptionTypes::confirm("Are you sure you would like to remove the NAT '#{nat['name']}' from router '#{router['name']}'?", options)
1882
+ return 9, "aborted command"
1883
+ end
1884
+ @network_routers_interface.setopts(options)
1885
+ if options[:dry_run]
1886
+ print_dry_run @network_routers_interface.dry.destroy_nat(router['id'], nat['id'])
1887
+ return
1888
+ end
1889
+ json_response = @network_routers_interface.destroy_nat(router['id'], nat['id'])
1890
+ if options[:json]
1891
+ print JSON.pretty_generate(json_response)
1892
+ print "\n"
1893
+ elsif !options[:quiet]
1894
+ print_green_success "\nNAT #{nat['name']} for router #{router['name']} is being removed...\n"
1895
+ _nats(router['id'], options)
1896
+ end
1897
+ rescue RestClient::Exception => e
1898
+ print_rest_exception(e, options)
1899
+ exit 1
1900
+ end
1901
+ end
1902
+
1903
+ def bgp_neighbors(args)
1904
+ options = {}
1905
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1906
+ opts.banner = subcommand_usage("[router]")
1907
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
1908
+ opts.footer = "List network router BGP neighbors." + "\n" +
1909
+ "[router] is required. This is the name or id of a network router."
1910
+ end
1911
+
1912
+ optparse.parse!(args)
1913
+ connect(options)
1914
+
1915
+ if args.count < 1
1916
+ puts optparse
1917
+ return 1
1918
+ end
1919
+ _bgp_neighbors(args[0], options)
1920
+ end
1921
+
1922
+ def _bgp_neighbors(router_id, options)
1923
+ @network_routers_interface.setopts(options)
1924
+ if options[:dry_run]
1925
+ if args[0].to_s =~ /\A\d{1,}\Z/
1926
+ print_dry_run @network_routers_interface.dry.get(router_id.to_i)
1927
+ else
1928
+ print_dry_run @network_routers_interface.dry.list({name:router_id})
1929
+ end
1930
+ return
1931
+ end
1932
+ router = find_router(router_id)
1933
+ if router.nil?
1934
+ return 1
1935
+ end
1936
+
1937
+ if router['type']['hasBgp']
1938
+ json_response = {'networkRouterBgpNeighbors' => router['bgpNeighbors']}
1939
+ render_response(json_response, options, 'networkRouterBgpNeighbor') do
1940
+ print_h1 "Network Router BGP Neighbors For: #{router['name']}"
1941
+ print cyan
1942
+ print_bgp_neighbors(router)
1943
+ end
1944
+ else
1945
+ print_red_alert "BGP not supported for #{router['type']['name']}"
1946
+ end
1947
+ print reset
1948
+ end
1949
+
1950
+ def bgp_neighbor(args)
1951
+ options = {}
1952
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
1953
+ opts.banner = subcommand_usage("[router] [BGP neighbor]")
1954
+ build_common_options(opts, options, [:json, :yaml, :csv, :fields, :dry_run, :remote])
1955
+ opts.footer = "Display details on network router BGP neighbor." + "\n" +
1956
+ "[router] is required. This is the name or id of a network router.\n" +
1957
+ "[BGP neighbor] is required. This is the id of a BGP neighbor.\n"
1958
+ end
1959
+
1960
+ optparse.parse!(args)
1961
+ connect(options)
1962
+
1963
+ if args.count < 2
1964
+ puts optparse
1965
+ return 1
1966
+ end
1967
+
1968
+ @network_routers_interface.setopts(options)
1969
+ if options[:dry_run]
1970
+ if args[0].to_s =~ /\A\d{1,}\Z/
1971
+ print_dry_run @network_routers_interface.dry.get(args[0].to_i)
1972
+ else
1973
+ print_dry_run @network_routers_interface.dry.list({name:args[0]})
1974
+ end
1975
+ return
1976
+ end
1977
+ router = find_router(args[0])
1978
+ if router.nil?
1979
+ return 1
1980
+ end
1981
+
1982
+ if router['type']['hasBgp']
1983
+ bgp_neighbor = (router['bgpNeighbors'] || []).find {|it| it['id'] == args[1].to_i}
1984
+
1985
+ if bgp_neighbor
1986
+ json_response = {'networkRouterBgpNeighbor' => bgp_neighbor}
1987
+ render_response(json_response, options, 'networkRouterBgpNeighbor') do
1988
+ print_h1 "Network Router BGP Neighbor Details"
1989
+ print cyan
1990
+
1991
+ description_cols = {
1992
+ "ID" => lambda {|it| it['id']}
1993
+ }
1994
+
1995
+ router['type']['bgpNeighborOptionTypes'].sort_by {|it| it['displayOrder']}.each do |option_type|
1996
+ description_cols[option_type['fieldLabel']] = lambda {|it| MtnCloud::Cli::OptionTypes.get_option_value(it, option_type, true)}
1997
+ end
1998
+ print_description_list(description_cols, bgp_neighbor)
1999
+ end
2000
+ else
2001
+ print_red_alert "BGP Neighbors #{args[1]} not found for router #{router['name']}"
2002
+ end
2003
+ else
2004
+ print_red_alert "BGP Neighbors not supported for #{router['type']['name']}"
2005
+ end
2006
+ println reset
2007
+ end
2008
+
2009
+ def add_bgp_neighbor(args)
2010
+ options = {:options=>{}}
2011
+ params = {}
2012
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
2013
+ opts.banner = subcommand_usage("[router]")
2014
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
2015
+ opts.footer = "Create a network router BGP neighbor."
2016
+ end
2017
+ optparse.parse!(args)
2018
+ connect(options)
2019
+ if args.count < 1
2020
+ print_error MtnCloud::Terminal.angry_prompt
2021
+ puts_error "wrong number of arguments, expected 1 and got (#{args.count}) #{args.inspect}\n#{optparse}"
2022
+ return 1
2023
+ end
2024
+
2025
+ router = find_router(args[0])
2026
+
2027
+ if router.nil?
2028
+ return 1
2029
+ end
2030
+
2031
+ if !router['type']['hasNat']
2032
+ print_red_alert "BGP not supported for #{router['type']['name']}"
2033
+ return 1
2034
+ end
2035
+
2036
+ if options[:payload]
2037
+ payload = options[:payload]
2038
+ else
2039
+ option_types = router['type']['bgpNeighborOptionTypes'].sort_by {|it| it['displayOrder']}
2040
+
2041
+ # prompt options
2042
+ option_result = MtnCloud::Cli::OptionTypes.prompt(option_types, options[:options].deep_merge({:context_map => {'bgpNeighbor' => ''}}), @api_client, {'networkRouterId' => router['id']}, nil, true)
2043
+ payload = {'networkRouterBgpNeighbor' => params.deep_merge(option_result)}
2044
+ end
2045
+
2046
+ @network_routers_interface.setopts(options)
2047
+ if options[:dry_run]
2048
+ print_dry_run @network_routers_interface.dry.create_bgp_neighbor(router['id'], payload)
2049
+ return
2050
+ end
2051
+
2052
+ json_response = @network_routers_interface.create_bgp_neighbor(router['id'], payload)
2053
+ render_response(json_response, options, 'networkRouterBgpNeighbor') do
2054
+ print_green_success "\nAdded Network Router BGP neighbor #{json_response['id']}\n"
2055
+ _bgp_neighbors(router['id'], options)
2056
+ end
2057
+ end
2058
+
2059
+ def update_bgp_neighbor(args)
2060
+ options = {:options=>{}}
2061
+ params = {}
2062
+ optparse = MtnCloud::Cli::OptionParser.new do|opts|
2063
+ opts.banner = subcommand_usage("[router] [BGP neighbor]")
2064
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
2065
+ opts.footer = "Update a network router BGP neighbor.\n" +
2066
+ "[router] is required. This is the name or id of an existing network router.\n" +
2067
+ "[BGP neighbor] is required. This is the id of an existing network router BGP neighbor."
2068
+ end
2069
+ optparse.parse!(args)
2070
+ if args.count != 2
2071
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
2072
+ end
2073
+ connect(options)
2074
+
2075
+ router = find_router(args[0])
2076
+
2077
+ if router.nil?
2078
+ return 1
2079
+ end
2080
+
2081
+ if !router['type']['hasBgp']
2082
+ print_red_alert "BGP not supported for #{router['type']['name']}"
2083
+ return 1
2084
+ end
2085
+
2086
+ bgp_neighbor = router['bgpNeighbors'] ? router['bgpNeighbors'].find {|it| it['id'] == args[1].to_i} : nil
2087
+
2088
+ if !bgp_neighbor
2089
+ print_red_alert "BGP neighbor #{args[1]} not found for router #{router['name']}"
2090
+ exit 1
2091
+ end
2092
+
2093
+ payload = parse_payload(options) || {'networkRouterBgpNeighbor' => params}
2094
+ payload['networkRouterBgpNeighbor'].deep_merge!(options[:options].reject {|k,v| k.is_a?(Symbol) }) if options[:options] && !payload['networkRouterBgpNeighbor'].nil?
2095
+
2096
+ if payload['networkRouterBgpNeighbor'].empty?
2097
+ option_types = router['type']['bgpNeighborOptionTypes'].sort_by {|it| it['displayOrder']}
2098
+ print_green_success "Nothing to update"
2099
+ println cyan
2100
+ print MtnCloud::Cli::OptionTypes.display_option_types_help(
2101
+ option_types,
2102
+ {:include_context => true, :context_map => {'bgpNeighbor' => ''}, :color => cyan, :title => "Available BGP Neighbor Options"}
2103
+ )
2104
+ exit 1
2105
+ end
2106
+
2107
+ @network_routers_interface.setopts(options)
2108
+ if options[:dry_run]
2109
+ print_dry_run @network_routers_interface.dry.update_bgp_neighbor(router['id'], bgp_neighbor['id'], payload)
2110
+ return
2111
+ end
2112
+
2113
+ json_response = @network_routers_interface.update_bgp_neighbor(router['id'], bgp_neighbor['id'], payload)
2114
+ render_response(json_response, options, 'networkRouterBgpNeighbor') do
2115
+ print_green_success "\nUpdated Network Router BGP Neighbor #{bgp_neighbor['id']}\n"
2116
+ _bgp_neighbors(router['id'], options)
2117
+ end
2118
+ end
2119
+
2120
+ def remove_bgp_neighbor(args)
2121
+ options = {}
2122
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
2123
+ opts.banner = subcommand_usage("[router] [BGP neighbor]")
2124
+ build_common_options(opts, options, [:auto_confirm, :json, :dry_run, :quiet, :remote])
2125
+ opts.footer = "Delete a network router BGP neighbor.\n" +
2126
+ "[router] is required. This is the name or id of an existing network router."
2127
+ "[BGP neighbor] is required. This is the id of an existing network router BGP neighbor."
2128
+ end
2129
+ optparse.parse!(args)
2130
+ if args.count != 2
2131
+ raise_command_error "wrong number of arguments, expected 2 and got (#{args.count}) #{args}\n#{optparse}"
2132
+ end
2133
+ connect(options)
2134
+
2135
+ router = find_router(args[0])
2136
+ return if !router
2137
+
2138
+ if !router['type']['hasBgp']
2139
+ print_red_alert "BGP not supported for #{router['type']['name']}"
2140
+ return 1
2141
+ end
2142
+
2143
+ bgp_neighbor = router['bgpNeighbors'] ? router['bgpNeighbors'].find {|it| it['id'] == args[1].to_i} : nil
2144
+
2145
+ if !bgp_neighbor
2146
+ print_red_alert "BGP neighbor #{args[1]} not found for router #{router['name']}"
2147
+ exit 1
2148
+ end
2149
+
2150
+ unless options[:yes] || ::MtnCloud::Cli::OptionTypes::confirm("Are you sure you would like to remove the BGP neighbor '#{bgp_neighbor['id']}' from router '#{router['name']}'?", options)
2151
+ return 9, "aborted command"
2152
+ end
2153
+ @network_routers_interface.setopts(options)
2154
+ if options[:dry_run]
2155
+ print_dry_run @network_routers_interface.dry.destroy_bgp_neighbor(router['id'], bgp_neighbor['id'])
2156
+ return
2157
+ end
2158
+ json_response = @network_routers_interface.destroy_bgp_neighbor(router['id'], bgp_neighbor['id'])
2159
+ render_response(json_response, options, 'networkRouterBgpNeighbor') do
2160
+ print_green_success "\nDeleted Network Router BGP Neighbor #{bgp_neighbor['id']}\n"
2161
+ _bgp_neighbors(router['id'], options)
2162
+ end
2163
+ end
2164
+
2165
+ def types(args)
2166
+ options = {}
2167
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
2168
+ opts.banner = subcommand_usage()
2169
+ build_common_options(opts, options, [:json, :dry_run, :remote])
2170
+ opts.footer = "List network router types."
2171
+ end
2172
+ optparse.parse!(args)
2173
+ connect(options)
2174
+ begin
2175
+ params = {}
2176
+ params.merge!(parse_list_options(options))
2177
+
2178
+ @network_routers_interface.setopts(options)
2179
+ if options[:dry_run]
2180
+ print_dry_run @network_routers_interface.dry.types(params)
2181
+ return
2182
+ end
2183
+
2184
+ json_response = @network_routers_interface.types(params)
2185
+
2186
+ if options[:json]
2187
+ print JSON.pretty_generate(json_response)
2188
+ print "\n"
2189
+ return
2190
+ end
2191
+
2192
+ title = "Network Router Types"
2193
+ subtitles = []
2194
+ subtitles += parse_list_subtitles(options)
2195
+ print_h1 title, subtitles
2196
+
2197
+ router_types = json_response['networkRouterTypes']
2198
+
2199
+ if router_types.empty?
2200
+ println yellow,"No network router types found.",reset
2201
+ else
2202
+ print as_pretty_table(router_types, {'ID' => 'id', 'NAME' => 'name'}, options)
2203
+ end
2204
+ println reset
2205
+ return 0
2206
+ rescue RestClient::Exception => e
2207
+ print_rest_exception(e, options)
2208
+ exit 1
2209
+ end
2210
+ end
2211
+
2212
+ def type(args)
2213
+ options = {}
2214
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
2215
+ opts.banner = subcommand_usage("[type]")
2216
+ opts.on('-t', '--type VALUE', String, "Name or ID of router type") do |val|
2217
+ options[:options]['routerType'] = val
2218
+ end
2219
+ build_common_options(opts, options, [:list, :json, :dry_run, :remote])
2220
+ opts.footer = "Display network router type details."
2221
+ end
2222
+ optparse.parse!(args)
2223
+
2224
+ if args.count > 1
2225
+ print_error MtnCloud::Terminal.angry_prompt
2226
+ puts_error "wrong number of arguments, expected 0-1 and got (#{args.count}) #{args.inspect}\n#{optparse}"
2227
+ return 1
2228
+ end
2229
+
2230
+ if args.count > 0
2231
+ options[:options]['routerType'] = args[0]
2232
+ end
2233
+
2234
+ begin
2235
+ connect(options)
2236
+ @network_routers_interface.setopts(options)
2237
+ if options[:dry_run]
2238
+ print_dry_run @network_routers_interface.dry.types(params)
2239
+ return
2240
+ end
2241
+
2242
+ router_type = prompt_router_type(options)
2243
+
2244
+ if options[:json]
2245
+ print JSON.pretty_generate({'networkRouterType' => router_type})
2246
+ print "\n"
2247
+ return
2248
+ end
2249
+
2250
+ print_h1 "Network Router Type Details For: #{router_type['name']}"
2251
+ print cyan
2252
+
2253
+ description_cols = {
2254
+ "ID" => lambda {|it| it['id'] },
2255
+ "Name" => lambda {|it| it['name'] },
2256
+ "Code" => lambda {|it| it['code'] },
2257
+ "Enabled" => lambda {|it| format_boolean(it['enabled'])},
2258
+ "Creatable" => lambda {|it| format_boolean(it['creatable'])},
2259
+ "Selectable" => lambda {|it| format_boolean(it['selectable'])},
2260
+ "Firewall" => lambda {|it| format_boolean(it['hasFirewall'])},
2261
+ "DHCP" => lambda {|it| format_boolean(it['hasDhcp'])},
2262
+ "Routing" => lambda {|it| format_boolean(it['hasRouting'])},
2263
+ "Network Server" => lambda {|it| format_boolean(it['hasNetworkServer'])}
2264
+ }
2265
+ print_description_list(description_cols, router_type)
2266
+
2267
+ {'optionTypes' => 'Router', 'ruleOptionTypes' => 'Firewall Rule', 'ruleGroupOptionTypes' => 'Firewall Rule Group', 'natOptionTypes' => 'NAT', 'bgpNeighborOptionTypes' => 'BGP Neighbor'}.each_pair do |field, title|
2268
+ if !router_type[field].nil? && router_type[field].count > 0
2269
+ println cyan
2270
+ print MtnCloud::Cli::OptionTypes.display_option_types_help(
2271
+ router_type[field].reject {|it| ['enabled'].include?(it['fieldName'])},
2272
+ {:include_context => true, :context_map => {'networkRouter' => ''}, :color => cyan, :title => "Available #{title} Options"}
2273
+ )
2274
+ end
2275
+ end
2276
+ print reset
2277
+ return 0
2278
+ rescue RestClient::Exception => e
2279
+ print_rest_exception(e, options)
2280
+ exit 1
2281
+ end
2282
+ end
2283
+
2284
+ def update_permissions(args)
2285
+ options = {}
2286
+ optparse = MtnCloud::Cli::OptionParser.new do |opts|
2287
+ opts.banner = subcommand_usage( "[router]")
2288
+ add_perms_options(opts, options, ['plans', 'groups'])
2289
+ build_common_options(opts, options, [:options, :payload, :json, :dry_run, :remote])
2290
+ opts.footer = "Update a network router permissions.\n" +
2291
+ "[router] is required. This is the name or id of an existing network router."
2292
+ end
2293
+
2294
+ optparse.parse!(args)
2295
+ if args.count != 1
2296
+ raise_command_error "wrong number of arguments, expected 1 and got (#{args.count}) #{args}\n#{optparse}"
2297
+ end
2298
+ connect(options)
2299
+
2300
+ begin
2301
+ if !is_master_account
2302
+ print_red_alert "Permissions only available for master tenant"
2303
+ return 1
2304
+ end
2305
+
2306
+ router = find_router(args[0])
2307
+ return 1 if router.nil?
2308
+
2309
+ if options[:payload]
2310
+ payload = options[:payload]
2311
+ # support -O OPTION switch on top of --payload
2312
+ if options[:options]
2313
+ payload['permissions'] ||= {}
2314
+ payload['permissions'].deep_merge!(options[:options].reject {|k,v| k.is_a?(Symbol) })
2315
+ end
2316
+ else
2317
+ perms = {}
2318
+ if !options[:visibility].nil?
2319
+ perms['visibility'] = options[:visibility]
2320
+ end
2321
+ if !options[:tenants].nil?
2322
+ perms['tenantPermissions'] = {'accounts' => options[:tenants].collect {|id| id.to_i}}
2323
+ end
2324
+ payload = {'permissions' => perms}
2325
+ end
2326
+
2327
+ @network_routers_interface.setopts(options)
2328
+ if options[:dry_run]
2329
+ print_dry_run @network_routers_interface.dry.update_permissions(router['id'], payload)
2330
+ return
2331
+ end
2332
+ json_response = @network_routers_interface.update_permissions(router['id'], payload)
2333
+ if options[:json]
2334
+ print JSON.pretty_generate(json_response)
2335
+ print "\n"
2336
+ elsif json_response['success']
2337
+ print_green_success "\nUpdated Network Router Permissions\n"
2338
+ else
2339
+ print_rest_errors(json_response, options)
2340
+ end
2341
+ end
2342
+ end
2343
+
2344
+ private
2345
+
2346
+ def print_firewall(router, options = {}) #details=false, rules_only=false, rule_groups_only=false)
2347
+ if router['type']['hasFirewall']
2348
+ if router['firewall']
2349
+ if options[:details]
2350
+ description_cols = {
2351
+ "Network Router" => lambda {|it| it['name'] },
2352
+ "Enabled" => lambda {|it| format_boolean(it['firewall']['enabled'])},
2353
+ "Version" => lambda {|it| it['firewall']['version']},
2354
+ "Default Policy" => lambda {|it| (router['firewall']['defaultPolicy'] || {})['action']}
2355
+ }
2356
+ (router['firewall']['global'] || {}).each do |k,v|
2357
+ description_cols[k.gsub(/[A-Z]/, ' \0').downcase] = lambda {|it| it['firewall']['global'][k]}
2358
+ end
2359
+
2360
+ print_description_list(description_cols, router)
2361
+
2362
+ _firewall_rule_groups(router, options) if router['type']['hasFirewallGroups']
2363
+ _firewall_rules(router, options) if router['type']['hasFirewall']
2364
+ else
2365
+ print "Enabled: #{format_boolean(router['firewall']['enabled'])}".center(20)
2366
+ print "Version: #{router['firewall']['version']}".center(20)
2367
+ print "Default Policy: #{(router['firewall']['defaultPolicy'] || {})['action']}".center(20)
2368
+ println
2369
+ end
2370
+ else
2371
+ println "Enabled: #{format_boolean(false)}".center(20)
2372
+ end
2373
+ end
2374
+ end
2375
+
2376
+ def print_dhcp(router, details=false)
2377
+ if router['type']['hasDhcp']
2378
+ if router['dhcp']
2379
+ if details
2380
+ description_cols = {
2381
+ "Network Router" => lambda {|it| it['name'] },
2382
+ "Enabled" => lambda {|it| format_boolean(it['dhcp']['enabled'])},
2383
+ "Version" => lambda {|it| it['dhcp']['version']},
2384
+ "Feature" => lambda {|it| it['dhcp']['featureType']},
2385
+ "Logs Enabled" => lambda {|it| format_boolean((it['dhcp']['logging'] || {})['enable'])},
2386
+ "Log Level" => lambda {|it| (it['dhcp']['logging'] || {})['logLevel']}
2387
+ }
2388
+
2389
+ print_description_list(description_cols, router)
2390
+
2391
+ print_h2 "IP Pools"
2392
+ print cyan
2393
+
2394
+ if (router['dhcp']['ipPools'] || []).count > 0
2395
+ rows = router['dhcp']['ipPools'].collect do |it|
2396
+ {
2397
+ ip_range: it['ipRange'],
2398
+ gateway: it['defaultGateway'],
2399
+ subnet: it['subnetMask'],
2400
+ dns: it['primaryNameServer'],
2401
+ domain: it['domainName']
2402
+ }
2403
+ end
2404
+ puts as_pretty_table(rows, [:ip_range, :gateway, :subnet, :dns, :domain])
2405
+ else
2406
+ println "No IP pools"
2407
+ end
2408
+ else
2409
+ print "Enabled: #{format_boolean(router['dhcp']['enabled'])}".center(20)
2410
+ print "Version: #{router['dhcp']['version']}".center(20)
2411
+ print "Feature: #{router['dhcp']['version']}".center(20)
2412
+ print "Logs Enabled: #{(format_boolean((router['dhcp']['logging'] || {})['enable']))}".center(20)
2413
+ print "Log Level: #{(router['dhcp']['logging'] || {})['logLevel']}".center(20)
2414
+ println
2415
+ end
2416
+ else
2417
+ print "Enabled: #{format_boolean(false)}".center(20)
2418
+ print "Logs Enabled: #{format_boolean(false)}".center(20)
2419
+ println
2420
+ end
2421
+ end
2422
+ end
2423
+
2424
+ def print_routes(router)
2425
+ if router['type']['hasRouting']
2426
+ if router['routes'].count > 0
2427
+ rows = router['routes'].collect do |it|
2428
+ {
2429
+ id: it['id'],
2430
+ name: it['name'],
2431
+ network: it['source'],
2432
+ next_hop: it['destination'],
2433
+ interface: it['externalInterface'],
2434
+ default_route: format_boolean(it['defaultRoute']),
2435
+ mtu: it['networkMtu']
2436
+ }
2437
+ end
2438
+ puts as_pretty_table(rows, [:id, :name, :network, :next_hop, :interface, :default_route, :mtu])
2439
+ else
2440
+ println "No routes\n"
2441
+ end
2442
+ end
2443
+ end
2444
+
2445
+ def print_nats(router)
2446
+ if router['type']['hasNat']
2447
+ if router['nats'].count > 0
2448
+ rows = router['nats'].collect do |it|
2449
+ {
2450
+ id: it['id'],
2451
+ name: it['name'],
2452
+ description: it['description'],
2453
+ source_network: it['sourceNetwork'],
2454
+ destination_network: it['destinationNetwork'],
2455
+ translated_network: it['translatedNetwork']
2456
+ }
2457
+ end
2458
+ puts as_pretty_table(rows, [:id, :name, :description, :source_network, :destination_network, :translated_network])
2459
+ else
2460
+ println "No NATs\n"
2461
+ end
2462
+ end
2463
+ end
2464
+
2465
+ def print_bgp_neighbors(router)
2466
+ if router['type']['hasBgp']
2467
+ if router['bgpNeighbors'].count > 0
2468
+ rows = router['bgpNeighbors'].sort_by {|it| it['id']}.collect do |it|
2469
+ {
2470
+ id: it['id'],
2471
+ ip_address: it['ipAddress'],
2472
+ bfd_enabled: it['bfdEnabled'],
2473
+ remote_as: it['remoteAs'],
2474
+ route_filtering_out: it['routeFilteringOut'],
2475
+ route_filtering_in: it['routeFilteringIn'],
2476
+ allow_as_in: it['allowAsIn']
2477
+ }
2478
+ end
2479
+ puts as_pretty_table(rows, [:id, :ip_address, :bfd_enabled, :remote_as, :route_filtering_out, :route_filtering_in, :allow_as_in])
2480
+ else
2481
+ println "No BGP Neighbors\n"
2482
+ end
2483
+ end
2484
+ end
2485
+
2486
+ def format_router_status(router, return_color = cyan)
2487
+ status = router['status']
2488
+ color = white
2489
+ color = green if status == 'ok'
2490
+ color = yellow if status == 'warning'
2491
+ color = red if status == 'error'
2492
+ "#{color}#{status.upcase}#{return_color}"
2493
+ end
2494
+
2495
+ def router_integration_label(router)
2496
+ integration = router['networkServer']['integration'] || {}
2497
+ integration['integrationType'] ? integration['integrationType']['name'] : router['zone']['name']
2498
+ end
2499
+
2500
+ def find_router(val)
2501
+ if val.to_s =~ /\A\d{1,}\Z/
2502
+ return find_router_by_id(val)
2503
+ else
2504
+ if router = find_router_by_name(val)
2505
+ return find_router_by_id(router['id'])
2506
+ end
2507
+ end
2508
+ end
2509
+
2510
+ def find_router_by_id(id)
2511
+ begin
2512
+ json_response = @network_routers_interface.get(id.to_i)
2513
+ return json_response['networkRouter']
2514
+ rescue RestClient::Exception => e
2515
+ if e.response && e.response.code == 404
2516
+ print_red_alert "Network Router not found by id #{id}"
2517
+ return nil
2518
+ else
2519
+ raise e
2520
+ end
2521
+ end
2522
+ end
2523
+
2524
+ def find_router_by_name(name)
2525
+ json_response = @network_routers_interface.list({phrase: name.to_s})
2526
+ routers = json_response['networkRouters']
2527
+ if routers.empty?
2528
+ print_red_alert "Network Router not found by name #{name}"
2529
+ return nil
2530
+ elsif routers.size > 1
2531
+ print_red_alert "#{routers.size} network routers found by name #{name}"
2532
+ rows = routers.collect do |it|
2533
+ {id: it['id'], name: it['name']}
2534
+ end
2535
+ puts as_pretty_table(rows, [:id, :name], {color:red})
2536
+ return nil
2537
+ else
2538
+ return routers[0]
2539
+ end
2540
+ end
2541
+
2542
+ def find_router_type(val)
2543
+ types = @network_routers_interface.types()['networkRouterTypes']
2544
+ (val.to_s =~ /\A\d{1,}\Z/) ? types.find {|it| it['id'].to_i == val.to_i} : types.find {|it| it['name'] == val}
2545
+ end
2546
+
2547
+ def prompt_router_type(options)
2548
+ if options[:options]['routerType']
2549
+ router_type = find_router_type(options[:options]['routerType'])
2550
+ if router_type.nil?
2551
+ print_red_alert "Network router type #{options[:options]['routerType']} not found"
2552
+ exit 1
2553
+ end
2554
+ else
2555
+ router_types = @network_routers_interface.types()['networkRouterTypes']
2556
+ router_type_id = MtnCloud::Cli::OptionTypes.prompt([{'fieldName' => 'routerType', 'type' => 'select', 'fieldLabel' => 'Network Router Type', 'required' => true, 'selectOptions' => router_types.collect {|it| {'name' => it['name'], 'value' => it['id']}}}], options[:options], @api_client,{}, nil, true)['routerType']
2557
+ router_type = router_types.find {|type| type['id'] == router_type_id}
2558
+ end
2559
+ router_type
2560
+ end
2561
+
2562
+ def available_groups()
2563
+ @network_routers_interface.groups
2564
+ end
2565
+
2566
+ def find_firewall_rule(router, rule_id)
2567
+ rule = nil
2568
+ if router['type']['hasFirewallGroups']
2569
+ if router['firewall'] && router['firewall']['ruleGroups']
2570
+ router['firewall']['ruleGroups'].each do |group|
2571
+ if !rule && group['rules']
2572
+ if rule = group['rules'].find { |it| it['name'] == rule_id || it['id'] == rule_id.to_i }
2573
+ rule['groupId'] = group['id']
2574
+ end
2575
+ end
2576
+ end
2577
+ end
2578
+ else
2579
+ rule = router['firewall'] && router['firewall']['rules'] ? router['firewall']['rules'].find {|it| it['name'] == rule_id || it['id'] == rule_id.to_i} : nil
2580
+ end
2581
+ rule
2582
+ end
2583
+
2584
+ def find_firewall_rule_group(router_id, val)
2585
+ if val.to_s =~ /\A\d{1,}\Z/
2586
+ return find_firewall_rule_group_by_id(router_id, val)
2587
+ else
2588
+ if group = find_firewall_rule_group_by_name(router_id, val)
2589
+ return find_firewall_rule_group_by_id(router_id, group['id'])
2590
+ end
2591
+ end
2592
+ end
2593
+
2594
+ def find_firewall_rule_group_by_id(router_id, group_id)
2595
+ begin
2596
+ json_response = @network_routers_interface.get_firewall_rule_group(router_id, group_id.to_i)
2597
+ return json_response['ruleGroup']
2598
+ rescue RestClient::Exception => e
2599
+ if e.response && e.response.code == 404
2600
+ print_red_alert "Network firewall rule group not found by id #{group_id}"
2601
+ return nil
2602
+ else
2603
+ raise e
2604
+ end
2605
+ end
2606
+ end
2607
+
2608
+ def find_firewall_rule_group_by_name(router_id, name)
2609
+ groups = search_firewall_rule_groups(router_id, name)
2610
+ if groups.empty?
2611
+ print_red_alert "Network firewall rule group not found by name #{name}"
2612
+ return nil
2613
+ elsif groups.size > 1
2614
+ print_red_alert "#{scopes.size} network firewall rule groups found by name #{name}"
2615
+ rows = groups.collect do |it|
2616
+ {id: it['id'], name: it['name']}
2617
+ end
2618
+ puts as_pretty_table(rows, [:id, :name], {color:red})
2619
+ return nil
2620
+ else
2621
+ return groups[0]
2622
+ end
2623
+ end
2624
+
2625
+ def search_firewall_rule_groups(router_id, phrase = nil)
2626
+ @network_routers_interface.list_firewall_rule_groups(router_id, phrase ? {phrase: phrase.to_s} : {})['ruleGroups']
2627
+ end
2628
+ end