Cara modern menulis ulang file lib

21

Masalahnya sudah diketahui: libkelas dimuat secara eksklusif melalui autoloader, dan kami tidak dapat mengubahnya selain:

  • Menyalinnya seluruhnya ke codePool yang diperiksa lebih awal dari lib.
  • Menginstal autoloader PSR-0 , menentukan classmap autoload, dan kemudian menyalin file seluruhnya ke dalam struktur folder itu sebagai gantinya. [solusi saya saat ini]

Saya berada di tempat yang sulit karena saya ingin berpotensi menyentuh banyak file-file ini - tetapi demi kewarasan dan stabilitas / peningkatan kemampuan toko saya tidak ingin menyalin seluruh kelas perpustakaan.

Sekarang jelas ada solusi potensial untuk masalah ini, tetapi mereka semua datang dengan masalah mereka sendiri:

  • Buka rute AOP dan gunakan perpustakaan berbasis PHP seperti Go! AOP : Terakhir saya periksa ini akan membutuhkan kelas Magento untuk dimuat oleh komposer autoloader, bukan hanya yang tersedia. Flyingmana telah melakukan beberapa pekerjaan di bidang ini, tetapi sudah pasti tidak siap untuk penggunaan produksi dan kebutuhan saya lebih cepat. Saya juga ingin mengirim sebagai ekstensi, dan itu akan memerlukan lebih banyak pengaturan komposer.
  • Buka rute AOP dan gunakan ekstensi PHP asli : Mungkin yang paling menguntungkan saat ini, tetapi akan memerlukan menginstal ekstensi terpisah, belum lagi bahwa itu tidak akan bekerja dengan HHVM.
  • Gunakan classkit dan / atau runkit PHP : Ini adalah ekstensi PHP asli lain sehingga memiliki masalah yang sama seperti di atas.
  • Patch situs panggilan untuk menggunakan \Danslo\Varien_Xversi namespaced ( ) saya sendiri , kemudian diperluas dari yang asli ( \Varien_X): Ada terlalu banyak callites untuk ditambal dan itu akan membutuhkan sejumlah penulisan ulang yang konyol. Bukan pilihan.
  • Roll my own: Seharusnya mungkin untuk:

    1. Tulis autoloader saya sendiri.
    2. Salin kelas asli ke folder terpisah ( {root_dir}/var/tmp), bungkus dalam namespace \Magento { < original contents > }.
    3. Sertakan file itu.
    4. Sertakan kelas modifikasi saya OriginalClass extends Magento\OriginalClass {}

Kelemahan dari ini jelas: pembuatan kode dinamis, regex, sedikit overhead untuk memuat kelas yang ditulis ulang. Tapi saya hampir yakin bahwa pada titik ini akan mengalahkan menyalin ~ 5.000 baris kode ketika saya hanya ingin menyentuh / menambah ~ 100 baris.

Saya tahu saya banyak bertanya, tetapi adakah yang modern dan relatif bersih di luar sana yang membantu menyelesaikan masalah ini?

Daniel Sloof
sumber
1
Apakah Anda sudah menemukan solusi pengamat Alans? stackoverflow.com/a/4636662/158325
B00MER

Jawaban:

9

Memutuskan untuk menerapkan Go! Kerangka kerja AOP di Magento.

Lihat Danslo_Aop di github.

Daniel Sloof
sumber
2

Buka rute AOP dan gunakan perpustakaan berbasis PHP seperti Go! AOP: Terakhir saya periksa ini akan membutuhkan kelas Magento untuk dimuat oleh komposer autoloader, bukan hanya yang tersedia. Flyingmana telah melakukan beberapa pekerjaan di bidang ini, tetapi sudah pasti tidak siap untuk penggunaan produksi dan kebutuhan saya lebih cepat. Saya juga ingin mengirim sebagai ekstensi, dan itu akan memerlukan lebih banyak pengaturan komposer.

Saya ingin menambahkan Go itu! Kerangka kerja AOP dapat bekerja tanpa komposer, saya dapat membantu dengan konfigurasi (buat saja masalah pada github untuk itu). Komposer diperlukan hanya untuk integrasi transparan dengan aplikasi modern.

Cukup ganti include $filenameatau require $filenamedi bootstrap Anda dengan include FilterInjectorTransformer::rewrite($filename)dan konfigurasikan autoloader untuk Go! AOP itu sendiri.

lisachenko
sumber
1
Wow bagus. Saya pasti akan mencoba ini.
Daniel Sloof
0

Pergilah dengan pendekatan autoloader. Ganti nama / semua / kelas di lib dengan awalan:

find lib -name '*.php' -exec sed -e 's,^class ,class Oldlib_,' {} +

Jalankan "override fixer" berikut ini setiap kali Anda menambahkan file ke mylib:

find lib -name '*.php' -print | while read FILE
do
    classname=$(echo ${FILE}|sed -e 's,^lib/,,' -e 's,\.php$,,' -e 's,/,_,g')
    if [ ! -f mylib/${FILE#lib/} ]; then
        # ensure is_a works by providing a stub with correct classname
        echo "class ${classname} extends Oldlib_${classname} {}" > mylib/${classname}.php
    elif [ -f mylib/${classname}.php ]; then
        # we have a new override, but the old file still exists
        rm mylib/${classname}.php
    fi
done

Ajari autoloader untuk kembali mylib/${classname}.phpjika ada dan mylib/full/path/to/class.phpjika tidak dan mylib/full/path/to/class.phptidak.

Masukkan override Anda mylib/full/path/to/class.phpdan perpanjang versi Oldlib_.

Upgrade hanya memutar kembali awalan di lib / meng-upgrade-nya, menerapkan kembali awalan, jalankan kembali fixer override. Yang tersisa adalah barang-barang yang dipindahkan lib/dan sebelumnya diganti, tetapi itu tidak terkait dengan masalah. Masalah Anda mungkin adalah jumlah file pada direktori mylib /, tapi saya yakin Anda bisa menyelesaikannya :).

Melvyn
sumber
Pendekatan ini memperkenalkan banyak risiko dan hal-hal untuk dipertahankan terutama dalam hal peningkatan. Ini juga melanggar aturan "jangan sentuh inti". Selain itu, ini bukan opsi yang layak untuk pengembang ekstensi.
beeplogic
Dengan segala hormat ~ meskipun solusi Anda berfungsi ... itu tidak dapat dianggap sebagai a moderncara menulis ulang file lib. Pemrograman imperatif adalah sekolah kuno;)
Eddie B
0

Anda juga dapat menentukan Stream kustom dan menambahkannya di atas jalur pengisian otomatis. Ini bekerja dengan autoloader dan adopsi minimal. Lihat contoh

KAndy
sumber