Edit, Update & Create Notes via REST API
Ringkasan
Video ini membahas cara mengedit dan membuat note posts melalui REST API. Kita membangun toggle edit/cancel, mengirim POST request untuk update, membuat form create note, dan menggunakan delegated events agar tombol pada note baru juga berfungsi.
1. Edit Mode: Readonly ↔ Editable Toggle
Konsep:
- Saat halaman pertama dimuat: field bersifat
readonly(tidak bisa diedit) - Klik Edit: hapus
readonly, tambah border animasi, tampilkan tombol Save - Klik Cancel: kembalikan
readonly, sembunyikan tombol Save
Tambahkan Tombol Save di Template
File: page-my-notes.php (dalam <li> loop)
html
<li data-id="<?php the_ID(); ?>">
<input readonly class="note-title-field" value="<?php echo esc_attr(get_the_title()); ?>">
<span class="edit-note"><i class="fa fa-pencil" aria-hidden="true"></i> Edit</span>
<span class="delete-note"><i class="fa fa-trash-o" aria-hidden="true"></i> Delete</span>
<textarea readonly class="note-body-field"><?php echo esc_attr(wp_strip_all_tags(get_the_content())); ?></textarea>
<span class="update-note btn btn--blue btn--small">
<i class="fa fa-arrow-right" aria-hidden="true"></i> Save
</span>
</li>JavaScript: Edit/Cancel Toggle
javascript
editNote(e) {
var thisNote = $(e.target).parents("li");
if (thisNote.data("state") == "editable") {
this.makeNoteReadOnly(thisNote);
} else {
this.makeNoteEditable(thisNote);
}
}
makeNoteEditable(thisNote) {
thisNote.find(".edit-note").html('<i class="fa fa-times" aria-hidden="true"></i> Cancel');
thisNote.find(".note-title-field, .note-body-field").removeAttr("readonly").addClass("note-active-field");
thisNote.find(".update-note").addClass("update-note--visible");
thisNote.data("state", "editable");
}
makeNoteReadOnly(thisNote) {
thisNote.find(".edit-note").html('<i class="fa fa-pencil" aria-hidden="true"></i> Edit');
thisNote.find(".note-title-field, .note-body-field").attr("readonly", "readonly").removeClass("note-active-field");
thisNote.find(".update-note").removeClass("update-note--visible");
thisNote.data("state", "cancel");
}Penting: Gunakan
.bind(this)pada event handler agarthistetap menunjuk ke class:javascript$(".edit-note").on("click", this.editNote.bind(this));
2. Update Post via POST Request
javascript
updateNote(e) {
var thisNote = $(e.target).parents("li");
var ourUpdatedPost = {
'title': thisNote.find(".note-title-field").val(),
'content': thisNote.find(".note-body-field").val()
}
$.ajax({
beforeSend: (xhr) => {
xhr.setRequestHeader('X-WP-Nonce', universityData.nonce);
},
url: universityData.root_url + '/wp-json/wp/v2/note/' + thisNote.data('id'),
type: 'POST', // POST request = update existing
data: ourUpdatedPost, // Data yang dikirim ke server
success: (response) => {
this.makeNoteReadOnly(thisNote); // Kembali ke readonly = feedback sukses
console.log("Congrats");
console.log(response);
},
error: (response) => {
console.log("Sorry");
console.log(response);
}
});
}Perbedaan DELETE vs POST Request:
| Aspek | DELETE | POST (Update) |
|---|---|---|
type | 'DELETE' | 'POST' |
data | Tidak perlu | {title: ..., content: ...} |
| URL | /note/{id} | /note/{id} (sama!) |
3. Create Note: Form & POST Request Tanpa ID
Form HTML di page-my-notes.php (sebelum <ul>):
html
<div class="create-note">
<h2 class="headline headline--medium">Create New Note</h2>
<input class="new-note-title" placeholder="Title">
<textarea class="new-note-body" placeholder="Your note here..."></textarea>
<span class="submit-note btn btn--blue btn--small">Create Note</span>
</div>JavaScript:
javascript
createNote(e) {
var ourNewPost = {
'title': $(".new-note-title").val(),
'content': $(".new-note-body").val(),
'status': 'publish' // Nanti diubah ke 'private'
}
$.ajax({
beforeSend: (xhr) => {
xhr.setRequestHeader('X-WP-Nonce', universityData.nonce);
},
url: universityData.root_url + '/wp-json/wp/v2/note', // TANPA ID = create baru!
type: 'POST',
data: ourNewPost,
success: (response) => {
// Kosongkan form
$(".new-note-title, .new-note-body").val('');
// Tambahkan note baru ke halaman
$(`<li data-id="${response.id}">
<input readonly class="note-title-field" value="${response.title.raw}">
<span class="edit-note"><i class="fa fa-pencil" aria-hidden="true"></i> Edit</span>
<span class="delete-note"><i class="fa fa-trash-o" aria-hidden="true"></i> Delete</span>
<textarea readonly class="note-body-field">${response.content.raw}</textarea>
<span class="update-note btn btn--blue btn--small">
<i class="fa fa-arrow-right" aria-hidden="true"></i> Save
</span>
</li>`).prependTo("#my-notes").hide().slideDown();
console.log("Congrats");
console.log(response);
},
error: (response) => {
console.log("Sorry");
console.log(response);
}
});
}Perbedaan Update vs Create:
| Aspek | Update | Create |
|---|---|---|
| URL | /wp-json/wp/v2/note/{id} | /wp-json/wp/v2/note (tanpa ID!) |
| Data extra | — | status: 'publish' |
| Response | Data post yang diupdate | Data post baru (termasuk id baru) |
Response Data yang Tersedia:
| Property | Contoh |
|---|---|
response.id | 142 |
response.title.raw | "My New Note" |
response.content.raw | "Note body text" |
4. Delegated Events (Agar Tombol Note Baru Berfungsi)
Masalah:
Tombol edit/delete pada note yang baru dibuat tidak merespons klik — karena event listener hanya dipasang saat halaman pertama dimuat.
Solusi: Event Delegation
javascript
// SEBELUM (hanya untuk elemen yang sudah ada)
$(".delete-note").on("click", this.deleteNote);
// SESUDAH (untuk elemen yang ada DAN yang akan dibuat)
$("#my-notes").on("click", ".delete-note", this.deleteNote);Cara Kerja:
- Event listener dipasang pada parent container (
#my-notes) yang selalu ada - Argumen ketiga (
.delete-note) = filter — hanya trigger jika elemen yang diklik cocok - Berlaku untuk elemen yang ada sekarang DAN di masa depan
Terapkan untuk Semua Event:
javascript
events() {
$("#my-notes").on("click", ".delete-note", this.deleteNote);
$("#my-notes").on("click", ".edit-note", this.editNote.bind(this));
$("#my-notes").on("click", ".update-note", this.updateNote.bind(this));
$(".submit-note").on("click", this.createNote.bind(this));
}Diagram CRUD via REST API
CREATE: POST /wp-json/wp/v2/note (tanpa ID)
READ: GET /wp-json/wp/v2/note (list semua)
READ: GET /wp-json/wp/v2/note/{id} (satu post)
UPDATE: POST /wp-json/wp/v2/note/{id} (dengan ID + data)
DELETE: DELETE /wp-json/wp/v2/note/{id} (dengan ID)