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.backup.example;
019
020import java.io.IOException;
021
022import org.apache.hadoop.hbase.zookeeper.ZKWatcher;
023import org.apache.yetus.audience.InterfaceAudience;
024import org.apache.hadoop.conf.Configuration;
025import org.apache.hadoop.conf.Configured;
026import org.apache.hadoop.hbase.client.ClusterConnection;
027import org.apache.hadoop.hbase.util.Bytes;
028import org.apache.hadoop.hbase.zookeeper.ZNodePaths;
029import org.apache.zookeeper.KeeperException;
030
031/**
032 * Example class for how to use the table archiving coordinated via zookeeper
033 */
034@InterfaceAudience.Private
035public class ZKTableArchiveClient extends Configured {
036
037  /** Configuration key for the archive node. */
038  private static final String ZOOKEEPER_ZNODE_HFILE_ARCHIVE_KEY = "zookeeper.znode.hfile.archive";
039  private ClusterConnection connection;
040
041  public ZKTableArchiveClient(Configuration conf, ClusterConnection connection) {
042    super(conf);
043    this.connection = connection;
044  }
045
046  /**
047   * Turn on backups for all HFiles for the given table.
048   * <p>
049   * All deleted hfiles are moved to the archive directory under the table directory, rather than
050   * being deleted.
051   * <p>
052   * If backups are already enabled for this table, does nothing.
053   * <p>
054   * If the table does not exist, the archiving the table's hfiles is still enabled as a future
055   * table with that name may be created shortly.
056   * @param table name of the table to start backing up
057   * @throws IOException if an unexpected exception occurs
058   * @throws KeeperException if zookeeper can't be reached
059   */
060  public void enableHFileBackupAsync(final byte[] table) throws IOException, KeeperException {
061    createHFileArchiveManager().enableHFileBackup(table).stop();
062  }
063
064  /**
065   * Disable hfile backups for the given table.
066   * <p>
067   * Previously backed up files are still retained (if present).
068   * <p>
069   * Asynchronous operation - some extra HFiles may be retained, in the archive directory after
070   * disable is called, dependent on the latency in zookeeper to the servers.
071   * @param table name of the table stop backing up
072   * @throws IOException if an unexpected exception occurs
073   * @throws KeeperException if zookeeper can't be reached
074   */
075  public void disableHFileBackup(String table) throws IOException, KeeperException {
076    disableHFileBackup(Bytes.toBytes(table));
077  }
078
079  /**
080   * Disable hfile backups for the given table.
081   * <p>
082   * Previously backed up files are still retained (if present).
083   * <p>
084   * Asynchronous operation - some extra HFiles may be retained, in the archive directory after
085   * disable is called, dependent on the latency in zookeeper to the servers.
086   * @param table name of the table stop backing up
087   * @throws IOException if an unexpected exception occurs
088   * @throws KeeperException if zookeeper can't be reached
089   */
090  public void disableHFileBackup(final byte[] table) throws IOException, KeeperException {
091    createHFileArchiveManager().disableHFileBackup(table).stop();
092  }
093
094  /**
095   * Disable hfile backups for all tables.
096   * <p>
097   * Previously backed up files are still retained (if present).
098   * <p>
099   * Asynchronous operation - some extra HFiles may be retained, in the archive directory after
100   * disable is called, dependent on the latency in zookeeper to the servers.
101   * @throws IOException if an unexpected exception occurs
102   * @throws KeeperException if zookeeper can't be reached
103   */
104  public void disableHFileBackup() throws IOException, KeeperException {
105    createHFileArchiveManager().disableHFileBackup().stop();
106  }
107
108  /**
109   * Determine if archiving is enabled (but not necessarily fully propagated) for a table
110   * @param table name of the table to check
111   * @return <tt>true</tt> if it is, <tt>false</tt> otherwise
112   * @throws IOException if a connection to ZooKeeper cannot be established
113   * @throws KeeperException
114   */
115  public boolean getArchivingEnabled(byte[] table) throws IOException, KeeperException {
116    HFileArchiveManager manager = createHFileArchiveManager();
117    try {
118      return manager.isArchivingEnabled(table);
119    } finally {
120      manager.stop();
121    }
122  }
123
124  /**
125   * Determine if archiving is enabled (but not necessarily fully propagated) for a table
126   * @param table name of the table to check
127   * @return <tt>true</tt> if it is, <tt>false</tt> otherwise
128   * @throws IOException if an unexpected network issue occurs
129   * @throws KeeperException if zookeeper can't be reached
130   */
131  public boolean getArchivingEnabled(String table) throws IOException, KeeperException {
132    return getArchivingEnabled(Bytes.toBytes(table));
133  }
134
135  /**
136   * @return A new {@link HFileArchiveManager} to manage which tables' hfiles should be archived
137   *         rather than deleted.
138   * @throws KeeperException if we can't reach zookeeper
139   * @throws IOException if an unexpected network issue occurs
140   */
141  private synchronized HFileArchiveManager createHFileArchiveManager() throws KeeperException,
142      IOException {
143    return new HFileArchiveManager(this.connection, this.getConf());
144  }
145
146  /**
147   * @param conf conf to read for the base archive node
148   * @param zooKeeper zookeeper to used for building the full path
149   * @return get the znode for long-term archival of a table for
150   */
151  public static String getArchiveZNode(Configuration conf, ZKWatcher zooKeeper) {
152    return ZNodePaths.joinZNode(zooKeeper.getZNodePaths().baseZNode, conf.get(
153      ZOOKEEPER_ZNODE_HFILE_ARCHIVE_KEY, TableHFileArchiveTracker.HFILE_ARCHIVE_ZNODE_PARENT));
154  }
155}