In the previous example we reviewed how Transparent Persistence should be used with simple types. Let's now look how it is done with the collections.
In order to make collections TP Activatable you will need to use db4o-specific ArrayList4 collection. This collection implements .NET/Java collection interfaces, therefore it can be easily integrated with your code. The following class contains a collection of Pilot objects:
01/* Copyright (C) 2007 db4objects Inc. http://www.db4o.com */ 02
03
package com.db4odoc.tpexample; 04
05
import java.util.*; 06
07
import com.db4o.activation.*; 08
import com.db4o.collections.*; 09
import com.db4o.ta.*; 10
11
12
public class Team implements Activatable { 13
14
private List<Pilot> _pilots = new ArrayList4<Pilot>(); 15
16
String _name; 17
18
//TA Activator 19
transient Activator _activator; 20
21
// Bind the class to an object container 22
public void bind(Activator activator) { 23
if (_activator == activator) { 24
return; 25
} 26
if (activator != null && _activator != null) { 27
throw new IllegalStateException(); 28
} 29
_activator = activator; 30
} 31
32
// activate object fields 33
public void activate(ActivationPurpose purpose) { 34
if (_activator == null) return; 35
_activator.activate(purpose); 36
} 37
38
public void addPilot(Pilot pilot) { 39
// activate before adding new pilots 40
activate(ActivationPurpose.WRITE); 41
_pilots.add(pilot); 42
} 43
44
public void listAllPilots() { 45
// activate before printing the collection members 46
activate(ActivationPurpose.READ); 47
48
for (Iterator<Pilot> iter = _pilots.iterator(); iter.hasNext();) { 49
Pilot pilot = (Pilot) iter.next(); 50
System.out.println(pilot); 51
} 52
} 53
54
List<Pilot> getPilots() { 55
activate(ActivationPurpose.READ); 56
return _pilots; 57
} 58
}
You can see that except for using ArrayList4, the implementation follows the same rules as in the previous simple example.
Its usage has no surprises as well:
01private static void storeCollection() { 02
new File(DB4O_FILE_NAME).delete(); 03
ObjectContainer container = database(configureTP()); 04
if (container != null) { 05
try { 06
Team team = new Team(); 07
for (int i = 0; i < 10; i++) { 08
team.addPilot(new Pilot("Pilot #" + i)); 09
} 10
container.store(team); 11
} catch (Exception ex) { 12
ex.printStackTrace(); 13
} finally { 14
closeDatabase(); 15
} 16
} 17
}
01private static void testCollectionPersistence() { 02
storeCollection(); 03
ObjectContainer container = database(configureTP()); 04
if (container != null) { 05
try { 06
Team team = (Team) container.queryByExample(new Team()).next(); 07
// this method will activate all the members in the collection 08
Iterator<Pilot> it = team.getPilots().iterator(); 09
while (it.hasNext()){ 10
Pilot p = it.next(); 11
p.setName("Modified: " + p.getName()); 12
} 13
team.addPilot(new Pilot("New pilot")); 14
// explicitly commit to persist changes 15
container.commit(); 16
} catch (Exception ex) { 17
ex.printStackTrace(); 18
} finally { 19
// If TP changes were not committed explicitly, 20
// they would be persisted with the #close call 21
closeDatabase(); 22
} 23
} 24
// reopen the database and check the changes 25
container = database(configureTP()); 26
if (container != null) { 27
try { 28
Team team = (Team) container.queryByExample(new Team()).next(); 29
team.listAllPilots(); 30
} catch (Exception ex) { 31
ex.printStackTrace(); 32
} finally { 33
closeDatabase(); 34
} 35
} 36
}
So the only thing you should remember when using TP with collections is to use ArrayList4 instead of platform-specific collection.