#1: draft of user page using Vuex
This commit is contained in:
parent
d87e555dea
commit
0684f927b4
5 changed files with 143 additions and 36 deletions
|
@ -22,7 +22,8 @@
|
|||
"vue-material": "^0.6.3",
|
||||
"vue-resource": "^1.0.3",
|
||||
"vue-router": "^2.1.1",
|
||||
"vuejs-datepicker": "^0.4.27"
|
||||
"vuejs-datepicker": "^0.4.27",
|
||||
"vuex": "^2.1.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"autoprefixer": "^6.4.0",
|
||||
|
|
113
src/Toolbar.vue
113
src/Toolbar.vue
|
@ -1,11 +1,20 @@
|
|||
<template>
|
||||
<md-toolbar id="toolbar" class="md-dense">
|
||||
<span v-if="currentPath == 'user'">
|
||||
<md-button class="md-icon-button" @click="goBack()">
|
||||
<md-icon>backspace</md-icon>
|
||||
</md-button>
|
||||
</span>
|
||||
<span v-else class="button-spacer"> </span>
|
||||
<h2 id="toolbar-title" class="md-title">ibt2</h2>
|
||||
<span v-if="loggedInUser.username">
|
||||
<span id="logged-in">
|
||||
Logged in: <router-link :to="userUrl">{{ loggedInUser.username }}</router-link>
|
||||
<md-button id="logged-in-icon" class="md-icon-button" @click="toUserPage()">
|
||||
<md-icon>person_pin</md-icon>
|
||||
</md-button>
|
||||
<span id="logged-in" class="md-subheading">
|
||||
<router-link :to="userUrl" class="username-link">{{ loggedInUser.username }}</router-link>
|
||||
</span>
|
||||
<md-button class="md-icon-button" @click="logout()">
|
||||
<md-button id="logout-icon" class="md-icon-button" @click="logout()">
|
||||
<md-icon>exit_to_app</md-icon>
|
||||
</md-button>
|
||||
</span>
|
||||
|
@ -15,11 +24,16 @@
|
|||
</md-button>
|
||||
<span v-show="showLoginForm" id="login-form">
|
||||
<md-input-container id="username-input" class="login-input" md-inline>
|
||||
<md-input ref="usernameInput" @keyup.enter.native="focusToPassword()" v-model="username" placeholder="username" md-inline />
|
||||
</md-input-container>
|
||||
<md-input-container id="password-input" class="login-input" md-inline>
|
||||
<md-input ref="passwordInput" @keyup.enter.native="login()" v-model="password" placeholder="password" type="password" md-line />
|
||||
</md-input-container>
|
||||
<md-input ref="usernameInput" @keyup.enter.native="focusToPassword()" v-model="username" placeholder="username" md-inline />
|
||||
</md-input-container>
|
||||
<span id="password-block">
|
||||
<md-input-container id="password-input" class="login-input" md-inline>
|
||||
<md-input ref="passwordInput" @keyup.enter.native="login()" v-model="password" placeholder="password" type="password" md-line />
|
||||
</md-input-container>
|
||||
<md-button id="login-button" class="md-icon-button" @click="login()">
|
||||
<md-icon>play_circle_outline</md-icon>
|
||||
</md-button>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
</md-toolbar>
|
||||
|
@ -31,8 +45,7 @@ export default {
|
|||
return {
|
||||
username: '',
|
||||
password: '',
|
||||
showLoginForm: false,
|
||||
loggedInUser: {username: ''}
|
||||
showLoginForm: false
|
||||
}
|
||||
},
|
||||
|
||||
|
@ -43,10 +56,19 @@ export default {
|
|||
return '';
|
||||
}
|
||||
return '/user/' + this.loggedInUser._id;
|
||||
},
|
||||
|
||||
loggedInUser() {
|
||||
return this.$store.state.loggedInUser;
|
||||
},
|
||||
|
||||
currentPath() {
|
||||
return this.$route.name;
|
||||
}
|
||||
},
|
||||
|
||||
beforeCreate: function() {
|
||||
this.usersUrl = this.$resource('users');
|
||||
this.currentUserUrl = this.$resource('users/current');
|
||||
this.loginUrl = this.$resource('login');
|
||||
this.logoutUrl = this.$resource('logout');
|
||||
|
@ -57,6 +79,14 @@ export default {
|
|||
},
|
||||
|
||||
methods: {
|
||||
goBack() {
|
||||
this.$router.back();
|
||||
},
|
||||
|
||||
toUserPage() {
|
||||
this.$router.push(this.userUrl);
|
||||
},
|
||||
|
||||
focusToLoginForm() {
|
||||
this.showLoginForm = true;
|
||||
var that = this;
|
||||
|
@ -68,10 +98,13 @@ export default {
|
|||
},
|
||||
|
||||
login() {
|
||||
this.loginUrl.save({username: this.username, password: this.password}).then((response) => {
|
||||
var user_data = {username: this.username, password: this.password};
|
||||
this.loginUrl.save(user_data).then((response) => {
|
||||
return response.json();
|
||||
}, (response) => {
|
||||
alert('login: failed to get resource');
|
||||
if (response.status == 401) {
|
||||
this.createUser(user_data);
|
||||
}
|
||||
}).then((data) => {
|
||||
this.showLoginForm = false;
|
||||
this.getUserInfo();
|
||||
|
@ -84,28 +117,42 @@ export default {
|
|||
}, (response) => {
|
||||
alert('logout: failed to get resource');
|
||||
}).then((json) => {
|
||||
this.loggedInUser = {};
|
||||
this.$store.commit('clearLoggedInUser');
|
||||
});
|
||||
},
|
||||
|
||||
createUser(user_data) {
|
||||
user_data.username = user_data.username || {};
|
||||
user_data.username = user_data.username || this.username;
|
||||
user_data.password = user_data.password || this.password;
|
||||
this.usersUrl.save(user_data).then((response) => {
|
||||
return response.json();
|
||||
}, (response) => {
|
||||
alert('createUser: failed to get resource');
|
||||
}).then((json) => {
|
||||
this.showLoginForm = false;
|
||||
this.getUserInfo();
|
||||
});
|
||||
|
||||
},
|
||||
|
||||
getUserInfo(callback) {
|
||||
this.currentUserUrl.get().then((response) => {
|
||||
return response.json();
|
||||
}, (response) => {
|
||||
alert('getUserInfo: failed to get resource');
|
||||
}).then((data) => {
|
||||
this.loggedInUser = data || {};
|
||||
data = data || {};
|
||||
this.$store.commit('setLoggedInUser', data);
|
||||
if (callback) {
|
||||
callback(this.loggedInUser);
|
||||
callback(data);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
|
||||
#toolbar-title {
|
||||
flex: 1;
|
||||
}
|
||||
|
@ -117,23 +164,53 @@ export default {
|
|||
padding-left: 4px;
|
||||
min-height: 24px;
|
||||
line-height: 0px;
|
||||
margin-right: 20px;
|
||||
background-color: white;
|
||||
}
|
||||
|
||||
#username-input {
|
||||
display: inline;
|
||||
float: left;
|
||||
margin-right: 20px;
|
||||
}
|
||||
|
||||
#password-input {
|
||||
display: inline;
|
||||
float: left;
|
||||
}
|
||||
|
||||
#password-block {
|
||||
display: inline;
|
||||
float: right;
|
||||
}
|
||||
|
||||
#login-button {
|
||||
height: 32px;
|
||||
}
|
||||
|
||||
#logged-in-icon {
|
||||
margin-right: 0px;
|
||||
padding-right: 0px;
|
||||
color: #f6f72f !important;
|
||||
}
|
||||
|
||||
#logged-in {
|
||||
position: relative;
|
||||
top: 10px;
|
||||
|
||||
}
|
||||
|
||||
#logout-icon {
|
||||
margin-left: 0px;
|
||||
padding-left: 0px;
|
||||
}
|
||||
|
||||
.username-link {
|
||||
font-weight: bold;
|
||||
color: #f6f72f !important;
|
||||
}
|
||||
|
||||
.button-spacer {
|
||||
width: 52px;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
|
23
src/User.vue
23
src/User.vue
|
@ -1,6 +1,6 @@
|
|||
<template>
|
||||
<div id="user">
|
||||
User
|
||||
User {{loggedInUser}}
|
||||
</div>
|
||||
</template>
|
||||
<script>
|
||||
|
@ -11,6 +11,15 @@ export default {
|
|||
}
|
||||
},
|
||||
|
||||
computed: {
|
||||
count() {
|
||||
return this.$store.state.count;
|
||||
},
|
||||
loggedInUser() {
|
||||
return this.$store.state.loggedInUser;
|
||||
}
|
||||
},
|
||||
|
||||
beforeCreate: function() {
|
||||
this.userUrl = this.$resource('users');
|
||||
},
|
||||
|
@ -19,18 +28,6 @@ export default {
|
|||
},
|
||||
|
||||
methods: {
|
||||
getUserInfo(callback) {
|
||||
this.currentUserUrl.get().then((response) => {
|
||||
return response.json();
|
||||
}, (response) => {
|
||||
alert('getUserInfo: failed to get resource');
|
||||
}).then((data) => {
|
||||
this.loggedInUser = data || {};
|
||||
if (callback) {
|
||||
callback(this.loggedInUser);
|
||||
}
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
components: {
|
||||
|
|
25
src/main.js
25
src/main.js
|
@ -1,6 +1,7 @@
|
|||
// The Vue build version to load with the `import` command
|
||||
// (runtime-only or standalone) has been set in webpack.base.conf with an alias.
|
||||
import Vue from 'vue';
|
||||
import Vuex from 'vuex';
|
||||
import VueRouter from 'vue-router';
|
||||
import VueResource from 'vue-resource';
|
||||
import VueMaterial from 'vue-material';
|
||||
|
@ -8,25 +9,41 @@ import 'vue-material/dist/vue-material.css';
|
|||
import 'roboto-fontface/css/roboto/roboto-fontface.css';
|
||||
import 'material-design-icons/iconfont/material-icons.css';
|
||||
import jQuery from 'jquery';
|
||||
import store_data from './store.js';
|
||||
import App from './App';
|
||||
import User from './User';
|
||||
import Toolbar from './Toolbar';
|
||||
|
||||
Vue.use(Vuex);
|
||||
Vue.use(VueRouter);
|
||||
Vue.use(VueResource);
|
||||
Vue.use(VueMaterial);
|
||||
|
||||
var routes = [
|
||||
{path: '/', component: App},
|
||||
{path: '/day/', component: App},
|
||||
{path: '/day/:day', component: App},
|
||||
{path: '/user/:user', component: User}
|
||||
{path: '/', name: 'root', component: App},
|
||||
{path: '/day/', name: 'days', component: App},
|
||||
{path: '/day/:day', name: 'day', component: App},
|
||||
{path: '/user/:user', name: 'user', component: User}
|
||||
];
|
||||
|
||||
const store = new Vuex.Store(store_data);
|
||||
const router = new VueRouter({routes});
|
||||
|
||||
const store2 = new Vuex.Store({
|
||||
state: {
|
||||
count: 0
|
||||
},
|
||||
mutations: {
|
||||
increment (state) {
|
||||
state.count++;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
var vue = new Vue({
|
||||
el: '#app',
|
||||
store: store,
|
||||
template: '<div id="app"><Toolbar /><router-view class="view"></router-view></div>',
|
||||
router: router,
|
||||
components: { App, Toolbar, User }
|
||||
|
|
15
src/store.js
Normal file
15
src/store.js
Normal file
|
@ -0,0 +1,15 @@
|
|||
|
||||
export default {
|
||||
state: {
|
||||
loggedInUser: {username: ''}
|
||||
},
|
||||
mutations: {
|
||||
clearLoggedInUser(state, user) {
|
||||
state.loggedInUser = {username: ''};
|
||||
},
|
||||
setLoggedInUser(state, user) {
|
||||
state.loggedInUser = user;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
Loading…
Reference in a new issue