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 */
018
019package org.apache.hadoop.hdfs.server.namenode;
020
021import org.apache.hadoop.fs.StorageType;
022import org.apache.hadoop.hdfs.util.EnumCounters;
023
024/**
025 * Counters for namespace, storage space and storage type space quota and usage.
026 */
027public class QuotaCounts {
028  // Name space and storage space counts (HDFS-7775 refactors the original disk
029  // space count to storage space counts)
030  private EnumCounters<Quota> nsSsCounts;
031  // Storage type space counts
032  private EnumCounters<StorageType> tsCounts;
033
034  public static class Builder {
035    private EnumCounters<Quota> nsSsCounts;
036    private EnumCounters<StorageType> tsCounts;
037
038    public Builder() {
039      this.nsSsCounts = new EnumCounters<Quota>(Quota.class);
040      this.tsCounts = new EnumCounters<StorageType>(StorageType.class);
041    }
042
043    public Builder nameSpace(long val) {
044      this.nsSsCounts.set(Quota.NAMESPACE, val);
045      return this;
046    }
047
048    public Builder storageSpace(long val) {
049      this.nsSsCounts.set(Quota.STORAGESPACE, val);
050      return this;
051    }
052
053    public Builder typeSpaces(EnumCounters<StorageType> val) {
054      if (val != null) {
055        this.tsCounts.set(val);
056      }
057      return this;
058    }
059
060    public Builder typeSpaces(long val) {
061      this.tsCounts.reset(val);
062      return this;
063    }
064
065    public Builder quotaCount(QuotaCounts that) {
066      this.nsSsCounts.set(that.nsSsCounts);
067      this.tsCounts.set(that.tsCounts);
068      return this;
069    }
070
071    public QuotaCounts build() {
072      return new QuotaCounts(this);
073    }
074  }
075
076  private QuotaCounts(Builder builder) {
077    this.nsSsCounts = builder.nsSsCounts;
078    this.tsCounts = builder.tsCounts;
079  }
080
081  public QuotaCounts add(QuotaCounts that) {
082    this.nsSsCounts.add(that.nsSsCounts);
083    this.tsCounts.add(that.tsCounts);
084    return this;
085  }
086
087  public QuotaCounts subtract(QuotaCounts that) {
088    this.nsSsCounts.subtract(that.nsSsCounts);
089    this.tsCounts.subtract(that.tsCounts);
090    return this;
091  }
092
093  /**
094   * Returns a QuotaCounts whose value is {@code (-this)}.
095   *
096   * @return {@code -this}
097   */
098  public QuotaCounts negation() {
099    QuotaCounts ret = new QuotaCounts.Builder().quotaCount(this).build();
100    ret.nsSsCounts.negation();
101    ret.tsCounts.negation();
102    return ret;
103  }
104
105  public long getNameSpace(){
106    return nsSsCounts.get(Quota.NAMESPACE);
107  }
108
109  public void setNameSpace(long nameSpaceCount) {
110    this.nsSsCounts.set(Quota.NAMESPACE, nameSpaceCount);
111  }
112
113  public void addNameSpace(long nsDelta) {
114    this.nsSsCounts.add(Quota.NAMESPACE, nsDelta);
115  }
116
117  public long getStorageSpace(){
118    return nsSsCounts.get(Quota.STORAGESPACE);
119  }
120
121  public void setStorageSpace(long spaceCount) {
122    this.nsSsCounts.set(Quota.STORAGESPACE, spaceCount);
123  }
124
125  public void addStorageSpace(long dsDelta) {
126    this.nsSsCounts.add(Quota.STORAGESPACE, dsDelta);
127  }
128
129  public EnumCounters<StorageType> getTypeSpaces() {
130    EnumCounters<StorageType> ret =
131        new EnumCounters<StorageType>(StorageType.class);
132    ret.set(tsCounts);
133    return ret;
134  }
135
136  void setTypeSpaces(EnumCounters<StorageType> that) {
137    if (that != null) {
138      this.tsCounts.set(that);
139    }
140  }
141
142  long getTypeSpace(StorageType type) {
143    return this.tsCounts.get(type);
144  }
145
146  void setTypeSpace(StorageType type, long spaceCount) {
147    this.tsCounts.set(type, spaceCount);
148  }
149
150  public void addTypeSpace(StorageType type, long delta) {
151    this.tsCounts.add(type, delta);
152  }
153
154  public boolean anyNsSsCountGreaterOrEqual(long val) {
155    return nsSsCounts.anyGreaterOrEqual(val);
156  }
157
158  public boolean anyTypeSpaceCountGreaterOrEqual(long val) {
159    return tsCounts.anyGreaterOrEqual(val);
160  }
161
162  @Override
163  public String toString() {
164    return "name space=" + getNameSpace() +
165        "\nstorage space=" + getStorageSpace() +
166        "\nstorage types=" + getTypeSpaces();
167  }
168
169  @Override
170  public boolean equals(Object obj) {
171    if (obj == this) {
172      return true;
173    } else if (obj == null || !(obj instanceof QuotaCounts)) {
174      return false;
175    }
176    final QuotaCounts that = (QuotaCounts)obj;
177    return this.nsSsCounts.equals(that.nsSsCounts)
178        && this.tsCounts.equals(that.tsCounts);
179  }
180
181  @Override
182  public int hashCode() {
183    assert false : "hashCode not designed";
184    return 42; // any arbitrary constant will do
185  }
186
187}