Data not display inside vuetify v-text-field with Nuxt & Firestore - firebase

this is a related question which I've asked before:
Get document data from Firestore and show the data into each of the form input field using Nuxt & Vuetify
I want the data that I've submitted to display on the v-text-field input.
As you can see from the image, I can submit my form and I can get the data accordingly.
Name: siradley_ <-- this come from my firestore
but I want it to display inside the v-text-field input, not outside the input field.
Currently, I still not know how to do it.
Any help on how to do it?
<template>
<div>
<v-container>
<v-layout>
<v-flex>
<v-card>
<v-card-text>
<v-form>
<v-layout>
<v-row>
<v-col cols="12" sm="6" md="6" v-for="(test, id) in Test">
<v-text-field
v-model="editedItem.name">{{ test.name }}</v-text-field>
<p>Name: {{ test.name }}</p>
</v-col>
<v-col cols="12" sm="6" md="6">
<v-btn #click="test">Test</v-btn>
</v-col>
</v-row>
</v-layout>
</v-form>
</v-card-text>
</v-card>
</v-flex>
</v-layout>
</v-container>
</div>
</template>
my script
<script>
import firebase from "firebase/app";
import firestore from "#/plugins/firebasetest";
export default {
middleware: "authentication",
layout: 'dashboard',
data: () => ({
Test: [
{
name: '',
}
],
editedItem: {
name: '',
}
}),
created() {
this.readTest();
},
methods: {
readTest() {
this.Test = [];
firestore
.collection('test')
.doc(firebase.auth().currentUser.uid)
.get()
.then((doc) => {
this.Test.push({ ...doc.data(), id: doc.id });
console.log({ ...doc.data(), id: doc.id });
})
},
test() {
var data = {
name: this.editedItem.name,
}
firestore
.collection('test')
.doc(firebase.auth().currentUser.uid)
.set(data)
.then((doc) => {
window.location.reload();
console.log({ ...doc.data, id: doc.id })
})
},
},
}
</script>

you have to update the value editedItem.name in your data object after getting the value from the server.
you have two way data binding set on the v-text-field (i.e. v-model), so you just need to use v-text-field like this:
<v-text-field v-model="editedItem.name" ></v-text-field>
and then in the code after you get the data from the server update the mentioned field in the data:
async getDataFromServerExample() {
const data = await getData();
this.editedItem.name = data.properFieldFromServerResponse;
}
then everything should work fine.

Finally can solve it hehe.
Referring to this Unable to display data in Vue.js form after pulling from Cloud Firestore , I now can display my input data inside my v-text-field.
Here's how I do it:
<v-form>
<v-layout>
<v-row :items="Test">
<v-col cols="12" sm="6" md="6">
<v-text-field
v-model="editedItem.name"></v-text-field>
</v-col>
<v-col cols="12" sm="6" md="6">
<v-btn #click="test">Test</v-btn>
</v-col>
</v-row>
</v-layout>
</v-form>
<script>
import firebase from "firebase/app";
import firestore from "#/plugins/firebasetest";
export default {
middleware: "authentication",
layout: 'dashboard',
data: () => ({
editedItem: {
name: '',
}
}),
created() {
this.readTest();
},
methods: {
readTest() {
let _this = this;
firestore
.collection('test')
.doc(firebase.auth().currentUser.uid)
.get()
.then((doc) => {
if (doc.exists) {
console.log("Document data:", doc.data())
_this.editedItem.name = doc.data().name
} else {
console.log("No Document!");
}
}).catch((error) => {
console.log("Error :(");
})
},
},
}
</script>
I added let _this = this; and _this.editedItem.name = doc.data().name and it works.

Related

Problem using signInWithEmailAndPassword method form Firebase 9 in Nuxt Vue

I'm working on this problem for a few days and I don't know how to solve it.
This is my nuxt login page and I use the new Firebase 9 auth pack to authenticate a user.
I call the signInWithEmailAndPassword method to authenticate.
When I try it with the correct credentials I never get into the first then() of the Promise:
.then((userCredential) => {
alert(userCredential)
this.$store.commit('setUser', userCredential.user)
})
But when I type in the incorrect credentials, I always get the correct error (in the catch) and the second then() is always executed.
I don't understand why I can't log in.
Can anyone help me?
Sorry for the bad English.
My login page: (pages/index.vue)
<template>
<v-container fluid fill-height>
<v-layout align-center justify-center>
<v-flex xs12 sm8 md4>
<v-card class="elevation-12">
<v-toolbar dark color="primary">
<v-toolbar-title>Anmelden</v-toolbar-title>
</v-toolbar>
<v-card-text>
<v-form
id="login-form"
ref="form"
v-model="valid"
lazy-validation
#submit.prevent="emailLogin()"
>
<v-text-field
v-model="formData.email"
:rules="emailRules"
name="email"
label="E-Mail"
counter
required
/>
<v-text-field
v-model="formData.password"
:append-icon="show ? 'mdi-eye' : 'mdi-eye-off'"
:rules="passwordRules"
:type="show ? 'text' : 'password'"
name="password"
label="Passwort"
counter
required
#click:append="show = !show"
/>
</v-form>
</v-card-text>
<v-snackbar
v-model="snackbar"
:timeout="timeout"
>
{{ text }}
<template #action="{ attrs }">
<v-btn
color="yellow accent-2"
text
v-bind="attrs"
#click="snackbar = false"
>
Schließen
</v-btn>
</template>
</v-snackbar>
<v-card-actions>
<v-spacer />
<v-btn
type="submit"
form="login-form"
:disabled="!valid"
block
color="primary"
class="mr-4"
>
Login
</v-btn>
</v-card-actions>
</v-card>
</v-flex>
</v-layout>
</v-container>
</template>
<script>
import { auth, signInWithEmailAndPassword } from '#/plugins/firebase'
export default {
data: () => ({
show: false,
valid: true,
snackbar: '',
timeout: 10000,
text: '',
formData: {
email: '',
password: ''
},
emailRules: [
v => !!v || 'E-Mail ist verpflichtend',
v => /.+#.+\..+/.test(v) || 'Keine gültige E-Mail-Adresse'
],
passwordRules: [
v => !!v || 'Passwort ist verpflichtend'
]
}),
methods: {
emailLogin () {
signInWithEmailAndPassword(auth, this.formData.email, this.formData.password)
.then((userCredential) => {
alert(userCredential)
this.$store.commit('setUser', userCredential.user)
})
.catch((error) => {
switch (error.code) {
case 'auth/invalid-email':
this.text = 'Die E-Mail-Adresse ist falsch'
break
case 'auth/user-disabled':
this.text = 'Der User ist deaktiviert'
break
case 'auth/user-not-found':
this.text = 'Kein Account gefunden'
break
case 'auth/wrong-password':
this.text = 'Das Passwort ist falsch'
break
default:
this.text = 'Es ist ein Fehler aufgetreten: ' + error.message
break
}
this.snackbar = true
}).then(() => {
this.formData.email = ''
this.formData.password = ''
this.$refs.form.resetValidation()
this.$router.push('/post')
})
}
}
}
</script>
My firebase setup file: (plugins/firbase.js) --> is registered in nuxt.config.js
import { initializeApp } from 'firebase/app'
import { getFirestore } from 'firebase/firestore'
import { getStorage } from 'firebase/storage'
import { getAuth, signInWithEmailAndPassword, signOut, onAuthStateChanged } from 'firebase/auth'
const firebaseConfig = {
apiKey: 'key',
authDomain: 'domain',
projectId: 'project',
storageBucket: 'bucket',
messagingSenderId: 'message',
appId: 'app',
measurementId: 'measure'
}
const app = initializeApp(firebaseConfig)
const auth = getAuth(app)
const fire = getFirestore(app)
const storage = getStorage(app)
export { auth, fire, storage, signInWithEmailAndPassword, signOut, onAuthStateChanged }

Vue/Nuxt - Iterating Through Firestore Collection of Documents using v-for

First Vue/Firebase project. Using NuxtJS (with Vue v2.x) with Vuetify and Firestore. Attempting to iterate through a collection of documents and render Vuetify Card components with relevant data. Currently, I'm getting a list of components with the exact same data from a single Document. I able to log Collection items to the console, so I know the data is arriving correctly.
<template>
<section class="container">
<div>
<ul v-for="article in articles" id="articleCardList" :key="article">
<li>
<v-card dark>
<div class="d-flex flex-no-wrap justify-space-between">
<v-avatar class="ma-3" size="125" tile>
<v-img :key="article.thumbnail" :src="thumbnail"></v-img>
</v-avatar>
<div>
<v-card-title :key="article.title" class="text-h5">{{
title
}}</v-card-title>
<v-card-subtitle :key="article.description">{{
description
}}</v-card-subtitle>
<v-card-actions>
<v-card-text
:key="article.source"
class="ml-2 mt-3"
fab
icon
height="40px"
right
width="40px"
>{{ source }}
</v-card-text>
<v-card-text
:key="article.date"
class="ml-2 mt-3"
fab
icon
height="40px"
right
width="40px"
>{{ date }}
</v-card-text>
</v-card-actions>
</div>
</div>
</v-card>
</li>
</ul>
</template>
<script>
import { fireDb } from '~/plugins/firebase.js'
export default {
data() {
return {
writeSuccessful: false,
readSuccessful: false,
articles: this.articles,
}
},
methods: {
async readFromFirestore() {
fireDb
.collection('autoracing_articles')
.get()
.then((querySnapShot) => {
querySnapShot.forEach((doc) => {
this.articles = [
this.id,
this.title,
this.description,
this.thumbnail,
this.date,
this.link,
this.source,
]
console.log(this.articles)
})
})
},
},
}
</script>
It doesn't look like articles is populated correctly.
To collect all the documents into an array, initialize this.articles to an empty array, then use Array.prototype.push() to append an object of the document fields:
export default {
data() {
return {
articles: []
}
},
methods: {
async readFromFirestore() {
this.articles = []
fireDb
.collection('autoracing_articles')
.get()
.then((querySnapShot) => {
querySnapShot.forEach((doc) => {
this.articles.push({
id: doc.id,
title: doc.data().title,
description: doc.data().description,
thumbnail: doc.data().thumbnail,
date: doc.data().date,
link: doc.data().link,
source: doc.data().source,
})
})
})
},
}
}

Vue.js - Invalid prop: type check failed for prop "src". Expected String, Object, got Promise

I'm trying to get an image inserted into my firebase's firestore and storage and display it on a v-card
my v-card code:
<v-row>
<v-col cols="3" v-for="massage in massages" :key="massage.id">
<v-card
class="mx-auto"
max-width="400"
>
<v-img
v-if="massage.image"
class="white--text align-end"
height="200px"
:src="massage.image"
>
</v-img>
<v-card-title>{{massage.title}}</v-card-title>
<v-card-text class="text--primary">
<div>{{massage.shortDescription}}</div>
</v-card-text>
<v-card-actions>
<v-btn
color="orange"
text
#click="goTodetail(massage.id)"
>
Explore
</v-btn>
</v-card-actions>
</v-card>
</v-col>
</v-row>
my script:
<script>
import{ db, storage} from '#/firebase.js';
export default {
el: '#vue',
name: 'BaseHeading',
// massId:this.$route.params.Pid,
components: {
BaseInfoCard: () => import('#/components/base/InfoCard'),
},
data() {
return{
massages:[],
showmassage: false,
showrehabilitation: false,
showsupport: false,
modal_1: true,
modal_2: false,
modal_3: false,
}
},
created() {
try{
db.collection("massages").get().then((querySnapshot) => {
querySnapshot.forEach((doc) => {
let img = ''
if(doc.data().image){
img = storage.ref().child(doc.data().image).getDownloadURL()
}
this.massages.push({
id: doc.id,
title: doc.data().title,
shortDescription: doc.data().shortDescription,
image: img
})
})
});
}catch(e){
console.log(e)
}
},
}
</script>
I think it provides promise but cannot figure out how to deal with it. The error is Invalid prop: type check failed for prop "src". Expected String, Object, got Promise.
I tried to put the following in the props:
props: {
src: [ String, Object],
},
but I still have the same error
Resolve the Promise when retrieving the image URL, before you pass it into your massage object.
created() {
try {
db.collection('massages')
.get()
.then((querySnapshot) => {
querySnapshot.forEach(async (doc) => {
// start pertinent change
if (doc.data().image) {
storage
.ref()
.child(doc.data().image)
.getDownloadURL()
.then((url) => {
this.massages.push({
id: doc.id,
title: doc.data().title,
shortDescription: doc.data().shortDescription,
image: url,
})
})
} else {
this.massages.push({
id: doc.id,
title: doc.data().title,
shortDescription: doc.data().shortDescription,
})
}
// end pertinent change
})
})
} catch (e) {
console.log(e)
}
}

action not found in Vuex store

I'm following a course here:
https://thinkster.io/tutorials/nuxt-js-project/adding-authentication
I am working on adding authentication to my app and have login/logout buttons that partially work with firebase authentication. I can log in fine, but the issue is that when I'm logged in, the action in my Vuex store doesn't seem to run, therefore leaving the user logged in and the state not updating to display the logout button.
default.vue
<template>
<v-app>
<v-navigation-drawer
v-model="drawer"
:mini-variant="miniVariant"
:clipped="clipped"
fixed
app
>
<v-list>
<v-list-item
v-for="(item, i) in items"
:key="i"
:to="item.to"
router
exact
>
<v-list-item-action>
<v-icon>{{ item.icon }}</v-icon>
</v-list-item-action>
<v-list-item-content>
<v-list-item-title v-text="item.title" />
</v-list-item-content>
</v-list-item>
<button v-if="!mySession" #click="login">Login</button>
<button v-else #click="logout">Logout</button>
</v-list>
</v-navigation-drawer>
<!-- <v-toolbar fixed app :clipped-left="clipped">
<v-toolbar-side-icon #click="drawer = !drawer"></v-toolbar-side-icon>
<v-tool-bar-title v-text="title"></v-tool-bar-title>
<v-spacer></v-spacer>
<v-toolbar-items>
<v-btn #click="login">Login</v-btn>
<v-btn #click="logout">Logout</v-btn>
</v-toolbar-items>
</v-toolbar> -->
<v-app-bar
:clipped-left="clipped"
fixed
app
>
<v-app-bar-nav-icon #click.stop="drawer = !drawer" />
<v-btn
icon
#click.stop="clipped = !clipped"
>
<v-icon>mdi-application</v-icon>
</v-btn>
<v-btn
icon
#click.stop="fixed = !fixed"
>
<v-icon>mdi-minus</v-icon>
</v-btn>
<v-toolbar-title v-text="title" />
<v-spacer />
</v-app-bar>
<v-content>
<v-container>
<nuxt />
</v-container>
</v-content>
<v-navigation-drawer
v-model="rightDrawer"
:right="right"
temporary
fixed
>
<v-list>
<v-list-item #click.native="right = !right">
<v-list-item-action>
<v-icon light>
mdi-repeat
</v-icon>
</v-list-item-action>
<v-list-item-title>Switch drawer (click me)</v-list-item-title>
</v-list-item>
</v-list>
</v-navigation-drawer>
<v-footer
:fixed="fixed"
app
>
<span>© 2019</span>
</v-footer>
</v-app>
</template>
<script>
import {db} from '#/plugins/firebase'
import firebase from 'firebase/app'
import 'firebase/auth'
export default {
created() {
this.$store.dispatch('setSession');
},
data () {
return {
clipped: false,
drawer: false,
fixed: false,
items: [
{
icon: 'mdi-apps',
title: 'Welcome',
to: '/'
},
{
icon: 'cart',
title: 'Checkout',
to: '/checkout'
}
],
miniVariant: false,
right: true,
rightDrawer: false,
title: 'Vuetify.js'
}
},
methods: {
login() {
console.log('login');
let provider = new firebase.auth.GoogleAuthProvider();
firebase.auth()
.signInWithPopup(provider)
.then(function(result) {
console.log('signed in');
})
.catch(function(error) {
console.log(error);
})
},
logout() {
console.log('logout');
firebase.auth()
.signOut()
.then(() => {
console.log('sign out')
}).catch((error) => {
console.log(error)
})
}
},
computed: {
mySession() {
return this.$store.getters.session;
}
}
}
</script>
store/index.js
import Vuex from 'vuex'
import firebase from 'firebase/app'
import 'firebase/auth'
const createStore = () => {
return new Vuex.Store({
state: {
session: false
},
mutations: {
SET_SESSION(state, session) {
state.session = session;
}
},
getters: {
session: state => state.session
},
actions: {
setSession({commit}) {
firebase.auth().onAuthStateChanged(user => {
console.log(user);
console.log('change');
commit('SET_SESSION', user || false);
})
}
}
})
}
export default createStore
in console I am getting an error message that says:
"[vuex] unknown action type: setSession"
To reiterate, I can login using Google oauth, but when logged in, the state does not change and the logout button does not appear.
Thanks for the help!
Update:
Well now I'm extra confused. I did push updates 15 mins ago but for some reason my store/index.js file is outdated and isn't updating/saving? I have no idea what I'm doing wrong.
When looking at my store/index.js file on Github, it shows the default template:
https://github.com/SIeep/US-kratom/blob/master/US-Kratom/store/index.js
But what I have, and what was just copied from the course I'm taking is:
import Vuex from 'vuex';
import firebase from 'firebase/app';
import 'firebase/auth';
const createStore = () => {
return new Vuex.Store({
state: {
session: false,
products: []
},
mutations: {
SET_SESSION(state, session) {
state.session = session;
},
SET_PRODUCT(state, product) {
state.products = product;
}
},
getters: {
session: state => state.session,
products: state => state.products
},
actions: {
setSession({ commit }) {
firebase.auth().onAuthStateChanged(user => {
commit('SET_SESSION', user || false);
});
},
setProduct({ commit }, products) {
commit('SET_PRODUCT', products);
}
}
});
};
export default createStore;
I am saving the file and everything but it's not updating on Github which is obviously the issue with my app as well.
Erik from Thinkster.io ended up fixing the code for me. Update is here:
[https://github.com/SIeep/US-kratom/commit/bd55deacadfc065edc7df9c1365ae832a32b9b43][1]

Editing date and updating it in FireBase with vue.js , vuex?

I'm a beginner in writing vue js. I want to edit an exiting date in the app am working on based on a tutorial video am watching and the new date should be updated both in the app and Firebase when the SAVE button is clicked.
Am getting an error this which i think is not allowing the v-dialog to show but when i change the v-model in the v-date-picker to date which is included in my data as
props: ['meetup'],
data () {
return {
editDialog: false,
editableDate: null,
date: new Date().toISOString().substr(0,10)
}
}
the v-dialog works with no error but i get this error when the v-model is changed from date to editableDate:
vue.runtime.esm.js?ff9b:587 [Vue warn]: Invalid prop: type check failed for prop "value". Expected Array, String, got Date.
vue.runtime.esm.js?ff9b:587 [Vue warn]: Error in data(): "TypeError: dateString.split is not a function"
vue.runtime.esm.js?ff9b:1737 TypeError: dateString.split is not a function
vue.runtime.esm.js?ff9b:587 [Vue warn]: Error in nextTick: "TypeError: Cannot set property 'isDark' of undefined"
TypeError: Cannot set property 'isDark' of undefined
<template>
<v-dialog width="350px" persistent v-model="editDialog" ref="dialog" lazy full-width>
<v-btn accent slot="activator">
Edit Date
</v-btn>
<v-card>
<v-container>
<v-layout row wrap>
<v-flex xs12>
<v-card-title>Edit Meetup Date</v-card-title>
</v-flex>
</v-layout>
<v-divider></v-divider>
<v-layout row wrap>
<v-flex xs12>
<v-date-picker v-model="editableDate" style="width: 100%" actions>
<v-spacer></v-spacer>
<template slot-scope="{save, cancel}">
<v-btn
class="blue--text darken-1"
flat
#click.native="editDialog = false">
Close
</v-btn>
<v-btn
class="blue--text darken-1"
flat
#click.native="onSaveChanges">
Save
</v-btn>
</template>
</v-date-picker>
</v-flex>
</v-layout>
</v-container>
</v-card>
</v-dialog>
</template>
scripts
<script>
export default {
props: ['meetup'],
data () {
return {
editDialog: false,
editableDate: null
}
},
methods: {
onSaveChanges () {
const newDate = new Date(this.meetup.date)
const newDay = new Date(this.editableDate).getUTCDate()
const newMonth = new Date(this.editableDate).getUTCMonth()
const newYear = new Date(this.editableDate).getUTCFullYear()
newDate.setUTCDate(newDay)
newDate.setUTCMonth(newMonth)
newDate.setUTCFullYear(newYear)
this.$store.dispatch('updateMeetupData', {
id: this.meetup.id,
date: newDate
})
}
},
created () {
this.editableDate = new Date(this.meetup.date)
}
}
</script>
Have tried all i could but to no avail please i need help
This is my store
updateMeetupData ({commit}, payload) {
commit('setLoading', true)
const updateObj = {}
if (payload.title) {
updateObj.title = payload.title
}
if (payload.description) {
updateObj.description = payload.description
}
if (payload.date) {
updateObj.date = payload.date
}
firebase.database().ref('meetups').child(payload.id).update(updateObj)
.then(() => {
commit('setLoading', false)
commit('updateMeetup', payload)
})
.catch(error => {
console.log(error)
commit('setLoading', false)
})
},

Resources