@@ -2725,3 +2725,294 @@ def fetchJobStatusJSON(self, job_url):
27252725 except Exception as e :
27262726 logger .error ("Failed to check job status: %s" , e )
27272727 return "Error"
2728+
2729+ def getAllPartitionProfiles (self , lpar_uuid , profile_name = None ):
2730+ url = "https://{0}/rest/api/uom/LogicalPartition/{1}/LogicalPartitionProfile" .format (self .hmc_ip , lpar_uuid )
2731+ header = {'X-API-Session' : self .session ,
2732+ 'Accept' : '*/*' }
2733+ resp = open_url (url ,
2734+ headers = header ,
2735+ method = 'GET' ,
2736+ validate_certs = False ,
2737+ force_basic_auth = True ,
2738+ timeout = 300 )
2739+ if resp .code != 200 :
2740+ logger .debug ("Get of partition profile failed. Respsonse code: %d" , resp .code )
2741+ return None
2742+ response = resp .read ()
2743+ if profile_name is None :
2744+ return response
2745+ elif profile_name is not None :
2746+ post_response = xml_strip_namespace (response )
2747+ entries = post_response .xpath ("//entry" )
2748+ for entry in entries :
2749+ profile_name_elem = entry .xpath (".//ProfileName" )
2750+ if profile_name_elem and profile_name_elem [0 ].text == profile_name :
2751+ atom_id_elem = entry .xpath (".//AtomID" )
2752+ if atom_id_elem :
2753+ return atom_id_elem [0 ].text
2754+ return None
2755+
2756+ def getCurrentPartitionProfiles (self , lpar_uuid , profile_uuid ):
2757+ url = "https://{0}/rest/api/uom/LogicalPartition/{1}/LogicalPartitionProfile/{2}" .format (self .hmc_ip , lpar_uuid , profile_uuid )
2758+ header = {'X-API-Session' : self .session ,
2759+ 'Accept' : '*/*' }
2760+ resp = open_url (url ,
2761+ headers = header ,
2762+ method = 'GET' ,
2763+ validate_certs = False ,
2764+ force_basic_auth = True ,
2765+ timeout = 300 )
2766+ if resp .code != 200 :
2767+ logger .debug ("Get of partition profile failed. Respsonse code: %d" , resp .code )
2768+ return None
2769+ response = resp .read ()
2770+ return response
2771+
2772+ def copyPartitionProfile (self , lpar_uuid , params ):
2773+ payload = {
2774+ "JobRequest" : {
2775+ "Metadata" : {
2776+ "Atom" : ""
2777+ },
2778+ "RequestedOperation" : {
2779+ "Metadata" : {
2780+ "Atom" : ""
2781+ },
2782+ "OperationName" : "CopyProfile" ,
2783+ "GroupName" : "LogicalPartition"
2784+ },
2785+ "JobParameters" : {
2786+ "Metadata" : {
2787+ "Atom" : ""
2788+ },
2789+ "JobParameter" : [
2790+ {
2791+ "Metadata" : {
2792+ "Atom" : ""
2793+ },
2794+ "ParameterName" : "existingPartitionProfileName" ,
2795+ "ParameterValue" : params ['name' ]
2796+ },
2797+ {
2798+ "Metadata" : {
2799+ "Atom" : ""
2800+ },
2801+ "ParameterName" : "newPartitionProfileName" ,
2802+ "ParameterValue" : params ['duplicate_prof_name' ]
2803+ }
2804+ ]
2805+ }
2806+ }
2807+ }
2808+ url = "https://{0}/rest/api/uom/LogicalPartition/{1}/do/CopyProfile" .format (self .hmc_ip , lpar_uuid )
2809+ header = {'X-API-Session' : self .session ,
2810+ 'Accept' : 'application/json' ,
2811+ 'Content-Type' : 'application/vnd.ibm.powervm.web+json; type=JobRequest' }
2812+ try :
2813+ resp = open_url (url ,
2814+ headers = header ,
2815+ data = json .dumps (payload ),
2816+ method = 'PUT' ,
2817+ validate_certs = False ,
2818+ force_basic_auth = True ,
2819+ timeout = 300 )
2820+ resp = json .loads (resp .read ())
2821+ self_link = resp ['entry' ]['selfLink' ]
2822+ response = self .fetchJobStatusJSON (self_link )
2823+ status = response ['entry' ]['content' ]['JobResponse' ]['Status' ]
2824+ if status == 'FAILED_BEFORE_COMPLETION' :
2825+ response = response ['entry' ]['content' ]['JobResponse' ]
2826+ if response .get ('ResponseException' ):
2827+ return response
2828+ elif status == 'COMPLETED_OK' :
2829+ return 200
2830+ except Exception as e :
2831+ logger .debug ("Error in copyPartitionProfile: %s" , str (e ))
2832+ return f"Error: { str (e )} "
2833+
2834+ def dedicatedProcessorPayload (self , params ):
2835+ payload = '''
2836+ <AssignAllResources kxe="false" kb="COD">false</AssignAllResources>
2837+ <ProcessorAttributes kxe="false" kb="CUR" schemaVersion="V1_0">
2838+ <Metadata>
2839+ <Atom/>
2840+ </Metadata>
2841+ <DedicatedProcessorConfiguration kxe="false" kb="CUD" schemaVersion="V1_0">
2842+ <Metadata>
2843+ <Atom/>
2844+ </Metadata>
2845+ <DesiredProcessors kb="CUD" kxe="false">{0}</DesiredProcessors>
2846+ <MaximumProcessors kb="CUD" kxe="false">{1}</MaximumProcessors>
2847+ <MinimumProcessors kxe="false" kb="CUD">{2}</MinimumProcessors>
2848+ </DedicatedProcessorConfiguration>
2849+ <HasDedicatedProcessors kxe="false" kb="CUD">{3}</HasDedicatedProcessors>
2850+ <SharingMode kxe="false" kb="CUD">{4}</SharingMode>
2851+ </ProcessorAttributes>
2852+ ''' .format (params ['desired_processors' ], params ['maximum_processors' ], params ['minimum_processors' ],
2853+ params ['processor_mode' ], params ['allow_processor_sharing' ])
2854+ return payload
2855+
2856+ def sharedProcessorPayload (self , params ):
2857+ payload = '''
2858+ <AssignAllResources kb="COD" kxe="false">false</AssignAllResources>
2859+ <ProcessorAttributes kxe="false" kb="CUR" schemaVersion="V1_0">
2860+ <Metadata>
2861+ <Atom/>
2862+ </Metadata>
2863+ <HasDedicatedProcessors kxe="false" kb="CUD">{0}</HasDedicatedProcessors>
2864+ <SharedProcessorConfiguration kxe="false" kb="CUD" schemaVersion="V1_0">
2865+ <Metadata>
2866+ <Atom/>
2867+ </Metadata>
2868+ <DesiredProcessingUnits kb="CUD" kxe="false">{1}</DesiredProcessingUnits>
2869+ <DesiredVirtualProcessors kxe="false" kb="CUD">{2}</DesiredVirtualProcessors>
2870+ <MaximumProcessingUnits kb="CUD" kxe="false">{3}</MaximumProcessingUnits>
2871+ <MaximumVirtualProcessors kxe="false" kb="CUD">{4}</MaximumVirtualProcessors>
2872+ <MinimumProcessingUnits kxe="false" kb="CUD">{5}</MinimumProcessingUnits>
2873+ <MinimumVirtualProcessors kb="CUD" kxe="false">{6}</MinimumVirtualProcessors>
2874+ <SharedProcessorPoolID kb="CUD" kxe="false">{7}</SharedProcessorPoolID>
2875+ <UncappedWeight kb="CUD" kxe="false">{8}</UncappedWeight>
2876+ </SharedProcessorConfiguration>
2877+ <SharingMode kb="CUD" kxe="false">{9}</SharingMode>
2878+ </ProcessorAttributes>
2879+ ''' .format (params ['processor_mode' ], params ['desired_processing_units' ], params ['desired_processors' ],
2880+ params ['maximum_processing_units' ], params ['maximum_processors' ], params ['minimum_processing_units' ],
2881+ params ['minimum_processors' ], params ['shared_processor_pool' ], params ['uncapped_weight' ], params ['sharing_mode' ])
2882+ return payload
2883+
2884+ def createPartitionProfile (self , lpar_uuid , params ):
2885+ partiton_profile_xmlstr = ''
2886+ template_partition_profile = '''<LogicalPartitionProfile:LogicalPartitionProfile
2887+ xmlns:LogicalPartitionProfile="http://www.ibm.com/xmlns/systems/power/firmware/uom/mc/2012_10/"
2888+ xmlns="http://www.ibm.com/xmlns/systems/power/firmware/uom/mc/2012_10/"
2889+ xmlns:ns2="http://www.w3.org/XML/1998/namespace/k2" schemaVersion="V1_0">'''
2890+ partiton_profile_xmlstr += template_partition_profile
2891+ if params ['processor_mode' ].lower () == 'false' :
2892+ partiton_profile_xmlstr += self .sharedProcessorPayload (params )
2893+ else :
2894+ partiton_profile_xmlstr += self .dedicatedProcessorPayload (params )
2895+ memory_payload = '''<ProfileMemory kb="CUR" kxe="false" schemaVersion="V1_0">
2896+ <Metadata>
2897+ <Atom/>
2898+ </Metadata>
2899+ <ActiveMemoryExpansionEnabled kb="CUD" kxe="false">{0}</ActiveMemoryExpansionEnabled>
2900+ <ActiveMemorySharingEnabled kb="CUD" kxe="false">false</ActiveMemorySharingEnabled>
2901+ <DesiredHugePageCount kb="CUD" kxe="false">{1}</DesiredHugePageCount>
2902+ <DesiredMemory kxe="false" kb="CUD">{2}</DesiredMemory>
2903+ <ExpansionFactor kb="CUD" kxe="false">{3}</ExpansionFactor>
2904+ <HardwarePageTableRatio kb="CUD" kxe="false">{4}</HardwarePageTableRatio>
2905+ <MaximumHugePageCount kb="CUD" kxe="false">{5}</MaximumHugePageCount>
2906+ <MaximumMemory kb="CUD" kxe="false">{6}</MaximumMemory>
2907+ <MinimumHugePageCount kb="CUD" kxe="false">{7}</MinimumHugePageCount>
2908+ <MinimumMemory kxe="false" kb="CUD">{8}</MinimumMemory>
2909+ <DesiredPhysicalPageTableRatio ksv="V1_6_0" kb="CUD" kxe="false">{9}</DesiredPhysicalPageTableRatio>
2910+ </ProfileMemory>
2911+ <ProfileName kb="CUR" kxe="false">{10}</ProfileName>
2912+ </LogicalPartitionProfile:LogicalPartitionProfile>
2913+ ''' .format (str (params ['active_memory_expansion' ]).lower (),
2914+ params ['desired_huge_pagecount' ], params ['desired_memory' ], params ['expansion_factor' ], params ['hardware_page_tableratio' ],
2915+ params ['maximum_huge_pagecount' ], params ['maximum_memory' ], params ['minimum_huge_pagecount' ],
2916+ params ['minimum_memory' ], params ['desired_physical_page_tableratio' ], params ['name' ])
2917+ partiton_profile_xmlstr += memory_payload
2918+ if 'sharing_mode' in params :
2919+ if params ['sharing_mode' ] == 'capped' :
2920+ xml_tree = etree .fromstring (partiton_profile_xmlstr .encode ())
2921+ for elem in xml_tree .xpath ('.//*[local-name()="UncappedWeight"]' ):
2922+ elem .getparent ().remove (elem )
2923+ partiton_profile_xmlstr = etree .tostring (xml_tree , encoding = 'unicode' )
2924+ url = "https://{0}/rest/api/uom/LogicalPartition/{1}/LogicalPartitionProfile" .format (self .hmc_ip , lpar_uuid )
2925+ header = {'X-API-Session' : self .session ,
2926+ 'Accept' : '*/*' ,
2927+ 'Content-Type' : 'application/vnd.ibm.powervm.uom+xml; type=LogicalPartitionProfile' }
2928+ try :
2929+ resp = open_url (url ,
2930+ headers = header ,
2931+ data = partiton_profile_xmlstr ,
2932+ method = 'PUT' ,
2933+ validate_certs = False ,
2934+ force_basic_auth = True ,
2935+ timeout = 300 )
2936+ response = resp .read ()
2937+ except Exception as e :
2938+ if hasattr (e , 'read' ):
2939+ response = e .read ()
2940+ post_response = xml_strip_namespace (response )
2941+ error_message_elements = post_response .xpath ("//Message" )
2942+ logger .debug (response )
2943+ return e .code , error_message_elements [0 ].text .strip ()
2944+ else :
2945+ return f"Error: { str (e )} "
2946+ post_response = xml_strip_namespace (response )
2947+ profile_name_elements = post_response .xpath ("//ProfileName" )
2948+ if profile_name_elements :
2949+ return 200 , profile_name_elements [0 ].text
2950+ return "Error: Profile creation failed with unknown error"
2951+
2952+ def updatePartitionProfile (self , lpar_uuid , partition_uuid , params ):
2953+ partiton_profile_xmlstr = ''
2954+ template_partition_profile = '''<LogicalPartitionProfile:LogicalPartitionProfile
2955+ xmlns:LogicalPartitionProfile="http://www.ibm.com/xmlns/systems/power/firmware/uom/mc/2012_10/"
2956+ xmlns="http://www.ibm.com/xmlns/systems/power/firmware/uom/mc/2012_10/"
2957+ xmlns:ns2="http://www.w3.org/XML/1998/namespace/k2" schemaVersion="V1_0">'''
2958+ partiton_profile_xmlstr += template_partition_profile
2959+ if params ['processor_mode' ].lower () == 'false' :
2960+ partiton_profile_xmlstr += self .sharedProcessorPayload (params )
2961+ else :
2962+ partiton_profile_xmlstr += self .dedicatedProcessorPayload (params )
2963+ memory_payload = '''<ProfileMemory kb="CUR" kxe="false" schemaVersion="V1_0">
2964+ <Metadata>
2965+ <Atom/>
2966+ </Metadata>
2967+ <ActiveMemoryExpansionEnabled kb="CUD" kxe="false">{0}</ActiveMemoryExpansionEnabled>
2968+ <ActiveMemorySharingEnabled kb="CUD" kxe="false">false</ActiveMemorySharingEnabled>
2969+ <DesiredHugePageCount kb="CUD" kxe="false">{1}</DesiredHugePageCount>
2970+ <DesiredMemory kxe="false" kb="CUD">{2}</DesiredMemory>
2971+ <ExpansionFactor kb="CUD" kxe="false">{3}</ExpansionFactor>
2972+ <HardwarePageTableRatio kb="CUD" kxe="false">{4}</HardwarePageTableRatio>
2973+ <MaximumHugePageCount kb="CUD" kxe="false">{5}</MaximumHugePageCount>
2974+ <MaximumMemory kb="CUD" kxe="false">{6}</MaximumMemory>
2975+ <MinimumHugePageCount kb="CUD" kxe="false">{7}</MinimumHugePageCount>
2976+ <MinimumMemory kxe="false" kb="CUD">{8}</MinimumMemory>
2977+ <DesiredPhysicalPageTableRatio ksv="V1_6_0" kb="CUD" kxe="false">{9}</DesiredPhysicalPageTableRatio>
2978+ </ProfileMemory>
2979+ <ProfileName kb="CUR" kxe="false">{10}</ProfileName>
2980+ </LogicalPartitionProfile:LogicalPartitionProfile>
2981+ ''' .format (str (params ['active_memory_expansion' ]).lower (),
2982+ params ['desired_huge_pagecount' ], params ['desired_memory' ], params ['expansion_factor' ], params ['hardware_page_tableratio' ],
2983+ params ['maximum_huge_pagecount' ], params ['maximum_memory' ], params ['minimum_huge_pagecount' ],
2984+ params ['minimum_memory' ], params ['desired_physical_page_tableratio' ], params ['name' ])
2985+ partiton_profile_xmlstr += memory_payload
2986+ if 'sharing_mode' in params :
2987+ if params ['sharing_mode' ] == 'capped' :
2988+ xml_tree = etree .fromstring (partiton_profile_xmlstr .encode ())
2989+ for elem in xml_tree .xpath ('.//*[local-name()="UncappedWeight"]' ):
2990+ elem .getparent ().remove (elem )
2991+ partiton_profile_xmlstr = etree .tostring (xml_tree , encoding = 'unicode' )
2992+ url = "https://{0}/rest/api/uom/LogicalPartition/{1}/LogicalPartitionProfile/{2}" .format (self .hmc_ip , lpar_uuid , partition_uuid )
2993+ header = {'X-API-Session' : self .session ,
2994+ 'Accept' : '*/*' ,
2995+ 'Content-Type' : 'application/vnd.ibm.powervm.uom+xml; type=LogicalPartitionProfile' }
2996+ try :
2997+ resp = open_url (url ,
2998+ headers = header ,
2999+ data = partiton_profile_xmlstr ,
3000+ method = 'POST' ,
3001+ validate_certs = False ,
3002+ force_basic_auth = True ,
3003+ timeout = 300 )
3004+ response = resp .read ()
3005+ except Exception as e :
3006+ if hasattr (e , 'read' ):
3007+ response = e .read ()
3008+ post_response = xml_strip_namespace (response )
3009+ error_message_elements = post_response .xpath ("//Message" )
3010+ logger .debug (response )
3011+ return e .code , error_message_elements [0 ].text .strip ()
3012+ else :
3013+ return f"Error: { str (e )} "
3014+ post_response = xml_strip_namespace (response )
3015+ profile_name_elements = post_response .xpath ("//ProfileName" )
3016+ if profile_name_elements :
3017+ return 200 , profile_name_elements [0 ].text
3018+ return "Error: Profile creation failed with unknown error"
0 commit comments