xmerl namespace handling

Robert Raschke rtrlists@REDACTED
Mon Aug 3 12:42:06 CEST 2009


Hi,

in xmerl_xsd.erl there's code that checks namespaces while validating where
it looks like the comments and the code disagree (in R13B01, lines
4809-4843):

%% mk_EII_QName/2
%% makes a name with qualified info out of an Element Information Item
%% A) If name is qualified get namespace matching prefix.
%% B) If not qualified search parents for a namespace:
%% 1) use default namespace if defined, else.
%% 2) if a parent is qualified use that namespace or
%% 3) no namespace is applied
mk_EII_QName(Name,#xmlElement{name=Me,namespace=NS,parents=P},S)
  when is_list(Name) ->
    mk_EII_QName(list_to_atom(Name),
         #xmlElement{name=Me,namespace=NS,parents=P},S);
mk_EII_QName(Name,#xmlElement{name=Me,namespace=NS,parents=P},S) ->
    Scope = S#xsd_state.scope,
    NameStr = atom_to_list(Name),
    case string:tokens(NameStr,":") of
    ["xmlns",PrefixDef] -> %% special case
        {'xmlns',Scope,namespace(PrefixDef,NS,[])};
    [Prefix,LocalName] -> %% A
        {list_to_atom(LocalName),Scope,namespace(Prefix,NS,[])};
    [_LocalName] -> %% B
        {Name,Scope,mk_EII_namespace([{Me,0}|P],NS,S)}
    end.
mk_EII_namespace([],#xmlNamespace{default=DefaultNS},_S) ->
    DefaultNS;
%%mk_EII_namespace([{PName,_}|GrandPs],NS=#xmlNamespace{default=[]},S) ->
mk_EII_namespace([{PName,_}|GrandPs],NS,S) ->
    NameStr = atom_to_list(PName),
    case string:tokens(NameStr,":") of
    [Prefix,_LocalName] ->
        namespace(Prefix,NS,[]);
    [_LocalName] ->
        mk_EII_namespace(GrandPs,NS,S)
    end;
mk_EII_namespace(_,NS,_S) ->
    NS#xmlNamespace.default.

In the case B (unqualified name), it looks like the code will apply a
parent's qualified namespace, even if the node with the unqualified name has
a default namespace defined (contradicting B.1).

The upshot of this is that it is not possible to use xmerl_xsd:validate/2 to
validate unqualified internal elements that are part of a larger (qualified)
tree. The commented out line suggests to me that there was an attempt to
rectify this, but I'm not sure.

I don't really know if this is a bug or not. It looks intentional.

Myself, I would think that mk_Ell_namespace/3 should have a first clause
along the lines of

mk_EII_namespace(_,#xmlNamespace{default=DefaultNS},_S) when
is_list(DefaultNS), length(DefaultNS)>0 ->
    DefaultNS;

to agree with the comment.

But is the comment correct in terms of XML/XSD/namespace handling?

Robby


More information about the erlang-questions mailing list