use of org.apache.sling.api.resource.PersistenceException in project sling by apache.
the class AnnouncementRegistryImpl method checkExpiredAnnouncements.
@Override
public synchronized void checkExpiredAnnouncements() {
for (Iterator<Entry<String, CachedAnnouncement>> it = ownAnnouncementsCache.entrySet().iterator(); it.hasNext(); ) {
final Entry<String, CachedAnnouncement> entry = it.next();
if (entry.getValue().hasExpired()) {
// then we have an expiry
it.remove();
final String instanceId = entry.getKey();
logger.info("checkExpiredAnnouncements: topology connector of " + instanceId + " (to me=" + slingId + ", inherited=" + entry.getValue().getAnnouncement().isInherited() + ") has expired.");
deleteAnnouncementsOf(instanceId);
}
}
//SLING-4139 : also make sure there are no stale announcements
// in the repository (from a crash or any other action).
// The ownAnnouncementsCache is the authorative set
// of announcements that are registered to this
// instance's registry - and the repository must not
// contain any additional announcements
ResourceResolver resourceResolver = null;
boolean requiresCommit = false;
try {
resourceResolver = resourceResolverFactory.getServiceResourceResolver(null);
final Resource announcementsResource = ResourceHelper.getOrCreateResource(resourceResolver, config.getClusterInstancesPath() + "/" + slingId + "/announcements");
final Iterator<Resource> it = announcementsResource.getChildren().iterator();
while (it.hasNext()) {
final Resource res = it.next();
final String ownerId = res.getName();
if (ownAnnouncementsCache.containsKey(ownerId)) {
// fine then, we'll leave this announcement untouched
continue;
}
// otherwise this announcement is likely from an earlier incarnation
// of this instance - hence stale - hence we must remove it now
// (SLING-4139)
ResourceHelper.deleteResource(resourceResolver, res.getPath());
requiresCommit = true;
}
if (requiresCommit) {
resourceResolver.commit();
}
resourceResolver.close();
resourceResolver = null;
} catch (LoginException e) {
logger.error("checkExpiredAnnouncements: could not log in administratively when checking " + "for expired announcements of slingId=" + slingId + ": " + e, e);
} catch (PersistenceException e) {
logger.error("checkExpiredAnnouncements: got PersistenceException when checking " + "for expired announcements of slingId=" + slingId + ": " + e, e);
} finally {
if (resourceResolver != null) {
resourceResolver.revert();
resourceResolver.close();
resourceResolver = null;
}
}
}
use of org.apache.sling.api.resource.PersistenceException in project sling by apache.
the class AnnouncementRegistryImpl method registerAnnouncement.
@Override
public synchronized long registerAnnouncement(final Announcement topologyAnnouncement) {
if (topologyAnnouncement == null) {
throw new IllegalArgumentException("topologyAnnouncement must not be null");
}
if (!topologyAnnouncement.isValid()) {
logger.warn("topologyAnnouncement is not valid");
return -1;
}
if (resourceResolverFactory == null) {
logger.error("registerAnnouncement: resourceResolverFactory is null");
return -1;
}
final CachedAnnouncement cachedAnnouncement = ownAnnouncementsCache.get(topologyAnnouncement.getOwnerId());
if (cachedAnnouncement != null) {
if (logger.isDebugEnabled()) {
logger.debug("registerAnnouncement: got existing cached announcement for ownerId=" + topologyAnnouncement.getOwnerId());
}
try {
if (topologyAnnouncement.correspondsTo(cachedAnnouncement.getAnnouncement())) {
// then nothing has changed with this announcement, so just update
// the heartbeat and fine is.
// this should actually be the normal case for a stable connector
logger.debug("registerAnnouncement: nothing has changed, only updating heartbeat in-memory.");
return cachedAnnouncement.registerPing(topologyAnnouncement, config);
}
logger.debug("registerAnnouncement: incoming announcement differs from existing one!");
} catch (JsonException e) {
logger.error("registerAnnouncement: got JSONException while converting incoming announcement to JSON: " + e, e);
}
// otherwise the repository and the cache require to be updated
// resetting the cache therefore at this point already
ownAnnouncementsCache.remove(topologyAnnouncement.getOwnerId());
} else {
logger.debug("registerAnnouncement: no cached announcement yet for ownerId=" + topologyAnnouncement.getOwnerId());
}
logger.debug("registerAnnouncement: getting the list of all local announcements");
final Collection<Announcement> announcements = new LinkedList<Announcement>();
fillWithCachedAnnouncements(announcements);
if (logger.isDebugEnabled()) {
logger.debug("registerAnnouncement: list returned: " + (announcements == null ? "null" : announcements.size()));
}
for (Iterator<Announcement> it1 = announcements.iterator(); it1.hasNext(); ) {
Announcement announcement = it1.next();
if (announcement.getOwnerId().equals(topologyAnnouncement.getOwnerId())) {
// then this is from the same owner - skip this
continue;
}
// analyse to see if any of the instances in the announcement
// include the new owner
Collection<InstanceDescription> attachedInstances = announcement.listInstances();
for (Iterator<InstanceDescription> it2 = attachedInstances.iterator(); it2.hasNext(); ) {
InstanceDescription instanceDescription = it2.next();
if (topologyAnnouncement.getOwnerId().equals(instanceDescription.getSlingId())) {
logger.info("registerAnnouncement: already have this instance attached: " + instanceDescription.getSlingId());
return -1;
}
}
}
ResourceResolver resourceResolver = null;
try {
resourceResolver = resourceResolverFactory.getServiceResourceResolver(null);
final Resource announcementsResource = ResourceHelper.getOrCreateResource(resourceResolver, config.getClusterInstancesPath() + "/" + slingId + "/announcements");
topologyAnnouncement.persistTo(announcementsResource);
resourceResolver.commit();
ownAnnouncementsCache.put(topologyAnnouncement.getOwnerId(), new CachedAnnouncement(topologyAnnouncement, config));
} catch (LoginException e) {
logger.error("registerAnnouncement: could not log in administratively: " + e, e);
throw new RuntimeException("Could not log in to repository (" + e + ")", e);
} catch (PersistenceException e) {
logger.error("registerAnnouncement: got a PersistenceException: " + e, e);
throw new RuntimeException("Exception while talking to repository (" + e + ")", e);
} catch (JsonException e) {
logger.error("registerAnnouncement: got a JSONException: " + e, e);
throw new RuntimeException("Exception while converting json (" + e + ")", e);
} finally {
if (resourceResolver != null) {
resourceResolver.close();
}
}
return 0;
}
use of org.apache.sling.api.resource.PersistenceException in project sling by apache.
the class AnnouncementRegistryImpl method deleteAnnouncementsOf.
private final void deleteAnnouncementsOf(final String instanceId) {
ResourceResolver resourceResolver = null;
try {
resourceResolver = resourceResolverFactory.getServiceResourceResolver(null);
ResourceHelper.deleteResource(resourceResolver, config.getClusterInstancesPath() + "/" + slingId + "/announcements/" + instanceId);
resourceResolver.commit();
resourceResolver.close();
resourceResolver = null;
} catch (LoginException e) {
logger.error("deleteAnnouncementsOf: could not log in administratively when deleting " + "announcements of instanceId=" + instanceId + ": " + e, e);
} catch (PersistenceException e) {
logger.error("deleteAnnouncementsOf: got PersistenceException when deleting " + "announcements of instanceId=" + instanceId + ": " + e, e);
} finally {
if (resourceResolver != null) {
resourceResolver.revert();
resourceResolver.close();
resourceResolver = null;
}
}
}
use of org.apache.sling.api.resource.PersistenceException in project sling by apache.
the class AnnouncementRegistryImpl method addAllExcept.
@Override
public synchronized void addAllExcept(final Announcement target, final ClusterView clusterView, final AnnouncementFilter filter) {
ResourceResolver resourceResolver = null;
try {
resourceResolver = resourceResolverFactory.getServiceResourceResolver(null);
final Resource clusterInstancesResource = ResourceHelper.getOrCreateResource(resourceResolver, config.getClusterInstancesPath());
final Iterator<Resource> it0 = clusterInstancesResource.getChildren().iterator();
Resource announcementsResource;
while (it0.hasNext()) {
final Resource aClusterInstanceResource = it0.next();
final String instanceId = aClusterInstanceResource.getName();
//TODO: add ClusterView.contains(instanceSlingId) for convenience to next api change
if (!contains(clusterView, instanceId)) {
// (corresponds to earlier expiry-handling)
continue;
}
announcementsResource = aClusterInstanceResource.getChild("announcements");
if (announcementsResource == null) {
continue;
}
Iterator<Resource> it = announcementsResource.getChildren().iterator();
while (it.hasNext()) {
Resource anAnnouncement = it.next();
if (logger.isDebugEnabled()) {
logger.debug("addAllExcept: anAnnouncement=" + anAnnouncement);
}
Announcement topologyAnnouncement;
topologyAnnouncement = Announcement.fromJSON(anAnnouncement.adaptTo(ValueMap.class).get("topologyAnnouncement", String.class));
if (filter != null && !filter.accept(aClusterInstanceResource.getName(), topologyAnnouncement)) {
continue;
}
target.addIncomingTopologyAnnouncement(topologyAnnouncement);
}
}
// even before SLING-3389 this method only did read operations,
// hence no commit was ever necessary. The close happens in the finally block
} catch (LoginException e) {
logger.error("handleEvent: could not log in administratively: " + e, e);
throw new RuntimeException("Could not log in to repository (" + e + ")", e);
} catch (PersistenceException e) {
logger.error("handleEvent: got a PersistenceException: " + e, e);
throw new RuntimeException("Exception while talking to repository (" + e + ")", e);
} catch (JsonException e) {
logger.error("handleEvent: got a JSONException: " + e, e);
throw new RuntimeException("Exception while converting json (" + e + ")", e);
} finally {
if (resourceResolver != null) {
resourceResolver.close();
}
}
}
use of org.apache.sling.api.resource.PersistenceException in project sling by apache.
the class DistributedEventReceiver method cleanUpObsoleteEvents.
private void cleanUpObsoleteEvents() {
if (this.cleanupPeriod > 0) {
this.logger.debug("Cleaning up distributed events, removing all entries older than {} minutes.", this.cleanupPeriod);
ResourceResolver resolver = null;
try {
resolver = this.resourceResolverFactory.getServiceResourceResolver(null);
final ResourceHelper.BatchResourceRemover brr = ResourceHelper.getBatchResourceRemover(50);
final Resource baseResource = resolver.getResource(this.ownRootPath);
// sanity check - should never be null
if (baseResource != null) {
final Calendar oldDate = Calendar.getInstance();
oldDate.add(Calendar.MINUTE, -1 * this.cleanupPeriod);
// check years
final int oldYear = oldDate.get(Calendar.YEAR);
final Iterator<Resource> yearIter = baseResource.listChildren();
while (yearIter.hasNext()) {
final Resource yearResource = yearIter.next();
final int year = Integer.valueOf(yearResource.getName());
if (year < oldYear) {
brr.delete(yearResource);
} else if (year == oldYear) {
// same year - check months
final int oldMonth = oldDate.get(Calendar.MONTH) + 1;
final Iterator<Resource> monthIter = yearResource.listChildren();
while (monthIter.hasNext()) {
final Resource monthResource = monthIter.next();
final int month = Integer.valueOf(monthResource.getName());
if (month < oldMonth) {
brr.delete(monthResource);
} else if (month == oldMonth) {
// same month - check days
final int oldDay = oldDate.get(Calendar.DAY_OF_MONTH);
final Iterator<Resource> dayIter = monthResource.listChildren();
while (dayIter.hasNext()) {
final Resource dayResource = dayIter.next();
final int day = Integer.valueOf(dayResource.getName());
if (day < oldDay) {
brr.delete(dayResource);
} else if (day == oldDay) {
// same day - check hours
final int oldHour = oldDate.get(Calendar.HOUR_OF_DAY);
final Iterator<Resource> hourIter = dayResource.listChildren();
while (hourIter.hasNext()) {
final Resource hourResource = hourIter.next();
final int hour = Integer.valueOf(hourResource.getName());
if (hour < oldHour) {
brr.delete(hourResource);
} else if (hour == oldHour) {
// same hour - check minutes
final int oldMinute = oldDate.get(Calendar.MINUTE);
final Iterator<Resource> minuteIter = hourResource.listChildren();
while (minuteIter.hasNext()) {
final Resource minuteResource = minuteIter.next();
final int minute = Integer.valueOf(minuteResource.getName());
if (minute < oldMinute) {
brr.delete(minuteResource);
}
}
}
}
}
}
}
}
}
}
}
// final commit for outstanding resources
resolver.commit();
} catch (final PersistenceException pe) {
// in the case of an error, we just log this as a warning
this.logger.warn("Exception during job resource tree cleanup.", pe);
} catch (final LoginException ignore) {
this.ignoreException(ignore);
} finally {
if (resolver != null) {
resolver.close();
}
}
}
}
Aggregations