so

XML Resolver refactor refactor

Volume 8, Issue 4; 27 Jan 2024

Working on the C# implementation of the XML Resolver was instructive. It instructed me that the new design was kind of a mess and the Java implementation of that design was also…bad. So I’ve fixed that.

As of sometime this afternoon, all of the unit tests for both the Java and C# versions of XML Resolver passed. That’s a big milestone; it paves the way for official “6.0.0” releases.

I’m working my way through the JavaDoc and then I’ll have to go through whatever the C# version of that is called. Then I have to turn my attention to the user documentation.

It’s awkward because a lot of things are the same, but a lot of things are different. What I’ll probably end up doing is moving the current documentation under a /legacy/ URI and making the main pages about the new version.

The new version is a substantial improvement and I want to encourage folks to migrate. At the same time, it’s probably a bit of infrastructure in your project and I’ve done that annoying thing where I’ve changed the API, so I know it’s not something everyone will want to do immediately.

The biggest user-visible change, I think, is that a bunch of different objects that implemented different APIs have all gone away. The Resolver, StAXResolver, and XercesResolver objects are no more. Most of the APIs were implemented on Resolver, but there were several different resolver objects because the various systems have incompatible APIs.

Instead, now there’s an XMLResolver object that has methods that return instances of the different APIs. That feels a lot cleaner. You can also use the XMLResolver object to interrogate the catalog or resolve resources directly, if that’s a thing you want to do.

The design is more-or-less the same now in both Java and C#. I’ve worked harder to make the C# API more C#-like (using the naming conventions expected, for example, and treating nullable with care).

Where they diverge, I think it’s because there are fundamental differences in how the Java APIs and the C# API work. Aside from the thing that’s absolutely fucking broken on C#, those differences are a matter of design. I’d have made different choices, but no one asked me.

One slightly awkward thing on C# is that my object is called XmlResolver and the system API for setting up a resolver on C# is called System.Xml.XmlResolver. That means there’s a name clash. I’ve noodled around with various ways to fix that, but I don’t really like any of them.

This means that in C# you’re going to be left doing this:

XmlReaderSettings settings = new XmlReaderSettings();
settings.XmlResolver = XmlResolver.XmlResolver.GetXmlResolver();

Which is, on the one hand, kind of ugly. But on the other hand, that’s pretty much exactly the one line of code that you need, so I’m going to see if that’s ok.

Also up next: “integration testing”. That is, will it work on SaxonJ and SaxonCS? It probably won’t work in Saxon 12.x because of the API changes, so I’ll be focusing on V.next, the-thing-that-will-eventually-be-13.0.

#C# #Java #XML #XML Resolver