---
# System prepended metadata

title: Partition and Queue 配置
tags: [筆記, Yunikorn]

---

# Partition and Queue 配置
queue 基礎配置在[其他官方文檔](https://yunikorn.apache.org/docs/design/scheduler_configuration/)講到

在此部分將提及一些通用的 queue 的配置，這會需要[Access Control Lists](https://yunikorn.apache.org/docs/user_guide/acls/) 與 [Placement rules](https://yunikorn.apache.org/docs/user_guide/placement_rules/) 的知識
除此之外，這裡解釋了如何創建 partition 及 queue 配置該怎麼修改，以符合 schedler

有關 scheduler 是如何取得 user 或 group 的資訊的，請參考[其他文檔筆記](/@ntcu-k8s/Hki5A6lMR)

## 配置
在這邊提及的 scheduler 配置文件只著重描述 partition 及 queue 的配置

預設值為 `queue.yaml` ，此部分可以在 ConfigMap 的 `service.policyGroup` 中更改

`queue.yaml` 預設值可參考[github 原始碼](https://github.com/apache/yunikorn-core/blob/master/config/queues.yaml)

## Partitions
Partitions 是 scheduler 配置裡最高層級的屬性，可同時存在多個 partition 的配置
配置的基本架構如下：
```yaml
partitions:
  - name: <name of the 1st partition>
  - name: <name of the 2nd partition>
```
預設的 partition 名稱為 `default`， partition 內的定義包含了「每一部份 shim 的 scheduler」所需的所有配置

partition 至少需要以下兩個屬性：
- name
- queue

queue 的配置將在之後提及

對於以下的屬性則非必須：
- placementrules
- limits
- nodesortpolicy
- preemption

上兩個屬性在之後會提及
對於 `nodesortpolicy` 則可參考 [官方文檔](https://yunikorn.apache.org/docs/user_guide/sorting_policies/#node-sorting)
而 `preemption` 是在設定「在此 partition 上，是否允許 preemption 的動作」，此預設值為 `true`

以下為一個 `nodesortpolicy` 為 *fair* 且不允許 preemption 的 partition 配置範例
```yaml
partitions:
  - name: <name of the partition>
    nodesortpolicy: fair
    preemption:
      enabled: false
```

:::danger
注意：
目前 k8s 唯一的 shim 不支援 `default` 以外的任何其他 partition
[參考](https://issues.apache.org/jira/browse/YUNIKORN-22)
:::

## Queue
Yunikorn 以 resource queue 來管理資源， resource queue 有以下的特性：
- queue 有階層式的架構
- queue 可預設**最小**需要的資源及**最大**會使用資源上限
- task 只能在 leaf queue 上執行
- queue 有**靜態**(配置文件)及**動態**(Yunikorn 內部管理)兩種狀態
- queue 層級的資源公平性由 scheduler 強制執行(is enforced by the scheduler)
- job 只能在特定 queue 下執行

> INFO:
> Yunikorn queue 與 k8s namespace 的差別：
> - k8s NS 的資源被其以下的 object 使用
> - queue 的資源基於內部 jobs 的資源使用
> 
> 這使得 Yunikron queue 擁有更細顆粒的資源管理

### 配置架構
queues 是主要的配置屬性，它可以定義一個階層式的架構給 queues

對於 `root` 的 queue 配置是選擇性的，但為了確保一致性， Yunikorn 會在以下情況插入 `root` 的 queue：
- 在最高層級有多於一個的 queue 定義
- 最高層級的那個 queue name 不是 `root`

在插入 `root` queue 後，文件定義的 queue 會變為 `root` 的 child queue

基本的架構式 `queues` 範例為：
```yaml
queues:
- name: <name of the queue>
  queues:
  - name: <name of the queue>
```

### queue 概念
對於 `queues` 屬性，有以下子屬性：
- name
- parent
- queues
- maxapplications
- properties
- adminacl
- submitacl
- resources
- limits

每個 queue 的 name 在其階層應為單一的，因為在解析時， Yunikorn 將會把 queue 的關係以 "." 相連，如
```yaml
queues:
- name: root
    queues:
    - name: testqueue
    
    queues:
    - name: parent
        queues:
        - name: testqueue
```
會有 `root.testqueue` 及 `root.parent.testqueue` 這兩種解析，因此如果定義在同一階層不是獨特的， Yunikorn 將會駁回定義
而也因為是以 "." 分割，所以 queue 的 name 不能有 "."

queue 有兩種 type：
- parent (有其他 sub-queue)
- leaf (沒有其他 sub-queue，且 `parent` 屬性不為 `true`)

而 application 只能被分配給 *leaf queue*，Trying to override a *parent queue* type in the configuration will cause a parsing error of the configuration.

`maxapplications` 屬性是一個大於等於 1 的整數值，設為 0 則不允許任何 application 的 allocation
child queue 的 `maxapplication` 小於等於 parent queue 的 `maxapplication`

`properties` 包含簡單的 key/value，這用於進一步隊列自訂功能，例如[應用程式排序](https://yunikorn.apache.org/docs/user_guide/sorting_policies/#application-sorting)和優先調度，在[之後](#Properties)會再提及

對於管理動作的存取權為 `adminacl` ，而提交 application 則為 `submitacl`，ACLs 的概念請參考[官方文檔](https://yunikorn.apache.org/docs/user_guide/acls/)

queue 的資源限制為 `resources` 屬性管理， user/group limits 則是 `limits`，這兩個會在之後提及

以下是 `root.namespaces` 作為 *parent queue* 且擁有 `limits` 的範例：
```yaml
partitions:
  - name: default
    queues:
      - name: namespaces
        parent: true
        maxapplications: 12
        resources:
          guaranteed:
            {memory: 1G, vcore: 10}
          max:
            {memory: 10G, vcore: 100}
        queues:
          - name: level1
            maxapplications: 8
            resources:
              guaranteed:
                {memory: 500M, vcore: 5}
              max:
                {memory: 5G, vcore: 50}
```

## Placement rules
對於 placement rules 的配置文件請參考[官方文檔](https://yunikorn.apache.org/docs/user_guide/placement_rules/)

每個 partition 只會定義一組 placement rule，如果沒有 placement rule 被定義，那所有 application 都應該被設定一個 queue 來提交

## Limits
### 配置架構
定義了一組 `limit` 給單一一個 queue ，架構如下：
```yaml
limits:
  - limit: <description>
  - limit: <description>
```

`limit` 是一個複雜的配置屬性，它定義了一個 user 或一組 group 的 limit
不在定義範圍內的 user / group 不會被 limit 的定義限制，詳細架構如下：
```yaml
limits:
  - limit: <description>
    users:
    - <user name or "*">
    - <user name>
    groups:
    - <group name or "*">
    - <group name>
    maxapplications: <1..maxint>
    maxresources:
      <resource name 1>: <0..maxint>[suffix]
      <resource name 2>: <0..maxint>[suffix]
```

### limits 概念
定義的 limit 會遞迴地應用在每個 child queue，也就是說 `root` 的 `limits` 會被用於所有 queue，同時，`root` 的 `limits` 等同於 `partition` 的 `limits`

`limits` 有以下子屬性：
- limit
- users
- groups
- maxapplications
- maxresources

`limit` 是個可選的敘述，單純用於理解及可讀性

`user` / `group` 有以下兩種情況：
- 萬用字元 "\*"
- users / groups 的 list

多於 1 個 user / group 的配置將被視為第二種情況，且重複的 user / group 將會被忽略
不允許在其他 list 旁使用 "\*" ，使用 "\*" 給 group 時，[必須配置至少一個命名組的 limit](https://yunikorn.apache.org/docs/design/user_group_resource_usage_enforcement/#group)

`maxapplications` 是一個無號整數，**不可**被設為 0，其定義了對於 user / group 的可執行 applications 的數量

`maxresources` 定義了一個或多個資源的上限，不在 list 內的資源用量則不受限定，其語法在[之後](#Resources)提及
上限可被設定為 0 ，用於禁止 user / group 使用特定資源，但整體資源量不可為 0
如果 queue 上的資源不可用，則應使用 queue 定義上的最大資源。

不允許資源為 0 、`maxresources` 也為 0 的配置文件

`limit` 是針對每個 user / group 的，而不是他們的組合限制，也就是說：
```yaml
limit: "example entry"
maxapplications: 10
users:
- sue
- bob
```
在這個範例中， user `sue` 與 user `bob` 都可以執行 10 個 applications

## Properties
用於表明 queue 額外的屬性，有下面幾種：
| 名稱 | 描述 |
|-----|------|
| `application.sort.policy` | queue 裡排序 application 的方法 |
| `application.sort.priority` | 在 queue 裡排序時，是否參考 priority |
| `priority.policy` | 設定 queue 間的排序 priority |
| `priority.offset` | 設定 queue 在同層級的 priority  |
| `preemption.policy` | 是否允許 preemption |
| `preemption.delay` | preemption 的延遲時間 |

### application.sort.policy
此設定對 *parent queue* 沒有效用

可修改值：`fifo` 、 `fair` 、 `stateware`
預設值：`fifo`

> `stateware` 已在 1.5 被棄用了，其將在 1.6 版本移除，在之後 `stateware` 將被視為 `fifo`

可參考[官方文檔](https://yunikorn.apache.org/docs/user_guide/sorting_policies/#application-sorting)以獲得更多資訊

### application.sort.priority
此設定可被 *child queue* 繼承

可修改值：`enabled` 、 `disabled`
預設值：`enabled`

> 1.2 以前的 Yunikorn 是沒有這一屬性的

### priority.policy
此設定不會被 *child queue* 繼承

可修改值：`default` 、 `fence`
預設值： `default`

使用 `default` 的話，priority 則會應用於每個 queue
使用 `fence` 的話，priority 則對於每個 queue 都不同

參考[官方文檔](https://yunikorn.apache.org/docs/user_guide/priorities/)以獲得更多資訊

### priority.offset
此設定不會被 *child queue* 繼承

可修改值：32位元的有號數字
預設值： 0

使用 `default` 的話，priority 會對於此值調整
使用 `fence` 的話，priority 則是被設定為此值，也就是說，在 queue 裡的 tasks 的 priority 將被忽略

參考[官方文檔](https://yunikorn.apache.org/docs/user_guide/priorities/)以獲得更多資訊

### preemption.policy

可修改值：`default` 、 `fence` 、 `disabled`
預設值：`default`

使用 `fence` 時，此 queue 及其以下的 queue 內的 tasks 不能 preemption 其他 queue 的 tasks，也就是說，preemption 只會發生在當前 queue 及以下

參考[官方文檔](https://yunikorn.apache.org/docs/design/preemption/#preemption-fence)以獲得更多資訊

### preemption.delay
此設定只能在 *leaf queue* 上使用

可修改值：參考[Golang 文檔](https://pkg.go.dev/time#ParseDuration)
預設值：`30s`

## Resources
`resources` 有 `guaranteed` 跟 `max` 兩種子屬性
資源限制是遞迴式地往下檢查

資源用量分為兩種情況：
- leaf queue: 被指定的資源量總和
- parent queue: 其下所有 queue 的資源量總和

基本上來說 *root queue* 的資源上限就是整個 cluster 的資源上限，若指定 root 的資源上限可能會出錯，它也沒有 `guaranteed` 的子屬性

`max` 的值會在 allocation 時給出硬性限制，其值可被設定為 `0`，這在[上面](#limits-概念)有提及過
`guaranteed` 會被用於計算其在 queue 裡的份額，因此它也被作為 allocation 的輸入， preemption 也會參考這個數值

基本架構如下：
```yaml
resources:
  guaranteed:
    <resource name 1>: <0..maxint>[suffix]
    <resource name 2>: <0..maxint>[suffix]
  max:
    <resource name 1>: <0..maxint>[suffix]
    <resource name 2>: <0..maxint>[suffix]
```

上面提到的 suffix 有以下情況：
- 記憶體
    - 可以是 `k` 、 `M` 、 `G` 、 `T` 、 `P` 跟 `E` 
    - 也可以是 `ki` 、 `Mi` 、 `Gi` 、 `Ti` 、 `Pi` 跟 `Ei` 
    - 或者 bytes
- vcore
    - `m` 對於 millicores

## *child queue* 模板
*parent queue* 可以定義模板給**動態**的 *leaf queue*，可在任一階層定義給 *parent queue*
當一個 *parent queue* 沒有模板時，它會往上找到一個模板來使用(如果有的話)

可給定的屬性有以下幾種：
- application sort policy
- max resources
- guaranteed resources
- max applications

以下是範例：
```yaml
 partitions:
   - name: default
     placementrules:
       - name: provided
         create: true
     queues:
       - name: root
         submitacl: '*'
         childtemplate:
           maxapplications: 10
           properties:
             application.sort.policy: fifo
           resources:
             guaranteed:
               vcore: 1
               memory: 1G
             max:
               vcore: 20
               memory: 600G
         queues:
           - name: parent
             parent: true
             childtemplate:
               resources:
                 max:
                   vcore: 21
                   memory: 610G
           - name: notemplate
             parent: true
```
在這裡，`root.parent.sales` 會直接使用 `root.parent` 定義的 child template
作為對比，`root.noteplate.sales` 會使用 `root` 的 child template，因為它的 *parent queue* 沒有 child template ，而從 `root` 那邊繼承而來

---
[官方文檔連結](https://yunikorn.apache.org/docs/user_guide/queue_config)