MapOnly 1.0.0

dotnet add package MapOnly --version 1.0.0
                    
NuGet\Install-Package MapOnly -Version 1.0.0
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="MapOnly" Version="1.0.0" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="MapOnly" Version="1.0.0" />
                    
Directory.Packages.props
<PackageReference Include="MapOnly" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add MapOnly --version 1.0.0
                    
#r "nuget: MapOnly, 1.0.0"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package MapOnly@1.0.0
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=MapOnly&version=1.0.0
                    
Install as a Cake Addin
#tool nuget:?package=MapOnly&version=1.0.0
                    
Install as a Cake Tool

Welcome to MapOnly Documentation

Introduction

MapOnly is a simple and lightweight .NET library for object-to-object mapping. If you need a straightforward library focused solely on mapping without extra complexity, MapOnly is the perfect choice for you.

Requirements

  • .NET Standard 2.0+
  • .NET Standard 2.1+
  • .NET 6.0+
  • .NET 8.0+
  • .NET Framework 4.6.1+

Installation

# Using .NET CLI
dotnet add package MapOnly

# Using Package Manager Console
Install-Package MapOnly

# Or search "MapOnly" in NuGet Package Manager

Features

  • ✨ Simple and intuitive API
  • 🚀 Lightweight with minimal dependencies
  • 🎯 Automatic property mapping by name
  • 🔧 Custom property mappings
  • 🚫 Property ignore functionality
  • 💎 Support for constant values
  • 🏷️ Attribute-based configuration
  • ✅ Fully tested and documented

Quick Start

Basic Usage (No Configuration Required)

For simple object mapping where properties have the same names:

using MapOnly;

// Map using the new instance creation overload (recommended)
var userDto = user.Map<User, UserDto>();

// Or if you need to map to an existing instance
var existingDto = new UserDto();
user.Map(existingDto);

With Configuration

For custom mappings, configure once at application startup:

// At application startup
MapExtension.Create<User, UserDto>()
    .Add(u => u.FullName, dto => dto.DisplayName)
    .Ignore(dto => dto.InternalField);

// Then use throughout your application
var userDto = user.Map<User, UserDto>();

Methods

1. Create

This method creates a mapping configuration between two classes. If the classes have the same property names, automatic mapping will work without configuration.

Syntax
using MapOnly;

MapExtension.Create<SourceClass, DestinationClass>()
Example
MapExtension.Create<UserViewModel, User>()

2. Add

For properties with different names or when you need to set constant values, use the Add method.

Syntax
using MapOnly;

// Map properties with different names
MapExtension.Create<SourceClass, DestinationClass>()
    .Add(source => source.Property1, dest => dest.Property2);

// Set a constant value
MapExtension.Create<SourceClass, DestinationClass>()
    .Add(dest => dest.Property1, "ConstantValue");
Example
MapExtension.Create<UserViewModel, User>()
    .Add(v => v.DisplayName, u => u.FullName)
    .Add(u => u.CreatedBy, "Admin");

3. Ignore

Use this method to exclude properties from mapping.

Syntax
using MapOnly;

MapExtension.Create<SourceClass, DestinationClass>()
    .Ignore(dest => dest.Property1);
Example
MapExtension.Create<UserViewModel, User>()
    .Add(x => x.Birthday, a => a.UpdatedDate)
    .Ignore(u => u.CreatedDate)
    .Ignore(u => u.CreatedUser)
    .Ignore(u => u.IsActive)
    .Ignore(u => u.UpdatedDate)
    .Ignore(u => u.UpdatedUser);

4. Map

Converts one object to another following configured or automatic mappings.

Syntax
// Recommended: Automatically create destination instance
var destination = source.Map<SourceClass, DestinationClass>();

// Alternative: Map to existing instance (useful when updating objects)
var destination = new DestinationClass();
source.Map(destination);
Example
// Simple mapping - automatically creates UserViewModel instance
var viewModel = user.Map<User, UserViewModel>();

// Map collections
var userViewModels = users
    .Select(u => u.Map<User, UserViewModel>())
    .ToList();

// Map to existing instance (e.g., updating an entity)
var existingUser = GetUserFromDatabase(id);
userViewModel.Map(existingUser);
SaveChanges();

Advanced: Attribute-Based Mapping

You can also use attributes to control mapping behavior:

public class MyClass
{
    public int Id { get; set; }
    
    [MapAttribute(Ignored = true)]
    public string InternalProperty { get; set; }
}

Configuration

Configure your mappings once at application startup. MapOnly uses a static configuration that persists throughout your application's lifetime.

ASP.NET Core / Modern .NET

Program.cs or Startup.cs:

// Program.cs (.NET 6+)
var builder = WebApplication.CreateBuilder(args);

// Configure MapOnly mappings
ConfigureMappings();

var app = builder.Build();
app.Run();

static void ConfigureMappings()
{
    MapExtension.Create<User, UserDto>()
        .Add(u => u.FullName, dto => dto.DisplayName)
        .Ignore(dto => dto.CreatedDate);

    MapExtension.Create<Product, ProductDto>()
        .Ignore(dto => dto.InternalId);
}

Or create a dedicated configuration class:

// MappingConfiguration.cs
public static class MappingConfiguration
{
    public static void Configure()
    {
        ConfigureUserMappings();
        ConfigureProductMappings();
    }

    private static void ConfigureUserMappings()
    {
        MapExtension.Create<User, UserDto>()
            .Add(u => u.FullName, dto => dto.DisplayName)
            .Ignore(dto => dto.CreatedDate);
    }

    private static void ConfigureProductMappings()
    {
        MapExtension.Create<Product, ProductDto>()
            .Ignore(dto => dto.InternalId);
    }
}

// Program.cs
MappingConfiguration.Configure();

ASP.NET MVC / Web API (.NET Framework)

Global.asax.cs:

protected void Application_Start()
{
    // Other configurations...
    AreaRegistration.RegisterAllAreas();
    RouteConfig.RegisterRoutes(RouteTable.Routes);
    
    // Configure MapOnly
    MappingConfiguration.Configure();
}

Console / Desktop Applications

Program.cs:

static class Program
{
    [STAThread]
    static void Main()
    {
        // Configure mappings at startup
        MappingConfiguration.Configure();

        // Rest of your application
        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);
        Application.Run(new MainForm());
    }
}

Best Practices

  1. Configure Once, Use Everywhere: Set up all mappings at application startup
  2. Organize by Domain: Group related mappings together in separate methods
  3. Keep It Simple: Only configure mappings for properties that differ between source and destination
  4. Use the Automatic Creation Overload: Prefer source.Map<TSource, TDest>() over source.Map(new TDest())
// ✅ Recommended
var dto = user.Map<User, UserDto>();

// ❌ Less efficient (creates instance before calling Map)
var dto = user.Map(new UserDto());

// ✅ Good - when you need to update an existing instance
var existingEntity = repository.Get(id);
dto.Map(existingEntity);
repository.Update(existingEntity);

Change Log

Version 0.3.0 (Latest)

  • 🎯 Multi-target support: .NET Standard 2.0/2.1, .NET 6.0/8.0
  • ✨ Nullable reference types enabled
  • 🐛 Bug fixes: Better null handling, skip missing properties
  • 📚 Improved documentation and error messages
  • ✅ Comprehensive unit test coverage
  • 🔒 Security improvements

Version 0.2.1

  • Initial stable release

License

MIT License - See LICENSE.txt for details

Contributing

Contributions are welcome! Please feel free to submit a Pull Request.

Product Compatible and additional computed target framework versions.
.NET net5.0 was computed.  net5.0-windows was computed.  net6.0 is compatible.  net6.0-android was computed.  net6.0-ios was computed.  net6.0-maccatalyst was computed.  net6.0-macos was computed.  net6.0-tvos was computed.  net6.0-windows was computed.  net7.0 was computed.  net7.0-android was computed.  net7.0-ios was computed.  net7.0-maccatalyst was computed.  net7.0-macos was computed.  net7.0-tvos was computed.  net7.0-windows was computed.  net8.0 is compatible.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed.  net9.0 was computed.  net9.0-android was computed.  net9.0-browser was computed.  net9.0-ios was computed.  net9.0-maccatalyst was computed.  net9.0-macos was computed.  net9.0-tvos was computed.  net9.0-windows was computed.  net10.0 was computed.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
.NET Core netcoreapp2.0 was computed.  netcoreapp2.1 was computed.  netcoreapp2.2 was computed.  netcoreapp3.0 was computed.  netcoreapp3.1 was computed. 
.NET Standard netstandard2.0 is compatible.  netstandard2.1 is compatible. 
.NET Framework net461 was computed.  net462 was computed.  net463 was computed.  net47 was computed.  net471 was computed.  net472 was computed.  net48 was computed.  net481 was computed. 
MonoAndroid monoandroid was computed. 
MonoMac monomac was computed. 
MonoTouch monotouch was computed. 
Tizen tizen40 was computed.  tizen60 was computed. 
Xamarin.iOS xamarinios was computed. 
Xamarin.Mac xamarinmac was computed. 
Xamarin.TVOS xamarintvos was computed. 
Xamarin.WatchOS xamarinwatchos was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.
  • .NETStandard 2.0

    • No dependencies.
  • .NETStandard 2.1

    • No dependencies.
  • net6.0

    • No dependencies.
  • net8.0

    • No dependencies.

NuGet packages

This package is not used by any NuGet packages.

GitHub repositories

This package is not used by any popular GitHub repositories.