Not sure if DB4O provides anything like this out of the box, but could implement some kind of pessimistic lock yourself, whereby the same object either won't be returned or will be returned in a read-only mode. You'd need to maintain a list of objects being edited, and check this list each time you return your objects. But then there are problems such as users leaving and object getting stuck in 'edit mode' etc. You generally need some kind of service involving a timeout mechanism to deal with that. It can get complicated.
Or do it optimistically, e.g. let both users edit it but only save changes from the first user, and give the second user a warning when they try to save it. Usually done with a timestamp.
Edit
To provide a concrete example, this C# code provides a basic way to 'lock' an object so it isn't brought back every time. In real life it will be more complex though.
using System;
using System.Collections.Generic;
using System.Linq;
namespace ListTest
{
class Program
{
static void Main(string[] args)
{
DataAccess dataAccess = new DataAccess();
// get objects from database
List<MyThing> things = dataAccess.GetThings();
MyThing thingToWorkOn = things[things.Count-1];
printThingList(things);
// lock the object to work on
dataAccess.LockThing(thingToWorkOn);
// someone else gets the list - doesn't include thing being edited
List<MyThing> moreThings = dataAccess.GetThings();
printThingList(moreThings);
// edit the object
thingToWorkOn.Name = "Harrold";
thingToWorkOn.Name = "Harry";
// save the object and unlock it
dataAccess.Save(thingToWorkOn);
dataAccess.UnlockThing(thingToWorkOn);
// now when someone else gets the list, includes all objects
List<MyThing> evenMoreThings = dataAccess.GetThings();
printThingList(evenMoreThings);
}
static void printThingList(List<MyThing> things)
{
Console.WriteLine("* Things *");
things.ForEach(x => Console.WriteLine(x.Name));
Console.WriteLine();
}
}
// The objects you're working with. Could just use 'object' or some interface.
class MyThing : IEquatable<MyThing>
{
public string Name { get; set; }
public bool Equals(MyThing other)
{
return other.Name == this.Name;
}
}
// Class to get objects from database.
class DataAccess
{
// simple list to store 'locked' objects
private static List<MyThing> lockedThings = new List<MyThing>();
// Get all objects except the locked ones
public List<MyThing> GetThings()
{
List<MyThing> thingsFromDatabase = LoadThingsFromDatabase();
var nonLockedThings = (from thing in thingsFromDatabase
where !lockedThings.Contains(thing)
select thing
).ToList<MyThing>();
return nonLockedThings;
}
// lock an object so it can't be seen by anyone else
public void LockThing(MyThing thingToLock)
{
lockedThings.Add(thingToLock);
}
// unlock an object
public void UnlockThing(MyThing thingToLock)
{
lockedThings.Remove(thingToLock);
}
public void Save(MyThing thing)
{
// save to database
}
// dummy method to give us some objects
private List<MyThing> LoadThingsFromDatabase()
{
return new List<MyThing>() {
new MyThing(){ Name="Tom" },
new MyThing(){ Name="Dick" },
new MyThing(){ Name="Harry" }
};
}
}
}