summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndrey Kleshchev <andreykproductengine@lindenlab.com>2023-03-28 19:38:26 +0300
committerAndrey Kleshchev <andreykproductengine@lindenlab.com>2023-03-28 21:37:32 +0300
commit3bf9c78f564f0b6c4fd79163bd63c0a6c1fab7cb (patch)
treea3ff8c1df49926f26385efc6aa55f006e18b471a
parentd21a1aace63967fe62b12b71b7f683f662dfcf4a (diff)
SL-18003 Improve dupplicate prevention
Try getting lost and found
-rw-r--r--indra/newview/llaisapi.cpp46
-rw-r--r--indra/newview/llaisapi.h1
-rw-r--r--indra/newview/llinventorymodel.cpp11
-rw-r--r--indra/newview/llinventorymodelbackgroundfetch.cpp147
-rw-r--r--indra/newview/llinventorymodelbackgroundfetch.h22
-rw-r--r--indra/newview/llviewerinventory.cpp28
-rw-r--r--indra/newview/llviewerinventory.h14
7 files changed, 183 insertions, 86 deletions
diff --git a/indra/newview/llaisapi.cpp b/indra/newview/llaisapi.cpp
index 6a43c901e7..f869f1652b 100644
--- a/indra/newview/llaisapi.cpp
+++ b/indra/newview/llaisapi.cpp
@@ -445,6 +445,52 @@ void AISAPI::FetchCategoryChildren(const LLUUID &catId, ITEM_TYPE type, bool rec
EnqueueAISCommand("FetchCategoryChildren", proc);
}
+// some folders can be requested by name, like
+// animatn | bodypart | clothing | current | favorite | gesture | inbox | landmark | lsltext
+// lstndfnd | my_otfts | notecard | object | outbox | root | snapshot | sound | texture | trash
+void AISAPI::FetchCategoryChildren(const std::string &identifier, bool recursive, completion_t callback, S32 depth)
+{
+ std::string cap;
+
+ cap = getInvCap();
+ if (cap.empty())
+ {
+ LL_WARNS("Inventory") << "Inventory cap not found!" << LL_ENDL;
+ callback(LLUUID::null);
+ return;
+ }
+ std::string url = cap + std::string("/category/") + identifier + "/children";
+
+ if (recursive)
+ {
+ url += "?depth=*";
+ }
+ else
+ {
+ url += "?depth=" + std::to_string(depth);
+ }
+
+ invokationFn_t getFn = boost::bind(
+ // Humans ignore next line. It is just a cast to specify which LLCoreHttpUtil::HttpCoroutineAdapter routine overload.
+ static_cast<LLSD(LLCoreHttpUtil::HttpCoroutineAdapter::*)(LLCore::HttpRequest::ptr_t, const std::string &, LLCore::HttpOptions::ptr_t, LLCore::HttpHeaders::ptr_t)>
+ //----
+ // _1 -> httpAdapter
+ // _2 -> httpRequest
+ // _3 -> url
+ // _4 -> body
+ // _5 -> httpOptions
+ // _6 -> httpHeaders
+ (&LLCoreHttpUtil::HttpCoroutineAdapter::getAndSuspend), _1, _2, _3, _5, _6);
+
+ // get doesn't use body, can pass additional data
+ LLSD body;
+ body["depth"] = recursive ? S32_MAX : depth;
+ LLCoprocedureManager::CoProcedure_t proc(boost::bind(&AISAPI::InvokeAISCommandCoro,
+ _1, getFn, url, LLUUID::null, body, callback, FETCHCATEGORYCHILDREN));
+
+ EnqueueAISCommand("FetchCategoryChildren", proc);
+}
+
/*static*/
void AISAPI::FetchCategoryCategories(const LLUUID &catId, ITEM_TYPE type, bool recursive, completion_t callback, S32 depth)
{
diff --git a/indra/newview/llaisapi.h b/indra/newview/llaisapi.h
index dd02951cd4..d083004195 100644
--- a/indra/newview/llaisapi.h
+++ b/indra/newview/llaisapi.h
@@ -57,6 +57,7 @@ public:
static void UpdateItem(const LLUUID &itemId, const LLSD &updates, completion_t callback = completion_t());
static void FetchItem(const LLUUID &itemId, ITEM_TYPE type, completion_t callback = completion_t());
static void FetchCategoryChildren(const LLUUID &catId, ITEM_TYPE type = AISAPI::ITEM_TYPE::INVENTORY, bool recursive = false, completion_t callback = completion_t(), S32 depth = 0);
+ static void FetchCategoryChildren(const std::string &identifier, bool recursive = false, completion_t callback = completion_t(), S32 depth = 0);
static void FetchCategoryCategories(const LLUUID &catId, ITEM_TYPE type = AISAPI::ITEM_TYPE::INVENTORY, bool recursive = false, completion_t callback = completion_t(), S32 depth = 0);
static void CopyLibraryCategory(const LLUUID& sourceId, const LLUUID& destId, bool copySubfolders, completion_t callback = completion_t());
diff --git a/indra/newview/llinventorymodel.cpp b/indra/newview/llinventorymodel.cpp
index bfc7840708..9a874350bf 100644
--- a/indra/newview/llinventorymodel.cpp
+++ b/indra/newview/llinventorymodel.cpp
@@ -3453,8 +3453,8 @@ void LLInventoryModel::processUpdateCreateInventoryItem(LLMessageSystem* msg, vo
gInventoryCallbacks.fire(callback_id, item_id);
// todo: instead of unpacking message fully,
- // grab only an item_id, then fetch via AIS
- LLInventoryModelBackgroundFetch::instance().start(item_id, false);
+ // grab only an item_id, then fetch
+ LLInventoryModelBackgroundFetch::instance().scheduleItemFetch(item_id, true);
}
}
@@ -3798,10 +3798,7 @@ void LLInventoryModel::processBulkUpdateInventory(LLMessageSystem* msg, void**)
// Temporary workaround: just fetch the item using AIS to get missing fields.
// If this works fine we might want to extract ids only from the message
// then use AIS as a primary fetcher
-
- // Use AIS derectly to not reset folder's version
- // Todo: May be LLInventoryModelBackgroundFetch needs a 'forced' option
- AISAPI::FetchCategoryChildren((*cit)->getUUID(), AISAPI::INVENTORY);
+ LLInventoryModelBackgroundFetch::instance().scheduleFolderFetch((*cit)->getUUID(), true /*force, since it has changes*/);
}
for (item_array_t::iterator iit = items.begin(); iit != items.end(); ++iit)
{
@@ -3810,7 +3807,7 @@ void LLInventoryModel::processBulkUpdateInventory(LLMessageSystem* msg, void**)
// Temporary workaround: just fetch the item using AIS to get missing fields.
// If this works fine we might want to extract ids only from the message
// then use AIS as a primary fetcher
- LLInventoryModelBackgroundFetch::instance().scheduleItemFetch((*iit)->getUUID());
+ LLInventoryModelBackgroundFetch::instance().scheduleItemFetch((*iit)->getUUID(), true);
}
gInventory.notifyObservers();
diff --git a/indra/newview/llinventorymodelbackgroundfetch.cpp b/indra/newview/llinventorymodelbackgroundfetch.cpp
index 4cb4b9ee9c..a9357bfdb3 100644
--- a/indra/newview/llinventorymodelbackgroundfetch.cpp
+++ b/indra/newview/llinventorymodelbackgroundfetch.cpp
@@ -252,7 +252,7 @@ BOOL LLInventoryModelBackgroundFetch::folderFetchActive() const
void LLInventoryModelBackgroundFetch::addRequestAtFront(const LLUUID & id, bool recursive, bool is_category)
{
- ERecursionType recursion_type = recursive ? RT_RECURSIVE : RT_NONE;
+ EFetchType recursion_type = recursive ? FT_RECURSIVE : FT_DEFAULT;
if (is_category)
{
mFetchFolderQueue.push_front(FetchQueueInfo(id, recursion_type, is_category));
@@ -265,7 +265,7 @@ void LLInventoryModelBackgroundFetch::addRequestAtFront(const LLUUID & id, bool
void LLInventoryModelBackgroundFetch::addRequestAtBack(const LLUUID & id, bool recursive, bool is_category)
{
- ERecursionType recursion_type = recursive ? RT_RECURSIVE : RT_NONE;
+ EFetchType recursion_type = recursive ? FT_RECURSIVE : FT_DEFAULT;
if (is_category)
{
mFetchFolderQueue.push_back(FetchQueueInfo(id, recursion_type, is_category));
@@ -287,7 +287,7 @@ void LLInventoryModelBackgroundFetch::start(const LLUUID& id, bool recursive)
mBackgroundFetchActive = true;
mFolderFetchActive = true;
- ERecursionType recursion_type = recursive ? RT_RECURSIVE : RT_NONE;
+ EFetchType recursion_type = recursive ? FT_RECURSIVE : FT_DEFAULT;
if (id.isNull())
{
if (! mRecursiveInventoryFetchStarted)
@@ -298,7 +298,7 @@ void LLInventoryModelBackgroundFetch::start(const LLUUID& id, bool recursive)
// Not only root folder can be massive, but
// most system folders will be requested independently
// so request root folder and content separately
- mFetchFolderQueue.push_front(FetchQueueInfo(gInventory.getRootFolderID(), RT_CONTENT));
+ mFetchFolderQueue.push_front(FetchQueueInfo(gInventory.getRootFolderID(), FT_CONTENT_RECURSIVE));
}
else
{
@@ -351,32 +351,45 @@ void LLInventoryModelBackgroundFetch::start(const LLUUID& id, bool recursive)
}
}
-void LLInventoryModelBackgroundFetch::scheduleItemFetch(const LLUUID& item_id)
+void LLInventoryModelBackgroundFetch::scheduleFolderFetch(const LLUUID& cat_id, bool forced)
{
- if (mFetchItemQueue.empty() || mFetchItemQueue.front().mUUID != item_id)
+ if (AISAPI::isAvailable())
{
- mBackgroundFetchActive = true;
-
- mFetchItemQueue.push_front(FetchQueueInfo(item_id, RT_NONE, false));
+ if (mFetchFolderQueue.empty() || mFetchFolderQueue.back().mUUID != cat_id)
+ {
+ // On AIS make sure root goes to the top and follow up recursive
+ // fetches, not individual requests
+ mFetchFolderQueue.push_back(FetchQueueInfo(cat_id, forced ? FT_FORCED : FT_DEFAULT));
+ gIdleCallbacks.addFunction(&LLInventoryModelBackgroundFetch::backgroundFetchCB, NULL);
+ }
+ }
+ else if (mFetchFolderQueue.empty() || mFetchFolderQueue.front().mUUID != cat_id)
+ {
+ // Specific folder requests go to front of queue.
+ mFetchFolderQueue.push_front(FetchQueueInfo(cat_id, forced ? FT_FORCED : FT_DEFAULT));
gIdleCallbacks.addFunction(&LLInventoryModelBackgroundFetch::backgroundFetchCB, NULL);
}
}
-void LLInventoryModelBackgroundFetch::findLostItems()
+void LLInventoryModelBackgroundFetch::scheduleItemFetch(const LLUUID& item_id, bool forced)
{
- if (AISAPI::isAvailable())
- {
- LL_WARNS() << "Not implemented yet" << LL_ENDL;
- }
- else
+ if (mFetchItemQueue.empty() || mFetchItemQueue.front().mUUID != item_id)
{
mBackgroundFetchActive = true;
- mFolderFetchActive = true;
- mFetchFolderQueue.push_back(FetchQueueInfo(LLUUID::null, RT_RECURSIVE));
+
+ mFetchItemQueue.push_front(FetchQueueInfo(item_id, forced ? FT_FORCED : FT_DEFAULT, false));
gIdleCallbacks.addFunction(&LLInventoryModelBackgroundFetch::backgroundFetchCB, NULL);
}
}
+void LLInventoryModelBackgroundFetch::findLostItems()
+{
+ mBackgroundFetchActive = true;
+ mFolderFetchActive = true;
+ mFetchFolderQueue.push_back(FetchQueueInfo(LLUUID::null, FT_RECURSIVE));
+ gIdleCallbacks.addFunction(&LLInventoryModelBackgroundFetch::backgroundFetchCB, NULL);
+}
+
void LLInventoryModelBackgroundFetch::setAllFoldersFetched()
{
if (mRecursiveInventoryFetchStarted &&
@@ -449,7 +462,10 @@ void ais_simple_folder_callback(const LLUUID& inv_id)
{
LLInventoryModelBackgroundFetch::instance().incrFetchFolderCount(-1);
LLViewerInventoryCategory * cat(gInventory.getCategory(inv_id));
- if (cat) cat->setFetching(false);
+ if (cat)
+ {
+ cat->setFetching(LLViewerInventoryCategory::FETCH_NONE);
+ }
}
void ais_simple_item_callback(const LLUUID& inv_id)
@@ -457,24 +473,24 @@ void ais_simple_item_callback(const LLUUID& inv_id)
LLInventoryModelBackgroundFetch::instance().incrFetchCount(-1);
}
-void LLInventoryModelBackgroundFetch::onAISFodlerCalback(const LLUUID &request_id, const LLUUID &response_id, ERecursionType recursion)
+void LLInventoryModelBackgroundFetch::onAISFodlerCalback(const LLUUID &request_id, const LLUUID &response_id, EFetchType recursion)
{
incrFetchFolderCount(-1);
if (response_id.isNull()) // Failure
{
- if (recursion == RT_RECURSIVE)
+ if (recursion == FT_RECURSIVE)
{
// A full recursive request failed.
// Try requesting folder and nested content separately
mBackgroundFetchActive = true;
mFolderFetchActive = true;
- mFetchFolderQueue.push_front(FetchQueueInfo(request_id, RT_CONTENT));
+ mFetchFolderQueue.push_front(FetchQueueInfo(request_id, FT_CONTENT_RECURSIVE));
gIdleCallbacks.addFunction(&LLInventoryModelBackgroundFetch::backgroundFetchCB, NULL);
}
}
else
{
- if (recursion == RT_CONTENT)
+ if (recursion == FT_CONTENT_RECURSIVE)
{
// Got the folder, now recursively request content
LLInventoryModel::cat_array_t * categories(NULL);
@@ -484,7 +500,7 @@ void LLInventoryModelBackgroundFetch::onAISFodlerCalback(const LLUUID &request_i
it != categories->end();
++it)
{
- mFetchFolderQueue.push_front(FetchQueueInfo((*it)->getUUID(), RT_RECURSIVE));
+ mFetchFolderQueue.push_front(FetchQueueInfo((*it)->getUUID(), FT_RECURSIVE));
}
if (!mFetchFolderQueue.empty())
{
@@ -499,7 +515,7 @@ void LLInventoryModelBackgroundFetch::onAISFodlerCalback(const LLUUID &request_i
LLViewerInventoryCategory * cat(gInventory.getCategory(request_id));
if (cat)
{
- cat->setFetching(false);
+ cat->setFetching(LLViewerInventoryCategory::FETCH_NONE);
}
}
@@ -561,12 +577,11 @@ void LLInventoryModelBackgroundFetch::bulkFetchViaAis(const FetchQueueInfo& fetc
if (fetch_info.mIsCategory)
{
const LLUUID & cat_id(fetch_info.mUUID);
- if (cat_id.isNull()) // Lost and found
+ if (cat_id.isNull())
{
- LL_WARNS() << "Lost and found not implemented yet" << LL_ENDL;
- // todo: needs to be requested from ais in special manner?
- /*AISAPI::FetchCategoryChildren(LLUUID::null, AISAPI::INVENTORY, false, ais_simple_callback);
- incrFetchFolderCount(1);*/
+ // Lost and found
+ AISAPI::FetchCategoryChildren("lstndfnd", true, ais_simple_folder_callback);
+ incrFetchFolderCount(1);
}
else
{
@@ -574,32 +589,42 @@ void LLInventoryModelBackgroundFetch::bulkFetchViaAis(const FetchQueueInfo& fetc
LLViewerInventoryCategory * cat(gInventory.getCategory(cat_id));
if (cat)
{
- if (LLViewerInventoryCategory::VERSION_UNKNOWN == cat->getVersion())
+ if (LLViewerInventoryCategory::VERSION_UNKNOWN == cat->getVersion() || fetch_info.mFetchType == FT_FORCED)
{
- if (ALEXANDRIA_LINDEN_ID == cat->getOwnerID())
- {
- AISAPI::FetchCategoryChildren(cat->getUUID(), AISAPI::LIBRARY, fetch_info.mRecursive == RT_RECURSIVE, ais_simple_folder_callback);
- }
- else
+ LLViewerInventoryCategory::EFetchType target_state =
+ fetch_info.mFetchType >= FT_CONTENT_RECURSIVE
+ ? LLViewerInventoryCategory::FETCH_RECURSIVE
+ : LLViewerInventoryCategory::FETCH_NORMAL;
+ // start again if we did a non-recursive fetch before
+ if (cat->getFetching() < target_state)
{
- LLUUID cat_id = cat->getUUID();
- ERecursionType type = fetch_info.mRecursive;
- AISAPI::FetchCategoryChildren(
- cat_id,
- AISAPI::INVENTORY,
- type == RT_RECURSIVE,
- [cat_id, type](const LLUUID &response_id)
+
+ if (ALEXANDRIA_LINDEN_ID == cat->getOwnerID())
{
- LLInventoryModelBackgroundFetch::instance().onAISFodlerCalback(cat_id, response_id, type);
- });
+ AISAPI::FetchCategoryChildren(cat->getUUID(), AISAPI::LIBRARY, fetch_info.mFetchType == FT_RECURSIVE, ais_simple_folder_callback);
+ }
+ else
+ {
+ LLUUID cat_id = cat->getUUID();
+ EFetchType type = fetch_info.mFetchType;
+ AISAPI::FetchCategoryChildren(
+ cat_id,
+ AISAPI::INVENTORY,
+ type == FT_RECURSIVE,
+ [cat_id, type](const LLUUID &response_id)
+ {
+ LLInventoryModelBackgroundFetch::instance().onAISFodlerCalback(cat_id, response_id, type);
+ });
+ }
+ incrFetchFolderCount(1);
+
+ cat->setFetching(target_state);
}
- incrFetchFolderCount(1);
- cat->setFetching(true);
}
else
{
// Already fetched, check if anything inside needs fetching
- if (fetch_info.mRecursive)
+ if (fetch_info.mFetchType >= FT_CONTENT_RECURSIVE)
{
LLInventoryModel::cat_array_t * categories(NULL);
LLInventoryModel::item_array_t * items(NULL);
@@ -609,7 +634,7 @@ void LLInventoryModelBackgroundFetch::bulkFetchViaAis(const FetchQueueInfo& fetc
++it)
{
// not push_front to not cause an infinite loop
- mFetchFolderQueue.push_back(FetchQueueInfo((*it)->getUUID(), fetch_info.mRecursive));
+ mFetchFolderQueue.push_back(FetchQueueInfo((*it)->getUUID(), fetch_info.mFetchType));
}
}
}
@@ -622,21 +647,25 @@ void LLInventoryModelBackgroundFetch::bulkFetchViaAis(const FetchQueueInfo& fetc
if (itemp)
{
- if (itemp->getPermissions().getOwner() == gAgent.getID())
- {
- AISAPI::FetchItem(fetch_info.mUUID, AISAPI::INVENTORY, ais_simple_item_callback);
- }
- else
+ if (!itemp->isFinished() || fetch_info.mFetchType == FT_FORCED)
{
- AISAPI::FetchItem(fetch_info.mUUID, AISAPI::LIBRARY, ais_simple_item_callback);
+ if (itemp->getPermissions().getOwner() == gAgent.getID())
+ {
+ AISAPI::FetchItem(fetch_info.mUUID, AISAPI::INVENTORY, ais_simple_item_callback);
+ }
+ else
+ {
+ AISAPI::FetchItem(fetch_info.mUUID, AISAPI::LIBRARY, ais_simple_item_callback);
+ }
+ mFetchCount++;
}
}
- else
+ else // We don't know it, assume incomplete
{
// Assume agent's inventory, library wouldn't have gotten here
AISAPI::FetchItem(fetch_info.mUUID, AISAPI::INVENTORY, ais_simple_item_callback);
+ mFetchCount++;
}
- mFetchCount++;
}
}
@@ -736,7 +765,7 @@ void LLInventoryModelBackgroundFetch::bulkFetch()
else
{
// May already have this folder, but append child folders to list.
- if (fetch_info.mRecursive)
+ if (fetch_info.mFetchType >= FT_CONTENT_RECURSIVE)
{
LLInventoryModel::cat_array_t * categories(NULL);
LLInventoryModel::item_array_t * items(NULL);
@@ -745,13 +774,13 @@ void LLInventoryModelBackgroundFetch::bulkFetch()
it != categories->end();
++it)
{
- mFetchFolderQueue.push_back(FetchQueueInfo((*it)->getUUID(), fetch_info.mRecursive));
+ mFetchFolderQueue.push_back(FetchQueueInfo((*it)->getUUID(), fetch_info.mFetchType));
}
}
}
}
}
- if (fetch_info.mRecursive)
+ if (fetch_info.mFetchType >= FT_CONTENT_RECURSIVE)
{
recursive_cats.push_back(cat_id);
}
diff --git a/indra/newview/llinventorymodelbackgroundfetch.h b/indra/newview/llinventorymodelbackgroundfetch.h
index 6a8b616a82..eae2ba6af8 100644
--- a/indra/newview/llinventorymodelbackgroundfetch.h
+++ b/indra/newview/llinventorymodelbackgroundfetch.h
@@ -47,10 +47,11 @@ class LLInventoryModelBackgroundFetch : public LLSingleton<LLInventoryModelBackg
~LLInventoryModelBackgroundFetch();
public:
- // Start background breadth-first fetching of inventory contents.
+ // Start background breadth-first fetching of inventory contents.
// This gets triggered when performing a filter-search.
void start(const LLUUID& cat_id = LLUUID::null, bool recursive = true);
- void scheduleItemFetch(const LLUUID& item_id);
+ void scheduleFolderFetch(const LLUUID& cat_id, bool forced = false);
+ void scheduleItemFetch(const LLUUID& item_id, bool forced = false);
BOOL folderFetchActive() const;
bool isEverythingFetched() const; // completing the fetch once per session should be sufficient
@@ -80,25 +81,26 @@ public:
protected:
typedef enum {
- RT_NONE = 0,
- RT_CONTENT, // request content recursively
- RT_RECURSIVE, // request everything recursively
- } ERecursionType;
+ FT_DEFAULT = 0,
+ FT_FORCED, // request even if already loaded
+ FT_CONTENT_RECURSIVE, // request content recursively
+ FT_RECURSIVE, // request everything recursively
+ } EFetchType;
struct FetchQueueInfo
{
- FetchQueueInfo(const LLUUID& id, ERecursionType recursive, bool is_category = true)
+ FetchQueueInfo(const LLUUID& id, EFetchType recursive, bool is_category = true)
: mUUID(id),
mIsCategory(is_category),
- mRecursive(recursive)
+ mFetchType(recursive)
{}
LLUUID mUUID;
bool mIsCategory;
- ERecursionType mRecursive;
+ EFetchType mFetchType;
};
typedef std::deque<FetchQueueInfo> fetch_queue_t;
- void onAISFodlerCalback(const LLUUID &request_id, const LLUUID &response_id, ERecursionType recursion);
+ void onAISFodlerCalback(const LLUUID &request_id, const LLUUID &response_id, EFetchType recursion);
void bulkFetchViaAis();
void bulkFetchViaAis(const FetchQueueInfo& fetch_info);
void bulkFetch();
diff --git a/indra/newview/llviewerinventory.cpp b/indra/newview/llviewerinventory.cpp
index 6f62ba5409..8ec7719ade 100644
--- a/indra/newview/llviewerinventory.cpp
+++ b/indra/newview/llviewerinventory.cpp
@@ -561,7 +561,8 @@ LLViewerInventoryCategory::LLViewerInventoryCategory(const LLUUID& uuid,
LLInventoryCategory(uuid, parent_uuid, pref, name),
mOwnerID(owner_id),
mVersion(LLViewerInventoryCategory::VERSION_UNKNOWN),
- mDescendentCount(LLViewerInventoryCategory::DESCENDENT_COUNT_UNKNOWN)
+ mDescendentCount(LLViewerInventoryCategory::DESCENDENT_COUNT_UNKNOWN),
+ mFetching(FETCH_NONE)
{
mDescendentsRequested.reset();
}
@@ -569,7 +570,8 @@ LLViewerInventoryCategory::LLViewerInventoryCategory(const LLUUID& uuid,
LLViewerInventoryCategory::LLViewerInventoryCategory(const LLUUID& owner_id) :
mOwnerID(owner_id),
mVersion(LLViewerInventoryCategory::VERSION_UNKNOWN),
- mDescendentCount(LLViewerInventoryCategory::DESCENDENT_COUNT_UNKNOWN)
+ mDescendentCount(LLViewerInventoryCategory::DESCENDENT_COUNT_UNKNOWN),
+ mFetching(FETCH_NONE)
{
mDescendentsRequested.reset();
}
@@ -670,21 +672,33 @@ bool LLViewerInventoryCategory::fetch()
return false;
}
-void LLViewerInventoryCategory::setFetching(bool fetching)
+LLViewerInventoryCategory::EFetchType LLViewerInventoryCategory::getFetching()
{
- if (fetching)
+ // if timer hasn't expired, request was scheduled, but not in progress
+ // if mFetching request was actually started
+ if (mDescendentsRequested.hasExpired())
{
- if ((VERSION_UNKNOWN == getVersion())
- && mDescendentsRequested.hasExpired())
+ mFetching = FETCH_NONE;
+ }
+ return mFetching;
+}
+
+void LLViewerInventoryCategory::setFetching(LLViewerInventoryCategory::EFetchType fetching)
+{
+ if (fetching > mFetching) // allow a switch from normal to recursive
+ {
+ if (mDescendentsRequested.hasExpired() || (mFetching == FETCH_NONE))
{
const F32 FETCH_TIMER_EXPIRY = 10.0f;
mDescendentsRequested.reset();
mDescendentsRequested.setTimerExpirySec(FETCH_TIMER_EXPIRY);
}
+ mFetching = fetching;
}
- else
+ else if (fetching = FETCH_NONE)
{
mDescendentsRequested.stop();
+ mFetching = fetching;
}
}
diff --git a/indra/newview/llviewerinventory.h b/indra/newview/llviewerinventory.h
index 2ae2cebe5c..95a4c84999 100644
--- a/indra/newview/llviewerinventory.h
+++ b/indra/newview/llviewerinventory.h
@@ -209,10 +209,17 @@ public:
S32 getVersion() const;
void setVersion(S32 version);
- // Returns true if a fetch was issued.
+ // Returns true if a fetch was issued (not nessesary in progress).
bool fetch();
- // Returns true if a fetch was issued.
- void setFetching(bool);
+
+ typedef enum {
+ FETCH_NONE = 0,
+ FETCH_NORMAL,
+ FETCH_RECURSIVE,
+ } EFetchType;
+ EFetchType getFetching();
+ // marks as fetch being in progress or as done
+ void setFetching(EFetchType);
// used to help make caching more robust - for example, if
// someone is getting 4 packets but logs out after 3. the viewer
@@ -242,6 +249,7 @@ protected:
LLUUID mOwnerID;
S32 mVersion;
S32 mDescendentCount;
+ EFetchType mFetching;
LLFrameTimer mDescendentsRequested;
};