I am trying to edit a post using state manager vuex, in vue3 using compostion API and here is my code:
<template>
<div class="container py-5">
<h3 class="mb-5 border-top-0 border-start-0 border-end-0 pb-3 border">
Edit Post
</h3>
<div v-if="formData.loading">
<div class="spinner-border text-primary" role="status"></div>
</div>
<form v-else @submit.prevent="validation">
<div class="form col-md-7">
<div class="mb-3">
<label for="title" class="form-label">Title</label>
<input
v-model="formData.title"
type="text"
class="form-control"
@input="formData.titleErr = false"
id="title"
placeholder="Please inter the title"
/>
<p class="my-2 text-danger" v-if="formData.titleErr">
This title is not valid
</p>
</div>
<div class="mb-3">
<label for="content" class="form-label">content</label>
<textarea
class="form-control"
id="content"
placeholder="Please enter the context"
rows="7"
v-model="formData.content"
@input="formData.contentErr = false"
></textarea>
<p class="my-2 text-danger" v-if="formData.contentErr">
This content is not valid
</p>
</div>
<button
type="submit"
value=""
class="btn btn-primary"
@click="validation">
Edit
</button>
</div>
</form>
</div>
</template>
And here is the script
<script>
import { computed, onMounted, reactive } from "vue";
import { useStore } from "vuex";
import { useRoute } from "vue-router";
export default {
setup() {
const store = useStore();
const formData = reactive({
title: "",
titleErr: false,
invalidTitle: true,
content: "",
contentErr: false,
invalidContent: true,
loading: false,
});
const route = useRoute();
const postInfo = computed(() => store.getters["postsModule/setSinglePost"]);
onMounted(() => {
formData.title = postInfo.value.title;
formData.content = postInfo.value.body;
});
const validation = () => {
if (formData.title === "" && formData.invalidTitle) {
formData.titleErr = true;
} else {
formData.invalidTitle = !formData.invalidTitle;
formData.titleErr = false;
}
if (formData.content === "" && formData.invalidContent) {
formData.contentErr = true;
} else {
formData.invalidContent = !formData.invalidContent;
formData.contentErr = false;
}
if (
formData.title !== "" &&
!formData.invalidTitle &&
formData.content !== "" &&
!formData.invalidContent
) {
const data = {
title: formData.title,
body: formData.content,
};
editPost(data);
}
formData.title = "";
formData.content = "";
};
return { formData, validation, postInfo };
},
};
</script>
The problem is that I need the value of postInfo which is taken from the store, however, the data is not updated correctly. The first time the page is rendered, all the inputs are empty, the other times the data is related to the last rendered time. maybe the problem is that the computed value is not envoked when the first render happened because setup is not returned any thing yet.
by the way here is the store
import axios from "axios";
import Swal from "sweetalert2";
const postsModule = {
namespaced: true,
state: {
posts: [],
singlePost: {},
},
getters: {
setPosts(state) {
return state.posts;
},
setSinglePost(state) {
return state.singlePost;
},
},
mutations: {
getPosts(state, posts) {
return (state.posts = posts);
},
getSingle(state, post) {
return (state.singlePost = post);
},
},
actions: {
// get post list
async fetchPosts({ commit }) {
const res = await axios.get(`http://localhost:3004/posts`);
const data = res.data;
commit("getPosts", data);
},
// view each post
async fetchSinglePost({ commit }, id) {
const res = await axios.get(`http://localhost:3004/posts/${id}`);
commit("getSingle", res.data);
},
// delete single post
async deleteSinglePost({ commit }, id) {
const res = await axios.delete(`http://localhost:3004/posts/${id}`);
commit("updateAfterDelete", res.data);
},
// create post
async createSinglePost(context, newPostData) {
await axios.post(`http://localhost:3004/posts`, newPostData);
Swal.fire({
title: "Thanks!",
text: "submission is done",
icon: "success",
confirmButtonText: "Cool",
});
},
},
};
export default postsModule;
Is there any solution for it to sync the computed value correctly through any render? I mean when the first component is rendered the inputs values are not empty.