Stashr
<- All articles

Should You Keep Images and Other Assets in Git?

Decide which assets belong in Git, Git LFS, or a DAM by comparing release coupling, binary history, collaboration, public URLs, APIs, and transforms.

Small, stable interface assets often belong in Git. Shared, frequently updated, or delivery-heavy media often belongs in a digital asset manager. The right boundary depends on whether the file is part of the software build or content that should evolve independently from the code.

This is not an argument to remove every image from a repository. It is a guide to recognizing when binary assets are making source control perform a job it was not designed to perform.

The short answer

AssetGitDAM
Tiny icons tightly coupled to a releaseStrong fitUsually unnecessary
Code-generated fixtures and snapshotsStrong fitUsually unnecessary
Product screenshots updated by marketingAwkwardStrong fit
Shared campaign media across several sitesDuplicated or coupledStrong fit
Large video and downloadable documentsRepository burdenStrong fit
Assets that need readable public URLsRequires deployment strategyCore DAM behavior
Files edited only by developersNatural workflowOptional
Files managed by non-developersRequires repository access or toolingDashboard workflow

Use Git when asset and code must change atomically. Use a DAM when the asset needs its own ownership, metadata, delivery, and update lifecycle.

What Git does well

Git gives source files history, branches, review, reproducible checkouts, and a clear connection to software releases. Those properties are valuable for assets such as:

  • small icons imported by components;
  • local fonts with appropriate licensing;
  • application-store metadata tied to a release;
  • test fixtures and visual-regression baselines;
  • diagrams generated from repository source;
  • offline assets required for the application to start;
  • immutable artwork that changes only with code.

Keeping these files beside the code makes the build self-contained. A pull request can review the component and its icon together, and checking out the commit restores the exact pair.

Moving everything to a remote DAM would introduce a network dependency where none is needed.

Why binary history becomes expensive

Git stores history, and binary files do not merge or compress like source text. Replacing a large image or video adds another binary object to repository history even if the filename stays the same.

Git hosting platforms place limits and recommendations around large files. GitHub's Git Large File Storage documentation explains that Git LFS stores a pointer in the repository while the large object is held separately. This preserves a Git-oriented workflow but introduces its own storage, bandwidth, and client requirements.

The practical issues appear over time:

  • clones and CI fetch more data;
  • repository archives become larger;
  • old binary versions remain in history;
  • contributors need LFS installed and configured where applicable;
  • the same campaign asset is copied into several repositories;
  • non-developers need pull requests or another publishing path;
  • a content change becomes coupled to an application deployment.

These costs do not matter for a handful of small icons. They matter for a growing content library.

Decide whether the asset is code or content

Ask what should happen when the file changes.

If changing it should require code review, a tested build, and a release, Git is a sensible owner.

If a marketer should replace it without repository access, a documentation tool should upload it through an API, or several applications should use the same URL, the asset has a content lifecycle. A DAM is the stronger owner.

Examples of code-coupled assets:

  • an SVG icon used by one component;
  • an onboarding illustration bundled for offline use;
  • a test image that reproduces a decoder bug;
  • a launch screen tied to an app-store binary.

Examples of content assets:

  • article cover images;
  • press kits and data sheets;
  • social previews;
  • product screenshots that change between releases;
  • client logos used across sites;
  • campaign videos;
  • downloadable PDFs maintained by another team.

The boundary can be mixed within one product.

Deployment paths versus delivery paths

An asset in Git normally reaches users through the application build and deployment system. Its URL depends on the framework, bundler, public directory, fingerprinting strategy, and hosting platform.

That is useful when the asset should be versioned with the release. It is inconvenient when the same file belongs to several applications or must change independently.

Stashr returns a public path that reflects ownership:

/workspace/project/folder/filename

For example:

/acme/docs/articles/git-vs-dam.webp

The URL can be used in HTML, CSS, email, a CMS, or application data without copying the binary into each repository.

Readable paths also improve review. A developer can see which workspace and project owns a file from the URL itself.

Collaboration without repository access

Source control is optimized for developers. Giving every person who updates a screenshot or PDF access to a repository, branch workflow, and deployment pipeline creates unnecessary risk and training.

A DAM dashboard separates asset operations from code operations. In Stashr, collaborators can work inside a project and folder structure, while developers consume the resulting URLs or automate uploads with scoped API keys.

Stashr does not currently provide formal approval workflows, granular asset roles, or version history. If your organization needs those controls, use a platform that implements them. The benefit here is a simpler division: people manage delivery-ready assets in the library, and developers manage code in Git.

APIs instead of committed binaries

A CMS, build script, or backend can upload files to Stashr using an assets:write key. The upload includes a project identifier, optional folder, title, alt text, and tags. The response supplies the canonical delivery URL.

A read-only integration can use assets:read to discover assets and folders without gaining mutation access. Separate keys make it possible to revoke one integration without breaking others.

Management credentials stay server-side. Browser clients use public delivery URLs, not API keys.

The API-key documentation and upload guide provide the current request shape.

Image variants without committing copies

Repositories often accumulate manual renditions:

hero-mobile.jpg
hero-tablet.jpg
hero-desktop.jpg
hero-desktop@2x.jpg
hero-webp.webp

Some are genuine art direction. Others are mechanical size and format changes.

Stashr can deliver common mechanical variants from one managed image:

?w=480&format=webp&q=80
?w=1200&h=630&fit=cover&format=jpeg&q=88

The transform URL documents the presentation without adding another library asset. Stashr supports explicit WebP, AVIF, JPEG, and PNG output, common fit modes, and dimensions up to 4096. It does not automatically choose the browser format, enlarge beyond the source, or transform video.

Read the responsive images guide for a full srcset example.

Git LFS is useful, but it is not a DAM

Git LFS addresses the mechanics of large binary storage within a Git workflow. It is valuable when large files still need to be versioned and reviewed with a repository.

It does not by itself provide a product asset library, project dashboard, asset alt text, public delivery paths, image transforms, or an API designed for marketers and content systems. Those can be built around it, but they are separate concerns.

Use Git LFS when the core requirement is “this large file belongs to the repository.” Use a DAM when the requirement is “this asset belongs to a product and must be found, described, delivered, and updated independently.”

A practical hybrid policy

Many teams should use both systems.

Keep in Git:

  • small code-coupled icons and illustrations;
  • assets required for offline startup;
  • tests and fixtures;
  • files that must change atomically with code;
  • generated assets whose source and build recipe live in the repository.

Keep in the DAM:

  • article and marketing imagery;
  • downloadable documents;
  • frequently updated screenshots;
  • media shared across products;
  • files managed by non-developers;
  • large videos, audio, and campaign exports;
  • assets that need stable public URLs or delivery transforms.

Document the boundary in the repository README or contributor guide so new assets do not drift into whichever location feels convenient that day.

Migrating assets out of Git safely

Move one class at a time.

  1. Identify live references and the applications using them.
  2. Create the correct Stashr project and folder.
  3. Upload the asset with a stable filename and metadata.
  4. Store the returned delivery URL.
  5. Update references in a controlled code change.
  6. Verify the real application, responsive variants, and error behavior.
  7. Keep a rollback path through the release.
  8. Remove the old working-tree file only when no live reference requires it.

Removing a file from the current tree does not erase it from Git history. Repository-history cleanup is a separate, potentially disruptive operation and should not be bundled casually into an asset migration.

Choose the owner by lifecycle

The best rule is not a size threshold. It is lifecycle ownership.

If the binary is part of the software and should move through pull requests and releases, keep it in Git. If it is product content that needs independent management and delivery, put it in a DAM. If it is a large repository artifact that still must be versioned with code, Git LFS may be appropriate.

For the broader category, read what a DAM means for developers. For a project structure, see how to organize website assets. Or start a Stashr workspace and migrate one non-critical asset class first.