aboutsummaryrefslogtreecommitdiff
path: root/.github/workflows/ci_build_major_branch_keymap.yml
blob: 0804c9e2d04309e4b45cd0e24121cb75c8ea1e80 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
name: CI Build Major Branch Keymap

permissions:
  contents: read
  actions: write

on:
  workflow_call:
    inputs:
      branch:
        type: string
        required: true
      keymap:
        type: string
        required: true
      slice_length:
        type: string
        required: true

jobs:
  generate_targets:
    name: "Generate targets (${{ inputs.keymap }})"
    runs-on: ubuntu-latest
    container: ghcr.io/qmk/qmk_cli

    outputs:
      targets: ${{ steps.generate_targets.outputs.targets }}

    steps:
      - name: Install prerequisites
        run: |
          apt-get update
          apt-get install -y jq

      - name: Disable safe.directory check
        run: |
          git config --global --add safe.directory '*'

      - name: Checkout QMK Firmware
        uses: actions/checkout@v4

      - name: Generate build targets
        id: generate_targets
        run: |
          { # Intentionally use `shuf` here so that we share manufacturers across all build groups -- some have a lot of ARM-based boards which inherently take longer
            counter=0
            echo -n '{'
            qmk find -km ${{ inputs.keymap }} 2>/dev/null | sort | uniq | shuf | xargs -L${{ inputs.slice_length }} | while IFS=$'\n' read target ; do
                if [ $counter -gt 0 ]; then
                    echo -n ','
                fi
                counter=$((counter+1))
                printf "\"group %02d\":{" $counter
                echo -n '"targets":"'
                echo $target | tr ' ' '\n' | sort | uniq | xargs echo -n
                echo -n '"}'
            done
            echo -n '}'
          } | sed -e 's@\n@@g' > targets.json

          # Output the target keys as a variable
          echo "targets=$(jq -c 'keys' targets.json)" >> $GITHUB_OUTPUT

      - name: Upload targets json
        uses: actions/upload-artifact@v4
        with:
          name: targets-${{ inputs.keymap }}
          path: targets.json

  build_targets:
    name: "Compile ${{ matrix.target }} (${{ inputs.keymap }})"
    needs: generate_targets
    runs-on: ubuntu-latest
    container: ghcr.io/qmk/qmk_cli
    continue-on-error: true

    strategy:
      matrix:
        target: ${{ fromJson(needs.generate_targets.outputs.targets) }}

    steps:
      - name: Install prerequisites
        run: |
          apt-get update
          apt-get install -y jq

      - name: Disable safe.directory check
        run: |
          git config --global --add safe.directory '*'

      - name: Checkout QMK Firmware
        uses: actions/checkout@v4

      - name: Get target definitions
        uses: actions/download-artifact@v4
        with:
          name: targets-${{ inputs.keymap }}
          path: .

      - name: Deploy submodules
        run: |
          qmk git-submodule -f

      - name: Dump targets
        run: |
          jq -r '.["${{ matrix.target }}"].targets' targets.json | tr ' ' '\n' | sort

      - name: Build targets
        continue-on-error: true
        run: |
          export NCPUS=$(( $(nproc 2>/dev/null || sysctl -n hw.ncpu 2>/dev/null || getconf _NPROCESSORS_ONLN 2>/dev/null) -1 ))
          qmk mass-compile -t -j $NCPUS -e DUMP_CI_METADATA=yes $(jq -r '.["${{ matrix.target }}"].targets' targets.json) || touch .failed

      - name: Upload binaries
        uses: actions/upload-artifact@v4
        with:
          name: firmware-${{ inputs.keymap }}-${{ matrix.target }}
          if-no-files-found: ignore
          path: |
            *.bin
            *.hex
            *.uf2
            .build/failed.*
            .failed

      - name: Fail build if any group failed
        run: |
          # Exit with failure if the compilation stage failed
          [ ! -f .failed ] || exit 1

  repack_firmware:
    if: always()
    name: "Repack artifacts"
    needs: build_targets
    runs-on: ubuntu-latest

    steps:
      - name: Checkout QMK Firmware
        uses: actions/checkout@v4

      - name: Download firmwares
        uses: actions/download-artifact@v4
        with:
          pattern: firmware-${{ inputs.keymap }}-*
          path: .
          merge-multiple: true

      - name: Upload all firmwares
        uses: actions/upload-artifact@v4
        with:
          name: firmware-${{ inputs.keymap }}
          if-no-files-found: ignore
          path: |
            *.bin
            *.hex
            *.uf2
            .build/failed.*
            .failed

      - name: Generate output logs
        run: |
          # Generate the step summary markdown
          ./util/ci/generate_failure_markdown.sh > $GITHUB_STEP_SUMMARY || true
          # Truncate to a maximum of 1MB to deal with GitHub workflow limit
          truncate --size='<960K' $GITHUB_STEP_SUMMARY || true

      - name: Delete temporary build artifacts
        uses: geekyeggo/delete-artifact@v5
        with:
          name: |
            firmware-${{ inputs.keymap }}-*
            targets-${{ inputs.keymap }}

      - name: 'CI Discord Notification'
        if: always()
        working-directory: util/ci/
        env:
          DISCORD_WEBHOOK: ${{ secrets.CI_DISCORD_WEBHOOK }}
        run: |
          python3 -m pip install -r requirements.txt
          python3 ./discord-results.py --branch ${{ inputs.branch || github.ref_name }} --keymap ${{ inputs.keymap }} --url ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}