The OnTopic assembly represents the core domain layer of the OnTopic library. It includes the primary entity (Topic), abstractions (e.g., ITopicRepository), and associated classes (e.g., KeyedTopicCollection<>).
Topic: This is the core entity in OnTopic, and models all attributes, relationships, and references associated with a topic record.
Note: Any class that derives from
Topicwill automatically be loaded byTopicFactory.Create(), thus allowing content type specific business logic to be added to anyTopicinstance. This is especially useful for customAttributeDescriptortypes used to extend the OnTopic Editor.
Out of the box, the OnTopic library contains two specially derived topics for supporting core infrastructure requirements:
ContentTypeDescriptor: AContentTypeDescriptoris composed of multipleAttributeDescriptorinstances which describe the schema of a content type. This is primarily used by the OnTopic Editor.AttributeDescriptor: AnAttributeDescriptordescribes a single attribute on aContentTypeDescriptor. This includes theAttributeType,Description,DisplayGroup, and whether or not it's required (IsRequired).
Note: In addition, the OnTopic Editor can be extended through types derived from
AttributeDescriptor, such as theBooleanAttributeDescriptor. Plugins may optionally implement these in order to overwrite theEditorTypeorModelTypeof the attribute, and thus determine where and how their values will be stored.
ITopicRepository: Defines an interface for data access, withLoad(),Save(),Delete(),Move(),Refresh(), andRollback()methods.ITopicMappingService: Defines an interface for a service that can convert aTopicinto any arbitrary data transfer object based on predetermined conventions—or vice versa (via theIReverseTopicMappingService).IHierarchicalTopicMappingService<T>: Defines an interface for applying theITopicMappingServiceto hierarchical data with constraints on depth. Used primarily for mapping data for navigation components, such as theNavigationTopicViewComponentBase<T>.ITypeLookupService: Defines an interface that can identifyTypeobjects based on aLookup(typeName)query. Used by e.g.ITopicMappingServiceto find correspondingTopicViewModelclasses to map to.
TopicMappingService: A default implementation of theITopicMappingService, with built-in conventions that should address the majority of mapping requirements. This also includes a number of attributes for annotating view models with hints that theTopicMappingServicecan use to fine-tune the mapping process.CachedTopicMappingService: Provides an optional caching layer for decorating theTopicMappingService—or anyITopicMappingServiceimplementation.
ReverseTopicMappingService: A default implementation of theIReverseTopicMappingService, honoring similar conventions and attribute hints as theTopicMappingService. Useful for merging binding models with topics as part of form processing.HierarchicalTopicMappingService<T>: A default implementation of theIHierarchicalTopicMappingService<T>, which accepts anITopicMappingServicefor mapping each individual node in the hierarchy.CachedHierarchicalTopicMappingService<T>: Provides an optional caching layer for theHierarchicalTopicMappingService—or anyIHierarchicalTopicMappingServiceimplementation.
StaticTypeLookupService: A basic implementation of theITypeLookupServiceinterface that allows types to be explicitly registered; useful when a small number of well-known types are expected.DynamicTypeLookupService: A reflection-based implementation of theITypeLookupServiceinterface that looks up types from all loaded assemblies based on aFunc<Type, bool>delegate passed to the constructor.DynamicTopicLookupService: A version ofDynamicTypeLookupServicethat returns all classes that derive fromTopic; this is the default implementation forTopicFactory.DynamicTopicViewModeLookupService: A version ofDynamicTypeLookupServicethat returns all classes that end withViewModel; this is useful for theTopicMappingService.DynamicTopicBindingModelLookupService: A version ofDynamicTypeLookupServicethat returns all classes that implementITopicBindingModel; this is useful for theReverseTopicMappingService.
Querying: TheTopicExtensionsclass exposes optional extension methods for querying a topic (and its descendants) based on attribute values. This includes the usefulTopic.FindAll(Func<Topic, bool>)method for querying an entire topic graph and returning topics validated by a predicate. There are also specialty extensions for queryingIEnumerable<Topic>.Attributes: TheAttributeCollectionExtensionsclass exposes optional extension methods for strongly typed access to theAttributeCollection. This includes e.g.,GetBooleanValue()andSetBooleanValue(), which takes care of the conversion to and from the underlyingstringvalue type.
The OnTopic assembly contains a number of generic, keyed, and/or read-only collections for working with topics. These include:
| Read-Write | Read-Only | |
|---|---|---|
| Unkeyed | TopicCollection |
ReadOnlyTopicCollection |
| Keyed | KeyedTopicCollection |
ReadOnlyKeyedTopicCollection |
| Keyed (Generic) | KeyedTopicCollection<T> |
ReadOnlyKeyedTopicCollection |
The OnTopic.Collections.Specialized namespace includes a number of collections that are used by the OnTopic library, but won't generally be used directly by implementors, except as exposed by the core library. These include:
TrackedRecordCollection{TItem, TValue, TAttribute}: AKeyedCollection<TItem, TValue>ofTrackedRecord<TValue>instances which tracks theIsDirtystatus andDeletedItems, while also enforcing business logic against corresponding properties on the associatedTopic.AttributeCollection: ATrackedRecordCollectionofAttributeRecordinstances keyed byAttributeRecord.Key; exposed byTopic.Attributes.TopicReferenceCollection: ATrackedRecordCollectionofTopicReferenceRecordinstances keyed byTopicReference.Key; exposed byTopic.References.
TopicMultiMap: Provides a multi-map (or collection-of-collections) for topics organized by a collection key.ReadOnlyTopicMultiMap: A read-only interface to theTopicMultiMap, thus allowing simple enumeration of the collection withouthout exposing any write access.TopicRelationshipMultiMap: ATopicMultiMapofKeyValuesPairinstances keyed byKeyValuesPair.Key; exposed byTopic.Relationships.
The following are intended to provide support for the Editor domain objects, ContentTypeDescriptor and AttributeDescriptor.
ContentTypeDescriptorCollection: AKeyedCollectionofContentTypeDescriptorobjects keyed byIdandKey.AttributeDescriptorCollection: AKeyedCollectionofAttributeDescriptorobjects keyed byIdandKey.
The core Topic library has been designed to be view model agnostic; i.e., view models should be defined for the specific presentation framework (e.g., ASP.NET Core) and customer. That said, to facilitate reusability of features that work with view models, several interfaces are defined which can be applied as appropriate. These include:
ICoreTopicViewModel: Includes core propertiesKeyandContentTypenecessary for everyTopic.ITopicViewModel: Includes universal properties such asUniqueKey,WebPath,Id, andTitle.
IHierarchicalTopicViewModel<T>: Includes a genericChildrenproperty necessary to model a hierarchical graph.INavigableTopicViewModel: Includes core propertiesTitle,ShortTitle, andWebPath, necessary treating a topic as a navigable link.INavigationTopicViewModel<T>: IncludesIHierarchicalTopicViewModel<T>and theIsSelected()view logic method, for use with navigation menus.
ITopicBindingModel: Includes the bare minimum properties—namelyKeyandContentType—needed to support a binding model that will be consumed by theIReverseTopicMappingService.IAssociatedTopicBindingModel: Includes the bare minimum properties—namelyUniqueKey—needed to associate another topic on a binding model that will be consumed by theIReverseTopicMappingService.
In addition to these interfaces, a set of concrete implementations of view models corresponding to the default schemas for the out-of-the-box content types can be found in the OnTopic.ViewModels package.