Replace the current Keep Job Artifacts action with Protect Job Artifacts
Description
The Keep action for job artifacts is not modeled well in the database and its implementation is an obstacle to improving the artifact expiration process.
As described in #38199 (moved), when a user clicks the Keep button on the artifacts pane of a CI Job, the app sets the artifacts_expire_at column to NULL. Meaning, these artifacts never expire. If the expire_at column is already NULL, the Keep button is not shown.
There are a handful of problems caused by implementing Keep artifacts in this way.
-
It prevents us from implementing artifact expiration policies that aren't based on time. For example, the famous #23777 (moved). If artifacts are set to to expire when they are no longer associated the last-known-good
Build, thenKeepbecomes meaningless. EveryJob Artifacthasexpires_atset toNULLand clickingKeepcan't make it moreNULL. -
You can't
unkeepartifacts when you decide you no longer need them. See #29182 (moved). There's no way tell the system to allow them to expire by the currently-in-force expiration policy. -
You don't know who kept the artifacts or when. Unlike
erased_atanderased_by, we're missingkept_atandkept_by. As an administrator it's important to know who is keeping artifacts beyond the established expiration criteria.
Proposal
Replace the Keep artifacts feature with Protect artifacts
I really like the word Keep as it relates to artifacts, but Unkeep doesn't work for me and Remove is inaccurate. Protect and Unprotect work well together, and are used in other places within GitLab.
Extend the Build model
At a minimum we should add the columns artifacts_protected (bool), artifacts_protected_by (user), artifacts_protected_at (date).
Replace the Keep button with a Protect button
When the Protect button is clicked, provide an Unprotect button, and update the label to say:
The artifacts from this job were protected from removal by @haboustak 6 days ago
Stretch goal: Implement an artifact timeline
It would be ideal to implement artifact events. Each protect/unprotect/erase transition is recorded in a timeline. Example:
The artifacts from this job were erased 25 minutes ago.
The artifacts from this job were unprotected by @haboustak 2 weeks ago
The artifacts from this job were protected from removal by @haboustak 8 months ago
~"feature proposal"