Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.java.programmer > #32323 > unrolled thread

JPA and extra fields

Started byCecil Westerhof <Cecil@decebal.nl>
First post2015-08-13 20:12 +0200
Last post2015-08-20 03:49 +0200
Articles 20 on this page of 25 — 5 participants

Back to article view | Back to comp.lang.java.programmer


Contents

  JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-13 20:12 +0200
    Re: JPA and extra fields Eternal Hope <laughingspam99@gmail.com> - 2015-08-13 20:29 +0100
      Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-17 07:40 +0200
    Re: JPA and extra fields Arne Vajhøj <arne@vajhoej.dk> - 2015-08-13 22:30 -0400
      Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-17 08:22 +0200
        Re: JPA and extra fields Martin Gregorie <martin@address-in-sig.invalid> - 2015-08-17 11:40 +0000
          Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-17 14:36 +0200
            Re: JPA and extra fields Martin Gregorie <martin@address-in-sig.invalid> - 2015-08-17 18:08 +0000
              Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-17 21:24 +0200
                Re: JPA and extra fields Martin Gregorie <martin@address-in-sig.invalid> - 2015-08-17 22:47 +0000
                  Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-19 11:32 +0200
            Re: JPA and extra fields Arne Vajhøj <arne@vajhoej.dk> - 2015-08-17 19:48 -0400
          Re: JPA and extra fields Eternal Hope <laughingspam99@gmail.com> - 2015-08-18 06:25 +0100
            Re: JPA and extra fields Martin Gregorie <martin@address-in-sig.invalid> - 2015-08-18 10:49 +0000
              Re: JPA and extra fields Eternal Hope <laughingspam99@gmail.com> - 2015-08-19 09:00 +0100
                Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-19 11:36 +0200
                  Re: JPA and extra fields Martin Gregorie <martin@address-in-sig.invalid> - 2015-08-19 10:48 +0000
        Re: JPA and extra fields Arne Vajhøj <arne@vajhoej.dk> - 2015-08-17 19:46 -0400
          Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-19 11:28 +0200
      Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-19 11:53 +0200
        Re: JPA and extra fields Martin Gregorie <martin@address-in-sig.invalid> - 2015-08-19 10:51 +0000
          Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-19 13:14 +0200
            Re: JPA and extra fields Cecil Westerhof <Cecil@decebal.nl> - 2015-08-19 14:19 +0200
        Re: JPA and extra fields Arne Vajhøj <arne@vajhoej.dk> - 2015-08-19 19:13 -0400
    Re: JPA and extra fields Silvio <silvio@internet.com> - 2015-08-20 03:49 +0200

Page 1 of 2  [1] 2  Next page →


#32323 — JPA and extra fields

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-13 20:12 +0200
SubjectJPA and extra fields
Message-ID<87zj1v3vnq.fsf@Equus.decebal.nl>
I am new to JPA. I have to migrate a JDBC application to JPA. For a
certain class there are some extra fields in the table that are not in
the class itself. (For example creation time, modification time and
user that created the entity.) Is it possible to keep those fields in
the table and updated, without putting the values in the class?

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [next] | [standalone]


#32325

FromEternal Hope <laughingspam99@gmail.com>
Date2015-08-13 20:29 +0100
Message-ID<mqir44$15b$1@dont-email.me>
In reply to#32323
On 13/08/2015 19:12, Cecil Westerhof wrote:
> I am new to JPA. I have to migrate a JDBC application to JPA. For a
> certain class there are some extra fields in the table that are not in
> the class itself.

How do you know they belong to the class if they are not in the class?
look at the sql, where do these mystery fields come from, are they 
passed in along with the object instance that contains the other fields 
in which case they would need to be contained within some other class if 
it's Java (the horror) are they generated by some stored procedure (the 
horror, the horror) or a trigger (oh the horror).

  (For example creation time, modification time and
> user that created the entity.) Is it possible to keep those fields in
> the table and updated, without putting the values in the class?

Why in [insert deity here]'s name would you want to do that?
Is this some bastard son (of an application) of an unholy alliance 
between a DBA and an OO designer? Why do you want to avoid adding them 
to the class? Is it because, in your Java brain you feel they don't 
'belong' there? If they don't belong in the class then they don't belong 
in the table *unless* they are fields in another class that has some 
sort of containment relationship with your container class? 
(aggregation, composition) in which case they are contained by the 
container class and therefore somehow 'belong' in some 'OO' realty in 
the container.

Trying to map an application to a relational database using a ORM 
framework when some of the fields aren't contained in some way in you 
existential object graph seems a bit like hearding cats ... is it even 
possible, don't know, don't reallyy know JPA but in answer to your othr 
question, as long as you have a driver in your classpath then I can't 
see why you can't use what you want when you want to do what you want.

It all just sounds so ... *nasty*



-- 
Laughing Spam Fritter

[toc] | [prev] | [next] | [standalone]


#32332

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-17 07:40 +0200
Message-ID<87vbcescae.fsf@Equus.decebal.nl>
In reply to#32325
On Thursday 13 Aug 2015 21:29 CEST, Eternal Hope wrote:

> On 13/08/2015 19:12, Cecil Westerhof wrote:
>> I am new to JPA. I have to migrate a JDBC application to JPA. For a
>> certain class there are some extra fields in the table that are not
>> in the class itself.
>
> How do you know they belong to the class if they are not in the
> class? look at the sql, where do these mystery fields come from, are
> they passed in along with the object instance that contains the
> other fields in which case they would need to be contained within
> some other class if it's Java (the horror) are they generated by
> some stored procedure (the horror, the horror) or a trigger (oh the
> horror).

They belong NOT to the class. Extra code is used to fill those table
fields.


> (For example creation time, modification time and
>> user that created the entity.) Is it possible to keep those fields
>> in the table and updated, without putting the values in the class?
>
> Why in [insert deity here]'s name would you want to do that? Is this
> some bastard son (of an application) of an unholy alliance between a
> DBA and an OO designer? Why do you want to avoid adding them to the
> class? Is it because, in your Java brain you feel they don't belong'
> there? If they don't belong in the class then they don't belong in
> the table *unless* they are fields in another class that has some
> sort of containment relationship with your container class?
> (aggregation, composition) in which case they are contained by the
> container class and therefore somehow 'belong' in some 'OO' realty
> in the container.

Well, I only have to change from JDBC to JPA, I did not design the
class and the table. That is probably done a decade (or longer ago).

Personally I find the date fields not that strange. It is good to know
when a record is created, or mutated, but not that useful in the class
itself.


> Trying to map an application to a relational database using a ORM
> framework when some of the fields aren't contained in some way in
> you existential object graph seems a bit like hearding cats ... is
> it even possible, don't know, don't reallyy know JPA but in answer
> to your othr question, as long as you have a driver in your
> classpath then I can't see why you can't use what you want when you
> want to do what you want.
>
> It all just sounds so ... *nasty*

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [prev] | [next] | [standalone]


#32328

FromArne Vajhøj <arne@vajhoej.dk>
Date2015-08-13 22:30 -0400
Message-ID<55cd52c4$0$298$14726298@news.sunsite.dk>
In reply to#32323
On 8/13/2015 2:12 PM, Cecil Westerhof wrote:
> I am new to JPA. I have to migrate a JDBC application to JPA. For a
> certain class there are some extra fields in the table that are not in
> the class itself. (For example creation time, modification time and
> user that created the entity.) Is it possible to keep those fields in
> the table and updated, without putting the values in the class?

I can see different ways of moving forward.

1)

Keep those fields out of the class an update them in the database
via triggers.

Possible create a view without those fields and have the entity map
to that instead of the table.

2)

Add the fields to the class but do not expose them in its
public API. And let them be updated internally.

Possible by mapping fields and either no getter/setter
or protected.

3)

Add the fields to the entity class the normal way
but create a new domain class without the fields
and convert from entity class to domain class when
leaving DAL.

Arne


[toc] | [prev] | [next] | [standalone]


#32334

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-17 08:22 +0200
Message-ID<87r3n2sact.fsf@Equus.decebal.nl>
In reply to#32328
On Friday 14 Aug 2015 04:30 CEST, Arne Vajhøj wrote:

> On 8/13/2015 2:12 PM, Cecil Westerhof wrote:
>> I am new to JPA. I have to migrate a JDBC application to JPA. For a
>> certain class there are some extra fields in the table that are not
>> in the class itself. (For example creation time, modification time
>> and user that created the entity.) Is it possible to keep those
>> fields in the table and updated, without putting the values in the
>> class?
>
> I can see different ways of moving forward.
>
> 1)
>
> Keep those fields out of the class an update them in the database
> via triggers.
>
> Possible create a view without those fields and have the entity map
> to that instead of the table.
>
> 2)
>
> Add the fields to the class but do not expose them in its
> public API. And let them be updated internally.
>
> Possible by mapping fields and either no getter/setter
> or protected.
>
> 3)
>
> Add the fields to the entity class the normal way
> but create a new domain class without the fields
> and convert from entity class to domain class when
> leaving DAL.

The first option seems the best to me. (But I am not sure it is
possible with all fields.) Is also depending on the database. The
application uses a CISC database. I am not sure if these have this
capability.

But I think I have to use the second possibility.

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [prev] | [next] | [standalone]


#32335

FromMartin Gregorie <martin@address-in-sig.invalid>
Date2015-08-17 11:40 +0000
Message-ID<mqsh70$s82$1@dont-email.me>
In reply to#32334
On Mon, 17 Aug 2015 08:22:10 +0200, Cecil Westerhof wrote:

> On Friday 14 Aug 2015 04:30 CEST, Arne Vajhøj wrote:
> 
>> On 8/13/2015 2:12 PM, Cecil Westerhof wrote:
>>> I am new to JPA. I have to migrate a JDBC application to JPA. For a
>>> certain class there are some extra fields in the table that are not in
>>> the class itself. (For example creation time, modification time and
>>> user that created the entity.) Is it possible to keep those fields in
>>> the table and updated, without putting the values in the class?
>>
>> I can see different ways of moving forward.
>>
>> 1)
>>
>> Keep those fields out of the class an update them in the database via
>> triggers.
>>
>> Possible create a view without those fields and have the entity map to
>> that instead of the table.
>>
>> 2)
>>
>> Add the fields to the class but do not expose them in its public API.
>> And let them be updated internally.
>>
>> Possible by mapping fields and either no getter/setter or protected.
>>
>> 3)
>>
>> Add the fields to the entity class the normal way but create a new
>> domain class without the fields and convert from entity class to domain
>> class when leaving DAL.
> 
> The first option seems the best to me. (But I am not sure it is possible
> with all fields.) Is also depending on the database. The application
> uses a CISC database. I am not sure if these have this capability.
> 
> But I think I have to use the second possibility.
>
Does the system have an owner who is generally responsible for change 
management, agreeing enhancements etc? If so what do they say about these 
fields? 

I agree about the value of adding columns to tables that are not used by 
the application and whose sole purpose is the keep track of when rows get 
updated and by which program. I've used them in the past and used 
triggers to maintain them independently from the application: by using 
triggers defined by the DBA and called below application level, a 
careless programmer can't forget to update them and their maintenance 
doesn't impact on application logic.
 

-- 
martin@   | Martin Gregorie
gregorie. | Essex, UK
org       |

[toc] | [prev] | [next] | [standalone]


#32336

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-17 14:36 +0200
Message-ID<87io8ert0x.fsf@Equus.decebal.nl>
In reply to#32335
On Monday 17 Aug 2015 13:40 CEST, Martin Gregorie wrote:

> On Mon, 17 Aug 2015 08:22:10 +0200, Cecil Westerhof wrote:
>
>> On Friday 14 Aug 2015 04:30 CEST, Arne Vajhøj wrote:
>>
>>> On 8/13/2015 2:12 PM, Cecil Westerhof wrote:
>>>> I am new to JPA. I have to migrate a JDBC application to JPA. For
>>>> a certain class there are some extra fields in the table that are
>>>> not in the class itself. (For example creation time, modification
>>>> time and user that created the entity.) Is it possible to keep
>>>> those fields in the table and updated, without putting the values
>>>> in the class?
>>>
>>> I can see different ways of moving forward.
>>>
>>> 1)
>>>
>>> Keep those fields out of the class an update them in the database
>>> via triggers.
>>>
>>> Possible create a view without those fields and have the entity
>>> map to that instead of the table.
>>>
>>> 2)
>>>
>>> Add the fields to the class but do not expose them in its public
>>> API. And let them be updated internally.
>>>
>>> Possible by mapping fields and either no getter/setter or
>>> protected.
>>>
>>> 3)
>>>
>>> Add the fields to the entity class the normal way but create a new
>>> domain class without the fields and convert from entity class to
>>> domain class when leaving DAL.
>>
>> The first option seems the best to me. (But I am not sure it is
>> possible with all fields.) Is also depending on the database. The
>> application uses a CISC database. I am not sure if these have this
>> capability.
>>
>> But I think I have to use the second possibility.
>>
> Does the system have an owner who is generally responsible for
> change management, agreeing enhancements etc? If so what do they say
> about these fields?

I wish. :-( I have to find out what the different things mean. At
least I managed to get some old documentation that describes the
tables. (On the SQL level.)

Another part of the problem that there is also Cobol code which
maintains another part of the functionalities. So my hands are a bit
tied.


> I agree about the value of adding columns to tables that are not
> used by the application and whose sole purpose is the keep track of
> when rows get updated and by which program. I've used them in the
> past and used triggers to maintain them independently from the
> application: by using triggers defined by the DBA and called below
> application level, a careless programmer can't forget to update them
> and their maintenance doesn't impact on application logic.

I started implementing these values. I hope to get tomorrow some
information about if it can be done with triggers. But I am afraid
not. For example booleans are done with char of one long. I think I
write an annotation for those.

But I also have to save the user that created/mutated. For those I can
not use triggers I think. So those still have to be implemented.


Well, I dive further into the code to understand what it is doing. ;-)

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [prev] | [next] | [standalone]


#32340

FromMartin Gregorie <martin@address-in-sig.invalid>
Date2015-08-17 18:08 +0000
Message-ID<mqt7uh$ga1$1@dont-email.me>
In reply to#32336
On Mon, 17 Aug 2015 14:36:30 +0200, Cecil Westerhof wrote:

> Another part of the problem that there is also Cobol code which
> maintains another part of the functionalities. So my hands are a bit
> tied.
>
Understood - see below for an obvious link to COBOL.
 
> For example booleans are done with char of one long. I think I write an
> annotation for those.
>
That sounds like COBOL all right, which doesn't have a simple way of 
defining booleans. The best you can do is set up a single character 
variable (which can be character, numeric or alphabetic) and define a set 
of level 88 values against it, something like this:

  01   ERROR-CONTROL.
   05  ERROR-DESCRIPTION  PIC X(50).
   05  ERROR-INDICATOR    PIC X.
    88 ERROR_FOUND        VALUE "Y".

which you could use like this:

*
* Clear both the error description and the error-indicator
*
  MOVE SPACE TO ERROR-CONTROL.
  ...
  IF FIRST-NAME = SPACE 
     MOVE "Y" TO ERROR-INDICATOR
     MOVE "Missing first name" to ERROR-DESCRIPTION. 
  ...
  ...
  IF ERROR-FOUND PERFORM REPORT-ERROR-TO-USER.

If the system uses a COBOL copy library to define records and other 
variables and/or commonly used procedure division sentences or 
paragraphs, it would be worth looking there for constant definitions.

The only method of linking 88 levels to a data item is to write them 
immediately after the data item that they test.


-- 
martin@   | Martin Gregorie
gregorie. | Essex, UK
org       |

[toc] | [prev] | [next] | [standalone]


#32341

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-17 21:24 +0200
Message-ID<87bne5sopd.fsf@Equus.decebal.nl>
In reply to#32340
On Monday 17 Aug 2015 20:08 CEST, Martin Gregorie wrote:

> On Mon, 17 Aug 2015 14:36:30 +0200, Cecil Westerhof wrote:
>
>> Another part of the problem that there is also Cobol code which
>> maintains another part of the functionalities. So my hands are a
>> bit tied.
>>
> Understood - see below for an obvious link to COBOL.
>
>> For example booleans are done with char of one long. I think I
>> write an annotation for those.
>>
> That sounds like COBOL all right, which doesn't have a simple way of
> defining booleans. The best you can do is set up a single character
> variable (which can be character, numeric or alphabetic) and define
> a set of level 88 values against it, something like this:
>
> 01   ERROR-CONTROL.
> 05  ERROR-DESCRIPTION  PIC X(50).
> 05  ERROR-INDICATOR    PIC X.
> 88 ERROR_FOUND        VALUE "Y".
>
> which you could use like this:
>
> *
> * Clear both the error description and the error-indicator
> *
> MOVE SPACE TO ERROR-CONTROL.
> ...
> IF FIRST-NAME = SPACE 
> MOVE "Y" TO ERROR-INDICATOR
> MOVE "Missing first name" to ERROR-DESCRIPTION. 
> ...
> ...
> IF ERROR-FOUND PERFORM REPORT-ERROR-TO-USER.
>
> If the system uses a COBOL copy library to define records and other
> variables and/or commonly used procedure division sentences or
> paragraphs, it would be worth looking there for constant
> definitions.
>
> The only method of linking 88 levels to a data item is to write them
> immediately after the data item that they test.

Luckily I only have to take care of the Java code. ;-)


By the way, through setter and getter functions I can work with a
boolean in Java.

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [prev] | [next] | [standalone]


#32343

FromMartin Gregorie <martin@address-in-sig.invalid>
Date2015-08-17 22:47 +0000
Message-ID<mqto96$2ks$1@dont-email.me>
In reply to#32341
On Mon, 17 Aug 2015 21:24:30 +0200, Cecil Westerhof wrote:

> Luckily I only have to take care of the Java code. ;-)
>
Sure. I wasn't saying you should be using it, just trying to explain why 
'boolean' flags have ended up being stored as char(1) fields in the 
database. I always find I can deal with a non-intuitive approach if I 
know its background: this often makes the rationale for doing it that way 
a lot clearer. Back when I was grinding out COBOL on mainframes we often 
ended up storing control flags as single character fields that were set 
to Y or N of only because it made file dumps easier to read (0/1 values 
tend to disapear from view in a record containing mainly numeric fields.

I'm assuming that the COBOL part of the system is rather older than the 
Java bits. Is this correct?
 
> 
> By the way, through setter and getter functions I can work with a
> boolean in Java.
>
Yep. Its as good a way as any of handling the conversion.

Recently I've been doing a bit of work with ICG log files. The IGC 
standard says that a logfile is a set of records, each represented as a 
CRLF terminated line containing fixed length ASCII strings. So, the easy 
way to deal with them in Java is to convert a log file to and from an 
internal Java format that stores it as a list of class instances (one per 
record type), with each class using 'natural' Java ways of storing the 
fields (Date, String, int, etc).


-- 
martin@   | Martin Gregorie
gregorie. | Essex, UK
org       |

[toc] | [prev] | [next] | [standalone]


#32355

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-19 11:32 +0200
Message-ID<87vbcbr5cw.fsf@Equus.decebal.nl>
In reply to#32343
On Tuesday 18 Aug 2015 00:47 CEST, Martin Gregorie wrote:

> I'm assuming that the COBOL part of the system is rather older than
> the Java bits. Is this correct?

I think so, but the Java code is probably also not touched for six
years.

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [prev] | [next] | [standalone]


#32346

FromArne Vajhøj <arne@vajhoej.dk>
Date2015-08-17 19:48 -0400
Message-ID<55d272ce$0$301$14726298@news.sunsite.dk>
In reply to#32336
On 8/17/2015 8:36 AM, Cecil Westerhof wrote:
> On Monday 17 Aug 2015 13:40 CEST, Martin Gregorie wrote:
>> Does the system have an owner who is generally responsible for
>> change management, agreeing enhancements etc? If so what do they say
>> about these fields?
>
> I wish. :-( I have to find out what the different things mean. At
> least I managed to get some old documentation that describes the
> tables. (On the SQL level.)
>
> Another part of the problem that there is also Cobol code which
> maintains another part of the functionalities. So my hands are a bit
> tied.

You would be surprised about how common this type of scenario is.

Arne

[toc] | [prev] | [next] | [standalone]


#32350

FromEternal Hope <laughingspam99@gmail.com>
Date2015-08-18 06:25 +0100
Message-ID<mqufi0$605$1@dont-email.me>
In reply to#32335
On 17/08/2015 12:40, Martin Gregorie wrote:
> On Mon, 17 Aug 2015 08:22:10 +0200, Cecil Westerhof wrote:
>
>> On Friday 14 Aug 2015 04:30 CEST, Arne Vajhøj wrote:

<snip>

>
> I agree about the value of adding columns to tables that are not used by
> the application and whose sole purpose is the keep track of when rows get
> updated and by which program. I've used them in the past and used
> triggers to maintain them independently from the application: by using
> triggers defined by the DBA and called below application level, a
> careless programmer can't forget to update them and their maintenance
> doesn't impact on application logic.

<humor>
Ah yes, of course, the infallable and omnipotent DBA cleverly using 
defensive programming to defend against the lazy and incompetent 
developer. It was ever thus. :-)
</humor>

 > and their maintenance
 > doesn't impact on application logic.

... but scatters that logic around the different layers of an 
application making it harder to get an overview and consequently 
impacting on the cost of maintenance.

The 'Object' view

A system of Things

Thing t                  //A Thing
ThingWorker tw           //A user/consumer of Things
ThingFactory tf          //C[reates] a Thing
ThingPersistance tp      //R[ead] U[pdate] D[estroy] a Thing
ThingServer ts           //initialize a Thing plus sql

t = tf.giveMeANewThing(tw)

ThingFactory.giveMeANewThing(ThingWorker tw){
     ThingServer ts
     Timestamp now

     Thing newThing = new Thing();  //it's a factory, it creates Things
     ts.initializeThing(newThing);

     newThing.setCreated(now);
     newThing.setUpdated(now);
     newThing.setCreator(tw.getIdentity());

     return newThing;
}

... //do lot's of stuff with your new Thing, takes time.

tw.doStuff(t);

... //later, possibly much later

tp.updateThing(t);

Surely the time and place to set created is when the Thing is created
also who created it.

Either you have a cohesive system of 'Objects' or you don't.

This is how I do it and I can change the persistance mechanism
however and whenever I want without regard to failities that may or may 
not be present in the underlying implementation of that mechanism.

Just interested that's all.


-- 
Laughing Spam Fritter

[toc] | [prev] | [next] | [standalone]


#32351

FromMartin Gregorie <martin@address-in-sig.invalid>
Date2015-08-18 10:49 +0000
Message-ID<mqv2ke$u6r$1@dont-email.me>
In reply to#32350
On Tue, 18 Aug 2015 06:25:58 +0100, Eternal Hope wrote:

> On 17/08/2015 12:40, Martin Gregorie wrote:
>> I agree about the value of adding columns to tables that are not used
>> by the application and whose sole purpose is the keep track of when
>> rows get updated and by which program. I've used them in the past and
>> used triggers to maintain them independently from the application: by
>> using triggers defined by the DBA and called below application level, a
>> careless programmer can't forget to update them and their maintenance
>> doesn't impact on application logic.
> 
> <humor>
> Ah yes, of course, the infallable and omnipotent DBA cleverly using
> defensive programming to defend against the lazy and incompetent
> developer. It was ever thus. :-)
> </humor>
>
Not quite so much. In a large system you generally have a mix of online 
(interactive) modules and several processes that are run overnight. In a 
system like this it can be quite hard to determine which of the several 
processes that update the database has the reported bug in it. Adding the 
updating program name and a timestamp to each table is low cost, since 
using it merely adds a couple of column changes to a row that's going to 
be updated anyway. In practise its turns out to be a pretty good 
indication of where to start looking for the bug.

> ... but scatters that logic around the different layers of an
> application making it harder to get an overview and consequently
> impacting on the cost of maintenance.
>
I don't agree. If updating the program name and last update time is done 
by a single trigger that is triggered by 'on update' clauses in the 
schema, it doesn't have any impact on the application logic.

Some DBMS support this: others don't and the system designer may choose 
not to use this technique if this sort of trigger isn't supported. Its 
only real flaw is that it doesn't work for tracking deletions: to do that 
you'd need to maintain some sort of changes log and that probably would 
have an impact on throughput. To solve this I like to build the tracing/
debugging code used during development in the live system, but under 
control of debugging controls. This is really useful: if an interactive 
user reports an anomaly you can ask them to switch tracing on, do it 
again and turn tracing off. Once again, finding the fault is generally 
pretty easy.

> Surely the time and place to set created is when the Thing is created
> also who created it.
>
No argument here. In this case I think the two effects are similar and 
that its more a matter of style whether the create/update/delete stamp is 
maintained by the application logic or, if the DBMS has the appropriate 
hooks, as an addition to the schema.
 
> Either you have a cohesive system of 'Objects' or you don't.
> 
Quite. I first did this when I was using a database where it was really 
easy to add a common piece of code that (a) maintained the progname
+timestamp and (b) could dump every record that was read or written to 
the database. It was a single code module that could be invoked for every 
i/o operation on every record type in the database. Its data tracing 
operation could be interactively switched on or off without restarting 
the DBMS, so using it during development was a no-brainer and so was 
leaving it in the live system for trouble shooting.
  
> Just interested that's all.
>
Interesting discussion.


-- 
martin@   | Martin Gregorie
gregorie. | Essex, UK
org       |

[toc] | [prev] | [next] | [standalone]


#32353

FromEternal Hope <laughingspam99@gmail.com>
Date2015-08-19 09:00 +0100
Message-ID<mr1cvb$e61$1@dont-email.me>
In reply to#32351
On 18/08/2015 11:49, Martin Gregorie wrote:
> On Tue, 18 Aug 2015 06:25:58 +0100, Eternal Hope wrote:
>
>> On 17/08/2015 12:40, Martin Gregorie wrote:

<snip>

>> ... but scatters that logic around the different layers of an
>> application making it harder to get an overview and consequently
>> impacting on the cost of maintenance.
>>
> I don't agree. If updating the program name and last update time is done
> by a single trigger that is triggered by 'on update' clauses in the
> schema, it doesn't have any impact on the application logic.

... but it *is* (part of) the logic, that's the point. If the fields are 
not 'important' to the application then I question the need for them in 
the first place, if they *are* important then they belong in the 
application, they should generated by the application and managed by the 
application.

However, I think I understand where you are coming from.

I think anyway !?!

If you have a database that has been around for a while and you have a 
number of unconnected (to each other) client interfaces to that database 
extant, possibly written in different languages and it's important in 
some way to know who (or which application in fact) updated some table 
then I can see the point.

In fact 'logically' this behaviour could be seen as a separate interface 
to the database and an application in it's own right ...

However if this is the case then there seems to be little point 
concerning yourself with those fields as they in effect belong to some 
other application and can safely be ignored.

However (again) the OP seems concerned about them, which casually 
implies they sort of belong to the application he is dealing with in 
which case, if they belong to the application they should be managed by 
the application etc etc

I think we both know the age old OO versus RDBMS argumnent has been done 
to death but this is slightly different, it's about responsibility and 
determining the responsibilitys of an Object in a system of Objects has 
always been hard to get *right*.

<snippage>



-- 
Laughing Spam Fritter

[toc] | [prev] | [next] | [standalone]


#32354

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-19 11:36 +0200
Message-ID<87r3mzr55r.fsf@Equus.decebal.nl>
In reply to#32353
On Wednesday 19 Aug 2015 10:00 CEST, Eternal Hope wrote:

> However (again) the OP seems concerned about them, which casually
> implies they sort of belong to the application he is dealing with in
> which case, if they belong to the application they should be managed
> by the application etc etc

When I rewrite the code I need to make sure I break nothing. So in
this way it is important to me. But the fields are never used in the
application itself. They are only written into the database.

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [prev] | [next] | [standalone]


#32361

FromMartin Gregorie <martin@address-in-sig.invalid>
Date2015-08-19 10:48 +0000
Message-ID<mr1mu5$c4n$1@dont-email.me>
In reply to#32354
On Wed, 19 Aug 2015 11:36:32 +0200, Cecil Westerhof wrote:

> But the fields are never used in the
> application itself. They are only written into the database.
>
...which I strongly suspect they are a debugging aid and have been 
arguing that, if it makes more sense to maintain them separately from the 
application logic, then do it that way.

The app where I first used this trick was a music scheduling system, so 
had a number of subsystems:
- a classical music catalogue (complex because a work frequently
  lacks a name but often exists as various versions and arrangements, 
  and equally frequently needs to be structured as movements/acts and
  parts within the movement of act
- a performers catalogue
- a performance catalogue, used for planning, performance scheduling and 
  tracking repeated performances
- the ability to track usage of parts of work for contractual purposes.
- clash checking (used to avoid undue concentration on particular
  composers/performers/works)
- tracking composer anniversaries (used in planning)

Consequently, both the online parts of the system and the overnight batch 
operation had a good-sized suite of largely unconnected subsystems but 
all accessed the same parts of a fairly complex database. Hence the need 
to keep tabs on which program had last updated a record.

All this was long ago and far away, so the entire system was written in 
COBOL and worked with 80x25 green screens and printed reports.


-- 
martin@   | Martin Gregorie
gregorie. | Essex, UK
org       |

[toc] | [prev] | [next] | [standalone]


#32345

FromArne Vajhøj <arne@vajhoej.dk>
Date2015-08-17 19:46 -0400
Message-ID<55d2726f$0$301$14726298@news.sunsite.dk>
In reply to#32334
On 8/17/2015 2:22 AM, Cecil Westerhof wrote:
> On Friday 14 Aug 2015 04:30 CEST, Arne Vajhøj wrote:
>>
>> I can see different ways of moving forward.
>>
>> 1)
>>
>> Keep those fields out of the class an update them in the database
>> via triggers.
>>
>> Possible create a view without those fields and have the entity map
>> to that instead of the table.
>>
>> 2)
>>
>> Add the fields to the class but do not expose them in its
>> public API. And let them be updated internally.
>>
>> Possible by mapping fields and either no getter/setter
>> or protected.
>>
>> 3)
>>
>> Add the fields to the entity class the normal way
>> but create a new domain class without the fields
>> and convert from entity class to domain class when
>> leaving DAL.
>
> The first option seems the best to me. (But I am not sure it is
> possible with all fields.) Is also depending on the database. The
> application uses a CISC database. I am not sure if these have this
> capability.
>
> But I think I have to use the second possibility.

CISC or CICS?

If CICS then I would expect a DB2 database behind it and that
has all the bells and whistles you may need.

Arne

[toc] | [prev] | [next] | [standalone]


#32356

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-19 11:28 +0200
Message-ID<87zj1nr5ij.fsf@Equus.decebal.nl>
In reply to#32345
On Tuesday 18 Aug 2015 01:46 CEST, Arne Vajhøj wrote:

> CISC or CICS?

I mixed hardware and software. ;-)


> If CICS then I would expect a DB2 database behind it and that
> has all the bells and whistles you may need.

The person I needed to talk to did not have time for me yet. :-(

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [prev] | [next] | [standalone]


#32358

FromCecil Westerhof <Cecil@decebal.nl>
Date2015-08-19 11:53 +0200
Message-ID<87mvxnr4e8.fsf@Equus.decebal.nl>
In reply to#32328
On Friday 14 Aug 2015 04:30 CEST, Arne Vajhøj wrote:

> On 8/13/2015 2:12 PM, Cecil Westerhof wrote:
>> I am new to JPA. I have to migrate a JDBC application to JPA. For a
>> certain class there are some extra fields in the table that are not
>> in the class itself. (For example creation time, modification time
>> and user that created the entity.) Is it possible to keep those
>> fields in the table and updated, without putting the values in the
>> class?

[…]

> 2)
>
> Add the fields to the class but do not expose them in its
> public API. And let them be updated internally.
>
> Possible by mapping fields and either no getter/setter
> or protected.

I do not need the getter fields, but I use setter fields like:
    public void setDatecreated(final Date datecreated) {
        this.datecreated = datecreated;
    }

    public void setUserIDCreated(final String userIDCreated) {
        this.userIDCreatie = userIDCreatie;
    }

    public void setTimeMutated(final Timestamp timeMutated) {
    this.tiimeMutated = timeMutated;
    }

    public void setUserIDMutated(final String userIDMutated) {
        this.userIDMutated = userIDMutated;
    }

The first two could be done in the initialisation of the entity, but
that would give a difference in functionality, so I do not opt for
that.

Another possibility would be to write the functions beforeCreate and
beforeMutate. That would be probably better as my current solution?

-- 
Cecil Westerhof
Senior Software Engineer
LinkedIn: http://www.linkedin.com/in/cecilwesterhof

[toc] | [prev] | [next] | [standalone]


Page 1 of 2  [1] 2  Next page →

Back to top | Article view | comp.lang.java.programmer


csiph-web