ADempiere 3.6 Cookbook

5 (1 reviews total)
By Ajit Kumar
    Advance your knowledge in tech with a Packt subscription

  • Instant online access to over 7,500+ books and videos
  • Constantly updated with 100+ new titles each month
  • Breadth and depth in over 1,000+ technologies
  1. Preparing the Ground

About this book

ADempiere is one the of the leading open source ERP products in today's business market. ADempiere offers everything you need to make your business successful: efficient data management, streamlined business processes, reduction in costs, and minimal complexity.

This practical cookbook offers effective recipes for the extension and customization of ADempiere. It bypasses unnecessary theory. You will learn to install ADempiere correctly and get straight into practical tasks.

When you read the book, you'll understand ADempiere workflow and the important functions of managing your data. Real-world business-critical activities such as integrating ADempiere with e-mail clients, office suites, shipping data, analytical processing tools, reporting tools, shopping carts, and web services are covered in detail.

Publication date:
March 2011
Publisher
Packt
Pages
332
ISBN
9781849513388

 

Chapter 1. Preparing the Ground

In this chapter, we will cover:

  • Creating the installer from the source code

  • Installing ADempiere

  • Debugging the ADempiere client application (Desktop version)

  • Debugging the ADempiere server application (Web version)

  • Running multiple instances on a single machine

  • Giving ADempiere your identity

 

Introduction


Before we get started with the real customization work in ADempiere, it is very important that we set up the right environment for the development and equip ourselves with the tools required for the customization. Most important among them is the ability to debug the existing code, so that when we make changes to the existing code or add a new functionality, we would have a way to find out the source of the problem, identify the cause, and make the necessary change to resolve it.

With this goal in perspective, in this chapter, we will understand how to setup ADempiere development environment and the different deployment mechanism which can be applied to the operational aspect of ADempiere. The chapter starts with the focus on the development environment where we will see how to check out the code from the ADempiere SVN repository, build it, create an installer from it, use the installer to install ADempiere on your system, debug the client version of ADempiere, and debug the server version. Subsequently, we will move on to the operational aspect where we will understand what it takes to run multiple instances of the ADempiere server on a single machine. As part of this, we will cover different deployment topologies, keeping the database and the application server in perspective and understand the topology-wise differences.

With most of the Open Source applications, it is more likely that you will customize or enhance ADempiere to suit yours or your customers' needs and you would like to give it your identity. You may want to give it a different name, use a different logo, or a different look-and-feel. We will cover this aspect in the last recipe of this chapter.

Like any other software application, ADempiere also requires certain software to be installed and configured on your system. In order to be able to customize or enhance ADempiere, you need a few more tools/applications and we have to have them properly configured before we start on our goal. Though not mandated by ADempiere, throughout this book, we will use the following list of software on the MS Windows platform:

  • Eclipse Galileo (Eclipse for JEE development)

  • JBoss 4.2.3 GA

  • JDK 1.6

  • PostgreSQL Database 8.x

  • SVN client (for example, TortoiseSVN)

Note

Though ADempiere supports Oracle and Oracle XE databases, for this book, we will use PostgreSQL database to keep these things simple and light.

The steps to install and configure the previously listed software are out of this book's scope. You may refer to http://wiki.postgresql.org/wiki/Detailed_installation_guides for the installation steps. Each one of these software come along with their own installation and setup manual. Kindly refer to them for installation and configuration. There is no specific configuration requirement for using this software with ADempiere. So, if you follow the respective installation manuals, you will be fine. However, at the end of the installation of all the software, ensure that the following environment variables are set and they are valid:

  • JAVA_HOME

For ease of reference, let us assume that the following is the installation path for the previously listed software on your system and the corresponding name that we will use to refer to those paths:

  • Eclipse Galileo —C:\EclipseGalileo – ECLIPSE_HOME

  • JBoss 4.2.3 GA —C:\JBoss_423_GA – JBOSS_HOME

  • JDK 1.6 or above —C:\Java\jdk1.6_X JAVA_HOME

  • PostgreSQL Database 8.x —C:\postgresql8.x – POSTGRES_HOME

At this point, we are all set to get started on our tour of ADempiere customization and enhancement.

Note

JBoss 4.2 version has been used throughout this book as it is closer to the version which ADempiere 3.4 uses. Though the steps are not too different in JBoss 5.0, I would refrain from making it a rule.

 

Creating the installer from the source code


The recipe describes the steps involved in building the ADempiere source code and creating an installer out of it, which is ready for you to install on your own system or any other system. These installer images are installable on MS Windows as well as Linux systems.

This is the basic recipe and a pre-requisite for any other recipe mentioned in this book.

How to do it...

  1. 1. Check out the ADempiere code from the following SVN URL:

    https://adempiere.svn.sourceforge.net/svnroot/adempiere/tags/adempiere360lts.

    • Say, we have checked out the ADempiere code in the C:\adempiere_svn\ tags\adempiere360lts folder. We'll refer to the C:\adempiere_svn folder by name, say, ADEMPIERE_SVN

  2. 2. Start Eclipse.

  3. 3. Click on File menu and select Import...

  4. 4. Select the Existing Projects into Workspace option under the General category and click on the Next button. Dialog with the title Import Projects appears with the Select root directory radio button.

  1. 5. Click on the Browse button next to the Select root directory radio button and select the adempiere360lts folder under the<ADEMPIERE_SVN>\tags folder. This will add adempiere_360 to the Projects list.

  1. 6. Click on the Finish button. This will import the project adempiere_360 into your Eclipse Workspace and build it, if the Build Automatically option is set in your Eclipse. If not, build the project.

  1. 7. Expand the adempiere_360 project in Eclipse. You will see the utils_dev folder.

  2. 8. Expand the utils_dev folder and you will find build.xml. This is the Ant build script to compile the ADempiere source code and create the installable binaries.

  3. 9. Right click on build.xml and select Run As | Ant Build. This will start the build process.

The following message appears in the console at the end of the build:

A successful build will create the adempiere folder under the project folder and the following binary installers are created, which can be used to install ADempiere on MS Windows or Linux:

  • Adempiere_360LTS.zip

  • Adempiere_360LTS.tar.gz

How it works...

In step 1, we first get the ADempiere code from its SVN repository. In steps 2 through to 6, we compile the code. In steps 7 through to 9, we create the distributions (Linux as well as MS Windows) by running the default Ant target inside the build.xml file, present under the utils_dev folder

There's more...

In this recipe, we saw how we can use the Ant build file build.xml to compile the code and create the installation packages (.zip and .tar.gz files). The same can be achieved by running a batch file.

Using RUN_Build.bat to create the installer

If you like working with command prompt, then you can use the<ADEMPIERE_SVN>\ tags\adempiere360lts\utils_dev\RUN_Build.bat script from the command prompt. This script, after a successful build, will create the installers.

Note

For the Linux users, there is an equivalent script with the extension .sh. For all the .bat script for MS Windows, there is a corresponding .sh shell script available.

 

Installing ADempiere


Now that we have created the installers in the previous recipe, here we will make use of it to install an instance of ADempiere for our use. This recipe describes the steps involved in installing and setting up the ADempiere instance to make it usable.

Getting ready

  1. 1. Create a new database in PostgreSQL by name, say, adempiere360.

  2. 2. Add the adempiere user in the PostgreSQL database with adempiere as the password.

  3. 3. Stop and restart PostgreSQL.

  4. 4. Copy the<ADEMPIERE_SVN>\ tags\adempiere360lts \adempiere\Adempiere folder and its content to C:\. Now, you will have the C:\Adempiere folder.

  5. 5. Set the environment variable ADEMPIERE_HOME to C:\Adempiere.

How to do it...

  1. 1. Open a command prompt by selecting Start Button | Run | Open and enter cmd.

  2. 2. Change the directory to<ADEMPIERE_HOME>\data.

  3. 3. Run the following commands to set up the ADempiere schema:

    psql -U adempiere -d adempiere360 -c "drop schema sqlj cascade"
    psql -U adempiere -d adempiere360 -f Adempiere_pg.dmp >> dump_errors.log.
    
  4. When prompted, enter adempiere as the password.

  1. 4. Change the directory to<ADEMPIERE_HOME>.

  2. 5. Run RUN_setup.bat. This will bring up a window to enter various details.

  3. 6. Enter the valid values.

Database Server

localhost/127.0.0.1

Database Type

postgresql

Database Name

adempieredb

Database User

adempiere

Database Password

adempiere

System Password

<your PostgreSQL database admin user password>

  1. 7. Click on the Test button. First time setup will pop up the Key Store Dialog. Enter the relevant details, as shown in the following screenshot, and click on the tick button:

  1. 8. Click on the Test button and verify that all the tests have been passed (a tick mark appear next to the fields, as shown in the following screen shot):

  1. 9. Click on the Save button to save the settings.

  2. 10. Accept the license term, when prompted. This will create an Adempiere.properties file in the <ADEMPIERE_HOME> folder.

  3. 11. When setup is complete, change directory to <ADEMPIERE_HOME>.

  4. 12. Run RUN_Adempiere.bat. This will start the client version of ADempiere and will show you the following login screen.

13. Click on the button, which is on the right-hand side of the Server field, and verify that the database connection details is correct. Change the settings, if needed, and click on the Test Database button to make sure that the cross icon changes to a tick icon, as shown in the following screen shot:

  1. 14. If you want to run the server version of ADempiere, then change the directory to <ADEMPIERE_HOME>\utils and run RUN_Server2.bat. This will deploy ADempiere in JBoss, which is distributed along with it, and start the JBoss server. After the server has been started, you may verify your ADempiere installation by accessing the following URL from the browser of your choice —http://localhost:8080/webui—8080 is the default JBoss port. If it is different in your case, replace 8080 with your JBoss' port number. This needs to be done to ensure that the port that you are using for your JBoss server instance is free; otherwise the server will not run.

    To stop the server, you shall run RUN_Server2Stop.bat.

How it works...

First, we create the database and import the ADempiere data dump using steps 1 through to 3. In steps 4 through to 10, we complete the initial setup of our ADempiere instance with details such as database detail, mail server detail, and so on, so that it is ready to run. Steps 11 through to 13 helps us to run the desktop as the well as web version of ADempiere.

There's more...

Alternatively, to import ADempiere schema and the initial (GardenWorld) data, you may go to the<ADEMPIERE_HOME>\utils folder and run the RUN_ImportAdempiere.bat file.

See also

  • Creating installer from the source code

 

Debugging the ADempiere client application (Desktop version)


Debugging the client version is pretty straightforward and quick. In this recipe, we will see how to configure the project in Eclipse so that we can debug ADempiere when we run it as a client application (the Swing version).

Getting ready

Before we can run ADempiere, there are properties, specific to ADempiere, which need to be configured properly for example, JDK location detail, application server detail, database detail, SMTP detail (for e-mails), and so on. The following steps must be completed to ensure that these properties are set up correctly:

  1. 1. In Eclipse, open the Open Resource window and select the Setup.java file. It is available under the install\src\org\compiere\install package of your adempiere360lts project.

  2. 2. Right-click on the Setup.java file in the Project Explorer and select the option Run As | Java Application. This will launch an ADempiere setup screen.

For the client version, we need to set the fields in the following sections of the screen:

  • Java

  • Adempiere

  • Database Server

  • Mail Server (Optional)

Click on the Test button and if everything was set correctly, you will see the Ok message at the bottom of the setup screen. In case you get errors, verify the values you have entered. Correct them and Test until you get the Ok message. Any errors during the testing are also shown on this window.

Note

In case any errors occur during your practice and it is not described in the book, you may refer to the ADempiere Wiki and forums for more information.

  1. 3. Click on the Save button. This will create the Adempiere.properties file in the Adempiere Home directory. After creating the property file, the program tries to build the code base but fails with a build error. Do not worry! Our intention was to only get the Adempiere.properties file created, which we will use in our subsequent setups.

How to do it...

Now that we have got the Adempiere.properties file out, it is a trivial task to be able to debug the application. Here are the steps:

  1. 1. In Eclipse, open the Open Resource window and select the Adempiere.java file. It is available under the base\src\org\compiere folder of your adempiere_360 project. This class is the entry point class for the client version.

  1. 2. Add a break-point at Line 594 inside the main method.

  2. 3. Right-click on the Adempiere.java file and select Debug As | Debug Configuration. This will bring up the Debug Configurations window.

  1. 4. Click on the Arguments tab and specify the following VM arguments:

    DPropertyFile="C:\adempiere_svn\tags\adempiere360lts\ADempiere.properties"
    DADEMPIERE_HOME="C:\ tags\adempiere360lts"
    
    • PropertyFile: Points to the Adempiere.properties file, which we had created earlier

    • ADEMPIERE_HOME: Points to the Adempiere folder

  1. 5. Click on the Debug button to start the debugging.

  2. 6. Use the toolbar on the Debug window to debug the code. This way, you can figure out how the control is flowing in the ADempiere source code and gain a better understanding of the subject.

How it works...

Adempiere.java is the main class file which provides the entry point for the desktop version of ADempiere. This is the class where you will find the main method. To this class, the two important properties—PropertyFile and ADEMPIERE_HOME must be passed so that it can read the setup information (database, mail server, JRE path, and so on) and run the application.

See also

  • Creating an installer from the source code

  • Installing Adempiere

 

Debugging the ADempiere server application (web version)


Working with the web/server version of ADempiere is equally practical and required as compared to the client/desktop version. The server version runs inside a J2EE container, like JBoss. In this recipe, we will see how to configure ADempiere and JBoss to be able to debug the code when it is deployed as a server. Though ADempiere comes along with a JBoss distribution, to have a better understanding of the subject matter, we will use the external JBoss installation.

Getting ready

  • Verify that JBoss is installed on your system and set up correctly

How to do it...

  1. 1. In Eclipse, go to the Servers view.

  2. 2. Right-click and select New | Server. You will see the New Server window.

  1. 3. On the New Server window, select the JBoss V4.2 and click the Next button. This will take you to the New JBoss V4.2 Runtime window.

  1. 4. On the runtime window, enter the following values and click the Next button:

    JRE: Choose JDK 1.6 or above

    Application Server Directory: Set this to your JBoss installation folder (which is JBOSS_HOME)

    This will take you to the following New JBoss V4.2 Server window:

  1. 5. On the New JBoss v4.2 Server window, enter the following and click the Next button:

    • Address: 127.0.0.1

    • Port: 9080 (make sure that this port is not being used by any other application on your system)

    • JNDI Port: 1099 (make sure that this port is not being used by any other application on your system)

    • Server Configuration: default

      Clicking on the Next button will take you to the Add and Remove window:

  1. 6. On the Add and Remove window, select Adempiere_trunk from the Available list, and add it to the Configured list.

  1. 7. Click on the Finish button. This will add an entry in the Servers view.

  1. 8. Open org.adempiere.webui.AdempiereWebUI.java and add a break-point inside the constructor.

  2. 9. Right-click on the server entry, which we just created, and select the Open menu option.

  1. 10. On the Overview screen, change the Start value under the Timeouts category to 500.

Note

For the default Server Configuration, the port number is defaulted to 8080 unless you go and change the config files of JBoss, which we'll see in the subsequent recipe. For now, note that even though you enter 9080 as the port, the JBoss server will run on port 8080. So, make sure that port 8080 is free on your system.

  1. 11. Click on the Open launch configuration. This will bring up the Edit configuration window to edit the JBoss configuration.

  1. 12. On the Arguments tab, add the following to the VM arguments:

    -DPropertyFile="C:\adempiere_svn\tags\adempiere360lts\ADempiere.properties"
    DADEMPIERE_HOME="C:\adempiere_svn\tags\adempiere360lts"
    
  2. 13. On the Classpath tab, click on the Add External JARs button to add the JARs from the following folders:

    • <ADEMPIERE_SVN>\tags\adempiere360lts\tools\lib

    Note

    Exclude the following JARs: ant.jar, ant-commons-net.jar, ant-contrib-1.0b1.jar, ant-launcher.jar, j2ee.jar, jnlp.jar, log4j.jar, commons-logging.jar, servlet-api.jar

    • <ADEMPIERE_SVN>\tags\adempiere360lts\JasperReportsTools\lib

    Note

    Exclude the following JARs: jfreechart-1.0.13.jar

    • Add <JAVA_HOME>\jre\lib\javaws.jar

  3. 14. Click Apply followed by the OK button.

  4. 15. Refresh the project adempiere_360.

  5. 16. Right-click on the JBoss server entry on the Servers view and select the Publish menu option. This will start the process of build and deployment. The application is deployed with the context name Adempiere_trunk.

  1. 4. After publish is completed (you will see the Synchronized text next to the JBoss server entry in the Servers view), right-click on the server and select the Debug menu option.

  • This will start the JBoss server in the debug mode and the debugger will stop at your break-point. Using the Debug toolbar, you will be able to debug ADempiere as a server application. If you resume the application, the server will run and you will see the following screen when you access the URL http://localhost:8080/Adempiere_trunk/ in your browser.

How it works...

Steps 1 through 7 take care of creating a JBoss server entry in Eclipse and adding the ADempiere project deployment resource to the JBoss server runtime. It is important to verify that the JBoss and JNDI port numbers (9080 and 1099) are free. Steps 9 through 14 are where the project related detail (for example, classpath) is configured in the JBoss server runtime. This is important for the deployment of the ADempiere server version in JBoss and running the same. The configuration adds the required JAR files and ADempiere classes to the JBoss configuration so that they are available to the runtime when we run the server.

See also

  • Creating the installer from the source code

  • Installing ADempiere

 

Running multiple instances on a single server


In this recipe, the focus is on running multiple instances of ADempiere on a single server. This is a very practical requirement when you want to host ADempiere for multiple clients on a single server. Even though each instance of ADempiere is meant to handle multiple clients and organizations, there may be a scenario where you may have to put up multiple instances of ADempiere not only from the technical perspective, but also from an operational perspective. For example, one instance is to be run on PostgreSQL whereas the other instance is to be run on Oracle. And, if you have that scenario, this recipe will try to address it.

Here, we are going to cover two deployment topologies. In one, we will have 1-1-1 mapping between JBoss, ADempiere, and Database, that is, one instance of JBoss server hosting one instance of ADempiere, which is connecting to one database. The following image depicts the 1-1-1 setup.

In the second instance, we will have 1-N-1 mapping where one instance of the JBoss server will host multiple instances of ADempiere instances and each one of them will connect to a single database. The following image depicts the 1-N-1 setup:

Getting ready

These steps are common to 1-1-1 as well as 1-N-1 setup.

  • Copy the<ADEMPIERE_SVN>\tags\adempiere360lts to<ADEMPIERE_SVN>\tags\adempiere360lts_2.

  • Change the project name to adempiere_360_2 in the<ADEMPIERE_SVN>\tags\adempiere360lts_2\.project file.

  • Import the<ADEMPIERE_SVN>\tags\adempiere360lts_2 project into Eclipse.

  • Create the adempiere360_2 database in PostgreSQL and set up the schema and the initial data by following the steps mentioned in the Installing ADempiere recipe. Remember to use the already created user adempiere.

How to do it...

  1. 1. Running instance with 1-1-1 Setup.

    Here we will set up one more JBoss and ADempiere instance.

    • Go to the<JBOSS_HOME>\server folder

    • Copy the default folder to adempiere360lts_2. You may have any name for your server

    • Modify the port numbers in the following files so that they are not shared with the default server ports and they are available on your system:

      < JBOSS_HOME>\server\ adempiere360lts_2\conf\jboss-service.xml: Modify the following ports—8083, 1099, 1098, 4444, 4445

      < JBOSS_HOME>\server\ adempiere360lts_2\deploy\ejb3.deployer\META-INF\jboss-service.xml: Modify the following port—3873

      < JBOSS_HOME>\server\ adempiere360lts_2\deploy\jms\uil2-service.xml: Modify the following port—8093

      < JBOSS_HOME>\server\ adempiere360lts_2\deploy\jboss-web.deployer\server.xml: Modify the following ports—8080, 8443, 8009

    • Open the<ADEMPIERE_SVN>\tags\adempiere360lts_2\.settings\org.eclipse.wst.common.component file and change the deploy-name from Adempiere_trunk to Adempiere_360_2 (you may have any name or your choice)

    • Go to Eclipse and refresh the adempiere_360_2 project

    • Follow the steps mentioned in Debugging ADempiere server application recipe to add a new JBoss server pointing to <JBOSS_HOME>\server\adempiere360lts_2 and deploy Adempiere_360_2 to it. Make sure, your PropertyFile VM argument points to the Adempiere.properties created in<ADEMPIERE_SVN>\tags\adempiere360lts_2 folder and ADEMPIERE_HOME VM argument points to<ADEMPIERE_SVN>\tags\adempiere360lts_2

    • Now, run the JBoss default server, where you had Adempiere_trunk deployed, and also run the second JBoss server where you have Adempiere_360_2 deployed

  2. 2. Running an instance with 1-N-1 Setup.

    • Go to Eclipse

    • Right-click on the JBoss server entry in the Servers view, which we had created with the default configuration and to which Adempiere_trunk was deployed, and click Add and Remove. You will see Adempiere_trunk listed under the Configured items and Adempiere_360_2 listed under the Available items

    • Add Adempiere_360_2 to the Configured list and click on the Finish button

    • Right-click on the JBoss server entry and click Publish to deploy Adempiere_360_2. Adempiere_360_2 will be the context for this ADempiere instance

    • Right-click on the JBoss server entry and click on Start the server with two instances of ADempiere deployed. You can now access the two instances by accessing the following URLs:

      http://localhost:8080/Adempiere_trunk/

      http://localhost:8080/ Adempiere_360_2/

  • Both ADempiere instances will be pointing to the same database as the database connection detail is mentioned in the Adempiere.properties file and a common property file is used in the VM arguments of the JBoss server.

How it works...

In order to have an instance with 1-1-1 setup, important point to make is making sure that we are able to run multiple instances of the JBoss server on a single machine. This requires us to make changes to the different port numbers, which one or another service in JBoss uses. If this is not done, some or some other service would not run and that would lead to an error while we try to deploy and run the application.

In the 1-N-1 setup, JBoss ports are not of concern as we will be running a single instance of it. However, the important point here is the deployment name for the multiple instances of the ADempiere application. Uniqueness must be maintained across ADempiere instances in terms of deploy-name, otherwise the deployment of one instance will overwrite the deployment of a second instance, as it uses the deploy-name as the WAR filename.

See also

  • Creating an installer from the source code

  • Installing ADempiere

 

Giving ADempiere your identity


If you are reading this book, you have, or may have, some customization or enhancement needs in your mind. Be it look and feel (UI color, CSS, icons and so on), name, or logo. Effectively, we would have a practical need to give ADempiere our own identity. Here we will discuss the various points where you may make the changes to have your own identity of the application.

Getting ready

Verify that you have completed the following recipes:

  1. 1. Creating the Installer from the source code.

  2. 2. Installing ADempiere.

  3. 3. Debugging the ADempiere server application.

How to do it...

  • Change, say, NAME to your application name in base/src/org/compiere/ADempiere.java. Additionally, you may also change the splash images, product images, product sub-title, and so on

  • Change, say, APP_NAME to your application name in zkwebui/WEB-INF/src/org/adempiere/webui/ADempiereWebUI.java

  • CSS—For the web application, which is based on the ZK UI framework, you can modify the<ADEMPIERE_SVN>\tags\adempiere360lts\zkwebui\css\ default.css.dsp file to modify the styles

  • Images—There are lots of images. They include images used as ADempiere logos/icons of various kinds, button icons, toolbar icons, and other UI-related images. The simplest way to replace an existing image with yours is to:

    • Search for the files with .ico,.png,.jpg,.jpeg, and.gif extensions in the<ADEMPIERE_SVN>\tags\adempiere360lts folder

    • Find the image of your interest and note down that image dimension and type (jpg/png/gif/ico/and so on)

    • Create your image of the same dimension and type

    • Replace the existing image with your image

    • Launch the ADempiere application and notice the difference

Here is a custom identity that I have given by changing the application name and the logo:

In the preceding diagram, we have changed the application name to Eagle and the logo with my EagleRP product logo. Similarly, you shall be able to make other changes you may need to give ADempiere your identity.

After you have done this, you may also want to commit the same in your project repository so that for all the subsequent builds and deployments, you will use this repository where all the CSS and new images will be part of the installer.

See also

  • Creating the installer from the source code

  • Installing ADempiere

About the Author

  • Ajit Kumar

    Ajit Kumar has over 16 years of experience in technology areas ranging from embedded systems to large enterprise applications. He worked with various multinational corporations such as Honeywell, Hughes, Virtusa, and Convergys, before starting his own company—Walking Tree—which specializes in Sencha frameworks.

    Ajit has authored books on open source frameworks, including Sencha Touch Cookbook, Sencha Touch Cookbook Second Edition, Sencha MVC Architecture, and ADempiere 3.6 Cookbook, all by Packt Publishing, which he considers his way of thanking the awesome open source community!

    Browse publications by this author

Latest Reviews

(1 reviews total)
Exactly what I requested - brilliant
ADempiere 3.6 Cookbook
Unlock this book and the full library for FREE
Start free trial