fixes #2: dialogs to show errors
This commit is contained in:
parent
a6a4deff70
commit
8ceaabf5b8
8 changed files with 95 additions and 35 deletions
10
src/App.vue
10
src/App.vue
|
@ -11,12 +11,14 @@
|
||||||
</md-layout>
|
</md-layout>
|
||||||
</md-layout>
|
</md-layout>
|
||||||
</md-layout>
|
</md-layout>
|
||||||
|
<ibt-dialog ref="dialogObj" />
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
<script>
|
<script>
|
||||||
|
|
||||||
import Datepicker from 'vuejs-datepicker';
|
import Datepicker from 'vuejs-datepicker';
|
||||||
import Group from './Group';
|
import Group from './Group';
|
||||||
|
import IbtDialog from './IbtDialog.vue';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
data() {
|
data() {
|
||||||
|
@ -97,7 +99,7 @@ export default {
|
||||||
this.daysUrl.query(params).then((response) => {
|
this.daysUrl.query(params).then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('getSummary: failed to get resource');
|
this.$refs.dialogObj.show({text: 'unable to get the monthly summary'});
|
||||||
}).then((json) => {
|
}).then((json) => {
|
||||||
this.daysSummary = json;
|
this.daysSummary = json;
|
||||||
});
|
});
|
||||||
|
@ -118,9 +120,9 @@ export default {
|
||||||
this.daysUrl.get({day: day}).then((response) => {
|
this.daysUrl.get({day: day}).then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('getDay: failed to get resource');
|
this.$refs.dialogObj.show({text: 'unable to get information about this day'});
|
||||||
}).then((dayData) => {
|
}).then((dayData) => {
|
||||||
if (!dayData.day) {
|
if (!(dayData && dayData.day)) {
|
||||||
dayData.day = day;
|
dayData.day = day;
|
||||||
}
|
}
|
||||||
this.day = dayData;
|
this.day = dayData;
|
||||||
|
@ -129,7 +131,7 @@ export default {
|
||||||
},
|
},
|
||||||
|
|
||||||
components: {
|
components: {
|
||||||
Datepicker, Group
|
Datepicker, Group, IbtDialog
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
<template>
|
<template>
|
||||||
<md-list-item :key="attendee._id">
|
<md-list-item class="attendee-list-item" :key="attendee._id">
|
||||||
<md-icon>person</md-icon>
|
<md-icon>person</md-icon>
|
||||||
<span v-if="!edit">{{attendee.name}}</span>
|
<span v-if="!edit">{{attendee.name}}</span>
|
||||||
<md-input-container md-inline v-if="edit">
|
<md-input-container md-inline v-if="edit">
|
||||||
|
@ -21,10 +21,13 @@
|
||||||
</md-menu-item>
|
</md-menu-item>
|
||||||
</md-menu-content>
|
</md-menu-content>
|
||||||
</md-menu>
|
</md-menu>
|
||||||
|
<ibt-dialog ref="dialogObj" />
|
||||||
</md-list-item>
|
</md-list-item>
|
||||||
</template>
|
</template>
|
||||||
<script>
|
<script>
|
||||||
|
|
||||||
|
import IbtDialog from './IbtDialog.vue';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
props: {attendee: {default: {}}},
|
props: {attendee: {default: {}}},
|
||||||
|
|
||||||
|
@ -62,7 +65,7 @@ export default {
|
||||||
this.attendeesUrl.update({id: this.attendee._id}, this.attendee).then((response) => {
|
this.attendeesUrl.update({id: this.attendee._id}, this.attendee).then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('updateAttendee: failed to update resource');
|
this.$refs.dialogObj.show({text: 'unable to update the attendee'});
|
||||||
}).then((json) => {
|
}).then((json) => {
|
||||||
this.edit = false;
|
this.edit = false;
|
||||||
this.$emit('updated');
|
this.$emit('updated');
|
||||||
|
@ -73,19 +76,23 @@ export default {
|
||||||
this.attendeesUrl.delete({id: this.attendee._id}).then((response) => {
|
this.attendeesUrl.delete({id: this.attendee._id}).then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('deleteAttendee: failed to delete resource');
|
this.$refs.dialogObj.show({text: 'unable to delete the attendee'});
|
||||||
}).then((json) => {
|
}).then((json) => {
|
||||||
this.$emit('updated');
|
this.$emit('updated');
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
|
|
||||||
|
components: {IbtDialog}
|
||||||
};
|
};
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
<style>
|
<style>
|
||||||
|
|
||||||
.md-list-item .md-list-item-holder>.md-icon:first-child {
|
.md-list-item .md-list-item-holder>.md-icon:first-child {
|
||||||
margin-right: 16px;
|
margin-right: 16px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.attendee-list-item {
|
||||||
|
min-width: 250px;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -41,11 +41,13 @@
|
||||||
</md-list>
|
</md-list>
|
||||||
</md-card-content>
|
</md-card-content>
|
||||||
</md-card>
|
</md-card>
|
||||||
|
<ibt-dialog ref="dialogObj" />
|
||||||
</md-layout>
|
</md-layout>
|
||||||
</template>
|
</template>
|
||||||
<script>
|
<script>
|
||||||
|
|
||||||
import Attendee from './Attendee';
|
import Attendee from './Attendee';
|
||||||
|
import IbtDialog from './IbtDialog.vue';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
props: {group: {}, day: {}, addNewGroup: {default: false}},
|
props: {group: {}, day: {}, addNewGroup: {default: false}},
|
||||||
|
@ -87,7 +89,7 @@ export default {
|
||||||
this.attendeesUrl.save({day: this.day, group: group, name: newAttendee}).then((response) => {
|
this.attendeesUrl.save({day: this.day, group: group, name: newAttendee}).then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('addAttendee: failed to get resource');
|
this.$refs.dialogObj.show({text: 'unable to add the attendee'});
|
||||||
}).then((json) => {
|
}).then((json) => {
|
||||||
this.reset();
|
this.reset();
|
||||||
this.$emit('updated');
|
this.$emit('updated');
|
||||||
|
@ -95,7 +97,7 @@ export default {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
components: { Attendee }
|
components: { Attendee, IbtDialog }
|
||||||
};
|
};
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
@ -127,7 +129,7 @@ export default {
|
||||||
}
|
}
|
||||||
|
|
||||||
.new-group {
|
.new-group {
|
||||||
width: 260px;
|
min-width: 250px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.new-group-header i:after {
|
.new-group-header i:after {
|
||||||
|
|
22
src/IbtDialog.vue
Normal file
22
src/IbtDialog.vue
Normal file
|
@ -0,0 +1,22 @@
|
||||||
|
<template>
|
||||||
|
<md-dialog-alert :md-content="dialog.text" :md-ok-text="dialog.ok" ref="ibtDialogObj" />
|
||||||
|
</template>
|
||||||
|
<script>
|
||||||
|
|
||||||
|
export default {
|
||||||
|
props: {dialog: {default: function(){return {text: 'snap! some error has occurred', ok: 'ok'}}}},
|
||||||
|
|
||||||
|
methods: {
|
||||||
|
show(opts) {
|
||||||
|
if (!opts) {
|
||||||
|
opts = {};
|
||||||
|
}
|
||||||
|
this.dialog.text = opts.text || this.dialog.text;
|
||||||
|
this.dialog.ok = opts.ok || this.dialog.ok;
|
||||||
|
this.$refs.ibtDialogObj.open();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
<style>
|
||||||
|
</style>
|
|
@ -28,11 +28,7 @@
|
||||||
</md-button>
|
</md-button>
|
||||||
</span>
|
</span>
|
||||||
<span v-else>
|
<span v-else>
|
||||||
<md-button v-show="!showLoginForm" class="md-icon-button" @click="focusToLoginForm()">
|
<span id="login-form">
|
||||||
<md-tooltip md-direction="left">login or create a new user</md-tooltip>
|
|
||||||
<md-icon>power_settings_new</md-icon>
|
|
||||||
</md-button>
|
|
||||||
<span v-show="showLoginForm" id="login-form">
|
|
||||||
<md-input-container id="username-input" class="login-input" md-inline>
|
<md-input-container id="username-input" class="login-input" md-inline>
|
||||||
<md-tooltip md-direction="bottom">login name or create a new user if it doesn't exist</md-tooltip>
|
<md-tooltip md-direction="bottom">login name or create a new user if it doesn't exist</md-tooltip>
|
||||||
<md-input ref="usernameInput" @keyup.enter.native="focusToPassword()" v-model="username" placeholder="username" md-inline />
|
<md-input ref="usernameInput" @keyup.enter.native="focusToPassword()" v-model="username" placeholder="username" md-inline />
|
||||||
|
@ -49,16 +45,27 @@
|
||||||
</span>
|
</span>
|
||||||
</span>
|
</span>
|
||||||
</span>
|
</span>
|
||||||
|
<md-snackbar md-position="top center" ref="snackbar">
|
||||||
|
<span>{{ snackbackMessage }}</span>
|
||||||
|
<md-button @click="$refs.snackbar.close()" class="snackbar-close">[x]</md-button>
|
||||||
|
</md-snackbar>
|
||||||
|
<ibt-dialog ref="dialogObj" />
|
||||||
</md-toolbar>
|
</md-toolbar>
|
||||||
</template>
|
</template>
|
||||||
<script>
|
<script>
|
||||||
|
|
||||||
|
import IbtDialog from './IbtDialog.vue';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
data () {
|
data () {
|
||||||
return {
|
return {
|
||||||
username: '',
|
username: '',
|
||||||
password: '',
|
password: '',
|
||||||
showLoginForm: false
|
snackbackMessage: '',
|
||||||
|
dialog: {
|
||||||
|
text: 'some error',
|
||||||
|
ok: 'ok'
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -105,7 +112,6 @@ export default {
|
||||||
},
|
},
|
||||||
|
|
||||||
focusToLoginForm() {
|
focusToLoginForm() {
|
||||||
this.showLoginForm = true;
|
|
||||||
var that = this;
|
var that = this;
|
||||||
setTimeout(function() { that.$refs.usernameInput.$el.focus(); }, 400);
|
setTimeout(function() { that.$refs.usernameInput.$el.focus(); }, 400);
|
||||||
},
|
},
|
||||||
|
@ -123,13 +129,12 @@ export default {
|
||||||
// Unable to login? Let's try to create the user!
|
// Unable to login? Let's try to create the user!
|
||||||
if (response.status == 401) {
|
if (response.status == 401) {
|
||||||
if (opt.stopHere) {
|
if (opt.stopHere) {
|
||||||
alert('login: failed to get resource');
|
this.$refs.dialogObj.show({text: 'failed to login and create a new user. Wrong username and password?'});
|
||||||
} else {
|
} else {
|
||||||
this.createUser(user_data);
|
this.createUser(user_data);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}).then((data) => {
|
}).then((data) => {
|
||||||
this.showLoginForm = false;
|
|
||||||
this.getUserInfo();
|
this.getUserInfo();
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
@ -138,9 +143,10 @@ export default {
|
||||||
this.logoutUrl.get().then((response) => {
|
this.logoutUrl.get().then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('logout: failed to get resource');
|
this.$refs.dialogObj.show({text: 'failed to logout'});
|
||||||
}).then((json) => {
|
}).then((json) => {
|
||||||
this.$store.commit('clearLoggedInUser');
|
this.$store.commit('clearLoggedInUser');
|
||||||
|
this.showMessage('logged out');
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -161,7 +167,7 @@ export default {
|
||||||
this.currentUserUrl.get().then((response) => {
|
this.currentUserUrl.get().then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('getUserInfo: failed to get resource');
|
this.$refs.dialogObj.show({text: 'unable to get user info'});
|
||||||
}).then((data) => {
|
}).then((data) => {
|
||||||
data = data || {};
|
data = data || {};
|
||||||
this.$store.commit('setLoggedInUser', data);
|
this.$store.commit('setLoggedInUser', data);
|
||||||
|
@ -169,8 +175,15 @@ export default {
|
||||||
callback(data);
|
callback(data);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
showMessage(message) {
|
||||||
|
this.snackbackMessage = message;
|
||||||
|
this.$refs.snackbar.open();
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
|
|
||||||
|
components: { IbtDialog }
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
<style>
|
<style>
|
||||||
|
@ -239,4 +252,9 @@ export default {
|
||||||
color: white !important;
|
color: white !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.snackbar-close {
|
||||||
|
font-weight: bold;
|
||||||
|
color: #f6f72f;
|
||||||
|
}
|
||||||
|
|
||||||
</style>
|
</style>
|
||||||
|
|
12
src/User.vue
12
src/User.vue
|
@ -19,10 +19,13 @@
|
||||||
<md-button class="md-raised md-primary" @click="save()">Save</md-button>
|
<md-button class="md-raised md-primary" @click="save()">Save</md-button>
|
||||||
</md-card-content>
|
</md-card-content>
|
||||||
</md-card>
|
</md-card>
|
||||||
|
<ibt-dialog ref="dialogObj" />
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
<script>
|
<script>
|
||||||
|
|
||||||
|
import IbtDialog from './IbtDialog.vue';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
data () {
|
data () {
|
||||||
return {
|
return {
|
||||||
|
@ -50,22 +53,25 @@ export default {
|
||||||
this.usersUrl.get({id: id}).then((response) => {
|
this.usersUrl.get({id: id}).then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('getUsers: unable to get resource');
|
this.$refs.dialogObj.show({text: 'unable to get user'});
|
||||||
}).then((data) => {
|
}).then((data) => {
|
||||||
this.user = data || {};
|
this.user = data || {};
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
save() {
|
save() {
|
||||||
var user_data = {password: this.password, email: this.user.email};
|
var user_data = {password: this.password, email: this.user.email};
|
||||||
this.usersUrl.update({id: this.user._id}, user_data).then((response) => {
|
this.usersUrl.update({id: this.user._id}, user_data).then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('save: unable to get resource');
|
this.$refs.dialogObj.show({text: 'unable to save user settings'});
|
||||||
}).then((data) => {
|
}).then((data) => {
|
||||||
this.user = data;
|
this.user = data;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
|
|
||||||
|
components: { IbtDialog }
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
|
|
@ -27,10 +27,13 @@
|
||||||
</md-table>
|
</md-table>
|
||||||
</md-card-content>
|
</md-card-content>
|
||||||
</md-card>
|
</md-card>
|
||||||
|
<ibt-dialog ref="dialogObj" />
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
<script>
|
<script>
|
||||||
|
|
||||||
|
import IbtDialog from './IbtDialog.vue';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
data () {
|
data () {
|
||||||
return {
|
return {
|
||||||
|
@ -61,7 +64,7 @@ export default {
|
||||||
this.usersUrl.get().then((response) => {
|
this.usersUrl.get().then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('getUsers: unable to get resource');
|
this.$refs.dialogObj.show({text: 'unable to get the list of users'});
|
||||||
}).then((data) => {
|
}).then((data) => {
|
||||||
this.users = data.users || [];
|
this.users = data.users || [];
|
||||||
});
|
});
|
||||||
|
@ -71,11 +74,13 @@ export default {
|
||||||
this.usersUrl.update({id: userId}).then((response) => {
|
this.usersUrl.update({id: userId}).then((response) => {
|
||||||
return response.json();
|
return response.json();
|
||||||
}, (response) => {
|
}, (response) => {
|
||||||
alert('deleteUser: unable to get resource');
|
this.$refs.dialogObj.show({text: 'unable to delete the user'});
|
||||||
}).then((data) => {
|
}).then((data) => {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
|
|
||||||
|
components: { IbtDialog }
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
|
|
@ -41,11 +41,9 @@ class Ibt2Tests(unittest.TestCase):
|
||||||
self.db['users'].remove({'username': 'newuser2'})
|
self.db['users'].remove({'username': 'newuser2'})
|
||||||
|
|
||||||
def tearDown(self):
|
def tearDown(self):
|
||||||
return
|
self.db['attendees'].drop()
|
||||||
self.add_attendee({'day': '2017-01-15', 'name': 'A name', 'group': 'group A'})
|
self.db['users'].remove({'username': 'newuser'})
|
||||||
self.add_attendee({'day': '2017-01-16', 'name': 'A new name', 'group': 'group C'})
|
self.db['users'].remove({'username': 'newuser2'})
|
||||||
self.add_attendee({'day': '2017-01-15', 'name': 'Another name', 'group': 'group A'})
|
|
||||||
self.add_attendee({'day': '2017-01-15', 'name': 'Yet another name', 'group': 'group B'})
|
|
||||||
|
|
||||||
def add_attendee(self, attendee):
|
def add_attendee(self, attendee):
|
||||||
r = requests.post('%sattendees' % BASE_URL, json=attendee)
|
r = requests.post('%sattendees' % BASE_URL, json=attendee)
|
||||||
|
|
Loading…
Reference in a new issue