Membawa Scaffolder ke level produksi: merancang workflow multi-langkah dengan logika kondisional if dan when, memanfaatkan output berupa link, entity, dan entityRef, membatasi template dengan permission, serta membangun custom action memakai createTemplateAction untuk memprovisikan resource cloud dari tooling internal.

Di episode 6, kalian merangkai template tiga langkah: fetch, publish, register. Di episode 9, kalian merapikan konfigurasi yang melingkupinya. Episode 10 menggabungkan keduanya pada level yang lebih tinggi: Scaffolder Advanced & Custom Actions. Template tidak lagi sekadar menyalin folder — ia bisa bercabang berdasarkan jawaban user, menghasilkan entity dan link, dibatasi oleh permission, bahkan memanggil tooling internal untuk memprovisikan resource cloud. Di sinilah Scaffolder berubah dari pembuat repository menjadi orkestrator platform engineering.
Sebelum masuk detail, bandingkan dulu bagaimana konsep berevolusi dari episode 6 ke episode 10:
| Konsep | Dasar (episode 6) | Lanjutan (episode 10) |
|---|---|---|
| Steps | Sedikit dan linier | Banyak, bercabang dengan kondisi |
| Output | links dan text | links, entities, dan entityRef |
| Akses | Semua user bisa memakai | Dibatasi permission per template |
| Actions | Bawaan saja | Bawaan ditambah custom action internal |
Workflow lanjutan bisa terdiri dari banyak langkah: ambil template, buat repository, jalankan audit, panggil API internal, lalu daftarkan entity. Setiap langkah tetap berjalan berurutan dan bisa mengonsumsi output langkah sebelumnya. Panjangnya pipeline bukan masalah — yang penting setiap langkah punya id yang jelas agar output-nya bisa dirujuk oleh langkah berikutnya maupun oleh output template. Dalam praktik, urutan yang umum adalah fetch:template terlebih dahulu, lalu publish:github, dan di antara keduanya disisipkan langkah-langkah validasi atau provisi yang memakai output langkah sebelumnya lewat pola steps.<id>.output.<field>.
Tidak semua langkah harus selalu dijalankan. Scaffolder mendukung conditional logic lewat when pada langkah: langkah hanya dieksekusi jika kondisi terpenuhi. Kondisi biasanya memakai nilai parameter atau output langkah sebelumnya — sangat berguna untuk template yang melayani lebih dari satu jenis komponen.
steps:
- id: fetch-base
name: Ambil Base Template
action: fetch:template
input:
url: ./templates/service
values:
name: ${{ parameters.name }}
- id: provision-db
name: Provisi Database
action: acme:cloud:provision-database
input:
instance: ${{ parameters.name }}-db
when:
condition: ${{ parameters.includeDatabase }}
- id: publish
name: Publikasikan ke GitHub
action: publish:github
input:
repoUrl: ${{ parameters.repoUrl }}Langkah provision-db hanya berjalan jika user mencentang includeDatabase di formulir. Bagi yang tidak membutuhkan database, pipeline melewati langkah itu tanpa gangguan. Kondisi bisa disusun lebih kompleks dengan operator seperti not, allOf, dan anyOf untuk kebutuhan yang lebih rumit.
Output template tidak lagi hanya berupa link. Ada tiga bentuk utama:
| Tipe output | Isi | Pemakaian |
|---|---|---|
links | Daftar tautan dengan judul dan ikon | Menuju repository, pipeline, atau dashboard |
entities | Entity lengkap atau referensi entity | Mendaftarkan entity baru hasil scaffolding |
entityRef | Referensi entity dalam format katalog | Menautkan entity yang sudah ada |
Output berjenis entities memungkinkan template mendaftarkan komponen, API, atau resource sekaligus. entityRef dalam format katalog seperti component:default/payment-api menjadikan referensi antar entity konsisten dan bisa ditautkan oleh catalog — tema yang akan sangat dalam kita bahas di episode 11.
Tidak semua template layak dipakai semua orang. Template untuk infra internal, misalnya, sebaiknya hanya bisa dijalankan tim platform. Template permissions mengikat Scaffolder ke permission framework Backstage: sebelum template dieksekusi, kebijakan permission diperiksa, dan user yang tidak diizinkan akan ditolak. Kebijakan bisa berbasis ownership — misalnya hanya owner dari grup tertentu yang boleh menjalankan template — atau aturan kustom lewat permission policy. Dengan ini, golden path tetap terbuka bagi banyak tim, tetapi jalan yang sensitif bisa dijaga.
Action bawaan cukup untuk alur standar, tetapi tooling internal hampir selalu punya kebutuhan unik: membuat tiket, memprovisikan database, memanggil pipeline internal, atau mengirim notifikasi. Semua itu bisa dibungkus menjadi custom action menggunakan createTemplateAction dari backend scaffolder.
import { createTemplateAction } from '@backstage/plugin-scaffolder-node';
export const createJiraTicket = createTemplateAction({
id: 'acme:jira:create-ticket',
description: 'Membuat tiket di Jira internal',
schema: {
input: {
type: 'object',
required: ['title'],
properties: {
title: { type: 'string', title: 'Judul tiket' },
},
},
},
async handler(ctx) {
const ticket = await jiraClient.createTicket({
summary: ctx.input.title,
});
ctx.logger.info(`Tiket dibuat untuk ${ctx.input.title}`);
ctx.output('ticketUrl', ticket.url);
},
});Handler menerima ctx dengan ctx.input berisi nilai dari template, ctx.output untuk menuliskan hasil, dan ctx.logger untuk logging. id yang dipakai menjadi nama action yang dipanggil template lewat action: acme:jira:create-ticket.
Custom action yang sudah dibuat perlu didaftarkan ke action registry scaffolder — daftar action yang dikenal backend. Lewat scaffolder extension point, kalian menambahkan satu atau lebih action ke registry saat backend dinyalakan.
import { createBackendModule } from '@backstage/backend-plugin-api';
import { scaffolderActionsExtensionPoint } from '@backstage/plugin-scaffolder-node/alpha';
import { createJiraTicket } from './actions/jira';
export default createBackendModule({
pluginId: 'scaffolder',
moduleId: 'acme-actions',
register(reg) {
reg.registerInit({
deps: { scaffolder: scaffolderActionsExtensionPoint },
async init({ scaffolder }) {
scaffolder.addActions(createJiraTicket);
},
});
},
});Setelah modul ini dimuat, action acme:jira:create-ticket tersedia untuk semua template. Action registry menjadi katalog tindakan yang boleh dipakai template — mengelolanya rapi berarti menjaga permukaan integrasi platform kalian tetap terkontrol.
Nilai strategis custom action yang sesungguhnya adalah menghubungkan Scaffolder ke tooling internal organisasi: penyedia cloud, platform orchestration, sistem tiket, atau pipeline data. Sebuah template pembuatan layanan bisa, misalnya, memanggil action internal yang memprovisikan VPC dan database di cloud sebelum repository diterbitkan. Alur datanya berantai: output action provisi VPC berupa vpcId menjadi input action provisi database, lalu hasilnya dipakai action berikutnya. Dengan pola ini, seluruh proses pembuatan layanan — dari kode hingga infrastruktur — berjalan lewat satu golden path, dan kredensial cloud diambil dari ctx.secrets atau environment, bukan ditulis di template.
Tip
Mulailah menulis custom action dari hal kecil: bungkus satu panggilan API internal dengan createTemplateAction, uji lewat template sederhana, baru kemudian perbanyak kompleksitasnya. Id action yang jelas, schema input yang wajib, dan pemakaian ctx.secrets untuk kredensial akan menjaga action tetap aman dipakai template mana pun.
Pada episode 10 ini, kalian membawa Scaffolder ke level produksi: workflow multi-langkah dengan data mengalir antar langkah, conditional logic lewat when dengan operator not, allOf, dan anyOf, output berupa links, entities, dan entityRef, template permissions untuk membatasi akses, serta custom action memakai createTemplateAction yang didaftarkan lewat action registry untuk memprovisikan resource cloud dari tooling internal.
Inti yang harus dibawa pulang:
when membuat langkah dijalankan hanya jika kondisi terpenuhi.entities dan entityRef menghubungkan hasil scaffolding ke catalog.createTemplateAction mengubah API internal menjadi action yang bisa dipakai template apa pun.ctx.secrets atau environment.Di episode 11 berikutnya, kita melihat sisi data di balik semua entity yang kalian scaffold: Catalog Advanced & Data Model — relasi antar entity seperti ownership, partOf, dependsOn, dan providesApi, pemodelan system, domain, dan resource, filter katalog, serta cara menjaga kualitas katalog di CI.