Share class with annotations - java

I want to use a simple class with hibernate annotations in a non db project.
I dont wanna dublicate the code and remove annotations.
Is there a way for doing this like using annotations in subclass for parent class's attributes. So i can share the parent class.
Any help would be great, thanks.
Edit:
For example: I have a class:
#Entity
#Table(name = "Sample")
Class Sample{
#Column(name = "attr1")
private String attr1;
// getter setters etc.
}
This class works good for a java project with db dependencies set.
But I serve a restful service with this class.
My client app do not need any db related functions so I dont include any db related jars.
So this is my problem I want to use same classes since both are common for two projects. But I do not need db jars which leads to #Entity annotations to compile errors.
If there is some way to do this, I would be very happy.
Thanks alot.

use hibernate validation groups
Basic Validation Example
create 2 validation groups and use one of them for db project and other for not db project

Related

Defining JPA repositories in test

I created some library with aspect which works with JPA repositories. What I am trying to achieve is to create tests for that particular aspect. There are neither repositories nor entities in source code of the library. So in test I need to test this aspect inside of spring context with test entities and repositories. So in test sources I defined DataJpaTest with properties to enable in-memory h2 and jpa ddl create, an entity class and repository interface which derives from CrudRepository. By starting of test I see JPA saying after scanning that 0 repositories found.
I have tried to add repository class into context configuration annotation, then in enable JPA repositories, used also entity scan. Nothing works and I understand that what can be is that probably either repositories and entities scan generally disabled in test classes or there is some kind of other trick which I do not know yet. Does enybody tackled already such a problem?
have you mentioned the annotations in their respective places?
like this
entity class
#Entity
#Table(name = "demoEntity")
public class DemoEntity{
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private int id;
//attributes
//methods / getters & setters
}
then repository
#Repository
public interface DemoEntityRepository extends JpaRepository<DemoEntity, Intiger>{
}
hopefully, then it should work else you can ping me any time, I'm always here.
and please provide some sample code or error pages for better understanding.

Creating Java Boilerplate Code with IntelliJ

Is it possible to create a template/live template with IntelliJ to create the full stack of usual boilerplate for a Domain Object?
Let me give you an example: A usual structure in in a backend could look something like this:
Define a functional domain object: Foobar
Create the entity FoobarEntity:
#Entity #Table(name="foobar") #Getter #Setter
public class FoobarEntity implements Persistable<Long> {
#Id
private Long id;
#Column
private String someData;
#Column
private String someMoreData;
}
Now the boilerplate party starts, create data transfer objects, data access objects, services, ...: Create FoobarDto (to get started), Interface FoobarDao (CRUD) and default implementation FoobarDaoJpa, Interface FoobarService (CRUD) and default implementation FoobarServiceImpl, a mapper to map from Entity to Dto FoobarDtoMapper, maybe a Spring config FoobarConfig, maybe a filter object to search FoobarSearchFilter, maybe some more Classes for a REST api like FoobarRessource, FoobarController, ...
Some further considerations: More annotations (like #Service or something like that) would be somehow useless since the all the classes start with the same code base (like add, delete, edit, load methods for a service and a dao) but, however, will grow in the further process of development.
Is this somehow possible with IntelliJ (or another tool you know)?
You can create entities like that with hibernate plugin. It creates entities according to your table structure. Just add hibernate framework to your project (in linux, press Ctrl + Shift + a, then type hibernate and select add hibernate framework), then you'll get a task window like that:
Now right click on your projects name (will be different in your case) and select Generate Persistence Mapping > By Database Schema.
Now a window will open and you can select the tables you want to create an entity for.
Note that you need to have set up your database in idea to make this work.
For your third point, use file templates. Again, press Ctrl + Shift + a, but then type file template - create the templates once and just use them...

Dynamic schema in Hibernate #Table Annotation

Imagine you have four MySQL database schemas across two environments:
foo (the prod db),
bar (the in-progress restructuring of the foo db),
foo_beta (the test db),
and bar_beta (the test db for new structures).
Further, imagine you have a Spring Boot app with Hibernate annotations on the entities, like so:
#Table(name="customer", schema="bar")
public class Customer { ... }
#Table(name="customer", schema="foo")
public class LegacyCustomer { ... }
When developing locally it's no problem. You mimic the production database table names in your local environment. But then you try to demo functionality before it goes live and want to upload it to the server. You start another instance of the app on another port and realize this copy needs to point to "foo_beta" and "bar_beta", not "foo" and "bar"! What to do!
Were you using only one schema in your app, you could've left off the schema all-together and specified hibernate.default_schema, but... you're using two. So that's out.
Spring EL--e.g. #Table(name="customer", schema="${myApp.schemaName}") isn't an option--(with even some snooty "no-one needs this" comments), so if dynamically defining schemas is absurd, what does one do? Other than, you know, not getting into this ridiculous scenario in the first place.
I have fixed such kind of problem by adding support for my own schema annotation to Hibernate. It is not very hard to implement by extending LocalSessionFactoryBean (or AnnotationSessionFactoryBean for Hibernate 3). The annotation looks like this
#Target(TYPE)
#Retention(RUNTIME)
public #interface Schema {
String alias() default "";
String group() default "";
}
Example of using
#Entity
#Table
#Schema(alias = "em", group = "ref")
public class SomePersistent {
}
And a schema name for every combination of alias and group is specified in a spring configuration.
you can try with interceptors
public class CustomInterceptor extends EmptyInterceptor {
#Override
public String onPrepareStatement(String sql) {
String prepedStatement = super.onPrepareStatement(sql);
prepedStatement = prepedStatement.replaceAll("schema", "Schema1");
return prepedStatement;
}
}
add this interceptor in session object as
Session session = sessionFactory.withOptions().interceptor(new MyInterceptor()).openSession();
so what happens is when ever onPrepareStatement is executed this block of code will be called and schema name will be changed from schema to schema1.
You can override the settings you declare in the annotations using a orm.xml file. Configure maven or whatever you use to generate your deployable build artifacts to create that override file for the test environment.

Auto-generate JPA XML mappings from clean Java classes / POJOs using library/tool

I am currently working for a client who developed several clean, non-annotated Java POJO domain models. Every domain model contains about 15-50 classes. So far, these Java POJO domain models have only been used in Android apps.
For a new project my client is undertaking, it is necessary to use these domain models server side, and save the instances of their classes to a sql database.
We will use JPA for this. Since the jar needs to be reused in the existing Android apps, using JPA annotations is not an option. So, I need to create JPA xml mappings for these 100+ classes.
I was wondering: is it possible to auto generate JPA Xml mappings from clean Java classes/POJOs using some lib/tool? When I started looking, I thought I was going to find a "javamodel 2 jpa xml mapping" tool pretty quick, but so far, no luck, and I have already been looking for a while.
To me, it seems like a tool that would be useful in tons of scenarios, so I almost can't believe it doesn't exist.
I know about tools such as hbm2java. I know it is possible to create POJOS/orm mapping from a ddl and POJOS/DDL from an orm mapping. But I need the orm mapping given the POJOs.
Also, I know a JPA xml mapping can be pretty short and simple/basic properties are auto mapped. I realize I won't have to map every single property, but still, I am facing a lot of repetitive work if such a tool does not exist.
So, does a "javamodel 2 jpa xml mapping" tool exist?
I created a simple tool for this, hosted at Github: https://github.com/IntegratingStuff/java2jpa
Basic usage example:
Java2JpaMappingGenerator java2JpaMappingGenerator =
new Java2JpaMappingGenerator();
java2JpaMappingGenerator.setRenderJpaMappingForClassStrategy(
new RenderJpaMappingForClassStrategyDefaultImpl());
JpaMappingRendererDefaultImpl jpaMappingRenderer =
new JpaMappingRendererDefaultImpl("target/META-INF/orm.xml");
java2JpaMappingGenerator.setJpaMappingRenderer(jpaMappingRenderer);
java2JpaMappingGenerator.generateJpaMappingsForPackages("com.test.model");
jpaMappingRenderer.createMappedFiles();
With this tool, you can create JPA Xml mappings from a Java POJO domain model. However, often you will need to create a custom implementation of the RenderJpaMappingForClassStrategy interface for you own model in order to use the tool efficiently.
Maybe stupid idea but how about a batch generator creating fasade/proxy .java files with JPA #Annotation tags. Big show stopper might be your app must use JPACustomer type not real one. Just one suggestion don't kill the messenger.
#Entity
#Table(name="customer")
public class JPACustomer extends Customer {
#Id #GeneratedValue(strategy=GenerationType.IDENTITY)
public long getId() { return super.getId(); }
public void setId(long id) { super.setId(id); }
#Column(name="name")
public String getName() { return super.getName(); }
public void setName(String s) { super.setName(s); }
// ElementCollection provides simple OneToMany linking in OpenJPA.
// joinColumn.name=foreign key column in child table
#ElementCollection(fetch=FetchType.LAZY)
#CollectionTable(name="cust_role", joinColumns={#JoinColumn(name="cust_id")})
#Column(name="role")
public List<String> getRoles() { return super.getRoles(); }
public void setRoles(List<String> roles) { super.setRoles(roles); }
...
}
I would recommend using Eclipse's JPA support (Dali)

Difference between JPA Entity and Hibernate Entity

When I annotate a class with #Entity and try to resolve the dependencies, I get to choose the package between two different packages, javax.persistence.Entity and org.hibernate.annotations.Entity
The javax package is JPA's entity-annotation, but why is there a hibernate entity-annotation and difference does it have with JPA's annotation? Is it just an extension to allow more attributes to be defined?
org.hibernate.annotations.Entity has some extra attributes that javax.persistence.Entity has not standarized. The extra features will only work if using hibernate's AnnotationConfiguration directly or if hibernate is the JPA provider.
from the FAQ:
edit: new link the specific question:
edit: new link the answer:
I use #org.hibernate.annotations.Entity and get an Unknown entity exception
Always import #javax.persistence.Entity
#org.hibernate.annotations.Entity completes #javax.persistence.Entity but is not a replacement
For instance, there is an attribute called optimisticLock, which tells hibernate whether to use the standard version column or to compare all columns when updating. This behavior is not in the JPA spec, so in order to configure it, you must use hibernate specific extension found in their own annotation.
Like this:
#Entity
#org.hibernate.annotations.Entity(optimisticLock=OptimisticLockType.ALL)
public class MyEntity implements Serializable {
...
}
#org.hibernate.annotations used in your project, if suppose you want to use JDBC template or ibatis we need to change the code. if we use javax.persistence there is no need to change the code. This is the main difference between org.hibernate.annotations and javax persistence
I'm not sure about the differences but I am sure that if you have the Hibernate jars in your classpath you are using Hibernate JPA. Hibernate provides an implementation of JPA. Even though you are using the javax.persistence package you are using Hibernate JPA.
The difference could be only in the naming. They might provide the same classes both in the Hibernate package space and the javax package space.

Categories