Class XFactory
Factory for generating objects from XML elements using registered generator functions.
public class XFactory
- Inheritance
-
XFactory
- Inherited Members
- Extension Methods
Remarks
Each XFactory instance owns its own Generators registry. A process-wide Default singleton serves the common case (single shared factory across the simulation pipeline); other instances can be created for test isolation or parallel pipelines that need disjoint registries.
Types that participate in XML round-trip expose a
public static void Reg(XFactory factory = null) method that adds
themselves (and chains Reg(factory) on dependents) to the given
factory's Generators. Boot roots (e.g.
LocalProjectService.Reg()) call the top-level Reg() once at
startup with the default factory.
The static Gen<T> / GenByChild<T> /
GenByFile<T> entry points always read from
Default. Callers that need to deserialize from a custom
factory's registry must look up the delegate directly, as the entry points
do: factory.TypedGenerators[(xname, typeof(T))] first, then
factory.Generators[xname].
The element's name, not T, picks the generator, and the generator
decides the type of the object it builds — unless a generator is registered
for the element name and the type asked for (TypedGenerators),
which is taken before the one registered for the name alone, by every entry
point (GenListSkippingUnloadable<T>(IEnumerable<XElement>, string, IProgress<IMessage>, bool, object[]) asks for its T). When that
object is not a T, the static entry points that read one object (Gen,
GenByChild and GenByFile) return null — the
GenFileRefSource family a FileRefSource<T> whose
data is null — and report an
XFactory-Load--TypeMismatch error on their progress, naming
the element, the type it is read as and T;
GenListSkippingUnloadable<T>(IEnumerable<XElement>, string, IProgress<IMessage>, bool, object[]) skips such an element with a
warning. An element name that is not registered throws
KeyNotFoundException from the entry points that read one
object.
Properties
Default
Process-wide default factory used by the static Gen<T>
family. Reg-style methods register here when called with
no explicit factory argument.
public static XFactory Default { get; }
Property Value
Generators
XML-name → generator-function map for this factory instance. Populated
by each type's Reg(this) call. Concurrent so that parallel
Reg calls (e.g. independent test classes each booting the
registration graph) can TryAdd without corrupting the map.
public ConcurrentDictionary<string, XFactory.XGeneratorDelegate> Generators { get; }
Property Value
TypedGenerators
(XML name, type asked for) → generator-function map for this factory instance. A generator registered for the element name and the type asked for is taken before the one registered for the name alone in Generators, and only for that type: the type asked for must equal the type registered (not a base class of it, not an interface it implements). A type's legacy reading registers here — the element whose name is read as another type today is still read as the type a caller of an earlier version asks for. Concurrent for the same reason as Generators.
public ConcurrentDictionary<(string XName, Type Type), XFactory.XGeneratorDelegate> TypedGenerators { get; }
Property Value
Methods
GenByChild<T>(XElement, string, IProgress<IMessage>, bool, object[])
Generates an object of type T from the first child element (discards relative file path).
public static T GenByChild<T>(XElement src, string baseDirectory, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
Returns
- T
Type Parameters
T
Remarks
Returns null and reports on progress in the cases
Gen<T>(XElement, string, out string, IProgress<IMessage>, bool, object[]) lists.
GenByChild<T>(XElement, string, out string, IProgress<IMessage>, bool, object[])
Generates an object of type T from the first child element of the provided XML element.
public static T GenByChild<T>(XElement src, string baseDirectory, out string relFile, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
srcXElementbaseDirectorystringrelFilestringprogressIProgress<IMessage>enableRebaseboolresobject[]
Returns
- T
Type Parameters
T
Remarks
Returns null and reports on progress in the cases
Gen<T>(XElement, string, out string, IProgress<IMessage>, bool, object[]) lists.
GenByFile<T>(string, string, IProgress<IMessage>, bool, object[])
Generates an object of type T from an XML file.
public static T GenByFile<T>(string baseDirectory, string relFile, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
Returns
- T
Type Parameters
T
Remarks
The file's root element picks the generator, so the root element, not
T, decides the type of the object read (a
generator registered for the root element's name and
T itself, TypedGenerators, first). A file
that cannot be read, or whose root element is read as a type that is
not a T, yields null and an error on
progress (XmlSource-Read–Failed or
XFactory-Load–TypeMismatch); see
Gen<T>(XElement, string, out string, IProgress<IMessage>, bool, object[]).
GenFileRefSourceByChild<T>(XElement, string, IProgress<IMessage>, bool, object[])
Generates a FileRefSource<T> from the first child element.
public static FileRefSource<T> GenFileRefSourceByChild<T>(XElement src, string baseDirectory, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class, IMakeXmlSource
Parameters
Returns
Type Parameters
T
Remarks
The data is null in the cases
Gen<T>(XElement, string, out string, IProgress<IMessage>, bool, object[]) lists.
GenFileRefSourceByFile<T>(string, string, IProgress<IMessage>, bool, object[])
Generates a FileRefSource<T> from an XML file.
public static FileRefSource<T> GenFileRefSourceByFile<T>(string baseDirectory, string relFile, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class, IMakeXmlSource
Parameters
Returns
Type Parameters
T
Remarks
The data is null in the cases
GenByFile<T>(string, string, IProgress<IMessage>, bool, object[]) lists.
GenFileRefSource<T>(XElement, string, IProgress<IMessage>, bool, object[])
Generates a FileRefSource<T> from an XML element.
public static FileRefSource<T> GenFileRefSource<T>(XElement src, string baseDirectory, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class, IMakeXmlSource
Parameters
Returns
Type Parameters
T
Remarks
The data is null in the cases
Gen<T>(XElement, string, out string, IProgress<IMessage>, bool, object[]) lists.
GenListSkippingUnloadable<T>(IEnumerable<XElement>, string, IProgress<IMessage>, bool, object[])
Deserializes each element of elements into a
T, skipping — instead of throwing on — any element
whose XName is not registered (e.g. a renamed or removed component),
whose generator throws, or whose generator builds an object that is not
a T. Each skipped element is reported to
progress as a Warning
(XFactory-Load–SkippedUnloadable, naming the element,
T and the reason). An element that yields no
object — an <XmlSource> whose file cannot be read, reported
as XmlSource-Read–Failed — is left out without a warning. A
generator registered for the element name and T
(TypedGenerators) is taken before the one registered for
the name alone, as by Gen<T>.
Use when a partially-loadable list (such as a saved pipeline whose schema
has drifted while a feature is in development) is preferable to aborting
the whole load.
public static List<T> GenListSkippingUnloadable<T>(IEnumerable<XElement> elements, string baseDirectory, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
elementsIEnumerable<XElement>baseDirectorystringprogressIProgress<IMessage>enableRebaseboolresobject[]
Returns
- List<T>
Type Parameters
T
Gen<T>(XElement, string, IProgress<IMessage>, bool, object[])
Generates an object of type T from an XML element (discards relative file path).
public static T Gen<T>(XElement src, string baseDirectory, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
Returns
- T
Type Parameters
T
Remarks
Returns null and reports on progress in the cases
Gen<T>(XElement, string, out string, IProgress<IMessage>, bool, object[]) lists.
Gen<T>(XElement, string, out string, IProgress<IMessage>, bool, object[])
Generates an object of type T from an XML element using Default.
public static T Gen<T>(XElement src, string baseDirectory, out string relFile, IProgress<IMessage> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
srcXElementbaseDirectorystringrelFilestringprogressIProgress<IMessage>enableRebaseboolresobject[]
Returns
- T
Type Parameters
T
Remarks
An <XmlSource> wrapper whose file cannot be read yields
null — never an exception — and an XmlSource-Read--Failed
error on progress naming the resolved path;
relFile still receives the reference so the holder
can keep it (and write it back on save through
MakeXmlSourceToFileRef(IMakeXmlSource, string, string, bool)).
The element's name — for an <XmlSource> wrapper, the name
of the root element of the file it refers to — picks the generator, so
it decides the type of the object read, not T;
a generator registered for the element name and
T itself (TypedGenerators) is taken
before the one registered for the name alone.
When that object is not a T, the result is
null and an XFactory-Load--TypeMismatch error on
progress names the element, the type it is read as
and T; read such an element as that type, a base
class of it or an interface it implements. A generator that builds
nothing yields null without a report, and a null
progress takes no report. An element name that is
not registered throws KeyNotFoundException.