* Scripts edited within a prim will now be persisted correctly
* On restart the latest save will be restored rather than the very first dragged in scripts * Also add previously missed out database commits to separate prim inventory commit path (sigh)ThreadPoolClientBranch
parent
38991ba0e6
commit
46fe6e2f97
|
@ -167,7 +167,6 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
|
|
||||||
DataTable prims = m_primTable;
|
DataTable prims = m_primTable;
|
||||||
DataTable shapes = m_shapeTable;
|
DataTable shapes = m_shapeTable;
|
||||||
DataTable items = m_itemsTable;
|
|
||||||
|
|
||||||
string selectExp = "SceneGroupID = '" + Util.ToRawUuidString(obj) + "'";
|
string selectExp = "SceneGroupID = '" + Util.ToRawUuidString(obj) + "'";
|
||||||
lock (m_dataSet)
|
lock (m_dataSet)
|
||||||
|
@ -185,14 +184,7 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
|
|
||||||
if (persistPrimInventories)
|
if (persistPrimInventories)
|
||||||
{
|
{
|
||||||
// Remove items rows
|
RemoveItems(uuid);
|
||||||
String sql = String.Format("primID = '{0}'", uuid);
|
|
||||||
DataRow[] itemRows = items.Select(sql);
|
|
||||||
|
|
||||||
foreach (DataRow itemRow in itemRows)
|
|
||||||
{
|
|
||||||
itemRow.Delete();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Remove prim row
|
// Remove prim row
|
||||||
|
@ -203,6 +195,21 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
Commit();
|
Commit();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Remove all persisted items of the given prim.
|
||||||
|
/// The caller must acquire the necessrary synchronization locks and commit or rollback changes.
|
||||||
|
/// </summary>
|
||||||
|
private void RemoveItems(LLUUID uuid)
|
||||||
|
{
|
||||||
|
String sql = String.Format("primID = '{0}'", uuid);
|
||||||
|
DataRow[] itemRows = m_itemsTable.Select(sql);
|
||||||
|
|
||||||
|
foreach (DataRow itemRow in itemRows)
|
||||||
|
{
|
||||||
|
itemRow.Delete();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Load persisted objects from region storage.
|
/// Load persisted objects from region storage.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -1196,83 +1203,34 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
}
|
}
|
||||||
|
|
||||||
// see IRegionDatastore
|
// see IRegionDatastore
|
||||||
public void StorePrimInventory(LLUUID primID, IDictionary<LLUUID, TaskInventoryItem> items)
|
public void StorePrimInventory(LLUUID primID, ICollection<TaskInventoryItem> items)
|
||||||
{
|
{
|
||||||
if (!persistPrimInventories)
|
if (!persistPrimInventories)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
MainLog.Instance.Verbose("DATASTORE", "Entered StorePrimInventory with prim ID {0}", primID);
|
MainLog.Instance.Verbose("DATASTORE", "Persisting Prim Inventory with prim ID {0}", primID);
|
||||||
|
|
||||||
|
// For now, we're just going to crudely remove all the previous inventory items
|
||||||
|
// no matter whether they have changed or not, and replace them with the current set.
|
||||||
lock (m_dataSet)
|
lock (m_dataSet)
|
||||||
{
|
{
|
||||||
// Find all existing inventory rows for this prim
|
RemoveItems(primID);
|
||||||
DataTable dbItems = m_itemsTable;
|
|
||||||
|
|
||||||
String sql = String.Format("primID = '{0}'", primID);
|
|
||||||
DataRow[] dbItemRows = dbItems.Select(sql);
|
|
||||||
|
|
||||||
// Build structures for manipulation purposes
|
// repalce with current inventory details
|
||||||
IDictionary<String, DataRow> dbItemsToRemove = new Dictionary<String, DataRow>();
|
foreach (TaskInventoryItem newItem in items)
|
||||||
ICollection<TaskInventoryItem> itemsToAdd = new List<TaskInventoryItem>();
|
|
||||||
|
|
||||||
foreach (DataRow row in dbItemRows)
|
|
||||||
{
|
{
|
||||||
// MainLog.Instance.Verbose(
|
// MainLog.Instance.Verbose(
|
||||||
// "DATASTORE",
|
// "DATASTORE",
|
||||||
// "Found item {0}, {1} in prim id {2}",
|
// "Adding item {0}, {1} to prim ID {2}",
|
||||||
// row["name"], row["itemID"], primID);
|
// newItem.Name, newItem.ItemID, newItem.ParentPartID);
|
||||||
|
|
||||||
dbItemsToRemove.Add((String)row["itemID"], row);
|
DataRow newItemRow = m_itemsTable.NewRow();
|
||||||
}
|
|
||||||
|
|
||||||
// Eliminate rows from the deletion set which already exist for this prim's inventory
|
|
||||||
// TODO Very temporary, need to take account of simple metadata changes soon
|
|
||||||
lock (items)
|
|
||||||
{
|
|
||||||
foreach (LLUUID itemId in items.Keys)
|
|
||||||
{
|
|
||||||
String rawItemId = itemId.ToString();
|
|
||||||
|
|
||||||
if (dbItemsToRemove.ContainsKey(rawItemId))
|
|
||||||
{
|
|
||||||
// MainLog.Instance.Verbose(
|
|
||||||
// "DATASTORE",
|
|
||||||
// "Discarding item {0}, {1} from remove candidates for prim id {2}",
|
|
||||||
// items[itemId].Name, rawItemId, primID);
|
|
||||||
|
|
||||||
dbItemsToRemove.Remove(rawItemId);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
itemsToAdd.Add(items[itemId]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Delete excess rows
|
|
||||||
foreach (DataRow row in dbItemsToRemove.Values)
|
|
||||||
{
|
|
||||||
MainLog.Instance.Verbose(
|
|
||||||
"DATASTORE",
|
|
||||||
"Removing item {0}, {1} from prim ID {2}",
|
|
||||||
row["name"], row["itemID"], row["primID"]);
|
|
||||||
|
|
||||||
row.Delete();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Insert items not already present
|
|
||||||
foreach (TaskInventoryItem newItem in itemsToAdd)
|
|
||||||
{
|
|
||||||
MainLog.Instance.Verbose(
|
|
||||||
"DATASTORE",
|
|
||||||
"Adding item {0}, {1} to prim ID {2}",
|
|
||||||
newItem.Name, newItem.ItemID, newItem.ParentPartID);
|
|
||||||
|
|
||||||
DataRow newItemRow = dbItems.NewRow();
|
|
||||||
fillItemRow(newItemRow, newItem);
|
fillItemRow(newItemRow, newItem);
|
||||||
dbItems.Rows.Add(newItemRow);
|
m_itemsTable.Rows.Add(newItemRow);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Commit();
|
||||||
}
|
}
|
||||||
|
|
||||||
/***********************************************************************
|
/***********************************************************************
|
||||||
|
|
|
@ -209,7 +209,6 @@ namespace OpenSim.Framework.Data.SQLite
|
||||||
|
|
||||||
DataTable prims = ds.Tables["prims"];
|
DataTable prims = ds.Tables["prims"];
|
||||||
DataTable shapes = ds.Tables["primshapes"];
|
DataTable shapes = ds.Tables["primshapes"];
|
||||||
DataTable items = ds.Tables["primitems"];
|
|
||||||
|
|
||||||
string selectExp = "SceneGroupID = '" + Util.ToRawUuidString(obj) + "'";
|
string selectExp = "SceneGroupID = '" + Util.ToRawUuidString(obj) + "'";
|
||||||
lock (ds)
|
lock (ds)
|
||||||
|
@ -227,14 +226,7 @@ namespace OpenSim.Framework.Data.SQLite
|
||||||
|
|
||||||
if (persistPrimInventories)
|
if (persistPrimInventories)
|
||||||
{
|
{
|
||||||
// Remove items rows
|
RemoveItems(uuid);
|
||||||
String sql = String.Format("primID = '{0}'", uuid);
|
|
||||||
DataRow[] itemRows = items.Select(sql);
|
|
||||||
|
|
||||||
foreach (DataRow itemRow in itemRows)
|
|
||||||
{
|
|
||||||
itemRow.Delete();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Remove prim row
|
// Remove prim row
|
||||||
|
@ -245,6 +237,23 @@ namespace OpenSim.Framework.Data.SQLite
|
||||||
Commit();
|
Commit();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Remove all persisted items of the given prim.
|
||||||
|
/// The caller must acquire the necessrary synchronization locks and commit or rollback changes.
|
||||||
|
/// </summary>
|
||||||
|
private void RemoveItems(LLUUID uuid)
|
||||||
|
{
|
||||||
|
DataTable items = ds.Tables["primitems"];
|
||||||
|
|
||||||
|
String sql = String.Format("primID = '{0}'", uuid);
|
||||||
|
DataRow[] itemRows = items.Select(sql);
|
||||||
|
|
||||||
|
foreach (DataRow itemRow in itemRows)
|
||||||
|
{
|
||||||
|
itemRow.Delete();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Load persisted objects from region storage.
|
/// Load persisted objects from region storage.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -1251,74 +1260,36 @@ namespace OpenSim.Framework.Data.SQLite
|
||||||
}
|
}
|
||||||
|
|
||||||
// see IRegionDatastore
|
// see IRegionDatastore
|
||||||
public void StorePrimInventory(LLUUID primID, IDictionary<LLUUID, TaskInventoryItem> items)
|
public void StorePrimInventory(LLUUID primID, ICollection<TaskInventoryItem> items)
|
||||||
{
|
{
|
||||||
if (!persistPrimInventories)
|
if (!persistPrimInventories)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
MainLog.Instance.Verbose("DATASTORE", "Entered StorePrimInventory with prim ID {0}", primID);
|
MainLog.Instance.Verbose("DATASTORE", "Entered StorePrimInventory with prim ID {0}", primID);
|
||||||
|
|
||||||
|
DataTable dbItems = ds.Tables["primitems"];
|
||||||
|
|
||||||
|
// For now, we're just going to crudely remove all the previous inventory items
|
||||||
|
// no matter whether they have changed or not, and replace them with the current set.
|
||||||
lock (ds)
|
lock (ds)
|
||||||
{
|
{
|
||||||
// Find all existing inventory rows for this prim
|
RemoveItems(primID);
|
||||||
DataTable dbItems = ds.Tables["primitems"];
|
|
||||||
|
|
||||||
String sql = String.Format("primID = '{0}'", primID);
|
|
||||||
DataRow[] dbItemRows = dbItems.Select(sql);
|
|
||||||
|
|
||||||
// Build structures for manipulation purposes
|
// repalce with current inventory details
|
||||||
IDictionary<String, DataRow> dbItemsToRemove = new Dictionary<String, DataRow>();
|
foreach (TaskInventoryItem newItem in items)
|
||||||
ICollection<TaskInventoryItem> itemsToAdd
|
|
||||||
= new List<TaskInventoryItem>();
|
|
||||||
|
|
||||||
foreach (DataRow row in dbItemRows)
|
|
||||||
{
|
{
|
||||||
dbItemsToRemove.Add((String)row["itemID"], row);
|
// MainLog.Instance.Verbose(
|
||||||
}
|
// "DATASTORE",
|
||||||
|
// "Adding item {0}, {1} to prim ID {2}",
|
||||||
// Eliminate rows from the deletion set which already exist for this prim's inventory
|
// newItem.Name, newItem.ItemID, newItem.ParentPartID);
|
||||||
// TODO Very temporary, need to take account of simple metadata changes soon
|
|
||||||
lock (items)
|
|
||||||
{
|
|
||||||
foreach (LLUUID itemId in items.Keys)
|
|
||||||
{
|
|
||||||
String rawItemId = itemId.ToString();
|
|
||||||
|
|
||||||
if (dbItemsToRemove.ContainsKey(rawItemId))
|
|
||||||
{
|
|
||||||
dbItemsToRemove.Remove(rawItemId);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
itemsToAdd.Add(items[itemId]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Delete excess rows
|
|
||||||
foreach (DataRow row in dbItemsToRemove.Values)
|
|
||||||
{
|
|
||||||
MainLog.Instance.Verbose(
|
|
||||||
"DATASTORE",
|
|
||||||
"Removing item {0}, {1} from prim ID {2}",
|
|
||||||
row["name"], row["itemID"], row["primID"]);
|
|
||||||
|
|
||||||
row.Delete();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Insert items not already present
|
|
||||||
foreach (TaskInventoryItem newItem in itemsToAdd)
|
|
||||||
{
|
|
||||||
MainLog.Instance.Verbose(
|
|
||||||
"DATASTORE",
|
|
||||||
"Adding item {0}, {1} to prim ID {2}",
|
|
||||||
newItem.Name, newItem.ItemID, newItem.ParentPartID);
|
|
||||||
|
|
||||||
DataRow newItemRow = dbItems.NewRow();
|
DataRow newItemRow = dbItems.NewRow();
|
||||||
fillItemRow(newItemRow, newItem);
|
fillItemRow(newItemRow, newItem);
|
||||||
dbItems.Rows.Add(newItemRow);
|
dbItems.Rows.Add(newItemRow);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Commit();
|
||||||
}
|
}
|
||||||
|
|
||||||
/***********************************************************************
|
/***********************************************************************
|
||||||
|
|
|
@ -63,7 +63,7 @@ namespace OpenSim.Region.Environment.Interfaces
|
||||||
/// Store a prim's inventory
|
/// Store a prim's inventory
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
void StorePrimInventory(LLUUID primID, IDictionary<LLUUID, TaskInventoryItem> items);
|
void StorePrimInventory(LLUUID primID, ICollection<TaskInventoryItem> items);
|
||||||
|
|
||||||
List<SceneObjectGroup> LoadObjects(LLUUID regionUUID);
|
List<SceneObjectGroup> LoadObjects(LLUUID regionUUID);
|
||||||
|
|
||||||
|
|
|
@ -401,7 +401,10 @@ namespace OpenSim.Region.Environment.Scenes
|
||||||
{
|
{
|
||||||
if (HasInventoryChanged)
|
if (HasInventoryChanged)
|
||||||
{
|
{
|
||||||
datastore.StorePrimInventory(UUID, TaskInventory);
|
lock (TaskInventory)
|
||||||
|
{
|
||||||
|
datastore.StorePrimInventory(UUID, TaskInventory.Values);
|
||||||
|
}
|
||||||
|
|
||||||
HasInventoryChanged = false;
|
HasInventoryChanged = false;
|
||||||
}
|
}
|
||||||
|
|
|
@ -754,7 +754,7 @@ namespace OpenSim.DataStore.MSSQL
|
||||||
}
|
}
|
||||||
|
|
||||||
// see IRegionDatastore
|
// see IRegionDatastore
|
||||||
public void StorePrimInventory(LLUUID primID, IDictionary<LLUUID, TaskInventoryItem> items)
|
public void StorePrimInventory(LLUUID primID, ICollection<TaskInventoryItem> items)
|
||||||
{
|
{
|
||||||
// No implementation yet
|
// No implementation yet
|
||||||
}
|
}
|
||||||
|
|
|
@ -51,7 +51,7 @@ namespace OpenSim.DataStore.NullStorage
|
||||||
}
|
}
|
||||||
|
|
||||||
// see IRegionDatastore
|
// see IRegionDatastore
|
||||||
public void StorePrimInventory(LLUUID primID, IDictionary<LLUUID, TaskInventoryItem> items)
|
public void StorePrimInventory(LLUUID primID, ICollection<TaskInventoryItem> items)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue