Hi Kwadwo, I tested several embedded SQL statements to compare SNC vs. ODBC vs. my expectations.
- PowerBuilder 2019 R2
- Microsoft SQL Server 2019
- DBMS = "SNC"
- DBMS = "ODBC" <= ODBC driver = "SQL Server Native Client 11.0", version 2011.110.7462.06
- DBMS = "ODBC" <= ODBC driver = "SQL Server", version 10.00.19041.01
MY FINDINGS
- The different ODBC drivers acted identical - - - no exceptions
- All DBMS drivers return identical SQLNRows - - - except for ROLLBACK
- Valid SELECT
- SQLNRows = 1
- Invalid SELECT returning 2+ rows
- SQLNRows = 0
- SQLCode = -1 -- read: PB signals failure
- SQLDBCode = 0 -- read: SELECT is valid syntax in DB server, but PB has buffer overrun
- SQLErrText = "Select returned more than one row"
- ROLLBACK - differences
- SNC returns number of reverted rows
- ODBC returns zero
TEST SCRIPT
NOTE - EDITED (I inserted my complete test script so anyone can run same test in your environment so we can compare and discuss results.
// PUBLIC FUNCTION = of_Test_SQLNRows ( )
// Test SQLNRows return values from embedded SQL.
// 1. Create TEST table in database (see comment below).
// 2. Call this function.
// TEST TABLE IN DATABASE --------------------------------------------------------------------------
// CREATE TABLE dbo.test_sqlnrows(
// id int identity not null,
// name nvarchar(50),
// value int,
// CONSTRAINT pk_test_sqlnrows PRIMARY KEY (id));
// -------------------------------------------------------------------------------------------------
constant string EOL = '~r~n'
constant string TAB = '~t'
long count, id
string text, name
text = 'DBMS = ' + SQLCA.DBMS + EOL + EOL
text += 'Test--' + TAB + 'SQL # rows' + TAB + 'NRows' + TAB + 'Notes---------' + EOL
// -------------------------------------------------------------------------------------------------
text += '(A)' + TAB + 'INSERT 1 row' + TAB
INSERT INTO test_sqlnrows(name, value) VALUES ('Test embedded', 4);
text += string(SQLCA.SQLNRows) + EOL
// -------------------------------------------------------------------------------------------------
text += '(B)' + TAB + 'SELECT 1 row' + TAB
SELECT newID INTO :id FROM (SELECT SCOPE_IDENTITY() newID) data;
text += string(SQLCA.SQLNRows) + EOL
// -------------------------------------------------------------------------------------------------
text += '(C)' + TAB + 'COMMIT 1 row' + TAB
COMMIT;
text += string(SQLCA.SQLNRows) + EOL
// -------------------------------------------------------------------------------------------------
text += '(D)' + TAB + 'SELECT COUNT' + TAB
SELECT count(*) INTO :count FROM test_sqlnrows WHERE value = 4;
text += string(SQLCA.SQLNRows) + TAB + ' COUNT(*) = ' + string(count) + EOL
// -------------------------------------------------------------------------------------------------
text += '(E)' + TAB + 'SELECT ' + string(count) + ' rows' + TAB
SELECT name INTO :name FROM test_sqlnrows WHERE value = 4;
text += string(SQLCA.SQLNRows) + EOL
text += TAB + 'SQL Code ' + TAB + string(SQLCA.SQLCode) + ' =>' + TAB + 'PB buffer overrun' + EOL
text += TAB + 'SQL DB Code =' + TAB + string(SQLCA.SQLDBCode) + ' =>' + TAB + 'Valid in DBMS' + EOL
text += TAB + 'SQL Err Text = "' + SQLCA.SQLErrText + '"' + EOL
// -------------------------------------------------------------------------------------------------
text += '(F)' + TAB + 'UPDATE ' + string(count) + ' rows' + TAB
UPDATE test_sqlnrows SET name = REVERSE(name) WHERE value = 4;
text += string(SQLCA.SQLNRows) + EOL
// -------------------------------------------------------------------------------------------------
text += '(G)' + TAB + 'ROLLBACK all ' + string(count) + TAB
ROLLBACK;
text += string(SQLCA.SQLNRows) + EOL
// -------------------------------------------------------------------------------------------------
MessageBox("Test SQLNRows", text)
// DONE
Test Results
Check no. |
SQL |
SQLNRows for SNC |
SQLNrows for ODBC |
Comments |
A |
INSERT |
1 |
1 |
|
B |
SELECT |
1 |
1 |
|
C |
COMMIT |
0 |
0 |
COMMIT changes no rows |
D |
SELECT |
1 |
1 |
Result of COUNT(*) is one value in one row |
E |
SELECT |
0 |
0 |
SQLCode = -1 SQLDBCode = 0 SQLErrText = Select returned more than one row |
F |
UPDATE |
17 |
18 |
ODBC: extra row inserted - hence 18, not 17 |
G |
ROLLBACK |
17 |
0 |
SNC: ROLLBACK reverted UPDATE to 17 rows. ODBC: ROLLBACK states 0 despite reverted data. |
NOTE: Each time I run my test I add one extra row. That's why my UPDATE gradually increases.
HTH /Michael