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.quotas;
019
020import static org.junit.jupiter.api.Assertions.assertEquals;
021import static org.junit.jupiter.api.Assertions.assertFalse;
022import static org.junit.jupiter.api.Assertions.assertNotNull;
023import static org.junit.jupiter.api.Assertions.assertTrue;
024import static org.mockito.Mockito.mock;
025
026import java.util.Collections;
027import java.util.HashMap;
028import java.util.Map;
029import java.util.Map.Entry;
030import org.apache.hadoop.hbase.TableName;
031import org.apache.hadoop.hbase.quotas.SpaceQuotaSnapshot.SpaceQuotaStatus;
032import org.apache.hadoop.hbase.quotas.policies.DefaultViolationPolicyEnforcement;
033import org.apache.hadoop.hbase.quotas.policies.MissingSnapshotViolationPolicyEnforcement;
034import org.apache.hadoop.hbase.quotas.policies.NoWritesViolationPolicyEnforcement;
035import org.apache.hadoop.hbase.regionserver.RegionServerServices;
036import org.apache.hadoop.hbase.testclassification.SmallTests;
037import org.junit.jupiter.api.BeforeEach;
038import org.junit.jupiter.api.Tag;
039import org.junit.jupiter.api.Test;
040
041/**
042 * Test class for {@link ActivePolicyEnforcement}.
043 */
044@Tag(SmallTests.TAG)
045public class TestActivePolicyEnforcement {
046
047  private RegionServerServices rss;
048
049  @BeforeEach
050  public void setup() {
051    rss = mock(RegionServerServices.class);
052  }
053
054  @Test
055  public void testGetter() {
056    final TableName tableName = TableName.valueOf("table");
057    Map<TableName, SpaceViolationPolicyEnforcement> map = new HashMap<>();
058    map.put(tableName, new NoWritesViolationPolicyEnforcement());
059    ActivePolicyEnforcement ape = new ActivePolicyEnforcement(map, Collections.emptyMap(), null);
060    assertEquals(map.get(tableName), ape.getPolicyEnforcement(tableName));
061  }
062
063  @Test
064  public void testNoPolicyReturnsNoopEnforcement() {
065    ActivePolicyEnforcement ape = new ActivePolicyEnforcement(new HashMap<>(),
066      Collections.emptyMap(), mock(RegionServerServices.class));
067    SpaceViolationPolicyEnforcement enforcement =
068      ape.getPolicyEnforcement(TableName.valueOf("nonexistent"));
069    assertNotNull(enforcement);
070    assertTrue(enforcement instanceof MissingSnapshotViolationPolicyEnforcement,
071      "Expected an instance of MissingSnapshotViolationPolicyEnforcement, but got "
072        + enforcement.getClass());
073  }
074
075  @Test
076  public void testNoBulkLoadChecksOnNoSnapshot() {
077    ActivePolicyEnforcement ape =
078      new ActivePolicyEnforcement(new HashMap<TableName, SpaceViolationPolicyEnforcement>(),
079        Collections.<TableName, SpaceQuotaSnapshot> emptyMap(), mock(RegionServerServices.class));
080    SpaceViolationPolicyEnforcement enforcement =
081      ape.getPolicyEnforcement(TableName.valueOf("nonexistent"));
082    assertFalse(enforcement.shouldCheckBulkLoads(), "Should not check bulkloads");
083  }
084
085  @Test
086  public void testNoQuotaReturnsSingletonPolicyEnforcement() {
087    final ActivePolicyEnforcement ape =
088      new ActivePolicyEnforcement(Collections.emptyMap(), Collections.emptyMap(), rss);
089    final TableName tableName = TableName.valueOf("my_table");
090    SpaceViolationPolicyEnforcement policyEnforcement = ape.getPolicyEnforcement(tableName);
091    // This should be the same exact instance, the singleton
092    assertTrue(policyEnforcement == MissingSnapshotViolationPolicyEnforcement.getInstance());
093    assertEquals(1, ape.getLocallyCachedPolicies().size());
094    Entry<TableName, SpaceViolationPolicyEnforcement> entry =
095      ape.getLocallyCachedPolicies().entrySet().iterator().next();
096    assertTrue(policyEnforcement == entry.getValue());
097  }
098
099  @Test
100  public void testNonViolatingQuotaCachesPolicyEnforcment() {
101    final Map<TableName, SpaceQuotaSnapshot> snapshots = new HashMap<>();
102    final TableName tableName = TableName.valueOf("my_table");
103    snapshots.put(tableName, new SpaceQuotaSnapshot(SpaceQuotaStatus.notInViolation(), 0, 1024));
104    final ActivePolicyEnforcement ape =
105      new ActivePolicyEnforcement(Collections.emptyMap(), snapshots, rss);
106    SpaceViolationPolicyEnforcement policyEnforcement = ape.getPolicyEnforcement(tableName);
107    assertTrue(policyEnforcement instanceof DefaultViolationPolicyEnforcement,
108      "Found the wrong class: " + policyEnforcement.getClass());
109    SpaceViolationPolicyEnforcement copy = ape.getPolicyEnforcement(tableName);
110    assertTrue(policyEnforcement == copy, "Expected the instance to be cached");
111    Entry<TableName, SpaceViolationPolicyEnforcement> entry =
112      ape.getLocallyCachedPolicies().entrySet().iterator().next();
113    assertTrue(policyEnforcement == entry.getValue());
114  }
115
116  @Test
117  public void testViolatingQuotaCachesNothing() {
118    final TableName tableName = TableName.valueOf("my_table");
119    SpaceViolationPolicyEnforcement policyEnforcement = mock(SpaceViolationPolicyEnforcement.class);
120    final Map<TableName, SpaceViolationPolicyEnforcement> activePolicies = new HashMap<>();
121    activePolicies.put(tableName, policyEnforcement);
122    final ActivePolicyEnforcement ape =
123      new ActivePolicyEnforcement(activePolicies, Collections.emptyMap(), rss);
124    assertTrue(ape.getPolicyEnforcement(tableName) == policyEnforcement);
125    assertEquals(0, ape.getLocallyCachedPolicies().size());
126  }
127}