SQL Server. Conseguir el Registro anterior al que estoy.

08/08/2006 - 17:19 por Fabián Tomás de Paula | Informe spam
Con la siguiente instrucción, creo una UDF en el servidor que lo que hace es
devolverme el registro próximo al que estuve, valiendome de ello del nombre
del articulo.

CREATE FUNCTION [dbo].[fn_NxtArticulo] (@LastNombre varchar(70) = NULL)

RETURNS TABLE

AS

RETURN (

SELECT CodInt, MAX(Descrip+Present) AS NameArticulo

FROM (SELECT TOP 2 WITH TIES *

FROM Articulo

WHERE CASE WHEN @LastNombre IS NULL THEN 1

WHEN @LastNombre<Descrip+Present THEN 1

ELSE 0

END=1

ORDER BY Descrip, Present) AS N

GROUP BY CodInt, Descrip, Present

)

Cómo podría hacer para que con un código similar a éste me devuelva el
anterior al que estuve.

Desde ya gracias.

Fabián
 

Leer las respuestas

#1 Fabián Tomás de Paula
08/08/2006 - 20:54 | Informe spam
Acá les dejo la Definición de una Clase CursorAdapter, la misma permite
"NAVEGAR" una tabla
situada ésta en un SQL Server.
Espero les agrade el código. Por lo pronto a mi me resultó. Espero que les
sea útil.
Le agradezo a Carlos Sacristán que me dio el Tip avisándome que estaba yendo
por mal camino.
Gracias nuevamente.

Saludos a todos. Buena Semana

Fabián.

Funciones que Utiliza la Clase CursorAdapter

# DEFINE _Space0 ""
# DEFINE _Space1 " "
# DEFINE _Punto "."
# DEFINE _Coma ", "
FUNCTION GetFields
LPARAMETER cCursorAlias, cUpdateTable
IF EMPTY(DBF(cCursorAlias))
MESSAGEBOX("No hay ningun cursor abierto", 64, "Importante:")

RETURN c_Space0
ENDIF

LOCAL cCad2Return, nContFiels

cCad2Return = ""

FOR nContFiels = 1 TO FCOUNT(cCursorAlias)
IF (UPPER(FIELD(nContFiels, cCursorAlias)) == "ADOBOOKMARK") = .F.
cCad2Return = cCad2Return+;
PROPER(FIELD(nContFiels, cCursorAlias))+_Space1+;
PROPER(cUpdateTable)+_Punto+;
PROPER(FIELD(nContFiels, cCursorAlias))+_Coma
ENDIF
ENDFOR
STORE LEFT(cCad2Return, LEN(cCad2Return)-2) TO cCad2Return
RETURN cCad2Return
ENDFUNC

FUNCTION GetListFields
LPARAMETER cCursorAlias

IF TYPE("cCursorAlias") <> "C"
IF USED()
cCursorAlias = ALIAS()
ELSE
cCursorAlias = ""
ENDIF
ENDIF

IF EMPTY(DBF(cCursorAlias))
MESSAGEBOX("No hay ningun cursor abierto", 64, "Importante:")

RETURN ""
ENDIF

LOCAL cCad2Return, nContFiels

cCad2Return = ""

FOR nContFiels = 1 TO FCOUNT(cCursorAlias)
IF (UPPER(FIELD(nContFiels, cCursorAlias)) == "ADOBOOKMARK") = .F.
cCad2Return = cCad2Return + PROPER(FIELD(nContFiels, cCursorAlias)) + ","
ENDIF
ENDFOR

STORE LEFT(cCad2Return, LEN(cCad2Return) - 1) TO cCad2Return

RETURN cCad2Return
ENDFUNC


*
* Clase _CursorAdapter para abrir una tabla ubicada en un SQL SERVER
*
#DEFINE ADSTATECLOSED 0x00000000
#DEFINE ADSTATEOPEN 0x00000001
#DEFINE ADSTATECONNECTING 0x00000002
#DEFINE ADSTATEEXECUTING 0x00000004
#define ADOCONNECT_TIMEOUT_DEFAULT 15
#define ADOQUERY_TIMEOUT_DEFAULT 30
#Define _StringDB [Provider=SQLOLEDB.1;Integrated
Security=SSPI;Trusted_Connection=Yes;APP=Microsoft Visual
FoxPro;WSID=HOSTName;Initial CatalogºSEdeDATOS;Data
Source=HOSTName\SERVERNAME;]

DEFINE Class _CursorAdapter AS CursorAdapter
HIDDEN NavigateTable
HIDDEN SQLADOConnection
HIDDEN NavigateNextSort
HIDDEN NavigatePriorSort
HIDDEN NavigateKey2Comp

NavigateTable = ""
NavigateNextSort = ""
NavigatePriorSort = ""
NavigateKey2Comp = ""
SQLADOConnection = .NULL.

FUNCTION Init
LPARAMETERS cAlias, cDb2update, lUpdateTable, cKeyfieldlist, nBuffer,;
cNavigateKey2Comp, cNavigateNextSort, cNavigatePriorSort

IF VARTYPE(cAlias) <> "C" OR EMPTY(cAlias)
RETURN .F.
ENDIF

IF TYPE("cDb2update") <> "C" .OR. EMPTY(cDb2update)
cDb2update = cAliasCA
ENDIF

IF lUpdateTable
IF TYPE("cKeyfieldlist") <> "C" .OR. EMPTY(cKeyfieldlist)
cKeyfieldlist = ""
lUpdateTable = .F.
ENDIF
ELSE
STORE "" TO cKeyfieldlist
ENDIF

IF TYPE("nBuffer") <> "N" OR INLIST(nBuffer, 3, 5) = .F.
nBuffer = 5
ENDIF

IF INLIST("C", VARTYPE(cNavigateKey2Comp), VARTYPE(cNavigateNextSort),
VARTYPE(cNavigatePriorSort)) = .F.;
OR INLIST(.T., EMPTY(cNavigateKey2Comp), EMPTY(cNavigateNextSort),
EMPTY(cNavigatePriorSort))
STORE 0 TO cNavigateKey2Comp, cNavigateNextSort, cNavigatePriorSort
ENDIF

LOCAL cIdADOConn, oRS AS ADODB.Recordset, lInit AS Logical
LOCAL oADOConnObj AS ADODB.Connection
LOCAL oException AS Exception

WITH This
oADOConnObj = CREATEOBJECT("ADODB.Connection")

With oADOConnObj
.ConnectionString = _StringDB
.ConnectionTimeout = ADOCONNECT_TIMEOUT_DEFAULT
.CommandTimeout = ADOQUERY_TIMEOUT_DEFAULT
EndWith

TRY
IF (oADOConnObj.State == ADSTATEOPEN) == .F.
oADOConnObj.Open()
ENDIF
CATCH TO oException
MESSAGEBOX(oException.Message)
FINALLY
lInit = .T.
ENDTRY

IF lInit
lInit = .F.

TRY
oRS = CREATEOBJECT("ADODB.Recordset")
CATCH TO oException
MESSAGEBOX(oException.Message)
FINALLY
lInit = .T.

WITH oRS
WITH .DataSource
.CursorLocation = 3 &&adUseClient
.LockType = 3 &&adLockOptimistic
ENDWITH

.ActiveConnection = oADOConnObj
ENDWITH

.DataSourceType = "ADO"
.DataSource = oRS
.MapBinary = .T.
.MapVarchar = .T.
.Alias = cAlias
.BufferModeOverride = nBuffer
.NavigateTable = cDb2update
.NavigateNextSort = cNavigateNextSort
.NavigatePriorSort = cNavigatePriorSort
.NavigateKey2Comp = cNavigateKey2Comp
.SelectCmd = "SELECT * FROM " + cDb2update + " WHERE 1 = 0"

STORE lUpdateTable TO .AllowDelete,;
.AllowUpdate,;
.AllowInsert

lInit = .CursorFill()

IF lInit = .F.
* Replace with error code here
DIMENSION laError[1]

AERROR(laError)

MESSAGEBOX(laError[2])
ELSE
IF lUpdateTable
.Tables = cDb2update
.UpdateNameList = GetFields(.Alias, cDb2update)
.KeyFieldList = cKeyfieldlist
.UpdaTableFieldList = GetListFields(.Alias)
ENDIF
ENDIF
ENDTRY
ENDIF
ENDWITH

RETURN lInit
ENDFUNC

FUNCTION Next
LOCAL cCurrent, lReturn

STORE "" TO cCurrent

WITH This
IF USED(.Alias)
SELECT(.Alias)

cCurrent = EVALUATE(.NavigateKey2Comp)
ENDIF

TEXT TO cSQL TEXTMERGE NOSHOW
SELECT TOP 1 * FROM <<.NavigateTable>> WHERE <<.NavigateKey2Comp>> > <<"'" +
cCurrent + "'">> Order By <<.NavigateNextSort>>
ENDTEXT

.SelectCmd = cSQL

lReturn = .CursorFill()

IF lReturn = .F.
* Replace with error code here
DIMENSION laError[1]

AERROR(laError)

MESSAGEBOX(laError[2])
ELSE
IF EOF(.Alias)
.Last()
ENDIF
ENDIF
ENDWITH

RETURN lReturn
ENDFUNC

FUNCTION Last
LOCAL cCurrent, lReturn

WITH This
IF USED(.Alias)
USE IN (.Alias)
ENDIF

TEXT TO cSQL TEXTMERGE NOSHOW
SELECT TOP 1 * FROM <<.NavigateTable>> Order By <<.NavigatePriorSort>>
ENDTEXT

.SelectCmd = cSQL

lReturn = .CursorFill()

IF lReturn = .F.
* Replace with error code here
DIMENSION laError[1]

AERROR(laError)

MESSAGEBOX(laError[2])
ENDIF
ENDWITH

RETURN lReturn
ENDFUNC

FUNCTION First
LOCAL cCurrent, lReturn

WITH This
IF USED(.Alias)
USE IN (.Alias)
ENDIF

TEXT TO cSQL TEXTMERGE NOSHOW
SELECT TOP 1 * FROM <<.NavigateTable>> Order By <<.NavigateNextSort>>
ENDTEXT

.SelectCmd = cSQL

lReturn = .CursorFill()

IF lReturn = .F.
* Replace with error code here
DIMENSION laError[1]

AERROR(laError)

MESSAGEBOX(laError[2])
ENDIF
ENDWITH

RETURN lReturn
ENDFUNC

FUNCTION Prior
LOCAL cCurrent, lReturn

STORE "" TO cCurrent

WITH This
IF USED(.Alias)
SELECT(.Alias)

cCurrent = EVALUATE(.NavigateKey2Comp)
ENDIF

TEXT TO cSQL TEXTMERGE NOSHOW
SELECT TOP 1 * FROM <<.NavigateTable>> WHERE <<.NavigateKey2Comp>> < <<"'" +
cCurrent + "'">> Order By <<.NavigatePriorSort>>
ENDTEXT

.SelectCmd = cSQL

lReturn = .CursorFill()

IF lReturn = .F.
* Replace with error code here
DIMENSION laError[1]

AERROR(laError)

MESSAGEBOX(laError[2])
ELSE
IF EOF(.Alias)
.First()
ENDIF
ENDIF
ENDWITH

RETURN lReturn
ENDFUNC
ENDDEFINE


"Fabián Tomás de Paula" escribió en el mensaje
news:
Con la siguiente instrucción, creo una UDF en el servidor que lo que hace
es devolverme el registro próximo al que estuve, valiendome de ello del
nombre del articulo.

CREATE FUNCTION [dbo].[fn_NxtArticulo] (@LastNombre varchar(70) = NULL)

RETURNS TABLE

AS

RETURN (

SELECT CodInt, MAX(Descrip+Present) AS NameArticulo

FROM (SELECT TOP 2 WITH TIES *

FROM Articulo

WHERE CASE WHEN @LastNombre IS NULL THEN 1

WHEN @LastNombre<Descrip+Present THEN 1

ELSE 0

END=1

ORDER BY Descrip, Present) AS N

GROUP BY CodInt, Descrip, Present

)

Cómo podría hacer para que con un código similar a éste me devuelva el
anterior al que estuve.

Desde ya gracias.

Fabián


Preguntas similares