I need to customise Liferay's default behaviour: currently, each organization must hava a unique name -- I need to override this behaviour to allow duplicate names. Also, currently there are lots of entities in current Organization_ table in database.
Is it possible to override default model and remove uniqueness constraint while preserving old entities? If yes, how would I approach this?
Of course, I could just add unique suffixes to new saved entities and remove them on display, but this approach seems wierd.
Is it possible to override default model and remove uniqueness
constraint while preserving old entities?
Yes, it surely is, as you can override everything in Liferay
If yes, how would I approach this?
Sarcastic Approach
identify all the places, where Liferay handles Organizations and might implicitly rely on their uniqueness.
hope that I indeed found all the places
evaluate if it's feasible to change all those places to not rely on the uniqueness of the name any more
hope that I found everything, and that my changes make sense
set aside a lot of money to pay for future maintenance of my changes, when I need to adopt the changes to future versions of Liferay.
to 10. determine that it's not worth it and move on to an alternative solution
Alternative Approach:
Determine where this new display is required
implement alternative name, e.g. through Expandos (Custom Fields)
change display where needed to show the Expando values instead of the organization's name.
Related
I am new to Optaplanner. I thought I had understood what planning entities are, as well as planning variables, genuine or some inverse-kind shadow ones. I have started studying the documentation, the examples and old StackOverflow's questions, but some doubts remain.
When trying to make incremental my score calculator, I have found some unexpected methods in the IncrementalScoreCalculator interface. Together with beforeVariableChanged and afterVariableChanged, I find *EntityAdded and *EntityRemoved, which make me suspect that entity objects may be added and removed. Moreover, these methods are implemented in the NQueens documented example, but in the kind of examples I looking at, examples of distributing shifts, resources, time slots, etc., I find that the domain is designed in such a way that planning entities are expected to be modified, but not added or removed.
I don't know if the addition/removal of entity objects is something used somewhere, as in route planning problems which I haven't dove into, and if these additions and removals are explicit or implicit. So, might planning entities be added or removed by Optaplanner without being asked to?
No, OptaPlanner out-of-the-box will not add or remove planning entity instances, because the default move selectors only modify planning entities, they don't create or destroy them.
OptaPlanner doesn't have any generic move selectors yet that can do that (and once we do, they won't be on by default).
If you write a custom move (see MoveListFactory and MoveIteratorFactory in docs), then you could choose to add/remove entities in moves, which is why those methods exists, but very few users do that.
During my career I saw two different designs, how to model business objects in DB:
Always use Long as ID for entity
Choose the most suitable as possible.
And now, we have "Resource" entity which we can download from another service. Each resource contains natural ID - email(email is just an example, we can imagine other situation when we should use String). And I want to use it as primary ID in database. But my workmates want to create additional property - Long id. I am not sure, why should I create this additional property. Of course, DB model is simpler because all entities have the same structure, but I prefer to use String id.
What do you think, guys, which model is much better and why?
First of all, I am not sure if assuming that an email can be a "Resource"s unique natural ID, since that would mean for every new resource, you need to create a new email and a resource can not read emails, but I know cases, so that may be right.
So to the question:
Impacts
Numeric IDs are faster to look up, in every case. But since Strings are pretty fast as well (when using appropriate indices) that might be enough for most of applications out there.
Numeric IDs use less space (which is usually the least problem)
String IDs are usually preferred in cases where heterogenous systems are involved (which you can see in your example: the service provides the "Resource"s with String id's). One reason for that isthat it's easier to debug, e.g. the user might see with one look, what object is referred to, another reason that Strings are the most common denominator of virtually any system (encoding problems will be there though ^^).
If you have to do lots of manual jobs in a database, you can type numbers faster, since Strings tend to be longer
If you use natural IDs it is a pretty common case that the id consists of more than one column. This makes SQL statements longer and more error prone, just as it makes Object Relational Mapper Configurations longer and more error prone.
You usually have some unique identifier (like an email), that but might change over time (people marry ^^). In those cases it is quite common to add some artifical id's as well (have both)
In your case you do not have a choice (?) other than use that string id to communicate with this service, so you at least must have this as well.
So now for my own oppinion: I think as a developer, you have less work and less problems with numeric IDs, though debugging is a little harder. As a database administrator if you have only one column it does not matter if it's String or Long, since it does not complicate joins. As long as the String is immutable, e.g. never changes, you are allright. If it can change it will definitely give you lots of headaches as an administrator (and the stupid developer won't care a bit ^^). If it might change over time, use numeric IDs.
I agree in principal that you should use natural IDs where possible, though in this case email is potentially not a good candidate. Natural IDs should be immutable, i.e. they should never change. If there is any probability that the system would need to change/disassociate an email from a resource, you're essentially changing the identity of the record.
If it were me, and there were no other potential natural IDs; use a unique number. In this case it is not adding any unnecessary complexity, and leaves the design open for future changes to requirements around the email property.
Michal,
Email and such character data columns may not be the right choice for ID as the case sensitivity depends on the database implementation and/or collation being used. Do you want user#server.com and USER#SERVER.COM to give you the same result? Whether it is possible or not depends on your choice of database/OS/collation. When you have character data based IDs, you silently push these concerns from the application to the database administration & collation config.
This might be good as it is only a one time activity and your DB admin can set it up for you but more often than not, you have to maintain seperate DB scripts for different OS & databases.
In my view, there is no thumb rule for this and you have to make the best judgement depending upon the situation.
In addition to the arguments already mentioned, you can search for "surrogate key" or visit the Wikipedia's page on this topic http://en.wikipedia.org/wiki/Surrogate_key which lists many pros and cons.
What is the best practice for updating a model where only certain fields are meant to be updated?
Eg.
If I have a person model with:
Name
Birthdate
Address
And a form where I want to update only:
Address
The two options I can currently see are:
To have a custom form model that has only address - on postback call the DB to retrieve my object to fill in Name and Birthdate, then persist back to the DB.
Custom update SQL to only update the relevant fields.
I'd prefer to make use of the hibernate model if possible, so I'm using #1 currently.
Is there a better way?
How Hibernate constructs an SQL Update can be configured to update only the fields that changed, using an attribute called dynamic-update on the class mapping.
If hibernate leaves useful-looking functionality like this deactivated by default it's because there are trade-offs to be made. The linked documentation goes on to say:
The dynamic-update and dynamic-insert settings are not inherited by subclasses, so they can also be specified on the or elements. Although these settings can increase performance in some cases, they can actually decrease performance in others.
Best Practice is to skip performance optimization until you need it.
Usually with Java EE when we create Model, we define the fields and types of fields through XML or annotation before compilation time. Is there a way to change those in runtime? Or better, is it possible to create a new Model based on the user's input during the runtime? Such that the number of columns and types of fields are dynamic (determined at runtime)?
Help is much appreciated. Thank you.
I felt the need to clarify myself.
Yes, I meant database modeling, when talking about Model.
As for the use cases, I want to provide a means for users to define and create their own tables. Infinite flexibility is not required. However some degree of freedom has to be there: e.g. the users can define what fields are needed to describe their product.
You sound like you want to be able to change both objects and schema according to user input at runtime. This sounds like a chaotic recipe for disaster to me. I've never seen it done.
I have seen general schemas that incorporate foreign key relationships to generic tables of name/value pairs, but these tend to become infinitely flexible abstractions that can neither be easily understood nor get out of their own way when it comes to performance.
I'm betting that your users really don't want infinite flexibility. I'd caution you against taking this direction. Better to get your real use cases straight.
Anything is possible, of course. My direct experience tells me that it's a bad idea that your users will hate if you can pull it off. Best of luck.
I worked on a system where we had such facilities. To stay efficient, we would generate/alter the table dynamically for the customer schema. We also needed to embed a meta-model (the model of the model) to process information in the entities dynamically.
Option 1: With custom tables, you have full flexibility, but it also increases the complexity significantly, notably the update/migration of existing data. Here is a list of things you will need to consider:
What if the type of a column change?
What if a column is added? Is there a default value?
What if a column is removed? Can I discard the existing information?
How to manage renaming of a column?
How to make things portable across databases?
How to make it efficient at database-level (e.g. indexes) ?
How to manage a human error (e.g. user removes a column then changes its mind)?
How to manage migration (script, deployment, etc.) when new version of the system is installed at customer site?
How to have this while using an ORM?
Option 2: A lightweight alternative is to add a few "spare" columns in the business tables of different types (e.g.: "USER_DATE_1", "USER_DATE_2", etc.) I've seen that a few times. It will makes your DBA scream and is not really considered a good practice, but at least can facilitates a few things, e.g. (migration scripts, ORM integration).
Option 3: Another option is to store everything in a table with a structure property/data. But then it's really a disaster for database performance. Anything that is not completely trivial will require many joins. And the DBA will scream even more.
Option 4: It is a mix of options 2 and 3. Core tables are fixed, but a table with property/data can be used to somehow extend them.
In summary: think twice before you go this way. It can be done, but has a significant impact on the design and maintenance of the application.
This is somehow possible using meta-modeling techniques:
tables for table / column / types at the database level
key/value structures at the Java level
But this has obvious limitations (lack of strong typed objects) and can IMHO get quickly very complicated (not even sure how to deal with relations). I wouldn't use this approach to define domain objects entirely, but only to extend existing ones (products, articles, etc).
If I remember well, this is what some e-commerce solutions (e.g. BroadVision) were doing.
I think I have found a good answer myself. Those new no-sql (hbase, cassandra) database seems to be exactly what I was looking for. Thanks everyone for your answeres.
Let's say I have a set of Countries in my application. I expect this data to change but not very often. In other words, I do not look at this set as an operational data (I would not provide CRUD operations for Country, for example).
That said I have to store this data somewhere. I see two ways to do that:
Database driven. Create and populate a Country table. Provide some sort of DAO to access it (findById() ?). This way client code will have to know Id of a country (which also can be a name or ISO code). On the application side I will have a class Country.
Application driven. Create an Enum where I can list all the Countries known to my system. It will be stored in DB as well, but the difference would be that now client code does not have to have lookup method (findById, findByName, etc) and hardcode Id, names or ISO codes. It will reference particular country directly.
I lean towards second solution for several reasons. How do you do this?
Is this correct to call this 'dictionary data'?
Addendum: One of the main problems here is that if I have a lookup method like findByName("Czechoslovakia") then after 1992 this will return nothing. I do not know how the client code will react on it (after all it sorta expects always get the Country back, because, well, it is a dictionary data). It gets even worse if I have something like findById(ID_CZ). It will be really hard to find all these dependencies.
If I will remove Country.Czechoslovakia from my enum, I will force myself to take care of any dependency on Czechoslovakia.
In some applications I've worked on there has been a single 'Enum' table in the database that contained all of this type of data. It simply consisted of two columns: EnumName and Value, and would be populated like this:
"Country", "Germany"
"Country", "United Kingdom"
"Country", "United States"
"Fruit", "Apple"
"Fruit", "Banana"
"Fruit", "Orange"
This was then read in and cached at the beginning of the application execution. The advantages being that we weren't using dozens of database tables for each distinct enumeration type; and we didn't have to recompile anything if we needed to alter the data.
This could easily be extended to include extra columns, e.g. to specify a default sort order or alternative IDs.
This won't help you, but it depends...
-What are you going to do with those countries ?
Will you store them in other tables in the DB / what will happen with existing data if you add new countries / will other applications access to those datas ?
-Are you going to translate the contry names in several languages ?
-Will the business logic of your application depend on the choosen country ?
-Do you need a Country class ?
etc...
Without more informations I would start with an Enum with a few countries and refactor depending on my needs...
If it's not going to change very often and you can afford to bring the application down to apply updates, I'd place it in a Java enumeration and write my own methods for findById(), findByName() and so on.
Advantages:
Fast - no DB access for invariant data (or caching requirement);
Simple;
Plays nice with refactoring tools.
Disadvantages:
Need to bring down the application to update.
If you place the data in its own jarfile, updating is as simple as updating the jar and restarting the application.
The hardcoding concern can be made to go away either by consumers storing a value of the enumeration itself, or by referencing the ISO code which is unlikely to change for countries...
If you're worried about keeping this enumeration "in synch" with the database, write an integration test that checks exactly that and run it regularly (eg: on your CI machine).
Personally, I've always gone for the database approach, mostly because I'm already storing other information in the database so writing another DAO is easy.
But another approach might be to store it in a properties file in the jar? I've never done it that way in Java, but it seems to be common in iPhone development (something I'm currently learning).
I'd probably have a text file embedded into my jar. I'd load it into memory on start-up (or on first use.) At that point:
It's easy to change (even by someone with no programming knowledge)
It's easy to update even without full redeployment - put just the text file somewhere on the class path
No database access required
EDIT: Okay, if you need to refer to the particular country data from code, then either:
Use the enum approach, which will always mean redeployment
Use the above approach, but keep an enum of country IDs and then have a unit test to make sure that each ID is mapped in the text file. That means you could change the rest of the data without redeployment, and a non-technical person can still update the data without seeing scary code everywhere.
Ultimately it's a case of balancing pros and cons - if the advantages above aren't relevant for you (e.g. there'll always be a coder on hand, and deployment isn't an issue) then an enum makes sense.
One of the advantages of using a database table is you can put foreign key constraints in. That way your referential integrity will always be intact. No need to run integration tests as DanVinton suggested for enums, it will never get out of sync.
I also wouldn't try making a general enum table as saw-lau suggested, mainly because you lose clean foreign key constraints, which is the main advantage of having them in the DB in the first place (might was well stick them in a text file). Databases are good at handling lots of tables. Prefix the table names with "ENUM_" if you want to distinguish them in some fashion.
The app can always load them into a Map as start-up time or when triggered by a reload event.
EDIT: From comments, "Of course I will use foreign key constraints in my DB. But it can be done with or without using enums on app side"
Ah, I missed that bit while reading the second bullet point in your question. However I still say it is better to load them into a Map, mainly based on DRY. Otherwise, when whoever has to maintain it comes to add a new country, they're surely going to update in one place but not the other, and be scratching their heads until they figure out that they needed to update it in two different places. A case of premature optimisation. The performance benefit would be minimal, at the cost of less maintainable code, IMHO.
I'd start off doing the easiest thing possible - an enum. When it comes to the point that countries change almost as frequently as my code, then I'd make the table external so that it can be updated without a rebuild. But note when you make it external you add a whole can of UI, testing and documentation worms.