Tuesday, March 27, 2012

IDE test server overview

One of the goals of EDT is to let you test your applications without having to configure and deploy to your target environment. However, we must also use care not to alter the behavior of the application when in test mode.

The IDE test server (based on Jetty) is a major player in this regard, allowing you to invoke services from a Rich UI client without deploying them. Not only will the test server run the service right out of the EGL source project, it'll also automatically manages itself by updating configurations when files such as your deployment descriptors change. You don't even start the server yourself - it's started up when needed, and runs in the background. By the way, the server runs in debug mode, so you can set breakpoints in the service and step through the code.

Now, there are some situations where the server needs to be restarted for changes to take effect. You'll be prompted if this happens, and given the choice to terminate the server now or let it keep running. The most typical case is when the Java debugger's hot code replace fails (e.g. you modified a part but the generated Java code contains a type of change that the Java debugger does not support "swapping in", such as a new global field).

I mentioned previously that the server is started automatically, and an important addendum is that the server instance has a "base project", which dictates the classpath, the list of available deployment descriptors, etc. When invoking a service, one of the following rules is used to determine the "base project":
  • When invoking a dedicated service, the project of the main Rich UI handler is the base project.
  • When invoking a REST service, the project containing the service is the base project.
This allows us to best match the deployed environment. If you open the Debug perspective, the Debug view will list all the test server processes. The process name will indicate the "base project" of that particular server, and there is only one server process per base project. You can use this information to terminate a specific project test server. (Once killed it'll get started back up automatically the next time it's needed.)

Before I go, a couple tips:
  • When invoking a dedicated service, make sure the project containing the service is on the Java Build Path of the Rich UI project.
  • To invoke a service in a RESTful way, the service must be listed as a REST service in the deployment descriptor, otherwise it will not be exposed as a REST service (this is to match the deployed application's behavior). Then to use the test server instead of trying to invoke the deployed service, use the following workspace URI format for your REST binding: workspace://myServiceProject/myPackage.myService. If you use the 'http://' URI format then the test server will not be used.
  • If you're using JNDI database access in your services, you can benefit from connection pooling (which provides a significant performance boost) simply by defining an Apache Tomcat runtime at Window > Preferences > Server > Runtime Environments. Otherwise it'll still work, but will run slower.
And if you're a developer looking to extend EDT, the test server can also be extended to support new concepts (information on this can be found on the wiki).

-Justin

Tuesday, March 20, 2012

EDT 0.8 Milestone 3 now available

The third and final milestone build for EDT 0.8 is now available for download. Check out the new and noteworthy page to learn more about this milestone.

To install EDT 0.8 Milestone 3, you'll need to add the Milestone Build site to your Available Software Sites list under the Help>Install New Software menu option. We suggest you call the site "EGL Development Tools milestones". The site URL is: http://download.eclipse.org/edt/milestones/1.0/

Once the milestone site has been added (which you may have done for a previous milestone), using Help>Check for Updates should find the newest milestone build.

With this milestone, we've completed all the new function being added to EDT 0.8. We're pretty excited about the content! We'll be testing over the next few weeks. We welcome you to help the test effort! If you find a bug, you can open it in Bugzilla.

As always, we welcome your feedback and questions on the EDT forum.

Changes to the String type in EDT .8

In EDT .8, the String type has been changed from a Value type to a Reference type.  (More information on Value types and Reference types can be found on the EDT Language Overview Wiki page) .  In general, this change will not have an impact on existing EGL code, but it is possible for existing functions to behave differently at runtime if they specify a parameter of type String, and do not specify an explicit modifier (i.e. 'in', 'inout', etc).

In EDT, the default modifier for a Value type function parameter is 'inout', which means that the original value is passed to the function parameter, instead of a copy, and any changes made to the parameter in the function will be visible to the caller of the function.  For example:


function func1()
  var1 int = 2;  // int is a Value type
  addOneFunction(var1); 
  // var1 is now 3
end

function addOneFunction(param1 int)
  param1 += 1;  // Add one to param1
end


In EDT, the default modifier for a Reference type function parameter is 'in', which means that a copy of the value is passed to the function parameter, and any changes made to the parameter in the function will not be visible to the caller of the function.  For example:


function func1()
  var1 Decimal = 2; // decimal is a Reference type
  doNotAddOneFunction(var1); 
  // var1 is still 2
end

function doNotAddOneFunction(param1 Decimal)
  param1 += 1;  // Add one to param1
end


Now that Strings are Reference types in EDT, code that used to rely on the default behavior of the 'addOneFunction' will produce different results, similar to the 'doNotAddOneFunction' function, if an explicit modifier is not specified.  For example:


function func1()
  var1 String;
  modifyString(var1); 
  // In EDT .7, var1 would be "Modified String"
  // In EDT .8, var1 will now be ""
end

function modifyString(param1 String)
  param1 += "Modified String";
end


To resolve these issues, you can add an explicit modifier to the function parameter:

function modifyString(param1 String inout)


Additional information on Reference types and Function Parameters
When a reference type is passed to a function parameter using the 'in' modifier, a copy is made by allocating new memory for the parameter that points to the same memory as the value being passed to the function.  If you assign the parameter a new value, only the memory allocated for the parameter is updated to point to the memory used by the new value. 

When a reference type is passed to a function parameter using the 'inout' modifier, the parameter essentially maps to the same memory as the value being passed into the parameter.  If you assign the parameter to a new value, the value passed into the function is updated as well, since the parameter represents the same memory as the original value.

-Brian

Tuesday, March 6, 2012

I say Snippet...Snippet Good

One of the goals of the EDT project is to provide a large collection of source code examples, known as snippets, that show how to complete various tasks in EGL. These code samples can be very useful for someone that has never written an application in EGL before, and they can help experienced EGL developers remember how to write an infrequently used operation, or educate themselves on previously unused parts of the language.  The current collection of EGL snippets can be found on the EDT Code Snippets wiki page, which is conveniently broken down into sections on; EGL native types, user defined types, statements, database access, services, and Rich UI development. 

While most snippets are only a few lines long, and describe how to use a particular statement or type found in the EGL language, there are some snippets that describe higher level concepts that are often used in a typical EGL application.  An example of a small snippet is the following, which shows how to declare a new Dictionary with some initial values:

http://wiki.eclipse.org/EDT:Declaring_data#Values_of_type_Dictionary

An example of a larger snippet, which shows how to load multiple rows of values from a database, can be found in the section on working with a database:

http://wiki.eclipse.org/EDT:Working_with_a_database#Getting_multiple_rows_with_one_statement
While there is a lot of content on these pages, there is always room for more!  If you have a suggestion, feel free to post a comment to this blog entry, and we can see about adding it to the collection.  Better yet, if you're an Eclipse member, you can add the snippet yourself using the instructions found on the snippet page.  Once you see how easy it is to add a new snippet (I added one to the Dictionary section while writing this blog entry and with Devo songs running through my head), you will hopefully find yourself adding many new snippets to share with the EDT community.

Brian

Tuesday, February 28, 2012

EDT 0.8 Milestone 2 now available

The second milestone build for EDT 0.8 is now available for download.  Check out the new and noteworthy page to learn more about this milestone. In particular, we've added support for JNDI and IBM i.

To install EDT 0.8 Milestone 2, you'll need to add the Milestone Build site to your Available Software Sites list under the Help>Install New Software menu option. We suggest you call the site "EGL Development Tools milestones".  The site URL is: http://download.eclipse.org/edt/milestones/1.0/

Once the milestone site has been added (which you may have done for Milestone 1), using Help>Check for Updates should find any new milestone builds. For more information about what's coming in the next milestone of EDT 0.8, see the EDT 0.8 Planning page.

As always, we welcome your feedback and questions on the EDT forum.

Two down, one to go!

Monday, February 20, 2012

Using the Rich UI editor

The Rich UI editor allows you to visually create a web application. Once you have created an EGL web 2.0 project, you can add a Rich UI handler to it. The Rich UI handler provides a default template that includes a GridLayout to help with placement of widgets on the page. In the Design view, you can drag and drop widgets from the Palette onto any cell of the GridLayout.  Use the Properties tab to edit the widget, such as changing border, spacing, or alignment.

Decide you want to move a widget? Just drag and drop it to a new location. Need more space for widgets? Increase the number of rows and columns for the GridLayout using the Properties, or right-click within a GridLayout cell and select Insert to add a row or column above or below the current cell.  (You can also Delete rows and columns via right-clicking on the GridLayout.)



One of our favorite features of the Rich UI editor is the ability to auto-generate a UI based on an EGL variable. You can drag-and-drop an EGL variable, such as a record type, from the EGL Data view to the Design view. The Insert Data wizard let's you select the fields to appear along with label, widget type and name.


To help you get started using the Rich UI editor, members of our development team in China have developed a tutorial to Create a Rich UI logon page.  This tutorial is a good way to familiarize yourself with the Rich UI editor for EGL. The tutorial covers using the Insert Data wizard as a quick way to create the UI from a record, as well as creating an event handler and testing the page using Preview.

Theresa

Monday, February 6, 2012

Testing using EGL Unit (EUnit)

EGL Unit (EUnit) is a testing framework provided with EDT to develop test variations, generate driver programs, and validate the runtime results. You develop your tests once in EGL and execute them on all desired platforms using EDT generators, your extensions, and/or your own generators. The driver program is convenient to produce, simple to run, and the pretty results easy to analyze. Once you’ve built a set of test variations that validates the core logic of your application, the framework allows you to quickly assert the quality of your foundation. 


For step-by-step instructions on how to write, generate, execute, and review test cases, see the EUnit wiki page. Here’s a sample EUnit test library to illustrate the simplicity and power of the framework. This statusTest library has five test variations and displays the possible test results.

package framework;

// basic EUnit test library for testcase status
library statusTests
      
       function testStatusPassed(){@Test}
           LogResult.assertTrue1(100 > 50 );
       end
      
       function testStatusPassed02(){@Test}
           actual string = "restraint";
           expect string = "restraint";
           LogResult.assertStringEqual1(actual, expect);
       end
      
       function testStatusFailed(){@Test}
           success boolean = 100 < 50;
           LogResult.assertTrue("Testing fail condition", success );
       end
      
       function testStatusError(){@Test}
           stuff int[] {1,2,3,4};
           actual int = stuff[13];
           LogResult.assertBigIntEqual1(3, actual);
       end
      
       function testStatusSkipped() {@Test}
           LogResult.logStdOut("Some info about the defect");
           LogResult.skipped("Bugzilla xxxx. Compile problem.");
       End
end

A test variation needs to include the test annotation {@Test} and use one of the LogResults assert functions. Using content assist is a great away to check out the available assertion functions.  To ensure your foundation, you want your test variations to be used frequently and interpreted by anyone. The skipped function denotes a variation that has a known issue and logStdOut allows for additional information to be included.  For the prettiest view of the results, you will need Business Intelligence and Reporting Tools (BIRT). Here’s the Statistics Chart:



This chart provides a quick color-coded summary count of passing and non-passing test cases for all the test libraries exercised by the driver program. For more detailed information, you can open the individual report (.etr) for each library.  Here’s the detailed report for the statusTest library:



Framework.statusTests

Reason: test case count: 5

passed: 2
failed: 1
error: 1
skipped: 1
first test case with error: statusTests::testStatusFailed

msg:
statusTests::testStatusPassed: OK
statusTests::testStatusPassed02: OK
statusTests::testStatusFailed: FAILED - Testing fail condition
statusTests::testStatusError: ERROR - uncaught exception for: statusTests::testStatusError
    => EGL0010E: List index 12 is out of bounds. The list's size is 4.
Some info about the defect
statusTests::testStatusSkipped: SKIPPED - Bugzilla xxxx. Compile problem.

The file provides a convenience link to the associated EGL library in case the test case needs to be reviewed or altered. The file contains the totals by status (passed, failed, etc.), indicates the first failing test case by identifying the function name.  The msg section provides detailed information for each test variation.  It is common for a developer to run the tests, save the result root, apply code changes, rerun the tests, and compare the results files to ensure the expected core behavior.


Utilizing the EUnit test framework will help you ensure the solid foundation of your application. You just need to evolve the test suite along side your application.
The EUnit framework can be used to automate your testing efforts. Please post any features you’d like to see in EUnit, as we hope to add more to this useful tool.


Kathy