rbeapi 0.2.0 → 0.3.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 (57) hide show
  1. data/.gitignore +1 -0
  2. data/CHANGELOG.md +12 -0
  3. data/Gemfile +4 -0
  4. data/README.md +9 -9
  5. data/Rakefile +20 -0
  6. data/lib/rbeapi/api/bgp.rb +770 -0
  7. data/lib/rbeapi/api/dns.rb +32 -31
  8. data/lib/rbeapi/api/interfaces.rb +106 -87
  9. data/lib/rbeapi/api/ipinterfaces.rb +27 -42
  10. data/lib/rbeapi/api/logging.rb +9 -19
  11. data/lib/rbeapi/api/mlag.rb +60 -90
  12. data/lib/rbeapi/api/ntp.rb +12 -17
  13. data/lib/rbeapi/api/ospf.rb +9 -26
  14. data/lib/rbeapi/api/radius.rb +29 -43
  15. data/lib/rbeapi/api/snmp.rb +54 -83
  16. data/lib/rbeapi/api/staticroutes.rb +68 -21
  17. data/lib/rbeapi/api/stp.rb +41 -49
  18. data/lib/rbeapi/api/switchports.rb +41 -68
  19. data/lib/rbeapi/api/system.rb +6 -12
  20. data/lib/rbeapi/api/tacacs.rb +12 -21
  21. data/lib/rbeapi/api/varp.rb +25 -26
  22. data/lib/rbeapi/api/vlans.rb +19 -28
  23. data/lib/rbeapi/api.rb +30 -21
  24. data/lib/rbeapi/client.rb +3 -1
  25. data/lib/rbeapi/version.rb +1 -1
  26. data/rbeapi.spec.tmpl +4 -0
  27. data/spec/spec_helper.rb +8 -0
  28. data/spec/system/api_ospf_interfaces_spec.rb +16 -0
  29. data/spec/system/api_ospf_spec.rb +14 -0
  30. data/spec/system/api_varp_interfaces_spec.rb +16 -0
  31. data/spec/system/rbeapi/api/dns_spec.rb +66 -0
  32. data/spec/system/rbeapi/api/interfaces_base_spec.rb +4 -4
  33. data/spec/system/rbeapi/api/interfaces_ethernet_spec.rb +6 -6
  34. data/spec/system/rbeapi/api/interfaces_portchannel_spec.rb +6 -6
  35. data/spec/system/rbeapi/api/interfaces_vxlan_spec.rb +4 -4
  36. data/spec/system/rbeapi/api/ipinterfaces_spec.rb +44 -0
  37. data/spec/system/rbeapi/api/logging_spec.rb +18 -2
  38. data/spec/system/rbeapi/api/mlag_spec.rb +94 -2
  39. data/spec/system/rbeapi/api/ntp_spec.rb +14 -0
  40. data/spec/system/rbeapi/api/snmp_spec.rb +105 -0
  41. data/spec/system/rbeapi/api/stp_interfaces_spec.rb +43 -6
  42. data/spec/system/rbeapi/api/stp_spec.rb +18 -6
  43. data/spec/system/rbeapi/api/switchports_spec.rb +75 -3
  44. data/spec/system/rbeapi/api/system_spec.rb +16 -0
  45. data/spec/system/rbeapi/api/vlans_spec.rb +28 -0
  46. data/spec/unit/rbeapi/api/bgp/bgp_neighbors_spec.rb +289 -0
  47. data/spec/unit/rbeapi/api/bgp/bgp_spec.rb +192 -0
  48. data/spec/unit/rbeapi/api/bgp/fixture_bgp.text +101 -0
  49. data/spec/unit/rbeapi/api/interfaces/base_spec.rb +7 -13
  50. data/spec/unit/rbeapi/api/interfaces/ethernet_spec.rb +3 -3
  51. data/spec/unit/rbeapi/api/interfaces/portchannel_spec.rb +11 -16
  52. data/spec/unit/rbeapi/api/interfaces/vxlan_spec.rb +15 -21
  53. data/spec/unit/rbeapi/api/mlag/default_spec.rb +13 -19
  54. data/spec/unit/rbeapi/api/staticroutes/default_spec.rb +138 -0
  55. data/spec/unit/rbeapi/api/staticroutes/fixture_staticroutes.text +5 -0
  56. data/spec/unit/rbeapi/api/vlans/default_spec.rb +4 -4
  57. metadata +15 -4
@@ -0,0 +1,770 @@
1
+ #
2
+ # Copyright (c) 2015, Arista Networks, Inc.
3
+ # All rights reserved.
4
+ #
5
+ # Redistribution and use in source and binary forms, with or without
6
+ # modification, are permitted provided that the following conditions are
7
+ # met:
8
+ #
9
+ # Redistributions of source code must retain the above copyright notice,
10
+ # this list of conditions and the following disclaimer.
11
+ #
12
+ # Redistributions in binary form must reproduce the above copyright
13
+ # notice, this list of conditions and the following disclaimer in the
14
+ # documentation and/or other materials provided with the distribution.
15
+ #
16
+ # Neither the name of Arista Networks nor the names of its
17
+ # contributors may be used to endorse or promote products derived from
18
+ # this software without specific prior written permission.
19
+ #
20
+ # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21
+ # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22
+ # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
23
+ # A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL ARISTA NETWORKS
24
+ # BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
25
+ # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
26
+ # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
27
+ # BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
28
+ # WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
29
+ # OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
30
+ # IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31
+ #
32
+ require 'rbeapi/api'
33
+
34
+ ##
35
+ # Eos is the toplevel namespace for working with Arista EOS nodes
36
+ module Rbeapi
37
+ ##
38
+ # Api is module namespace for working with the EOS command API
39
+ module Api
40
+ ##
41
+ # The Bgp class implements global BGP router configuration
42
+ class Bgp < Entity
43
+ attr_reader :neighbors
44
+
45
+ def initialize(node)
46
+ super(node)
47
+ @neighbors = BgpNeighbors.new(node)
48
+ end
49
+
50
+ ##
51
+ # get returns the BGP routing configuration from the nodes current
52
+ # configuration.
53
+ #
54
+ # @return [nil, Hash<Symbol, Object>] Returns the BGP resource as a
55
+ # Hash.
56
+ def get
57
+ config = get_block('^router bgp .*')
58
+ return {} unless config
59
+
60
+ response = Bgp.parse_bgp_as(config)
61
+ response.merge!(parse_router_id(config))
62
+ response.merge!(parse_shutdown(config))
63
+ response.merge!(parse_networks(config))
64
+ response[:neighbors] = @neighbors.getall
65
+ response
66
+ end
67
+
68
+ ##
69
+ # parse_bgp_as scans the BGP routing configuration for the
70
+ # AS number. Defined as a class method. Used by the BgpNeighbors
71
+ # class below.
72
+ #
73
+ # @param [String] :config The switch config.
74
+ #
75
+ # @return [Hash<Symbol, Object>] resource hash attribute
76
+ def self.parse_bgp_as(config)
77
+ value = config.scan(/^router bgp (\d+)/).first
78
+ { bgp_as: value[0] }
79
+ end
80
+
81
+ ##
82
+ # parse_router_id scans the BGP routing configuration for the
83
+ # router ID.
84
+ #
85
+ # @api private
86
+ #
87
+ # @param [String] :config The switch config.
88
+ #
89
+ # @return [Hash<Symbol, Object>] resource hash attribute
90
+ def parse_router_id(config)
91
+ value = config.scan(/router-id ([^\s]+)/).first
92
+ value = value ? value[0] : nil
93
+ { router_id: value }
94
+ end
95
+ private :parse_router_id
96
+
97
+ ##
98
+ # parse_shutdown scans the BGP routing configuration for the
99
+ # shutdown status.
100
+ #
101
+ # @api private
102
+ #
103
+ # @param [String] :config The switch config.
104
+ #
105
+ # @return [Hash<Symbol, Object>] resource hash attribute. Returns
106
+ # true if shutdown, false otherwise.
107
+ def parse_shutdown(config)
108
+ value = config.include?('no shutdown')
109
+ { shutdown: !value }
110
+ end
111
+ private :parse_shutdown
112
+
113
+ ##
114
+ # parse_networks scans the BGP routing configuration for all
115
+ # the network entries.
116
+ #
117
+ # @api private
118
+ #
119
+ # @param [String] :config The switch config.
120
+ #
121
+ # @return [Hash<Symbol, Object>] resource hash attribute
122
+ # @return [Array<Hash>] Single element hash with Array of network hashes
123
+ def parse_networks(config)
124
+ networks = []
125
+ lines = config.scan(%r{network (.+)/(\d+)(?: route-map (\w+))*})
126
+ lines.each do |prefix, mask, rmap|
127
+ rmap = rmap == '' ? nil : rmap
128
+ networks << { prefix: prefix, masklen: mask.to_i, route_map: rmap }
129
+ end
130
+ { networks: networks }
131
+ end
132
+ private :parse_networks
133
+
134
+ ##
135
+ # create will create a new instance of BGP routing on the node.
136
+ #
137
+ # @commands
138
+ # router bgp <bgp_as>
139
+ #
140
+ # @param [String] :bgp_as The BGP autonomous system number to be
141
+ # configured for the local BGP routing instance.
142
+ #
143
+ # @return [Boolean] returns true if the command completed successfully
144
+ def create(bgp_as)
145
+ value = bgp_as
146
+ configure("router bgp #{value}")
147
+ end
148
+
149
+ ##
150
+ # delete will delete the BGP routing instance from the node.
151
+ #
152
+ # @commands
153
+ # no router bgp <bgp_as>
154
+ #
155
+ # @return [Boolean] returns true if the command completed successfully
156
+ def delete
157
+ config = get
158
+ return true unless config
159
+ configure("no router bgp #{config[:bgp_as]}")
160
+ end
161
+
162
+ ##
163
+ # default will configure the BGP routing using the default
164
+ # keyword. This command has the same effect as deleting the BGP
165
+ # routine instance from the nodes running configuration.
166
+ #
167
+ # @commands
168
+ # default router bgp <bgp_as>
169
+ #
170
+ # @return [Boolean] returns true if the command complete successfully
171
+ def default
172
+ config = get
173
+ return true unless config
174
+ configure("default router bgp #{config[:bgp_as]}")
175
+ end
176
+
177
+ ##
178
+ # configure_bgp adds the command to go to BGP config mode.
179
+ # Then it adds the passed in command. The commands are then
180
+ # passed on to configure.
181
+ #
182
+ # @api private
183
+ #
184
+ # @param [String] :cmd Command to run under BGP mode
185
+ #
186
+ # @return [Boolean] returns true if the command complete successfully
187
+ def configure_bgp(cmd)
188
+ config = get_block('^router bgp .*')
189
+ fail 'BGP router is not configured' unless config
190
+ bgp_as = Bgp.parse_bgp_as(config)
191
+ cmds = ["router bgp #{bgp_as[:bgp_as]}", cmd]
192
+ configure(cmds)
193
+ end
194
+ private :configure_bgp
195
+
196
+ ##
197
+ # set_router_id sets the router_id for the BGP routing instance.
198
+ #
199
+ # @commands
200
+ # router bgp <bgp_as>
201
+ # {no | default} router-id <router_id>
202
+ #
203
+ # @param [hash] :opts Optional keyword arguments
204
+ #
205
+ # @option :opts [String] :value The BGP routing process router-id
206
+ # value. When no ID has been specified (i.e. value not set), the
207
+ # local router ID is set to the following:
208
+ # * The loopback IP address when a single loopback interface is
209
+ # configured.
210
+ # * The loopback with the highest IP address when multiple loopback
211
+ # interfaces are configured.
212
+ # * The highest IP address on a physical interface when no loopback
213
+ # interfaces are configure
214
+ #
215
+ # @option :opts [Boolean] :enable If false then the command is
216
+ # negated. Default is true.
217
+ #
218
+ # @option :opts [Boolean] :default Configure the router-id using
219
+ # the default keyword
220
+ #
221
+ # @return [Boolean] returns true if the command complete successfully
222
+ def set_router_id(opts = {})
223
+ configure_bgp(command_builder('router-id', opts))
224
+ end
225
+
226
+ ##
227
+ # set_shutdown configures the administrative state for the global
228
+ # BGP routing process. The value option is not used by this method.
229
+ #
230
+ # @commands
231
+ # router bgp <bgp_as>
232
+ # {no | default} shutdown
233
+ #
234
+ # @param [hash] :opts Optional keyword arguments
235
+ #
236
+ # @option :opts [Boolean] :enable If enable is true then the BGP
237
+ # routing process is administratively enabled and if enable is
238
+ # False then the BGP routing process is administratively
239
+ # disabled.
240
+ #
241
+ # @option :opts [Boolean] :default Configure the router-id using
242
+ # the default keyword
243
+ #
244
+ # @return [Boolean] returns true if the command complete successfully
245
+ def set_shutdown(opts = {})
246
+ fail 'set_shutdown has the value option set' if opts[:value]
247
+ # Shutdown semantics are opposite of enable semantics so invert enable
248
+ value = !opts[:enable]
249
+ opts.merge!(enable: value)
250
+ configure_bgp(command_builder('shutdown', opts))
251
+ end
252
+
253
+ ##
254
+ # add_network creates a new instance of a BGP network on the node.
255
+ #
256
+ # @commands
257
+ # router bgp <bgp_as>
258
+ # network <prefix>/<masklen>
259
+ # route-map <route_map>
260
+ #
261
+ # @param [String] :prefix The IPv4 prefix to configure as part of
262
+ # the network statement. The value must be a valid IPv4 prefix.
263
+ # @param [String] :masklen The IPv4 subnet mask length in bits.
264
+ # The masklen must be in the valid range of 1 to 32.
265
+ # @param [String] :route_map The route-map name to apply to the
266
+ # network statement when configured.
267
+ #
268
+ # @return [Boolean] returns true if the command complete successfully
269
+ def add_network(prefix, masklen, route_map = nil)
270
+ cmd = "network #{prefix}/#{masklen}"
271
+ cmd << " route-map #{route_map}" if route_map
272
+ configure_bgp(cmd)
273
+ end
274
+
275
+ ##
276
+ # remove_network removes the instance of a BGP network on the node.
277
+ #
278
+ # @commands
279
+ # router bgp <bgp_as>
280
+ # {no} shutdown
281
+ #
282
+ # @param [String] :prefix The IPv4 prefix to configure as part of
283
+ # the network statement. The value must be a valid IPv4 prefix.
284
+ # @param [String] :masklen The IPv4 subnet mask length in bits.
285
+ # The masklen must be in the valid range of 1 to 32.
286
+ # @param [String] :route_map The route-map name to apply to the
287
+ # network statement when configured.
288
+ #
289
+ # @return [Boolean] returns true if the command complete successfully
290
+ def remove_network(prefix, masklen, route_map = nil)
291
+ cmd = "no network #{prefix}/#{masklen}"
292
+ cmd << " route-map #{route_map}" if route_map
293
+ configure_bgp(cmd)
294
+ end
295
+ end
296
+
297
+ ##
298
+ # The BgpNeighbors class implements BGP neighbor configuration
299
+ class BgpNeighbors < Entity
300
+ ##
301
+ # get returns a single BGP neighbor entry from the nodes current
302
+ # configuration.
303
+ #
304
+ # @param [String] :name The name of the BGP neighbor to manage.
305
+ # This value can be either an IPv4 address or string (in the
306
+ # case of managing a peer group).
307
+ #
308
+ # @return [nil, Hash<Symbol, Object>] Returns the BGP neighbor
309
+ # resource as a Hash.
310
+ def get(name)
311
+ config = get_block('^router bgp .*')
312
+ return nil unless config
313
+
314
+ response = parse_peer_group(config, name)
315
+ response.merge!(parse_remote_as(config, name))
316
+ response.merge!(parse_send_community(config, name))
317
+ response.merge!(parse_shutdown(config, name))
318
+ response.merge!(parse_description(config, name))
319
+ response.merge!(parse_next_hop_self(config, name))
320
+ response.merge!(parse_route_map_in(config, name))
321
+ response.merge!(parse_route_map_out(config, name))
322
+ response
323
+ end
324
+
325
+ ##
326
+ # getall returns the collection of all neighbor entries for the
327
+ # BGP router instance.
328
+ #
329
+ # @return [nil, Hash<Symbol, Object>] Returns a hash that
330
+ # represents the entire BGP neighbor collection from the nodes
331
+ # running configuration. If there a BGP router is not configured
332
+ # or contains no neighbor entries then this method will return
333
+ # an empty hash.
334
+ def getall
335
+ config = get_block('^router bgp .*')
336
+ return nil unless config
337
+
338
+ entries = config.scan(/neighbor ([^\s]+)/)
339
+ entries.uniq.each_with_object({}) do |name, hsh|
340
+ resource = get(name[0])
341
+ hsh[name[0]] = resource if resource
342
+ end
343
+ end
344
+
345
+ ##
346
+ # parse_peer_group scans the BGP neighbor entries for the
347
+ # peer group.
348
+ #
349
+ # @api private
350
+ #
351
+ # @param [String] :config The switch config.
352
+ # @param [String] :name The name of the BGP neighbor to manage.
353
+ # This value can be either an IPv4 address or string (in the
354
+ # case of managing a peer group).
355
+ #
356
+ # @return [Hash<Symbol, Object>] resource hash attribute
357
+ def parse_peer_group(config, name)
358
+ value = config.scan(/neighbor #{name} peer-group ([^\s]+)/)
359
+ peer_group = value[0] ? value[0][0] : nil
360
+ { peer_group: peer_group }
361
+ end
362
+ private :parse_peer_group
363
+
364
+ ##
365
+ # parse_remote_as scans the BGP neighbor entries for the
366
+ # remote AS.
367
+ #
368
+ # @api private
369
+ #
370
+ # @param [String] :config The switch config.
371
+ # @param [String] :name The name of the BGP neighbor to manage.
372
+ # This value can be either an IPv4 address or string (in the
373
+ # case of managing a peer group).
374
+ #
375
+ # @return [Hash<Symbol, Object>] resource hash attribute
376
+ def parse_remote_as(config, name)
377
+ value = config.scan(/neighbor #{name} remote-as (\d+)/)
378
+ remote_as = value[0] ? value[0][0] : nil
379
+ { remote_as: remote_as }
380
+ end
381
+ private :parse_remote_as
382
+
383
+ ##
384
+ # parse_send_community scans the BGP neighbor entries for the
385
+ # remote AS.
386
+ #
387
+ # @api private
388
+ #
389
+ # @param [String] :config The switch config.
390
+ # @param [String] :name The name of the BGP neighbor to manage.
391
+ # This value can be either an IPv4 address or string (in the
392
+ # case of managing a peer group).
393
+ #
394
+ # @return [Hash<Symbol, Object>] resource hash attribute
395
+ def parse_send_community(config, name)
396
+ value = config.scan(/no neighbor #{name} send-community/)
397
+ enabled = value[0] ? false : true
398
+ { send_community: enabled }
399
+ end
400
+ private :parse_send_community
401
+
402
+ ##
403
+ # parse_shutdown scans the BGP neighbor entries for the
404
+ # remote AS.
405
+ #
406
+ # @api private
407
+ #
408
+ # @param [String] :config The switch config.
409
+ # @param [String] :name The name of the BGP neighbor to manage.
410
+ # This value can be either an IPv4 address or string (in the
411
+ # case of managing a peer group).
412
+ #
413
+ # @return [Hash<Symbol, Object>] resource hash attribute. Returns
414
+ # true if shutdown, false otherwise.
415
+ def parse_shutdown(config, name)
416
+ value = config.scan(/no neighbor #{name} shutdown/)
417
+ shutdown = value[0] ? false : true
418
+ { shutdown: shutdown }
419
+ end
420
+ private :parse_shutdown
421
+
422
+ ##
423
+ # parse_description scans the BGP neighbor entries for the
424
+ # description.
425
+ #
426
+ # @api private
427
+ #
428
+ # @param [String] :config The switch config.
429
+ # @param [String] :name The name of the BGP neighbor to manage.
430
+ # This value can be either an IPv4 address or string (in the
431
+ # case of managing a peer group).
432
+ #
433
+ # @return [Hash<Symbol, Object>] resource hash attribute
434
+ def parse_description(config, name)
435
+ value = config.scan(/neighbor #{name} description (.*)$/)
436
+ description = value[0] ? value[0][0] : nil
437
+ { description: description }
438
+ end
439
+ private :parse_description
440
+
441
+ ##
442
+ # parse_next_hop_self scans the BGP neighbor entries for the
443
+ # next hop self.
444
+ #
445
+ # @api private
446
+ #
447
+ # @param [String] :config The switch config.
448
+ # @param [String] :name The name of the BGP neighbor to manage.
449
+ # This value can be either an IPv4 address or string (in the
450
+ # case of managing a peer group).
451
+ #
452
+ # @return [Hash<Symbol, Object>] resource hash attribute
453
+ def parse_next_hop_self(config, name)
454
+ value = config.scan(/no neighbor #{name} next-hop-self/)
455
+ enabled = value[0] ? false : true
456
+ { next_hop_self: enabled }
457
+ end
458
+ private :parse_next_hop_self
459
+
460
+ ##
461
+ # parse_route_map_in scans the BGP neighbor entries for the
462
+ # route map in.
463
+ #
464
+ # @api private
465
+ #
466
+ # @param [String] :config The switch config.
467
+ # @param [String] :name The name of the BGP neighbor to manage.
468
+ # This value can be either an IPv4 address or string (in the
469
+ # case of managing a peer group).
470
+ #
471
+ # @return [Hash<Symbol, Object>] resource hash attribute
472
+ def parse_route_map_in(config, name)
473
+ value = config.scan(/neighbor #{name} route-map ([^\s]+) in/)
474
+ route_map_in = value[0] ? value[0][0] : nil
475
+ { route_map_in: route_map_in }
476
+ end
477
+ private :parse_route_map_in
478
+
479
+ ##
480
+ # parse_route_map_out scans the BGP neighbor entries for the
481
+ # route map in.
482
+ #
483
+ # @api private
484
+ #
485
+ # @param [String] :config The switch config.
486
+ # @param [String] :name The name of the BGP neighbor to manage.
487
+ # This value can be either an IPv4 address or string (in the
488
+ # case of managing a peer group).
489
+ #
490
+ # @return [Hash<Symbol, Object>] resource hash attribute
491
+ def parse_route_map_out(config, name)
492
+ value = config.scan(/neighbor #{name} route-map ([^\s]+) out/)
493
+ route_map_out = value[0] ? value[0][0] : nil
494
+ { route_map_out: route_map_out }
495
+ end
496
+ private :parse_route_map_out
497
+
498
+ ##
499
+ # configure_bgp adds the command to go to BGP config mode.
500
+ # Then it adds the passed in command. The commands are then
501
+ # passed on to configure.
502
+ #
503
+ # @api private
504
+ #
505
+ # @param [String] :cmd Command to run under BGP mode
506
+ #
507
+ # @return [Boolean] returns true if the command complete successfully
508
+ def configure_bgp(cmd)
509
+ config = get_block('^router bgp .*')
510
+ fail 'BGP router is not configured' unless config
511
+ bgp_as = Bgp.parse_bgp_as(config)
512
+ cmds = ["router bgp #{bgp_as[:bgp_as]}", cmd]
513
+ configure(cmds)
514
+ end
515
+ private :configure_bgp
516
+
517
+ ##
518
+ # create will create a new instance of a BGP neighbor on the node.
519
+ # The neighbor is created in the shutdown state and then enabled.
520
+ #
521
+ # @param [String] :name The name of the BGP neighbor to manage.
522
+ # This value can be either an IPv4 address or string (in the
523
+ # case of managing a peer group).
524
+ #
525
+ # @return [Boolean] returns true if the command completed successfully
526
+ def create(name)
527
+ set_shutdown(name, enable: false)
528
+ end
529
+
530
+ ##
531
+ # delete will delete the BGP neighbor from the node.
532
+ #
533
+ # @commands
534
+ # no neighbor <name>
535
+ # or
536
+ # no neighbor <name> peer-group
537
+ #
538
+ # @param [String] :name The name of the BGP neighbor to manage.
539
+ # This value can be either an IPv4 address or string (in the
540
+ # case of managing a peer group).
541
+ #
542
+ # @return [Boolean] returns true if the command completed successfully
543
+ def delete(name)
544
+ cmd = "no neighbor #{name}"
545
+ response = configure_bgp(cmd)
546
+ unless response
547
+ cmd = "no neighbor #{name} peer-group"
548
+ response = configure_bgp(cmd)
549
+ end
550
+ response
551
+ end
552
+
553
+ ##
554
+ # neigh_command_builder for neighbors which calls command_builder
555
+ #
556
+ # @param [String] :name The name of the BGP neighbor to manage.
557
+ # @param [String] :cmd The command portion of the neighbor command.
558
+ # @param [hash] :opts Optional keyword arguments
559
+ #
560
+ # @option :opts [String] :value Value being set.
561
+ #
562
+ # @option :opts [Boolean] :enable If false then the command is
563
+ # negated. Default is true.
564
+ #
565
+ # @option :opts [Boolean] :default Configure the command using
566
+ # the default keyword.
567
+ #
568
+ # @return [String] Returns built command string
569
+ def neigh_command_builder(name, cmd, opts)
570
+ command_builder("neighbor #{name} #{cmd}", opts)
571
+ end
572
+
573
+ ##
574
+ # set_peer_group creates a BGP static peer group name.
575
+ #
576
+ # @commands
577
+ # router bgp <bgp_as>
578
+ # {no | default} neighbor <name> peer-group <group-name>
579
+ #
580
+ # @param [String] :name The IP address of the neighbor
581
+ # @param [hash] :opts Optional keyword arguments
582
+ #
583
+ # @option :opts [String] :value The group name.
584
+ #
585
+ # @option :opts [Boolean] :enable If false then the command is
586
+ # negated. Default is true.
587
+ #
588
+ # @option :opts [Boolean] :default Configure the peer group using
589
+ # the default keyword
590
+ #
591
+ # @return [Boolean] returns true if the command complete successfully
592
+ def set_peer_group(name, opts = {})
593
+ configure_bgp(neigh_command_builder(name, 'peer-group', opts))
594
+ end
595
+
596
+ ##
597
+ # set_remote_as configures the expected AS number for a neighbor
598
+ # (peer).
599
+ #
600
+ # @commands
601
+ # router bgp <bgp_as>
602
+ # {no | default} neighbor <name> remote-as <as-id>
603
+ #
604
+ # @param [String] :name The IP address or name of the peer group.
605
+ # @param [hash] :opts Optional keyword arguments
606
+ #
607
+ # @option :opts [String] :value The remote as-id.
608
+ #
609
+ # @option :opts [Boolean] :enable If false then the command is
610
+ # negated. Default is true.
611
+ #
612
+ # @option :opts [Boolean] :default Configure the peer group using
613
+ # the default keyword
614
+ #
615
+ # @return [Boolean] returns true if the command complete successfully
616
+ def set_remote_as(name, opts = {})
617
+ configure_bgp(neigh_command_builder(name, 'remote-as', opts))
618
+ end
619
+
620
+ ##
621
+ # set_shutdown disables the specified neighbor. The value option is
622
+ # not used by this method.
623
+ #
624
+ # @commands
625
+ # router bgp <bgp_as>
626
+ # {no | default} neighbor <name> shutdown
627
+ #
628
+ # @param [String] :name The IP address or name of the peer group.
629
+ # @param [hash] :opts Optional keyword arguments
630
+ #
631
+ # @option :opts [String] :enable True enables the specified neighbor.
632
+ # False disables the specified neighbor.
633
+ #
634
+ # @option :opts [Boolean] :default Configure the peer group using
635
+ # the default keyword
636
+ #
637
+ # @return [Boolean] returns true if the command complete successfully
638
+ def set_shutdown(name, opts = {})
639
+ fail 'set_shutdown has value option set' if opts[:value]
640
+ # Shutdown semantics are opposite of enable semantics so invert enable
641
+ value = !opts[:enable]
642
+ opts.merge!(enable: value)
643
+ configure_bgp(neigh_command_builder(name, 'shutdown', opts))
644
+ end
645
+
646
+ ##
647
+ # set_send_community configures the switch to send community
648
+ # attributes to the specified BGP neighbor. The value option is
649
+ # not used by this method.
650
+ #
651
+ # @commands
652
+ # router bgp <bgp_as>
653
+ # {no | default} neighbor <name> send-community
654
+ #
655
+ # @param [String] :name The IP address or name of the peer group.
656
+ # @param [hash] :opts Optional keyword arguments
657
+ #
658
+ # @option :opts [String] :enable True enables the feature. False
659
+ # disables the feature.
660
+ #
661
+ # @option :opts [Boolean] :default Configure the peer group using
662
+ # the default keyword
663
+ #
664
+ # @return [Boolean] returns true if the command complete successfully
665
+ def set_send_community(name, opts = {})
666
+ fail 'send_community has the value option set' if opts[:value]
667
+ configure_bgp(neigh_command_builder(name, 'send-community', opts))
668
+ end
669
+
670
+ ##
671
+ # set_next_hop_self configures the switch to list its address as
672
+ # the next hop in routes that it advertises to the specified
673
+ # BGP-speaking neighbor or neighbors in the specified peer group.
674
+ # The value option is not used by this method.
675
+ #
676
+ # @commands
677
+ # router bgp <bgp_as>
678
+ # {no | default} neighbor <name> next-hop-self
679
+ #
680
+ # @param [String] :name The IP address or name of the peer group.
681
+ # @param [hash] :opts Optional keyword arguments
682
+ #
683
+ # @option :opts [String] :enable True enables the feature. False
684
+ # disables the feature.
685
+ #
686
+ # @option :opts [Boolean] :default Configure the peer group using
687
+ # the default keyword
688
+ #
689
+ # @return [Boolean] returns true if the command complete successfully
690
+ def set_next_hop_self(name, opts = {})
691
+ fail 'set_next_hop_self has the value option set' if opts[:value]
692
+ configure_bgp(neigh_command_builder(name, 'next-hop-self', opts))
693
+ end
694
+
695
+ ##
696
+ # set_route_map_in command applies a route map to inbound BGP
697
+ # routes.
698
+ #
699
+ # @commands
700
+ # router bgp <bgp_as>
701
+ # {no | default} neighbor <name> route-map <name> in
702
+ #
703
+ # @param [String] :name The IP address or name of the peer group.
704
+ # @param [hash] :opts Optional keyword arguments
705
+ #
706
+ # @option :opts [String] :value Name of a route map.
707
+ #
708
+ # @option :opts [Boolean] :enable If false then the command is
709
+ # negated. Default is true.
710
+ #
711
+ # @option :opts [Boolean] :default Configure the peer group using
712
+ # the default keyword
713
+ #
714
+ # @return [Boolean] returns true if the command complete successfully
715
+ def set_route_map_in(name, opts = {})
716
+ cmd = neigh_command_builder(name, 'route-map', opts) + ' in'
717
+ configure_bgp(cmd)
718
+ end
719
+
720
+ ##
721
+ # set_route_map_out command applies a route map to outbound BGP
722
+ # routes.
723
+ #
724
+ # @commands
725
+ # router bgp <bgp_as>
726
+ # {no | default} neighbor <name> route-map <name> out
727
+ #
728
+ # @param [String] :name The IP address or name of the peer group.
729
+ # @param [hash] :opts Optional keyword arguments
730
+ #
731
+ # @option :opts [String] :value Name of a route map.
732
+ #
733
+ # @option :opts [Boolean] :enable If false then the command is
734
+ # negated. Default is true.
735
+ #
736
+ # @option :opts [Boolean] :default Configure the peer group using
737
+ # the default keyword
738
+ #
739
+ # @return [Boolean] returns true if the command complete successfully
740
+ def set_route_map_out(name, opts = {})
741
+ cmd = neigh_command_builder(name, 'route-map', opts) + ' out'
742
+ configure_bgp(cmd)
743
+ end
744
+
745
+ ##
746
+ # set_description associates descriptive text with the specified
747
+ # peer or peer group.
748
+ #
749
+ # @commands
750
+ # router bgp <bgp_as>
751
+ # {no | default} neighbor <name> description <string>
752
+ #
753
+ # @param [String] :name The IP address or name of the peer group.
754
+ # @param [hash] :opts Optional keyword arguments
755
+ #
756
+ # @option :opts [String] :value The description string.
757
+ #
758
+ # @option :opts [Boolean] :enable If false then the command is
759
+ # negated. Default is true.
760
+ #
761
+ # @option :opts [Boolean] :default Configure the peer group using
762
+ # the default keyword
763
+ #
764
+ # @return [Boolean] returns true if the command complete successfully
765
+ def set_description(name, opts = {})
766
+ configure_bgp(neigh_command_builder(name, 'description', opts))
767
+ end
768
+ end
769
+ end
770
+ end