CLI version: 5.23.1
Summary
railway config plan perpetually reports env-var updates for variables whose declared value in .railway/railway.ts is byte-identical to the live value. Running railway config apply does not make the diff converge — the next plan reports the exact same set of changes. Only env vars set to literal strings are affected; vars declared with preserve() are correctly excluded.
Repro
- Link a project/environment whose service has env vars set to known values.
- In
.railway/railway.ts, declare a service with env literals that exactly match the live values:
service("backend", {
// ...
env: {
SECRET_THING: preserve(), // excluded from plan — correct
NODE_ENV: "production", // matches live exactly
PORT: "3001", // matches live exactly
},
})
railway config plan → reports Update variable for NODE_ENV and PORT.
railway config apply.
railway config plan again → reports the same updates.
Actual
Plan: 0 to add, N to change, 0 to destroy
+ Update variable backend.NODE_ENV
└ backend.NODE_ENV (preserve() → «hidden»)
+ Update variable backend.PORT
└ backend.PORT (preserve() → «hidden»)
...
Every literal-valued var appears on every plan, forever. preserve() vars never appear.
Expected
A literal-valued var whose live value already matches the declaration should not appear in the plan, and the plan should converge to "up to date" after apply.
Notes
0 to add / 0 to destroy — nothing destructive; values verified identical to live before and after apply.
- The
(preserve() → «hidden») rendering plus the never-converging behavior suggests the differ isn't reading back the current value to compare literal-valued vars, so it always re-proposes them.
CLI version: 5.23.1
Summary
railway config planperpetually reports env-var updates for variables whose declared value in.railway/railway.tsis byte-identical to the live value. Runningrailway config applydoes not make the diff converge — the nextplanreports the exact same set of changes. Only env vars set to literal strings are affected; vars declared withpreserve()are correctly excluded.Repro
.railway/railway.ts, declare a service withenvliterals that exactly match the live values:railway config plan→ reportsUpdate variableforNODE_ENVandPORT.railway config apply.railway config planagain → reports the same updates.Actual
Every literal-valued var appears on every plan, forever.
preserve()vars never appear.Expected
A literal-valued var whose live value already matches the declaration should not appear in the plan, and the plan should converge to "up to date" after
apply.Notes
0 to add / 0 to destroy— nothing destructive; values verified identical to live before and after apply.(preserve() → «hidden»)rendering plus the never-converging behavior suggests the differ isn't reading back the current value to compare literal-valued vars, so it always re-proposes them.