
The client asks for the file the build produced. Tonight, three proofs, in a repository the agency or the client can open. Name the artifact: the name, the run that uploaded it, and the retention that applies to it. Show a file from a different run that is not this artifact. Show another client's repository that does not list it. If any of the three needs the person who pressed the button and then left, you have not shown the file. You have a green check and a hope.
This is one file a workflow stored after a run. It is not the digest of what is running. Name the commit the client is running is the image digest or the commit the release was built from, set next to the commit you believe you shipped. A digest can be right while the artifact from that run has already expired, and an artifact can still be downloadable while production is on a different digest. It is not which environment received a change. Which environment got that change? is the environment name and the artifact that landed there, in that page's sense of a deployed change. A landing environment is not the retention on a stored file. It is not the migration the database applied. Name the migration the deploy applied is a schema version. A migration is not a zip. It is not the owner a file records. Who owns the file they changed? is a rule on the base branch. An owner is not an upload.
None of what follows is a retention period for this client's repository, and none of it is legal advice. The limits below are one vendor's current quotas for a workflow host, and the retention sentences are that vendor's settings page. The counts below that are a 2021 study of public repositories. A quota is not a census of your deploys. A study from ten months after a feature launched is not the run you opened tonight. They do tell you which numbers people mix up when they try to sound precise about a file they have not named.
GitHub's settings page for a repository prints one default and then a note that moves other objects onto it. By default, checks, workflow runs, commit statuses, and the artifacts and log files generated by workflows are retained for 90 days, then deleted. The note says that starting 1 October 2026, those policies apply to checks, workflow runs, and commit statuses in addition to artifacts and logs. Until that date, the same note says, checks, workflow runs, and commit statuses are retained for 400+ days regardless of the configured retention. 90 is not 400. An artifact is already inside the 90-day sentence. A check, before the date the note names, is inside the 400+ sentence. Do not move 400 onto the file. Public repositories can set the retention anywhere between 1 day and 90 days. Private repositories can set it anywhere between 1 day and 400 days. 1 is not 90. 90 is not 400. A change applies to new objects. It does not rewrite the expiry of an object that already exists. A managed repository cannot exceed the limit set above it. You can also set a retention on one artifact. That per-artifact value is not the repository default, and the page does not print a sample number of days for it (GitHub, Managing GitHub Actions settings for a repository).
A cache is the object people substitute for an artifact, and the same settings page gives it different numbers. Cache retention defaults to 7 days. Public repositories can go up to 90 days. Private and internal repositories can go up to 365 days, or up to the organization limit. 7 is not 90. 90 days of cache is not 90 days of artifacts, even when the digits match, because the sentences name different objects. 365 is not 400. The cache size eviction limit defaults to 10 GB, and the page says qualifying accounts can configure it up to 10,000 GB, or up to the organization limit. 10 is not 10,000. That cache ceiling is not the artifact retention.
The limits page is a third document, and its 10 GB is not automatically the settings page's 10 GB. Storage for GitHub-hosted runners, which the page says support cannot increase: GitHub Free, artifact storage 500 MB, minutes 2,000, cache storage 10 GB. GitHub Pro, 1 GB, 3,000 minutes, 10 GB cache. GitHub Free for organizations matches Free: 500 MB, 2,000, 10 GB. GitHub Team, artifact storage 2 GB, 3,000 minutes, 10 GB cache, and custom image storage 75 GB. GitHub Enterprise Cloud, artifact storage 50 GB, 50,000 minutes, 10 GB cache, and custom image storage 150 GB. 500 MB is not 10 GB. 2,000 minutes is not 500 MB. 50 GB of artifacts is not 50,000 minutes. 10 GB of cache is the figure every plan in that table prints, and custom image storage is not applicable on Free, Pro, or Free for organizations. 75 is not 150. The settings page's configurable cache ceiling of 10,000 GB is not this table's 10 GB, and the limits page's statement that support cannot increase those storage limits is not the settings page's configuration sentence. Quote the page you are looking at. Do not let one 10 answer for the other (GitHub, Actions limits).
Time limits on that same page reuse small integers for different clocks. A workflow run is cancelled at 35 days, and that period includes waiting and approval. A gate approval may wait 30 days. 35 is not 30. A job matrix can generate at most 256 jobs per workflow run, on GitHub-hosted and self-hosted runners. A workflow run can be re-run at most 50 times, counting full re-runs and re-runs of a subset. 256 is not 50. A workflow file larger than 500 KB will not start. 500 KB is not 500 MB of artifact storage, and it is not 500 workflow runs. The queue limit is 500 workflow runs per 10 seconds, and a run that calls 30 reusable workflows counts as 1 toward that limit. 30 is not 500. 1 is not 30. A concurrency group can queue 100 runs when queue is max. 100 is not 500.
Hosted and self-hosted jobs do not share a clock, and the API limits do not share the workflow limits. A GitHub-hosted job can run 6 hours. A self-hosted job can run 5 days, and it can sit in the queue 24 hours before it is cancelled. 6 hours is not 5 days. 24 hours is not 6 hours. 5 days is not the 35-day workflow cap. Runner registration is 1,500 runners per 5 minutes per repository, organization, or enterprise. A runner group can hold 10,000 runners. 1,500 is not 10,000. Cache uploads are 200 per minute, downloads 1,500 per minute, deletes 400 per minute. That 1,500 downloads per minute is not the 1,500 events per 10 seconds that may trigger workflows, and neither is the 1,500 runner registrations per 5 minutes. Three ceilings, one integer. 200 is not 400.
Concurrency and the API budget are where 5, 50, and 5,000 each mean more than one thing. Standard hosted runners, total concurrent jobs and the macOS cap: Free 20 and 5, Pro 40 and 5, Team 60 and 5, Enterprise 500 and 50. The macOS 5 does not rise when the total rises from 20 to 60. Enterprise's 50 macOS jobs is not Enterprise's 50 GB of artifacts and not its 50,000 minutes. Larger runners: Team and Enterprise both list 1,000 total concurrent jobs and 100 GPU jobs. Team's macOS cap on larger runners is 5. Enterprise's is 50. 1,000 is not 100. The page says the macOS maximum is shared across standard and larger runners. Shared is not doubled. An unauthenticated API call is 60 per hour. An authenticated user is 5,000 per hour. A GitHub App or OAuth app owned by an Enterprise Cloud organization is 15,000 per hour. The GITHUB_TOKEN is 1,000 per hour per repository, and 15,000 for resources that belong to an Enterprise Cloud account. 1,000 is not 5,000. 60 is not 1,000. An installation that is not on Enterprise Cloud starts at 5,000 and can gain 50 requests per hour for each repository past 20, and 50 per hour for each user past 20, and cannot pass 12,500. 12,500 is not 15,000. 20 repositories is not 20 concurrent jobs. The page's example: an app with a 15,000 limit makes 10,000 requests on your behalf, your personal 5,000 is exhausted, and the app still has 5,000 remaining. Those two 5,000s are printed. They are not the same budget. 10,000 is not 5,000.
The study people cite when they want a count of artifact uploads is a different document, and it is not a retention period. Timothy Kinsman, Mairieli Wessel, Marco Gerosa, and Christoph Treude studied GitHub Actions at the 2021 International Conference on Mining Software Repositories. They started from the RepoReapers set of 446,862 repositories classified as engineered projects. The adoption count is taken on a different set: 416,266 repositories that had received pull requests in the window they used. 446,862 is not 416,266. Of those 416,266, they identified 3,190 that had adopted at least one Action, which they print as 0.7%. 3,190 is not 0.7. They collected the data 10 months after the feature was released to the public. The introduction places the release in November 2019. 10 months is not a date in November. Workflows live in .github/workflows as YAML, .yml or .yaml. A directory is not an artifact (Kinsman, Wessel, Gerosa, and Treude, How Do Software Developers Use GitHub Actions to Automate Their Workflows?).
Inside those 3,190 repositories they found 708 different predefined Actions, spread across 20 categories. The category table's total row prints 708 and 156.77. 156.77 is not 100. The caption says the percentages do not add to 100 because about half of the Actions are assigned to two categories, a primary and a secondary. About half is not 156.77. Uncategorised is 280 Actions, 39.55%. Continuous integration is 192, 27.12%. Utilities 173, 24.44%. Deployment 87, 12.29%. Publishing 70, 9.89%. 280 is not 192. 39.55 is not 27.12. The 20 categories are the named rows. Uncategorised is an extra row, not one of the 20. Desktop tools and Mobile each print 5 and 0.70%. 0.70% of Actions is not the 0.7% of repositories. Same digits, different denominators. A typical Action, their median, is added twice and never removed or modified. Twice is not never. Added is not removed.
The frequent Actions are a usage count, not a file you can download tonight. actions/checkout appears 7,962 times. actions/setup-python 1,756. actions/cache 1,729. actions/upload-artifact 1,441. actions/download-artifact 580. 7,962 is not 1,441. 1,441 is not 580. The paper describes upload-artifact as uploading artifacts from a workflow so data can be shared between jobs and stored once the workflow completes. That sentence is a 2021 description of an Action. It is not a 90-day retention, and 1,441 repositories is not the name of your file. actions/cache at 1,729 is not a 10 GB cache and not a 7-day default. They also kept 926 projects that had used at least one Action for 6 months, and they model 6 months before adoption and 6 months after, a 12-month window, excluding 30 days. 926 is not 3,190. 6 is not 12. 30 days is not 6 months. They categorized 209 issues. Maintenance is 43 issues, 20.57%. Announcements 35, 16.74%. Requests to implement an Action 34, 16.27%. Switching tools 32, 15.31%. Problems 31, 14.83%. Those five rows are not the 209. The paper does not print their sum as the size of the set. Do not replace 209 with an addition.
Do the three proofs on one real run, in the repository that actually holds it. First, the binding. Copy the artifact name, the run identifier, and the expiry or the retention that applies. If the screen shows only a green check, write that the file was not stored. Do not infer a file from a passing test. Second, the other run. A file from a different run, or a log that is not the artifact, is not this file. A cache entry is not that second artifact. If you cannot show an object that is not this file, you have a counter, not a record. Third, the other client. A repository that belongs to someone else does not list this artifact. If the only store is a shared bucket and you cannot say whose run uploaded the file, write that. A client you cannot name is the finding. It is not a reason to tell them the build is attached.
Three moves feel like the proof and are a second problem. Deleting the artifact because the quota was close, and then describing the missing file as a cleanup. Raising a cache to 10,000 GB because that is the largest number on the settings page, while the object the client asked for is an artifact on a 90-day clock. 10,000 is a cache ceiling. It is not a file. Asking a model which artifact the run kept. The model will describe a plausible zip. It will not open the run. A digest you can read off the running process, while the client is asking which build is live, is name the commit the client is running. Reading that digest does not restore an expired artifact.
The path is ordinary when one branch's records stay distinct from the next branch's. CampAI is one role-based system for more than one branch: a student lifecycle, fees, and administration that an operator opens for a branch. The shape that matters here is one branch you can point at, distinct from the next branch. That case is not a workflow-artifact ledger. Nothing in the description is a headcount, a duration, or a result figure. If the only control on the screen deletes every client's files together, you do not have this proof. You have a shared bin.
There is a version of this call where hiring the path is the wrong purchase. The work is not sold, so there is no client repository to open. The client has asked to meet the people who will write the code. A stored zip will not hide that. The criteria for choosing a firm, when you are still choosing, sit on the page for a top SaaS development company. That page is criteria. It does not rank anyone, including us. The room only has a slide. Or the buyer only wants a template of a workflow, with no repository to put it in. Or the buyer wants a legal opinion about who owns a build output. Hire the lawyer. A white label software development partner is the wrong purchase for a blank.
When the run is real and the repository cannot name the file, the missing object is specific. The artifact on that run, a second run's file that is not this one, and a second client's repository that does not list it. A white label software development partner that expects this will put the repository where the client can download the file, before the first week is billed, because a zip on a laptop you do not hold is not an artifact you can name. One that can only paste a screenshot of a green check is telling you who holds the file. Where the next slice is one capability and the acceptance sentence names the artifact, an AI integration sprint is the shape that can require the three proofs as the definition of done. Where you are not sure which repository the current engagement writes to, a two-week AI readiness assessment maps the systems. The findings are yours. They are not 90 days, and they are not 1,441.
A subscription status, and the embedding one passage was stored with, are different objects: which status is that subscription in? and which embedding did that passage use?. Do not record either on this page. A status is not a file. A vector length is not a retention period.
Before you tell them the file is attached, do the three proofs and write the name. Name the artifact, the run, and the retention, or write that the file was not stored. Show a different run's file that is not this one. Show another client's repository that does not hold it. Do not delete the artifact to avoid the row, and do not ask a model what the build produced. A 2021 count can tell you how often a public repository used an upload action. The binding is the page you can defend.
Questions
Three records, in a repository the agency or the client can open. The artifact name, the run that uploaded it, and the retention that applies to it. A file from a different run that is not this artifact. Another client's repository that does not list it. If you cannot open the run, write that.
No. A cache and an artifact are different objects, with different defaults. The settings page prints 7 days for caches and 90 days for artifacts and logs. 7 is not 90. A count of repositories that once used an upload action is not the file on this run.
When the work is not sold under the agency's name, when the client asked to meet the builders, when the room only has a slide, when the buyer only wants a template, or when the buyer wants a legal opinion.
Find this useful? Tell Google to show you more of it.
