This thread looks to be a little on the old side and therefore may no longer be relevant. Please see if there is a newer thread on the subject and ensure you're using the most recent build of any software if your question regards a particular product.
This thread has been locked and is no longer accepting new posts, if you have a question regarding this topic please email us at support@mindscape.co.nz
|
Hi, I didn't find a place where I can ask for features, so I will post them here. Feel free to move this post. * Mulitiply views for the domain model. *T4 templates to customize code generation. * Customizable view of an Entity. * Enhanced Inheritance. Don't take me wrong, I really like LightSpeed! Kind regards, Sörnt |
|
|
Thanks for these suggestions -- we really appreciate your taking the time to write them up. Regarding multiple views, we will be investigating this for a future version when Visual Studio 2010 is more widely established. VS2008 does not really support multiple views; we've heard that VS2010 will have a way of handling this but haven't had chance to research it yet. We know many customers have large models and are keen to see this! In the meantime, we do have some options for focusing in on specific bits of your model: see http://www.mindscape.co.nz/blog/index.php/2009/05/11/navigating-around-models-in-the-lightspeed-designer/, http://www.mindscape.co.nz/blog/index.php/2009/05/26/sub-views-in-the-lightspeed-designer/ and http://www.mindscape.co.nz/blog/index.php/2009/05/27/visualising-eager-load-graphs-in-the-lightspeed-designer/ for info. We don't have support for T4, but the templates for the designer are written in NVelocity, and you can modify them to incorporate your own requirements. See http://www.mindscape.co.nz/blog/index.php/2009/09/16/customising-lightspeed-entity-templates/ for a primer. Does this help or is there something more you're looking for? Regarding customisable views, this is definitely an interesting idea. We will have to have a think about whether we can implement it without over-cluttering the interface, but we agree it would be a useful feature. Regarding inheritance, we are working on an implementation of class table inheritance, in which an inheritance hierarchy is spread out across multiple tables (table per class, with each table containing only the columns introduced by that class). This is included in current nightly builds and you are welcome to play with it though please don't be surprised if you find bugs -- it's still in development! However, we don't plan to support arbitrary column mappings across multiple tables: we know this can be useful with some legacy databases, but it's too much of an edge case for us to tackle right now. Does class table inheritance answer your request, or are you looking for something more configurable? If so, what's your use case? Again, many thanks for the suggestions! |
|
|
I second Sörnt's suggestions re: * Mulitiply views for the domain model - this is a real pain point for us as navigating around larger model is really cumbersome and slow (did anyone notice slow scrolling with larger model?), as the designer stands at the moment, the automatic arrangement and filter-based view doesn't provide a smooth user experience. * T4 templates to customize code generation - at the moment, we are manually creating a whole bunch of repetitive supporting classes and infrastructure code, which is real tiresome and error-prone. I'll be keen to see a cleaner code generation strategy. |
|
|
Thanks as always for the feedback. However, can you expand on what T4 gives you that template customisation with NVelocity doesn't? (This isn't an attempt to bat away the request: I just want to understand the use case so that we know what you're asking us to support.) |
|
|
We use LightSpeed purely for the data access layer. We have our own repository layer, service layer, and data transfer objects. Most of customizations are done through partial classes and extensions. With LightSpeed, we see it as a great modeling tool, and it would be quite good to use it to generate those supporting code based on our design/convention. We are not completely comfortable about changing the included templates for the future compatibility reason. However, we are open to other non-intrusive ways to extend the model and code generation on a per project basis. Does this help with kicking off a brainstorm? :) |
|
|
Hi Ivan, I wasn't aware that there is a documented way to do code gen based on the model. Thank you for the hint. I will have a look at NVelocity and see what it can do for me. The T4 template was just a suggestion. That template technique is widely used with VS. Kind regards, |
|
|
* So hopfully VS2010 does provide support for multiply views. If not you need to think about a plan B. Maybe a provide the multiply view support within that tab you have allready (some kind of sub-tabs). * I don't want replace the default template. I want to be able to execute additional templates (in configurable way). * I guess it will not be possible to display all infos at once without "overloading" the user interface. But that is the users problem. If I opt in all possible extra infos for an entity, than I have to deal with the presentation. It's OK since It is my choice what is displayed. * Class table inheritance sounds to be exactly what I was looking for. Kind regards, Sörnt |
|
|
Righty ho, T4 support will be in the 13 April nightly build, available from about 1500 GMT. Here's a sample (generating a text file rather than code, but I want to keep it simple): -------------------------------------------------- <#@ template inherits="Microsoft.VisualStudio.TextTemplating.VSHost.ModelingTextTransformation" #> ----------------------------------------------------- The key incantation is the LightSpeedModel directive and its 'processor' attribute. This hooks up the T4 template to the LightSpeed directive processor and through that to the file named in the 'requires' clause. You will also need to reference the two assemblies noted. These assemblies should NOT be redistributed with your own code and should therefore not be referenced from the project that hosts the T4 template: use the Reference Paths project option instead, or specify the path to these DLLs in the @assembly directive. As always, please report any issues. |
|
|
THANK YOU! THANK YOU! THANK YOU! :D |
|
|
Super cool :-) |
|
|
Hi, I needed to fully qualify the assembly file name within VS2010 in order to get the templates to work. I first specifiy them via the Project properties-> "Reference Paths" and added there the folder "C:\Program Files (x86)\Mindscape\LightSpeed\Tools\Designer\" but I got the error message: Compiling transformation: Metadata file 'Mindscape.LightSpeed.Generator.Model.dll' could not be found D:\Projekte\VS2010\dummys\biSLApp\biSLApp\biSLApp.Web\DomainModel\Template1.tt As soon as I added the full qualified file name to the assemply parama section it was working.
|
|
|
I would like to create the MetaDataClass for the Entites. To create the DataAnnotations for an Entity , I need access to the EntityProperty.Validations. Is it possible to make that property public? Kind regards, Sörnt |
|
|
Usefully would also be access to EntityProperty.Property. Kind regards, |
|
|
Thanks for the info about needing to path-qualify the DLL names. We haven't seen this issue and we will try to reproduce it, but I fear it is most likely a T4 issue and outside our control. The EntityProperty.Validations collection is public and should be visible to your code. It is of type LinkedElementCollection<Validation> and all the validation classes are public too. Not sure what you mean by EntityProperty.Property. We don't have a property of that name. Can you clarify what you're looking for here? Thanks! |
|
|
Hi Ivan,
I have that script: <#@ template inherits="Microsoft.VisualStudio.TextTemplating.VSHost.ModelingTextTransformation" language="C#" debug="true" #>
Which gives me that output: Object-Model: To get an idea which objects are available, I used Reflector for this assembly: Mindscape.LightSpeed.Generator.Integration.Dsl.
public virtual LinkedElementCollection<EntityProperty> EntityProperties { get; }
|
|
|
Just found the Defintion: That EntityProperty type has got a that Property: Property IPropertyReference.Property { get; } (private) |
|
|
You should just be able to write prop.ValidateEmail, prop.ValidateFormat, etc. -- again these are all public properties (on the Property base class). But note that these are calculated from the Validations collection -- basically they are a way for us to present a friendly UI in the properties grid rather than the user having to work directly with the Validations collection. Programmatically it's better to work with the Validations collection because it saves you having to do parsing on e.g. the Length or Range strings -- the various Validation-derived types have the data in a much more structured way. To see the Validation-derived types, go into the LightSpeed Model Explorer, right-click a property in the tree, and look at the list of Add New Xxx Validation options; to see the attributes of each Validation-derived type, create a validation of that type, right-click it in the tree view and choose Properties. |
|
|
You shouldn't normally need to work with IPropertyReference -- it's an abstraction primarily used by the database synchronisation subsystem. For an EntityProperty, IPropertyReference.Property just returns this, i.e. the EntityProperty itself, and IPropertyReference.Validations returns the public Validations collection. (Yes, we will try to document a stable, formal API for T4 users at some point, so that you can know which bits you should use and which bits you can / should ignore -- unfortunately this is one of those areas where documentation lags development because we did not originally anticipate releasing T4 support and so the documentation has a lot of catching up to do!) |
|
|
No wories about the documentation. Be sure, I will ask for the bits I need :-) Sörnt |
|
|
Hi Ivan, At the Entity type there are these properties defined: Entity.OptimisticConcurrencyCheckingDomainPropertyId (GUID) Can you please give me a hint of the purpose for Entity.OptimisticConcurrencyCheckingDomainPropertyId? I guess I need to evaluate Entity.OptimisticConcurrencyCheckingDomainPropertyId somehow when Entity.OptimisticConcurrencyChecking == true. Regards, |
|
|
All XxxDomainPropertyId fields are handles for the Visual Studio property storage manager (it's all tied in with undo-redo support) -- the OptimisticConcurrencyCheckingDomainPropertyId basically identifies the "slot" where the OptimisticConcurrencyChecking property value is stored. A bit like the XxxProperty fields for WPF or Silverlight dependency properties. You should never need to use the XxxDomainPropertyId properties in a template. |
|
|
Thank you for the clarification. I am in the progress to create a more codegen streamlined model from the LightSpeed provided model. So for my current template: <#@ template inherits="Microsoft.VisualStudio.TextTemplating.VSHost.ModelingTextTransformation" language="C#" hostspecific="true" debug="true"#> I get that output: // Last created at 09.05.2010 18:52:16 |
|
|
Hi Ivan, I found the "ComparisonValidation" but I didn't find where it is used within properties of an entity. So far I was able to transform all the validations to the DataAnnotation Attributes:
My Script: <#@ template inherits="Microsoft.VisualStudio.TextTemplating.VSHost.ModelingTextTransformation" language="C#" hostspecific="true" debug="true"#>
the output: // Last created at 12.05.2010 07:14:31
|
|
|
A ComparisonValidation compares the property against a given value -- for example, Age must be greater than or equal to 0, Height must be less than 250cm, etc. It maps to a LightSpeed ValidateComparisonAttribute. |
|
|
I am at the Entity object and iterating over the ValueObjectProperties list.
|
|
|
This is an artefact of the weird way Visual Studio represents associations. Entity.ValueObjects gets the set of ValueObject objects to which the Entity has links, not the links themselves (and the name is an attribute of the link, not the ValueObject, because there could be multiple properties of the same ValueObject type). To get the links themselves, you need to write: EntityHasValueObjectProperties.GetLinksToValueObjectProperties(someEntity); This returns a collection of EntityHasValueObjectProperties objects, which represent the links, and from which you can get the Name property as required. Note this is a static method on the EntityHasValueObjectProperties class, not an instance method on the Entity class. By the way, the same applies to anything that's represented in the designer as a connector, e.g. if you want the properties of OneToManyAssociations, you will need to write OneToManyAssociation.GetLinksToOneToManyAssociations(entity), if you want to get the discriminator of an inheritance arrow you will need to write BaseToDerivedAssociation.GetLinkToBaseClass(entity), etc. |
|
|
Hi Ivan, I need some help with ThroughAssociation that uses a Auto Through Entity. EntityA and EntityB connected via ThroughAssociation that uses a Auto Through Entity = "AutoEntity". At EntityA I see the ThroughAssociationTargets pointing to EntityB. At EntityB I see the ThroughAssociationSources pointing to EntitA. Another thing: How do the auto generated DTO's respect the aggregate settings? Regards, Sörnt |
|
|
Auto Through Entity is a property of a ThroughAssociation arrow, so we're in the same scenario as we were with properties of a OneToManyAssociation arrow: you need to call one of the static %arrow_class%.GetLinksTo* methods: in this case, ThroughAssociation.GetLinksToThroughAssociationTargets(Entity). This returns the collection of ThroughAssociation arrows, each of which has a HasAutoThroughEntity and an AutoThroughEntity (name) property. DTOs don't know about aggregate settings: they are dumb data objects. Aggregates refer to the materialisation of entities from the database. These entities may then be copied into DTOs or updated from DTOs, but the aggregate no longer plays a part at that stage. |
|
|
Thank you for the "ThroughAssociation" hint. I searched for something like "ManyToMany". Regarding to the DTOs: If I load an entity with an aggregate (only some fields) and use the copy constructor of the DTOs will the not loaded fields (not part of that aggregate) be loaded lazy? I get the feeling that the DTO's a bit to dumb. There should be DTO types foreach defined aggregate. |
|
|
Regarding to the Auto Through Entity. I didn't see any property for aggregates (source/target). Are auto aggregates loaded allways lazy or eager? Regarding to OneToOne association. How do the settings for "Eager Load Source/Target" and "Source/Target Aggregates" work together. For example: Eager Load Source = true When loading the target entity with an aggregate of "Agg3". So far my template generates all Entities, Value Objects and ThroughAssociations "RIA conform". My goal for the first set of templates is to create one template for the object model and another for the DomainService so that I finally have queryable and updatable Ria Service. The for the second set I would like to extend the object/domain service template to take the aggregate definition into account (for each aggregate a specific type). |
|
|
Auto Through Entities provide *minimal* configuration. If you need to configure properties explicitly on the through entity or the aggregates, then you should use an explicit through entity. The aggregates for an auto through entity are currently lazy-loaded, but if it's important to you, I'd configure it explicitly rather than relying on the current behaviour. (I really mean this. It's quite possible that we'll change auto through entities to eager-load their associations in the future.) Re association loading in the presence of both Eager Load and Aggregates: you are correct. If Eager Load is true, then the association will always be eager loaded, and the aggregates are therefore irrelevant. |
|
|
I have got a problem with ModelDataType of type "Decimal". For "Decimal" it gives me back "Double" while the correspondent LS entity attribute is of type Decimal.
|
|
|
GetAttributeSafeClrType returns a CLR type which can represent values of the specified ModelDataType and can be stored in an attribute. (Hence the "AttributeSafe" part of the name.) Decimals cannot be stored in attributes (see compiler error CS0182 in MSDN). Therefore GetAttributeSafeClrType returns double instead, as double is the only type that can store the Decimal value range and can be stored in an attribute. |
|
|
Hi Ivan, that is how the LS Object looks like: [Serializable] ...
And to answer my question. Just call "GetClrType()" intead of "GetAttributeSafeClrType()" |
|
|
just in case anyone else is following this thread - here's the first cut at the t4 script we're using to generate the dtos. in our case we want to generate the dtos in our wcf contracts assembly - not in the model assembly. so i've effectively replicated the LS-generated dto classes and extension methods (though i've taken a few shortcuts and missed some use cases such as composite PK, just because i don't need them) GeneratedDtos.tt (in our WCF contracts project): <#@ template inherits="Microsoft.VisualStudio.TextTemplating.VSHost.ModelingTextTransformation" #>
GeneratedDtoExtensions.tt (in our Model project): <#@ template inherits="Microsoft.VisualStudio.TextTemplating.VSHost.ModelingTextTransformation" #>
justin |
|