Software

Simple if(falsey) statement not working [on hold]

Vuejs - Wed, 2017-07-19 14:47

I have a statement in code which checks a string like so:

if(str){ //do something here }

Even if my str = "" the code inside the check is being executed. Anyone had this? I have checked in console that str == false returns true so really cannot see why the code would be reached?

Cheers

Editing to add answer

My issue appears to be due to the fact that I was using webpack sourcemap and framework Vue.js. There is a setting in a file webpack.dev.config,

devtool: '#cheap-module-eval-source-map'

If I remove the "cheap-module' then debugging operates as expected.

devtool: '#eval-source-map'
Categories: Software

How to fetch data before mounting the root Vue instance?

Vuejs - Wed, 2017-07-19 14:25

TL;DR: vue-devtools does not work correctly if I wait for async stuff to finish before creating / mounting the root Vue instance

I'm new to Vue.js and I'm developping a back office app where nothing is accessible unless the user is logged. Except for the sign in / up pages of course.

So on page load I do something like this:

// Set up store and router ... router.beforeEach(function (to, from, next) { /* redirect to auth if store.state.auth.isLogged is false */ } // Dispatch an action that send a request to the API to get the connected user // (or null if the user is not logged) store.dispatch('getAuth').then(user) { // Mount the app one the request is done and the mutation for isLogged is done new Vue({ el: '#app', router, store, // ... }); }

And in my index.html I have a pure HTML/CSS loading page that waits for the vue app to mount.

So this works fine, on load, the app check if the user is logged and once this is done, it redirects to the auth pag if needed.

My problem is mainly with vue-devtools, it seems that if the root Vue instance is not mounted on page load, I can't inspect elements from the vue-devtools, but the vuex inspection works.

Am I doing something wrong? Or is it a problem with the devtools ?

Categories: Software

Manage Presentation Data in Vue (Resize Events)?

Vuejs - Wed, 2017-07-19 12:34

I'm working a Vue project, and I'm using Vuex to manage the applications state. I've separated out the view of the app into many small layouts, as Vue components. For example I have a layout for a header and a floating stats panel.

I've written a custom directive for affixing the stats panel. Currently, this works similar to Bootstrap where you set a value, and when the page scrolls beyond that point an affix CSS class gets added to the element. This value is based on the height of the header. As app is responsive, I would rather have this value computed from the header outerHeight property.

Now, I can think of several ways on how to accomplish this, however I'm not sure the proper Vue way to do it.

  1. I could listen for resize events and have the header update it's height in the Vuex store. However, it seems poor practice to have the store manage presentation data.
  2. I could pass the id of the header to the affix directive, and use getElementById to check the height. But this is bypassing Vue completely.
  3. I could add a method to the header to return its' height, and have the parent component that holds both the header and stats panel use that to update the affix value. This however, gets messy if header and stats don't share the same parent.

Are there any other options? What would be best practice? Thanks!

Categories: Software

Passing ref's content from a child to another VueJS child component

Vuejs - Wed, 2017-07-19 12:28

I'm learning VueJS and I got a little confused on the ref, $refs lecture. I tried to understand it from vue's documentation, but I didn't get what I want to know.

If for example I have this component:

<user-item ref="details"></user-item>

and I get the data from this component using

this.$refs.details

to use that data in the User parent component, because this user-item is a child for User component.

<div id="User"> <user-item ref="details"></user-item> </div>

In the same time I have another component called, let's say Permissions that's child too, for User component:

<div id="User"> <user-item ref="details"></user-item> <permissions></permissions> </div>

In this Permissions component I need the same this.$refs.details, but from what I test, like an experiment, doesn't work.

This is just a simple example.

Can someone please tell me how can I do it?

Categories: Software

testcafe injecting many specs to one test

Vuejs - Wed, 2017-07-19 12:15

I have specified files: model and spec for every page like main page & register page. Every spec file has their own fixture and tests checking one mage (for example: register page).

The question is how can I include many spec files into one big checking every page.

Categories: Software

Vue.js 2 with laravel Role Based Auth Admin Panel

Vuejs - Wed, 2017-07-19 12:00

I need suggestion how can i make a role based admin panel using vue.js 2 and laravel 5. I need routes in vue.js routes file and in laravel only one entry point for all router.

Ex :

Laravel route looks like :

/* Dashboard Index */ Route::group(['prefix' => 'dashboard', 'middleware' => ['auth', 'admin']], function () { Route::get('{path?}', 'HomeController@dashboard')->where('path', '[\/\w\.-]*'); });

Routes.js looks like :

export default [ { path: '/dashboard', component: Dashboard, beforeEnter: requireAuth, children: [ { path: '/', redirect: '/dashboard/home' }, { path: 'home', component: require('dashboard/Home.vue') }, { path: '*', redirect: '/dashboard' } ] } ]
Categories: Software

Vuex getter will not update

Vuejs - Wed, 2017-07-19 11:25

I am using a datepicker to set a moment.js date which is being set in my Vuex store:

Store state:

const state = { arrival: '', departure: '' }

Getters:

const getters = { arrival: state => state.arrival, departure: state => state.departure, prettyArrival: (state) => { if (state.arrival instanceof moment) { return state.arrival.format(state.prettyFormat); } return ''; } }

My vuex store is properly updating the arrival state(which is a moment.js object) because I can clearly see the devtools showing the updates and the original state changing.

The prettyArrival is not updating at all though. It is only being set once when the arrival changes from an empty string to a moment.js object.

My arrival getter shows in the devtools like this:

arrival:"2017-07-21T09:15:53.770Z"

When I log it I get the moment.js object though with seems to contain reactiveGetters and reactiveSetters so the reactivity seems in place.

Is there something wrong with how I set up my getter or is something else wrong here?

Any tips are welcome, if you need more info let me know.

Categories: Software

How can I use selectize in an input form in Vue

Vuejs - Wed, 2017-07-19 11:22

Suppose I have an input field: <input type="text" placeholder="Select Teams" /> and I should be able to select Support by clicking the input field.

enter image description here

and then

enter image description here

I learned that this is possible using selectize. How should I be able to incorporate it as a vue directive?

Categories: Software

vue js navigate to url with question mark

Vuejs - Wed, 2017-07-19 11:07

my Vue js project login template click button it redirects to like this

http://localhost:8080/#/login to http://localhost:8080/?#/login

how to solve it?

Categories: Software

Vue.js Avoriaz unit test produces translation warnings when vue-i18n is used

Vuejs - Wed, 2017-07-19 10:21
Summary

I am using vue-i18n for i18n and Avoriaz for unit testing my Vue.js components. I get many warnings because of not translated strings, which I can't fix. How can I get rid of these warnings?

Warning example

'[vue-i18n] Cannot translate the value of keypath 'description.first'. Use the value of keypath as default.'

Test setup import Vue from 'vue' import Vuex from 'vuex' import { mount } from 'avoriaz' import sinon from 'sinon' import VueResource from 'vue-resource' import BootstrapVue from 'bootstrap-vue' import VueI18n from 'vue-i18n' import store from './../../../state/index' import Register from '@/components/Register' Vue.use(BootstrapVue) Vue.use(VueResource) Vue.use(VueI18n) describe('Register', () => { it('should accept inputs', () => { store.locale = 'en' const wrapper = mount(Register, { store }) let name = 'Hans' let password = '123' let nameInput = wrapper.find('input')[0] let passwordInput = wrapper.find('input')[1] nameInput.element.value = name passwordInput.element.value = password nameInput.trigger('input') passwordInput.trigger('input') expect(wrapper.vm.$store.state.user.name).to.equal(name) expect(wrapper.vm.$store.state.user.password).to.equal(password) }) }) Tested component <template> <div class="row justify-content-md-center"> <div class="col-6"> <b-form-fieldset :description="$t('description.first')" :label="$t('label.first')" :label-size="1"> <b-form-input v-model="name"></b-form-input> </b-form-fieldset> <b-form-fieldset :description="$t('description.second')" :label="$t('label.second')" :label-size="1"> <b-form-input v-model="password" type="password"></b-form-input> </b-form-fieldset> <b-button variant="outline-success" size="sm" @click="create">{{ $t('button.first') }}</b-button> </div> </div> </template> <script> export default { i18n: { messages: { en: { 'description.first': 'Enter a name', 'label.first': 'Name *', 'description.second': 'Enter a password', 'label.second': 'Password *', 'button.first': 'Create' }, de: { 'description.first': 'Gebe einen Namen ein', 'label.first': 'Name *', 'description.second': 'Gebe ein Passwort ein', 'label.second': 'Passwort *', 'figcaption.first': 'Du kannst einen dieser Nutzer wählen, um dich einzuloggen.', 'button.first': 'Erstellen' } } }, computed: { user: { get () { return this.$store.state.user } }, name: { get () { return this.$store.state.user.name }, /** * @param name */ set (name) { this.$store.commit('SET_USER_NAME', name) } }, password: { get () { return this.$store.state.user.password }, /** * @param password */ set (password) { this.$store.commit('SET_USER_PASSWORD', password) } } }, methods: { create () { this.$store.dispatch('saveUser', this.user) } } } </script>
Categories: Software

Setting a value in v-if block

Vuejs - Wed, 2017-07-19 07:55

How do I use v-if to do two things

  1. Show The message and 2) set message.hasSublocationOutage to true.

So if there is an outage show the message and set the flag to true message.hasSublocationOutage Or pass true to a method

<div v-if="!subLocation.outageTag.length - 1"> There is a problem </div>
Categories: Software

Append new Item to a list in Vue 2

Vuejs - Wed, 2017-07-19 07:39

I have a very simple form which gets name and age from user and add this to a list.

You can check that on JSFiddle.

Here is HTML :

<div id="app"> <ul> <li v-for="user in users">{{ user.name +' '+ user.age }}</li> </ul> <hr> <form v-on:submit.prevent="addNewUser"> <input v-model="user.name" /> <input v-model="user.age" /> <button type="submit">Add User</button> </form> </div>

Here is Vue code:

new Vue({ el: '#app', data: { users: [{name:"Mack", age:20}], user: {name:"", age:0} }, methods: { addNewUser() { this.users.push(this.user); } } });

The Problem

The problem is where I trying to add more than one user to the list. As you can see, when I type new value for the new user, previous values of recently added users change too!

How can I fix it?

Categories: Software

How to pass props using slots from parent to child -vuejs

Vuejs - Wed, 2017-07-19 04:48

I have a parent component and a child component.

The parent component's template uses a slot so that one or more child components can be contained inside the parent.

The child component contains a prop called 'signal'.

I would like to be able to change data called 'parentVal' in the parent component so that the children's signal prop is updated with the parent's value.

This seems like it should be something simple, but I cannot figure out how to do this using slots: Here is a running example below:

const MyParent = Vue.component('my-parent', { template: `<div> <h3>Parent's Children:</h3> <slot :signal="parentVal"></slot> </div>`, data: function() { return { parentVal: 'value of parent' } } }); const MyChild = Vue.component('my-child', { template: '<h3>Showing child {{signal}}</h3>', props: ['signal'] }); new Vue({ el: '#app', components: { MyParent, MyChild } }) <script src="https://unpkg.com/vue/dist/vue.js"></script> <div id="app"> <my-parent> <my-child></my-child> <my-child></my-child> </my-parent> </div>

Categories: Software

How can I "while loop" an Axios GET call till a condition is met?

Vuejs - Wed, 2017-07-19 04:26

I have an API that returns a list of replies (limit 5 replies per call) for a message board thread. What I am trying to do, is look for a specific reply uuid in the response. If not found, make another AXIOS GET call for the next 5 replies.

I want to continue this loop until the UUID is called or the AXIOS GET call comes back with no results.

Example API Request:

http://localhost:8080/api/v2/replies?type=thread&key=e96c7431-a001-4cf2-9998-4e177cde0ec3

Example API Reponse:

"status": "success", "data": [ { "uuid": "0a6bc471-b12e-45fc-bc4b-323914b99cfa", "body": "This is a test 16.", "created_at": "2017-07-16T23:44:21+00:00" }, { "uuid": "0a2d2061-0642-47eb-a0f2-ca6ce5e2ea03", "body": "This is a test 15.", "created_at": "2017-07-16T23:44:16+00:00" }, { "uuid": "32eaa855-18b1-487c-b1e7-52965d59196b", "body": "This is a test 14.", "created_at": "2017-07-16T23:44:12+00:00" }, { "uuid": "3476bc69-3078-4693-9681-08dcf46ca438", "body": "This is a test 13.", "created_at": "2017-07-16T23:43:26+00:00" }, { "uuid": "a3175007-4be0-47d3-87d0-ecead1b65e3a", "body": "This is a test 12.", "created_at": "2017-07-16T23:43:21+00:00" } ], "meta": { "limit": 5, "offset": 0, "next_offset": 5, "previous_offset": null, "next_page": "http://localhost:8080/api/v2/replies?_limit=5&_offset=5", "previous_page": null }

The loop would call an AXIOS GET on the meta > next_page url until either the uuid is found in the results or the meta > next_page is null (meaning no more replies).

Categories: Software

File input on change in vue.js

Vuejs - Wed, 2017-07-19 02:19

Using plain HTML/JS, it is possible to view the JavaScript File objects of selected files for an input element like so:

<input type="file" id="input" multiple onchange="handleFiles(this.files)">

However, when converting it to the 'Vue' way it doesn't seem to work as intend and simply returns undefined instead of returning an Array of File objects.

This is how it looks in my Vue template:

<input type="file" id="file" class="custom-file-input" v-on:change="previewFiles(this.files)" multiple>

Where the previewFiles function is simply the following (located in methods):

methods: { previewFiles: function(files) { console.log(files) } }

Is there an alternate/correct way of doing this? Thanks

Categories: Software

How to correctly use Vue JS watch with lodash debounce

Vuejs - Wed, 2017-07-19 01:22

I'm using lodash to call a debounce function on a component like so:

... import _ from 'lodash'; export default { store, data: () => { return { foo: "", } }, watch: { searchStr: _.debounce(this.default.methods.checkSearchStr(str), 100) }, methods: { checkSearchStr(string) { console.log(this.foo) // <-- ISSUE 1 console.log(this.$store.dispatch('someMethod',string) // <-- ISSUE 2 } } }
  • Issue 1 is that my method checkSearchStr doesn't know about foo
  • Issue 2 is that my store is undefined as well

Why doesn't my method know this when called through _.debounce? And what is the correct usage?

Categories: Software

How to do center layout like this in Vuetify or Material Design?

Vuejs - Wed, 2017-07-19 01:19

I have this layout as of now: enter image description here

But my end goal is this, main content is centered. toolbar and page title is centered but a little bit on the left:

enter image description here

Here's my template layout in Vuetify/Vue

<v-tabs dark fixed centered> <v-toolbar extended class="cyan" dark> <v-toolbar-side-icon></v-toolbar-side-icon> <v-spacer></v-spacer> <v-btn icon> <v-icon>search</v-icon> </v-btn> <v-btn icon> <v-icon>more_vert</v-icon> </v-btn> <v-toolbar-title slot="extension" class="display-3">Share My Pic</v-toolbar-title> </v-toolbar> <v-tabs-bar slot="activators" class="cyan "> <v-tabs-slider class="yellow" >Slider</v-tabs-slider> <v-tabs-item v-for="i in tabArray" :key="i" :href="'#tab-' + i"> {{i}} </v-tabs-item> </v-tabs-bar> <v-tabs-content v-for="i in 3" :key="i" :id="'tab-' + i" > <v-card flat> <v-card-text>{{ text }}</v-card-text> </v-card> </v-tabs-content> </v-tabs>

Kindly help pls. Any good advice to move me in the right direction is appreciated.

-Adi

Categories: Software

how to execute jQuery code when route is visited?

Vuejs - Wed, 2017-07-19 00:41

I have an off-canvas menu that gets drawn in once a Vue route is clicked using jQuery, like so:

$('.order-drawer').show(); $('body').toggleClass( 'order-drawer-open' );

My route is very simple and is displayed as follows:

<router-link to="/order" exact class="order-drawer-toggler"> <a>Order Now</a> </router-link> <router-view></router-view>

Now, how can I make sure that when http://test.dev/test/#/order is viewed in the browser, that then my jQuery calls are getting executed? How can I call a function onload of a route view?

Categories: Software

Importing exif-js library Uncaught ReferenceError: EXIF is not defined error

Vuejs - Wed, 2017-07-19 00:40

I am using vue in a rails application and am trying to import the exif-js library into my script in order to access the global EXIF variable to use as such

var exif = EXIF.readFromBinaryFile(new BinaryFile(this.result));

I have downloaded the package by following these yarn instruction.

yarn add exif-js -- save

I realize I need to use the javascript import to include it into my scripts and have tried

<script> import EXIF from 'exif-js' previewPhoto() { var reader = new FileReader() reader.onload = () => { var exif = EXIF.readFromBinaryFile(new BinaryFile(this.result)); } </script>

and other variances such as import 'exif-js', however I keep getting Uncaught ReferenceError: EXIF is not defined error. How do I successfully import the library so that I can use it in my scripts.

Categories: Software

Behavior of events, and the $event variable in Vue.js

Vuejs - Tue, 2017-07-18 23:38

Using vue.js I am studying DOM manipulation and responses from events. I've noticed that on many events you can simply call a function. Here I simply increase a counter with each click of a button. No arguments are passed. This makes sense to me since there is no data needed by the function.

<div id="content"> <button @click="countUp()">Counter Control</button> <p>{{count}}</p> </div> <script> new Vue({ el: '#content', data: { count: 0 }, methods: { countUp: function(){ this.count ++; } } }) </script>

But now, with a slightly more complicated method at becomes necesary to provide the 'event' argument. The following div tracks the mousemove event and updates the cursors x and y coordinates in real time via methods.

<div @mousemove="updateCoords($event)" style="height:400px;width:400px;border:2px solid black;"> {{x}} {{y}} </div> //the following properties are set up in the data{} object x: 0, y: 0 //this method is added to the methods{} object and is passed event updateCoords: function(event){ this.x = event.clientX; this.y = event.clientY; }

Here this function does not work if event is not passed. It makes sense to me that we would pass something here since X and Y coordinates are dependent on the last location of the event. But how is this data accessed? Do certain events track and store data within themselves?

Finally it seems to make no difference if I pass my method the special $event variable or not. Calling...

@mousemove="updateCoords($event)" //is the same as @mousemove="updateCoords()"

Does view automatically know that an incoming event argument is $event? Or is $event important to use in some other particular case??

Thanks for reading

Categories: Software

Pages