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;
019
020import java.io.IOException;
021import java.util.Collection;
022import java.util.Collections;
023import java.util.Map;
024import java.util.Optional;
025import java.util.Set;
026import java.util.stream.Collectors;
027import java.util.stream.Stream;
028import org.apache.hadoop.fs.Path;
029import org.apache.hadoop.hbase.client.ColumnFamilyDescriptor;
030import org.apache.hadoop.hbase.client.ColumnFamilyDescriptorBuilder.ModifyableColumnFamilyDescriptor;
031import org.apache.hadoop.hbase.client.CoprocessorDescriptor;
032import org.apache.hadoop.hbase.client.CoprocessorDescriptorBuilder;
033import org.apache.hadoop.hbase.client.Durability;
034import org.apache.hadoop.hbase.client.TableDescriptor;
035import org.apache.hadoop.hbase.client.TableDescriptorBuilder;
036import org.apache.hadoop.hbase.client.TableDescriptorBuilder.ModifyableTableDescriptor;
037import org.apache.hadoop.hbase.exceptions.DeserializationException;
038import org.apache.hadoop.hbase.exceptions.HBaseException;
039import org.apache.hadoop.hbase.security.User;
040import org.apache.hadoop.hbase.util.Bytes;
041import org.apache.yetus.audience.InterfaceAudience;
042
043/**
044 * HTableDescriptor contains the details about an HBase table such as the descriptors of all the
045 * column families, is the table a catalog table, <code> hbase:meta </code>, if the table is read
046 * only, the maximum size of the memstore, when the region split should occur, coprocessors
047 * associated with it etc...
048 * @deprecated As of release 2.0.0, this will be removed in HBase 3.0.0. Use
049 *             {@link TableDescriptorBuilder} to build {@link HTableDescriptor}.
050 */
051@Deprecated
052@InterfaceAudience.Public
053public class HTableDescriptor implements TableDescriptor, Comparable<HTableDescriptor> {
054  public static final String SPLIT_POLICY = TableDescriptorBuilder.SPLIT_POLICY;
055  public static final String MAX_FILESIZE = TableDescriptorBuilder.MAX_FILESIZE;
056  public static final String OWNER = TableDescriptorBuilder.OWNER;
057  public static final Bytes OWNER_KEY = TableDescriptorBuilder.OWNER_KEY;
058  public static final String READONLY = TableDescriptorBuilder.READONLY;
059  public static final String COMPACTION_ENABLED = TableDescriptorBuilder.COMPACTION_ENABLED;
060  public static final String SPLIT_ENABLED = TableDescriptorBuilder.SPLIT_ENABLED;
061  public static final String MERGE_ENABLED = TableDescriptorBuilder.MERGE_ENABLED;
062  public static final String MEMSTORE_FLUSHSIZE = TableDescriptorBuilder.MEMSTORE_FLUSHSIZE;
063  public static final String FLUSH_POLICY = TableDescriptorBuilder.FLUSH_POLICY;
064  public static final String IS_ROOT = "IS_ROOT";
065  public static final String IS_META = TableDescriptorBuilder.IS_META;
066  public static final String DURABILITY = TableDescriptorBuilder.DURABILITY;
067  public static final String REGION_REPLICATION = TableDescriptorBuilder.REGION_REPLICATION;
068  public static final String REGION_MEMSTORE_REPLICATION =
069    TableDescriptorBuilder.REGION_MEMSTORE_REPLICATION;
070  public static final String NORMALIZATION_ENABLED = TableDescriptorBuilder.NORMALIZATION_ENABLED;
071  public static final boolean DEFAULT_NORMALIZATION_ENABLED =
072    TableDescriptorBuilder.DEFAULT_NORMALIZATION_ENABLED;
073  public static final String NORMALIZER_TARGET_REGION_COUNT =
074    TableDescriptorBuilder.NORMALIZER_TARGET_REGION_COUNT;
075  public static final String NORMALIZER_TARGET_REGION_SIZE =
076    TableDescriptorBuilder.NORMALIZER_TARGET_REGION_SIZE;
077  public static final String NORMALIZER_TARGET_REGION_SIZE_MB =
078    TableDescriptorBuilder.NORMALIZER_TARGET_REGION_SIZE_MB;
079  public static final String PRIORITY = TableDescriptorBuilder.PRIORITY;
080  public static final boolean DEFAULT_READONLY = TableDescriptorBuilder.DEFAULT_READONLY;
081  public static final boolean DEFAULT_COMPACTION_ENABLED =
082    TableDescriptorBuilder.DEFAULT_COMPACTION_ENABLED;
083  public static final long DEFAULT_MEMSTORE_FLUSH_SIZE =
084    TableDescriptorBuilder.DEFAULT_MEMSTORE_FLUSH_SIZE;
085  public static final int DEFAULT_REGION_REPLICATION =
086    TableDescriptorBuilder.DEFAULT_REGION_REPLICATION;
087  public static final boolean DEFAULT_REGION_MEMSTORE_REPLICATION =
088    TableDescriptorBuilder.DEFAULT_REGION_MEMSTORE_REPLICATION;
089
090  public static final String ERASURE_CODING_POLICY = TableDescriptorBuilder.ERASURE_CODING_POLICY;
091  protected final ModifyableTableDescriptor delegatee;
092
093  /**
094   * Construct a table descriptor specifying a TableName object
095   * @param name Table name.
096   * @see <a href="https://issues.apache.org/jira/browse/HBASE-174">HADOOP-1581 HBASE: (HBASE-174)
097   *      Un-openable tablename bug</a>
098   */
099  public HTableDescriptor(final TableName name) {
100    this(new ModifyableTableDescriptor(name));
101  }
102
103  /**
104   * Construct a table descriptor by cloning the descriptor passed as a parameter.
105   * <p>
106   * Makes a deep copy of the supplied descriptor. Can make a modifiable descriptor from an
107   * ImmutableHTableDescriptor.
108   * @param desc The descriptor.
109   */
110  public HTableDescriptor(final HTableDescriptor desc) {
111    this(desc, true);
112  }
113
114  protected HTableDescriptor(final HTableDescriptor desc, boolean deepClone) {
115    this(deepClone ? new ModifyableTableDescriptor(desc.getTableName(), desc) : desc.delegatee);
116  }
117
118  public HTableDescriptor(final TableDescriptor desc) {
119    this(new ModifyableTableDescriptor(desc.getTableName(), desc));
120  }
121
122  /**
123   * Construct a table descriptor by cloning the descriptor passed as a parameter but using a
124   * different table name.
125   * <p>
126   * Makes a deep copy of the supplied descriptor. Can make a modifiable descriptor from an
127   * ImmutableHTableDescriptor.
128   * @param name Table name.
129   * @param desc The descriptor.
130   */
131  public HTableDescriptor(final TableName name, final HTableDescriptor desc) {
132    this(new ModifyableTableDescriptor(name, desc));
133  }
134
135  protected HTableDescriptor(ModifyableTableDescriptor delegatee) {
136    this.delegatee = delegatee;
137  }
138
139  /**
140   * This is vestigial API. It will be removed in 3.0.
141   * @return always return the false
142   */
143  public boolean isRootRegion() {
144    return false;
145  }
146
147  /**
148   * Checks if this table is <code> hbase:meta </code> region.
149   * @return true if this table is <code> hbase:meta </code> region
150   */
151  @Override
152  public boolean isMetaRegion() {
153    return delegatee.isMetaRegion();
154  }
155
156  /**
157   * Checks if the table is a <code>hbase:meta</code> table
158   * @return true if table is <code> hbase:meta </code> region.
159   */
160  @Override
161  public boolean isMetaTable() {
162    return delegatee.isMetaTable();
163  }
164
165  /** Returns Getter for fetching an unmodifiable map. */
166  @Override
167  public Map<Bytes, Bytes> getValues() {
168    return delegatee.getValues();
169  }
170
171  /**
172   * Setter for storing metadata as a (key, value) pair in map
173   * @param key   The key.
174   * @param value The value. If null, removes the setting.
175   */
176  public HTableDescriptor setValue(byte[] key, byte[] value) {
177    getDelegateeForModification().setValue(key, value);
178    return this;
179  }
180
181  /*
182   * Setter for storing metadata as a (key, value) pair in map
183   * @param key The key.
184   * @param value The value. If null, removes the setting.
185   */
186  public HTableDescriptor setValue(final Bytes key, final Bytes value) {
187    getDelegateeForModification().setValue(key, value);
188    return this;
189  }
190
191  /**
192   * Setter for storing metadata as a (key, value) pair in map
193   * @param key   The key.
194   * @param value The value. If null, removes the setting.
195   */
196  public HTableDescriptor setValue(String key, String value) {
197    getDelegateeForModification().setValue(key, value);
198    return this;
199  }
200
201  /**
202   * Remove metadata represented by the key from the map
203   * @param key Key whose key and value we're to remove from HTableDescriptor parameters.
204   */
205  public void remove(final String key) {
206    getDelegateeForModification().removeValue(Bytes.toBytes(key));
207  }
208
209  /**
210   * Remove metadata represented by the key from the map
211   * @param key Key whose key and value we're to remove from HTableDescriptor parameters.
212   */
213  public void remove(Bytes key) {
214    getDelegateeForModification().removeValue(key);
215  }
216
217  /**
218   * Remove metadata represented by the key from the map
219   * @param key Key whose key and value we're to remove from HTableDescriptor parameters.
220   */
221  public void remove(final byte[] key) {
222    getDelegateeForModification().removeValue(key);
223  }
224
225  /**
226   * Check if the readOnly flag of the table is set. If the readOnly flag is set then the contents
227   * of the table can only be read from but not modified.
228   * @return true if all columns in the table should be read only
229   */
230  @Override
231  public boolean isReadOnly() {
232    return delegatee.isReadOnly();
233  }
234
235  /**
236   * Setting the table as read only sets all the columns in the table as read only. By default all
237   * tables are modifiable, but if the readOnly flag is set to true then the contents of the table
238   * can only be read but not modified.
239   * @param readOnly True if all of the columns in the table should be read only.
240   */
241  public HTableDescriptor setReadOnly(final boolean readOnly) {
242    getDelegateeForModification().setReadOnly(readOnly);
243    return this;
244  }
245
246  /**
247   * Check if the compaction enable flag of the table is true. If flag is false then no minor/major
248   * compactions will be done in real.
249   * @return true if table compaction enabled
250   */
251  @Override
252  public boolean isCompactionEnabled() {
253    return delegatee.isCompactionEnabled();
254  }
255
256  /**
257   * Setting the table compaction enable flag.
258   * @param isEnable True if enable compaction.
259   */
260  public HTableDescriptor setCompactionEnabled(final boolean isEnable) {
261    getDelegateeForModification().setCompactionEnabled(isEnable);
262    return this;
263  }
264
265  /**
266   * Sets the HDFS erasure coding policy for the table. This will be propagated to HDFS for the data
267   * dir of the table. Erasure coding is an alternative to normal replication which takes less space
268   * at the cost of locality. The policy must be available and enabled on the hdfs cluster before
269   * being set.
270   * @param policy the policy to set, or null to disable erasure coding
271   */
272  public HTableDescriptor setErasureCodingPolicy(final String policy) {
273    getDelegateeForModification().setErasureCodingPolicy(policy);
274    return this;
275  }
276
277  /**
278   * The HDFS erasure coding policy for a table. This will be set on the data dir of the table, and
279   * is an alternative to normal replication which takes less space at the cost of locality.
280   * @return the current policy, or null if undefined
281   */
282  @Override
283  public String getErasureCodingPolicy() {
284    return delegatee.getErasureCodingPolicy();
285  }
286
287  /**
288   * Check if the region split enable flag of the table is true. If flag is false then no split will
289   * be done.
290   * @return true if table region split enabled
291   */
292  @Override
293  public boolean isSplitEnabled() {
294    return delegatee.isSplitEnabled();
295  }
296
297  /**
298   * Setting the table region split enable flag.
299   * @param isEnable True if enable split.
300   */
301  public HTableDescriptor setSplitEnabled(final boolean isEnable) {
302    getDelegateeForModification().setSplitEnabled(isEnable);
303    return this;
304  }
305
306  /**
307   * Check if the region merge enable flag of the table is true. If flag is false then no merge will
308   * be done.
309   * @return true if table region merge enabled
310   */
311  @Override
312  public boolean isMergeEnabled() {
313    return delegatee.isMergeEnabled();
314  }
315
316  /**
317   * Setting the table region merge enable flag.
318   * @param isEnable True if enable merge.
319   */
320  public HTableDescriptor setMergeEnabled(final boolean isEnable) {
321    getDelegateeForModification().setMergeEnabled(isEnable);
322    return this;
323  }
324
325  /**
326   * Check if normalization enable flag of the table is true. If flag is false then no region
327   * normalizer won't attempt to normalize this table.
328   * @return true if region normalization is enabled for this table
329   */
330  @Override
331  public boolean isNormalizationEnabled() {
332    return delegatee.isNormalizationEnabled();
333  }
334
335  /**
336   * Setting the table normalization enable flag.
337   * @param isEnable True if enable normalization.
338   */
339  public HTableDescriptor setNormalizationEnabled(final boolean isEnable) {
340    getDelegateeForModification().setNormalizationEnabled(isEnable);
341    return this;
342  }
343
344  @Override
345  public int getNormalizerTargetRegionCount() {
346    return getDelegateeForModification().getNormalizerTargetRegionCount();
347  }
348
349  public HTableDescriptor setNormalizerTargetRegionCount(final int regionCount) {
350    getDelegateeForModification().setNormalizerTargetRegionCount(regionCount);
351    return this;
352  }
353
354  @Override
355  public long getNormalizerTargetRegionSize() {
356    return getDelegateeForModification().getNormalizerTargetRegionSize();
357  }
358
359  public HTableDescriptor setNormalizerTargetRegionSize(final long regionSize) {
360    getDelegateeForModification().setNormalizerTargetRegionSize(regionSize);
361    return this;
362  }
363
364  /**
365   * Sets the {@link Durability} setting for the table. This defaults to Durability.USE_DEFAULT.
366   * @param durability enum value
367   */
368  public HTableDescriptor setDurability(Durability durability) {
369    getDelegateeForModification().setDurability(durability);
370    return this;
371  }
372
373  /**
374   * Returns the durability setting for the table.
375   * @return durability setting for the table.
376   */
377  @Override
378  public Durability getDurability() {
379    return delegatee.getDurability();
380  }
381
382  /**
383   * Get the name of the table
384   */
385  @Override
386  public TableName getTableName() {
387    return delegatee.getTableName();
388  }
389
390  /**
391   * Get the name of the table as a String
392   * @return name of table as a String
393   */
394  public String getNameAsString() {
395    return delegatee.getTableName().getNameAsString();
396  }
397
398  /**
399   * This sets the class associated with the region split policy which determines when a region
400   * split should occur. The class used by default is defined in
401   * org.apache.hadoop.hbase.regionserver.RegionSplitPolicy
402   * @param clazz the class name
403   */
404  public HTableDescriptor setRegionSplitPolicyClassName(String clazz) {
405    getDelegateeForModification().setRegionSplitPolicyClassName(clazz);
406    return this;
407  }
408
409  /**
410   * This gets the class associated with the region split policy which determines when a region
411   * split should occur. The class used by default is defined in
412   * org.apache.hadoop.hbase.regionserver.RegionSplitPolicy
413   * @return the class name of the region split policy for this table. If this returns null, the
414   *         default split policy is used.
415   */
416  @Override
417  public String getRegionSplitPolicyClassName() {
418    return delegatee.getRegionSplitPolicyClassName();
419  }
420
421  /**
422   * Returns the maximum size upto which a region can grow to after which a region split is
423   * triggered. The region size is represented by the size of the biggest store file in that region.
424   * @return max hregion size for table, -1 if not set.
425   * @see #setMaxFileSize(long)
426   */
427  @Override
428  public long getMaxFileSize() {
429    return delegatee.getMaxFileSize();
430  }
431
432  /**
433   * Sets the maximum size upto which a region can grow to after which a region split is triggered.
434   * The region size is represented by the size of the biggest store file in that region, i.e. If
435   * the biggest store file grows beyond the maxFileSize, then the region split is triggered. This
436   * defaults to a value of 256 MB.
437   * <p>
438   * This is not an absolute value and might vary. Assume that a single row exceeds the maxFileSize
439   * then the storeFileSize will be greater than maxFileSize since a single row cannot be split
440   * across multiple regions
441   * </p>
442   * @param maxFileSize The maximum file size that a store file can grow to before a split is
443   *                    triggered.
444   */
445  public HTableDescriptor setMaxFileSize(long maxFileSize) {
446    getDelegateeForModification().setMaxFileSize(maxFileSize);
447    return this;
448  }
449
450  public HTableDescriptor setMaxFileSize(String maxFileSize) throws HBaseException {
451    getDelegateeForModification().setMaxFileSize(maxFileSize);
452    return this;
453  }
454
455  /**
456   * Returns the size of the memstore after which a flush to filesystem is triggered.
457   * @return memory cache flush size for each hregion, -1 if not set.
458   * @see #setMemStoreFlushSize(long)
459   */
460  @Override
461  public long getMemStoreFlushSize() {
462    return delegatee.getMemStoreFlushSize();
463  }
464
465  /**
466   * Represents the maximum size of the memstore after which the contents of the memstore are
467   * flushed to the filesystem. This defaults to a size of 64 MB.
468   * @param memstoreFlushSize memory cache flush size for each hregion
469   */
470  public HTableDescriptor setMemStoreFlushSize(long memstoreFlushSize) {
471    getDelegateeForModification().setMemStoreFlushSize(memstoreFlushSize);
472    return this;
473  }
474
475  public HTableDescriptor setMemStoreFlushSize(String memStoreFlushSize) throws HBaseException {
476    getDelegateeForModification().setMemStoreFlushSize(memStoreFlushSize);
477    return this;
478  }
479
480  /**
481   * This sets the class associated with the flush policy which determines determines the stores
482   * need to be flushed when flushing a region. The class used by default is defined in
483   * org.apache.hadoop.hbase.regionserver.FlushPolicy.
484   * @param clazz the class name
485   */
486  public HTableDescriptor setFlushPolicyClassName(String clazz) {
487    getDelegateeForModification().setFlushPolicyClassName(clazz);
488    return this;
489  }
490
491  /**
492   * This gets the class associated with the flush policy which determines the stores need to be
493   * flushed when flushing a region. The class used by default is defined in
494   * org.apache.hadoop.hbase.regionserver.FlushPolicy.
495   * @return the class name of the flush policy for this table. If this returns null, the default
496   *         flush policy is used.
497   */
498  @Override
499  public String getFlushPolicyClassName() {
500    return delegatee.getFlushPolicyClassName();
501  }
502
503  /**
504   * Adds a column family. For the updating purpose please use
505   * {@link #modifyFamily(HColumnDescriptor)} instead.
506   * @param family HColumnDescriptor of family to add.
507   */
508  public HTableDescriptor addFamily(final HColumnDescriptor family) {
509    getDelegateeForModification().setColumnFamily(family);
510    return this;
511  }
512
513  /**
514   * Modifies the existing column family.
515   * @param family HColumnDescriptor of family to update
516   * @return this (for chained invocation)
517   */
518  public HTableDescriptor modifyFamily(final HColumnDescriptor family) {
519    getDelegateeForModification().modifyColumnFamily(family);
520    return this;
521  }
522
523  /**
524   * Checks to see if this table contains the given column family
525   * @param familyName Family name or column name.
526   * @return true if the table contains the specified family name
527   */
528  public boolean hasFamily(final byte[] familyName) {
529    return delegatee.hasColumnFamily(familyName);
530  }
531
532  /**
533   * @return Name of this table and then a map of all of the column family descriptors.
534   * @see #getNameAsString()
535   */
536  @Override
537  public String toString() {
538    return delegatee.toString();
539  }
540
541  /**
542   * @return Name of this table and then a map of all of the column family descriptors (with only
543   *         the non-default column family attributes)
544   */
545  @Override
546  public String toStringCustomizedValues() {
547    return delegatee.toStringCustomizedValues();
548  }
549
550  /** Returns map of all table attributes formatted into string. */
551  public String toStringTableAttributes() {
552    return delegatee.toStringTableAttributes();
553  }
554
555  /**
556   * Compare the contents of the descriptor with another one passed as a parameter. Checks if the
557   * obj passed is an instance of HTableDescriptor, if yes then the contents of the descriptors are
558   * compared.
559   * @return true if the contents of the the two descriptors exactly match
560   * @see java.lang.Object#equals(java.lang.Object)
561   */
562  @Override
563  public boolean equals(Object obj) {
564    if (this == obj) {
565      return true;
566    }
567    if (obj instanceof HTableDescriptor) {
568      return delegatee.equals(((HTableDescriptor) obj).delegatee);
569    }
570    return false;
571  }
572
573  /**
574   * @see java.lang.Object#hashCode()
575   */
576  @Override
577  public int hashCode() {
578    return delegatee.hashCode();
579  }
580
581  // Comparable
582
583  /**
584   * Compares the descriptor with another descriptor which is passed as a parameter. This compares
585   * the content of the two descriptors and not the reference.
586   * @return 0 if the contents of the descriptors are exactly matching, 1 if there is a mismatch in
587   *         the contents
588   */
589  @Override
590  public int compareTo(final HTableDescriptor other) {
591    return TableDescriptor.COMPARATOR.compare(this, other);
592  }
593
594  /**
595   * Returns an unmodifiable collection of all the {@link HColumnDescriptor} of all the column
596   * families of the table.
597   * @deprecated since 2.0.0 and will be removed in 3.0.0. Use {@link #getColumnFamilies()} instead.
598   * @return Immutable collection of {@link HColumnDescriptor} of all the column families.
599   * @see #getColumnFamilies()
600   * @see <a href="https://issues.apache.org/jira/browse/HBASE-18008">HBASE-18008</a>
601   */
602  @Deprecated
603  public Collection<HColumnDescriptor> getFamilies() {
604    return Stream.of(delegatee.getColumnFamilies()).map(this::toHColumnDescriptor)
605      .collect(Collectors.toList());
606  }
607
608  /**
609   * Returns the configured replicas per region
610   */
611  @Override
612  public int getRegionReplication() {
613    return delegatee.getRegionReplication();
614  }
615
616  /**
617   * Sets the number of replicas per region.
618   * @param regionReplication the replication factor per region
619   */
620  public HTableDescriptor setRegionReplication(int regionReplication) {
621    getDelegateeForModification().setRegionReplication(regionReplication);
622    return this;
623  }
624
625  /**
626   * @deprecated As of release 2.0.0, this will be removed in HBase 3.0.0. Use
627   *             {@link #hasRegionMemStoreReplication()} instead
628   */
629  @Deprecated
630  public boolean hasRegionMemstoreReplication() {
631    return hasRegionMemStoreReplication();
632  }
633
634  /** Returns true if the read-replicas memstore replication is enabled. */
635  @Override
636  public boolean hasRegionMemStoreReplication() {
637    return delegatee.hasRegionMemStoreReplication();
638  }
639
640  /**
641   * @deprecated As of release 2.0.0, this will be removed in HBase 3.0.0. Use
642   *             {@link #setRegionMemStoreReplication(boolean)} instead
643   */
644  @Deprecated
645  public HTableDescriptor setRegionMemstoreReplication(boolean memstoreReplication) {
646    return setRegionMemStoreReplication(memstoreReplication);
647  }
648
649  /**
650   * Enable or Disable the memstore replication from the primary region to the replicas. The
651   * replication will be used only for meta operations (e.g. flush, compaction, ...)
652   * @param memstoreReplication true if the new data written to the primary region should be
653   *                            replicated. false if the secondaries can tollerate to have new data
654   *                            only when the primary flushes the memstore.
655   */
656  public HTableDescriptor setRegionMemStoreReplication(boolean memstoreReplication) {
657    getDelegateeForModification().setRegionMemStoreReplication(memstoreReplication);
658    return this;
659  }
660
661  public HTableDescriptor setPriority(int priority) {
662    getDelegateeForModification().setPriority(priority);
663    return this;
664  }
665
666  @Override
667  public int getPriority() {
668    return delegatee.getPriority();
669  }
670
671  /**
672   * Returns all the column family names of the current table. The map of HTableDescriptor contains
673   * mapping of family name to HColumnDescriptors. This returns all the keys of the family map which
674   * represents the column family names of the table.
675   * @return Immutable sorted set of the keys of the families.
676   * @deprecated As of release 2.0.0, this will be removed in HBase 3.0.0
677   *             (<a href="https://issues.apache.org/jira/browse/HBASE-18008">HBASE-18008</a>). Use
678   *             {@link #getColumnFamilyNames()}.
679   */
680  @Deprecated
681  public Set<byte[]> getFamiliesKeys() {
682    return delegatee.getColumnFamilyNames();
683  }
684
685  /**
686   * Returns the count of the column families of the table.
687   * @return Count of column families of the table
688   */
689  @Override
690  public int getColumnFamilyCount() {
691    return delegatee.getColumnFamilyCount();
692  }
693
694  /**
695   * Returns an array all the {@link HColumnDescriptor} of the column families of the table.
696   * @return Array of all the HColumnDescriptors of the current table
697   * @deprecated since 2.0.0 and will be removed in 3.0.0.
698   * @see #getFamilies()
699   * @see <a href="https://issues.apache.org/jira/browse/HBASE-18008">HBASE-18008</a>
700   */
701  @Deprecated
702  @Override
703  public HColumnDescriptor[] getColumnFamilies() {
704    return Stream.of(delegatee.getColumnFamilies()).map(this::toHColumnDescriptor)
705      .toArray(size -> new HColumnDescriptor[size]);
706  }
707
708  /**
709   * Returns the HColumnDescriptor for a specific column family with name as specified by the
710   * parameter column.
711   * @param column Column family name
712   * @return Column descriptor for the passed family name or the family on passed in column.
713   * @deprecated since 2.0.0 and will be removed in 3.0.0. Use {@link #getColumnFamily(byte[])}
714   *             instead.
715   * @see #getColumnFamily(byte[])
716   * @see <a href="https://issues.apache.org/jira/browse/HBASE-18008">HBASE-18008</a>
717   */
718  @Deprecated
719  public HColumnDescriptor getFamily(final byte[] column) {
720    return toHColumnDescriptor(delegatee.getColumnFamily(column));
721  }
722
723  /**
724   * Removes the HColumnDescriptor with name specified by the parameter column from the table
725   * descriptor
726   * @param column Name of the column family to be removed.
727   * @return Column descriptor for the passed family name or the family on passed in column.
728   */
729  public HColumnDescriptor removeFamily(final byte[] column) {
730    return toHColumnDescriptor(getDelegateeForModification().removeColumnFamily(column));
731  }
732
733  /**
734   * Return a HColumnDescriptor for user to keep the compatibility as much as possible.
735   * @param desc read-only ColumnFamilyDescriptor
736   * @return The older implementation of ColumnFamilyDescriptor
737   */
738  protected HColumnDescriptor toHColumnDescriptor(ColumnFamilyDescriptor desc) {
739    if (desc == null) {
740      return null;
741    } else if (desc instanceof ModifyableColumnFamilyDescriptor) {
742      return new HColumnDescriptor((ModifyableColumnFamilyDescriptor) desc);
743    } else if (desc instanceof HColumnDescriptor) {
744      return (HColumnDescriptor) desc;
745    } else {
746      return new HColumnDescriptor(new ModifyableColumnFamilyDescriptor(desc));
747    }
748  }
749
750  /**
751   * Add a table coprocessor to this table. The coprocessor type must be
752   * org.apache.hadoop.hbase.coprocessor.RegionCoprocessor. It won't check if the class can be
753   * loaded or not. Whether a coprocessor is loadable or not will be determined when a region is
754   * opened.
755   * @param className Full class name.
756   */
757  public HTableDescriptor addCoprocessor(String className) throws IOException {
758    getDelegateeForModification().setCoprocessor(className);
759    return this;
760  }
761
762  /**
763   * Add a table coprocessor to this table. The coprocessor type must be
764   * org.apache.hadoop.hbase.coprocessor.RegionCoprocessor. It won't check if the class can be
765   * loaded or not. Whether a coprocessor is loadable or not will be determined when a region is
766   * opened.
767   * @param jarFilePath Path of the jar file. If it's null, the class will be loaded from default
768   *                    classloader.
769   * @param className   Full class name.
770   * @param priority    Priority
771   * @param kvs         Arbitrary key-value parameter pairs passed into the coprocessor.
772   */
773  public HTableDescriptor addCoprocessor(String className, Path jarFilePath, int priority,
774    final Map<String, String> kvs) throws IOException {
775    getDelegateeForModification().setCoprocessor(CoprocessorDescriptorBuilder.newBuilder(className)
776      .setJarPath(jarFilePath == null ? null : jarFilePath.toString()).setPriority(priority)
777      .setProperties(kvs == null ? Collections.emptyMap() : kvs).build());
778    return this;
779  }
780
781  /**
782   * Add a table coprocessor to this table. The coprocessor type must be
783   * org.apache.hadoop.hbase.coprocessor.RegionCoprocessor. It won't check if the class can be
784   * loaded or not. Whether a coprocessor is loadable or not will be determined when a region is
785   * opened.
786   * @param specStr The Coprocessor specification all in in one String formatted so matches
787   *                {@link HConstants#CP_HTD_ATTR_VALUE_PATTERN}
788   */
789  public HTableDescriptor addCoprocessorWithSpec(final String specStr) throws IOException {
790    getDelegateeForModification().setCoprocessorWithSpec(specStr);
791    return this;
792  }
793
794  /**
795   * Check if the table has an attached co-processor represented by the name className
796   * @param classNameToMatch - Class name of the co-processor
797   * @return true of the table has a co-processor className
798   */
799  @Override
800  public boolean hasCoprocessor(String classNameToMatch) {
801    return delegatee.hasCoprocessor(classNameToMatch);
802  }
803
804  @Override
805  public Collection<CoprocessorDescriptor> getCoprocessorDescriptors() {
806    return delegatee.getCoprocessorDescriptors();
807  }
808
809  /**
810   * Remove a coprocessor from those set on the table
811   * @param className Class name of the co-processor
812   */
813  public void removeCoprocessor(String className) {
814    getDelegateeForModification().removeCoprocessor(className);
815  }
816
817  public final static String NAMESPACE_FAMILY_INFO = TableDescriptorBuilder.NAMESPACE_FAMILY_INFO;
818  public final static byte[] NAMESPACE_FAMILY_INFO_BYTES =
819    TableDescriptorBuilder.NAMESPACE_FAMILY_INFO_BYTES;
820  public final static byte[] NAMESPACE_COL_DESC_BYTES =
821    TableDescriptorBuilder.NAMESPACE_COL_DESC_BYTES;
822
823  /** Table descriptor for namespace table */
824  public static final HTableDescriptor NAMESPACE_TABLEDESC =
825    new HTableDescriptor(TableDescriptorBuilder.NAMESPACE_TABLEDESC);
826
827  /**
828   * Set the table owner.
829   * @deprecated since 0.94.1
830   * @see <a href="https://issues.apache.org/jira/browse/HBASE-6188">HBASE-6188</a>
831   */
832  @Deprecated
833  public HTableDescriptor setOwner(User owner) {
834    getDelegateeForModification().setOwner(owner);
835    return this;
836  }
837
838  /**
839   * Set the table owner.
840   * @deprecated since 0.94.1
841   * @see <a href="https://issues.apache.org/jira/browse/HBASE-6188">HBASE-6188</a>
842   */
843  // used by admin.rb:alter(table_name,*args) to update owner.
844  @Deprecated
845  public HTableDescriptor setOwnerString(String ownerString) {
846    getDelegateeForModification().setOwnerString(ownerString);
847    return this;
848  }
849
850  /**
851   * Get the table owner.
852   * @deprecated since 0.94.1
853   * @see <a href="https://issues.apache.org/jira/browse/HBASE-6188">HBASE-6188</a>
854   */
855  @Override
856  @Deprecated
857  public String getOwnerString() {
858    return delegatee.getOwnerString();
859  }
860
861  /**
862   * Returns This instance serialized with pb with pb magic prefix
863   */
864  public byte[] toByteArray() {
865    return TableDescriptorBuilder.toByteArray(delegatee);
866  }
867
868  /**
869   * Parse the serialized representation of a {@link HTableDescriptor}
870   * @param bytes A pb serialized {@link HTableDescriptor} instance with pb magic prefix
871   * @return An instance of {@link HTableDescriptor} made from <code>bytes</code>
872   * @see #toByteArray()
873   */
874  public static HTableDescriptor parseFrom(final byte[] bytes)
875    throws DeserializationException, IOException {
876    TableDescriptor desc = TableDescriptorBuilder.parseFrom(bytes);
877    if (desc instanceof ModifyableTableDescriptor) {
878      return new HTableDescriptor((ModifyableTableDescriptor) desc);
879    } else {
880      return new HTableDescriptor(desc);
881    }
882  }
883
884  /**
885   * Getter for accessing the configuration value by key
886   */
887  public String getConfigurationValue(String key) {
888    return delegatee.getValue(key);
889  }
890
891  /**
892   * Getter for fetching an unmodifiable map.
893   */
894  public Map<String, String> getConfiguration() {
895    return delegatee.getValues().entrySet().stream().collect(Collectors.toMap(
896      e -> Bytes.toString(e.getKey().get(), e.getKey().getOffset(), e.getKey().getLength()),
897      e -> Bytes.toString(e.getValue().get(), e.getValue().getOffset(), e.getValue().getLength())));
898  }
899
900  /**
901   * Setter for storing a configuration setting in map.
902   * @param key   Config key. Same as XML config key e.g. hbase.something.or.other.
903   * @param value String value. If null, removes the setting.
904   */
905  public HTableDescriptor setConfiguration(String key, String value) {
906    getDelegateeForModification().setValue(key, value);
907    return this;
908  }
909
910  /**
911   * Remove a config setting represented by the key from the map
912   */
913  public void removeConfiguration(final String key) {
914    getDelegateeForModification().removeValue(Bytes.toBytes(key));
915  }
916
917  @Override
918  public Bytes getValue(Bytes key) {
919    return delegatee.getValue(key);
920  }
921
922  @Override
923  public String getValue(String key) {
924    return delegatee.getValue(key);
925  }
926
927  @Override
928  public byte[] getValue(byte[] key) {
929    return delegatee.getValue(key);
930  }
931
932  @Override
933  public Set<byte[]> getColumnFamilyNames() {
934    return delegatee.getColumnFamilyNames();
935  }
936
937  @Override
938  public boolean hasColumnFamily(byte[] name) {
939    return delegatee.hasColumnFamily(name);
940  }
941
942  @Override
943  public ColumnFamilyDescriptor getColumnFamily(byte[] name) {
944    return delegatee.getColumnFamily(name);
945  }
946
947  protected ModifyableTableDescriptor getDelegateeForModification() {
948    return delegatee;
949  }
950
951  @Override
952  public Optional<String> getRegionServerGroup() {
953    return delegatee.getRegionServerGroup();
954  }
955}