Forum Discussion

Ken_R_'s avatar
Ken_R_
Icon for Nimbostratus rankNimbostratus
Dec 07, 2019

F5-SDK Error When Attempting to Add Pool Members

I've just started programming with Python (3.6.8) and found the f5-sdk module to be interesting. I've written a script to build nodes, pool members and a virtual server (v13.1.1.4), however while adding pool members to a pool, I receive the following error:

 

'Traceback (most recent call last):

 File "f5_build_sdk.py", line 68, in ltm_build

  name=pool[tuple('member')] + ':' + pool[tuple('port')],

TypeError: 'Pool' object is not subscriptable'

 

The REST api documentation suggests the object it is looking for is an array type, which I believe I have configured as such. I've done some other checking with various resources, but can't seem to find an answer. Below is the code I've written. Any help would be much appreciated.

 

#!/usr/bin/python

# -*- coding: utf-8 -*-

 

import requests

from ansible.module_utils.network.f5 import icontrol

from f5.bigip import ManagementRoot

from getpass import getpass

from icontrol.exceptions import iControlUnexpectedHTTPError

import sys

 

 

change = input('Change or Rollback? ').lower()

 

password = getpass()

requests.packages.urllib3.disable_warnings()

mgmt = ManagementRoot('test-ltm', 'admin', password)

ltm = mgmt.tm.ltm

 

# Build Details

node_details = [{'name': 'node-1', 'address': '1.1.1.2'}]

 

pool_details = [{

  'name': 'pool-1',

  'member': [{'name': 'node-1', 'port': '80'}],

  'monitor': 'tcp',

  'description': 'Test SDK Pool',

  'method': 'round-robin'

}]

 

virtual_details = [{

  'name': 'virtual-1',

  'vip': '1.1.1.1:80',

  'pool': 'pool-1',

  'type': 'standard',

  'profiles': [{

    'name': 'f5-tcp-wan',

    'context': 'clientside'

  }, {

    'name': 'f5-tcp-lan',

    'context': 'serverside'

  }, {

    'name': 'HTTP-X-Forwarded'

  }],

}]

 

 

def ltm_build():

  if change == 'change':

 

    # Node Creation

    for node in node_details:

      try:

        ltm.nodes.node.create(

          partition='Common',

          name=node['name'],

          address=node['address'])

      except iControlUnexpectedHTTPError as error:

        print('\n', f'node: {node["name"]} already exists...')

        sys.exit()

 

    # Pool Creation

    for pool in pool_details:

      try:

        ltm.pools.pool.create(partition='Common', name=pool['name'])

        pool = ltm.pools.pool.load(name=pool['name'])

        pool.members_s.members.create(

          partition='Common',

          name=pool['member'] + ':' + pool['port'],

          monitor=pool['monitor'])

      except (iControlUnexpectedHTTPError, TypeError) as error:

        print('\n', f'pool: {pool["name"]} server already exists...', '\n')

        sys.exit()

 

    # Virtual Server Creation

    for virtual in virtual_details:

      try:

        ltm.virtuals.virtual.create(

          partition='Common',

          name=virtual['name'],

          destination=virtual['vip'],

          mask='255.255.255.255',

          ipProtocol='tcp',

          pool=virtual['pool'],

          profiles=virtual['profiles'],

        )

      except iControlUnexpectedHTTPError as error:

        print(f'virtual_server: {virtual["name"]} server already exists...', '\n')

        sys.exit()

 

  elif change == 'rollback':

 

    # Remove Virtual Server

    for virtual in virtual_details:

      virtual = ltm.virtuals.virtual.load(

        partition='Common', name=virtual['name'])

      virtual.delete()

 

    # Delete Pool

    for pool in pool_details:

      pool = ltm.pools.pool.load(name=pool['name'])

      pool.delete()

 

    # Delete Node

    for node in node_details:

      ltm.nodes.node.load(partition='Common', name=node['name']).delete()

      print('\n', 'Rollback Complete...', '\n')

 

 

if __name__ == '__main__':

  ltm_build()

 

2 Replies

  • Hi Ken R.

     

    In your code; node, pool and virtual server definitions are dictionary in the list. You can remove list. "[ ]"

     

    or...

    pool.members_s.members.create(
    	partition='Common',
    	name=pool[0]['member'][0]['name'] + ':' + pool[0]['member'][0]['port'],
    	monitor=pool[0]['monitor'])

    ...can you try above code instead of following?

    pool.members_s.members.create(
    	partition='Common',
    	name=pool['member'] + ':' + pool['port'],
    	monitor=pool['monitor'])

     

  • Ken_R_'s avatar
    Ken_R_
    Icon for Nimbostratus rankNimbostratus

    eaa,

    Thanks for you help. I was able to write the script a little differently and its working the way I was hoping. Below is the script if you're curious...thanks again.

     

    #!/usr/bin/python

    # -*- coding: utf-8 -*-

     

    import requests

    from ansible.module_utils.network.f5 import icontrol

    from f5.bigip import ManagementRoot

    from getpass import getpass

    from icontrol.exceptions import iControlUnexpectedHTTPError

    import sys

     

    # Determines the type of change to be made.

     

    change = input('Change or Rollback? ').lower()

     

    password = getpass()

    requests.packages.urllib3.disable_warnings()

    mgmt = ManagementRoot('us6645ny-nelab-ltm2', 'admin', password)

    ltm = mgmt.tm.ltm

     

    # Node Details

     

    nodes = [{'name': 'sdk-node', 'address': '12.7.20.19'},

         {'name': 'sdk-node2', 'address': '12.7.20.192'}]

     

    # Pool Details

     

    pool_name = 'sdk-pool'

    member_port = '80'

     

    # Virtual Server Details

     

    vs_name = 'sdk-virtual'

    vip = '192.168.100.10'

    port = '80'

    profiles = [{'name': 'f5-tcp-wan', 'context': 'clientside'},

          {'name': 'f5-tcp-lan', 'context': 'serverside'},

          {'name': 'serverssl', 'context': 'serverside'},

          {'name': 'http'}]

     

     

    def ltm_build():

     

      if change == 'change':

        try:

          ltm.pools.pool.create(name=pool_name, monitor='tcp')

          pool = ltm.pools.pool.load(name=pool_name)

     

          for node in nodes:

            ltm.nodes.node.create(partition='Common',

                name=node['name'], address=node['address'])

            pool.members_s.members.create(partition='Common',

                name=node['name'] + ':' + member_port)

     

          params = {

            'name': vs_name,

            'destination': '{}:{}'.format(vip, port),

            'mask': '255.255.255.255',

            'pool': pool_name,

            'profiles': profiles,

            'partition': 'Common',

            'sourceAddressTranslation': {'type': 'automap'},

            }

          ltm.virtuals.virtual.create(**params)

        except iControlUnexpectedHTTPError:

     

          print('Duplicate Objects Exist...Build Failed')

          sys.exit()

     

     

    if __name__ == '__main__':

      ltm_build()