001/* 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018package org.apache.hadoop.hbase.io.hfile.bucket; 019 020import java.io.IOException; 021import java.util.concurrent.atomic.AtomicBoolean; 022import org.apache.yetus.audience.InterfaceAudience; 023import org.slf4j.Logger; 024import org.slf4j.LoggerFactory; 025 026@InterfaceAudience.Private 027public class BucketCachePersister extends Thread { 028 private final BucketCache cache; 029 private static final Logger LOG = LoggerFactory.getLogger(BucketCachePersister.class); 030 031 private AtomicBoolean shutdown = new AtomicBoolean(false); 032 033 public BucketCachePersister(BucketCache cache) { 034 super("bucket-cache-persister"); 035 this.cache = cache; 036 LOG.info("BucketCachePersister started with initial interval: {}", 037 cache.getBucketcachePersistInterval()); 038 } 039 040 public void run() { 041 try { 042 while (true) { 043 try { 044 Thread.sleep(cache.getBucketcachePersistInterval()); 045 if (cache.isCacheInconsistent()) { 046 LOG.debug("Cache is inconsistent, persisting to disk"); 047 cache.persistToFile(); 048 cache.setCacheInconsistent(false); 049 } 050 // Thread.interrupt may cause an InterruptException inside util method used for checksum 051 // calculation in persistToFile. This util currently swallows the exception, causing this 052 // thread to net get interrupt, so we added this flag to indicate the persister thread 053 // should stop. 054 if (shutdown.get()) { 055 break; 056 } 057 } catch (IOException e) { 058 LOG.warn("Exception in BucketCachePersister.", e); 059 } 060 } 061 LOG.info("Finishing cache persister thread."); 062 } catch (InterruptedException e) { 063 LOG.warn("Interrupting BucketCachePersister thread.", e); 064 } catch (Throwable e) { 065 LOG.error("Failed during persisting bucket cache to file: ", e); 066 } 067 } 068 069 public void shutdown() { 070 this.shutdown.set(true); 071 this.interrupt(); 072 } 073}