csdl3_chuong3

Màu nền
Font chữ
Font size
Chiều cao dòng

CHƯƠNG 3: VISUAL FOXPRO VI SQL SERVER

Visual FoxPro cung cấp hai cơ chế làm việc với dữ liệu dạng client/server là

view từ xa và cơ chế SQL pass through.

1. Làm vic vi view t xa

Một view từ xa là một phát biểu SELECT của SQL được lưu trữ trong cơ sở dữ

liệu của Visual FoxPro. View từ xa sử dụng cơ chế ODBC (Open DataBase

Connectivity) để kết nối dữ liệu.

1.1 Kết ni

Trước khi tạo một view từ xa thì phải xác định view đó sẽ kết nối vào cơ sở dữ

liệu như thế nào. Có nhiều cách để làm việc này, nhưng tất cả đều sử dụng ODBC. Vì

thế cả hai trình điều khiển ODBC ở server và client đều phải được cài đặt. Đối với

SQL server, việc cài đặt được thự hiện khi cài Visual Studio hoặc SQL Server.

Để có thể kết nối đến cơ sở dữ liệu đầu tiên chúng ta cần phải tạo một DSN.

Có ba loại DSN: Người dùng, hệ thống và file. Một DSN của người dùng chỉ có thể

được sử dụng bởi một người chỉ định, trong khi DSN hệ thống có thể được sử dụng

bởi bất kì người dùng nào trên máy. DSN người dùng và DSN hệ thống được lưu trữ

trong registry của máy trạm, trong khi file DSN được lưu trữ trong các file văn bản và

có thể tìm kiếm ở bất cứ nơi nào.

Lnh CREATE CONNECTION

Đặt tên cho kết nối tới cơ sở dữ liệu từ xa và lưu trữ trong cơ sở dữ liệu hiện

thời. Dạng lệnh:

CREATE CONNECTION [ConnectionName | ?]

[DATASOURCE cDataSourceName]

[USERID cUserID] [PASSWORD cPassWord]

[DATABASE cDatabaseName]

| CONNSTRING cConnectionString]

Trong đó:

ConnectionName: Tên của kết nối sẽ được tạo.

DATASOURCE cDataSourceName: Chỉ định tên nguồn dữ liệu trong ODBC

cho kết nối

USERID cUserID: Chỉ định tên truy cập dữ liệu được lưu trong dữ liệu ODBC

PASSWORD cPassWord: Chỉ định mật khNu truy cập dữ liệu được lưu trong

dữ liệu ODBC

DATABASE cDatabaseName: Tên cơ sở dữ liệu trên Server

CONNSTRING cConnectionString: Chỉ định một chuỗi kết nối cho các nguồn

dữ liệu ODBC. Chuỗi kết nối có thể được sử dụng thay thế việc khai báo rõ ràng trong

dữ liệu ODBC.

Ví dụ 1:

CLOSE DATABASES

OPEN DATABASE NorthWind

CREATE CONNECTION Myconn DATASOURCE "NorthWind"

CLEAR

DISPLAY CONNECTIONS

DELETE CONNECTIONS Myconn

Ví dụ 2:

CLOSE DATABASES

OPEN DATABASE NorthWind

St=[DSN=NorthWind; WSID=DRAGON;DATABASE=Northwind]

CREATE CONNECTIONS Myconn CONNSTRING (st)

1.2 To view t xa

Lnh CREATE SQL VIEW

CREATE [SQL] VIEW [ViewName] REMOTE

CONNECTION ConnectionName [SHARE] | CONNECTION DataSourceName

AS SQLSELECTStatement

Trong đó:

ViewName: Tên của view sẽ được tạo bởi lệnh

ConnectionName: Chỉ định tên của kết nối đã lập

DataSourceName: Tên của data source đã tồn tại để kết nối tới cơ sở dữ liệu.

SQLSELECTStatement: Câu lệnh SELECT của SQL

SHARE: Chỉ định kết nối được dùng chung cho các view từ xa.

Ví dụ:

CLOSE DATABASES

OPEN DATABASE Northwind

CREATE SQL VIEW MyView REMOTE CONNECTION Myconn SHARE;

AS SELECT * FROM Customers WHERE Country=’Mexico’

DBSETPROP(‘MyView’,’View’,’ShareConnection’, .T.)

USE MyView AGAIN IN 0

SELECT MyView

BROWSE LAST

USE IN MyView

DELETE VIEW MyView

Với ví dụ trên view này chỉ áp dụng cho các khách hàng ở Mexico mà không

áp dụng được với các khách hàng khác. Visual FoxPro cho phép tạo các view có

thông số, và các thông số này được đặt sau dấu chấm hỏi (?). Một thông số của view

là một biến nhớ, chúng sẽ được truyền vào view khi thực thi view đó.

Ví dụ tạo view có thông số cCountry như sau:

CLOSE DATABASES

OPEN DATABASE NorthWind

CREATE SQL VIEW MyView REMOTE CONNECTION Myconn SHARE;

AS SELECT * FROM Customers WHERE Country LIKE ?cCountry

cCountry=’U%’

USE MyView AGAIN IN 0

SELECT MyView

BROWSE LAST

USE IN MyView

DELETE VIEW myview

Nếu cCountry tồn tại khi view được mở hoặc sử dụng hàm REQUERY() hoặc

hàm REFRESH(), giá trị của biến sẽ được cung cấp cho mệnh đề where. Trong trường

hợp biến cCountry không tồn tại NSD sẽ được nhắc nhở cung cấp giá trị truyền cho

Nếu dùng hàm DBSETPROP():

Để chỉ định một cột làm khóa chính, dùng lệnh:

DBSetProp(Column_Name,"Field","KeyField",.T.)

Ví dụ:

DBSetProp(“MyView.customerid","Field","KeyField",.T.)

Để chỉ định một cột có thể cập nhật được, dùng lệnh:

DBSetProp(Column_name,"Field","Updatable",.T.)

Ví dụ

DBSetProp(“MyView.customerid","Field","Updatable",.T.)

Để cho view có thể cập nhật được, phải chỉ định

DBSetProp(View_Name,"View","SendUpdates",.T.)

Ví dụ

DBSetProp(“MyView”,"View","SendUpdates",.T.)

Chỉ định thuộc tính WhereType cho view, dùng lệnh

DBSetProp(View_Name,"View","WhereType", n)

Trong đó:

· n=1 (DB_KEY – Key field only): Xung đột sẽ xảy ra khi thay

đổi trên khóa chính. Khi đó, thay đổi trên khóa chính sẽ bị bỏ

qua.

· n=2 (DB_KEYANDUPDATETABLE – Key and updatable

fields): xung đột sẽ xảy ra khi thay đổi trên khóa chính hoặc các

trường (cột) cập nhật. Nếu có hai NSD cùng thay đổi trên các cột

cập nhật thì sẽ phát sinh lỗi.

· n=3 (DB_KEYANDMODIFIED – key and modified fields):

xung đột sẽ xảy ra khi thay đổi trên khóa chính hoặc các trường

(cột) cập nhật. Nếu có hai NSD cùng thay đổi trên một cột cập

nhật thì sẽ phát sinh lỗi.

· n=4 (DB_KEYANDTIMESTAMP – key and timestamp): xung

đột sẽ xảy ra khi thay đổi trên khóa chính hay thay đổi trên các

cột kiểu timestamp.

Ví dụ

DBSetProp(“MyView”,"View","WhereType",3)

Thiết lập thuộc tính UpdateType, dùng lệnh

DBSetProp(View_name,"View","UpdateType", n)

Trong đó

· n=1 (DB_UPDATE – SQL Update): Cập nhật dữ liệu mới

thay cho dữ liệu cũ.

· n=2 (DB_DELETEINSERT - SQL DELETE then INSERT):

Xóa dữ liệu cũ và chèn dữ liệu mới.

Ví dụ:

DBSetProp(“MyView”,"View","UpdateType", 1)

1.4 Bộ đệm cho view

Khi làm việc với cơ sở dữ liệu client/server, chúng ta không thể làm việc trực

tiếp được với các bảng mà làm việc trong các vùng đệm của các view. Với Visual

FoxPro có hai loại bộ đệm cho view: bộ đệm dòng và bộ đệm bảng. Bộ đệm dòng

hoàn tất các thay đổi mỗi lần trên một dòng còn bộ đệm bảng hoàn tất mỗi lần cho

nhiều dòng. Khi mở một view, bộ đệm dòng và bảng không được hỗ trợ. Để thay đổi

loại bộ đệm cần thiết lập thuộc tính cho cursor bằng hàm CURSORSETPROP(), dạng:

CURSORSETPROP(“Buffering”, nExpression, [,cTableAlias | nWorkArea])

Trong đó:

· nExpression=1: Tắt bộ đệm cho các dòng và các view.

· nExpression=2: Đặt bộ đệm dòng ở chế độ pessimistic

· nExpression=3: Đặt bộ đệm dòng ở chế độ optimistic

· nExpression=4: Đặt bộ đệm bảng ở chế độ pessimistic

· nExpression=5: Đặt bộ đệm bảng ở chế độ optimistic

Khi nExpression>1 thì cần chỉ định SET MULTILOCKS ON.

Ví dụ:

CURSORSETPROP(“Buffering”, 5, “MyView”)

Để quản lí trạng thái của các bộ đệm khi view đặt trong bộ đệm bảng, chúng ta

sử dụng hàm TABLEUPDATE() để gửi các thay đổi về server, TABLEREVERT() để

khôi phục trạng thái ban đầu của dữ liệu.

Hàm TABLEUPDATE(): Gửi các thay đổi về server

TABLEUPDATE( [nRows [, lForce]] [, cTableAlias | nWorkArea] )

Trong đó:

nRows: Chỉ định việc thay đổi trên bảng hay cursor đã hoàn tất

· nRows =0 (Tương đương với giá trị .F.): Hoàn tất sự thay đổi ở tại dòng

hiện tại và gửi các thay đổi này về server (ngầm định).

· nRows =1 (Tương đương với giá trị .T.): Hoàn tất sự thay đổi ở tất cả

các dòng trên bảng hay cursor và gửi các thay đổi này về server.

· nRows =2: Hoàn tất sự thay đổi ở tất cả các dòng trên bảng hay cursor

và gửi các thay đổi này về server. Tuy nhiên, nếu xuất hiện xung đột khi

cập nhật (tại một dòng nào đó) thì Visual FoxPro vẫn tiếp tục cập nhật

cho các dòng còn lại của bảng hay cursor.

lForce: Chỉ định xem Visual FoxPro có ghi đè các thay đổi trên bảng hay

cursor bởi NSD khác hay không

· lForce = .F. : Hoàn tất các thay đổi trên bảng hay cursor, bắt đầu từ

dòng đầu tiên cho đến dòng cuối cùng của bản hay cursor (Ngầm định).

· lForce = .T. : Ghi đè các thay đổi trên bảng hay cursor bởi NSD khác

trên mạng. Khi đó WhereType phải sử dụng là only key fields.

Hàm này trả về .T. khi các thay đổi hoàn tất thành công, và trả về .F. nếu xuất

hiện lỗi khi hoàn tất các thay đổi trên bảng hay cursor.

Ví dụ:

CLOSE DATABASES

OPEN DATABASE NorthWind

CREATE SQL VIEW MyView REMOTE CONNECTION Myconn SHARE;

AS SELECT * FROM Customers WHERE Country like ?cCountry

DBSETPROP(“MyView”,”View”,”ShareConnection”, .T.)

**Update on database server

** DBSETPROP("Myview","VIEW","SendUpdates",.T.)

cCountry=’M%’

USE MyView

SET MULTILOCKS ON && Must turn on for table buffering.

= CURSORSETPROP('Buffering', 5, 'MyView' ) && Enable table buffering.

CLEAR

GO TOP

? 'Original City value: '

?? City && Displays current City value (México D.F.

).

REPLACE City WITH 'New City'

? 'New City value: '

?? City && Displays new Cityvalue (New City).

= TABLEUPDATE(.T.) && Commits changes.

**Refreshing MyView

**=REQUERY()

? 'Updated City value: '

?? City && Displays current City value (New City).

USE IN MyView

DELETE VIEW MyView

Hàm TABLEREVERT(): Hủy bỏ các thay đổi ở vùng đệm dòng hay bảng

TABLEREVERT( [lAllRows [, cTableAlias | nWorkArea] ] )

Trong đó:

lAllRows: quyết định có hủy bỏ các thay đổi trên bảng hay cursor hay không?

· lAllRows=.F. : Chỉ những thay đổi trên dòng hiện tại của bảng hay

cursor bị hủy bỏ (ngầm định)

· lAllRows=.T. : Tất cả các thay đổi trên bảng hay cursor đều bị hủy bỏ

Hàm này trả về số các dòng của bảng hay cursor bị hủy bỏ.

Ví dụ:

CLOSE DATABASES

OPEN DATABASE NorthWind

CREATE SQL VIEW MyView REMOTE CONNECTION Myconn SHARE;

AS SELECT * FROM Customers WHERE Country like ?cCountry

DBSETPROP(“MyView”,”View”,”ShareConnection”, .T.)

*Update on database server

DBSETPROP("Myview","VIEW","SendUpdates",.T.)

cCountry=’M%’

USE MyView

SET MULTILOCKS ON && Must turn on for table buffering.

= CURSORSETPROP('Buffering', 5, 'MyView' ) && Enable table buffering.

CLEAR

Go top

?’original city valie:’

??city %%  díplays current city value(mexico DF)

REPLACE City WITH 'New City' && Changes field contents

? 'New City value: '

?? City && Displays new Cityvalue (New City).

= TABLEREVERT(.T.) && Discard all table changes.

=REQUERY()

? 'Reverted City value: '

?? City && Displays reverted City value (México D.F.).

USE IN MyView

DELETE VIEW MyView

1.5 Các kiu d liu tương thích

Giữa SQL Server và Visual FoxPro không có kiểu dữ liệu tưng xứng. Ví như,

Visual FoxPro hỗ trợ hai kiểu dữ liệu date và datetime, còn SQL Server thì không hỗ

trợ kiểu dữ liệu date nhưng lại có hai kiểu datetime và smalldatetime.

Khi tạo một view từ xa, Visual FoxPro sẽ tự động chuyển các kiểu dữ liệu của

SQL Server sang các kiểu dữ liệu tương ứng như bảng dưới.

Chúng ta cũng có thể sử dụng hàm DBSETPROP() để chuyển kiểu dữ liệu cho

bất kì trường (cột) nào trong view. Ví dụ, để ép kiểu từ datetime thành date trong

Visual FoxPro cho cột Birthday của view vEmployees ta dùng lệnh:

DBSETPROP(“vEmployees.BirthDay”,”Field”, “DataType”,”D”)

2. SQL Pass Through

View từ xa là cách dễ nhất để truy cập dữ liệu từ xa. Tuy nhiên, do dễ dàng sử

dụng nên nó thiếu tính mềm dẻo. Visual FoxPro có một cơ chế mạnh khác để quản lí

dữ liệu từ xa gọi là SQL Pass Through. SQL Pass Through có tất cả các tính năng mà

view từ xa cung cấp. Ngoài ra, SQL Pass Through còn có thể:

Thực thi các truy vấn khác với phát biểu SELECT

Lấy về nhiều tập kết quả trong một lời gọi.

Thực thi các thủ tục thường trú.

Tuy nhiên, SQL Pass Through

Không có giao diện NSD

Các kết nối phải quản lí thủ công

Các tập kết quả được mặc định là chỉ đọc, nên muồn cập nhật thì phải

cấu hình lại

2.1 Kết ni

Với kĩ thuật SQL Pass Through (SPT), chúng ta phải tạo và quản lí kết nối thủ

công. Để thiết lập các kết nối tới máy chủ từ xa chúng ta sử dụng một trong hai hàm

SQLConnect() và SQLStringConnect().

Hàm SQLConnect()

SQLCONNECT([cConnectionName | cDataSourceName [, cUserID [, cPassword ]][, lShared]])

Trong đó:

cConnectionName: chỉ định tên của kết nối được tạo bởi lệnh CREATE

CONNECTION

cDataSourceName: Tên của DSN có trong ODBC Administrator

cUserID: Tên của NSD dùng để đăng nhập vào server

cPassword : Mật khNu để đăng nhập vào server

lShared: Có tạo kết nối chia xẻ hay không.

Hàm này trả về một giá trị số và trả về số dương nếu kết nối thành công, trả về

-1 nếu thất bại.

Ví dụ:

LOCAL hConn

hConn=SQLConnect(“NorthWind”) && Northwind is DSN name

** Tên login: THTCKT, Mật khNu: 123456

hConn=SQLConnect("NorthWind","THTCKT","123456",.T.)

Ví dụ

CLOSE DATABASES

OPEN DATABASE NorthWind

** Kết nối MyConn có trong cơ sở dữ liệu NorthWind

hConn=SQLConnect("MyConn")

IF hConn < 0

= MESSAGEBOX('Cannot make connection', 16, 'SQL Connect Error')

ELSE && successful connection

= MESSAGEBOX('Connection made', 48, 'SQL Connect Message')

= SQLDISCONNECT(hConn)

ENDIF

Hàm SQLStringConnect()

SQLSTRINGCONNECT([lShared] | [cConnectString [, lSharable]])

Trong đó:

lShared: Có tạo kết nối chia xẻ hay không.

cConnectString: Chỉ định xâu kết nối đầy đủ để kết nối vào máy chủ. Xâu kết

nối bao gồm các tùy chọn được phân cách nhau bởi dấu chám phảy (;) để biểu diễn

nguồn dữ liệu và các thiết lập kết nối. Các tùy chọn thường sử dụng được cho ở bảng

sau:

lSharable: Chỉ định xâu kết nối cConnectString là chia xẻ hay không.

Hàm này trả về một giá trị số và trả về số dương nếu kết nối thành công, trả về

-1 nếu thất bại.

Ví dụ:

LOCAL hConn

stConn= “Driver=SQL Server;” ;

+ "SERVER=DRAGON\SQLEXPRESS;" ;

+ "UID=THTCKT;" ;

+ "PWD=123456;" ;

+ "DATABASE=NORTHWIND;" ;

+ "WSID=DRAGON"

hConn=SQLSTRINGCONNECT(stConn)

Ví dụ:

LOCAL hConn

stConn= “DSN=NorthWind;” ;

+ "DATABASE=NORTHWIND;" ;

+ "Trusted_connection=Yes"

hConn=SQLSTRINGCONNECT(stConn)

IF hConn < 0

= MESSAGEBOX('Cannot make connection', 16, 'SQL Connect Error')

ELSE && successful connection

= MESSAGEBOX('Connection made', 48, 'SQL Connect Message')

= SQLDISCONNECT(hConn)

ENDIF

Hàm SQLDisconnect()

nReturnValue = SQLDisconnect( nConnectionHandle )

2.2 Đệ trình các truy vn

Đa phần các tương tác với server từ xa trong Visual FoxPro thông qua hàm

SQLExec(). Nhiệm vụ chính của hàm SQLExec() là gửi một câu truy vấn tới server và

server sẽ trả kết quả về cho Visual FoxPro.

nSuccess = SQLEXEC(nStatementHandle[, cSQLCommand [, cCursorName]])

Trong đó

* In synchronous mode

nHandle = SQLConnect("Northwind")

IF nHandle > 0

IF SQLExec(nHandle, "Select * FROM Customers") = 1

BROWSE

ELSE

WAIT WINDOW "Trouble at the pass"

ENDIF

ELSE

WAIT WINDOW "Can't connect"

ENDIF

* Set up a parameterized SPT command

* Use the same connection as above

cCountry = ""

IF SQLPrepare(nHandle, ;

"SELECT * FROM Customers WHERE Country = ?cCountry") = 1

cCountry = "UK"

IF SQLExec(nHandle) = 1

* Got all UK Customers

BROWSE TITLE "Customers in the UK"

ENDIF

cCountry = "USA"

IF SQLExec(nHandle) = 1

* Got all US Customers

BROWSE TITLE "Customers in the USA"

ENDIF

ENDIF

Truy vn tr v mt tp kết qu

LOCAL hConn

stConn= “DSN=NorthWind;” ;

+ "DATABASE=NORTHWIND;" ;

+ "Trusted_connection=Yes"

hConn=SQLSTRINGCONNECT(stConn)

IF hConn < 0

= MESSAGEBOX('Cannot make connection', 16, 'SQL Connect Error')

ELSE && successful connection

lnResult=SQLExec(hConn,[SELECT * FROM Customers ];

+[ WHERE City LIKE ’M%’], [Customers])

IF lnResult>0

SELECT Customers

BROWSE

USE IN Customers

ELSE

=MESSAGEBOX([An error occurred],16,[Note])

ENDIF

= SQLDISCONNECT(hConn)

ENDIF

Truy vn tr v nhiu tp kết qu

LOCAL hConn

stConn= “Driver=SQL Server;” ;

+ "SERVER=DRAGON\SQLEXPRESS;" ;

+ "UID=THTCKT;" ;

+ "PWD=123456;" ;

+ "DATABASE=NORTHWIND;" ;

+ "WSID=DRAGON"

hConn=SQLSTRINGCONNECT(stConn)

IF hConn < 0

= MESSAGEBOX('Cannot make connection', 16, 'SQL Connect Error')

ELSE && successful connection

lnResult=SQLExec(hConn,[SELECT * FROM Customers ;] ;

+[ SELECT * FROM Employees])

IF lnResult>0

SELECT SQLResult

BROWSE TITLE "Customers "

USE IN SQLResult

SELECT SQLResult1

BROWSE TITLE "Employees "

USE IN SQLResult1

ELSE

=MESSAGEBOX([An error occurred],16,[Note])

ENDIF

= SQLDISCONNECT(hConn)

ENDIF

Các truy vn khác

CLEAR

LOCAL lnConn

LOCAL lnPercent AS Int && Input parameters must be typed.

LOCAL lnOutput

lnPercent = 50

lnOutput = 0

* Make connection, assuming a local trusted connection.

lnConn = SQLCONNECT('Pubs')

IF m.lnConn > 0 && Success.

* Set the active database to PUBS.

SQLEXEC(m.lnConn, 'use pubs')

* Execute SELECT statement.

SQLEXEC(m.lnConn, 'SELECT * FROM authors', 'PubAuthors')

BROWSE

* Execute INSERT statement, get value of identity field.

SQLEXEC(m.lnConn, "INSERT INTO JOBS (job_desc, min_lvl, max_lvl);

VALUES ('Developer',75,150)")

SQLEXEC(m.lnConn, "SELECT SCOPE_IDENTITY()", "job_id")

? "ID for added Job is " + LTRIM(STR(job_id.exp))

* Execute DELETE statement. Get number of records affected.

SQLEXEC(m.lnConn, "DELETE FROM JOBS WHERE job_desc ='Developer'")

SQLEXEC(m.lnConn, "SELECT @@ROWCOUNT", 'rowcount')

? rowcount.exp, "record(s) deleted"

* Call a stored procedure with no parameters.

SQLEXEC(m.lnConn, 'sp_who', 'activeusers')

BROWSE

* Execute stored procedure with an INPUT parameter.

SQLEXEC(m.lnConn, 'exec byroyalty ?lnPercent','HalfOffAuthors')

* Create temp stored procedure with OUTPUT parameter and call it.

SQLEXEC(m.lnConn, "CREATE PROCEDURE #MyProc @outparam int OUTPUT AS;

SELECT @outparam=100")

SQLEXEC(m.lnConn, "exec #myProc ?@lnOutput")

? m.lnOutput

* Create a temp stored procedure with INPUT and OUTPUT parameters

* and call it.

SQLEXEC(m.lnConn, "CREATE PROCEDURE #MyProc2 " + ;

"@inputparam INT, " + ;

"@outparam int OUTPUT " + ;

"AS SET @outparam=@inputparam*10")

SQLEXEC(m.lnConn, "exec #myProc2 ?lnPercent, ?@lnOutput")

? m.lnOutput

* Get version information.

SQLEXEC(m.lnConn, 'SELECT @@VERSION','SQLVersion1')

? STRTRAN(SQLVersion1.Exp,CHR(0))

* Disconnect.

SQLDISCONNECT(m.lnConn)

ELSE

? "Unable to connect to SQL Server"

ENDIF

RETURN

Truy vn tham s

Cũng giống như view từ xa, kỹ thuật SPT cũng cho phép gửi một truy vấn có

tham số. Các tham số là các biến nhớ và được để sau dấu chấm hỏi (?) như ví dụ sau:

LOCAL hConn, lcQuery, ldStart, ldStop

stConn= “DSN=NorthWind;” ;

+ "DATABASE=NORTHWIND;" ;

+ "Trusted_connection=Yes"

hConn=SQLSTRINGCONNECT(stConn)

IF hConn < 0

= MESSAGEBOX('Cannot make connection', 16, 'SQL Connect Error')

ELSE && successful connection

ldStart={^1998/1/1}

ldStop={^1998/12/31}

lcQuery=[SELECT C.CustomerID, O.OrderID,+ O.OrderDate, ];

+[C.CompanyName, C.City, C.Country ];

+ [ FROM dbo.Customers C INNER JOIN dbo.Orders O ];

+[ ON C.CustomerID = O.CustomerID ];

+[WHERE C.Country LIKE ( 'U%' ) ];

+[ AND O.OrderDate BETWEEN ?ldStart AND ?ldStop ];

+[ ORDER BY C.CustomerID]

lnResult=SQLExec(hConn,lcQuery, [Customers])

IF lnResult>0

SELECT Customers

BROWSE

USE IN Customers

ELSE

=MESSAGEBOX([An error occurred],16,[Note])

ENDIF

= SQLDISCONNECT(hConn)

ENDIF

2.3 Cp nht kết qu v server

Khi dùng SPT thì mặc nhiên tập kết quả là một cursor chỉ đọc. Điều này có

nghĩa là dữ liệu đã được gửi từ server về, còn khi NSD thay đổi trên cursor thì Visual

FoxPro không gửi lại server. Để Visual FoxPro gửi các thay đổi trên tập kết quả của

truy vấn thì chúng ta cần sử dụng hàm CURSORSETPROP() để thay đổi một số thuộc

tính của cursor. Cụ thể, để truy vấn cập nhật ngược trở về server thì phải:

Thiết lập thuộc tính Table cho cursor để xác định cập nhật về server cho

bảng nào

Thiết lập thuộc tính KeyFieldList cho cursor để xác định các trường

khóa của cursor

Thiết lập thuộc tính UpdatableFieldList cho cursor để xác định danh

sách các trường có thể cập nhật ngược về server.

Thiết lập thuộc tính UpdateNameList cho cursor để xác định tên của các

trường (cột) nào của cursor tương ứng với tên của cột trong bản trên

server

Thiết lập thuộc tính SendUpdates của cursor về .T.

Hàm CURSORSETPROP() cho phép thiết lập thuộc tính cho các bảng hay

cursor của FoxPro, và có cú pháp là:

CURSORSETPROP( cProperty [, eExpression] [,cTableAlias | nWorkArea])

Trong đó:

cProperty: Chỉ định tên thuộc tính của bảng hay cursor.

eExpression: Chỉ định giá trị cho các thuộc tính được chỉ định ở cProperty

Dưới đây là một số thuộc tính cơ bản và giá trị của nó có thể nhận:

Ví dụ:

LOCAL hConn, lcQuery, ldStart, ldStop

stConn= "DSN=NorthWind;" ;

+ "DATABASE=NORTHWIND;" ;

+ "Trusted_connection=Yes"

hConn=SQLSTRINGCONNECT(stConn)

IF hConn < 0

= MESSAGEBOX('Cannot make connection', 16, 'SQL Connect Error')

ELSE && successful connection

ldStart={^1998/1/1}

ldStop=DATETIME()

lcQuery=[SELECT OrderID, OrderDate, ShipCity AS City];

+ [ FROM Orders WHERE OrderDate BETWEEN ?ldStart ];

+[ AND ?ldStop ORDER BY OrderID]

lnResult=SQLExec(hConn,lcQuery, [curOrders])

IF lnResult>0

CURSORSETPROP("Tables","Orders","curOrders")

CURSORSETPROP("KeyFieldList","OrderID"," curOrders")

CURSORSETPROP("UpdatableFieldList","OrderDate, City","

curOrders ")

CURSORSETPROP("UpdateNameList", ;

"OrderID Orders.OrderID, "+;

"OrderDate Orders.OrderDate, "+ ;

“City Orders.ShipCity”, " curOrders")

CURSORSETPROP("WhereType",1," curOrders")

CURSORSETPROP("Buffering",5," curOrders")

CURSORSETPROP("SendUpdates",.F.," curOrders")

REPLACE OrderDate WITH Date(), City WITH “New City”

CURSORSETPROP("SendUpdates",.T.," curOrders")

=TABLEUPDATE(.T.)

USE IN curOrders

ELSE

=MESSAGEBOX([An error occurred],16,[Note])

ENDIF

= SQLDISCONNECT(hConn)

ENDIF

Bạn đang đọc truyện trên: Truyen2U.Pro