
Laidiena ievietošana CI, divreiz
GeekBye v1.8.4 pārvietoja laidiena būvējumus uz CI macOS un Windows platformām. Ko izmaiņu žurnāls nepasaka, ir tas, ka mēs to jau reiz izmēģinājām, mēnesi vēlāk izdzēsām runner izmaksu dēļ un noturējām tikai otrajā reizē — jo līdz tam laikam laidiena skripts jau strādāja ar roku.
v1.8.4 izmaiņu žurnālā ir rindiņa, kas izklausās pēc tīras rutīnas: "Laidiena būvējumi tagad nāk no CI gan macOS, gan Windows." Tā lasās kā tāda lieta, kas notiek vienreiz, tīri, un par ko vairs nekad nedomā. Tā nebija. Komanda jau reiz bija ievietojusi laidienus CI — un to izrāva ārā. Šis laidiens ir otrais mēģinājums, un iemesls, kāpēc tas noturējās, ir īstā inženierijas mācība, tāpēc izstāstīsim to pēc kārtas.
Pirmais mēģinājums un kāpēc tas aizgāja bojā
Vēl 2025. gada oktobrī pastāvēja release.yml. To iedarbināja tag push — iegrūd v*.*.* tagu, un macOS runner iedarbojās, būvēja un publicēja. Tas pats ar roku veica savu parakstīšanas iestatīšanu: solis, kas atšifrēja parakstīšanas sertifikātu, izveidoja un atbloķēja pagaidu keychain, importēja sertifikātu, lai codesign to varētu atrast, un atbilstošs sakopšanas solis beigās. Tas strādāja. Tas bija arī tikai macOS — Windows laidieni CI nebija vispār.
- novembrī to izdzēsa. Komita ziņojums ir neparasti atklāts par to, kāpēc: "remove GitHub Actions release workflow to conserve minutes / macOS runners cost 10x multiplier (100 billed minutes per 10-minute release). Releases will be done locally." Tas ir viss pirmā mēģinājuma stāsts vienā teikumā. GitHub par macOS runner laiku rēķina desmit reizes vairāk nekā par Linux, un tags iedarbināts laidiens nozīmē, ka katrs atsevišķais tags — ieskaitot vienreizējos, atkārtotos, tos "ak vai, aizmirsu paaugstināt versiju" — klusi iztērē simts apmaksātu minūšu. Automatizācija, ko tu nekontrolē, ir automatizācija, kas tērē naudu bez tavas ziņas. Tāpēc laidieni uz nākamajiem trīs ar pusi mēnešiem atgriezās izstrādātāja Mac datorā.
Kur grūtās problēmas patiešām tika atrisinātas
Lūk, daļa, kas liek otrajam mēģinājumam strādāt, un tā notika pilnībā ārpus CI. Tajos trīs ar pusi mēnešos vietējo laidienu laikā scripts/release.js — vienkāršais Node skripts, ko izstrādātājs palaiž ar roku — uzsūca katru iepakošanas problēmu, kas lietotnei bija, pa vienam labojumam:
- Vairākzīmolu atjaunošana. Šī ir vairākzīmolu koda bāze, kas no viena avota būvē gan GeekBye, gan Pavleur, kas nozīmē, ka laidiens nomaina
package.jsonlaukus un ikonu resursus mērķa produktam. Divi labojumi iemācīja skriptam pēc tam visu salikt atpakaļ, tā ka Pavleur būvēšana neatstāja tavu git koku netīru ar Pavleur identitāti. - Divu arhitektūru Windows. Labojums, lai būvētu abus x64 un arm64 Windows instalētājus, nevis vienu.
- Neparakstītā Windows apiešana. Jaunāks electron-builder ignorēja konfigurācijas karodziņu, kas bija paredzēts Windows parakstīšanas atspējošanai, tāpēc skripts iemācījās piespiest neparakstītu būvējumu, tā vietā vidē iestatot
CSC_IDENTITY_AUTO_DISCOVERY=false— sīkums, ko atklāj tikai tad, kad uz tā uzduras. - Notarizācijas automātiskā noteikšana. Skripts iemācījās paskatīties uz savu vidi un izlemt: parakstīšanas akreditācijas dati klāt? Paraksti. Klāt arī Apple notarizācijas akreditācijas dati? Notarizē. Neviena? Būvē neparakstītu. Nekādu karodziņu, ko atcerēties; noslēpumu klātbūtne ir konfigurācija.
Nekas no tā nav spožs. Tas viss ir tāda veida lieta, kas, ja tā tevi pārsteidz CI runner iekšpusē, maksā stundu push-gaidi-neizdevās-lasi-logus par katru mēģinājumu — ar 10x rēķinu. Atrisināts uz Mac, kura priekšā tu sēdi, katrs no tiem maksā minūti.
Otrais mēģinājums: sešdesmit sešas rindas
Kad CI atgriezās v1.8.4, workflow bija 66 rindas, un tā noteicošā īpašība ir tas, cik maz tas dara. Komits to apraksta vienkārši: "Manual workflow_dispatch trigger that builds both platforms in parallel, reusing existing release.js script. macOS builds are signed and notarized, Windows builds are unsigned." Katrs tajā ietvertais dizaina lēmums nāk no tā, ko sāpīgi iemācīja pirmais mēģinājums:
workflow_dispatch, nevis tags iedarbināts. Laidienu tu sāc, noklikšķinot "Run workflow." Cilvēks kontrolē katru apmaksāto macOS minūti. Izmaksu problēma, kas nogalināja pirmo versiju, tiek atrisināta, vienkārši neautomatizējot iedarbinātāju — vienīgo vietu, kur automatizācija bija aktīvi kaitīga.productievade. Dispatch pieņem nolaižamo izvēlni —geekbyevaipavleur— tā ka tas pats workflow piegādā jebkuru zīmolu. Vairākzīmolu šuve stiepjas visu ceļu līdz pat laidiena pogai.- Divi paralēli jobi.
build-macuzmacos-latest,build-winuzwindows-latest, darbojoties vienlaikus. Windows CI šeit ir patiešām jauns; oktobra workflow to nekad nebūvēja. - Nekādas parakstīšanas loģikas YAML. Tā ir visa būtība. Nav keychain žonglēšanas, nav sertifikāta importa soļa, nav sakopšanas. Mac jobs palaiž
node scripts/release.js <product> --publish, un Windows jobs palaiž to pašu ar--no-sign. Viss, ko pirmais workflow YAML darīja ar roku, tagad dzīvo skriptā, kas jau strādā. Workflow ir orķestrētājs, nevis implementācija.
Abas platformas vēlas pretējas lietas, un jobi to godīgi atspoguļo. macOS būvē zem hardened runtime, parakstītu un notarizētu caur electron-builder iebūvēto ceļu (@electron/notarize), ar akreditācijas datiem, kas piegādāti no repozitorija noslēpumiem un ko skripts nosaka automātiski. Windows būvē neparakstītus NSIS instalētājus x64 un arm64. Viens workflow, divi jobi, divi pilnīgi atšķirīgi jēdzieni par "pabeigts."
Pierādījums ir tajā, kas nenotika
Lūk, kā tu zini, ka secība bija pareiza: pēc divām tās pašas dienas korekcijām, kas nosauca palaišanas un izlaboja tokena noslēpuma nosaukumu, release.yml netika aiztikts vēl četrus mēnešus. Nekāda parakstīšanas kļūmes ātrlabojuma. Nekādas notarizācijas noraidījuma steigas. Nekādas "vietējais binārs runner trūkst" panikas. Koda parakstīšanas un notarizācijas cauruļvadam — CI žanram, kas visvairāk pazīstams ar mētāšanos — četru mēnešu klusums ir gandrīz nedzirdēts.
Bija klusi, jo troksnis jau bija noticis kaut kur lētāk. Cīņas, kas parasti izvēršas CI logu cilnē, ar 10x rēķinu, pa vienam force-push, bija izvērsušās izstrādātāju Mac datoros vietējā laikmetā. CI nebija jābūt vietai, kur iepakošana tika atkļūdota, jo iepakošana jau bija atkļūdota. Tā ir tēze vienā rindā: pārcel būvējumu prom no sava Mac tikai pēc tam, kad tavs Mac ir beidzis tevi pārsteigt.
Vienīgā sasaiste, kas joprojām var sagādāt nepatikšanas
Tas nav pilnīgi bez vājās vietas, un to ir vērts nosaukt, jo tā ir smalka. Swift binārie faili, no kuriem atkarīga macOS lietotne — OCR, ekrāna tveršana, transkribētāji — ir komitēti git. Bet laidiens nepiegādā komitētās kopijas; būvējums tos no jauna kompilē uz runner. Un check-swift-version.js vārti cieti apgāž visu laidienu, ja kompilators nav piespraustā versija. Šajā laidienā šī piespraude bija Swift 6.2.x, un nekas workflow to neinstalē — jobs vienkārši paļaujas, ka macos-latest noklusējuma Swift atbilst. Dienā, kad GitHub paceļ sava runner attēlu pāri piespraudei, laidiens apstājas, nevis tāpēc, ka lietotnē kaut kas ir nepareizi, bet tāpēc, ka cauruļvads ir klusi sasaistīts ar mašīnas attēlu, ko tas nekontrolē. Tā ir vienīgā implementācijas detaļa, ko šis plānais workflow neiegrūda kaut kur, kas pieder tam pašam.
Otra laidiena puse: mazākas slodzes
Laidiens nesa vienu nesaistītu funkciju, ko vērts pieminēt, jo tas ir tīrs piemērs latentuma uzlabojumam, atņemot. Assist Me darbība katrā pieprasījumā sūtīja backend vairāk konteksta, nekā tam bija vajadzīgs. Viens komits apcirpa divas lietas: līdzi sūtītā transkripta vēsture saruka no pēdējiem 30 ierakstiem uz pēdējiem 15, un lietotāja profila konteksta faili — kas tiek iešļirci system prompt katrā izsaukumā — tika cieti ierobežoti līdz 4,000 rakstzīmēm ar apciršanas marķieri. Mazāk ko serializēt, mazāk ko augšupielādēt, mazāk ko modelim izlasīt, pirms tas sāk atbildēt, kas ir metrika, ko komits optimizē: time-to-first-token. Godīguma labad: komits apgalvo paātrinājumu, bet to neizmēra — vēsturē nav pirms/pēc skaitļa, tāpēc uztver to kā labi pamatotu apciršanu, nevis ar etalontestu pierādītu uzvaru.
Trīs lietas, ko šis laidiens mums iemācīja
- CI ir plāns slānis virs skripta, kas jau strādā. 66 rindu workflow nav pašam savas parakstīšanas loģikas; tas izsauc skriptu, ko trīs vietējo laidienu mēneši jau bija atkļūdojuši. Ieliec mehānismu lietā, ko vari palaist ar roku, un ļauj CI tikai izlemt, kad to palaist.
- Automatizē darbu, ne vienmēr iedarbinātāju. Pirmais mēģinājums aizgāja bojā, jo tags iedarbināti laidieni automātiski tērēja ar 10x rēķinātas runner minūtes. Manuāls
workflow_dispatchsaglabā automatizāciju un noņem daļu, kas maksāja naudu — dažreiz cilvēks procesā ir tā funkcija. - Atkļūdo tur, kur iterācija ir lēta. Katra iepakošanas cīņa, kas atrisināta uz izstrādātāja Mac, ir cīņa, kas nekad nenotiek CI logu cilnē par desmitkārtīgu cenu. Pārcelies prom no Mac pēdējais, nevis pirmais.
Iepriekšējai nodaļai v1 stāstā — trīsdesmit valodu piegāde bez drošības tīkla (v1.8.3); un visai lokai — programmatūras piegādes līdz pilnībai anatomiju.