Software

What's the use of webpack in vue CLI?

Vuejs - Mon, 2017-08-07 11:06

Ok, so I'm not being able to comprehend what value "webpack" gives in conext of Vue CLI.

I just installed vue cli globally.

then I made a directory manually and created a c1.vue file in it. With the template, script and style tags and related code.

and i compiled it using the command vue build --prod --lib c1.vue and it produced a c1.css and a c1.js file(s).

I simply add these files to my custom index.html file and use vue using a cdn and everything works !

So what's the point of webpack ?

Categories: Software

Can I call a method from a watch and mounted?

Vuejs - Mon, 2017-08-07 10:46

I have a functionality (getAllData which does an external data query) which I need to call at two occasions: when the component is mounted and when a prop changes.

I am however getting a TypeError: this.getAllData is not a function when using it in a watch and in mounted.

Since methods can be called from methods, I am wondering whether this is true for methods being called from components such as watch or mounted.

My (simplified) instance is below:

export default { props: ['triggerReload'], data: function () { return { // some variables } }, watch: { triggerReload: this.getAllData() }, methods: { getAllData: function () { // this function correctly fetches external data } }, mounted: this.getAllData() }

My workaround will be to either duplicate the code of the function (which is not DRY) or to call an external function (defined outside the Vue instance - which is probably also an anti-pattern) EDIT: this is a component so I do not know how to call an external function and reference the instance (it is not instantiated by var vm = new Vue(...))

Categories: Software

Typescript emitted no output when running unit test

Vuejs - Mon, 2017-08-07 10:35

I have declared saveral variables in .d.ts files. It works right when running pack or build commands. But when I run unit test cases, things go wrong.

framework: vue+typescript+webpack

test runner: karma

I assume the problem is including .d.ts files is src, and I tried to exclude them. below is my regexp:

/\.\/(?!main\.ts)(?!((\S*\.d\.ts)|(\S*\.scss))$)/

tested already, seems it doesn't work. keep throwing these exceptions. drvies me crazy.

files in karma.conf.js

exceptions

anyone knows how to solve this issue?

Categories: Software

How to test async method in Vuejs's component when using jest and avoriaz

Vuejs - Mon, 2017-08-07 10:12

For instance, I have a component looks like this.

<template> <div id="app"> <button class="my-btn" @click="increment">{{ val }}</button> </div> </template> <script> export default { data: { return { val: 1, }; }, methods: { increment() { fetch('/echo/html/').then((response) => { this.val++; }).catch((error) => { console.log(error); }); }, }, } </script>

You can also check this fiddle as a simplified demo

In order to do unit test for this component, I wrote code like this.

// Jest used here test('should work', () => { // wrapper was generated by using avoriaz's mount API // `val` was 1 when mounted. expect(wrapper.data().val).toBe(1); // trigger click event for testing wrapper.find('.my-btn')[0].trigger('click'); // `val` should be 2 when the button clicked. // But how can I force jest to wait until `val` was set? expect(wrapper.data().val).toBe(2); });

It didn't work since expect ran before fetch's done, but I've no idea how to let jest wait until promise function done.
So how can I test in this use case?

Categories: Software

In Vue.js, POST method is not working using axios.post method

Vuejs - Mon, 2017-08-07 10:10

I am new to Vue.js. I am trying to create a simple login form, that will submit the values to a ASP.net Web API. When I click the submit button, I do not see the form data under POST. I am using Fiddler to check the POST data, which shows nothing under "WebForms" tab. On the ASP.net Web API the form object is shown as null. (For the sake of simplicity, I am passing hard code value to the post fields)

Following is the HTML inside login.vue

<template> <v-ons-page> <v-ons-toolbar> <div class="center">Log in </div> </v-ons-toolbar> <p style="text-align: center"> <img src="../assets/Image logo transparent.png" /> </p> <p style="text-align: center"> <v-ons-input modifier="underbar" placeholder="Username" type="text" v-model="user.name" float></v-ons-input> </p> <p style="text-align: center"> <v-ons-input modifier="underbar" type="password" placeholder="Password" v-model="user.password" float></v-ons-input> </p> <p style="text-align: center"> <v-ons-button @click="login($event)"> <div>Log in</div> </v-ons-button> </p> </v-ons-page> </template>

Following is the section where POST happens through axios

<script> import axios from 'axios' export default { name: 'login', data: { username: '', password: '' }, computed: { user: { get () { return this.$store.state.user } } }, methods: { login (event) { axios.post('http://localhost:54977/api/Roles', { username: 'Fred', password: 'Flintstone'}) .then(response => { this.$ons.notification.alert('Logeed in. Hurrey!!') }) .catch(e => { this.$ons.notification.alert('No donut for you. :(') this.errors.push(e) }) } } } </script>
Categories: Software

How to correctly import css/styl files into a JavaScript file?

Vuejs - Mon, 2017-08-07 10:09

The file I want to import has this location: src/assets/css/global.styl.

I import it into vue files like this:

src/App.vue

<style lang="stylus"> @import './assets/css/global'

I recently installed Storybook for Vue. I'm trying to import global.styl into the index.js file of Storybook for Vue:

src/stories/index.js

import '../assets/css/global.styl' // this works wine

However, I get this error:

ERROR in ./src/assets/css/global.styl Module not found: Error: Can't resolve './assets/img/buttons/radio-selected.svg' in 'E:\alex\vreditor\src\assets\css' @ ./src/assets/css/global.styl 7:12959-13009 @ ./src/stories/index.js @ ./.storybook/config.js @ multi ./~/@storybook/vue/dist/server/config/polyfills.js ./~/@storybook/vue/dist/server/config/globals.js (webpack)-hot-middleware/client.js?reload=true ./.storybook/config.js

Why is this? and how to solve it?

NOTE: Seems like global.styl is being correctly imported. The problem are the relative paths inside the file:

input[type="radio"]:checked + label { &::before { background-image: url('./assets/img/buttons/radio-selected.svg') // Storybook can't find this. } }
Categories: Software

How can I disable back button on the browser with vue component?

Vuejs - Mon, 2017-08-07 09:46

My vue component like this :

<template> <span class="rating"> ... </span> </template> <script> export default { props: { 'star': null }, ... } </script>

If the component is running I want to disable button back in the browser. So the user can not go back to the previous page

How can I do it?

Categories: Software

Webpack with babel-loader not emitting valid es5

Vuejs - Mon, 2017-08-07 09:42

I have a webpack config that is based off https://github.com/vuejs-templates/webpack-simple/blob/master/template/webpack.config.js It uses vue-loader and babel-loader. The issue is I cannot get it to generate ES5 code so that it will work in the most broad range of clients.

If I use the ES2015 preset, webpack.optimize.UglifyJsPlugin fails to minify the output because Uglify can only handle ES5 (not counting the harmony branch). The errors are similar to: Unexpected token: punc (() and occur in multiple files.

I can work around this by using babili-webpack-plugin which will minify the ES6 code but is very slow. However, when I deploy this code, I see errors being reported back saying Block-scoped declarations (let, const, function, class) not yet supported outside strict mode so I know they are older clients choking on ES6 code.

How can I get proper ES5 code output from babel-loader? I have tried multiple presets, with or without the transform-runtime plugin. Config below:

const webpack = require('webpack'); const globEntries = require('webpack-glob-entries'); const _ = require('lodash'); const path = require('path'); const BabiliPlugin = require("babili-webpack-plugin"); const env = process.env.NODE_ENV; let entries; if (env === 'production') { entries = globEntries('./src/**/vue/*.js'); } else { entries = _.mapValues(globEntries('./src/**/vue/*.js'), entry => [entry, 'webpack-hot-middleware/client?reload=true']); } module.exports = { entry: entries, output: { path: '/', ///no real path is required, just pass "/" publicPath: '/vue', filename: '[name].js', }, module: { rules: [ { test: /\.vue$/, loader: 'vue-loader', options: { loaders: { scss: 'vue-style-loader!css-loader!sass-loader', sass: 'vue-style-loader!css-loader!sass-loader?indentedSyntax', }, // other vue-loader options go here }, }, { test: /\.js$/, exclude: /node_modules/, use: { loader: 'babel-loader', query: { presets: ['es2015'], plugins: ['transform-runtime'], }, }, }, { test: /\.(png|jpg|gif|svg)$/, loader: 'file-loader', options: { name: '[name].[ext]?[hash]', }, }, ], }, resolve: { alias: { vue$: 'vue/dist/vue.esm.js', }, }, plugins: [ new webpack.HotModuleReplacementPlugin(), // Enable HMR new webpack.NoEmitOnErrorsPlugin(), ], performance: { hints: false, }, devtool: '#eval-source-map', }; if (env === 'staging' || env === 'production') { //module.exports.devtool = env === 'staging' ? '#source-map' : false; module.exports.devtool = '#source-map'; module.exports.output.path = path.resolve(__dirname, './src/v1/parse/cloud/public/vue'); // http://vue-loader.vuejs.org/en/workflow/production.html module.exports.plugins = (module.exports.plugins || []).concat([ new webpack.DefinePlugin({ 'process.env': { NODE_ENV: `"${env}"`, }, }), new webpack.optimize.UglifyJsPlugin({ sourceMap: true, compress: { warnings: false, }, }), // new BabiliPlugin(), new webpack.LoaderOptionsPlugin({ minimize: true, }), ]); }
Categories: Software

Vue.js data value not updating when adding new value

Vuejs - Mon, 2017-08-07 09:13

When new bars value are set, the data is not updated. Please check below;

I'm planning to do dynamic bars and buttons. Once the buttons are clicked, the new values will be updated to bars values.

Here is the link

HTML

<h1><span>Vue.js</span> Progress Bar</h1> <div id="app"> <div v-for="(index, bar) in bars" class="shell"> <div class="bar" :style="{ width: bar + '%' }" .> <span>{{ bar }}%</span> <input type="radio" id="radio-bar" value="{{ index }}" v-model="picked" v-on:change="set(index)"> </div> </div> <span v-for="(index, button) in buttons"> <button value="{{ button }}" @click.prevent="makeProgress(button)">{{ button }}</button> </span> <br> <p>Selected Bar: {{ picked }}</p> <p>Button Value: {{ buttonVal }}</p> </div>

JS

var dataURL = 'http://pb-api.herokuapp.com/bars'; var vm = new Vue({ el: "#app", data: { maxColor: "#F22613", bars: [], buttons: [], limit: 0, selectedBar: 0, buttonVal: 0 }, methods: { fetchData: function(params) { this.$http.get(dataURL, function(data) { this.$set('bars', data.bars); this.$set('buttons', data.buttons); this.$set('limit', data.limit); console.log(params); }); }, set: function(index) { this.selectedBar = index; }, makeProgress: function(button) { var self = this; self.buttonVal += button; this.reachMax(); Vue.set(this.bars, 0, 55); }, reachMax() { if(this.buttonVal >= this.limit){ alert('Reached Limit' + this.limit) } } }, created: function() { this.fetchData(); } });
Categories: Software

axios set headers in config vue js

Vuejs - Mon, 2017-08-07 09:12

Right now I use axios like this:

import axios from 'axios' axios.get(apiObjUrl, { headers: { 'Content-type': 'application/x-www-form-urlencoded', } }) .then(({data}) => {

How do I set global axios header? (I need to set localization header to use in all my requests)

Categories: Software

Laravel Vue SPA vs SSR

Vuejs - Mon, 2017-08-07 08:49

Many laravel/vue tutorials use ajax calls to get the data. It seems that the SPA is completely isolated from Laravel. I.e. Laravel is just a data API and the vue app could also simply be hosted on a third party external server (e.g. AWS S3). Is this the recommended way, or should I rather use Laravel for Routing and have separate views that implement individual components and already included data instead of using a SPA?

Categories: Software

insert tab pages inside v-ons-tabbar

Vuejs - Mon, 2017-08-07 08:37

Here's my component.

<template> <v-ons-page> <v-ons-tabbar :visible="true" :tabs="tabs" position="top"> </v-ons-tabbar> </v-ons-page> </template> <template id="pendingPage"> <v-ons-page> <p>pending items</p> </v-ons-page> </template> <template id="completedPage"> <v-ons-page> <p>completed items</p> </v-ons-page> </template> <script> import Vue from 'vue'; const pendingPage = { template: '#pendingPage' }; const completedPage = { template: '#completedPage' }; export default { data() { return { activeIndex: 0, tabs: [ { label: 'Pending', page: pendingPage }, { label: 'Completed', page: completedPage } ] }; } }; </script>

Expected: I expect my component to render two tabs - Pending & Completed.

Problem: It only renders completedPage.

What I am doing wrong here?

Categories: Software

How access Vue Js computed properties?

Vuejs - Mon, 2017-08-07 08:32

I have the next code with vuejs, i call axios method post and set the authenticated user correctly(cosole show the user), but when i call the computed property in the component the user is empty

export default { data() { return { isAuth: null, } }, computed: { authenticatedUser () { return this.getAuthenticatedUser() } }, created() { this.isAuth = this.$auth.isAuthenticated() this.setAuthenticatedUser() }, methods: { setAuthenticatedUser () { axios.get('/api/user') .then(response => { this.$auth.setAuthenticatedUser(response.data) console.log(this.$auth.getAuthenticatedUser()) }) }, getAuthenticatedUser(){ return this.$auth.getAuthenticatedUser() } }, router }

And this my code for get the authenticated user

export default function (Vue) { let authenticatedUser = {}; Vue.auth = { //set token setToken (token, expiration) { localStorage.setItem('token', token) localStorage.setItem('expiration', expiration) }, //get token getToken() { var token = localStorage.getItem('token') var expiration = localStorage.getItem('expiration') if( !token || !expiration) return null if(Date.now() > parseInt(expiration)){ this.destroyToken() return null } else{ return token } }, //destroy token destroyToken() { localStorage.removeItem('token') localStorage.removeItem('expiration') }, //isAuthenticated isAuthenticated() { if(this.getToken()) return true else return false }, setAuthenticatedUser(data){ return authenticatedUser = data; }, getAuthenticatedUser(){ return authenticatedUser; }, } Object.defineProperties(Vue.prototype, { $auth: { get() { return Vue.auth } } }) }

When i not use the computed property When i not use the computed property

When i use the computed property in the model When i use the computed property in the model

Categories: Software

Append array inside object using $set

Vuejs - Mon, 2017-08-07 06:16

I have an object and the structure looks like this

obj: { 1: { 'a': [ [] ], 'b': [ [] ] } }

Now, in watcher, I am trying to append 'c' => [ [] ] to this object.

  • I tried using this.obj[key]['c'] = [ [] ], but it doesn't watch changes on the props when I do it this way. I am almost sure that I need to use $set

  • this.$set(this.obj, key, { ['c']: [ [] ] }) - using this actually watches it, however it removes 'a' and 'b' properties entirely.

What is the proper way of using $set

Categories: Software

(vuejs)this.$router.go() doesn't work in safari of iOS 10.3.2 only

Vuejs - Mon, 2017-08-07 05:43

It's works fine in Android's broswer or iPhone's Safari with other versions of iOS. But in 10.3.2, doesn't jump to target page.

Categories: Software

Vue.js routing with Express

Vuejs - Mon, 2017-08-07 05:40

I've created a portfolio here https://temp-portfolio.herokuapp.com. My issue is that when a user refreshes a page other than index.html or goes straight to another link such as https://temp-portfolio.herokuapp.com/projects the routing doesn't render. I've set up everything using Node.js and Express on Heroku following this guide https://medium.com/@sagarjauhari/quick-n-clean-way-to-deploy-vue-webpack-apps-on-heroku-b522d3904bc8.

I tried rewriting the server to this https://stackoverflow.com/a/44226999/4178637 but the app crashes.

server.js

var express = require('express'); var path = require('path'); var serveStatic = require('serve-static'); app = express(); app.use(serveStatic(__dirname)); var port = process.env.PORT || 5000; app.listen(port); console.log('server started '+ port);

index.js

import Vue from 'vue' import Router from 'vue-router' import Nav from '@/components/Nav' import Home from '@/components/Home' import Projects from '@/components/Projects' import Urban from '@/components/Urban' import Seizure from '@/components/Seizure' import Explosion from '@/components/Explosion' import Decadence from '@/components/Decadence' import Threshold from '@/components/Threshold' Vue.use(Router) Vue.component('app-nav', Nav) export default new Router({ routes: [ { path: '/', name: 'Home', component: Home }, { path: '/projects', name: 'Projects', component: Projects }, { path: '/projects/urban', name: 'Urban', component: Urban }, { path: '/projects/seizure', name: 'Seizure', component: Seizure }, { path: '/projects/explosion', name: 'Explosion', component: Explosion }, { path: '/projects/decadence', name: 'Decadence', component: Decadence }, { path: '/projects/threshold', name: 'Threshold', component: Threshold } ], mode: 'history' })

main.js

import Vue from 'vue' import App from './App' import router from './router' import './assets/styles/styles.scss' Vue.config.productionTip = false new Vue({ el: '#app', router, template: '<App/>', components: { App } })
Categories: Software

Can't access data variable inside watcher, inside .map()

Vuejs - Mon, 2017-08-07 05:29

My root looks like this. I have defined types and history variables inside data and in watch, I am trying to access another variable rather than the one I am watching. Trying to access history variable outside .map() works however using it inside .map() returns undefined

new Vue({ el: '#root', data: { types: {}, history: {} } watch: { types: { handler(obj) { console.log(this.history) // works types.map(function(val) { console.log(this.history) // undefined }) } } } }
Categories: Software

Cannot access other data values inside watch

Vuejs - Mon, 2017-08-07 04:11

In my root, i have a setup like this,

new Vue({ el: '#root', data: { types: {}, history: {} } watch: { types: { handler(obj) { console.log(this.history) // gives me undefined } } } }

this.history throws undefined even though it is initialised as an empty object in data. Also, in this watcher, I can not use my methods inside methods: {}, it also says undefined.

However, if I do $vm0.history in my console, it doesn't say undefined.

What is the proper way of achieving this?

Categories: Software

vue js: How get parent id in directive (eg v-if)

Vuejs - Mon, 2017-08-07 01:52
<div class="video" id="LOLPS32nWsg"> <div class="frame_block" v-if="videoShow('LOLPS32nWsg')"> </div> </div> methods: { videoShow: function (videoId) { return (videoId === this.video_id) ? true : false; }, }

How get id from class="video" and use in directive v-if?

Categories: Software

Should my Vue.js code have multiple small instances or a single big instance?

Vuejs - Mon, 2017-08-07 01:51

I'm starting with vue.js. My question is about design patterns.

Should I have multiple Vue instances like this one:

var example = new Vue({ el: '#post-list', data: { posts: [ { title: 'Foo' }, { title: 'Bar' } ] } }); var example2 = new Vue({ el: '#post-list2', data: { posts: [ { title: 'Foo' }, { title: 'Bar' } ] } });

Or should I try to group my Vue code inside a big #app element like this:

var app= new Vue({ el: '#app', data: { posts1: [ { title: 'Foo' }, { title: 'Bar' } ], posts2: [ { title: 'Foo' }, { title: 'Bar' } ] } });

I'm looking for code maitenance and performance. What are the advantages of each approach? Is there a better pattern to follow?

Categories: Software

Pages