technote514-1 scriptingbestpractices

54
SIEBEL SYSTEMS, INC. 1 PROPRIETARY & CONFIDENTIAL EMPLOYEE EDUCATION DUPLICATION PROHIBITED Siebel Scripting Best Practices Resource Document This resource document contains detailed information regarding scripting best practices. Siebel Systems, Inc.

description

Siebel - Best Pratices

Transcript of technote514-1 scriptingbestpractices

Page 1: technote514-1 scriptingbestpractices

Siebel Scripting Best Practices Resource Document

This resource document contains detailed information regarding scripting best practices.

Siebel Systems, Inc.

SIEBEL SYSTEMS, INC. 1 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 2: technote514-1 scriptingbestpractices

SIEBEL SCRIPTING BEST PRACTICES MARCH 23, 2004

Copyright © 2004 Siebel Systems, Inc., 2207 Bridgepoint Parkway, San Mateo, CA 94404. All rights reserved. No part of this publication may be stored in a retrieval system, transmitted, or reproduced in any way, including but not limited to photocopy, photographic, magnetic, or other record, without the prior agreement and written permission of Siebel Systems, Inc.

Siebel Systems, Inc. considers information included in this document to be Confidential and Proprietary. Your access to and use of this Confidential and Proprietary Information is subject to the terms and conditions of the Siebel License Agreement or Non-Disclosure Agreement which has been executed and with which you agree to comply.

PROPRIETARY & CONFIDENTIAL 2 SIEBEL SYSTEMS, INC.DUPLICATION PROHIBITED EMPLOYEE EDUCATION

Page 3: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Table of ContentsIn Acrobat, you can click on any lesson or topic to jump to that area of the resource document. You can also use the Bookmarks feature in Acrobat to quickly navigate.

SCRIPTING FUNDAMENTALSScripting: Where to Begin . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5

Basic Process FlowBasic Process Flow. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6

1. Explore Declarative Configuration Alternatives2. Determine Where to Put the Script: Which Object?3. Determine Where to Put the Script: Which Event?4. Add Error Handling Template5. Add Method Body6. Test

SCRIPTING BEST PRACTICESWhen to Use Scripting. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9

Use Scripting as a Last ResortFollow Standard Naming Conventions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10Comment Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11Know When to Use Browser versus Server Script . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13Place Code in the Correct Event Handler . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14Use Fast Script In Event Handlers that Fire Frequently. . . . . . . . . . . . . . . . . . . . . . . . . . . 15Runtime versus Compiled Business Services . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 16Use Option Explicit . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 17Leverage Appropriate Debugging Techniques . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18

Debugging Siebel ApplicationsAlert and RaiseErrorTextWriting to a Text FileUsing the Debugger in Siebel ToolsUsing Object Manager Settings

Remove Unused Code from the Repository . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20Include Error Handling in All Scripts. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21

Proper Error HandlingError Handling in eScriptError Handling in Siebel VB

Use RaiseError and RaiseErrorText Properly . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 25Use Exception Information . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 26

Purpose of Exception HandlingException Information in eScriptException Information in Siebel VB

Place Return Statements Correctly: eScript . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 28Centralize Browser Script Using the “Top” Object . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29

SIEBEL SYSTEMS, INC. 3 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 4: technote514-1 scriptingbestpractices

SIEBEL SCRIPTING BEST PRACTICES MARCH 23, 2004

Know When to Use the Current Context versus a New Context in Server Script. . . . . . . 31Difference Between Current and New ContextGuidelines for Choosing Context

Use Smallest Possible Scope for Variables . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33Instantiate Objects Only As Needed . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34Destroy Object Variables When No Longer Needed . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 35Use Conditional Blocks To Run Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 36Verify Objects Returned . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 37

Verify Object Returned is Expected OneActiveBusObjectActiveBusCompParentBusComp

Verify Field is Active before Use . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39Leverage New Methods in Siebel 7. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 40

New MethodsUse Proper View Mode For Queries . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43Query Only Indexed Columns . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 44Use ForwardOnly Cursor Mode. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 45Verify Existence of Valid Record After Querying . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 46Use Switch or Select Case Statements . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 47Compare the Same Condition In If/Else If . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 48Use the Associate Method to Create Intersection Table Records . . . . . . . . . . . . . . . . . . . . 49Use Dynamic Values . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 50Use Logical Constants versus Literal Values . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 51Avoid Exit Function and Exit Sub . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 52Place GotoView at the End of a Script . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 53Use DeleteRecord Method Properly . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54

PROPRIETARY & CONFIDENTIAL 4 SIEBEL SYSTEMS, INC.DUPLICATION PROHIBITED EMPLOYEE EDUCATION

Page 5: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Scripting FundamentalsScripting: Where to Begin

Basic Process Flow

This flowchart outlines the basic process for developers to follow when writing script.

The objective is to minimize script—writing it only when necessary, and writing it once!

SIEBEL SYSTEMS, INC. 5 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 6: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Basic Process Flow

1. Explore Declarative Configura-tion Alternatives

Before writing any script, developers should explore all declarative configuration alternatives. This is an important step! It ensures that developers write script only when there is no configuration alternative, thus minimizing the amount of script.

2. Determine Where to Put the Script: Which Object?

After determining that the solution requires script, developers must determine where to put the script. A utility script that will be called from many locations such as applets, business components, and business services, is best implemented as a business service. This enables developers to write the script once for use by many objects.

An alternative to writing a business service is to write the method at the application level. Siebel Systems encourages developers to use business services, as they can be called by workflow processes; workflow processes cannot call custom application level methods.

If the method deals with data in a specific business component, that business component is the most likely object for the script. Writing script at the business component level prevents developers from having to re-write it on applets that leverage the same underlying business component. This only makes sense if the method is specific to a particular business component. If the same script is seen in many business components with only slight differences, move the script to a business service and parameterize it.

If the method controls the behavior of an applet, for example, if it is enabling a button or hiding/showing list columns or controls, write the script at the applet server level.

If the method facilitates interaction with the client’s desktop or communication with the user, make the script an applet browser script.

3. Determine Where to Put the Script: Which Event?

After determining the appropriate object, developers must determine the appropriate event within that object.

Business componentThere are two ways to think of scripting a business component: proactively and reactively. If you need to perform some sort of validation, but do not need to change data in any record other than the current record, use the Pre- event (for example, PreQuery, PreSetFieldValue, PreWriteRecord). This is a proactive approach: you are trying to stop or modify something the user is doing before it gets too far.

Continued on next page

SIEBEL SYSTEMS, INC. 6 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 7: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Basic Process Flow, Continued

3. Determine Where to Put the Script: Which Event? Continued

Never use Pre- events to change data in a record other than the current record. The Pre- event occurs before the Siebel application runs its own field-level validations and other processes in the underlying C++ class that might fail. If these processes fail, the Siebel application exits the Pre- event and does not roll back any changes to other objects. This could leave the application in an inconsistent state.

To perform further processing after a change has been applied, for example, after the application writes a record, implement a reactive script. A reactive script typically applies to the WriteRecord event. This is quite often a workflow process or some sort of integration. When taking a reactive approach, it is acceptable to manipulate data in records other than the current record.

AppletMost scripting for applet browser functionality will originate in the Applet_PreInvokeMethod event. This is where developers can trap methods invoked on an applet. Methods that interact with the user’s desktop, the user, or how the applet looks, should originate in this event. Siebel Systems recommends not putting all of the method code in the Applet_PreInvokeMethod event. Rather, create custom methods and call those methods from this event.

If the method accesses data in a record other than the current record or active business component, write a server script in the WebApplet_PreInvokeMethod event. If the method deals with data specific to the business component, then the business component is the appropriate place for the method. If, however, the method deals with something specific to the applet, write the script on the applet. Remember that you are trying to reduce the amount of script written.

Business ServiceThis is the best place to write script that will be called from anywhere. Ideally, write a method that can accept parameters to operate for a wide range of needs. This eliminates the need to duplicate code across objects and events, significantly simplifying maintenance efforts. Duplicating script is a common problem which frequently leads to thousands of pages of script! Since any script, even browser script, can call a business service, it is an ideal location for many situations. Siebel Systems recommends not putting all of the method script in the Service_PreInvokeMethod. Rather, break it into smaller scripts that the Service_PreInvokeMethod event of a business service can call.

Continued on next page

SIEBEL SYSTEMS, INC. 7 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 8: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Basic Process Flow, Continued

3. Determine Where to Put the Script: Which Event? Continued

The ApplicationThis is a good place for methods that need to fulfill the needs of many disparate calling scripts (as is a Business Service, as stated earlier). When to use TheApplication event instead of a Business Service will depend on your requirements.

While application-level scripts do centralize methods, they have limited visibility: application-level browser script may only be called by other browser scripts, and application-level server script only works for server scripts. Workflow processes cannot access methods defined at the application level. Therefore, if requirements dictate that methods be visible to both server and browser script, or to workflow processes, implement the functionality as a business service.

4. Add Error Handling Template

Put an error/exception handling strategy in place before writing any script. This includes creating an error handling template that you can apply to all scripted events. Applying the error handling skeleton to a method before writing the method, assures two things:• error handling is present and• future manipulation of the method will not cause a runtime error that

goes unnoticed.

5. Add Method Body

Now you are ready to write the actual method. “Sandwich” this code within the error handling code, so that you can catch any runtime errors.

6. Test This is the last and most important step of scripting. Make sure the tests are complete, covering all possible conditions. Failure to test completely results in more wasted time later trying to track down a bug.

SIEBEL SYSTEMS, INC. 8 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 9: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Scripting Best PracticesWhen to Use Scripting

Use Scripting as a Last Resort

Do not write script if there is a way to implement the required functionality through configuration. Declarative configuration is easier to maintain and upgrade, leading to a lower total cost of ownership.

Before writing any script, Siebel Systems highly recommends that you review the media-based training (MBT) titled Declarative Alternatives to Siebel Scripting. For more information about this MBT, log on to Siebel University at http://siebeluniversity.siebel.com.

Preferred alternatives to scripting include• Field validation• User properties• Workflow• Personalization• Run-time events• State model

SIEBEL SYSTEMS, INC. 9 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 10: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Follow Standard Naming Conventions

Have the project team agree upon a standard way of naming variables so that the scope and data type are identified easily. This significantly simplifies maintenance and troubleshooting efforts.

Data types

Scope

Data Type Prefix

Integer I

String S

Boolean B

Float f

Scope Modifier

Global Scope (only applicable for Siebel VB)

G_

Module/Instance Scope M_ or i_

Function or Local Scope No modifier or l_

SIEBEL SYSTEMS, INC. 10 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 11: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Comment Code

Commenting code is a very good practice to explain the business purpose behind the code. At the onset of a project, project teams should agree upon standard commenting practice to ensure consistency, and simplify the maintenance effort.

Include a comment header at the top of a method with an explanation of the code and revision history. Strictly maintain these headers so that they accurately reflect the script that they describe. If you do not maintain them along with the code, eventually they become confusing, misleading, or incorrect.

As well as adding a comment header, comment lines that perform non-standard or complex behavior.

Example of comment header:

'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

' Name: MyProcedure()

' Module: BusComp [Account]

' Arguments:

' oBC1BusComp BusComp for ABC (positioned)

' oBC2BusComp BusComp for XYZ (not yet' positioned)

'

' Return Value: Integer ContinueOperation -> Relationship is' OK' CancelOperation -> Relationship is' not OK

'

' Used Globals: gintCheckIt Set to 1 in' [Quote].[BusComp_ChangeRecord]' Evaluated and Reset here

'

' Static Vars: mintChecked Set to 0 in [Account]. ' [BusComp_ChangeRecord]' Evaluated and Set to 1 here

'

' NOTE: Procedure might be called recursively!!!

' History

Continued on next page'

SIEBEL SYSTEMS, INC. 11 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 12: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Comment Code, Continued

' Date AuthorPurpose

' 8/14/03SBoetigOriginal Creation

'

' Description: This procedure contacts Webline and retrieves ' a bunch of data that is stored on the ' Action BC in Siebel to maintain a sort of ' audit record.

''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

SIEBEL SYSTEMS, INC. 12 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 13: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Know When to Use Browser versus Server Script

Browser script is recommended for:• Communication with the user• Interaction with desktop applications• Data validation and manipulation limited to the current record

Server script is recommended for:• Query, insert, update, and delete operations• Access to data beyond the current record

SIEBEL SYSTEMS, INC. 13 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 14: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Place Code in the Correct Event Handler

One of the most common issues identified during script reviews is the inappropriate use of object events. Placing code in the wrong event handler can lead to corrupt data and may negatively impact performance.

Do not use Siebel application Pre- events (such as PreQuery, PreSetFieldValue, and PreWriteRecord) to manipulate data in objects other than the one hosting the script. (See “3. Determine Where to Put the Script: Which Event?” on page 6 for more information). The companion events, such as Query, SetFieldValue, and WriteRecord, occur after the internal and field-level validations succeed, and therefore are the appropriate events for such manipulation. For example, the WriteRecord event fires after the record writes successfully. When this event fires, you know that the record exists; therefore it is safe to create or modify data in other objects, without fearing orphaned records or an inconsistent state of the application.

eScript examplesBusComp_PreSetFieldValue Field level validation

BusComp_PreWriteRecord Record level validation

BusComp_SetFieldValue Field triggered actions

BusComp_WriteRecord Record triggered actions

Example: synchronizing two business components or creating activities

BusComp_PreQuery Code control over SearchSpecs

SIEBEL SYSTEMS, INC. 14 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 15: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Fast Script In Event Handlers that Fire Frequently

Avoid placing complex code in event handlers that fire frequently, such as BusComp_PreGetFieldValue, as it may degrade application performance.

The PreGetFieldValue event fires at least once for every field that is retrieved. This can amount to hundreds of calls to the event in rapid succession. Complex script in this event handler significantly degrades application performance.

Developers typically use script in the PreGetFieldValue event to return a value other than the one in the database. As an alternative, developers can use a calculated field. The calculated field holds the display value and the calculation performs the logic. In this case, the Siebel application exposes the calculated field, not the actual field, to the user.

For other frequently fired events, look for a configuration alternative, and if none is available, make the script as simple as possible. One alternative for complex calculations is to create a calculated field that uses the InvokeServiceMethod function. More detail on this function and its suggested use can be found in the Siebel Bookshelf.

SIEBEL SYSTEMS, INC. 15 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 16: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Runtime versus Compiled Business Services

Business services may be defined in Siebel Tools and compiled with the .srf file, or created as runtime business services in the client user interface. The decision on whether to make a business service compiled or runtime has no hard and fast rules. It ultimately depends on what you intend the service to do and how frequently you expect the code in the business service to change.

Runtime business services are not compiled into the .srf file. The database stores them as records and you can change them at any time. The next time a runtime service executes, it uses the changes to the definition. This makes them useful for logic that changes frequently and logic that you need to change without deploying a new .srf file. The drawback to a runtime business service is that anyone with access to the view can see the code. This can pose a security problem.

Runtime business services can be useful in a development environment to test frequent changes to scripts by using the business service simulator. Since no compiling is required, code development may be faster in the runtime environment. Once the code is complete and tested through the simulator, the developer can choose whether the business service should remain as a runtime service or if it should be migrated to Siebel Tools.

Compiled business services are defined in Siebel Tools and represent a functionality that needs more security and is not likely to change. You must compile and implement a new .srf file to implement any changes. Because these business services are compiled, they provide more security than runtime services and they are faster to load.

Note: If you define a business service called MyService as a runtime business service and as a compiled business service, the compiled version executes and the runtime version is ignored. For clarity, if you migrate a business service from a runtime version to a compiled version, you should inactivate or delete the runtime version so that it is clear to all developers that the runtime version is no longer being used.

SIEBEL SYSTEMS, INC. 16 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 17: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Option Explicit

Include the Option Explicit in the <general> <declarations> section of every object containing Siebel VB code.

Option Explicit requires that you explicitly declare every variable. The compiler returns an error if the Siebel application uses a variable before declaration; thus simplifying debugging efforts.

Without Option Explicit, the Siebel application defines and dimensions variables on the fly.

Example: if you defined a variable called ls_description, and later reference the variable as ls_dscription (missing an ‘e’), Option Explicit catches that a variable is being used that has not been defined. Without Option Explicit, the application defines a new variable as ls_dscription.

Since Option Explicit only evaluates during compile time, there is no performance impact.

SIEBEL SYSTEMS, INC. 17 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 18: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Leverage Appropriate Debugging Techniques

Debugging Siebel Applications

It is essential that you understand how to debug Siebel applications. There are four basic techniques:• Use alerts or RaiseErrorText methods to pop up message boxes• Write to a file using Trace or custom methods• Use the Siebel Debugger• Use object manager level logging

Alert and RaiseError-Text

The alert method in browser script and the RaiseErrorText method in server script enable you to display message boxes to the user.

The RaiseErrorText method stops the execution of a script; therefore, it is only appropriate for a quick check of something and is not a good way to debug scripts where the source of the error is hard to determine.

Alerts do not stop the execution of browser scripts and therefore are a quick and easy way to debug browser scripts.

Writing to a Text File

The most common way to debug a script is to write information to a text file. Accomplish this using the Trace function or an Siebel VB or eScript function. Using Trace, you can write the actual SQL to a file.

Using the Debugger in Siebel Tools

This is a useful tool for visually stepping through the code and looking at the values of variables real time. You can set break points anywhere until you isolate a problem.

Using Object Manager Settings

When an application is in production, it is not always possible to add debugging statements to script. In this situation, developers or systems administrators can change settings in the object manager to trace events and SQL.

Defined in the Component Parameters View:• OM - EL Tracing User Name: a comma separated list of logins to trace (for

example, SADMIN)• OM - Trace EL Allocation: traces object memory allocation (Set to 1)• OM - Trace EL Events: traces which events are triggered (Set to 1)• OM - Trace EL SQL: traces the SQL generated by script (Set to 1)

Continued on next page

SIEBEL SYSTEMS, INC. 18 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 19: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Leverage Appropriate Debugging Techniques, Continued

Using Object Manager Settings Continued

Defined in the Component Event Configuration View:• Object Manager Extension Language Log: enables the scripting to be

logged (Set to 1)

This graphic shows the two locations in the Siebel client application where object manager logging is turned on.

For the log level changes to take effect immediately, modify the Current Value parameter.

SIEBEL SYSTEMS, INC. 19 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 20: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Remove Unused Code from the Repository

Remove code that is:• Commented out• Set to Inactive • Never called

If you want to keep a record of obsolete code before removing it, you can do an export from Siebel Tools to save a copy of the script. To export a script to a text file, open the script editing window for the object in question, then choose File > Export. The script for all methods on that object will be exported to a file of type .js if the script is written in eScript, or .sbl if it is written in Siebel VB.

Alternatively, you can create an archive file, of file type .sif, with the object containing the script. Archive files contain all property definitions for the object, whereas a .js or .sbl file only contains the script.

Remove Empty MethodsExample of empty method in Siebel VB

Sub Application_Start (CommandLine As String)

End Sub

The event handler for an empty method shows up as Active in Siebel Tools. This can be confusing to developers who think the event is scripted due to its Active status. Also, empty methods can cause a small performance hit as the interpreter may run through the event handler unnecessarily.

SIEBEL SYSTEMS, INC. 20 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 21: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Include Error Handling in All Scripts

Proper Error Handling

Proactive handling of errors or exceptions significantly streamlines debugging. Without proper error handling, users may receive run-time errors from the interpreter, which are difficult to understand.

Proper error handling:• Returns custom error messages that are easier for the user or developer to

interpret• Is “bulletproof”, covering all methods that access Siebel Objects, external

COM objects or the OS

Error Handling in eScript

Implement eScript error handling through the try/catch/finally mechanism.• Try block: contains the logic that you want performed.• Catch block: captures the error.• Finally block: performs any cleanup work such as destroying object

references.

Example: function illustrateErrorHandling()

{

try

{

/*The try block encompasses all statements that

could cause an exception. */

...executable code goes here...

}//end try

The try keyword precedes a block of normal processing code that may throw an exception.

Continued on next page

SIEBEL SYSTEMS, INC. 21 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 22: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Include Error Handling in All Scripts, Continued

Error Handling in eScript Continued

catch(e)

{

if(defined(e.errText))

{

TheApplication().RaiseErrorText(“An exception occurred ” +

“in the “ + arguments.callee +

“ of the “ + this.Name() + “ object. “ +

“ERROR: ” + e.errText +

“STACK: ” + e.toString());

}

else

{

TheApplication().RaiseErrorText(“An exception occurred ” +

“in the “ + arguments.callee +

“ of the “ + this.Name() + “ object. “ +

“ERROR: ” + e.toString());

}

}//end catch

The catch keyword precedes a block of exception handling code. After a try block throws an exception, control over the program flow switches to the first catch block following it.

Use two methods to avoid hard coding the object and method names.• arguments.callee substitutes the method name in which the code is

running.• this.Name() substitutes the object name in which the script is running.

Using these methods allows developers to copy this catch block into any eScript server script routine without changing it at all.

Continued on next page

SIEBEL SYSTEMS, INC. 22 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 23: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Include Error Handling in All Scripts, Continued

Error Handling in eScript Continued

finally

{

// This block will always be called whether an exception is

// thrown or not.

// put the cleanup code here, for example:

bcContact = null;

boAccount = null;

}

The finally block always executes, so it is an ideal location for the final release of resources.

Error Handling in Siebel VB

There are two strategies for handling unexpected runtime errors in Visual Basic:1. On Error Goto <label>: traps runtime errors in the Err object and

transfers control immediately to the label specified. It can perform code cleanup and write the error parameters to a log file, after which the procedure may gracefully exit and inform the user of the error condition.

2. On Error Resume Next: traps the runtime error in the Err object and continues right along as though nothing happened. This is a dangerous form of error handling because it essentially ignores all errors. If no error handling is done immediately after Err object detects an error, it will continue processing as if nothing happened.

Siebel Systems recommends using On Error Goto <label> unless there is a compelling reason to use Resume Next.

Continued on next page

SIEBEL SYSTEMS, INC. 23 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 24: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Include Error Handling in All Scripts, Continued

Error Handling in Siebel VB Continued

Example of On Error Goto <Label>

Sub illustrateExceptionHandling()

‘In the event of an error, processing will immediately‘transfer to the label “errorhandler”

On Error GoTo errorhandler

‘Place code here that may experience an error

Dim lBO_test As BusObject

Dim lBC_test As BusComp

Set lBO_test = TheApplication.GetBusObject(“Account”)

Set lBC_test = lBO_test.GetBusComp(“Account”)

errorhandler:

Set lBC_test = Nothing

Set lBO_test = Nothing

If Err <> 0 Then

TheApplication.RaiseErrorText “An error has occurred ”& _

“illustrateExceptionHandling method ” & Chr$(13) & _

"object. " & Chr$(13) & _

"Error number: " & Err & Chr$(13) & _

"Error text: " & Error$ & Chr$(13) & _

"Error line: " & Erl

End If

Notice the use of Err object and Error function in the Application.RaiseErrorText function to retrieve error code and error text. Use the if condition to make sure that the Siebel application enters this error handling block only if an error occurred. Whether created by developers in the script above, raised by a function called in the script above, or created by the Siebel application because of some runtime condition, the Err variable will not contain zero.

SIEBEL SYSTEMS, INC. 24 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 25: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use RaiseError and RaiseErrorText Properly

In Siebel 7, developers sometimes use RaiseError and RaiseErrorText to display message boxes via script; however, these methods do not serve the same purpose as the MsgBox method, which was available in version 6.x and earlier. RaiseError and RaiseErrorText methods generate a server script exception causing the script to stop executing at that point. Therefore, it is important to place any code that must execute before calls to these methods.

SIEBEL SYSTEMS, INC. 25 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 26: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Exception Information

Purpose of Exception Handling

Do not ignore exceptions. Ignoring them can cause other runtime errors to occur.

It is the duty of the exception handling to• Catch exceptions• Stabilize the application• Log exception information or notify the users of what happened• Possibly, re-throw the exception• Possibly, set a return code

Exception Information in eScript

In eScript, the exception object stores error information in the:• errText attribute: exception.errText

• Populates when the Siebel application encounters an error during runtime or when the developer raises an exception using RaiseErrorText.

• toString() method: exception.toString()• Provides exception information from a COM object or from an

exception thrown by the developer using the throw statement.

There are two types of information:• Error description: the description of what went wrong.• Stack trace: the list of methods in the order in which they executed up to

the line where the exception occurred.

In eScript, you can obtain the method name dynamically from a native property of the method called “arguments”. This is an array of parameters specific to the method being invoked.

Example:if(defined(e.errText))

{

TheApplication().RaiseErrorText(“An exception occurred ” +

“in the “ + arguments.callee + “ of the “ + this.Name()

+ “ object. “ + “ERROR: ” + e.errText + “STACK: ”

+ e.toString());

}

else

{

TheApplication().RaiseErrorText(“An exception occurred ” +

in the “ + arguments.callee + “ of the “ + this.Name()

+ “ object. “ + “ERROR: ” + e.toString());

}

Continued on next page

SIEBEL SYSTEMS, INC. 26 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 27: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Exception Information, Continued

Exception Information in Siebel VB

In Siebel VB, the Err object stores the error information. Because Siebel VB does not include properties that store the method name, you must hard code the method name in the string passed to the RaiseErrorText method.

Example:

If Err <> 0 Then

TheApplication.RaiseErrorText "An error has occurred " & _

“illustrateExceptionHandling method ” & Chr$(13) & _

"in the " & Me.Name & _

" object. " & Chr$(13) & _

"Error number: " & Err & Chr$(13) & _

"Error text: " & Error$ & Chr$(13) & _

"Error line: " & Erl

End If

SIEBEL SYSTEMS, INC. 27 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 28: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Place Return Statements Correctly: eScript

A return statement in the finally clause of a try/catch/finally block suppresses any exceptions generated in the method or thrown to the method. These exceptions will not make it out of the method. When code in the finally clause causes an exception, the exception information makes it out of the method, but the original exception information is lost.

Ensure that the method itself contains the return statement. A method takes input, does something, and then returns a value, null, or an exception.

Example:function illustrateReturnStatement()

{

var myVar;

try

{

//executable code goes here

myVar = 1;

}

catch(e)

{

if(defined(e.errText))

{

TheApplication().RaiseErrorText("An exception occurred " +

"in the " + arguments.callee +

" of the " + this.Name() + " object. " +

"ERROR: " + e.errText +

"STACK: " + e.toString());

}

else

{

TheApplication().RaiseErrorText("An exception occurred " +

"in the " + arguments.callee +

" of the " + this.Name() + " object. " +

"ERROR: " + e.toString());

}

}//end catch

finally

{

//cleanup code goes here

}

return myVar;

}

SIEBEL SYSTEMS, INC. 28 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 29: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Centralize Browser Script Using the “Top” Object

In browser script, top is a shortcut to the top level document. Using the top object, developers can write a browser script function once and call it from anywhere within the browser aspect of objects.

Note: Scripted objects have a server side aspect which can only call server script and a browser side aspect which can only call browser script. Thus the top object, being a browser script object, can only be referenced from browser script. This is useful for any function which needs to interact programmatically with a client application or desktop, that would also need to be called from multiple places in the application.

The following example provides a logging function in the top object:1. Assign a pointer for the method to the top object:

• Include Top in (general) (declarations) of Application object top.log = trace_log;

This step assigns a function pointer to the top window object of the application, which any browser script can use.

2. Implement the method at the application levelfunction trace_log(as_text)

{

...include trace logic here.

{

After adding the function to the (general) (declarations) section, you will see it appear as a separate function in the script window, as shown below:

Continued on next page

SIEBEL SYSTEMS, INC. 29 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 30: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Centralize Browser Script Using the “Top” Object, Continued

3. Call the method from any browser script.

SIEBEL SYSTEMS, INC. 30 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 31: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Know When to Use the Current Context versus a New Context in Server Script

Difference Between Current and New Context

• Current (or UI) context deals with objects that the Siebel application created to support data that are currently available to the user.

• New (or Non-UI) context is a set of objects instantiated in script that have no tie to any objects or data that the user is currently viewing.

Keeping these two straight is important because the user may see programmatic manipulations of data if you use the wrong context. For example, consider a script running in any event of the Contact business component that needs to get a reference to the Contact business component to do a comparison or lookup.

This code returns a reference to the current instance of the Contact business component:

bc = this.BusObject().GetBusComp(“Contact”);

If this code is executed while a user is watching the user interface, the user sees any programmatic manipulations of the data.

Equivalent ways of getting a reference to the current Contact business component instance arebc = TheApplication().ActiveBusObject().GetBusComp(“Contact”);

bc = this;

To prevent users from seeing data manipulation that the script does, create a new, or non-UI, instance of the Contact business component.bo = TheApplication.GetBusComp(“Contact”);

bc = bo.GetBusComp(“Contact”);

The difference here is the business object. Since all business components live within an enclosing business object’s context, it is the business object that makes the difference. In this previous code example, the application created a new instance of the Contact business object, enabling data manipulation to occur outside of the current context.

Note that when the current record is instantiated and modified in a non-UI context instance, the warning message “The selected record has been modified by another user since it was retrieved” will be displayed to the user. This message appears because the script has modified the current record, and a refresh is necessary for the user to see the current field values. Therefore, if the script is going to update the current record, it may be preferable to use the UI context to avoid this message.

Continued on next page

SIEBEL SYSTEMS, INC. 31 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 32: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Know When to Use the Current Context versus a New Context in Server Script, Continued

Guidelines for Choosing Context

• Use the current context to• Access data with which the user is currently working• Perform processing that should be visible to the user

• Use a new context to• Invisibly query a visible business component• Use a business component in a different business object context

SIEBEL SYSTEMS, INC. 32 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 33: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Smallest Possible Scope for Variables

Developers frequently create instance level variables that can be accessed by many methods within an object. This is done at the application level so that any script can access the objects. While this is good for the purposes of instantiating an object only once, it is a bad practice for four reasons.1. Rules of encapsulation are usually violated.2. Scripts often step on each other.3. There is no event that guarantees that the objects are always destroyed. 4. It is difficult to “understand” the scope or state of variables, because they

are instantiated in one method and accessed in others.

It is far better to declare and use objects where they are needed and pass them as parameters to other methods.

SIEBEL SYSTEMS, INC. 33 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 34: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Instantiate Objects Only As Needed

Create object instances on an as-needed basis. Create object instances that are needed based upon the outcome of an evaluation after that evaluation. Otherwise, your code may create unused object instances that can negatively impact performance.

Correct order1. Evaluate condition2. Create objects3. Use objects

Incorrect order1. Create objects2. Evaluate condition3. Use objects

SIEBEL SYSTEMS, INC. 34 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 35: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Destroy Object Variables When No Longer Needed

Memory leaks are a common problem, so when a script creates an object reference, that same script must destroy the object reference before leaving the method.

Object references are:• COM objects• Property Sets• Business Services• Business Components• Business Objects• Applets

In eScript, destroy an object by setting it to null (oBC = null). In Siebel VB, destroy an object by setting it to nothing (Set oBC = Nothing).

Release objects in the reverse order in which the Siebel application created them; child objects first, parent objects second.• Pick/Associate/MVG business components before the parent business

component• Business components before business objects• No specific order for property sets and business services since they are

independently created from the application

Tightly couple object destruction with error handling to ensure that the Siebel application destroys objects in success and in failure. Therefore, destroy objects in the finally clause as this clause always executes, regardless of whether the method exits successfully or with errors.

finally

{

ChildObject = null;

ParentObject = null;

}

SIEBEL SYSTEMS, INC. 35 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 36: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Conditional Blocks To Run Code

Just as objects should be instantiated only as needed, code should be run only as needed.

A typical example is in the BusComp_PreSetFieldValue event. Code in this event is usually associated with a specific field, not all fields. Check which field the code is modifying before going any further.

Example:function BusComp_PreSetFieldValue(FieldName, FieldValue)

{

switch(FieldName)

{

case “Status”:

…do something…

break;

}

}

SIEBEL SYSTEMS, INC. 36 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 37: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Verify Objects Returned

Verify Object Returned is Expected One

Always verify that the object returned is the one expected, especially when calling methods such as ActiveBusObject, ActiveBusComp, and ParentBusComp.

ActiveBus-Object

ActiveBusObject returns the business object for the business component of the active applet. When a business component can be the child of more than one business object, check which object is actually returned from a call to this method.

ActiveBusObject only makes sense if used in a script running in the application object or in a business service. Script running in an applet or in a business component should use:

• Me.BusObject (in an applet and in a business component)• this.BusObject(); (in an applet and in a business component)

eScript Example:if(TheApplication().ActiveBusObject().Name() == “some name”)

{

…code here…

}

Siebel VB Example:If TheApplication.ActiveBusObject.Name = “some name” Then

…code here………

End If

ActiveBus-Comp

ActiveBusComp returns the business component associated with the active applet. When running script outside of a business component, verify the active business component with a call to this method.

ParentBus-Comp

ParentBusComp returns the parent business component when given the child business component of a link. Always make sure that a business component reference obtained with the ParentBusComp method is valid and is the one expected. Two situations could cause no reference to return:

• The business component is the parent and has no parent, such as the Account business component in the Account business object.

• The link that established a parent/child relationship in the business object has been removed or changed.

Continued on next page

SIEBEL SYSTEMS, INC. 37 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 38: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Verify Objects Returned, Continued

ParentBus-Comp Continued

If no reference is returned from ParentBusComp, no error is thrown. However, calling methods or referencing attributes on a null object will result in a runtime error. Therefore, always verify the reference returned when calling ParentBusComp.

eScript Examplevar lBC_parent = this.ParentBusComp();

if(lBC_parent != null && lBC_parent.Name() == “some name”)

{

……code……

}

Siebel VB ExampleSet lBC_parent = Me.ParentBusComp

If Not lBC_parent Is Nothing And lBC_Parent.Name = “some name” Then

………code……

End If

In this example, the script is verifying that there is a reference before getting the Name attribute.

SIEBEL SYSTEMS, INC. 38 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 39: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Verify Field is Active before Use

Calling GetFieldValue or SetFieldValue on an inactive field may lead to lost data or logic going astray.

Server script field is Active if• System field (Id, Created, Created By, Updated, Updated By)• LinkSpec property on BC set to TRUE• Force Active property on BC set to TRUE• Included in applet definition on active view• Used in calculation of calculated field on active applet• Explicitly activated using BusComp.ActivateField (strFldName)

Browser script field is Active if• Id field• Fields visible in the UI

Only use ActivateField if an ExecuteQuery statement succeeds it. As a standalone statement, ActivateField will not implicitly activate a non-activated field. ActivateField tells the Siebel application to include this database column in the next SQL statement it executes on the business component which just had a field activated.

Example:Incorrect Use

ActivateField(<Name>);⇓Incorrect use! The BC is not queried after this.

GetFieldValue(<Name>);

Correct Use

ActivateField(<Name>);

ExecuteQuery(ForwardOnly);

GetFieldValue(<Name>);

SIEBEL SYSTEMS, INC. 39 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 40: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Leverage New Methods in Siebel 7

New Methods ActivateMultipleFields, GetMultipleFieldValues, and SetMultipleFieldValues are new methods in Siebel 7. These methods are best used when accessing Siebel applications through COM, Java, C++, CORBA, and the Mobile/Dedicated Web Client Automation Server. Using these methods can help reduce redundant lines and make the program more readable.

Examplevar lbc_account = this;

var lPS_FieldNames = TheApplication().NewPropertySet();

var lPS_FieldValues = TheApplication().NewPropertySet();

var ls_account_products;

var ls_agreement_name;

var ls_project_name;

var ls_description;

var ls_name;

//set up the property set which will be used in all three

//methods to hold the field names.

lPS_FieldNames.SetProperty("Account Products", "");

lPS_FieldNames.SetProperty("Agreement Name", "");

lPS_FieldNames.SetProperty("Project Name", "");

lPS_FieldNames.SetProperty("Description", "");

lPS_FieldNames.SetProperty(“Name", "");

//activate the fields using the property set which has the //field names

lbc_account.ActivateMultipleFields(lPS_FieldNames);

Continued on next page

SIEBEL SYSTEMS, INC. 40 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 41: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Leverage New Methods in Siebel 7, Continued

New MethodsContinued lbc_account.ExecuteQuery(ForwardOnly);

if (lbc_account.FirstRecord())

{

//retrieve the values. This method acts sort of like a business

//service in that there is an input property set and an output

//property set. The field values will be in the second property set //passed in.

lbc_account.GetMultipleFieldValues(lPS_FieldNames,lPS_FieldValues);

//loop through property set to get values.

ls_account_products = lPS_FieldValues.GetProperty("Account Products");

ls_agreement_name = lPS_FieldValues.GetProperty("Agreement Name");

ls_project_name = lPS_FieldValues.GetProperty("Project Name");

ls_description = lPS_FieldValues.GetProperty("Description");

ls_name = lPS_FieldValues.GetProperty("Name");

}

//now set new values in the property set

lPS_FieldNames.SetProperty("Account Products", "All My Products");

lPS_FieldNames.SetProperty("Agreement Name", "Siebel Agreement");

lPS_FieldNames.SetProperty("Project Name", "Siebel Project #2");

lPS_FieldNames.SetProperty("Description", "This is the description");

lPS_FieldNames.SetProperty(“Name", "Joey Joe Joe Junior Shabbidoo");

//set the field values

lbc_account.SetMultipleFieldValues(lPS_FieldNames);

//commit the data

lbc_account.WriteRecord();

}

Continued on next page

SIEBEL SYSTEMS, INC. 41 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 42: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Leverage New Methods in Siebel 7, Continued

New MethodsContinued In this example, the code creates lPS_FieldNames to hold the field names and

lPS_FieldValues to hold the field values.

After setting the value using the SetProperty method, invoke ActivateMultipleFields and the Siebel application passes the property set in as parameter.

After calling the ExecuteQuery method, invoke GetMultipleFieldValues to get the field values. If you did not use GetMultipleFields and ActivateMultipleFields, you would have to individually activate or get each of the field values.

Notice the use of SetMultipleFieldValues here. If you did not use SetMultipleFieldValues, you would have to individually set the field values.

SIEBEL SYSTEMS, INC. 42 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 43: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Proper View Mode For Queries

View mode settings control the formulation of the SQL WHERE clause that the Siebel application sends to the database by using team or position visibility to limit the records available in the business component queried in the script.

Setting a query to AllView visibility mode gives the user access to all records, which may be different than the view mode of the current view in the UI. For example, a user may have SalesRep visibility on the UI whereas the script will be giving the user All visibility. This would give the user access to records the user might not need to access, or should not be able to access.

Setting view mode is especially important in an environment with mobile Web client users. Mobile users have a subset of data in their local databases. If you do not set the view mode correctly for limited visibility objects, unexpected behavior can occur, such as resetting foreign keys. For example, the application may set the Primary ID to No Match Row ID if a child record does not exist on the local database. This update has the potential to synchronize back up to the server, causing a data integrity problem.

To avoid this issue, use the GetViewMode method to determine the user’s visibility so that you can apply the same view mode in the query executed by the script.

eScript Example:with (bcAcct)

{

SetViewMode(this.GetViewMode());

Siebel VB Example:With bcAcct

.SetViewMode Me.GetViewMode

SIEBEL SYSTEMS, INC. 43 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 44: technote514-1 scriptingbestpractices

SIEBEL SCRIPTING BEST PRACTICES MARCH 23, 2004

Query Only Indexed Columns

To assist the database engine in efficiently retrieving and sorting data, be sure that search and sort specs reference indexed columns whenever possible. Sorting or searching on non-indexed fields can have detrimental effects on database performance, especially on large tables, as it produces table scans and temporary tables in the SQL execution plan. This is true of search and sort specifications that developers create in script, just as if they created them using configuration.

For best performance, ensure that such specifications cover the key columns of the desirable index, as well as cover them in the exact index sequence order. This encourages the database engine to use the index and may prevent unnecessary physical sorts in temporary tables.

PROPRIETARY & CONFIDENTIAL 44 SIEBEL SYSTEMS, INC.DUPLICATION PROHIBITED EMPLOYEE EDUCATION

Page 45: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use ForwardOnly Cursor Mode

If you do not specify a cursor mode when querying with Siebel eScript or Siebel VB, the Siebel application uses the default cursor mode of ForwardBackward. To support this cursor mode, the system creates a cache to maintain the entire record set.

If you will traverse through the record set from FirstRecord using NextRecord and will not return to a previous record, use ForwardOnly cursor mode. The system will not need to create the cache, improving performance. This is particularly true if you perform a look up or if you access a pick list.

Example:bcAccount.ExecuteQuery(ForwardOnly);

SIEBEL SYSTEMS, INC. 45 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 46: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Verify Existence of Valid Record After Querying

When performing a query, always check that a record is returned through the use of FirstRecord, NextRecord, or LastRecord methods, before attempting to retrieve or set a field value for the record. Do this even if it seems impossible that a record will not return.

Example:bcContact.ClearToQuery();

bcContact.SetSearchSpec(“Id”, sContactId);

bcContact.ExecuteQuery(ForwardOnly);

//Check to see that a record was actually returned

//by examining the return of FirstRecord().

if (bcContact.FirstRecord())

{

//okay to perform data processing…

}

SIEBEL SYSTEMS, INC. 46 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 47: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Switch or Select Case Statements

When you need to evaluate and compare a single expression with many different possibilities, the fastest and most readable way of doing this is to use switch (eScript) or select case (Siebel VB).

• It is more efficient because the expression is evaluated once, then compared to different values.

• It is easier to read than a series of nested if…else if statements. Using switch or select case statements can frequently compact multiple pages of script into a single page.

When using switch or select case, be sure to test all conditions, not just the most obvious ones. Logic errors can occur in code that does not consider all possible conditions. Consider using default or case else to hold a default set of behaviors that should occur if none of the stated conditions is met.

eScript Example:

Tip: In eScript, the keyword break is necessary to end a particular case. Otherwise, code falls through to the next case without stopping. Siebel VB does not require a break statement. Reaching the next keyword case will end the previous case.

Instead of Use

If(iNum == 1)sGrade = ‘A’;

else if(iNum ==2)

sGrade = ‘B’; else

if(iNum == 3)sGrade = ‘C’;

switch(iNum){ case 1: sGrade = ‘A’; break; case 2: sGrade = ‘B’; break; case 3: sGrade = ‘C’;}

SIEBEL SYSTEMS, INC. 47 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 48: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Compare the Same Condition In If/Else If

Verify that if/else if conditions compare a single expression. Otherwise, more than one case could be true at the same time, but only one condition will execute. If/else if blocks evaluate every condition until the first one evaluates to true. Then that condition executes and the code ignores the others.

Example:var ls_first = “first”;

var ls_second = “second”;

if (ls_first == “first”)

{

……do something……

}

else if (ls_second == “second”)

{

…………do something else………

}

In the example above, the code evaluates two conditions: ls_first and ls_second. Both evaluate to true, but the logic of only the first condition will execute.

As with switch and select case, be sure to test all conditions, not just the most obvious ones. Logic errors may occur in code if you do not consider all possibilities.

SIEBEL SYSTEMS, INC. 48 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 49: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use the Associate Method to Create Intersection Table Records

Use the Associate method to create records in an intersection table. This method automatically and correctly creates new records. Developers, unaware of this method, frequently try to implement the functionality with many lines of script when a single call to the Associate method will work.

Example:var lBC_mvg = this.GetMVGBusComp(“Sales Rep”);

var lBC_associate = lBC_mvg.GetAssocBusComp();

with(lBC_associate)

{

ClearToQuery();

SetSearchSpec(“Id”, SomeRowId);

ExecuteQuery(ForwardOnly);

if(FirstRecord())

Associate(NewAfter);

}

SIEBEL SYSTEMS, INC. 49 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 50: technote514-1 scriptingbestpractices

SIEBEL SCRIPTING BEST PRACTICES MARCH 23, 2004

Use Dynamic Values

Use dynamic values, as opposed to hard coded values, wherever possible. This is particularly important for values that may change often, because you must recompile and redeploy any changes to hard-coded values. Many commonly used values in scripting are available as process properties which can be obtained with the TheApplication.GetProfileAttr() function. For example, if you are writing an error handling script and want to pass the application name, you can use:

TheApplication.GetProfileAttr("ApplicationName")

Alternatively, you can store values in the List Of Values table or other database tables and query for them at runtime. This is most appropriate when there is only one dynamic value or a short list of values which you need to query for in the script. If you have one value, or a short list that will fit within one LOV entry, use the LookupValue function to retrieve the value. Using LookupValue is especially important if you have implemented Multilingual List of Values (MLOV).If you need to store multiple LOV values with a common LOV Type, the script can query directly on the List Of Values business component. In the following example, the LOV values are queried from the List Of Values buscomp, then concatenated together to form a query filter string.Example:

var statusList;var moreRecords;var boLOV;var bcLOV;

boLOV = TheApplication().GetBusObject("List Of Values");bcLOV = boLOV.GetBusComp("List Of Values");bcLOV.ClearToQuery();bcLOV.SetSearchSpec("Type","SR_STATUS");bcLOV.SetSearchSpec("Active","Y");bcLOV.ExecuteQuery(ForwardOnly);if (bcLOV.FirstRecord())

{statusList = bcLOV.GetFieldValue("Name");moreRecords = bcLOV.NextRecord();while (moreRecords != 0)

{statusList = statusList + " OR ";statusList = statusList + bcLOV.GetFieldValue("Name");moreRecords = bcLOV.NextRecord();}

}else

{statusList = "";}

PROPRIETARY & CONFIDENTIAL 50 SIEBEL SYSTEMS, INC.DUPLICATION PROHIBITED EMPLOYEE EDUCATION

Page 51: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Use Logical Constants versus Literal Values

Always use logical constants where they are available. It makes your code easier to read and easier to upgrade. Literal values are prone to upgrade problems as Siebel applications could change the behavior behind a literal value.

Example:bc.NewRecord(1);

Most likely, future developers reading this script will have to look up what 1 means. Also, if Siebel Systems were to change what this literal value does in the NewRecord method in the C++ class, this code may not behave as expected. Using the logical constant alleviates both of these issues. The above line of code is better implemented as:

bc.NewRecord(NewAfter);

These are the most commonly used logical constants and their literal values.

Type Logical Constant Value

CursorMode: ForwardBackward 0 (default)

ForwardOnly 1

ViewMode: SalesRep View 0

ManagerView 1

PersonalView 2

AllView 3

OrganizationView 5

ContactView 6

GroupView 7

CatalogView 8

SubOrganizationView 9

NewRecordLocation: NewBefore 0 (default)

NewAfter 1

NewBeforeCopy 2

NewAfterCopy 3

SIEBEL SYSTEMS, INC. 51 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 52: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Avoid Exit Function and Exit Sub

There are two general objections to using Exit Sub or Exit Function in Siebel VB.

First, it is difficult to follow the flow of a script with multiple exit points. It is easier to follow and maintain a script with one exit point.

Second, multiple exit points increase the chance of memory leaks from not properly destroying objects. When a script exits abruptly, object references are not released unless explicitly written that way. In methods where there are many exit points, developers have to duplicate this code in many locations.

SIEBEL SYSTEMS, INC. 52 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 53: technote514-1 scriptingbestpractices

MARCH 23, 2004 SIEBEL SCRIPTING BEST PRACTICES

Place GotoView at the End of a Script

The GotoView statement does not immediately exit a script and navigate to the specified view. Rather, the script holds the statement aside until the entire script executes. Finally, as the last statement, the script executes the method regardless of where it appeared in the script. For example, if the first statement in a script is a GotoView statement, it will not execute until all other code executes. Therefore, it is good practice to place GotoView statements at the end of a script, to represent what actually happens.

SIEBEL SYSTEMS, INC. 53 PROPRIETARY & CONFIDENTIALEMPLOYEE EDUCATION DUPLICATION PROHIBITED

Page 54: technote514-1 scriptingbestpractices

SIEBEL SCRIPTING BEST PRACTICES MARCH 23, 2004

Use DeleteRecord Method Properly

DeleteRecord implicitly moves the record pointer to the next record in the record set. A call to NextRecord after DeleteRecord causes the record pointer to move twice. This means that the Siebel application skips a record in the result set. If it is deleting records within a loop, the Siebel application skips every other record.

The following example illustrates the recommended approach for deleting records within a loop.

Siebel VBWhile(BC.FirstRecord <> 0)

BC.DeleteRecord

Wend

PROPRIETARY & CONFIDENTIAL 54 SIEBEL SYSTEMS, INC.DUPLICATION PROHIBITED EMPLOYEE EDUCATION