Java tutorial
/** * Copyright (C) 2011-2018 Red Hat, Inc. (https://github.com/Commonjava/indy) * * Licensed 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. */ package org.commonjava.indy.core.change; import org.apache.commons.lang.StringUtils; import org.commonjava.indy.audit.ChangeSummary; import org.commonjava.indy.change.event.ArtifactStoreEnablementEvent; import org.commonjava.indy.change.event.IndyStoreErrorEvent; import org.commonjava.indy.conf.IndyConfiguration; import org.commonjava.indy.core.expire.IndySchedulerException; import org.commonjava.indy.core.expire.ScheduleManager; import org.commonjava.indy.core.expire.SchedulerEvent; import org.commonjava.indy.core.expire.SchedulerTriggerEvent; import org.commonjava.indy.data.IndyDataException; import org.commonjava.indy.data.StoreDataManager; import org.commonjava.indy.measure.annotation.Measure; import org.commonjava.indy.measure.annotation.MetricNamed; import org.commonjava.indy.model.core.ArtifactStore; import org.commonjava.indy.model.core.StoreKey; import org.commonjava.indy.model.core.io.IndyObjectMapper; import org.commonjava.maven.galley.event.EventMetadata; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import javax.enterprise.context.ApplicationScoped; import javax.enterprise.event.Observes; import javax.inject.Inject; import java.io.IOException; import static org.commonjava.indy.measure.annotation.MetricNamed.DEFAULT; @ApplicationScoped public class StoreEnablementManager { public static final String DISABLE_TIMEOUT = "Disable-Timeout"; public static final int TIMEOUT_NEVER_DISABLE = -1; public static final int TIMEOUT_USE_DEFAULT = 0; @Inject private StoreDataManager storeDataManager; @Inject private ScheduleManager scheduleManager; @Inject private IndyObjectMapper objectMapper; @Inject private IndyConfiguration config; //FIXME: Convert to using ArtifactStoreEnablementEvent. @Measure(timers = @MetricNamed(DEFAULT)) public void onStoreEnablementChange(@Observes ArtifactStoreEnablementEvent event) { if (event.isPreprocessing()) { return; } for (ArtifactStore store : event) { if (!event.isDisabling()) { try { cancelReEnablementTimeout(store.getKey()); } catch (IndySchedulerException e) { Logger logger = LoggerFactory.getLogger(getClass()); logger.error(String.format("Failed to delete re-enablement job for %s.", store.getKey()), e); } } } } // public void onStoreUpdate( @Observes ArtifactStorePostUpdateEvent event ) // { // for ( ArtifactStore store : event ) // { // if ( store.isDisabled() ) // { // String toStr = store.getMetadata( DISABLE_TIMEOUT ); // if ( isNotEmpty( toStr ) ) // { // int timeout = Integer.parseInt( toStr ); // try // { // setReEnablementTimeout( store.getKey(), timeout ); // } // catch ( IndySchedulerException e ) // { // Logger logger = LoggerFactory.getLogger( getClass() ); // logger.error( String.format( "Failed to schedule re-enablement of %s.", store.getKey() ), e ); // } // } // } //// else //// { //// try //// { //// cancelReEnablementTimeout( store.getKey() ); //// } //// catch ( IndySchedulerException e ) //// { //// Logger logger = LoggerFactory.getLogger( getClass() ); //// logger.error( String.format( "Failed to delete re-enablement job for %s.", store.getKey() ), e ); //// } //// } // } // } @Measure(timers = @MetricNamed(DEFAULT)) public void onStoreError(@Observes IndyStoreErrorEvent evt) { Logger logger = LoggerFactory.getLogger(getClass()); StoreKey key = evt.getStoreKey(); Throwable error = evt.getError(); try { ArtifactStore store = storeDataManager.getArtifactStore(key); if (store == null) { logger.warn("Attempt to disable missing repo! Skipping."); return; } store = store.copyOf(); int disableTimeout = store.getDisableTimeout(); if (disableTimeout <= TIMEOUT_NEVER_DISABLE) { logger.debug("Disable-timeout set to {}, will never disable the repo", disableTimeout); store.setDisabled(false); } else { store.setDisabled(true); final ChangeSummary changeSummary = new ChangeSummary(ChangeSummary.SYSTEM_USER, String.format("Disabling %s due to error: %s\n\nStack Trace:\n %s", key, error, StringUtils.join(error.getStackTrace(), "\n "))); storeDataManager.storeArtifactStore(store, changeSummary, false, true, new EventMetadata()); logger.warn("{} has been disabled due to store-level error: {}\n Will re-enable in {} seconds.", key, error, disableTimeout == TIMEOUT_USE_DEFAULT ? config.getStoreDisableTimeoutSeconds() : disableTimeout); // TODO: How is it this doesn't duplicate the event handler method onStoreUpdate()...we're updating the store just above here. setReEnablementTimeout(key); } } catch (IndyDataException e) { logger.error(String.format("Failed to disable %s on error: %s", key, error), e); } catch (IndySchedulerException e) { logger.error(String.format("Failed to schedule re-enablement of %s for retry.", key), e); } } @Measure(timers = @MetricNamed(DEFAULT)) public void onDisableTimeout(@Observes SchedulerEvent evt) { Logger logger = LoggerFactory.getLogger(getClass()); logger.debug("Checking for store-reenable event in: {} (trigger? {} Disable-Timeout? {})", evt, evt instanceof SchedulerTriggerEvent, DISABLE_TIMEOUT.equals(evt.getJobType())); if ((evt instanceof SchedulerTriggerEvent) && DISABLE_TIMEOUT.equals(evt.getJobType())) { String keystr = evt.getPayload(); StoreKey key = null; try { key = objectMapper.readValue(keystr, StoreKey.class); } catch (IOException e) { logger.warn("Failed to read StoreKey from JSON string: '{}' in event payload.", keystr); } logger.debug("Read key: {} from JSON string: '{}' in event payload.", key, keystr); if (key != null) { try { ArtifactStore store = storeDataManager.getArtifactStore(key); if (store == null) { logger.warn("Attempt to re-enable missing repository! Skipping."); cancelReEnablementTimeout(key); return; } store = store.copyOf(); if (store.isDisabled()) { store.setDisabled(false); storeDataManager.storeArtifactStore(store, new ChangeSummary(ChangeSummary.SYSTEM_USER, "Re-enabling " + key), false, true, new EventMetadata()); cancelReEnablementTimeout(key); } } catch (IndyDataException e) { logger.error(String.format("Failed to re-enable %s", key), e); } catch (IndySchedulerException e) { logger.error(String.format("Failed to delete re-enablement job for %s.", key), e); } } } } private void cancelReEnablementTimeout(StoreKey key) throws IndySchedulerException { Logger logger = LoggerFactory.getLogger(getClass()); logger.warn("{} has been re-enabled for use.", key); scheduleManager.deleteJob(ScheduleManager.groupName(key, DISABLE_TIMEOUT), DISABLE_TIMEOUT); } private void setReEnablementTimeout(StoreKey key) throws IndySchedulerException { Logger logger = LoggerFactory.getLogger(getClass()); logger.warn("Reschedule enabling for: {}", key); scheduleManager.rescheduleDisableTimeout(key); } }