• Welcome, Guest. Please login.
 
September 22, 2019, 02:02:42 pm

News:

Welcome to the SQLitening support forums!


Show posts

This section allows you to view all posts made by this member. Note that you can only see posts made in areas you currently have access to.

Messages - cj

16
'Test multiple clients without multiple computers or SQLitening server

#INCLUDE "sqlitening.inc"  'fredrick9.bas

FUNCTION PBMAIN AS LONG

 LOCAL x,hthread AS LONG

 'Simulate 3 client workstations
 FOR x = 1 TO 3
  THREAD CREATE WorkStation(x) TO hThread
  THREAD CLOSE hThread  TO hThread
 NEXT
 DO:SLEEP 100:LOOP UNTIL THREADCOUNT=1
END FUNCTION

 ViewAll

'===========================================================
THREAD FUNCTION WorkStation(BYVAL x AS LONG)
 Helper x
END FUNCTION

SUB Helper(x AS LONG) THREADSAFE
 slopen "hello.db3","C"   '<--- would be in a shared folder on network
 slexe  "create table if not exists t1(column1)"
 slexe  USING$("insert into t1 values('write from thread#')",x)
 slclose
END SUB


'===========================================================
FUNCTION ViewAll AS STRING
 LOCAL s() AS STRING
 slopen "hello.db3"  
 slselary "select * from t1",s(),"Q9c"
 ? JOIN$(s(),$CR),,"All users done"
END FUNCTION
17
True, just a normal local area network.
Share a folder on one computer, and map to that folder on the clients.
The SQLitening server/service would not be needed nor the SQLiteingServer.exe be distributed.
Clients would use something like this: slOpen "z:\test\database.db3","C"
18
Fredrick,
Download/extract SQLiteningServer.bas https://sqlitening.planetsquires.com/index.php?topic=9697.0

SUB LogIt() can be modified to whatever you want.
Compile and replace SQLiteningServer.exe
'===================================================================================

Bypassing the server is much faster and less to distribute.
I tested without using SQLiteningServer to a mapped drive without issue.

slOpen "z:\test\database.db3","C"
Always use "begin immediate" or "begin exclusive" instead of just "begin"

I've used the server for many years and thinking of swithing to simple networking.

Is the server really needed or better on a small LAN?
19
Instructions added to post #1
20
Definitely.  See the first post in the general forum.
21
The link is to a modified SQLiteningServer.bas that might already do what you want.
Compile it and copy  SqliteningServer.exe to whereever your current SQLiteningServer.exe is.

If you installed the modified SQLiteningServer.Bas
the log (SqliteningServer.log) would look like this:

07-21-2019 14:45:23  SELECT * FROM parts LIMIT 1
07-21-2019 14:45:55  SELECT * FROM parts LIMIT 2 ORDER BY PRICE

Also, if you run the filewatcher.exe program, every time someone
accesses the server you would see a scrolling window move up one
line to show you the last line in the log file (SqliteningServer.log)

Sounds like all you need to do is install the modification
and optionally run file watcher to see the changes to the log in real-time.

Quote from: undefinedI've noticed running without the server is much faster on a local network
and not sure it is even needed by most.

>> Really? How does that work?
REM slConnect
22
Fredrick,

I haven't used procs, but was thinking of making it easier to insert functions into the server.
I'm not convinced adding code to the server is harder than using a proc once a function is added to demonstrate it that can be duplicated and modified.

After the modification below, SQliteningServer.bas compiles with a click.

1. Did you download and install this:
https://sqlitening.planetsquires.com/index.php?topic=9697.msg26453;topicseen#msg26453

2. Is this to add a time stamp to
  Every insert (unlikely)
  Create a table logging all entries?
  Create a flat file text log on disk?

3. This is for the server, right?

I've noticed running without the server is much faster on a local network
and not sure it is even needed by most.
23
Downloaded 97-times.
Wonder if anyone uses it?

Might add a new function or two to see if it would
be easier and faster than using the Procs method.
The code compiles "as is" with the update above.
24
General Board / SQLitening/MLG Demo using MLG_PUTEX
July 09, 2019, 01:02:24 pm
Instead of killing and adding grid this version uses MLG_PUTEX
It also leaves the scroll bars on at all times using /D switch

#PBFORMS CREATED V2.01

#COMPILE EXE    'slMlg.bas
#DIM ALL
'----------------------------------------------------------------------------------------
GLOBAL ghDlg,hGrid AS LONG

#PBFORMS BEGIN INCLUDES
#RESOURCE "slMLG.pbr"
#INCLUDE ONCE "WIN32API.INC"
#INCLUDE ONCE "COMMCTRL.INC"
#INCLUDE ONCE "PBForms.INC"
#PBFORMS END INCLUDES
#INCLUDE ONCE "mlg.inc"
#INCLUDE ONCE "sqlitening.inc"
'------------------------------------------------------------------------------
#PBFORMS BEGIN CONSTANTS
%IDC_GRID      = 1009
%GridLabel      = 1010
%TEXT_DATABASE  = 1011
%TEXT_SQL      = 1012
%LBL_DATABASE  = 1013
%LBL_SQL        = 1014
%BTN_RUN        = 1015
%LBL_LABEL1    = 1016
%IDC_STATUSBAR1 = 1017
#PBFORMS END CONSTANTS
#PBFORMS DECLARATIONS
FUNCTION PBMAIN()
  ShowDIALOG1 %HWND_DESKTOP
END FUNCTION

SUB Resize
 LOCAL DialogWidth,DialogHeight AS LONG
 LOCAL GridWidth  ,GridHeight  AS LONG

 'get size of dialog
 DIALOG  GET SIZE  ghDlg TO DialogWidth,DialogHeight

 'get size of MLG
 CONTROL GET SIZE ghDlg,%IDC_GRID TO GridWidth  ,GridHeight    'grid  width,height
 IF GridWidth THEN 'if 0 then do not redraw
  CONTROL SET SIZE ghDlg,%IDC_GRID,  DialogWidth-14,GridHeight  'set grid width
  CONTROL REDRAW  ghDlg,%IDC_GRID
 END IF
END SUB

CALLBACK FUNCTION ShowDIALOG1Proc()
 LOCAL DialogWidth,DialogHeight AS LONG
 LOCAL gridwidth,gridheight AS LONG
 LOCAL SelStart,SelEnd AS LONG

  SELECT CASE AS LONG CB.MSG
    CASE %WM_EXITSIZEMOVE
    Resize

    CASE %WM_INITDIALOG
    LOCAL s AS STRING
    ghDlg = CB.HNDL
    GridFromSQL

    CASE %WM_NCACTIVATE
      STATIC hWndSaveFocus AS DWORD
      IF ISFALSE CB.WPARAM THEN
        hWndSaveFocus = GetFocus()
      ELSEIF hWndSaveFocus THEN
        SetFocus(hWndSaveFocus)
        hWndSaveFocus = 0
      END IF
    CASE %WM_CHAR

    CASE %WM_COMMAND
      SELECT CASE AS LONG CB.CTL
        CASE %IDC_STATUSBAR1
        CASE %TEXT_DATABASE
        CASE %TEXT_SQL
          IF CB.CTLMSG = %EN_SETFOCUS THEN 'SQL input control got focus
            CONTROL SEND CB.HNDL, %TEXT_SQL,%EM_GETSEL, VARPTR(SelStart), VARPTR(SelEnd)
            CONTROL SEND CB.HNDL, %TEXT_SQl,%EM_SETSEL,SelEnd,SelEnd
          END IF

        CASE %BTN_RUN
          IF CB.CTLMSG = %BN_CLICKED OR CB.CTLMSG = 1 THEN
            GridFromSQL
            CONTROL SET FOCUS CB.HNDL,%TEXT_SQl
            CONTROL SEND CB.HNDL, %TEXT_SQL,%EM_GETSEL, VARPTR(SelStart), VARPTR(SelEnd)
            CONTROL SEND CB.HNDL, %TEXT_SQl,%EM_SETSEL,SelEnd,SelEnd
          END IF
        CASE %IDC_GRID
      END SELECT
  END SELECT
END FUNCTION

FUNCTION ShowDIALOG1(BYVAL hParent AS DWORD) AS LONG
  LOCAL lRslt AS LONG

#PBFORMS BEGIN DIALOG %IDD_DIALOG1->->
  LOCAL hDlg  AS DWORD

  DIALOG NEW hParent, "", 286, 170, 768, 359, %WS_POPUP OR %WS_BORDER OR _
    %WS_DLGFRAME OR %WS_THICKFRAME OR %WS_CAPTION OR %WS_SYSMENU OR _
    %WS_MINIMIZEBOX OR %WS_MAXIMIZEBOX OR %WS_VISIBLE OR %DS_3DLOOK OR _
    %DS_NOFAILCREATE OR %DS_SETFONT, %WS_EX_LEFT OR %WS_EX_LTRREADING OR _
    %WS_EX_RIGHTSCROLLBAR, TO hDlg
  CONTROL ADD TEXTBOX,  hDlg, %TEXT_DATABASE, "sample.db3", 43, 297, 99, 13
  CONTROL ADD TEXTBOX,  hDlg, %TEXT_SQL, "select * from parts limit 234", 42, _
    313, 441, 13
  CONTROL ADD LABEL,    hDlg, %GridLabel, "%GridLabel - Grid will display " + _
    "here", 0, 0, 752, 260
  CONTROL SET COLOR      hDlg, %GridLabel, %WHITE, %BLUE
  CONTROL ADD LABEL,    hDlg, %LBL_DATABASE, "Database", 5, 297, 32, 11
  CONTROL ADD LABEL,    hDlg, %LBL_SQL, "SQL", 5, 315, 23, 10
  CONTROL ADD BUTTON,    hDlg, %BTN_RUN, "Run", 5, 329, 23, 10
  CONTROL ADD LABEL,    hDlg, %LBL_LABEL1, "Press Enter or click Run", 5, _
    277, 324, 10
  CONTROL ADD STATUSBAR, hDlg, %IDC_STATUSBAR1, "Rows 0    Columns 0", 0, 0, _
    0, 0
#PBFORMS END DIALOG
CONTROL SET TEXT hDlg,%TEXT_SQL, _
"select manuf,redref,product,language,cpu_os,media,type,pgroup,printf('%.2f',price*.01) as PRICE from parts"

  'DIALOG SET TEXT hdlg,EXE.NAME$
  LOCAL Msg AS TagMsg
  LOCAL flag AS LONG  'prevent grid displaying twice when we set focus
  DIALOG SHOW MODELESS hDlg, CALL ShowDIALOG1Proc TO lRslt

  DO WHILE GetMessage(Msg, %NULL, 0, 0)
  IF IsDialogMessage(hDlg, Msg) = %FALSE THEN
    TranslateMessage Msg
    DispatchMessage  Msg
  END IF

  IF msg.wparam = 13 THEN                      'enter pressed in any control
    'DIALOG SET TEXT ghDlg,USING$("ID #  Counter #",GetDlgCtrlID(GetFocus),gCounter)
    'IF GetDlgCtrlID(GetFocus) = %TEXT_SQL THEN 'in %TEXT_SQL control?
      IF flag = 0 THEN GridFromSQL              'execute sql and MLG
      flag = flag XOR 1                        'toggle flag
      'CONTROL SET FOCUS hDlg,%TEXT_SQL          'focus to sql input control
      LOCAL selStart,SelEnd AS LONG
      CONTROL SEND hDlg, %TEXT_SQL,%EM_GETSEL, VARPTR(SelStart), VARPTR(SelEnd)
      CONTROL SEND hdlg, %TEXT_SQl,%EM_SETSEL,SelEnd,SelEnd
    'END IF
    CONTROL SET FOCUS hDlg,%TEXT_SQL          'always focus to sql input
  END IF

  LOOP WHILE ISWIN(hDlg)

  FUNCTION = lRslt
END FUNCTION

FUNCTION GridFromSQL AS LONG
 LOCAL rownum,colnum,rows,cols AS LONG
 LOCAL x AS LONG,y AS LONG,gridwidth,gridheight AS LONG

 LOCAL s AS STRING
 LOCAL sDatabase AS STRING
 LOCAL sql AS STRING
 LOCAL sRecordSet() AS STRING
 CONTROL GET TEXT ghDlg,%TEXT_DATABASE TO sDatabase
 CONTROL GET TEXT ghDlg,%TEXT_SQL  TO sql

 slOpen sDatabase,"C E0"  'E0 we will handle open database error open/close database each time called
 IF slGetErrorNumber THEN
  ? "Database name: " +  WRAP$(sdataBase,$DQ,$DQ) + $CR + slGetError,%MB_SYSTEMMODAL,"SQL Open"
  EXIT FUNCTION
 END IF

 slSelAry sql,sRecordSet(),"E0"  'E0 we will handle SQL error
 IF slGetErrorNumber THEN
  ? CHR$(slGetError,$CR,"Database name: ",WRAP$(sdataBase,$DQ,$DQ),$CR,$CR,sql),%MB_SYSTEMMODAL,"SQL Error"
  EXIT FUNCTION
 END IF

 rows = UBOUND(sRecordset,2)  'SQLitening(col,row) order
 cols = UBOUND(sRecordset,1)  'SQLitening(col,row) order
 REDIM RowsCols(rows,cols) AS STRING 'MLG(row,col) order

 CONTROL GET LOC ghdlg,%GridLabel TO x,y
 CONTROL GET SIZE ghdlg,%GridLabel TO gridwidth,gridheight
 CONTROL SHOW STATE ghDlg, %GridLabel, %SW_HIDE 'must hide grid position label

 STATIC newgrid AS LONG
 IF newgrid = 0 THEN
  newgrid = 1
  CONTROL KILL ghDlg,  %IDC_GRID    'start a fresh grid
  s = USING$("r#/c#/d-0",Rows,cols) 'initial rows and columns  /d-0 don't hide scrollbars
  CONTROL ADD "MYLITTLEGRID", ghDlg, %IDC_GRID, s, x, y, gridwidth,gridheight, %MLG_STYLE
  CONTROL HANDLE ghDlg, %IDC_GRID TO hGrid
  #IF %DEF(%MLG_UNLOCK)
  MLG_UNLOCK
  #ENDIF
 END IF

 'Create MLG(Row,Col) from SQLitening(Col,Row)
 FOR rownum = 0 TO rows
  FOR colnum = 1 TO cols
  RowsCols(rownum,colnum) = sRecordSet(colnum,rownum)
  NEXT
 NEXT
 Mlg_PutEx hGrid,RowsCols(),-4,1    'put array to MLG in row,col order
 FOR x = 1 TO UBOUND(RowsCols,2)    'column names should have been in grid?
  MLG_PUT hGrid,0,x,RowsCols(0,x),1
 NEXT
 slClose
 CONTROL SET TEXT ghDlg,%IDC_STATUSBAR1,USING$("Rows #,    Columns #",rows,cols)
 Resize
END FUNCTION
25
I was wondering how to do a transaction.  Here is an example:
https://www.thegeekstuff.com/2012/09/sqlite-command-examples/
26
Welcome.  Hope it helps.
28
General Board / CLI from PB
June 25, 2019, 12:06:16 am
1. If $Viewfile has a length the output goes to a text file and is displayed using default text viewer.
2. If $Viewfile is remarked, the output goes to the command line environment.
3. All select statements must be terminated with a semi-colon.
4. Backup, clone, import, export, view sql, ...
5. Many commands can be sent at once by separating each semi-colon terminated command with a $CRLF

Example:
sdatabase= "sample.db3"
sheller "select * from parts;" + $CRLF

'SQLite3Sheller -  script processor  6/24/19
'All select statements must be terminated with a semi-colon.
'Many uses; including backup, clone, import, export, view sql, ...

DECLARE FUNCTION ShellExecute LIB "Shell32.dll" ALIAS "ShellExecuteA" ( _
    BYVAL hwnd AS DWORD, lpOperation AS ASCIIZ, lpFile AS ASCIIZ, _
    lpParameters AS ASCIIZ, lpDirectory AS ASCIIZ, BYVAL nShowCmd AS LONG) _
    AS DWORD

$CommandFile="cj.cmd" 'file read by SQLite3.exe
$BatchFile  ="cj.bat" 'file shelled to
'$ViewFile  ="cj.txt" '<---  remark to use cmd.exe or unremark to view .txt file
'=====================================================================================
FUNCTION PBMAIN () AS LONG 'sqlite commands .modes ascii column html insert line list tabs tcl
 LOCAL s,sdatabase AS STRING
 sdatabase= "sample.db3"
 #IF %DEF($ViewFile)
  s=CHR$(".output ",$ViewFile,$CRLF)
 #ENDIF
 s+= CHR$("select '10 records of '||count(*)||' records (.mode tab)' from parts;",$CRLF)
 s+= CHR$(".mode tabs",$CRLF)
 s+= CHR$("select rowid,redref,substr(product,1,40) from parts limit 10;",$CRLF)
 s+= CHR$("select '';",$CRLF)
 s+= CHR$("select '10 records of '||count(*)||' records (.mode csv)' from parts;",$CRLF)
 s+= CHR$(".mode csv",$CRLF)
 s+= CHR$("select rowid,redref,substr(product,1,40) from parts limit 10;",$CRLF)
 sheller sdatabase,s
 #IF %DEF($ViewFile)
  DisplayTextFile $ViewFile
 #ENDIF
END FUNCTION
'=====================================================================================
FUNCTION sheller(sDataBase AS STRING,sCommands AS STRING) AS LONG
 LOCAL stemp AS STRING, h AS LONG
 h = FREEFILE
 OPEN $CommandFile FOR OUTPUT AS #h
 IF ERR THEN ? "Unable to open " + $CommandFile,%MB_SYSTEMMODAL,"Error":EXIT FUNCTION
 PRINT #h,sCommands;
 CLOSE #h
 h = FREEFILE
 OPEN $BatchFile FOR OUTPUT AS #h
 IF ERR THEN ? "Unable to open " + $BatchFile,%MB_SYSTEMMODAL,"Error":EXIT FUNCTION
 stemp = "sqlite3.exe " + sdatabase + " < " + $CommandFile
 PRINT #h,"@cls"
 PRINT #h,"@echo off"
 PRINT #h,stemp
 #IF NOT %DEF($ViewFile) 'viewfile not wanted
  PRINT #h,"pause"      'pause batch file so we can see results
 #ENDIF
 CLOSE #h
 #IF %DEF($ViewFile)
  h = SHELL($BatchFile,0)
 #ELSE
  h = SHELL($BatchFile)
 #ENDIF
END FUNCTION
'=====================================================================================
FUNCTION DisplayTextFile(sFileName AS STRING) AS LONG
 LOCAL zFileName AS ASCIIZ * 257
 zFileName = sFileName
 ShellExecute (0, "OPEN", zFileName, BYVAL 0, CURDIR$, %SW_SHOWNORMAL)
END FUNCTION
29
Shows how easy it is to display 2-dimensional recordsets in MLG
MLG_PUT hGrid,rownum,colnum,sRecordSet(colnum,rownum),0

Pressing Enter key (at anytime) or clicking Run executes the SQL and fills grid.

Added statusbar 6/22/19  1:39AM CST

Suggestions welcome

MLG can be purchased from Gary Beene gbeene@airmail.net

#PBFORMS CREATED V2.01
'------------------------------------------------------------------------------
#COMPILE EXE    'slMlg.bas
#DIM ALL
GLOBAL ghDlg AS DWORD

#PBFORMS BEGIN INCLUDES
#INCLUDE ONCE "WIN32API.INC"
#PBFORMS END INCLUDES
#INCLUDE ONCE "mlg.inc"
#INCLUDE ONCE "sqlitening.inc"
'------------------------------------------------------------------------------
#PBFORMS BEGIN CONSTANTS
%IDC_GRID      =  100
%GridLabel      = 1010
%TEXT_DATABASE  = 1011
%TEXT_SQL      = 1012
%LBL_DATABASE  = 1013
%LBL_SQL        = 1014
%BTN_RUN        = 1015
%LBL_LABEL1    = 1016
%IDC_STATUSBAR1 = 1017
#PBFORMS END CONSTANTS
#PBFORMS DECLARATIONS
FUNCTION PBMAIN()
  ShowDIALOG1 0
END FUNCTION

SUB Resize
 LOCAL DialogWidth,DialogHeight AS LONG
 LOCAL GridWidth  ,GridHeight  AS LONG
 DIALOG  GET SIZE  ghDlg TO DialogWidth,DialogHeight            'dialog width,height
 CONTROL GET SIZE ghDlg,%IDC_GRID TO GridWidth  ,GridHeight    'grid  width,height
 CONTROL SET SIZE ghDlg,%IDC_GRID,  DialogWidth-14,GridHeight  'set grid width
 CONTROL REDRAW  ghDlg,%IDC_GRID
END SUB

CALLBACK FUNCTION ShowDIALOG1Proc()
 LOCAL DialogWidth,DialogHeight AS LONG
 LOCAL gridwidth,gridheight AS LONG
 LOCAL SelStart,SelEnd AS LONG

  SELECT CASE AS LONG CB.MSG
    CASE %WM_EXITSIZEMOVE
    Resize

    CASE %WM_INITDIALOG
    ghDlg = CB.HNDL
    DIALOG  GET SIZE  ghDlg TO DialogWidth,DialogHeight            'dialog width,height
    CONTROL GET SIZE ghDlg,%GridLabel TO GridWidth ,GridHeight    'label size
    CONTROL SET SIZE ghDlg,%GridLabel,  DialogWidth-14,Gridheight  'set grid width

    CASE %WM_NCACTIVATE
      STATIC hWndSaveFocus AS DWORD
      IF ISFALSE CB.WPARAM THEN
        hWndSaveFocus = GetFocus()
      ELSEIF hWndSaveFocus THEN
        SetFocus(hWndSaveFocus)
        hWndSaveFocus = 0
      END IF

    CASE %WM_COMMAND
      SELECT CASE AS LONG CB.CTL
        CASE %IDC_STATUSBAR1
        CASE %TEXT_DATABASE
        CASE %TEXT_SQL
          IF CB.CTLMSG = %EN_SETFOCUS THEN 'SQL input control got focus
            CONTROL SEND CB.HNDL, %TEXT_SQL,%EM_GETSEL, VARPTR(SelStart), VARPTR(SelEnd)
            CONTROL SEND CB.HNDL, %TEXT_SQl,%EM_SETSEL,SelEnd,SelEnd
          END IF

        CASE %BTN_RUN
          IF CB.CTLMSG = %BN_CLICKED OR CB.CTLMSG = 1 THEN
            GridFromSQL
            CONTROL SET FOCUS CB.HNDL,%TEXT_SQl
            CONTROL SEND CB.HNDL, %TEXT_SQL,%EM_GETSEL, VARPTR(SelStart), VARPTR(SelEnd)
            CONTROL SEND CB.HNDL, %TEXT_SQl,%EM_SETSEL,SelEnd,SelEnd
          END IF
        CASE %IDC_GRID
      END SELECT
  END SELECT
END FUNCTION

FUNCTION ShowDIALOG1(BYVAL hParent AS DWORD) AS LONG
  LOCAL lRslt AS LONG

#PBFORMS BEGIN DIALOG %IDD_DIALOG1->->
  LOCAL hDlg  AS DWORD

  DIALOG NEW hParent, "", 286, 170, 768, 359, %WS_POPUP OR %WS_BORDER OR _
    %WS_DLGFRAME OR %WS_THICKFRAME OR %WS_CAPTION OR %WS_SYSMENU OR _
    %WS_MINIMIZEBOX OR %WS_MAXIMIZEBOX OR %WS_VISIBLE OR %DS_3DLOOK OR _
    %DS_NOFAILCREATE OR %DS_SETFONT, %WS_EX_LEFT OR %WS_EX_LTRREADING OR _
    %WS_EX_RIGHTSCROLLBAR, TO hDlg
  CONTROL ADD TEXTBOX,  hDlg, %TEXT_DATABASE, "", 43, 297, 99, 13
  CONTROL ADD TEXTBOX,  hDlg, %TEXT_SQL, "select * from parts limit 5", 42, _
    313, 441, 13
  CONTROL ADD LABEL,    hDlg, %GridLabel, "%GridLabel - Grid will display " + _
    "here", 0, 0, 752, 260
  CONTROL SET COLOR      hDlg, %GridLabel, %WHITE, %BLUE
  CONTROL ADD LABEL,    hDlg, %LBL_DATABASE, "Database", 5, 297, 32, 11
  CONTROL ADD LABEL,    hDlg, %LBL_SQL, "SQL", 5, 315, 23, 10
  CONTROL ADD BUTTON,    hDlg, %BTN_RUN, "Run", 5, 329, 23, 10
  CONTROL ADD LABEL,    hDlg, %LBL_LABEL1, "Press Enter or click Run", 5, _
    277, 324, 10
  CONTROL ADD STATUSBAR, hDlg, %IDC_STATUSBAR1, "Rows 0    Columns 0", 0, 0, _
    0, 0
#PBFORMS END DIALOG
  DIALOG SET TEXT hdlg,EXE.NAME$
  LOCAL Msg AS TagMsg
  LOCAL flag AS LONG  'prevent grid displaying twice when we set focus
  DIALOG SHOW MODELESS hDlg, CALL ShowDIALOG1Proc TO lRslt

  DO WHILE GetMessage(Msg, %NULL, 0, 0)
  IF IsDialogMessage(hDlg, Msg) = %FALSE THEN
    TranslateMessage Msg
    DispatchMessage  Msg
  END IF

  IF msg.wparam = 13 THEN                      'enter pressed in any control
    'DIALOG SET TEXT ghDlg,USING$("ID #  Counter #",GetDlgCtrlID(GetFocus),gCounter)
    IF GetDlgCtrlID(GetFocus) = %TEXT_SQL THEN 'in %TEXT_SQL control?
      IF flag = 0 THEN GridFromSQL              'execute sql and MLG
      flag = flag XOR 1                        'toggle flag
      LOCAL selStart,SelEnd AS LONG
      CONTROL SEND hDlg, %TEXT_SQL,%EM_GETSEL, VARPTR(SelStart), VARPTR(SelEnd)
      CONTROL SEND hdlg, %TEXT_SQl,%EM_SETSEL,SelEnd,SelEnd
    END IF
    CONTROL SET FOCUS hDlg,%TEXT_SQL          'always focus to sql input
  END IF

  LOOP WHILE ISWIN(hDlg)

  FUNCTION = lRslt
END FUNCTION

FUNCTION GridFromSQL AS LONG
 LOCAL rownum,colnum,rows,cols AS LONG
 LOCAL x AS LONG,y AS LONG,gridwidth,gridheight,hGrid AS LONG
 LOCAL s AS STRING
 LOCAL sDatabase AS STRING
 LOCAL sql AS STRING
 LOCAL sRecordSet() AS STRING
 CONTROL GET TEXT ghDlg,%TEXT_DATABASE TO sDatabase
 CONTROL GET TEXT ghDlg,%TEXT_SQL  TO sql

 IF LEN(TRIM$(sDataBase)) = 0 THEN
  sDatabase = "sample.db3"
  sql = "select manuf,redref,product,language,cpu_os,media,type,pgroup,printf('%.2f',price*.01) as PRICE from parts limit 5"
  CONTROL SET TEXT ghDlg,%TEXT_Database,"sample.db3"
  CONTROL SET TEXT ghDlg,%TEXT_SQL,sql
  DIALOG REDRAW ghDlg
 END IF

 slOpen sDatabase,"C E0"  'E0 we will handle open database error
 IF slGetErrorNumber THEN
  ? "Database name: " +  WRAP$(sdataBase,$DQ,$DQ) + $CR + slGetError,%MB_SYSTEMMODAL,"SQL Open"
  EXIT FUNCTION
 END IF

 slSelAry sql,sRecordSet(),"E0"  'E0 we will handle SQL error
 IF slGetErrorNumber THEN
  ? CHR$(slGetError,$CR,"Database name: ",WRAP$(sdataBase,$DQ,$DQ),$CR,$CR,sql),%MB_SYSTEMMODAL,"SQL Error"
  EXIT FUNCTION
 END IF

 rows = UBOUND(sRecordset,2)
 cols = UBOUND(sRecordset,1)
 s = USING$("r#/c#",Rows,cols) 'rows and columns
 CONTROL GET LOC ghdlg,%GridLabel TO x,y
 CONTROL GET SIZE ghdlg,%GridLabel TO gridwidth,gridheight
 CONTROL SHOW STATE ghDlg, %GridLabel, %SW_HIDE 'must hide grid position label
 CONTROL KILL ghDlg,%IDC_GRID                  'start a fresh grid
 CONTROL ADD "MYLITTLEGRID", ghDlg, %IDC_GRID, s, x, y, gridwidth,gridheight, %MLG_STYLE
 CONTROL HANDLE ghDlg, %IDC_GRID TO hGrid
 FOR rownum = 0 TO rows
  FOR colnum = 1 TO cols
  MLG_PUT hGrid,rownum,colnum,sRecordSet(colnum,rownum),0
  NEXT
 NEXT
 slClose
 CONTROL SET TEXT ghDlg,%IDC_STATUSBAR1,USING$("Rows #,    Columns #",rows,cols)
 Resize
END FUNCTION