Start_Element and End_Element are not called

Viewed 61

Trying for the first time xmlada, I have a hard time to get the SAX module working. This is the XML I'm trying to parse:

<?xml version="1.0" encoding="UTF-8"?>
<project>
    <name>Test project</name>
</project>

And this is the code I used:

xml-project_loader.ads

with Ada.Strings.Unbounded;
with Sax.Attributes;
with Sax.Readers;
with Unicode.CES;

package XML.Project_Loader is
     
   type Reader is new Sax.Readers.Sax_Reader with null record;
   
   procedure Load (Filepath : String);

   procedure Start_Element
     (Handler       : in out Reader;
      Namespace_URI : Unicode.CES.Byte_Sequence := "";
      Local_Name    : Unicode.CES.Byte_Sequence := "";
      Qname         : Unicode.CES.Byte_Sequence := "";
      Atts          : Sax.Attributes.Attributes'Class);

   procedure End_Element
     (Handler       : in out Reader;
      Namespace_URI : Unicode.CES.Byte_Sequence := "";
      Local_Name    : Unicode.CES.Byte_Sequence := "";
      Qname         : Unicode.CES.Byte_Sequence := "");

   procedure Characters
     (Handler : in out Reader;
      Ch      : Unicode.CES.Byte_Sequence);
   
private
   Project_Reader : Reader;
   
end XML.Project_Loader;

xml-project_loader.adb

with Ada.Text_IO;
with Input_Sources.File;

package body XML.Project_Loader is

   procedure Load (Filepath : String)
   is
      Input  : Input_Sources.File.File_Input;
   begin
      Input_Sources.File.Open (Filepath, Input);
      Project_Reader.Parse (Input);
      Input.Close;
   end Load;
   
   procedure Start_Element
     (Handler       : in out Reader;
      Namespace_URI : Unicode.CES.Byte_Sequence := "";
      Local_Name    : Unicode.CES.Byte_Sequence := "";
      Qname         : Unicode.CES.Byte_Sequence := "";
      Atts          : Sax.Attributes.Attributes'Class)
   is
   begin
      Ada.Text_IO.Put_Line ("[Start_Element] " & Local_Name);
   end Start_Element;

   procedure End_Element
     (Handler       : in out Reader;
      Namespace_URI : Unicode.CES.Byte_Sequence := "";
      Local_Name    : Unicode.CES.Byte_Sequence := "";
      Qname         : Unicode.CES.Byte_Sequence := "")
   is
   begin
      Ada.Text_IO.Put_Line ("[End_Element] " & Local_Name);
   end End_Element;
   
   procedure Characters
     (Handler : in out Reader;
      Ch      : Unicode.CES.Byte_Sequence)
   is 
   begin
      Ada.Text_IO.Put_Line ("[Characters] " & Ch);
   end Characters;

end XML.Project_Loader;

When I call the procedure XML.Project_Loader.Load, the ouput I get in the console is the following:

[Characters] Test project

The procedures Start_Element and End_Element are not called! I checked with GDB and indeed, they are not called.

Why are the procedures not called?

1 Answers

Because they’re not inherited.

You could say

overriding
procedure Start_Element
  (Handler ....

which would give you a warning about this.

The problem is that there are two sorts of reader declared in the package:

   type Sax_Reader is tagged private;
   type Sax_Reader_Access is access all Sax_Reader'Class;
   --  This package defines two types of XML readers: Reader is the historic
   --  type; Sax_Reader was added later on.
   --  These two readers differ by the type of parameters to their callbacks.
   --  The callbacks of Sax_Reader require less string copying and memory
   --  allocations, so are therefore more efficient. On the other hand, they
   --  do not pass strings directly (for the name of the elements for instance)
   --  but symbols (basically, naturals that can be converted to a string
   --  through calls to Get_Symbol below).
   --  New code is encouraged to extend Sax_Reader rather than Reader.

and, later,

   type Reader is new Sax_Reader with private;
   type Reader_Access is access all Reader'Class;
   --  This is the old type that was provided by this package

Your Reader

   type Reader is new Sax.Readers.Sax_Reader with null record;

expects the new Start_Element and End_Element profiles, but yours are declared with the old parameter profiles.

Related