This project is read-only.
1
Vote

Escape comma in string attribute

description

First of all thanks for developing qdfoxJSON:

Now the issue:
Escape comma in string attribute

Example:

lJson='{"code": 123,"atributteWithComma":"THIS STRING HAS A COMMA RIGHT HERE, AND SOME MORE TEXT "}'

JSON.Parse(lJson)

the problem is in the jsonHelper.parse -> ._split(Json)

it splits:

Atributte 1:
"code": 123

Atributte 2( Wrong ):
"atributteWithComma":"THIS STRING HAS A COMMA RIGHT HERE"

Atributte 3 ( Wrong ):
" AND SOME MORE TEXT "

it should escape the "," if it is an string JSON attribute

Thanks in advance.

P.D.: No sabia si postear en ingles o español, pero me parecio mas abarcador postear en ingles.
Saludos.

comments

germanmr wrote Jan 23, 2015 at 2:39 PM

Te paso una correccion que hice, el tema esta en la funcion _split()
intente hacer un fork del proyecto pero por alguna razon no puede subir.
Disculpa la demora para subir el codigo, ya lo habia corregido hace tiempo

HIDDEN PROCEDURE _Split(pcJSON)
 *
LOCAL nBlockCount,cObj,lOpenQuote,cChar
nBlockCount = 0  
cObj = pcJSON
lOpenQuote = .F.
lInicioValorAtributo=.F.
lTipoValor=""

FOR j = 1 TO LEN(cObj)
    cChar = SUBSTR(cObj, j, 1)

    DO CASE

        * Hasta aqui llego el valor del atributo String
        CASE lTipoValor="STRING" AND cChar $ '"'
            lTipoValor=""

        * De esta manera sabemos que el tipo del atributo es un NUMBER
        CASE lInicioValorAtributo AND INLIST(cChar,'-','+','1','2','3','4','5','6','7','8','9','0','e','E')
                lTipoValor='NUMBER'
                lInicioValorAtributo=.F.

        * De esta manera sabemos que es el comienzo del atributo STRING
        CASE lInicioValorAtributo AND cChar $ '"'
            lTipoValor="STRING"
            lInicioValorAtributo=.F.

        CASE cChar $ "[{"
            nBlockCount = nBlockCount + 1

        CASE cChar $ "]}"
            nBlockCount = nBLockCount - 1

        CASE cChar $ THIS.stringDelimitator
            IF lOpenQuote
                nBlockCount = nBLockCount - 1
            ELSE
                nBlockCount = nBlockCount + 1 
            ENDIF
            lOpenQuote = !lOpenQuote

        * Esto nos indica que es un inicio de valor de atributo
        * y no estoy adentro de un atributo
        CASE !lInicioValorAtributo AND cChar $ ":" AND lTipoValor<>"STRING"
            lInicioValorAtributo=.T.

        * Tomamos la coma como fin de bloque cuando no esta entre caracteres escapados y no estamos adentro del valor de un atributo STRING
        CASE cChar = "," AND nBlockCount = 0 AND lTipoValor<>"STRING"
               cObj = STUFF(cObj,j,1,CHR(254))
               lTipoValor=""
   ENDCASE
 ENDFOR   

 LOCAL ARRAY aObjects[1]
 LOCAL nCount, i, oResult
 oResult = CREATEOBJECT("Collection")
 nCount = ALINES(aObjects, STRT(cObj,CHR(254),CRLF))
 FOR i = 1 TO nCount
  oResult.add(aObjects[i])
 ENDFOR

 RETURN oResult
 *
ENDPROC

Gracias nuevamente por hacer el framework.

Saludos.