Classic ASP: how to convert a RecordSet to json notation using AXE json implementation

♀尐吖头ヾ 提交于 2019-11-28 10:10:57

问题


i'm doing an application with ajax using jQuery and some other tools, and in some part i want to retrieve data with ajax using a classic ASP backend, i saw that exists a good implementation of a JSON class in AXE (Asp extreme edition) framework, and i used it but currently i don't understand how to use it well.

Edit: based on the correct answer of JSON.Stringify fails on Scripting.Dictionary objects Thread, i decided to make a custom function to process Recordsets.

Edit 2: Now i'm losing the value data when call JSON.stringify inside function JSONStringify(object).

when the Recordset is passed as value to JSONStringify everything is ok but when JSON.stringify is executed, the "value" parameter that must contain the recordset becomes undefined

What i'm expecting (example)

passing a Recordset with from a SQL query SELECT name, tel FROM users a see an output like this

[
    {"name":"Jonh Smith", "tel":"12345678"},
    {"name":"April Michelson", "tel":"77788802"},
    ...
]

passing a Dictionary and see something similar based in the elements declared in dictionary.

{
   "element1":"value1",
   "element2":"value2",
   "element3":"value3",
   "element4":"value4",
   "element5":"value5"
}

and if i like to support other type object i can do it expanding the function

Source Code

getcatalogos.asp

<!--#include file="../includes/conexion.asp" -->
<!--#include file="../includes/json2.asp" -->
<!--#include file="../includes/json-stringify-parser.asp" -->
<%
Response.ContentType = "application/json"
dim aVals(2)

function getCatalogo(tipo, params)
    Dim oConn,oCmd,sSQL,oRs,cont2
    Dim aData,oPar,cont
    dim Info 

    set oConn = Server.CreateObject("ADODB.Connection")
    set oCmd = Server.CreateObject("ADODB.Command")

    sWhere = ""

    oConn.ConnectionString = strcon
    oConn.Open
    Set oCmd.ActiveConnection = oConn

    select case tipo
        case "g"
            sSQL = " SELECT cve_gr, descr FROM gr ORDER BY descr ;"
        case "z" 
            sSQL = " SELECT cve_zn, descr FROM zn WHERE cve_gr = ? ORDER BY descr ;"
            if IsArray(params) Then
                Set oPar=oCmd.CreateParameter (params(0),129,1,2,params(1))
                oCmd.Parameters.Append(oPar)
            End if
        case else
            getCatalogo = false
            exit function
    end select

    oCmd.CommandText = sSQL
    Set oRs = oCmd.Execute()
    if Not oRs.EOF Then
        response.write(JSONStringify(oRs))
        getCatalogo = true
    else
        getCatalogo = false
    end if
    oConn.Close
end function

aVals(0) = "cve_gr"
aVals(1) = request.querystring("gr")
if Not getCatalogo(request.querystring("t"),aVals) Then
    %>error<%
end if

%>

json-stringify-parser.asp

<!--#include file="vbsTyper.asp" -->
<script runat="server" language="JScript">

    function JSONStringify(object) {
        VBSTypeName(object);
        return JSON.stringify(object,stringifyData);
    }

    function stringifyData(holder, key, value) {
        var sType = '';
        var result;

        //response.write('pre...holder=' + holder + ',key=' + key + ',value=' + value);
        sType = VBSTypeName(value);
        //response.write('post =' + sType);

        //response.write(sType);
        switch(sType){
            case 'Dictionary':
                result = '{';
                for(var enr = new Enumerator(value); !enr.atEnd(); enr.moveNext()){
                    key = enr.item();
                    result += '"' + key + '": ' + JSON.stringify(value.Item(key));
                };
                result += '}';
                return(result);
                break;
            case 'Recordset':
                response.write('here!!!');
                var sTemp = '';
                result = '{';
                while(!value.EOF){
                    if(Len(result) > 0){
                        result += ',';
                    }
                    result += '{';
                    for (var i = value.Fields.Count - 1; i >= 0; i--){
                        if(len(sTemp) > 0){
                            sTemp += ',';
                        }
                        sTemp += '"' + value.Fields(i).name + '":' + JSON.stringify( value.Fields(i).value);
                    };
                    result += '}';
                }   
                result += '}';
                return result;
                break;
            default:
                //response.write(sType);
                return(value);
        }     
        // return the value to let it be processed in the usual way
        return result;
   }

</script>

vbsTyper.asp

<%
Function VBSTypeName(Obj)
    dim sType 
    sType = Cstr(TypeName(Obj))
    response.write(sType)
    VBSTypeName = sType
End Function
%>

回答1:


This:

response.write(JSON.stringify(oRs))

Should read something like this:

Do Until oRS.EOF
  response.write(JSON.stringify(oRs("cve_gr") & ":" & oRs("descr"))
  oRS.MoveNext
Loop



回答2:


kind of achieve it...

Short version: i had to modify the json2.asp and hack the stringify() function definition to make it works.

Long Version

later of see every line of code and giving up on the problem. i decided to take a look into json2.asp (AXE Framework) and try to see what it happening there.

look what i see:

from the lines 682 to 687 theres a validation if a custom stringy parser is found but later doesn't do anything ... only returns the Object value.

there's speculation from here, because i don't understand well how works every Javascript implementation, but implying that the original code runs well, that a standart javascript interpreter (read everything else but microsoft here) will force a serialization of the object in this sutuation, but the JScript interpreter try to parse the object and pass the value as null. resulting in that every function that uses a custom stringyfier can't read the object passed in the function.

what i did to resolve ok i inserted this chunk of code before line 688, forcing to execute the custom stringyfier with value directly passed as argument avoiding the implicit parsing.

        // Hack & patch to deliver the stringify-ing of the object correctly
        // IDK if this is CORRECT or dont but it works in VbScript
        if(replacer){
            var textval = rep(this,'',value);
            value = textval;
        }

later i had to do some changes in json-stringify-parser.asp because i had to fix some bugs resulting in this code

<!--#include file="vbsTyper.asp" -->
<script runat="server" language="JScript">

    function JSONStringify(object) {
        //VBSTypeName(object);
        return JSON.stringify(object,stringifyData,4);
    }

    function stringifyData(holder, key, value) {
        var sType = '';
        var result;

        //response.write('pre...holder=' + holder + ',key=' + key + ',value=' + value);
        sType = VBSTypeName(value);
        //response.write('post =' + sType);

        //response.write(sType);
        switch(sType){
            case 'Dictionary':
                result = '{';
                for(var enr = new Enumerator(value); !enr.atEnd(); enr.moveNext()){
                    key = enr.item();
                    result += '"' + key + '": ' + JSON.stringify(value.Item(key));
                };
                result += '}';
                return(result);
                break;
            case 'Recordset':
                //response.write('here!!!');
                var sTemp;
                result = '';
                while(!value.EOF){
                    if(result.length > 0){
                        result += ',';
                    }
                    result += '{';
                    sTemp=''
                    for (var i = 0; i < value.fields.Count; i++){
                        if(sTemp.length > 0){
                            sTemp += ',';
                        }
                        //response.write("i=" + i + ",");
                        sTemp += '"' + value.fields.item(i).name + '":' + JSON.stringify( value.fields.item(i).value);
                    };
                    result += sTemp + '}';
                    value.moveNext();
                }   
                result = '{' + result  + '}';
                return result;
                break;
            default:
                //response.write(sType);
                return(value);
        }     
        // return the value to let it be processed in the usual way
        return result;
   }

</script>

the part to parse a Recordset works, the part to parse a dictionary is same like the shown in JSON.Stringify fails on Scripting.Dictionary objects (a.k.a. i haven't tested yet) but for now i'm done with this.

testing my changes with a recordset object results in this output

"{
    {\"clave\":\"BC\",\"descripcion\":\"Cal\"},
    {\"clave\":\"CT\",\"descripcion\":\"Center\"},
    {\"clave\":\"NE\",\"descripcion\":\"Norw\"},
    {\"clave\":\"NO\",\"descripcion\":\"Nore\"},
    {\"clave\":\"NT\",\"descripcion\":\"North\"},
    {\"clave\":\"OC\",\"descripcion\":\"East\"},
    {\"clave\":\"OR\",\"descripcion\":\"West\"},
    {\"clave\":\"PE\",\"descripcion\":\"Pen\"},
    {\"clave\":\"SE\",\"descripcion\":\"Southe\"},
    {\"clave\":\"ZM\",\"descripcion\":\"Met\"}
}"

Questions Left

question that i have left withis kind of hack.

  • it's Ok that the output has (") character at the beggining and the end and i everything else has escape sencuences ?? or it's something that should not occurs.

  • this kind of hack is really wrong ... i can do it better, in this kind of situation ?

  • it's something wrong in my conclusion or arguments ??



来源:https://stackoverflow.com/questions/9332909/classic-asp-how-to-convert-a-recordset-to-json-notation-using-axe-json-implemen

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!