Strange ObjectModelParser behavior - Forum - OpenEdge General - Progress Community

Strange ObjectModelParser behavior

 Forum

Strange ObjectModelParser behavior

This question is answered

I have a path variable fileSource which points to a valid Json file ( verified by JsonLint https://jsonlint.com/, seriously, $2 / month is too much for you? ).

cpStream is utf-8, cpInternal is utf-8 (verified).

/* This fails */

define variable myPArser as ObjectModelParser no-undo.
define variable jc       as JsonCOnstruct     no-undo.

assign
  myParser = new ObjectModelParser ( )
  jc       = myParser:Parse ( fileSource )

  .

/* with message Json Parser Error at offset 1: lexical error: invalid char in json text. (11608) */

 

/* This succeeds */

define variable lc as longchar no-undo.

copy-lob from file fileSource to lc.

assign
  myParser = new ObjectModelParser ( )
  jc       = myParser:Parse ( lc )

  .

Isn't it about time ABL stopped doing stupid stuff? It's been 10 fn years since we started processing json. 

 

Verified Answer
  • ParseFile() is used to load JSON from files.
    Parse() is used to load JSON from variables.
All Replies
  • ParseFile() is used to load JSON from files.
    Parse() is used to load JSON from variables.
  • Version 10 was actually 2003, so maybe it's been closer to 15 years.

  • Hey, maybe it's about time I started wearing my classes while programming.  

  • /*------------------------------------------------------------------------

       File        : OverParser

       Purpose     :

       Syntax      :

       Description :

       Author(s)   :

       Created     : Fri Apr 20 10:01:48 EDT 2018

       Notes       : Just for kicks

     ----------------------------------------------------------------------*/

    using Progress.Lang.*.

    using Progress.Json.ObjectModel.*.

    block-level on error undo, throw.

    class OverParser inherits ObjectModelParser use-widget-pool:

     /*------------------------------------------------------------------------------

      Purpose:

      Notes:

     ------------------------------------------------------------------------------*/

     define protected variable myParser as ObjectModelParser no-undo.

     method public logical isJsony ( source as character ):

       define variable result as logical no-undo.

       define variable tSource   as character no-undo.

       define variable startChar as character no-undo.

       define variable endChar   as character no-undo.

       define variable wSize     as integer   no-undo.

       assign

         tSource = trim ( source )

         wSize   = length ( tSource, "character":u )

         .

       if wSize gt 0 then do:

         assign

           startChar = substring ( tSource, 1, 1 )

           endChar   = substring ( tSource, wSize, 1 )

           .

         assign

           result = false

           result = ( startChar eq endChar ) when index ( startChar, "~{[":u ) gt 0

           .

       end.

       finally:

         return result.

       end finally.

     end.

     method public JsonConstruct OverParse ( source as longchar ):

       define variable result as JsonCOnstruct no-undo.

       assign

         result = myParser:Parse ( source )

         .

       return result.

     end method /* OverParse */.

     method public JsonConstruct OverParse ( source as memptr ):

       define variable result as JsonCOnstruct no-undo.

       assign

         result = myParser:Parse ( source )

         .

       return result.

     end method /* OverParse */.

     method public JsonConstruct OverParse ( source as handle ):

       define variable result as JsonCOnstruct no-undo.

       assign

         result = myParser:Parse ( source )

         .

       return result.

     end method /* OverParse */.

     method public JsonConstruct OverParse ( source as character ):

       define variable result as JsonConstruct no-undo.

       define variable lc     as longchar      no-undo.

       fix-codepage ( lc ) = "utf-8".

       if isJsony ( source ) then do:

         assign

           result = myParser:Parse ( source )

           .

       end.

       else do:

         assign

           file-info:pathname = source

           .

         if file-info:full-pathname gt "" then do:

           copy-lob from file file-info:full-pathname to lc.

           assign

             result = myParser:Parse ( lc )

             .    

         end.

         else result = ?.      

       end.

       return result.

     end method /* OverParse */.

     constructor public OverParser (  ):

       super ().

       assign

         myParser = new ObjectModelParser ( )

         .    

     end constructor.

    end class /* OverParser */.

  • Out of curiosity. You're inheriting from ObjectModelParser. So your OverParser instance is already an ObjectModelParser Instance. Rather than NEW'ing a second ObjectModelParser

    myParser = new ObjectModelParser ( )

    Why don't you just do

    myParser = THIS-OBJECT .

    Speak to yourself - instead of speaking to a twin.

    Architect of the SmartComponent Library and WinKit

    Consultingwerk Ltd.

  • ... remove a set of parens from the code above.

    Architect of the SmartComponent Library and WinKit

    Consultingwerk Ltd.

  • I should point out that it is possible to do something along the lines of

    def var jsonData as JsonConstruct.

    jsonData = (new ObjectModelParser()):Parse( " [~"data~"] " ).

    Not as pretty but it works.

    I'd be tempted to make the Parse() methods static since it cleans the calling syntax up a bit, and the built-in ObjectModelParser has no context for each Parse*() call.

    I'd also note that things like "null" , 12345 and "hello greg" are valid JSON (though not yet supported by our parser.

  • Mostly because I wasn't paying attention to that part and once it compiled I shoved it out.