blob: ef4a427a47c72bdfeecd06b5ff53fd1069d1b16d [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "CacheableObjectPartList.hpp"
#include <geode/CacheableString.hpp>
#include <geode/ExceptionTypes.hpp>
#include "CacheableToken.hpp"
#include "ThinClientRegion.hpp"
namespace apache {
namespace geode {
namespace client {
void CacheableObjectPartList::toData(DataOutput&) const {
// don't really care about toData() and should never get invoked
throw UnsupportedOperationException(
"CacheableObjectPartList::toData not implemented");
}
void CacheableObjectPartList::fromData(DataInput& input) {
const auto hasKeys = input.readBoolean();
int32_t len = input.readInt32();
if (len > 0) {
std::shared_ptr<CacheableKey> key;
std::shared_ptr<Cacheable> value;
std::shared_ptr<Exception> ex;
// bool isException;
int32_t keysOffset = (m_keysOffset != nullptr ? *m_keysOffset : 0);
for (int32_t index = keysOffset; index < keysOffset + len; ++index) {
if (hasKeys) {
key = std::dynamic_pointer_cast<CacheableKey>(input.readObject());
} else if (m_keys != nullptr) {
key = m_keys->operator[](index);
} else {
throw FatalInternalException(
"CacheableObjectPartList: "
"hasKeys is false and m_keys is also nullptr");
}
if (m_resultKeys != nullptr) {
m_resultKeys->push_back(key);
}
// input.readBoolean(&isException);
uint8_t byte = input.read();
if (byte == 2 /* for exception*/) {
input.advanceCursor(input.readArrayLength());
// input.readObject(exMsgPtr, true);// Changed
auto exMsg = input.readString();
if (exMsg == "org.apache.geode.security.NotAuthorizedException") {
std::string message("Authorization exception at server: ");
message += exMsg;
ex = std::make_shared<NotAuthorizedException>(message);
} else {
std::string message("Exception at remote server: ");
message += exMsg;
ex = std::make_shared<CacheServerException>(message);
}
m_exceptions->emplace(key, ex);
} else {
input.readObject(value);
std::shared_ptr<Cacheable> oldValue;
if (m_addToLocalCache) {
// for both register interest and getAll it is desired
// to overwrite an invalidated entry
// TODO: what about destroyed token? need to handle
// destroys during register interest by not creating them
// same for invalidates?
int updateCount = -1;
MapOfUpdateCounters::iterator pos = m_updateCountMap->find(key);
if (pos != m_updateCountMap->end()) {
updateCount = pos->second;
m_updateCountMap->erase(pos);
}
std::shared_ptr<VersionTag> versionTag;
GfErrType err =
m_region->putLocal("getAll", false, key, value, oldValue, true,
updateCount, m_destroyTracker, versionTag);
if (err == GF_CACHE_CONCURRENT_MODIFICATION_EXCEPTION) {
LOGDEBUG(
"CacheableObjectPartList::fromData putLocal for key [%s] failed because the cache \
already contains an entry with higher version.",
Utils::nullSafeToString(key).c_str());
}
} else {
m_region->getEntry(key, oldValue);
}
// if value has already been received via notification or put by
// another thread, then return that
if (oldValue != nullptr && !CacheableToken::isInvalid(oldValue)) {
value = oldValue;
}
if (m_values != nullptr) {
m_values->emplace(key, value);
}
}
}
if (m_keysOffset != nullptr) {
*m_keysOffset += len;
}
}
}
size_t CacheableObjectPartList::objectSize() const { return 0; }
} // namespace client
} // namespace geode
} // namespace apache