The eiffel_from_python sample application

The sample application for this creates an Eiffel class, CALLED_FROM_PYTHON, and exports it to Python. The object is manipulated by a Python script in test_module.py, which is exported to Eiffel. The actual Eiffel program, a TEST object, creates the Eiffel CALLED_FROM_PYTHON object and passes it to the test_module.py script, a bizarre three-way shuffle that works fairly seamlessly.

Unfortunately, we are now getting to the point where the Makefile used to generate the sample program is already larger than all the source combined. It contains many peculiar-looking targets which automate the manufacture of automatically-generated code, the eiffel_gluemodule.so file, and many other temporaries, and is worth a look to really understand what is going on in this example; you can find it in the production/examples/eiffel_from_python file. Only the three source code files are listed below:

Example 11-11. The eiffel_from_python test application

The CALLED_FROM_PYTHON Eiffel class

class CALLED_FROM_PYTHON
   
creation   
   make
   
feature   
   
   make is
      --dummy creation feature
      do
      end
   
   print_message is
      do
	 std_output.put_string( "Hello, calling-eiffel-from-python world!%N" )
      end
   
   print_integer_addition( a, b : INTEGER ) is
      do
	 std_output.put_string( a.to_string + " + " + b.to_string + "=" + (a+b).to_string )
      end
   
end   

The test_module.py Python module

__doc__ = """

Exists only to test our ability to call Eiffel methods from Python.

"""

import eiffel_glue
import python_shadows

def test_eiffel_call( eiffel_object_pointer ) :
    t = python_shadows.eiffel_CALLED_FROM_PYTHON( eiffel_object_pointer )
    print "The following is output from an eiffel object\nscripted by a Python shadow class:"
    t.print_message()
    t.print_integer_addition( 1, 42 )
    print "\n"
    

The TEST Python class

class TEST
   
inherit
   PYTHON_CLIENT
   
creation
   make
   
feature
   
   make is
      local
	 test_module : TEST_MODULE
	 a : CALLED_FROM_PYTHON
	 r : PYTHON_OBJECT
	 i : INTEGER
	 p : POINTER
	 s : STRING
      do
	 initialize_python
	 i := py_run_simple_string( "import sys" )
	 i := py_run_simple_string( "sys.path.append( '.' )" )
	 create test_module.make
	 create a.make
	 r := test_module.test_eiffel_call( << swig_pointer_string( a ) >> )
      rescue
	 if py_err_occurred.is_not_null then
	    py_err_print
	 end
      end
	 
end

                               
                                

And when run, produces the following output:
[vputz@yak_prime eiffel_from_python]$ ./test
The following is output from an eiffel object
scripted by a Python shadow class:
Hello, calling-eiffel-from-python world!
1 + 42=43

[vputz@yak_prime eiffel_from_python]$