NEOS Server XML-RPC API

Users can submit jobs to and retrieve results from NEOS using NEOS's XML-RPC application programming interface. NEOS runs an XML-RPC server that can communicate with clients written in a variety of languages including C, C++, Java, Perl, PHP, Python, and Ruby. Any job submitted to NEOS using XML-RPC must be in the XML format required by the selected solver. Each solver's format is specified on the solver's interface page. From the list of available solvers, click on appropriate interface page and follow the "XML-RPC" link in the box in the top right corner of the page.

July 13, 2016: In order to conform with modern security standards, the NEOS Server will be switching from HTTP submissions to HTTPS submissions. Please update your client programs with the new URL for the NEOS XML-RPC server to avoid submission problems.

Contents

Example of XML Format Specification

Suppose you want to submit a nonlinearly constrained optimization problem to KNITRO using AMPL as the input method.

  1. From the list of solvers, go to the Nonlinearly
    Constrained Optimization
    section and click on KNITRO[AMPL Input].
  2. Notice the box labeled NEOS Interfaces to KNITRO in the upper right hand corner of the page. Click on XML-RPC.
  3. The KNITRO-AMPL XML-RPC page provides a template for an XML submission:
    <document>
        <category>nco</category>
        <solver>KNITRO</solver>
        <inputMethod>AMPL</inputMethod>
    
        <model><![CDATA[
        ...Insert Value Here...
        ]]></model>
    
        <data><![CDATA[
        ...Insert Value Here...
        ]]></data>
    
        <commands><![CDATA[
        ...Insert Value Here...
        ]]></commands>
    
        <comments><![CDATA[
        ...Insert Value Here...
        ]]></comments>
    
        </document>
    
  4. Once you have a XML description of the problem, you can use the NEOS XML-RPC API to submit the job.

Back to top

NEOS XML-RPC Application Programming Interface (API)

In this section, we document the NEOS XML-RPC API, the set of functions and routines to get information from NEOS,
to submit jobs to NEOS and to retrieve results from NEOS, and to maintain a solver on NEOS.


Routines for getting information from NEOS


help()
emailHelp()
Returns general help message for email users.
welcome()
Returns a welcome message.
version()
Returns the version number of the NEOS Server as a string.
ping()
Verifies that the NEOS Server is running. Returns the message 'NEOS Server is alive'.
printQueue()
Returns a string with a list of the current jobs on NEOS.
getSolverTemplate(category, solvername, inputMethod)
Returns a template for the requested solver. If the solver category:solvername:inputMethod exists on
NEOS, then this function returns an XML template to use when submitting jobs via XML-RPC or email.
getXML(category, name, input)
Returns the XML description of the requested solver. This function will be deprecated. Use
getSolverTemplate(category, solvername, inputMethod).
listAllSolvers()
Lists all of the solvers available on NEOS, formatted as category:solver:inputMethod.
listCategories()
Lists all of the solver categories available on NEOS, formatted as a dictionary with entries {'abbreviated
name':'full name',...}
.
listSolversInCategory(category)
Lists all of the NEOS solvers in the specified category, formatted as solver:input. The category can be
the full name or the abbreviation.

Back to top


Routines for submitting jobs and retrieving results from NEOS


submitJob(xmlstring, user='', interface='', id=0)
Submits an optimization job to NEOS. This method will return a tuple (jobnumber,password). Use the job
number and password to get the results, or the status, of a job using the methods getStatus(),
getIntermediateResults(), and getFinalResults(). If there is an error (e.g., NEOS job queue is full),
submitJob() will return the tuple (0, errormessage). For more information on the format of the
xmlstring argument, you can use the getSolverTemplate() function.
authenticatedSubmitJob(xmlstring, username, password)
Exactly the same as submitJob() except with user's credentials.
getJobStatus(jobNumber, password)
Gets the current status of the job. Returns "Done", "Running", "Waiting", "Unknown Job", or "Bad Password".
getJobInfo(jobNumber, password)
Gets information on the job. Returns a tuple (category, solver_name, input, status).
killJob(jobNumber, password, killmsg='')
Cancels a job submission that is running, or waiting to run, on NEOS. The job password is required to prevent
abuse of this function.
getFinalResults(jobNumber, password)
Gets results of a job submitted to NEOS. If the job is still running, then this function will hang until the job
is finished. The function returns a base-64 encoded object. Please read your XML-RPC client documentation for
information on how to decode. (For Python's xmlrpclib library, you can use the object's 'data' data member.)
getIntermediateResults(jobNumber, password, offset)
Gets intermediate results of a job submitted to NEOS, starting at the specified character offset up to the last
received data. Intermediate results are usually the standard output of the solver daemon. Note that because
output does not stream for jobs with "long" priority (default value), getIntermediateResults() will not
return any results for long priority jobs. Output does stream for jobs with "short" priority (maximum time
of 5 minutes).

If the job is still running, then this function will hang until another packet of output is sent to NEOS or the
job is finished. This function will return a tuple of the base-64 encoded object and the new offset (object,
newoffset). The offset refers to uncoded characters. Please read your XML-RPC client documentation for
information on how to decode. (For Python's xmlrpclib library, you can use the object's 'data' data member.)

getFinalResultsNonBlocking(jobNumber, password)
Gets results of a job submitted to NEOS (non-blocking), returned as a base-64 encoded object. If the job is
still running, then this function will return an empty string (base-64 encoded). Please read your XML-RPC client
documentation for information on how to decode. (For Python's xmlrpclib library, you can use the object's 'data'
data member.)
getIntermediateResultsNonBlocking(jobNumber, password, offset)
Gets intermediate results of a job submitted to NEOS, returned as a base-64 encoded object and the new offset.
The offset refers to the uncoded characters. Intermediate results are usually the standard output of the solver
daemon. Note that because output does not stream for jobs with "long" priority (default value),
getIntermediateResults() will not return any results for long priority jobs. Output does stream for jobs
with "short" priority (maximum time of 5 minutes).

Please read your XML-RPC client documentation for information on how to decode. (For Python's xmlrpclib library,
you can use the object's 'data' data member.)

Back to top


Routines for maintaining solvers on NEOS


pingHost(user, hostname)
Verifies a solver daemon. Returns a confirmation message, 'OK', if there is a solver daemon running on the host
under the user's account. Otherwise, returns an error message.
validateSolverXML(xmlString)
Checks the syntax of the solver XML description. Returns 'OK' or an error message. Prior to submitting a solver
description to NEOS, use this method to check if the syntax is correct.
registerSolver(xmlString)
Registers a new solver on NEOS. If you would like to make your solver available, please contact us.
Documentation for the steps to register a new solver are found here.
removeSolver(category, solvername, input, password)
Removes a solver from NEOS. To temporarily disable a solver, use the disableSolver() method instead.
disableSolver(category, solvername, input, password)
Temporarily disables a solver on NEOS. Removes the solver from the NEOS solvers index. Users who attempt to use
the solver will receive a message that it has been disabled. To reenable the solver, use the enableSolver()
method.
enableSolver(category, solvername, input, password)
Reenables a solver that has been disabled. To register a new solver, use the registerSolver() method.
registerExample(xmlstring, password)
Registers an example on the NEOS Server web pages. This function will upload an example (provided in the
xmlstring argument) to the NEOS Server web page for the specified solver.
removeExample(category, solvername, input, passwd, examplename)
Removes an example from the NEOS Server web pages. This function will remove the example (specified in the
examplename argument) from the NEOS Server web page for the solver specified in the solvername argument.

Back to top

Writing a Python Client

The Python script included below shows how to submit a job to NEOS and how to print the results to the console. To run the script, type
./NeosClient.py job.xml
where
job.xml is the name of the file that contains the XML description of the job in the format required by the solver. To generate the job XML, there are two options:

  • Go to the solver's interface page and click on the "XML-RPC" link in the box in the top right hand corner of the
    page. Create a file that follows the template for the solver.
  • Go to the solver's interface page and upload your input files as if you were doing a web submission. Then, at
    the bottom of the page, check the box that says "Dry run: generate job XML instead of submitting it to NEOS" and
    click the button that says "Submit to NEOS". Copy the XML code that is returned into a file.

Also, there is a Python client NeosClient.py included in the NEOS Server Client Tools package.


#!/usr/bin/env python

#########################################

# NeosClient.py

#########################################

import sys

import xmlrpclib

import time


NEOS_HOST="neos-server.org"

NEOS_PORT=3333



if len(sys.argv) != 2:

  sys.stderr.write("Usage: NeosClient <xmlfilename | queue> ")

  sys.exit(1)



neos=xmlrpclib.Server("https://%s:%d" % (NEOS_HOST, NEOS_PORT))



if sys.argv[1] == "queue":

  #Print NEOS job queue

  msg = neos.printQueue()

  sys.stdout.write(msg)



else:

  #Read XML file

  xmlfile = open(sys.argv[1],"r")

  xml=""

  buffer=1

  while buffer:

    buffer =  xmlfile.read()

    xml+= buffer

  xmlfile.close()



  (jobNumber,password) = neos.submitJob(xml)

  sys.stdout.write("JobNumber = %d " % jobNumber)



  offset=0

  status=""

  #Print out partial job output while job is running

  while status != "Done":

    (msg,offset) = neos.getIntermediateResults(jobNumber,password,offset)

    sys.stdout.write(msg.data)

    status = neos.getJobStatus(jobNumber, password)

 

  #Print out the final result

  msg = neos.getFinalResults(jobNumber, password).data

  sys.stdout.write(msg)

Back to top

Writing a Python 3 Client

There is a Python 3 client NeosClient.py included in the NEOS Server Client Tools package.


#!/usr/bin/env python3
#########################################
# NeosClient.py
#########################################
import sys
import xmlrpc.server
import xmlrpc.client

# Check that the arguments are supplied
if len(sys.argv) != 2:
    sys.stderr.write("Usage: NeosClient  ")
    sys.exit(1)

NEOS_HOST="neos-server.org"
NEOS_PORT=3333

# Connect to NEOS
neos = xmlrpc.client.ServerProxy("https://%s:%d" % (NEOS_HOST, NEOS_PORT))

# Verify the connection was successful
test = neos.ping()
if neos.ping() != "NeosServer is alive\n":
    sys.stderr.write("Could not make connection to the NEOS server")
    sys.exit(1)

if sys.argv[1] == "queue":
    # Print NEOS job queue
    msg = neos.printQueue()
    sys.stdout.write(msg)

else:
    xml = ""

    # Try to read the XML file
    try:
        xmlfile = open(sys.argv[1], "r")
        buffer = 1
        while buffer:
            buffer = xmlfile.read()
            xml += buffer
        xmlfile.close()
    except (FileNotFoundError, FileExistsError, IOError):
        sys.stderr.write("The file was not found or does not exist")
        sys.exit(1)

    # Submit the optimization problem to NEOS
    (jobNumber, password) = neos.submitJob(xml, Variables.CONTACT_EMAIL, 0)
    sys.stdout.write("JobNumber = %d \n" % jobNumber)

    # Check to make sure the queue is not full
    if jobNumber == 0:
        sys.stderr.write("NEOS error: %s" % password)
        sys.exit(1)
    else:
        offset = 0
        status = ""
        # Print out partial job output while job is running
        while status != "Done":
            (msg, offset) = neos.getIntermediateResults(jobNumber, password, offset)
            sys.stdout.write(msg.data.decode())
            status = neos.getJobStatus(jobNumber, password)

        # Print out the final result
        msg = neos.getFinalResults(jobNumber, password).data
        sys.stdout.write(msg.decode())


Writing a Java Client

If you want to write a Java application to submit jobs to NEOS via XML-RPC, there are two packages available to facilitate the process:

  • org.neos.client: contains methods to submit jobs to NEOS and retrieve results
  • org.neos.gams: contains methods to facilitate the input and output processing of GAMS jobs

For more information about the packages and/or to download them, see the Writing a Java Client page.

Back to top