In a earlier script we looked at using the command line tool sddesc from Chemical Computing Group to calculate a number of molecular descriptors and then import them into Vortex. However there a couple of issues with doing this not the least ensuring all the environment variables are set correctly. An alternative is to use MOE as a web service and access the tools using the SOAP protocol (Simple Object Access Protocol). This protocol provides a specification for exchanging structured information in the implementation of Web Services in computer networks. It relies on XML Information Set for its message format.
The MOE Web Server
You can start the MOE web server using the following command in a Terminal window
1 2 |
prompt$ /Applications/moe2012/bin/moeweb |
You should get a list of information including the IP address of the server and the port you need to address (usually port 8888)
You should also get a list of very useful web pages
1 2 3 4 5 6 7 8 |
YellowPages results now available: (1): [soap] DataTypes (2): [soap] DepictionLayout (3): [soap] MedChemProps (4): [soap] MolToSMILES (5): [soap] SMILESToMol (6): [soap] Version |
If you now open a web browser and go to
1 2 |
http://localhost:8888/soap.html |
You will get a web page giving a list of the available functions.
If like me you are not particularly familiar with constructing SOAP queries then these pages are invaluable. Select the SMILESToMol hyperlink and you should get the page below. Fill in a valid SMILES string and click on the “Preview SOAP Request” button and you can see the syntax of the expected SOAP request and this is what we will be included in the Vortex script as the SOAP request.
The MolToSMILES script
To start with I thought I’d create a script that retrieves the SMILES string from the web server, mainly because it avoids the complication of trying to parse the returned XML if there are multiple properties. We do however need to import an XML parsing library. The Element type is a flexible container object, designed to store hierarchical data structures in memory. The type can be described as a cross between a list and a dictionary, XML is an inherently hierarchical data format, and the most natural way to represent it is with a tree.
1 2 |
import xml.etree.ElementTree as ET |
The first part just allows the user to confirm that they are not posting proprietary information to an external web service. We then get the structure as a MOL file.
1 2 |
mymol = vortex.getMolProperty(mfm.getMolFileAtRow(r), 'MOL') |
Then we construct the SOAP request, we need the URL we are posting to and the data wrapped in the SOAP request format taken from the appropriate MOE SOAP function web page.
We then perform the request
1 2 3 |
request = urllib2.Request(url, data, headers=headers) contents = urllib2.urlopen(request).read() |
We then need to create a column in Vortex, and then parse the data, since there is only the SMILES string returned this is fairly straight-forward with help from Matt. The XML response from the MOE server is parsed using the python ElementTree module. This module parses an XML string using ET.fromstring()
into a hierarchical tree data structure that allows us to easily pick out various values in the response. In this case, the desired value is just the text within a tag named “smiles”, which can be found using a relatively simple XPath query:
mysmiles = root.find(‘.//smiles’)
This query recursively searches through the tree and returns the first element with the tag “smiles” that it finds. The text contents of that element is given by mysmiles.text
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 |
# Using MOE via a web service this uses a local copy of MOE # import sys import com.dotmatics.vortex.util.Util as Util if Util.getPlatform() == Util.PlatformIsWindows: sys.path.append(vortex.getVortexFolder() + '\\modules\\jythonconsole') sys.path.append(vortex.getVortexFolder() + '\\modules\\jythonlib') else: sys.path.append(vortex.getVortexFolder() + '/modules/jythonconsole') sys.path.append(vortex.getVortexFolder() + '/modules/jythonlib') import urllib2 import urllib import xml.etree.ElementTree as ET content = javax.swing.JPanel() label = javax.swing.JLabel("<html><b>Make sure this uses a local web service</b><p><br>If you don't want to post your data to the internet press Cancel.</html>") layout.fill(content, label, 2, 2) ret = vortex.showInDialog(content, "MOE Web Service") if ret == vortex.OK: mfm = vtable.getMolFileManager() rows = vtable.getRealRowCount() for r in range(0, rows): mymol = vortex.getMolProperty(mfm.getMolFileAtRow(r), 'MOL') url ='http://yourserver.local:8888/soap/MolToSMILES' data = '''<?xml version="1.0"?> <SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"> <SOAP-ENV:Body> <InputType> <molecule><![CDATA[%s]]></molecule> </InputType> </SOAP-ENV:Body> </SOAP-ENV:Envelope>''' % mymol headers = { 'Content-Type': 'text/html', 'Content-Length': len(data) } request = urllib2.Request(url, data, headers=headers) contents = urllib2.urlopen(request).read() # Create new columns in table if needed column = vtable.findColumnWithName('SMILES', 1, 3) vtable.fireTableStructureChanged() # Parse response root = ET.fromstring(contents) if root.tag == 'error': print 'Error from MOE server:' print root.text else: mysmiles = root.find('.//smiles') if mysmiles is not None: column = vtable.findColumnWithName('SMILES', 1, 3) column.setValueFromString(r, mysmiles.text) print mysmiles.text else: print 'Could not parse response:' print contents vtable.fireTableStructureChanged() |
The result of running this script is a new column called SMILES, and because Vortex is smart enough to realise what the contents are the SMILES strings get automatically rendered as 2D images.
You can download the script from here
Last updated May 2013