web-enabling legacy applications jeff haym data access worldwide consulting

39
Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Upload: primrose-perkins

Post on 11-Jan-2016

216 views

Category:

Documents


1 download

TRANSCRIPT

Page 1: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Web-Enabling Legacy Applications

Jeff Haym Data Access Worldwide Consulting

Page 2: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Legacy Applications

Found in corporate environments and even in today’s vertical markets.

Generally procedural code.Hundreds of programs in application.Years to write and test.Modified FMAC or DFRun.Years of data entry means lots of data.

Page 3: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Keeping Legacy Apps

Users resist change. Application is stable and has earned trust and

confidence from users. Reputation is on the line and rewriting and deploying

might jeopardize that. If we have invested a lot of time and money and a

total re-write is not feasible. If we don’t want to re-train our users nor rewrite

training manuals. We can continue to use legacy apps to their full

capacity without modifying a line of code and have it work with WebApp server modules.

Page 4: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Opportunities For Those Who Maintain A Legacy App

Break free from legacy technology get into ASP / VB Script / Java Script programming.

Moving procedural app to object oriented is quicker with WAS as understanding UI system messages not necessary.

Knowing business rules and using ddb makes it easier to learn and understand DD methods.

User feedback puts us ahead of the game – less prototyping.

Optimal solution for remote access - Client / Server. Reuse rules on other back ends without re-writing

server side stored procedures. HTML is similar to procedural DataFlex. Get the RAD development for the web as you have

come to expect from DAW products.

Page 5: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Add Web Based Functionality One Module At A Time

Publish reports on the webEnable Data entryRemote access via the webWebApp programs are fully compatible

with 2.3 runtime and up. (File structure changes performed by dbb will upgrade file to Rev. 3 and 2.3 runtime will not work)

Page 6: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

DD’s Strength

Hooks that can be programmed to allow for ‘any situation’ (mature methodology)

Consistently enforce these rules in every transaction (save edit and delete)

Ensure transaction integrity for multiple file saves in a DD structure.

Page 7: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Are DD’s Required? Although they automate so much work, and we

recommend using them, they are not required. However, it is best to let the dbb create them just

for the sake of running the wizards to generate ASP code with forms, that work with Web Business Objects, even if you do not initially use them to enforce business rules.

Modify wizard generated code to add procedural style reports, procedural style saves / edits / deletes.

Page 8: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

New Workspace / Empty DDs

Creating a new workspace will keep new development isolated from old.

Copy data file components into W/S data directory. - When ready to go “live” switch DataPath in WebApp workspace to look at “live” data.

GRADUALLY move business rules to DDs, 1 by 1 as needed by web based modules.

Page 9: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Reporting - Probably The Best Place To Start.

Let anyone anywhere see data.Data is already stored and that is the

most valuable part of any system.Can use familial looping techniques, and

use WriteHTML to output data. (repeat … until, while [found]… end)

Embed HTML into values being written.

Page 10: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Procedural Report Example (ASP)

<% oVote1.call "msg_ListIdeas", TopicID%>

Page 11: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Procedural Report (WBO) Procedure ListIDeas integer iTopicID integer iCount string sCountURL sCount for_all thread by index.2 constrain thread.topicid eq iTopicID do

increment iCount move iCount to sCount move ("Vote1Zoom.asp" - "?RecId=" - (string(thread.recnum)))

to sCountURL get HTMLLink sCountURL sCount to sCountURL send writehtml sCountURL send writehtmlbreak (' ' + thread.title ) end_for_all End_Procedure

Send RegisterInterface msg_ListIdeas "msg_ListIdeas" "iTopicID" "Lists and numbers topic ideas"

Page 12: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Procedural Save (ASP)<% UserName = request.cookies("User_Name") %><% TopicID = request.cookies("TopicID") %><% CastVote = request("T1") %>

<%If request("Request_method")="POST" Then if Request("SubmitButton")<>"" then oVote1.call "msg_SubmitVote", CastVote,

UserName, TopicID end if end if%>

Page 13: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Procedure SubmitVote integer iVote string sUserName integer iTopicID integer iCount string sCountURL sCount clear progress move iTopicID to progress.topicid move sUsername to progress.user_name find eq progress by index.1 [found] begin if (progress.voted gt 0) begin send writehtmlbreak '' send writehtml "Current User Has Already Voted" procedure_return end

end for_all thread by index.2

constrain thread.topicid eq iTopicID do increment iCount

if iVote eq iCount begin // found the one that was voted for reread increment thread.votes saverecord thread unlock end end_for_all End_Procedure

Page 14: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Migrating To DDO’sWe do not want to initially move business

rules contained in 100’s of programs at once to DD’s.

Allow time to test the business rules.Even though DDs are the most

manageable to development and maintain business rules, we do not want to leap before looking.

Page 15: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Tips for Creating Data Dictionaries

Different runtimes enforce relationships differently. WAS / VDF runtime will check: relating field is same

size and type. Uniquely indexed parent. Child relates to parent, n : 1 Remove multiple relationships between two files.

Start by analyzing relationships first to harness the DF methodology, rather than or fight hundreds and hundreds of messages.

Remove circular relationships - diamond relationships are OK.

How To Check relationships DDB > Reports > Check Relationships.

Page 16: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Relationship Tree

Page 17: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Circular Relationship

Since children always find their parents in a DD structure, the record in A must be the parent of B and C and Grand parent of D.

Page 18: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Legacy Circular Relationship.One possibility is to remove the

relationship and re-write the legacy app. That would probably contradict what ever reason(s) is keeping the app still running.

Set_relate MyChild.Child_Key to |FN0,0 in WebApp will programmatically clear the relationship when WebApp runtime executes the command but old flx’s will still rely on the relationship in the data file header.

Page 19: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

#1 Difference Between Procedural vs. OO Programming

Learning the distinction between using global buffer and dd (and its local buffer) is key.

Clearing a file buffer (clear MyFile) will not automatically clear a dd.

Whenever getting values a user has entered it use dd msgs.

Page 20: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Global Record Buffer

Perfectly legal to code using the global file buffer inside a DD.

The key is to know when.Any DD method that is called as a result

of a request_saveProgrammer can enforce transactions

with Begin_transaction / End_Transaction outside of DD’s.

Page 21: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Procedure Style Code To Deduct Quantity Sold From Inventory

REREAD… // find correct records in bufferMove (Invt.QtyOnHand - OrderItem.qty) to;

Invt.QtyOnHand)Saverecord Invt.qty_on_hand…. // UNLOCK

Page 22: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

OOP Style Code To Deduct Quantity Sold From Inventory

Move (Invt.QtyOnHand - OrderItem.qty) to; Invt.QtyOnHand)

Saverecord Invt.qty_on_hand

Same code! Just in different places.

Page 23: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

USE Global Buffer In The “Hooks” Called By Request_save

Validate_saveValidate_deleteCreatingDestroyingUpdateBackout

Page 24: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

DDO Structures Must Be Seeded

For a DD to find a child the parent buffers must be seeded.

To Save a child DD the parent DDs must be seeded

Transactional integrity is achieved by seeding all values at once and sending save of a child most file.

Page 25: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Saving Grace: Preparing DD Structure (Ex 1)

Seed buffer to find records,Clear MyParentFile_DDMove iSomeValue to MyParentFile.MyFieldSend request_find of MyParentFile_DD EQ ;

MyParentFile.File_Number 1 // index 1Ready to save children records (Set field

changed value, send request_save)

Page 26: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Saving Grace: Preparing DD Structure (Ex 2)

Clear MyFileMove iSomeValue to MyFile.MyFieldFind EQ MyFile by index.1If (found) send find_by_recnum to ; MyFile_DD MyFile.File_Number MyFile.recnum

Page 27: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Recnum Recnum can be used to seed a DD Concept may seem outdated but it is supported. DB Drivers support Recnum – automatic

increment field. Methodology relies on it DF PKG’s.

Clear my fileMove iSomeValue to MyFile.MyFieldFind eq MyFile by recnumSend Find_By_Recnum to myFile_DD

MyFile.file_number MyFile.recnum

Page 28: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

After DD Saves

After a save the DDs will clear.Must seed the entire structure again in

order to save again.

Page 29: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Log in routine (ASP Side)If request("Request_method")="POST" Then

UserName = request("User__Name")UserPass = request("User__Pass")MeetingID = request("Meeting__ID")If UserPass<>"" and UserName<>"" then

LoginOk = oLogin.call("Get_Login_User",UserName,UserPass,MeetingID)else

LoginOk = 0end ifIf LoginOk <> 0 then

response.cookies("TopicID")=oLogin.ddValue("Seats.topicid") response.cookies("User_Name")=oLogin.ddValue("Seats.user_name") Rights = "1"

else ' login failed, clear cookies. response.cookies("TopicID")="-1" response.cookies("User_Name")="Invalid" 'response.cookies("Rights")="-1" Rights = "-1" end ifelse Rights = "0"end if

Page 30: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Login Routine (WBO side) function login_user string sUserId string sPass string sMeetingID returns

integer integer hDD iMeetingID Move (oSeats_dd(Self)) to hDD Send Clear of hDD clear topic Move sMeetingID to topic.topicid

Move (Uppercase(sUserid)) to seats.user_name Move (Uppercase(sPass)) to seats.password Move sMeetingID to seats.topicid Move sMeetingID to topic.topicid Send Find of hDD EQ 1 Function_return (current_record(hdd)<>0) end_function

Page 31: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Selection / Pick list

Two different approaches.Option created by HTML code generated

by a method in a WBO DF.

Page 32: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Selection List For Report Report with a hypertext link approach.In WBO Procedure OnBody String sText Send WriteHtmlRowBegin Get AddRecordLink (HtmlEncode(Unit.Last - ', ' + Unit.first)) to ;

sText Send WriteHtmlCell sText 'Class="Data" Align="left"' Send WriteHtmlCell (HtmlEncode(Unit.bldg)) 'Class="Data“ ;

Align="left"' Send WriteHtmlCell (HtmlEncode(Unit.Number)) 'Class="Data“ ;

Align="left"' Send WriteHtmlRowEnd End_Procedure // OnBody

In ASP ZoomURL = "OwnerReportZoom.asp" ' name of zoom file. If blank none.

Page 33: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting
Page 34: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

ASP Zoom generated by WAS

By default it looks to see if a recnum was passed when the page was called.

If so, it will seed the asp forms with a record, otherwise it will be blank.

<% RecID = Request("RecId") Err=oUnit.RequestFindByRecId(“Unit", RecId)%>

Page 35: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Creating HTML Controls In WBOSend WriteHtml ('<select name="BrandClass"

onChange="document.forms[0].submit()">') Send WriteHtml ('<option value="null"><font

color="#FF0000">Select a Category</font>') For_All MktCls By Index.10 Constrain MktCls.Repair_YN EQ "Y" Constrain MktCls.BrandClass EQ sBrandClass Do If ((MktCls.Recnum = iSelected) And (sFirstTime = "N")) Send

WriteHtml ('<option selected value="') Else Send WriteHtml ('<option value="') Move (Trim(MktCls.ClassName)) To sClassName Send WriteHtml (MktCls.Recnum) Send WriteHtml ('" ') Send WriteHtml (MktCls.Recnum) Send WriteHtml ('> ') Send WriteHtml (HtmlEncode(sClassName)) Send WriteHtml ('</option>') End_For_All EndSend WriteHtml ('</select>')

Page 36: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting
Page 37: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Debugging

Showln’s - Interact with desktop (Locally)NT Event Log (Locally)Send Writehtml (Remote)Remote Output to Writing to a text file.

(Remote)

Page 38: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Cookies vs. Session variables

Cookie will be stored in the browsers memory and will be written to disk if the expiration date is not reached. Usually expire when session ends.

response.cookies(“BillID")=oSaveBillingAddress.DDValue(“CustBAdd.Custdadd_id")

Session variable is only in memory until session ends or times out.

Session(“BillID") = oSaveBillingAddress.DDValue("Custbadd.Custdadd_ID")

Page 39: Web-Enabling Legacy Applications Jeff Haym Data Access Worldwide Consulting

Web Enabling With VDF7

All runtimes are compatible with DF Data Files – VDF 7 could web-enable legacy apps

VDF7 can output in XML for business to business solutions.

VDF7 can output in XSL which could then be used to present data (reporting) by adding style sheets and HTML markup

For security reasons, most web solutions use a mirror of DB which is updated on a regular basis. VDF7 module could handle this, not just reading and writing XML documents.