anchor.diff:  
   == Overview
   
  -A *ResourceQuota* object enumerates hard resource usage limits per project. It
  -limits the total number of a particular type of object that may be created in
  -a project, and the total amount of
  -link:compute_resources.html[compute resources]
  +A `ResourceQuota` defines constraints that limit aggregrate resource consumption
  +per project.  It can limit the quantity of objects that can be created in a project
  +by type, as well as the total amount of link:compute_resources.html[compute resources]
   that may be consumed by resources in that project.
   
  -== Usage Limits
  -
  -The following describes the set of limits that may be enforced by a
  -*ResourceQuota*.
  -
  -.Usage limits
  +== Resources managed by quota
  +
  +The following describes the set of resources that may be managed by a `ResourceQuota`.
  +
  +.Resources managed by quota
   [cols="3a,8a",options="header"]
   |===
   
   |Resource Name |Description
   
   |`cpu`
  -|Total requested cpu usage across all containers
  +|Across all pods in a non-terminal state, the sum of cpu requests cannot exceed this value.
   
   |`memory`
  -|Total requested memory usage across all containers
  -
  -|`openshift.io/imagesize` [[imagesize]]<<zero,*>>
  -|Maximum size of a single image stored in an internal registry
  -
  -|`openshift.io/imagestreamsize` [[imagestreamsize]]<<zero,*>>
  -|Maximum size of image stream's images stored in an internal registry
  -
  -|`openshift.io/projectimagessize`
  -|Maximum size of all the project's images stored in an internal registry
  +|Across all pods in a non-terminal state, the sum of memory requests cannot exceed this value.
  +
  +|`requests.cpu`
  +|Across all pods in a non-terminal state, the sum of cpu requests cannot exceed this value.
  +
  +|`requests.memory`
  +|Across all pods in a non-terminal state, the sum of memory requests cannot exceed this value.
  +
  +|`limits.cpu`
  +|Across all pods in a non-terminal state, the sum of cpu limits cannot exceed this value.
  +
  +|`limits.memory`
  +|Across all pods in a non-terminal state, the sum of memory limits cannot exceed this value.
  +
  +|`configmaps`
  +|The total number of config maps that can exist in the project.
   
   |`pods`
  -|Total number of pods
  +|The total number of pods in a non-terminal state that can exist in the project.  A pod is in a terminal state if `status.phase in (Failed, Succeeded)` is true.
   
   |`replicationcontrollers`
  -|Total number of replication controllers
  +|The total number of replication controllers that can exist in the project.
   
   |`resourcequotas`
  -|Total number of resource quotas
  +|The total number of resource quotas that can exist in the project.
   
   |`services`
  -|Total number of services
  +|The total number of services that can exist in the project.
   
   |`secrets`
  -|Total number of secrets
  +|The total number of secrets that can exist in the project.
   
   |`persistentvolumeclaims`
  -|Total number of persistent volume claims
  -|===
  -
  -[[zero]]<<imagesize,*>> The resource is not scoped to a project. Thus it will
  -always have usage equal to zero.
  +|The total number of persistent volume claims that can exist in the project.
  +|===
  +
  +== Quota Scopes
  +
  +Each quota can have an associated set of scopes.  A quota will only
  +measure usage for a resource if it matches the intersection of enumerated
  +scopes.
  +
  +Adding a scope to a quota limits the number of resources it supports
  +to those that pertain to the scope.  Specifying a resource on the quota outside
  +of the allowed set would result in a validation error.
  +
  +.Quota scopes
  +[cols="3a,8a",options="header"]
  +|===
  +
  +|Scope |Description
  +
  +|`Terminating`
  +|Match pods where `spec.activeDeadlineSeconds >= 0`
  +
  +|`NotTerminating`
  +|Match pods where `spec.activeDeadlineSeconds is nil`
  +
  +|`BestEffort`
  +|Match pods that have best effort quality of service for either `cpu` or `memory`.
  +
  +|`NotBestEffort`
  +|Match pods that do not have best effort quality of service for `cpu` and `memory`.
  +|===
  +
  +A `BestEffort` scope restricts a quota to limit the following resources:
  +
  +1. pods 
  +
  +A `Terminating`, `NotTerminating`, and `NotBestEffort` scope restricts a quota to tracking the following resources:
  +
  +1. `pods`
  +2. `memory`, `requests.memory`, `limits.memory`
  +3. `cpu`, `requests.cpu`, `limits.cpu`
   
   == Quota Enforcement
   
  
positive.code: 
  === Compute Resources: Requests vs Limits
  
  When allocating compute resources, each container may specify a request and a limit value for either CPU or memory.  The quota tracking system will only cost the request value against the quota usage.  If a resource is tracked by quota, and no request value is provided, the associated entity is rejected as part of admission into the cluster.
  
  For an example, consider the following scenarios relative to tracking quota on CPU:
  
  .Quota tracking based on container requests
  [cols="3a,3a,3a,3a,8a",options="header"]
  |===
  
  |Pod |Container |Requests[CPU] |Limits[CPU] |Result
  
  |pod-x
  |a
  |100m
  |500m
  |The quota usage is incremented 100m
  
  |pod-y
  |b
  |100m
  |none
  |The quota usage is incremented 100m
  
  |pod-y
  |c
  |none
  |500m
  |The quota usage is incremented 500m since request will default to limit.
  
  |pod-z
  |d
  |none
  |none
  |The pod is rejected since it does not enumerate a request.
  
  |===
  
  The rationale for charging quota usage for the requested amount of a resource versus the limit is the belief that a user should only be charged for what they are scheduled against in the cluster.
  
  As a consequence, the user is able to spread its usage of a resource across multiple tiers of service. Let's demonstrate this via an example with a 4 cpu quota.
  
  The quota may be allocated as follows:
  
  .Quota with Burstable resources
  [cols="3a,3a,3a,3a,3a,8a",options="header"]
  |===
  
  |Pod |Container |Requests[CPU] |Limits[CPU] |Quality of Service Tier |Quota Usage
  
  |pod-x
  |a
  |1
  |4
  |Burstable
  |1
  
  |pod-y
  |b
  |2
  |2
  |Guaranteed
  |2
  
  |pod-z
  |c
  |1
  |3
  |Burstable
  |1
  
  |===
  
  The user is restricted from using *BestEffort* CPU containers, but at any point in time, the containers on the node may consume up to 9 CPU cores over a given time period if there is no contention on the node because it
  has **Burstable** containers.  If one wants to restrict the ratio between the request and limit, it is encouraged that the user define a `*LimitRange*` with `*MaxLimitRequestRatio*` to control burst out behavior. This would in effect, let an administrator keep the difference between request and limit more in line with tracked usage if desired.
  
  == Sample Resource Quota File
  
  resource-quota.json
  ====
  ----
  {
    "apiVersion": "v1",
    "kind": "ResourceQuota",
    "metadata": {
      "name": "quota" <1>
    },
    "spec": {
      "hard": {
        "memory": "1Gi", <2>
        "cpu": "20", <3>
        "openshift.io/imagesize": "5Gi", <4>
        "openshift.io/imagestreamsize": 15Gi", <5>
        "openshift.io/projectimagessize": 40Gi", <6>
        "pods": "10", <7>
        "services": "5", <8>
        "replicationcontrollers":"5", <9>
        "resourcequotas":"1" <10>
      }
    }
  }
  ----
  <1> The name of this quota document
  <2> The total amount of memory requested across all containers may not exceed 1Gi.
  <3> The total number of CPU requested across all containers may not exceed 20 Kubernetes compute units.
  <4> The size of a single image uploaded to internal registry may not exceed 5Gi.
  <5> The size of images of single image stream stored in internal registry may not exceed 15Gi.
  <6> The total size of project's images stored in internal registry may not exceed 40Gi.
  <7> The total number of pods in the project
  <8> The total number of services in the project
  <9> The total number of replication controllers in the project
  <10> The total number of resource quota documents in the project
  ====
  
  == Create a Quota
  
negative.code: --------                      ----    ----
  cpu                           5       20
  memory                        500Mi   1Gi
  pods                          5       10
  replicationcontrollers        5       5
  resourcequotas                1       1
  services                      3       5
  ----
  
  [[configuring_quota_sync_period]]
  
  