I have this function that uses PrettyTables to gather information about the Virtual Machines owned by a user. Right now, it only shows information and it works well. I have a new idea where I want to add a button to a new column which allows the user to reboot the virutal machine. I already know how to restart the virtual machines but what I'm struggling to figure out is the best way to create a dataset which i can iterate through and then create a HTML table. I've done similar stuff with PHP/SQL in the past and it was straight forward. I don't think I can iterate through PrettyTables so I'm wondering what is my best option? Pretty tables does a very good job of making it simple to create the table (as you can see below). I'm hoping to use another method, but also keep it very simple. Basically, making it relational and easy to iterate through. Any other suggestions are welcome. Thanks!
Here is my current code:
x = PrettyTable()
x.field_names = ["VM Name", "OS", "IP", "Power State"]
for uuid in virtual_machines:
vm = search_index.FindByUuid(None, uuid, True, False)
if vm.summary.guest.ipAddress == None:
ip = "Unavailable"
else:
ip = vm.summary.guest.ipAddress
if vm.summary.runtime.powerState == "poweredOff":
power_state = "OFF"
else:
power_state = "ON"
if vm.summary.guest.guestFullName == None:
os = "Unavailable"
else:
os = vm.summary.guest.guestFullName
x.add_row([vm.summary.config.name, os, ip, power_state])
table = x.get_html_string(attributes = {"class":"table table-striped"})
return table
Here is a sample of what it looks like and also what I plan to do with the button. http://prntscr.com/nki3ci
Figured out how to query the prettytable. It was a minor addition without having to redo it all.
html = '<table class="table"><tr><th>VM Name</th><th>OS</th><th>IP</th><th>Power
State</th></tr>'
htmlend = '</tr></table>'
body = ''
for vmm in x:
vmm.border = False
vmm.header = False
vm_name = (vmm.get_string(fields=["VM Name"]))
operating_system = (vmm.get_string(fields=["OS"]))
ip_addr = ((vmm.get_string(fields=["IP"])))
body += '<tr><td>'+ vm_name + '</td><td>' + operating_system + '</td> <td>'+ ip_addr +'</td> <td>ON</td></tr>'
html += body
html += htmlend
print(html)
Related
I'm having an AppModel application in my System Center Configuration Manager(SCCM) console. Please see below screenshot of the properties window of the SCCM application:
I need to know the value of 'Allow this application to be installed from the Install Application task sequence.....' checkbox. It is highlighted in yellow.
I tried to get it through wbemtest tool using below details:
Namespace: root\sms\site_[siteCode] e.g. root\sms\site_lab
Query: select * from SMS_Application
I hope I've got the correct Windows Management Instrumentation(WMI) class for AppModel CM applications.
But the output in wbemtest tool doesn't give any field in the result output which can reflect the current condition of checkbox:
Instance of SMS_Application
{
ApplicabilityCondition = "";
CategoryInstance_UniqueIDs = {};
CI_ID = 16777532;
CI_UniqueID = "ScopeId_6AFF9AA6-E784-4BB8-8DCF-816FCF7A7C09/Application_8e417c4c-da5d-4f1c-91af-ed63d63f9a62/3";
CIType_ID = 10;
CIVersion = 3;
CreatedBy = "NTL\\administrator";
DateCreated = "20190724122559.000000+000";
DateLastModified = "20200422051705.000000+000";
EULAAccepted = 2;
EULAExists = FALSE;
ExecutionContext = 0;
Featured = 0;
HasContent = TRUE;
IsBundle = FALSE;
IsDeployable = TRUE;
IsDeployed = FALSE;
IsEnabled = TRUE;
IsExpired = FALSE;
IsHidden = FALSE;
IsLatest = TRUE;
IsQuarantined = FALSE;
IsSuperseded = FALSE;
IsSuperseding = FALSE;
IsUserDefined = TRUE;
IsVersionCompatible = TRUE;
LastModifiedBy = "NTL\\estateadministrator";
LocalizedCategoryInstanceNames = {};
LocalizedDescription = "";
LocalizedDisplayName = "7-Zip 19.00 (x64 edition)";
LocalizedInformativeURL = "";
LocalizedPropertyLocaleID = 65535;
LogonRequirement = 0;
Manufacturer = "";
ModelID = 16777500;
ModelName = "ScopeId_6AFF9AA6-E784-4BB8-8DCF-816FCF7A7C09/Application_8e417c4c-da5d-4f1c-91af-ed63d63f9a62";
NumberOfDependentDTs = 0;
NumberOfDependentTS = 0;
NumberOfDeployments = 0;
NumberOfDeploymentTypes = 1;
NumberOfDevicesWithApp = 0;
NumberOfDevicesWithFailure = 0;
NumberOfSettings = 0;
NumberOfUsersWithApp = 0;
NumberOfUsersWithFailure = 0;
NumberOfUsersWithRequest = 0;
NumberOfVirtualEnvironments = 0;
PermittedUses = 0;
PlatformCategoryInstance_UniqueIDs = {};
PlatformType = 1;
SDMPackageVersion = 3;
SecuredScopeNames = {"Default"};
SedoObjectVersion = "9B99BA03-D0FA-417C-8BFF-6095B88AD179";
SoftwareVersion = "";
SourceCIVersion = 0;
SourceModelName = "";
SourceSite = "LAB";
SummarizationTime = "20200422125059.533000+***";
};
Is it possible that WMI class is not exposing all the columns of the database backed by this WMI class. Hence, I'm looking for the SQL DB table of SCCM DB so that I can query it directly at DB level. Can anyone help me in this regard?
Update: I also need the table which I can update to set/reset the Boolean field corresponding to the checkbox shown on UI.
The information is stored inside an XML element called SDMPackageXML in WMI. The corresponding table the console uses is fn_listApplicationCIs_List(1031) (it is also present in fn_listApplicationCIs(1031) I am at the moment not sure what the exact difference here is) where it is called SDMPackageDigest. The element is simply called "AutoInstall" and it is only present if set to true. To query it with WQL is impossible, however in a script it could be done by not using a query but a Get() on the SMS_Application Object (because SDMPackageXML is a lazy property) and then parsing the XML.
In SQL however it is possible to directly query the XML Part of a column like this:
SELECT
DisplayName,
CI_UniqueID
FROM
fn_ListApplicationCIs_List(1031) app
WHERE
app.isLatest = 1
AND
app.SDMPackageDigest.value('declare namespace p1="http://schemas.microsoft.com/SystemCenterConfigurationManager/2009/AppMgmtDigest";(p1:AppMgmtDigest/p1:Application/p1:AutoInstall)[1]', 'nvarchar(max)') = 'true'
(the isLatest is necessary to discard older versions of the application).
It is also possible to include the value in the select with that syntax, just keep in mind that it will be true for all Applications that are enabled for TS deployment and NULL for the others.
Now as for how to update. The SCCM DB should never be written to. I don't know if it would even be possible to achieve a change this way (it could be that WMI is always leading and would overwrite it), and as this is all undocumented it could be that changes have to be done at specific places or multiple places at the same time. If this has to be updated you have to resort to scripts, that can work with the lazy WMI properties. However I do not know of a way that is not dependent on SCCM specific dlls (doesn't mean there is none but I do not know how to work with XML well enough for this) so you will need Microsoft.ConfigurationManagement.ApplicationManagement.dll from the bin directory of a ConfigMgr Console Installation dir. (I wrote the code so that it would automatically find it on a computer where the Console is installed). Then you can do it like this (can of course also be wrapped in a for):
[System.Reflection.Assembly]::LoadFrom((Join-Path (Get-Item $env:SMS_ADMIN_UI_PATH).Parent.FullName "Microsoft.ConfigurationManagement.ApplicationManagement.dll"))
$app = gwmi -computer <siteserver> -namespace root\sms\site_<sitecode> -class sms_application -filter "LocalizedDisplayName='<appname>' and isLatest = 'true'"
$app.Get()
$sdmPackageXML = [Microsoft.ConfigurationManagement.ApplicationManagement.Serialization.SccmSerializer]::DeserializeFromString($app.SDMPackageXML, $true)
$sdmPackageXML.AutoInstall = $true
$app.SDMPackageXML = [Microsoft.ConfigurationManagement.ApplicationManagement.Serialization.SccmSerializer]::SerializeToString($sdmPackageXML, $true)
$app.Put()
The nice thing is that this deserialization always presents us with an AutoInstall property even if it is not present in the xml because it was written for sccm so we can just set it true/false as we want.
The reason we need the .dll is the serialization. Deserialisation can be done with a simple cast to [xml] as well but I am not sure how it could be serialized again. If this can be done there is no need for external dlls. (However the xml manipulation is less easy).
If you run this code on a machine with the sccm console anyway you could also skip the wmi part and use Get-CMApllication from the sccm ps commandlets (contains SDMPackageXML as well) however while the dll can be moved to any computer, the cmdlets are only installed with the console so I wrote the sample without them.
I am new to vtiger crm and need a code to add the dropdown that has values from the database table in add lead page.
Please provide a solution if somebody have ?
You can add drop-down field by using bellow code and follow the steps to achieve your result:
Add bellow code in one PHP file (e.g add_to_lead.php).
Put that file into your project directory.
Run that file from browser (e.g www.yourVtigerhost.com/add_to_lead.php)
$Vtiger_Utils_Log = true;
include_once('vtlib/Vtiger/Menu.php');
include_once('vtlib/Vtiger/Module.php');
$module = new Vtiger_Module();
$module = $module->getInstance('Leads');
// Create new Block into Lead Module and your drop-down added into new block
$block1 = new Vtiger_Block();
$block1->label = 'LBL_LEAD_INFORMATION';
$block1 = $block1->getInstance($block1->label,$module);
$field0 = new Vtiger_Field();
$field0->name = 'your field name';
$field0->table = $module->basetable;
$field0->label = 'Your field Name to display';
$field0->column = 'field_name';
$field0->columntype = 'VARCHAR(100)';
$field0->uitype = 15;
$field0->setPicklistValues( Array ('Dropdown Value1','Dropdown Value2','Dropdown Value3'));
$field0->typeofdata = 'V~O';
$block1->addField($field0);
New Dropdown have values like Dropdown Value1,Dropdown Value2,Dropdown Value3
If you want to add more values into dropdown than you can add from Setting-> Studio->Picklist Editor.
Now I'm developing a project about softlayer api. I wan't to get the os list by softlayer api. Just like the portal site. Is there certain method to get correct os list ? regards~
Is there a specific language example you are looking for? If you use the SoftLayer CLI you can do this with the following command
slcli vs create-options # For Virtual Guests
slcli server create-options # For Bare Metal Servers
Unfortunately, it's not possible to retrieve the same result than Control Portal making a single call, but it's possible using a programming language.
To see programming languages supported by SoftLayer:
SoftLayer Development Network
Take a look the following python script:
"""
List OSs for VSI similar than Portal
See below references for more details.
Important manual pages:
http://sldn.softlayer.com/reference/services/SoftLayer_Product_Package/getItemPrices
http://sldn.softlayer.com/article/object-filters
http://sldn.softlayer.com/article/object-Masks
#License: http://sldn.softlayer.com/article/License
#Author: SoftLayer Technologies, Inc. <sldn#softlayer.com>
"""
import SoftLayer
import datetime
import time
# Your SoftLayer's username and api Key
USERNAME = 'set me'
API_KEY = 'set me'
# Package id
packageId = 46
# Datacenter
datacenter = 'wdc04'
# Computing INstance
core = '1 x 2.0 GHz Core'
# Creating service
client = SoftLayer.Client(username=USERNAME, api_key=API_KEY)
packageService = client['SoftLayer_Product_Package']
# Declaring filters and mask to get additional information for items
filterDatacenter = {"itemPrices": {"pricingLocationGroup": {"locations": {"name": {"operation": datacenter}}}}}
objectMaskDatacenter = 'mask[pricingLocationGroup[locations]]'
objectMask = 'mask[pricingLocationGroup[locations],categories,item[id, description, capacity,softwareDescription[manufacturer],availabilityAttributeCount, availabilityAttributes[attributeType]]]'
filterInstance = {
'itemPrices': {
'categories': {
'categoryCode': {
'operation': 'os'
}
}
}
}
# Define a variable to get capacity
coreCapacity = 0
# To get item id information
itemId = 0
flag = False
# Define the manufacturers from which you like to get information
manufacturers = ["CentOS", "CloudLinux", "CoreOS", "Debian", "Microsoft", "Redhat", "Ubuntu"]
# Declare time to avoid list OS expired
now = time.strftime("%m/%d/%Y")
nowTime = time.mktime(datetime.datetime.strptime(now, "%m/%d/%Y").timetuple())
try:
conflicts = packageService.getItemConflicts(id=packageId)
itemPrices = packageService.getItemPrices(id=packageId, filter=filterDatacenter, mask=objectMask)
if len(itemPrices) == 0:
filterDatacenter = {"itemPrices":{"locationGroupId":{"operation":"is null"}}}
itemPrices = packageService.getItemPrices(id=packageId, filter=filterDatacenter, mask=objectMask)
for itemPrice in itemPrices:
if itemPrice['item']['description'] == core:
itemId = itemPrice['item']['id']
coreCapacity = itemPrice['item']['capacity']
result = packageService.getItemPrices(id=packageId, mask=objectMask, filter=filterInstance)
filtered_os = []
for item in result:
for attribute in item['item']['availabilityAttributes']:
expireTime = time.mktime(datetime.datetime.strptime(attribute['value'], "%m/%d/%Y").timetuple())
if ((attribute['attributeType']['keyName'] == 'UNAVAILABLE_AFTER_DATE_NEW_ORDERS') and (expireTime >= nowTime)):
filtered_os.append(item)
if item['item']['availabilityAttributeCount'] == 0:
filtered_os.append(item)
for manufacturer in manufacturers:
print(manufacturer)
for itemOs in filtered_os:
for conflict in conflicts:
if (((itemOs['item']['id'] == conflict['itemId']) and (itemId == conflict['resourceTableId'])) or ((itemId == conflict['itemId']) and (itemOs['item']['id'] == conflict['resourceTableId']))):
flag = False
break
else:
flag = True
if flag:
if itemOs['item']['softwareDescription']['manufacturer'] == manufacturer:
if 'capacityRestrictionMinimum' in itemOs:
if((itemOs['capacityRestrictionMinimum'] <= coreCapacity) and (coreCapacity <= itemOs['capacityRestrictionMaximum'])):
print("%s Price Id: %s Item Id: %s" % (itemOs['item']['description'], itemOs['id'], itemOs['item']['id']))
else:
print("%s Price Id: %s Item Id: %s" % (itemOs['item']['description'], itemOs['id'], itemOs['item']['id']))
print("---------------------------------------------------")
except SoftLayer.SoftLayerAPIError as e:
print('Unable to get Item Prices faultCode=%s, faultString=%s'
% (e.faultCode, e.faultString))
I added core variable, because the OSs have restriction for capacity of cores. Also I added datecenter to get the specific core item price for a specifc datacenter, perhaps it's something innecesary, but you can edit this script according your requirements.
The same idea could be applied for others programming languges.
I hope it helps, please let me know any doubt, comments or if you need further assistance.
Updated
I improved the script, I added the ability to check conflicts between items, in order to get the same result for each kind of Computing Instance
I'm trying to get the value of a key in the URL (localhost:8080?color=red) and display different pages according to what value is in the url (red or blue...etc). I'm not sure how to set that up, though, because nothing I've tried works. Any ideas? It's for a class assignment, so I can't use query_string.
if self.request.GET(['color','red']):
view = ContentPage()
fetch_data = Data()
name = fetch_data.red.name
description = fetch_data.red.description
self.response.write(view.print_first() + name + description + view.print_end())
else:
see = Page()
self.response.write(see.output())
Use self.request.get, like this:
color = self.request.get('color')
# do something with color
Hopefully someone here is familiar with creating customizations in Epicor 9. I've posted this to the Epicor forums as well, but unfortunately that forum seems pretty dead. Any help I can get would be much appreciated.
I've created a customization on the Order Entry form to display and store some extra information about our orders. One such field is the architect on the job. We store the architects in the customer table using a GroupCode of AR to distinguish them from regular customers. I have successfully added a button that launches a customer search dialog and filters the results to only display the architects (those with GroupCode AR). Here's where the problems come in. I have two questions:
1: On the customer search, there is a customer type field that defaults to a value of Customer. Other choices are < all>, Suspect, or Prospect. How can I make the search form default to < all>?
2: How do I take the architect (customer) I select through the search dialog and populate its CustID into the ShortChar01 field on my Order Entry customization? Here's the code I have:
private void SearchOnCustomerAdapterShowDialog()
{
// Wizard Generated Search Method
// You will need to call this method from another method in custom code
// For example, [Form]_Load or [Button]_Click
bool recSelected;
//string whereClause = string.Empty;
string whereClause = "GroupCode = 'AR'";
System.Data.DataSet dsCustomerAdapter = Epicor.Mfg.UI.FormFunctions.SearchFunctions.listLookup(this.oTrans, "CustomerAdapter", out recSelected, true, whereClause);
if (recSelected)
{
System.Data.DataRow adapterRow = dsCustomerAdapter.Tables[0].Rows[0];
// Map Search Fields to Application Fields
EpiDataView edvOrderHed = ((EpiDataView)(this.oTrans.EpiDataViews["OrderHed"]));
System.Data.DataRow edvOrderHedRow = edvOrderHed.CurrentDataRow;
if ((edvOrderHedRow != null))
{
edvOrderHedRow.BeginEdit();
edvOrderHedRow["ShortChar01"] = adapterRow["CustID"];
edvOrderHedRow.EndEdit();
}
}
}
When I select a record and click OK, I get an unhandled exception.
I think the problem you are/were having is that you aren't adding the CustNum to the Sales Order first. In my mind I would do it this way first, but there is might be ChangeCustomer BO method in oTrans that you could call to make sure everything defaults correct.
EpiDataView edvOrderHed = ((EpiDataView)(this.oTrans.EpiDataViews["OrderHed"]));
if (edvOrderHed.HasRow)
{
edvOrderHed[edvOrderHed.Row].BeginEdit();
edvOrderHed[edvOrderHed.Row]["CustNum"] = adapterRow["CustNum"];
edvOrderHed[edvOrderHed.Row]["ShortChar01"] = adapterRow["CustID"];
edvOrderHed[edvOrderHed.Row].EndEdit();
}
Hope that is helpful, even if late.