Forum Discussion

bitva_135199's avatar
bitva_135199
Icon for Nimbostratus rankNimbostratus
Mar 07, 2016

How to Create/Modify iApp via API?

Hi! I've been trying to follow some of the articles I've found around this but am having no luck. I think I'm missing something simple but not sure what yet. Any help you can give would be greatly appreciated!

I created an iApp through the GUI to my liking. I then retrieved it via the API like this:

 

curl -sk -u 'admin:pass' -H "Content-Type: application/json" https://10.1.1.1/mgmt/tm/sys/application/service/~Common~MyCoolSite.app~MyCoolSite?expandSubcollections=true |python -m json.tool >MyCoolSite.json

 

If I try to make a change to the iApp json file and POST it back I get this message:

 

$ curl -sk -u 'admin:pass' -H "Content-Type: application/json" -X POST --data @MyCoolSite.json https://10.1.1.1/mgmt/tm/sys/application/service

 

{"code":400,"message":"{\"code\":400,\"message\":\"script did not successfully complete: (\\"none\\" invalid IP address\n while executing\n\\"tmsh::create [string range $args 7 end] \\"\n (\\"create\\" arm line 1)\n invoked from within\n\\"switch -exact -- [string range $args 0 5] {\n create { tmsh::create [string range $args 7 end] }\n modify { tmsh::modify [string r...\\"\n (procedure \\"iapp::conf\\" line 14)\n invoked from within\n\\"iapp::conf create ltm virtual ${app}_vs destination [iapp::destination $::pool__addr $::pool__port] mask $mask $vs_params ip-protocol tcp mirror ...\\"\n invoked from within\n\\"subst $substa_out\\"\n invoked from within\n\\"if { [info exists [set substa_in]] } {\n set substa_out [subst $$substa_in]\n set substa_out [subst $substa_out]\n } else {\n...\\"\n (\\"uplevel\\" body line 3)\n invoked from within\n\\"uplevel {\n append ::substa_debug \\"\\n$substa_in\\"\n if { [info exists [set substa_in]] } {\n set substa_o","errorStack":[]}

I have a feeling I'm missing something simple here 🙂

Any ideas on where I've gone wrong?

 

Thanks so much!

 

14 Replies

  • JamesSevedge_23's avatar
    JamesSevedge_23
    Historic F5 Account

    I am not sure exactly what is going wrong with your POST attempt as I cannot see the json data being posted. Below I copied a working script which will use the http template and allows you from a bash shell to input some of the common args you would expect. I have the JSON all in the same file for simplicity in troubleshooting, you could always pull it out into a separate file like you did.

     

    Modifying answer as I submitted a new post with the code in a code block.

     

  • JamesSevedge_23's avatar
    JamesSevedge_23
    Historic F5 Account

    The post removed my comment symbols out, below should be correct as it is in a code block.

     

    !/bin/bash
     This script will create an application service using the f5.http template.  Commandline arg... -a is iapp name, -v is virtual server ip, -m is for pool member ip,
     -b is the big ip address, -u is for username, -p for password (defaults of admin/admin if flags not present)  -d is an optional paramater if you would like to delete the iapp.
     Full Command would look like: ./createiapp_http.sh -b 2.2.2.2 -a httpapp -v 1.1.1.1 -m 1.1.1.2 -u admin -p admin
     Full Command to delete would add the delete flag: ./createiapp_http.sh -b 2.2.2.2 -a httpapp -v 1.1.1.1 -m 1.1.1.2 -u admin -p admin -d
    
    delete=false
    user=admin
    pwd=admin
    while getopts a:v:b:u:p:m:d option
    do  case "$option"  in
            a) appname=$OPTARG;;
            v) vsip=$OPTARG;;
            m) pmember=$OPTARG;;
            b) bigip=$OPTARG;;
            u) user=$OPTARG;;
            p) pwd=$OPTARG;;
            d) delete=true;;
        esac 
    done
    
    echo "Delete equals: $delete"
    echo "Connecting to BIG IP: $bigip as $user"
    echo "iAPP Name: $appname"
    echo "VS IP: $vsip"
    echo "Pool Member: $pmember"
    
    if [ $delete == false ] ;   then
    curl -sk -u $user:$pwd https://$bigip/mgmt/tm/sys/application/service/ -H 'Content-Type: application/json' -X POST  -d '{"kind":"tm:sys:application:service:servicestate",
    
    "name":'\"$appname\"',
    
    "partition":"Common",
    
    "execute-action":"definition",
    
    "template":"/Common/f5.http",
    
    "templateReference":{"link":"https://localhost/mgmt/tm/sys/application/template/~Common~f5.http?ver=12.0.0"},
    
    "templateModified":"no",
    
    "trafficGroup":"/Common/traffic-group-1",
    
    "trafficGroupReference":{"link":"https://localhost/mgmt/tm/cm/traffic-group/~Common~traffic-group-1?ver=12.0.0"},
    
    "tables":[{"name":"basic__snatpool_members"},
    
    {"name":"net__snatpool_members"},
    
    {"name":"optimizations__hosts"},
    
    {"name":"pool__hosts",
    
    "columnNames":["name"],"rows":[{"row":["test.test.com"]}]},
    
    {"name":"pool__members",
    
    "columnNames":["addr","port","connection_limit"],
    
    "rows":[{"row":['\"$pmember\"',"80","0"]}]},
    
    {"name":"server_pools__servers"}],
    
    "variables":[{"name":"client__http_compression",
    
    "encrypted":"no",
    
    "value":"/create_new"},
    
    {"name":"monitor__monitor",
    
    "encrypted":"no","value":"/create_new"},
    
    {"name":"monitor__response","encrypted":"no","value":"none"},
    
    {"name":"monitor__uri","encrypted":"no","value":"/"},
    
    {"name":"net__client_mode","encrypted":"no","value":"wan"},
    
    {"name":"net__server_mode","encrypted":"no","value":"lan"},
    
    {"name":"pool__addr","encrypted":"no","value":'\"$vsip\"'},
    
    {"name":"pool__pool_to_use","encrypted":"no","value":"/create_new"},
    
    {"name":"pool__port","encrypted":"no","value":"80"},
    
    {"name":"asm__use_asm","value":"/do_not_use"},
    
    {"name":"ssl__mode","encrypted":"no","value":"no_ssl"},
    
    {"name":"ssl_encryption_questions__advanced","encrypted":"no","value":"no"},
    
    {"name":"ssl_encryption_questions__help","encrypted":"no","value":"hide"}]}' | jq .
    
    fi
    
    if [ $delete == true ] ; then
           curl -sk -u admin:admin https://$bigip/mgmt/tm/sys/application/service/~Common~$appname.app~$appname -H 'Content-Type: application/json' -X DELETE | jq .
           echo "iAPP $appname deleted"   
    fi 
    • bitva_135199's avatar
      bitva_135199
      Icon for Nimbostratus rankNimbostratus
      Hey, thanks for the reply. What you're doing there is another way I was thinking of going about a full create/destroy of an iApp. But I still couldn't add or remove nodes without deleting the full iApp stack and recreating. My understanding is I could resubmit with new/removed pool members or iRules right? I've put the JSON file I'm trying to POST (or PUT for modify I assumed) here: http://pastebin.com/8cWjMtk2 Thanks again!
    • JamesSevedge_23's avatar
      JamesSevedge_23
      Historic F5 Account
      You should be using PUT for modify, here is a link to a couple blog posts on using the rest api to create iapp services that will explain this better then I can, hope it helps! https://devcentral.f5.com/s/articles/building-application-delivery-services-from-templates-using-the-rest-api-part-two .
    • JamesSevedge_23's avatar
      JamesSevedge_23
      Historic F5 Account
      Ok, I just tested this with my script. I had to manually modify the POST line though to include the app service path and change to PUT. You could expand the script to write that logic in. Basically it is exactly the same as creation except you change the POST to PUT and append the application service path onto the URI, as well as make the change to pool member, etc... "curl -sk -u $user:$pwd https://$bigip/mgmt/tm/sys/application/service/~Common~$appname.app~$appname -H 'Content-Type: application/json' -X PUT -d "
  • Fred_Slater_856's avatar
    Fred_Slater_856
    Historic F5 Account
    iControl-REST is not fully idempotent, so you may run into a problem posting back what you get. You may also have a character interpretation issue, where Tcl is consuming the curly braces in your block of json. Look in /var/tmp/scriptd.out for a log of the tmsh statement that failed, and perhaps add more debugging statements to convince yourself that the values in MyCoolSite.json are showing up in the Tcl context.
  • ah, thanks, I'll check that out as well. I thought the API would handle the json --> tcl implementation, maybe not though huh
  • Hello,

     

    You may be interested in looking into Hitesh Patel's Application Services Integration iApp, which is designed to be a little simpler to deploy via the API. https://github.com/0xHiteshPatel/appsvcs_integration_iapp

     

    The iApp builds in some sane defaults, which can ease the number of attributes you need to provide in your API calls. It also does not use self-populating fields, meaning, you need to provide all details you want to specify. This is a good thing, as typical iApps can require fairly complex API calls.

     

    It's also compatible with systems like APIC, NSX, and Big-IQ.

     

    -Josh