Resizer 4.0.4 - Oct 25 2015

Download source, binaries, plugins, and sample code (15MB)

Up to 10x faster overall; 43x faster rendering with our custom C rendering engine. We also improved image quality and added precise sharpening tools. Read v4 highlights here

Excellent backwards-compatibility with v3.X, although we now require .NET 4.5.2 or higher.

Your purchase confirmation e-mail includes a link to download DRM-free binaries. You can use the public binaries and nuget packages if you've installed your license key in Web.config. See a red dot on your images? That means your license key is missing.

Render PDFs without the GPL via PdfiumRenderer.

New: Free disk caching via TinyCache.

Replace InterceptModule with AsyncInterceptModule to go async

Fast, consistent, async blob providers based on new ImageResizer.Storage.BlobProviderBase

Everything either Apache 2 or AGPL v3 licensed in addition to commercial licenses.

All dependencies updated to latest version. We now maintain a better, faster version of FreeImage.

.NET 4.5 or .NET 4.5.2 is now required by the core and all plugins. What does this mean?

  • We no longer support Windows XP or Windows Server 2003. You'll also want Visual Studio 2013 or newer. FastScaling requires .NET 4.5.2
  • You no longer need to install MvcRoutingShim and ImageResizer.Mvc.dll. ImageResizer is Routing compatible.
  • Extension methods are back! All our utility functions are now accessible in the ImageResizer.ExtensionMethods namespace.
  • We can access APIs for better filesystem consistency.
  • We can go async!

Changes in the pipeline

Assign StaticFileHandler for all VPP-only requests (Fixes #140). Apply .Rewrite changes to all (existing) image requests (fixes fake extension issue #8 and #113). Call ImageMissing for all image 404, not just those processed.

Core: Refactor InterceptModule & AsyncInterceptModule to use HttpModuleRequestAssistant, to deduplicate code.

Commands "ignoreicc" and "anchor" should not trigger processing alone. Autorotate should, as that has been legacy behavior.

Core: "scale", "stretch", "cropxunits", "cropyunits","mode" should not trigger image processing, as they are only modifier commands, and do nothing if used alone.

pipeline.authorizeAllImages defaults to "true" - So AuthorizeImage will be called for all image requests now by default.

Core: Add <pipeline defaultCommands"" /> XML setting; provides default commands

You can now delete certain querystring keys before they reach ImageResizer. Useful for removing a cache buster - so that a CDN cache can be busted without busting ImageResizer's disk cache at the same time. <pipeline dropQuerystringKeys="key1,key2,random" />

Keep in mind that the async pipeline can only access data from plugins which implement IVirtualFileAsync (or inherit from BlobProviderBase). The standard pipeline can access files exposed by any VirtualPathProvider.

Virtual file (blob provider) plugins are now much easier to create.

  • ImageResizer.Storage provides a standard, unified BlobProviderBase class with 90% of the functionality you need. Override FetchMetadataAsync and OpenAsync, and you'll have a full-fledged provider with async/sync pipeline support, metadata caching, and even (optional) exposure through the ASP.NET VirtualPathProvider system.

  • No more VirtualPathProvider. At startup, we install a single VirtualPathProviderShim. Any plugin can implement IVirtualImageProviderVpp and return true from bool VppExposeFile(string virtualPath). It will then be wrapped in a VirtualFile instance and shared to all systems which access the VirtualPathProvider system.

New interfaces include: IVirtualImageProviderAsync, IVirtualFileAsync, IVirtualImageProviderVpp, IVirtualImageProviderVppCaching, IVirtualFileWithModifiedDateAsync, IVirtualFileCacheAsync

All providers now default to vpp=true

Plugins referenced in Web.config are loaded differently

In V3, we used a convention-based approach to generate dozens of possible fully-qualified type names, and then tried those against each loaded assembly. This approach was slow, and broke with .NET 4, as it only loads assemblies with explicit references. We now maintain a hints file (which includes the assembly name), and use that to ensure a faster and more reliable load-time experience.

When installed via Web.config, custom plugins will need to be referenced by their fully-qualified name, such as "MyRootNamespace.MyPluginNamespace.MyPluginClass, MyAssembly"

Our blob providers have been rewritten.

They are now consistent in interface, functionality, and configuration, as they inherit from BlobProviderBase. This means you'll have to update some of your configuration.

We've dropped some deprecated (and redundant) classes

These include: ImageResizer.Mvc, AzureReader, S3Reader, Controls, StreamUtils, UrlHasher, WpfBuilder.

Smaller improvements

  • Autorotate is now built-in - no longer a plugin you must install.
  • Major core changes:
  • Add ImageJob.FinalWidth and ImageJob.FinalHeight (all pipelines). Closes #10. Needs unit tests.
  • Use NuGet restore, .NET 4.5 compatibility
  • Expose LoadNativeDependenciesForType(Type t) from Config.Plugins. Previously there was no code-based method to load a native dependency manually.
  • DiskCache: Attempt semi-transactional writes. Write to temporary file, then rename.
  • Update Webp to 0.4
  • Migrate to xUnit from MbUnit, improve code coverage.
  • Add Pipeline.AuthorizeAllImages configuration. When true, URL authorization and the AuthorizeImage event will be executed for all image requests, not just those processed or cached by ImageResizer.
  • Add BeforeEncode and EndBuildJob to AbstractImageProcessor and ImageBuilder to enable easier benchmarking.
  • Add IProfiler interface and ImageJob.Profiler property.
  • Add PluginConfig.AddPluginByName(string name, NameValueCollection pluginConfig = null) to enable code-driven installation of arbitrary plugins.
  • Add ImageResizer.Util.AsyncUtils class and CopyToMemoryStreamAsync extension method.

Bug fixes:

  • Fix layout bug #154 (using mode=crop and scale=canvas together)
  • Fixes #139, VirtualPathProviderShim was not installed. Caused 404s for as-is files from AzureReader2 and S3Reader2.
  • Fixes #135 - Fix WIC bug causing stack overrun. COM IStream mixes use of 32 and 64 bit pointers. We were using the Microsoft-supplied MemoryIStream class, and failed to comprehensively audit the interfaces as we do with our own code.
  • Fixed: WIC builder no longer throws a NullReferenceException when provided a null stream. (This was preventing the correct error message)
  • Fix #117 - AdvancedFilters applies effects only the the image portion of the canvas. Does not work if the image has been rotated arbitrary angles. Region boundary rounding may effect equalization or white balance calculation. Add LayoutBuilder.GetRingAsRectF(name) function.
  • Fixes #77; Ensure diagnostics page redaction code can handle a null node.
  • Fix Core Bug: EndProcess is never called for BuilderExtension plugins.
  • PathUtils.AddQueryString("/path?","key=value") should now produce "/path?key=value" instead of "/path?&key=value"
  • Don't nullref when passed a ~/aspnet path outside of ASP.NET. Drop the tilde and pass to the virtual path providers.
  • Fixes issue #54, InvalidOperationException in TinyCache when there are 0 recent reads. Supersedes pull request #105. Regression tests added.
  • Prevent nullref when VirtualFolder is used outside of an ASP.NET application.
  • Fixes #74. Delete unfinished image output file in case of an exception. Doesn't handle situation where source and dest path are the same; file will be deleted.
  • Fixes #44. Switch from FileStream.Flush() to FileStream.Flush(true) to ensure files are written to disk before the method completes.
  • Core: NoCache will buffer data to memorystream before writing to output stream. InvalidOperationException when accessing stream.Position within Bitmap.save - despite buffer = true. )
  • Fix bug where watermark imagequery commands are processed with the wrong Config

Fix incorrect status code when any IVirtualFileCache is installed and an 404 occurs. Source(Mem/Disk)Cache call .Open and .Read during the GetFile() stage (callers expect only a null result on not found failure). PipelineConfig.GetFile must absorb FileNotFound exceptions to prevent the behavior contract from being violated.

Catch DirectoryNotFoundException as well as FileNotFoundException, and cause a 404

Changes in plugins

  • DiskCache no longer supports HashModifiedDate (it's always true).
  • All storage plugins now default to vpp=true

Breaking changes for custom plugins:

  • breaking plugin api change: Replace AbstractImageProcessor.buildToStream and AbstractImageProcessor.buildToBitmap with AbstractImageProcessor.BuildJobBitmapToStream and ImageBuilder.BuildJobBitmapToBitmap.
  • breaking plugin api change: Replace ImageState.imageAttributes with float[][] ImageState.colorMatrix - permits InternalDrawImage to be implemented. ImageAttributes is write-only, cannot be read from.
  • InterceptModule now combines the date into the RequestKey, so no more conditional logic in plugins. ResponseArgs.HasModifiedDate and ResponseArgs.GetModifiedDateUtc are now obsolete.
  • Core: Replace ILicenseStore/ILicenseService with ILicenseProvider and ILicensedPlugin. Add WebConfigLicenseReader to plugins collection by default on asp.net. Replace LicenseVerifier project with offline-only implementation.

Deprecated functionality now removed:

  • Drop deprecated ImageResizer.Mvc AzureReader, S3Reader and Controls plugins.
  • Drop long-time deprecated StreamUtils class.
  • Drop long-time deprecated UrlHasher class.
  • Delete stub WPF plugin. WPF support is a sub-par goal considering it's poor image quality and other options available.
  • Drop misspelled, obsolete, duplicate CropRectange property from Instructions class.
  • Drop ImageResizer.Collections.ReadOnlyDictionary (unused)
  • Drop Builder and BuildTools; we now use FAKE and FakeBuilder instead
  • Delete WicCop; we never used it.
  • Drop all symbols-only nuget packages, makes build times 2x faster

All releases