React: Peringatan adalah mengubah input radio jenis yang tidak terkendali untuk dikendalikan ...

Dibuat pada 16 Mei 2016  ·  30Komentar  ·  Sumber: facebook/react

Saya memiliki kode ini

       <input name='test' value={1} type='radio' />
       <input name='test' value={2} type='radio' defaultChecked />

https://jsfiddle.net/69z2wepo/42137/

Dan saat saya mengklik radio, saya diberi peringatan
Peringatan: Tes mengubah input jenis radio yang tidak terkontrol untuk dikontrol. Elemen input tidak boleh beralih dari tidak terkontrol ke terkontrol (atau sebaliknya). Putuskan antara menggunakan elemen masukan yang terkontrol atau tidak terkontrol selama masa pakai komponen. Info lebih lanjut: https://fb.me/react-controlled-components

Jadi tidak jelas mengapa atau apakah itu bug?

Bug

Komentar yang paling membantu

@LiIa

Artinya this.state.isMustFill tidak selalu true atau false , melainkan true atau undefined , misalnya. Pastikan selalu boolean, dan masalahnya akan hilang.

Semua 30 komentar

Itu bug. : +1:

Saya pikir itu bereaksi terhadap value yang disetel tanpa mempertimbangkan bahwa itu adalah input radio yang menggunakan value berbeda.

Saya memiliki masalah terkait, saya mendapatkan peringatan bahwa saya mengalihkan komponen yang tidak terkontrol ke yang terkontrol dengan kode ini:

function CheckboxButton({checked, onChange, textComponent} = {}) {
    return (
        <label className='checkbox-button'>
            <input
                type='checkbox'
                checked={checked}
                onChange={onChange}/>
            {textComponent}
        </label>
    );
}

Jika saya menambahkan value prop yang tidak berguna maka tidak ada peringatan. Saya pikir kode peringatan harus mengakui bahwa properti value dari kotak centang tidak menunjukkan apakah itu dikontrol atau tidak, melainkan checked prop.

cc @zpao @spicyj sepertinya kami ingin memperbaikinya.

Ya, saya melihat ini sendiri kemarin.

Bug ini agak mengganggu. Untuk satu hal, ada banyak jenis masukan yang berbeda untuk dipertimbangkan (https://www.w3.org/TR/html5/forms.html#attr-input-type) dan browser tampaknya mendukung lebih banyak jenis daripada yang ditunjukkan spesifikasi (untuk Misalnya, Mozilla tampaknya mendukung "bulan" sesuai https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input).

Dalam kasus tertentu dari sebuah radio button, hal ini semakin diperumit oleh fakta bahwa Anda tidak dapat menentukan "kendali" dari sebuah grup hanya dengan melihat satu masukan. Anda perlu melihat semua input dengan name prop yang sama dalam grup formulir yang sama. Yuck.

Sayang sekali kami tidak bisa begitu saja melarang komponen yang tidak terkontrol. Itu akan membuat hidup jadi lebih mudah. : P.

Bug ini agak mengganggu. Untuk satu hal, ada banyak jenis masukan yang berbeda untuk dipertimbangkan (https://www.w3.org/TR/html5/forms.html#attr-input-type) dan browser tampaknya mendukung lebih banyak jenis daripada yang ditunjukkan spesifikasi (untuk Misalnya, Mozilla tampaknya mendukung "bulan" sesuai https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input).

@jimfb Tidak yakin apakah saya mengikuti, sejauh yang saya mengerti dan khawatirkan ini hanya tentang memeriksa apakah type="radio" atau type="checkbox" dan kemudian menguji checked bukan value , tampaknya value sedang diuji sekarang juga. Jenis lainnya seharusnya tidak terlalu penting karena mereka semua mengandalkan value .

Dalam kasus tertentu dari sebuah radio button, hal ini semakin diperumit oleh fakta bahwa Anda tidak dapat menentukan "kendali" dari sebuah grup hanya dengan melihat satu masukan. Anda perlu melihat semua input dengan prop nama yang sama dalam grup formulir yang sama. Yuck.

Mencampur radio yang terkontrol dan tidak terkendali juga menjadi masalah, tetapi IMHO masalah yang sepenuhnya terpisah. Peringatan ini hanya tentang mengalihkan input individu antara dikendalikan dan tidak terkontrol. Yaitu checked tidak boleh berubah dari null ke non-null atau sebaliknya pada komponen individual.

Sayang sekali kami tidak bisa begitu saja melarang komponen yang tidak terkontrol. Itu akan membuat hidup jadi lebih mudah. : P.

Saya masih berpendapat bahwa mereka harus menjadi komponen yang sepenuhnya terpisah.

Saya mengalami ini juga: mengklik radio menunjukkan kesalahan

<div className="radio">
                                        <label>
                                            <input type="radio" name="type" value="In Person" defaultChecked={true} />
                                            <span> In Person</span>
                                        </label>
                                    </div>
                                    <div className="radio margin-left-20">
                                        <label>
                                            <input type="radio" name="type" value="Phone" />
                                            <span> Phone</span>
                                        </label>
                                    </div>
                                    <div className="radio margin-left-20">
                                        <label>
                                            <input type="radio" name="type" value="Webex" />
                                            <span> Webex</span>
                                        </label>
                                    </div>

@syranide Saya pikir ini sedikit lebih rumit dari itu. Pikirkan tentang bagaimana Anda akan menerapkan peringatan ini untuk beralih antara tombol radio terkontrol dan tidak terkontrol.

Jika salah satu input radio dalam grup formulir tersebut memiliki atribut checked ditentukan, maka seluruh grup akan dikontrol. Pengendalian tidak dapat dilacak pada basis per node untuk tombol radio.

Mari kita bahas ini untuk menangani kasus 90% yang hanya memberi peringatan secara tidak benar. Kita bisa khawatir membuatnya sempurna di lain waktu.

@zpao Itulah yang saya bicarakan - peringatan ini tidak diaktifkan dengan benar (terlalu sering) untuk tombol radio.

jika kita hanya ingin perbaikan cepat, saya rasa kita hanya perlu menonaktifkan peringatan ini untuk tombol radio. Saya rasa tidak ada solusi 90% untuk tombol radio yang sesekali tidak akan mengaktifkan peringatan palsu. Perbaikan yang "benar" akan membutuhkan pelacakan semua masukan radio dalam setiap kelompok formulir.

Kasus uji dalam laporan awal adalah peringatan dan seharusnya tidak demikian. Ini bukan karena perlu melacak seluruh radio dalam kasus ini, itu karena kami salah melihat value untuk radio dan kotak centang (di sini: https://github.com/facebook/react/blob/master /src/renderers/dom/client/wrappers/ReactDOMInput.js#L169-L171). Kita tidak boleh kembali ke value , kita harus menggunakan tipe untuk menentukan apakah kita harus melihat checked atau value .

Anda sedang berbicara tentang masalah nyata tetapi bersinggungan dengan masalah ini.

@zpao Benar, tetapi grup radio yang tidak terkontrol tidak diperlukan untuk menyetel defaultChecked pada salah satu elemen. Dan grup radio terkontrol diizinkan untuk menyetel defaultChecked pada elemen terkontrol (untuk tombol reset). Ini berarti bahwa kecuali kita melakukan logika yang lebih cerdas, setiap pemeriksaan yang kita lakukan salah dan akan mengaktifkan peringatan palsu. Kami mungkin juga menghapus centang (untuk tombol radio) pada saat itu.

@syranide Saya pikir ini sedikit lebih rumit dari itu. Pikirkan tentang bagaimana Anda akan menerapkan peringatan ini untuk beralih antara tombol radio terkontrol dan tidak terkontrol.

Jika salah satu masukan radio dalam grup formulir tersebut memiliki atribut yang dicentang, maka seluruh grup akan dikontrol. Pengendalian tidak dapat dilacak pada basis per node untuk tombol radio.

@jimb Huh? Bukankah ini cara Anda menggunakan tombol radio https://jsfiddle.net/dt03qw4p/? Sama seperti value untuk input teks, jika checked adalah null, maka tidak terkontrol, jika bukan null maka dikontrol dan tergantung kebenarannya diperiksa atau tidak ... kan? Ia tidak perlu memeriksa radio lain untuk skenario ini, ia hanya perlu memeriksa apakah checked berubah dari null menjadi non-null atau sebaliknya (yaitu mengubah kontrol).

Atau apa yang saya lewatkan?

@syranide Apakah Anda diminta untuk menentukan checked={false} jika tombol radio tidak dicentang dalam komponen yang dikontrol? Hari ini, jawabannya tidak. Mungkin kita bisa / harus mengubahnya, tetapi ini adalah diskusi yang jauh lebih luas dan hampir pasti tidak dalam lingkup perbaikan cepat 90% yang diinginkan @zpao .

Contoh: ini adalah bentuk terkontrol hukum (tidak berubah):

<form>
  <input type="radio" name="foo" value="1" onChange={()=>{}} />
  <input type="radio" name="foo" value="2" onChange={()=>{}} checked />
  <input type="radio" name="foo" value="3" onChange={()=>{}} />
</form>

Jelas itu adalah contoh yang dibuat-buat. Anda dapat membayangkan bahwa pengguna memiliki daftar elemen dan hanya "menyetel" atribut yang dicentang pada salah satu yang dicentang. Tapi hasilnya sama saja.

"Pengendalian" input ditentukan oleh seluruh grup di dalam formulir. Kurangnya atribut checked tidak cukup untuk mengetahui apakah elemen input tertentu dikendalikan. Dalam hal ini, kontrol input pertama ditentukan oleh kontrol input kedua.

Itulah mengapa peringatan ini sangat rumit untuk tombol radio.

@syranide Apakah Anda diminta untuk menentukan check = {false} jika tombol radio tidak dicentang dalam komponen yang dikontrol? Hari ini, jawabannya tidak.

@jimfb Sebenarnya jawabannya adalah ya dalam arti ...? https://jsfiddle.net/hx2r7bc4/ (contoh dibuat-buat, tapi tetap saja)

Juga, saya akan menganggap sangat aneh bagi seseorang untuk memiliki komponen yang dikontrol dinamis dan tidak secara eksplisit menetapkan checked (saya ragu Anda akan menemukan orang yang melakukannya), selain itu, ini adalah peringatan dan pada dasarnya dimaksudkan untuk bersinar ringan pada perilaku buruk jadi saya tidak begitu yakin apakah saya akan menganggapnya sebagai masalah?

Contoh: ini adalah bentuk terkontrol hukum (tidak berubah):

Berhasil, saya tidak yakin apakah saya setuju bahwa itu ide yang bagus. Terlepas dari itu, itu tidak akan menjadi masalah, karena dicentang tidak disediakan properti bagi yang lain, Anda hampir dapat memastikan bahwa ini adalah tombol radio statis dan tidak dinamis. Jadi mereka tidak akan pernah mengubah kendali dan memperingatkan. Selanjutnya, Anda tidak boleh menggunakan pola itu untuk membuat tombol radio statis, untuk itulah readOnly .

Jadi sekali lagi, ini tampak seperti kasus win-win bagi saya, jika Anda melakukannya dengan salah / buruk, Anda mendapat peringatan. Tidak ada yang melakukannya dengan benar akan mendapat peringatan.

Mungkin saya telah melewatkan sesuatu, tetapi saya tidak melihat kasus apa pun yang melibatkan praktik baik yang benar-benar akan menyebabkan Anda melihat peringatan, hanya yang buruk.

Saya menarik komentar saya sebelumnya, spesifikasi menunjukkan bahwa value adalah atribut yang diperlukan untuk kotak centang (bahkan jika saya tidak berencana untuk menggunakannya)

https://html.spec.whatwg.org/multipage/forms.html#checkbox -state- (type = checkbox)

koreksi, MDN menunjukkan bahwa ini adalah atribut yang diperlukan: https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input/checkbox

Spesifikasi sebenarnya tidak mengatakan itu .. Saya tidak yakin apa kutipan untuk MDN tetapi tampaknya salah bagi saya. Secara pribadi saya lebih suka menghilangkan properti value untuk kotak centang, tampaknya masuk akal untuk browser untuk default ke on atau sesuatu jika perlu.

Sebenarnya jawabannya adalah ya dalam arti ...? https://jsfiddle.net/hx2r7bc4/ (contoh dibuat-buat, tapi tetap saja)

Wow, menyebalkan. Itu adalah hal paling mengerikan yang pernah saya lihat sepanjang bulan. Tapi saya akan memberi Anda kredit karena ini menunjukkan masalah dengan tidak menentukan prop yang diperiksa pada komponen yang dikontrol ketika semua nilai salah.

Juga, saya akan menganggapnya sangat aneh bagi seseorang untuk memiliki komponen terkontrol dan tidak secara eksplisit dicentang (saya ragu Anda akan menemukan orang yang bahkan melakukannya), selain itu, ini adalah peringatan dan pada dasarnya dimaksudkan untuk menjelaskan perilaku buruk jadi saya Saya tidak begitu yakin apakah saya akan menganggapnya sebagai masalah?

Saya tidak yakin itu aneh. Sangat intuitif / alami untuk mengulang beberapa data dan mengatur checked IFF data mengatakan bahwa nilai dicentang (dengan asumsi Anda tidak menggunakan jsx). Saya bahkan tidak yakin itu perilaku buruk (kecuali mengingat biola Anda di atas).

Bagaimanapun, saya kira saya baik-baik saja dengan melarang perilaku itu 👍. Saya pikir itu akan berhasil.


Satu-satunya kasus tepi lain yang saya khawatirkan adalah apa yang terjadi jika kotak centang terkontrol berubah menjadi input teks terkontrol, tetapi itu seharusnya mudah bagi kami untuk memperbaikinya, kami hanya perlu mengujinya setelah melakukan perubahan.

Saya bahkan tidak yakin itu perilaku buruk (kecuali mengingat biola Anda di atas).

Hanya untuk anak cucu. Kita tidak bisa secara realistis melepaskan diri dari nullness checked menentukan kontrol dengan desain saat ini. Mengingat bahwa null checked secara efektif berarti tidak terkendali, saya akan mengatakan bahwa salah untuk mencampurnya. Sekarang kebetulan Anda dapat mengandalkan pola itu selama salah satunya selalu dicentang, tetapi itu tidak dijamin benar. Mungkin ada nilai yang digunakan yang tidak sesuai dengan radio mana pun (belum tentu kesalahan), jika Anda melakukannya dengan "cara yang salah" maka beberapa radio akan tetap diperiksa.

Satu-satunya kasus tepi lain yang saya khawatirkan adalah apa yang terjadi jika kotak centang terkontrol berubah menjadi input teks terkontrol, tetapi itu seharusnya mudah bagi kami untuk memperbaikinya, kami hanya perlu mengujinya setelah melakukan perubahan.

IMHO, saya pikir saya memiliki PR tentang itu yang akan menganggapnya sama dengan memasang kembali komponen yang menurut saya semua orang setuju tetapi tidak pernah akhirnya digabungkan. Jadi sampai hal seperti itu terjadi, saya bahkan tidak akan mengkhawatirkannya, ini hampir merupakan kesalahan dalam arti untuk mengubah jenis input hari ini (ada juga kasus tepi rusak lainnya AFAIK).

Saya memiliki masalah yang sama. Ini kode saya:

<input type="checkbox" onChange={this.handlerMustfillChange} checked={this.state.isMustFill}/>

Dan ketika saya mengklik kotak centang saya mendapat peringatan yang sama.
warning.js: 44 Peringatan: QuestionHeader mengubah kotak centang jenis masukan yang tidak terkontrol untuk dikontrol.

@LiIa

Artinya this.state.isMustFill tidak selalu true atau false , melainkan true atau undefined , misalnya. Pastikan selalu boolean, dan masalahnya akan hilang.

Apakah masalah ini masih dianggap bug?
Saya mengubah menggunakan defaultValue dengan defaultChecked agar tidak ada peringatan.

<input type="radio" name="a" defaultValue="1" defaultChecked/>
<input type="radio" name="a" defaultValue="11"/>

@littlee Saya tidak menyalahkan Anda, saya menyalahkan kami, tapi itu sangat buruk.

@gaul
Ketika sebuah komponen memiliki prop value dan pada saat yang sama sebuah prop defaultValue (atau defaultChecked ), itu akan dianggap sebagai komponen yang tidak terkontrol.

Saya pikir ini harus dinyatakan secara eksplisit dengan contoh di dokumen Formulir , misalnya tulis Catatan tentang situasi ini, atau itu akan salah memahami pemula React.

@littlee , singkatnya yang Anda maksud Daripada checked={this.state.isMustFill} lakukan checked={!!this.state.isMustFill}

@kopahead

Alih-alih diperiksa = {this.state.isMustFill} lakukan diperiksa = {!! this.state.isMustFill}

Saya tidak berpikir itu terkait dengan apa yang saya katakan sebelumnya

saya memiliki peringatan yang sama. nilai casting dari null menjadi false menyelesaikan masalah:
<input type="checkbox" checked={!!this.state.someValue} onChange={.....} >

jadi sekarang saya harus meletakkan !! di mana-mana di kotak centang

coba: checked={(this.state.someValue)} sebagai gantinya yang di-cast ke boolean. falsey null / undefined / 0 / '' = false semuanya benar. ini berfungsi seperti operator terner:

checked={(this.state.item5) ? true : false}

Cara lain adalah:

checked={this.state.someValue === true}

Dalam kasus saya, nilai checked diberikan sebagai undefined saat komponen dimuat. Saya telah melewati false ketika itu adalah undefined .

Saya menggunakan kode berikut, peringatan itu menghilang.

function CheckboxButton({checked, onChange, textComponent} = {}) {
    return (
        <label className='checkbox-button'>
            <input
                type='checkbox'
                checked={checked || false}
                onChange={onChange}/>
            {textComponent}
        </label>
    );
}
Apakah halaman ini membantu?
0 / 5 - 0 peringkat