Apakah "Mapper" pola desain yang valid atau apakah itu variasi dari pola "Pabrik"?

37

Pola umum yang saya lihat adalah apa yang dikenal sebagai Mapperpola (tidak menjadi bingung dengan DataMapperyang merupakan sesuatu yang sama sekali berbeda), yang mengambil sebagai argumen semacam sumber data "mentah" (misalnya ADO.NET DataReaderatau DataSet) dan memetakan bidang ke properti pada objek bisnis / domain. Contoh:

class PersonMapper
{
    public Person Map(DataSet ds)
    {
        Person p = new Person();
        p.FirstName = ds.Tables[0].Rows[0]["FirstName"].ToString();
        // other properties...
        return p;
    }
}

Idenya adalah Gateway / DAO / Repository / etc Anda. akan memanggil ke Mapper sebelum kembali, sehingga Anda mendapatkan objek bisnis yang kaya versus wadah data yang mendasarinya.

Namun, ini tampaknya terkait, jika tidak identik, dengan pola Pabrik (dalam bahasa DDD, anyways), yang membangun dan mengembalikan objek domain. Wikipedia mengatakan ini: Pabrik DDD:

Pabrik: metode untuk membuat objek domain harus didelegasikan ke objek Factory khusus sehingga implementasi alternatif dapat dengan mudah dipertukarkan.

Dari kutipan itu, satu-satunya perbedaan yang dapat saya pikirkan adalah Pabrik DDD-style dapat diparameterisasi sehingga dapat mengembalikan jenis objek khusus jika diperlukan (misalnya BusinessCustomer versus ResidentialCustomer) sementara "Mapper" dikunci ke kelas tertentu dan hanya terjemahan.

Jadi apakah ada perbedaan antara kedua pola ini atau apakah keduanya pada dasarnya sama dengan nama yang berbeda?

Wayne Molina
sumber
Apakah ini berbeda dari ORM dan jika demikian, di mana perbedaannya?
JB King
ORM menangani pemetaan secara otomatis untuk Anda - ini lebih untuk skenario di mana Anda tidak dapat menggunakan ORM (atau harus menulis layer data Anda sendiri / ORM tipis)
Wayne Molina
1
Saya benar-benar berjuang untuk melihat bagaimana DataMapper adalah "sesuatu yang lain sama sekali."
pdr
Mungkin saya salah - saya pikir DataMapperpola melakukan akses database itu sendiri, sementara "Mapper" ini tidak menarik dari database, hanya mengubah set hasil semacam menjadi objek.
Wayne Molina
martinfowler.com/eaaCatalog/dataMapper.html Saya agak mengerti apa yang Anda maksud, tetapi membaca paragraf terakhir itu tentang yang benar. Lihatlah Katalog PEAA. martinfowler.com/eaaCatalog/index.html . Apa yang Anda jelaskan adalah sejenis Mapper, dan lebih cocok dengan DataMapper daripada yang lain.
pdr

Jawaban:

23

Meskipun ini adalah pertama kalinya saya mendengar tentang pola Mapper, bagi saya ini lebih mirip dengan pola Builder daripada Factory.

Dalam pola pabrik, Anda merangkum logika untuk membuat objek dari sejumlah kelas terkait. Contoh utama adalah situasi di mana Anda perlu membuat objek subclass tertentu dari beberapa kelas dasar abstrak tergantung pada beberapa parameter. Jadi Pabrik selalu mengembalikan pointer atau referensi ke kelas dasar, tetapi sebenarnya menciptakan objek dari kelas turunan yang sesuai berdasarkan parameter yang Anda berikan.

Sebaliknya, kelas Builder selalu membuat objek dari kelas yang sama. Anda akan menggunakannya jika pembuatan suatu objek rumit, misal konstruktornya membutuhkan banyak argumen, tidak semuanya bisa tersedia secara instan. Jadi objek pembangun mungkin merupakan tempat yang menyimpan nilai untuk argumen konstruktor sampai Anda memiliki semuanya dan siap untuk membuat "produk", atau itu dapat memberikan nilai default yang masuk akal dan memungkinkan Anda hanya menentukan argumen yang nilainya Anda perlu perubahan. Kasus penggunaan umum untuk pola Builder adalah untuk membuat objek yang mungkin Anda perlukan dalam tes unit, untuk menghindari mengacaukan kode tes dengan semua logika pembuatan.

Bagi saya seorang Mapper terdengar seperti varian Builder, di mana parameter konstruktor datang dalam bentuk catatan basis data atau beberapa struktur data "mentah" lainnya.

Dima
sumber
Hmm saya pernah mendengar tentang Builder tetapi tidak 100% menyadari apa yang diperlukan - ini membantu membersihkan semuanya! Hampir terdengar perbedaan utamanya adalah Factory mengembalikan antarmuka / kelas abstrak yang benar-benar kelas beton berdasarkan parameter (jika itu masuk akal) sementara Builder / Mapper mengambil data aktual dan memetakannya ke properti, tanpa banyak logika (jika ada) ?
Wayne Molina
1
@Waine M: cukup banyak. Meskipun bisa ada banyak logika dalam Builder, karena pemetaan data ke properti mungkin tidak sepenuhnya lurus ke depan. Bahkan, pembangun dapat berisi pembangun lain untuk membangun parameter. :)
Dima
5
Pola Builder memungkinkan Anda untuk menempatkan semua informasi yang diperlukan untuk membangun objek yang kompleks (biasanya tidak dapat diubah) dari waktu ke waktu dan kemudian instantiate objek di akhir proses. Bukan itu yang terjadi di sini.
pdr
+1 Setuju bahwa ini adalah pendekatan yang masuk akal, memiliki kelas 'mapper' yang terpisah untuk bertindak sebagai mediator antara objek DTO dan objek model domain. Ini juga berguna ketika objek model domain perlu dimasukkan ke dalam beberapa keadaan khusus ketika sedang dibangun (yaitu. NET ISupportInitialize antarmuka).
MattDavey
@ pdr, saya setuju bahwa seorang Mapper tidak persis seperti pembangun, karena semua data tersedia sekaligus. Tetapi sangat mirip, karena hanya membangun satu jenis objek.
Dima
8

Satu-satunya hal yang umum tentang Mapper, Builder dan Factory adalah mereka memberikan "produk buatan" - dan instance objek dari suatu tipe. Untuk menghindari kebingungan, saya merujuk pada diskusi berikut untuk definisi masing-masing.

  1. Mapper - dekat dengan apa yang dijelaskan di sini: http://www.codeproject.com/KB/library/AutoMapper.aspx . Ini tidak persis sama dengan di atas - tetapi terdekat saya temukan tentang mapper.

  2. Builder - sebagaimana didefinisikan di sini: http://www.oodesign.com/builder-pattern.html

  3. Factory - didefinisikan di sini: http://www.oodesign.com/factory-pattern.html

Mapper pada dasarnya adalah sebuah konstruktor dalam ke luar. Misalkan untuk sementara waktu, jika Anda tidak memiliki mapper - Ketika Anda masih membutuhkan banyak set parameter mereka semua argumen pada konstruktor. Sekarang seiring perkembangannya, beberapa aplikasi tidak menyadari atribut tambahan yang perlu dibangun di bawah konstruktor di mana seseorang menghitungnya atau menggunakan default. Yang penting adalah bahwa mapper dapat melakukan ini untuk Anda - dan akan lebih berguna jika ini memiliki keterkaitan dengan objek-objek eksternal untuk memutuskan algoritma konstruksi seperti itu.

Builder sangat berbeda dari mapper. Pembangun sangat penting ketika objek lengkap disusun menggunakan banyak bagian objek. Ini semacam merakit benda-benda dengan menyatukan banyak bagian. Bahkan inisialisasi objek bagian individu terkait dengan keberadaan bagian lain.

Pola pabrik terlihat sangat sederhana sejak awal. Ini mengembalikan objek yang baru dibangun. Jika ada konstruktor biasa yang dapat memberi saya contoh berfungsi penuh menggunakan operator seperti baru ()? mengapa saya membutuhkan pabrik yang memberi saya hasil yang sama?

Namun, penggunaan pola pabrik biasanya sangat spesifik; meskipun paling sering, tidak ditampilkan dalam literatur di mana ini diterapkan. Biasanya, aplikasi membuat pabrik yang dibagi ke berbagai objek yang perlu membuat objek produk seperti itu selama eksekusi. Ketika banyak produk tersebut dibuat, metode Pabrik memungkinkan pembuatan objek berdasarkan kebijakan tertentu misalnya, seseorang dapat memaksa template tertentu yang digunakan oleh metode pabrik ketika semua objek dibuat. Ini tidak seperti metode pembangun; di sini produk yang keluar hanya satu (dan independen). Ini juga tidak seperti mapper; di sini data eksternal ditetapkan untuk membuat objek sesuai klien sebenarnya minimal. Pola pabrik benar-benar memberikan (seperti namanya) objek produk yang secara konsisten serupa!

Dipan.

Dipan Mehta
sumber
4

Ketika saya melihat jawaban, saya melihat semua responden memberikan jawaban yang secara semantik salah. Saya pikir ini karena Anda terlalu fokus pada pertanyaan, yang difokuskan pada bagaimana mapper terkait dengan pabrik atau pembangun.

Padahal Mapper sebenarnya TIDAK mirip pabrik atau pembangun. Mapper paling mirip dengan pola adaptor (menggunakan bahasa GoF). Pola adaptor menyediakan fungsionalitas untuk mengubah satu representasi ke yang lain. OP merujuk ke DataSet dan DataReader di ADO.NET - nah bagaimana dengan SqlDataAdapter? Jawabannya ada dalam nama. Mapper adalah nama baru untuk sesuatu yang sudah lama diketahui oleh pemrogram lama: adaptor.

Mapper mengubah satu representasi ke yang lain - definisi utama dari pola adaptor.

Soto Ruben
sumber
1

Apa yang Anda lakukan di sini sebenarnya semacam konversi tipe (Anda mengonversi data mentah menjadi objek bisnis). Anda dapat menggunakan Pola Pabrik untuk melakukan hal itu (yaitu, ketik konversi), jadi ya, dalam beberapa cara, kelas Anda adalah pabrik (meskipun saya akan menggunakan Pabrik Statis untuk itu).

Oliver Weiler
sumber
0

Pembangun merangkum logika bisnis yang kompleks untuk membangun objek. Mapper di sisi lain hanya harus menyalin bidang dari satu ke yang lain.

Misalnya peta dari Objek Basis Data Karyawan ke Domain Objek Karyawan, peta dari Objek Karyawan Domain ke Kontrak Klien.

Pembangun di sisi lain menjadi tuan rumah beberapa keputusan bisnis untuk membangun objek. Dari sudut pandang Tanggung Jawab Tunggal, ini masuk akal.

pengguna95940
sumber