Vue.js 3 and search - javascript

I have a data coming from API. It is an array of "houses".
Code looks like this:
<template>
<div class="search__sort">
<input v-model="search" placeholder="Search for a house">
<button class="sort__button">Price</button>
<button class="sort__button">Size</button>
</div>
<div v-for="house in houses" :key="house.id" class="house">
<router-link :to="{ name: 'HouseDetails', params: { id: house.id}}" >
<h2>ID = {{ house }}</h2>
<h3> {{ house.location.street}} </h3>
<img :src="house.image" />
</router-link>
<button v-if="house.madeByMe" class="delete" #click="deleteHouse(house.id)">Delete</button>
</div>
</template>
<script>
import axios from 'axios'
export default {
name: 'Houses',
data(){
return {
houses: [],
}
},
created() {
this.getHouses();
},
methods: {
getHouses(){
// GET request using axios with set headers
const headers = { "CENSORED": "CENSORED" };
axios.get('myAPI', { headers })
.then(response => this.houses = response.data);
},
deleteHouse(id) {
const headers = { "CENSORED": "CENSORED" };
axios.delete('myAPI' + id, { headers })
.then(response => {
console.log(response);
})
.catch(function (error) {
console.log(error.response);
});
},
},
}
</script>
I somehow need to implement the filter by text input, so that for example, if user types a city name it will show all of those houses or a street name to filter that by street.
Any suggestions how I can do that with code that I already have?

You can use computed property:
new Vue({
el: '#demo',
data() {
return {
search: '',
houses: [{ "id": 2, "image": "myAPI/house1.jpg", "price": 123, "rooms": { "bedrooms": 1, "bathrooms": 1 }, "size": 500, "description": "oui", "location": { "street": "street 20", "city": "assas", "zip": "asasdd" }, "createdAt": "2020-05-07", "constructionYear": 2000, "hasGarage": false, "madeByMe": false }, { "id": 3, "image": "myAPI/house1.jpg", "price": 123, "rooms": { "bedrooms": 1, "bathrooms": 1 }, "size": 500, "description": "oui", "location": { "street": "street 20", "city": "adb", "zip": "asasdd" }, "createdAt": "2020-05-07", "constructionYear": 2000, "hasGarage": false, "madeByMe": false },{ "id": 4, "image": "myAPI/house1.jpg", "price": 123, "rooms": { "bedrooms": 1, "bathrooms": 1 }, "size": 500, "description": "oui", "location": { "street": "street 20", "city": "bbb", "zip": "asasdd" }, "createdAt": "2020-05-07", "constructionYear": 2000, "hasGarage": false, "madeByMe": false }],
}
},
computed: {
filteredHouses(){
return this.houses.filter(h => h.location.city.toLowerCase().includes(this.search.toLowerCase()))
}
}
})
Vue.config.productionTip = false
Vue.config.devtools = false
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<div id="demo">
<div class="search__sort">
<input v-model="search" placeholder="Search for a house">
<button class="sort__button">Price</button>
<button class="sort__button">Size</button>
</div>
<div v-for="house in filteredHouses" :key="house.id" class="house">
<h3> {{ house.location.city}} </h3>
<img :src="house.image" />
</div>
</div>

You will want to distinguish the difference between houses and displayedHouses such that, displayedHouses is your filtered array.
<h2>ID = {{ house }}</h2> is not going to play well with your testing
displayedHouses will be a computed looking something like:
computed:
{
/**
* #return {array} List of displayed houses from search input
*/
displayedHouses()
{
if (!this.houses || !this.houses.length)
{
return []
}
if (!this.search)
{
return this.houses
}
return this.houses.filter( (house) =>
{
return house.city.includes(this.search) || house.state.includes(this.search) // || whatever else you want
})
}
},

Related

how to display list of orders from my database in vue js

i've successfully updated my orders after payment please how can i display it in my vue front end
this is my html template which shows the list of orders made
<template>
<div>
<div
v-for="order in orders"
:key="order._id"
>
<div
v-for="product in order.products"
:key="product._id"
>
{{ product.productID.title }}
</div>
</div>
</div>
</template>
this is my script tag
<script>
import { mapActions } from "vuex";
import { mapGetters } from "vuex";
import axios from "axios";
export default {
name: "Products",
data() {
return {
orders: [],
name: "",
email: ""
};
},
created() {
//user is not authorized
if (localStorage.getItem("token") === null) {
this.$router.push("/login");
}
},
mounted() {
const token = localStorage.getItem("token");
axios
.get("http://localhost:5000/api/orders", {
headers: {
Authorization: "Bearer" + token,
"x-access-token": token
}
})
.then(res => {
console.log(res);
orders: res.products;
});
axios
.get("http://localhost:5000/api/auth/user", {
headers: {
Authorization: "Bearer" + token,
"x-access-token": token
}
})
.then(res => {
console.log(res);
this.name = res.data.user.name;
this.email = res.data.user.email;
})
.catch(error => {
console.log(error);
});
}
};
</script>
this the json object i get in my console
[
{
"_id": "62d163b638cbafee24c6d663",
"products": [
{
"productID": {
"_id": "625672a8370e769a8a93a51e",
"reviews": [],
"owner": {
"_id": "6220db7ee861f3dbbaf21e3d",
"name": "mr jacob",
"about": "hello",
"__v": 0
},
"category": "62566ec30e42d6c5ab370e7c",
"title": "galaxy note",
"description": "Lorem ipsum dolor sit amet, ",
"photo": "https://aji.s3.eu-west-2.amazonaws.com/1649832580792",
"price": 300,
"stockQuantity": 1,
"__v": 0,
"id": "625672a8370e769a8a93a51e"
},
"quantity": 1,
"price": 300,
"_id": "62d163b638cbafee24c6d664"
}
],
"owner": {
"_id": "6278e8bc1966b7d3783ced8e",
"name": "bas",
"email": "bas#gmail.com",
"password": "$2a$10$3QkbA805Pn/QBYMd6sULi.FGjETYoMf44wuV1mtOZahhPzm5zeL4G",
"__v": 0,
"address": "62b2cfd8d0846785cd87c64d"
},
"estimatedDelivery": "",
"__v": 0
}
]
i'm not getting any error in my console so i don't seem to know where the problem is
Your code looks fine to me and it is working fine. One small observation, As per the console data you posted, It should be this.orders = res instead of orders = res.products.
Live Demo :
new Vue({
el: '#app',
data: {
orders: []
},
mounted() {
const apiResponse = [
{
"_id": "62d163b638cbafee24c6d663",
"products": [
{
"productID": {
"_id": "625672a8370e769a8a93a51e",
"reviews": [],
"owner": {
"_id": "6220db7ee861f3dbbaf21e3d",
"name": "mr jacob",
"about": "hello",
"__v": 0
},
"category": "62566ec30e42d6c5ab370e7c",
"title": "galaxy note",
"description": "Lorem ipsum dolor sit amet, ",
"photo": "https://aji.s3.eu-west-2.amazonaws.com/1649832580792",
"price": 300,
"stockQuantity": 1,
"__v": 0,
"id": "625672a8370e769a8a93a51e"
},
"quantity": 1,
"price": 300,
"_id": "62d163b638cbafee24c6d664"
}
],
"owner": {
"_id": "6278e8bc1966b7d3783ced8e",
"name": "bas",
"email": "bas#gmail.com",
"password": "$2a$10$3QkbA805Pn/QBYMd6sULi.FGjETYoMf44wuV1mtOZahhPzm5zeL4G",
"__v": 0,
"address": "62b2cfd8d0846785cd87c64d"
},
"estimatedDelivery": "",
"__v": 0
}
];
this.orders = apiResponse;
}
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<div id="app">
<div
v-for="order in orders"
:key="order._id"
>
<div
v-for="product in order.products"
:key="product._id"
>
{{ product.productID.title }}
</div>
</div>
</div>
this.orders = res.data.products was what solved my problem

Vuejs get dynamic form all values

I have select and input component with made by buefy. Everything is ok till I realize how can I get the data.
I'm sort of new on vuejs. So I will be glad if you help me out.
Maybe I can do with Javascript but how?
I'm getting dynamic form from backend
Here is my codes;
Input.vue
<template>
<b-field :label="fieldLabel">
<b-input
:name="inputName"
:type="inputType"
:maxlength="inputType == 'textarea' ? 200 : null"
></b-input>
</b-field>
</template>
<script>
export default {
name: "Input",
props: {
inputType: {
type: String,
required: true,
default: "text",
},
inputName: {
type: String,
required: true,
},
fieldLabel: {
type: String,
required: true,
}
}
};
</script>
Home.vue
<template>
<div class="container is-max-desktop wrapper">
<div v-for="element in offer" :key="element.id">
<Input
v-model="element.fieldValue"
:fieldLabel="element.fieldLabel"
:inputType="element.fieldType"
:inputName="element.fieldName"
v-if="element.fieldType != 'select'"
class="mb-3"
/>
<Select
v-model="element.fieldValue"
:fieldLabel="element.fieldLabel"
:options="element.infoRequestFormOptions"
:selectName="element.fieldName"
v-if="element.fieldType == 'select'"
class="mb-3"
/>
</div>
<b-button type="is-danger" #click="getOffer()">GET</b-button>
</div>
</template>
<script>
import axios from "axios";
import Select from "../components/Select.vue";
import Input from "../components/Input.vue";
export default {
name: "Home",
data() {
return {
offer: [],
};
},
components: {
Select,
Input,
},
methods: {
getOfferForm() {
axios({
method: "get",
url: `/GETDYNAMICFORM`,
})
.then((response) => {
this.offer = response.data;
})
.catch(() => {
this.$buefy.toast.open({
duration: 3000,
message: "oops",
position: "is-bottom",
type: "is-danger",
});
});
},
getOffer() {
console.log(this.offer);
},
},
created() {
this.getOfferForm();
},
};
</script>
Example Dynamic Form Response like;
[ { "id": 58, "fieldLabel": "Name Surname", "providerLabel": "Name
Surname", "fieldName": "nmsrnm", "fieldType": "text", "fieldValue":
null, }, { "id": 60, "fieldLabel": "E-mail", "providerLabel":
"E-mail", "fieldName": "e_mail_60", "fieldType": "email",
"fieldValue": null, }, { "id": 2, "fieldLabel": "Budget",
"providerLabel": "Budget", "fieldName": "bdget", "fieldType":
"select", "fieldValue": "", "infoRequestFormOptions": [ { "id": 1,
"orderNum": 0, "optionValue": 0, "optionText": "Select", "minValue":
null, "maxValue": null }, { "id": 2, "orderNum": 1, "optionValue": 1,
"optionText": "10-30", "minValue": 10, "maxValue": 30 } ] } ]

Compare values over components / BootstrapVue

I'm working with BootstrapVue. I have following problem - I have a select dropdown in my parent.vue where I select my ID (as you can see it's my props) and I want to compare this with my json file...
Now I need to do following:
Check my selected ID (from parent.vue) with my json file and find the correct ID
Put all Articel in my dropdown selection
emit Rank of selected Articel back to parent
I don't have any clue how to solve that with a nested JSON File.. I think I have to use a v-for loop..
Thanks in advance for helping me out!
my code:
<template>
<b-card>
<div class="mt-2">CLOTHING ITEM</div>
<b-form-select type="text"></b-form-select>
</b-card>
</template>
<script>
import json from './json/ID.json'
export default {
name: "customerChoice",
data() {
return {
json: json,
}
},
props: ["ID"]
}
</script>
my nested json:
[
{
"ID": "1111",
"Product": {
"1": {
"Articel": "Jeans",
"Rank": "1"
},
"2": {
"Articel": "T-Shirt",
"Rank": "2"
}
}
},
{
"ID": "2222",
"Product": {
"1": {
"Articel": "Hoodie",
"Rank": "2"
},
"2": {
"Articel": "Jeans",
"Rank": ""
}
}
},
{
"ID": "3333",
"Product": {
"1": {
"Articel": "Socks",
"Rank": "1"
}
}
}
]
If I understand you correctly, take a look at following snippet:
Vue.component('Child', {
template: `
<b-card>
<div class="mt-2">CLOTHING ITEM</div>
<b-form-select type="text"
v-model="selected"
:options="articles"
text-field="Articel"
value-field="Rank"
>
</b-form-select>
</b-card>
`,
data() {
return {
json: [
{ID: "1111", "Product": {"1": {"Rank": "1", "Articel": "Jeans"}, "2": {"Articel": "T-Shirt", "Rank": "2"}}},
{ID: "2222", "Product": {"1": {"Articel": "Hoodie","Rank": "2"}, "2": {"Articel": "Jeans", "Rank": ""}}},
{ID: "3333", "Product": {"1": {"Articel": "Socks", "Rank": "1"}}}
],
selected: null,
}
},
props: ["id"],
computed: {
articles() {
const res = []
const art = this.json.find(j => j.ID === this.id)
for(let key in art.Product) {
res.push(art.Product[key])
}
return res
}
},
watch: {
selected() {
this.$emit('changed', this.selected)
}
}
})
new Vue({
el: '#demo',
data() {
return {
parentId: '1111',
rank: ''
}
},
methods: {
rankReceived(val) {
console.log(val)
this.rank = val
}
}
})
<script src="//unpkg.com/vue#latest/dist/vue.min.js"></script>
<script src="//unpkg.com/bootstrap-vue#latest/dist/bootstrap-vue.min.js"></script>
<div id="demo">
<h3>{{rank}}</h3>
<Child :id="parentId" #changed="rankReceived" />
</div>

VusJs: Error in render: "Type Error: Cannot read property 'data' of undefined"

enter image description here
i request data from API and data was succesfuly, but i get this error
<template>
<!-- <h1>{{ hasil }}</h1> -->
<div>
<div v-for=" h in hasil.data.data " :key="h.id">
<div class="card blue-grey darken-1 left-align">
<div class="card-content white-text">
<span class="card-title">Title: {{ h.title }} | ID: {{ h.id }}</span>
<p>Body: {{ h.body }}</p>
</div>
<div class="card-action">
This is a link
This is a link
</div>
</div>
</div>
</div>
</template>
<script>
import axios from 'axios'
export default {
name: 'ListArticle',
data () {
return {
hasil: []
}
},
created () {
axios.get('http://xxx.xxxxx.com/api/laravel')
.then(response => (this.hasil = response))
}
}
</script>
here the value
{
"current_page": 1,
"data": [
{
"id": 10,
"user_id": 1,
"category_posts_id": 1,
"title": "jjjjj kkkkk",
"body": "jjjjj kkkkkkkkkkkkkkk",
"slug": "jjjjj-kkkkk",
"active": 1,
"file_name": "phpheEduN.PNG",
"original_file_name": "Capture.PNG",
"file_path": "storage/app/public",
"created_at": "2018-05-01 13:00:13",
"updated_at": "2018-05-01 13:00:13",
"url": "xxx"
},
{
"id": 9,
"user_id": 1,
"category_posts_id": 1,
"title": "asaaaaaaa jhabsd",
"body": "aaa kjjkj",
"slug": "xxx",
"active": 1,
"file_name": "phpcUz7qV.PNG",
"original_file_name": "Capture.PNG",
"file_path": "storage/app/public",
"created_at": "2018-05-01 12:38:46",
"updated_at": "2018-05-01 12:38:46",
"url": ""
},
{
"id": 8,
"user_id": 1,
"category_posts_id": 1,
"title": "hkbakjbcscsdcsd",
"body": "alsdjnblsjdccsdsfsdfdsffsfs",
"slug": "hkbakjbcscsdcsd",
"active": 1,
"file_name": "php1LDUPr.PNG",
"original_file_name": "Capture.PNG",
"file_path": "storage/app/public",
"created_at": "2018-05-01 12:33:46",
"updated_at": "2018-05-01 12:33:46",
"url": ""
},
{
"id": 1,
"user_id": 1,
"category_posts_id": 1,
"title": "test title",
"body": "test body",
"slug": "test-title",
"active": 1,
"file_name": "",
"original_file_name": "",
"file_path": "",
"created_at": null,
"updated_at": null,
"url": ""
}
],
"first_page_url": "xxx",
"from": 1,
"last_page": 1,
"last_page_url": "xxx",
"next_page_url": null,
"path": "xxx",
"per_page": 5,
"prev_page_url": null,
"to": 4,
"total": 4
}
vue can't resolve data when vnode created,you can modify your code like this:
export default {
name: 'ListArticle',
data () {
return {
hasil: {data:{data:[]}}
}
},
created () {
axios.get('http://xxx.xxxxx.com/api/laravel')
.then(response => (this.hasil = response))
}
}
or like this:
<template>
<!-- <h1>{{ hasil }}</h1> -->
<div>
<div v-for=" h in hasil.data " :key="h.id">
<div class="card blue-grey darken-1 left-align">
<div class="card-content white-text">
<span class="card-title">Title: {{ h.title }} | ID: {{ h.id }}</span>
<p>Body: {{ h.body }}</p>
</div>
<div class="card-action">
This is a link
This is a link
</div>
</div>
</div>
</div>
</template>
export default {
name: 'ListArticle',
data () {
return {
hasil: {data:[]}
}
},
created () {
axios.get('http://xxx.xxxxx.com/api/laravel')
.then(response => (this.hasil = response.data))
}
}
The reason why you're getting the error Type Error: Cannot read property 'data' of undefined is because you're trying to accessthis when the arrow notation function in the axios request changes the this reference. You'd actually want to do something like this instead:
import axios from 'axios'
export default {
name: 'ListArticle',
data () {
return {
hasil: []
}
},
created () {
// Create reference to this so you can access the Vue
// reference inside arrow notation functions
var self = this;
axios.get('http://xxx.xxxxx.com/api/laravel')
.then(response => (self.hasil = response))
}
}

Generate dynamic data field using child component

I want to generate dynamic data field using value of prop passed in child component.
Code:
...
<datafieldcheckbox :categories="abc" #call-method="callfilteredproducts"></datafieldcheckbox>
new Vue({
el: "#app",
data: {
abc: null, // this will generate based on a value of prop passed in child component.
products: [
{
"id": "1",
"name": "Product1",
"abc": "EEE",
"skill": "Easy",
"color": "blue",
"price": 100.00
},
{
"id": 2,
"name": "Product2",
"abc": "EEE",
"skill": "Intermediate",
"color": "red",
"price": 120.00
},
{
"id": 3,
"name": "Product3",
"abc": "Office",
"skill": "Intermediate",
"color": "green",
"price": 190.00
}
]
...
const dfCheckBox = Vue.component('datafieldcheckbox', {
template: `<div id="one">
<h4><strong>Categories</strong></h4>
<ul class="categoriesFilter">
<li v-for="category in categories"><label><input type="checkbox" :id="category" :value="category" v-model="selectedFilters.categories" #click="filterProducts()"><span class="categoryName">{{category}}</span></label></li>
</ul>
</div>`,
data() {
return{
products : null,
selectedFilters: {
categories: [],
colors: [],
minPrice: null,
maxPrice: null
}
}
},
props : ['categories'],
methods: {
filterProducts(){
this.$emit('call-method', this.selectedFilters);
}
}
});
like in above code If I write abc then it will generate this kinda code in parent data:
Now let's say I have data in products and I want to find unique values of a key that is passed from child props.
Just pass the product array to child component and filter the category by checkbox. pls try this
template
<!-- child -->
<script type="text/x-template" id="grid-template">
<div>
<h2>
category list:
</h2>
<ul>
<li v-for="category in categories">
<label>{{category.abc}}</label>
<input type="checkbox" :value="category" v-model="selectedCategory" #change="emitback(selectedCategory)"/>
</li>
</ul>
</div>
</script>
<!-- parent -->
<div id="demo">
<h2>
selected category:
</h2>
<ul>
<li v-for="category in selectedCategory">
{{category.abc}}
</li>
</ul>
<datafieldcheckbox :categories="product" #call="callfilteredproducts"></datafieldcheckbox>
</div>
script
Vue.component('datafieldcheckbox', {
template: '#grid-template',
props: {
categories: Array,
},
created(){
console.log(this.categories);
},
data: function () {
return {
selectedCategory:[]
}
},
methods: {
emitback(selectedVal){
this.$emit('call',selectedVal);
}
}
})
// bootstrap the demo
var demo = new Vue({
el: '#demo',
data: {
selectedCategory:[],
product:[
{
"id": "1",
"name": "Product1",
"abc": "EEE",
"skill": "Easy",
"color": "blue",
"price": 100.00
},
{
"id": 2,
"name": "Product2",
"abc": "EEE",
"skill": "Intermediate",
"color": "red",
"price": 120.00
},
{
"id": 3,
"name": "Product3",
"abc": "Office",
"skill": "Intermediate",
"color": "green",
"price": 190.00
}
]
},
methods:{
callfilteredproducts(event){
console.log(event);
this.selectedCategory = event
}
}
})
demo Jsfiddle

Categories