Difference between revisions of "VBA"

From Apache OpenOffice Wiki
Jump to: navigation, search
Line 4: Line 4:
  
 
=== Latest News ===
 
=== Latest News ===
 +
* Update Wiki Page with latest info
 
* Novell and Sun to work together on the VBA incubator project more info [http://blogs.sun.com/GullFOSS/entry/sun_and_novell_work_together here]
 
* Novell and Sun to work together on the VBA incubator project more info [http://blogs.sun.com/GullFOSS/entry/sun_and_novell_work_together here]
 
* I am delighted that Andreas Bregas now joins me to co-lead the vba incubator project
 
* I am delighted that Andreas Bregas now joins me to co-lead the vba incubator project
 
* cws [http://eis.services.openoffice.org/EIS2/cws.ShowCWS?Path=SRC680%2Fnpower6 npower6] will contain the initial code drop
 
* cws [http://eis.services.openoffice.org/EIS2/cws.ShowCWS?Path=SRC680%2Fnpower6 npower6] will contain the initial code drop
  
=== How to enable the VBA model ===
+
=== Terminology ===
 +
In this page we talk alot about the 2 vba interopability solutions, I'd like to distinguish between them with simple terms ( The vba solution formally known as Sun's migration tools api etc. is quite a mouthful ) so forever more in the text below I will refer to
  
The VBA model is enabled by default in the current ooo-build. It's enough to [[Getting It|get]], [[Building with ooobuild|build]], [[Installing|install]], and [[Running|be able to run]] it.
+
* helperapi - The compatibility api generously donated by Sun that was part of their migration toolkit
 +
* oovbaapi - the ooo-build vba interoperabiltiy solution that soon will incorporate object implementations from the helperapi
  
=== How to disable the VBA model ===
+
=== Dashboard ===
 +
* cws [http://eis.services.openoffice.org/EIS2/cws.ShowCWS?Path=SRC680%2Fnpower6 npower6] approaching 'Ready For QA status'
 +
* cws [http://eis.services.openoffice.org/EIS2/cws.ShowCWS?Path=SRC680%2Fnpower7 npower7] created
  
Not Known.  Please document the process for disabling this "feature".  There are many people, particularly since the Novell/Microsoft deal, who are both wary of the potential for tainting Open Source software and wary of the possibility of allowing harmful code to run.
+
=== How to enable the VBA model ===
  
It would be far better not to have this code on a machine where it is not required and not run the potential risks, than have it on the machine with the possibility of having interlocks bypassed by malicious code which could then use it.
+
The VBA model is enabled by default in the current ooo-build. It's enough to [[Getting It|get]], [[Building with ooobuild|build]], [[Installing|install]], and [[Running|be able to run]] it.  
  
=== How can I help you? ===
+
If you are using upstream Openoffice and wish to play with this feature then check out and build the cws [http://eis.services.openoffice.org/EIS2/cws.ShowCWS?Path=SRC680%2Fnpower6 npower6] which contains the initial code drop for the oovbaapi
  
We need help in a couple of areas - Upstreaming, understanding the VBA usage patterns, implementation and testing; see below.
+
=== How to disable the VBA model ===
  
== Upstreaming ==
+
Depending on how your version of Openoffice delivers the VBA feature to you there are a number of ways to disable it.
  
Ideally we would like this work to be integrated upstream so that its easier to work on, easier to maintain and benifits the maximum amount of users. We'll need your support to kick start this, imagine native support for VBA macros from OpenOffice, it would be great to see that barrier to OpenOffice migration lowered if not lifted entirely.
+
If you have an Openoffice build from a linux distro ( or a windows one from Novell ) that has the vba interop feature all you need do is navigate to the 'Tools.Options.Load/Save.VBAProperties' page and uncheck the 'Load Excelbasic code to edit' option.
  
For the purposes of up-streaming the work really breaks down into a small set of changes to the core basic code - to support the various core features; and then a much larger set of UNO interfaces and implementations of a compatible Object Model.
+
If you are using an own build ( incorporating ) [http://eis.services.openoffice.org/EIS2/cws.ShowCWS?Path=SRC680%2Fnpower6 cws-npower6] the above method will always work. But if you built the vba interop feature as an office extension then you can of course disable or delete the vbaapi.oxt extension using the Extension Manager.
  
=== Core Changes ===
+
=== How can I help you? ===
  
Recently we have moved almost the entirety of the vba patches from [http://www.go-ooo.org ooo-build] into issuezilla.
+
We need help in a couple of areas - porting object from the helperapi, understanding the VBA usage patterns, implementation and testing; see below.
  
 
{|
 
{|
Line 52: Line 57:
  
 
This is not an exhaustive list, but gives some of the most critical pieces to get up-stream.
 
This is not an exhaustive list, but gives some of the most critical pieces to get up-stream.
 
=== Object Model bits ===
 
 
This patch set is far larger, and is bracketed under a single issue: [http://www.openoffice.org/issues/show_bug.cgi?id=68883 68883], the patches are in the ooo-build
 
[http://www.go-ooo.org/ooo-build/patches/vba vba] directory.
 
  
 
== Understanding the VBA usage patterns ==
 
== Understanding the VBA usage patterns ==
Line 94: Line 94:
 
==== Add an extension to the IDL ====
 
==== Add an extension to the IDL ====
  
The IDL lives in offapi/org/openoffice/vba/*, the IDL syntax can easily be gleaned from a few other IDL files. Two things are worth bearing in mind:
+
The IDL lives in oovbaapi/org/openoffice/*, the IDL syntax can easily be gleaned from a few other IDL files. Two things are worth bearing in mind:
 
* it's important that the argument names are correct, so that the <tt>MsgBox title:="hello"</tt> syntax works correctly.
 
* it's important that the argument names are correct, so that the <tt>MsgBox title:="hello"</tt> syntax works correctly.
 
* for optional arguments, or variant types you need to use the <tt>any</tt> type
 
* for optional arguments, or variant types you need to use the <tt>any</tt> type
  
 
Having edited the IDL extension you need to:
 
Having edited the IDL extension you need to:
* run: <tt>build && deliver</tt> in offapi (perhaps remove types.db first),
+
* run: <tt>build && deliver</tt> in oovbaapi (perhaps remove types.db first),
* run: <tt>build && deliver</tt> in the offuh toplevel directory. (This (re-)compiles C++ headers etc. for that interface).
+
  
 
==== Add the extension to the implementation ====
 
==== Add the extension to the implementation ====
  
 
The impl. code lives in <tt>sc/source/ui/vba/</tt> - find the right header &amp;amp;amp; source files.
 
The impl. code lives in <tt>sc/source/ui/vba/</tt> - find the right header &amp;amp;amp; source files.
Add the method (with the correct prototype) to the header - often it's easiest to cut/paste that from the compiled C++ headers in <tt>solenv/*/*/inc/org/openoffice/vba/</tt>
+
Add the method (with the correct prototype) to the header - often it's easiest to cut/paste that from the compiled C++ headers in <tt>sc/unxlngixxx/inc/org/openoffice/vba/</tt>
  
 
Then implement the method itself in the .cxx file. Run <tt>build debug=true</tt>
 
Then implement the method itself in the .cxx file. Run <tt>build debug=true</tt>
 
==== Add new constants to the IDL ====
 
 
VBA has alot of constants, we need help implementing similar constants in our api, implementing VBA constants is easy and would be a good place to start if you want to make an immediate contribution and learn about the project at the same time. To see the values and names for the VBA constants just open the "Object Browser" from the Visual Basic IDE, search for constants and you'll find 'em. Look in <tt>offapi/org/openoffice/vba/*/*</tt> to see whats missing (lots!!) Create a new IDL file for each "class" of constants, use <tt>offapi/org/openoffice/vba/Excel/XlCellType.idl</tt> as an example. The steps for building and adding the new constants is the same as described above for a extension, the only difference is that there are no source files to create :-)
 
  
 
==== Running it ====
 
==== Running it ====
Line 117: Line 112:
 
You did use [linkoo] right ? - in which case - just re-run soffice.bin (killall -9 soffice.bin first to ensure there is no lurking factory process).
 
You did use [linkoo] right ? - in which case - just re-run soffice.bin (killall -9 soffice.bin first to ensure there is no lurking factory process).
  
Now of course - you want to add a new test to exercise it to ooo-build/test/macro/*. And of course loop back to the begginning.
+
Now of course - you want to add a new test to exercise it to ooo-build/test/macro/*. And of course loop back to the beginning.
 
Once you've got something you want to share - a simple <tt>cvs diff -u | tee /tmp/foo.diff</tt> in ooo-build/scratch will yield a patch you can mail to Noel / the ooo-build mailing list to get your code folded in.
 
Once you've got something you want to share - a simple <tt>cvs diff -u | tee /tmp/foo.diff</tt> in ooo-build/scratch will yield a patch you can mail to Noel / the ooo-build mailing list to get your code folded in.
 
NB. it's important you sign the [http://www.openoffice.org/licenses/jca.pdf JCA] first.
 
NB. it's important you sign the [http://www.openoffice.org/licenses/jca.pdf JCA] first.
 
=== The scratch directory ===
 
 
  It's quite difficult to generate patches over already patched tree thus we have the ''ooo-build/scratch'' directory. Read the [http://cvs.gnome.org/viewcvs/ooo-build/scratch/README?view=markup ''ooo-build/scratch/README''] file to understand how the ''scratch'' directory works.
 
  Then run <code>scratch/place /root-of-working-copy-of-ooo-source</code> which will install &amp;amp;amp;amp; link these directories back - making it easy to generate a diff with 'cvs diff -u' &amp;amp;amp;amp;/or commit to ooo-build.
 
  
 
== Testing ==
 
== Testing ==
  
  It's extremely important to test the work which is already done. You can use test cases from the ''ooo-build/test/macro'' directory, you can extend them or you can write your own test cases.</p>
+
It's extremely important to test the work which is already done. You can use test cases from the ''ooo-build/test/macro'' directory, you can extend them or you can write your own test cases.</p>
 
+
It's a good idea to write test cases directly in the Microsoft Excel?
=== Brainstorming ===
+
 
+
Maybe, it's a good idea to write test cases directly in the Microsoft Excel?
+
  
 
== Accessing the VBA API from other languages ==
 
== Accessing the VBA API from other languages ==
  
 
The VBA API is implemented by an UNO service, the service is accessable via a singleton. As such it is possible to use the API from any language that has an UNO binding. The main entry points to the API are certain global variables { Application, ActiveWorkbook and ActiveSheet } or methods { WorkSheets, WorkBooks } exported by the service. Using these globals as a starting point the rest of the api can be accessed.
 
The VBA API is implemented by an UNO service, the service is accessable via a singleton. As such it is possible to use the API from any language that has an UNO binding. The main entry points to the API are certain global variables { Application, ActiveWorkbook and ActiveSheet } or methods { WorkSheets, WorkBooks } exported by the service. Using these globals as a starting point the rest of the api can be accessed.
 +
 +
'''NOTE:'''  Beaware the idl is not ( nor won't be for the forseeable future be 'published' ) it WILL change, so if you are using a language that has a binary depency on the interface ( like c++ & java ) then consider yourselves warned.
  
 
=== Python ===
 
=== Python ===

Revision as of 17:34, 22 February 2007

Visual Basic for Applications (VBA) is an implementation of Microsoft's Visual Basic which is built into all Microsoft Office applications.

Ooo-build contains a new VBA model which allows you to run macros from your Microsoft Office documents. This model is under heavy development by Novell and others, and it is expected that many macros won't run for now.

Latest News

  • Update Wiki Page with latest info
  • Novell and Sun to work together on the VBA incubator project more info here
  • I am delighted that Andreas Bregas now joins me to co-lead the vba incubator project
  • cws npower6 will contain the initial code drop

Terminology

In this page we talk alot about the 2 vba interopability solutions, I'd like to distinguish between them with simple terms ( The vba solution formally known as Sun's migration tools api etc. is quite a mouthful ) so forever more in the text below I will refer to

  • helperapi - The compatibility api generously donated by Sun that was part of their migration toolkit
  • oovbaapi - the ooo-build vba interoperabiltiy solution that soon will incorporate object implementations from the helperapi

Dashboard

How to enable the VBA model

The VBA model is enabled by default in the current ooo-build. It's enough to get, build, install, and be able to run it.

If you are using upstream Openoffice and wish to play with this feature then check out and build the cws npower6 which contains the initial code drop for the oovbaapi

How to disable the VBA model

Depending on how your version of Openoffice delivers the VBA feature to you there are a number of ways to disable it.

If you have an Openoffice build from a linux distro ( or a windows one from Novell ) that has the vba interop feature all you need do is navigate to the 'Tools.Options.Load/Save.VBAProperties' page and uncheck the 'Load Excelbasic code to edit' option.

If you are using an own build ( incorporating ) cws-npower6 the above method will always work. But if you built the vba interop feature as an office extension then you can of course disable or delete the vbaapi.oxt extension using the Extension Manager.

How can I help you?

We need help in a couple of areas - porting object from the helperapi, understanding the VBA usage patterns, implementation and testing; see below.

issue no. description
68894 adds core object model search scope eg. Range("A1") vs. Application.ActiveWorkbook.ActiveSheet.Range("A1")
68895 is related to the issue above, exports the uno vba object model as a property of the document model ( for ease of access by basic core )
64884 adds support default parameters, eg. for Range("A1") = 3, or aVarDimmedAsInteger = Range("A4")
68883 the UNO VBA Interoperabilty API ( IDL & implementation )
68897 allows dim r1 as Range ( only for objects in the openoffice.org.vba ) namespace, additionally allow vba contants defined in the same namespace to be accessed by leaf name only.
64882 when running in vba interoperability mode, the wait function will behave like its ms counterpart, e.g. wait( now() + timevalue("00:00:05" ) ) ' WAITS 5 SECS
68898 rudimentary support for the '[a1:b2]' evaluate syntax (currently only handles short cut range references).

This is not an exhaustive list, but gives some of the most critical pieces to get up-stream.

Understanding the VBA usage patterns

VBA model is huge and we need help in understanding the VBA usage patterns for prioritizing as we progress. It's important to receive as many Microsoft Office documents with macros as possible for analysis. We are interested in documents from developers and regular people too.

Dumping the VBA from your MS Office documents

libgsf

If you're worried about the sheet data you can use test-msvba from the libgsf. Download the latest test-msvba.c file and compile it with the following command:

gcc `pkg-config --libs --cflags libgsf-1` -o test-msvba test-msvba.c

Note: you need to have libgsf-devel package installed.

Now, you can dump the VBA from your documents with the following command:

find -name '*.xls' -exec sh -c 'test-msvba {} >> ~/excel-vba-stream-for-noel.bas' \;

pole

Or you can use POLE with GUI. POLE is a portable C++ library to access structured storage. It is designed to be compatible with Microsoft structured storage, also sometimes known as OLE Compound Document.

Exporting modules from the Microsoft Excel

Open your document and edit associated macros. You can see list of modules on the left side of your screen. Use the right mouse button and select Export from the context menu. The whole module will be saved as one huge *.bas.

Where to send

If you are going to send pure VBA streams, send them directly to [Noel dot Power at Novell dot com].

Implementation

The desired sequence

Add an extension to the IDL

The IDL lives in oovbaapi/org/openoffice/*, the IDL syntax can easily be gleaned from a few other IDL files. Two things are worth bearing in mind:

  • it's important that the argument names are correct, so that the MsgBox title:="hello" syntax works correctly.
  • for optional arguments, or variant types you need to use the any type

Having edited the IDL extension you need to:

  • run: build && deliver in oovbaapi (perhaps remove types.db first),

Add the extension to the implementation

The impl. code lives in sc/source/ui/vba/ - find the right header &amp;amp; source files. Add the method (with the correct prototype) to the header - often it's easiest to cut/paste that from the compiled C++ headers in sc/unxlngixxx/inc/org/openoffice/vba/

Then implement the method itself in the .cxx file. Run build debug=true

Running it

You did use [linkoo] right ? - in which case - just re-run soffice.bin (killall -9 soffice.bin first to ensure there is no lurking factory process).

Now of course - you want to add a new test to exercise it to ooo-build/test/macro/*. And of course loop back to the beginning. Once you've got something you want to share - a simple cvs diff -u | tee /tmp/foo.diff in ooo-build/scratch will yield a patch you can mail to Noel / the ooo-build mailing list to get your code folded in. NB. it's important you sign the JCA first.

Testing

It's extremely important to test the work which is already done. You can use test cases from the ooo-build/test/macro directory, you can extend them or you can write your own test cases.

It's a good idea to write test cases directly in the Microsoft Excel?

Accessing the VBA API from other languages

The VBA API is implemented by an UNO service, the service is accessable via a singleton. As such it is possible to use the API from any language that has an UNO binding. The main entry points to the API are certain global variables { Application, ActiveWorkbook and ActiveSheet } or methods { WorkSheets, WorkBooks } exported by the service. Using these globals as a starting point the rest of the api can be accessed.

NOTE: Beaware the idl is not ( nor won't be for the forseeable future be 'published' ) it WILL change, so if you are using a language that has a binary depency on the interface ( like c++ & java ) then consider yourselves warned.

Python

vba = uno.getComponentContext().getByName("/singletons/org.openoffice.vba.theGlobals")
sheet = vba.ActiveSheet
book = vba.ActiveWorkbook

Java

import org.openoffice.vba.*;
"
// getComponentCtxFromSomewhere is a fictional
// routine representing acquisition of the component context
// from e.g. remote ServiceManage if the code is a remote client
// or from the XScriptContext if this were a java ScriptingFramework script 

XComponentContext ctx = getComponentCtxFromSomewhere(); 
Object oGlobs = ctx.getValueByName(
                "/singletons/org.openoffice.vba.theGlobals");
XGlobals xGlobs = AnyConverter.toObject(
                new Type(XGlobals.class), oGlobs);
XWorkBook xWBook =  xGlobs.getActiveWorkbook();
XWorkSheet xSheet = xGlobs.getActiveWorkSheet();

OO Basic

Basic allows access to the global variables automatically just like VBA does, there is no need to create any services or access any singletons to use the API

msgbox "Name of the current document is " & ActiveWorkbook.Path
Personal tools