Skip to content

Conversation

@Gimcrack
Copy link

@Gimcrack Gimcrack commented Dec 8, 2025

I noticed some odd behavior when using prefixes, so I threw this together. Happy to discuss. Thanks!

Summary

CloudinaryStorageAdapter: Normalize paths, prevent double prefixing, and infer resource type for getUrl/write

This PR improves CloudinaryStorageAdapter path handling and resource-type detection to produce correct public IDs and URLs across platforms, while avoiding double application of the configured prefix. It also adds comprehensive unit tests to guard against regressions.

Key Changes

  • Path normalization and ID construction
    • Normalize backslashes to forward slashes for all incoming paths.
    • Build public_id using dirname/filename with forward slashes only, ensuring nested directories are preserved.
    • Strip leading ./ or / when applying a prefix to avoid prefix/./file or prefix//file artifacts.
    • Prevent double prefixing when a path is already prefixed.
  • Resource type inference
    • Detect MIME type from the normalized path and choose resource_type via:
      • image/*image
      • video/*video
      • else → raw
  • getUrl correctness
    • getUrl now resolves the correct public_id and inferred resource_type before querying Admin API, ensuring the returned secure URL matches the resource.
  • Prefix application helper
    • applyPrefixToPath now short-circuits if the incoming path already begins with the configured prefix, preventing duplication in list/delete directory operations.
  • Internal/API ergonomics
    • Use PHP’s str_starts_with and a small match(true) to improve clarity.

Files Changed

  • src/CloudinaryStorageAdapter.php
    • Refactor prepareResource to normalize paths, construct IDs consistently, apply prefix safely, and infer resource_type from MIME type.
    • Guard applyPrefixToPath against double prefixing.
  • tests/Unit/CloudinaryStorageAdapterTest.php
    • Add tests for:
      • Image path with backslashes → normalized public_id and image resource type.
      • Video path → video resource type.
      • Non-image/video path → raw resource type.
      • Prefix behavior with leading ./ and / stripping.
      • Nested backslash paths under a prefix.
      • getUrl behavior for images and videos.
      • getUrl with prefixed adapter:
        • Applies prefix when needed.
        • Does not double-apply when path already includes prefix.
        • Handles leading slash without double prefix.
        • Normalizes backslashes in incoming path.

Why

  • Fixes incorrect public_id generation on Windows-like inputs (backslashes), preventing broken uploads/URL lookups.
  • Prevents Fixtures/Fixtures/... or Fixtures//... issues when users pass already-prefixed paths or paths with leading separators.
  • Ensures correct resource_type is used for Admin/Upload API calls, avoiding 400s due to mismatched types.

Behavior Examples

  • Incoming: dir\nested\picture.jpg
    • Before: Could become malformed public_id with backslashes and wrong resource_type.
    • After: public_id = dir/nested/picture, resource_type = image.
  • Incoming with prefix Fixtures: /file.jpg or ./file.jpg
    • After: public_id = Fixtures/file, no double prefixing.
  • getUrl('media/clip.mp4')
    • After: Queries asset('media/clip', ['resource_type' => 'video']) and returns secure_url.

Tests

  • Expanded unit tests cover the above scenarios and serve as regression tests for path normalization and prefix logic.

Backwards Compatibility

  • Behavior changes are corrective and align with expected usage:
    • More accurate public_id and resource_type detection.
    • Safer prefix handling. Existing code that relied on prior incorrect behavior may see corrected IDs/URLs.
  • Requires PHP with str_starts_with (PHP 8.0+).

Risks

  • Edge cases in prefix comparison: str_starts_with($trimmed, $this->prefix) assumes exact textual prefix; if users intentionally pass different-cased prefixes, behavior will not double-apply but may differ on case-sensitive expectations.

Rollout/Verification

  • Run the added unit tests to verify behavior across common cases.
  • Manually verify URLs for a few sample images and videos with and without prefixes.

Checklist

  • Path normalization across all entry points
  • No double prefixing in getUrl, listContents, delete*
  • Correct resource_type inference for image/video/raw
  • Unit tests for regressions and new behavior

@vercel
Copy link

vercel bot commented Dec 8, 2025

@Gimcrack is attempting to deploy a commit to the Cloudinary DevX Team on Vercel.

A member of the Team first needs to authorize it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant