Entity framework map column only if it exists - sql

I am trying to find a way to only populate a property of my entity class, if the column exists in the query?
When I execute a query using DbSet.SqlQuery and returning the column (which is an alias) populated, everything is fine. But when using the built in functionality such as All(), Find(), ToArray() etc, it expects that column to be in the dataset.
Is there a way (without having to write all of the supporting queries manually) to mark a property in my entity class, as optional.
It is currently marked as a nullable DateTime but the framework still complains it does not exist when using the built in functionality.
Any suggestions would be great!
Cheers

No, because they have to build the SQL query. It doesn't matter if a column is nullable or not, what matters is that when they build the query, if that column does not exist, then the database will likely throw an error complaining that the column does not exist.
The only way around it is to not map it, or to query the schema when mapping and conditionally map the property (though I wouldn't recommend that).

Related

Nullablity of DB generated attributes

I'm working in a Kotlin based project and It force me to deal with any attribute that possibly can hold null. It's nice to find out somewhere nulls are possible while they are not welcome; but I see so much of ?.s and .!!s for attributes that DB generates, e.g. IDs. Maybe I'm abusing that operators?
Is there any convention to mark attribute as not nullable but still have DB generated values here? If I lookup an object It's safe to assume DB generated values are not null anymore. Can VM be made known to this? Maybe by framework or some annotations that language provide?
If your id is generated by the database it is nullable since the JVM/compiler/IDE has no way to know if your entity is already persisted or not.
What you could do though is implement additional methods that are guaranteed to return non-null values by throwing an exception otherwise.

Difference between field and property in OrientDB

I am using OrientDB for the first time. I read that this database operates in a schema less mode.
Although there seems to be some confusion between Field and Property. What is the difference between these two?
The ALTER command does work on fields but fields are shown under the property name in OrientDB studio in query results. Field operations are done through UPDATE. Am I missing something. Please clarify.
The field and property are the same thing in OrientDB.
When you use UPDATE you should not specify the word property or field, the property is just used in ALTER queries, for example ALTER PROPETY, see:
https://orientdb.com/docs/last/SQL-Alter-Property.html
and
https://orientdb.com/docs/last/SQL-Update.html

Using SQL views in Play Framework 2.1.x with Ebean

I have an application which is using Play Framework 2.1.x with Ebean. I would like to use SQL views (PostgreSQL v9.3) instead of actual tables. I tried to switch the "name" property in #Table annotation from actual table name to view name. Retrieving data from view to Ebean model works nice, but when there is a ManyToMany association, it generates an error. The problem is in name convention used by Ebean in order to generate JOIN clauses in SQL query.
For example I have a table named "customers" and a view named "customers_view" and ManyToMany association with table "customertags". In such case, Ebean generates JOIN clause using bridge table "customers_customerstags". But when I change #Table`s name property to "customers_view", associations are messed up. Ebean then generates JOIN with table "customers_view_customerstags" and so on.
I know that this can be fixed by using #JoinTable and #JoinColumn, BUT at first I want to ask some more experienced programmers if there is some other proper way on how to use SQL views in Play/Ebean which I am missing ?
I don't think you are missing anything. In the absence of #JoinTable etc Ebean is using a naming convention based on the table name (which is now your view).
An alternative work around to this issue by creating a view for the intersection table.
I also found a partial solution for this. There is a function in Ebean`s ServerConfig class called setNamingConvention. With this function you can set your own implementation of interface NamingConvention or you can override functions in included classes from Ebean.
I tried to override Ebean`s default implementation called UnderscoreNamingConvention. By overriding of function getM2MJoinTableName I was able to fix errors regarding creation of join table name in SQL query. Unfortunately join columns are still wrong. Join columns are generated from function NamingConvention.getTableName. It is also possible to override this function, but such change would break generation of FROM part of SQL.
Too bad there is no way to override generation of join columns in NamingConvention interface.
It seems there is no escape from this. Reasonable workaround is to use #JoinTable.

nhibernate legacy database extra columns

I have legacy database.
I need to add nhibernate but for several columns in a table.
How can I make nhibernate not to complain that there are no properties for some columns.
In the future it is possible that new columns will be added, but they are not needed in my project.
How can I do this ?
Regards,
Darko
You shouldn't have any problems if those database columns are nullable, or if they have default values. When you think about it, the same is true when you are trying to do an SQL INSERT on a table.
Just map the columns that you need to properties of a class.
If you just need to read, do no map them;
Otherwise, if you need to write in them, you will need to map them (if they are not nullable or do not have default values), in order to provide the values needed by the database.

Best way to map a hidden property in NHibernate (fluent)

I know this question could lead to a subjective answer, but I'd like to get an opinion from someone else.
Some background
Currently I have a class that maps a private string property to a geometry column in a PostgreSQL (PostGIS) database table along with a public string for WKT. The WKT is used by PostGIS to automatically update the geometry column, using a trigger. As I don't want to include any spatial references in my domain model, all querying is done using WKT strings and a custom spatial criterion, which wraps the WKT in a spatial PostGIS function and queries the private geometry property column reference. All of this works as expected.
The question
Since I need the column reference, I also need the property in my domainmodel, for NHibernate to map to, so I was wondering, what the best solution would be, for NHibernate to never select this property.
My current solution looks as follows with Fluent NHibernate:
Map(Reveal.Member<LocationReference>("Geometry"), "geometry")
.Generated.Always()
.ReadOnly()
.LazyLoad();
This does the trick, and when I select the entity, I won't get the property, unless I manually load it (which isn't possible through the lambda extensions). Unfortunately I would still be able to do a Criteria or HQL query for the property.
So are there any ways for me to do anything that prevents NHibernate from being able to do ever include the column in a select? Or is the above solution the only way to at least ignore the column when selecting with Query<> or QueryOver<>?
Well, I ended up removing the mapped property, because, even though it was lazy, NHibernate would sometimes load it anyway. What I did was actually a bit of a hack. I needed the alias for a property from the same class, so I used the mapping from another property and split the SqlString on '.', to get the correct alias.
All of this makes perfect sense to me, and the "workaround" is not nice, but I don't see any other way of doing it. NHibernate needs to know, what property it's dealing with, to assign proper aliases. Since I'm not mapping the property, it has no way of knowing, what alias I'm looking for.
I guess I'm doing a lot of hacking, just to avoid having to reference NHibernate.Spatial...