Сообщение о неверном вводе

This commit is contained in:
2021-06-03 20:17:01 +03:00
parent baac5a7c17
commit 61518b4fb4
3 changed files with 96 additions and 29 deletions

View File

@@ -2,19 +2,28 @@
<div> <div>
<img id="logo" src="./assets/logo.png"> <img id="logo" src="./assets/logo.png">
<div class="pageSide" v-if="loggedin"> <div class="pageSide" v-if="loggedin">
<img :src="image" > <img id="meme" :src="image">
<MazBtn
class="maz-btn--mini"
@click="logout"
>
Logout
</MazBtn>
</div> </div>
<Login v-else id="login" @auth="auth" /> <Login v-else id="login" @auth="auth" />
</div> </div>
</template> </template>
<script> <script>
import axios from 'axios';
import Login from './components/Login.vue' import Login from './components/Login.vue'
import { MazBtn } from 'maz-ui';
export default { export default {
name: 'App', name: 'App',
components: { components: {
Login Login,
MazBtn
}, },
data() { data() {
return { return {
@@ -27,6 +36,11 @@ export default {
this.loggedin = true this.loggedin = true
this.image = image this.image = image
} }
},
logout() {
axios.post('http://127.0.0.1:3000/api/logout').then(() => {
this.loggedin = false
});
} }
} }
} }
@@ -37,13 +51,10 @@ body {
background-color: #343a40; background-color: #343a40;
} }
#app { body {
font-family: Avenir, Helvetica, Arial, sans-serif; font-family: Avenir, Helvetica, Arial, sans-serif;
-webkit-font-smoothing: antialiased; -webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale; -moz-osx-font-smoothing: grayscale;
text-align: center;
color: #2c3e50;
margin-top: 60px;
} }
#logo { #logo {
@@ -54,10 +65,21 @@ body {
border-radius: 50%; border-radius: 50%;
} }
#meme {
width: 100%;
margin-bottom: 3em;
}
.pageSide { .pageSide {
padding: 1.5rem; padding: 1.5rem;
background-color: #FFF; background-color: #FFF;
border-radius: .3rem; border-radius: .3rem;
text-align: center; text-align: center;
max-width: 600px;
margin: auto;
}
@media screen and (max-width: 600px) {
} }
</style> </style>

View File

@@ -26,6 +26,11 @@
<PassNBtns loginMethod="email" @flip="usePhone = !usePhone" @auth="auth" /> <PassNBtns loginMethod="email" @flip="usePhone = !usePhone" @auth="auth" />
</div> </div>
</transition> </transition>
<transition name="slide">
<div v-if="msg" class="msg" v-bind:key="msg">
{{msg}}
</div>
</transition>
</div> </div>
</template> </template>
@@ -43,6 +48,7 @@ export default {
}, },
data() { data() {
return { return {
msg: '',
usePhone: false, usePhone: false,
email: '', email: '',
phone: '', phone: '',
@@ -57,7 +63,8 @@ export default {
return 'primary' return 'primary'
} }
}, },
async auth(pass) { auth(pass, onload) {
if (onload || (pass && this.usePhone ? this.phone : this.email)) {
axios({ axios({
method: "post", method: "post",
url: "http://127.0.0.1:3000/api/login", url: "http://127.0.0.1:3000/api/login",
@@ -71,20 +78,40 @@ export default {
pass: pass pass: pass
} }
}).then((response) => { }).then((response) => {
this.msg = ''
var bytes = new Uint8Array(response.data); var bytes = new Uint8Array(response.data);
var binary = bytes.reduce((data, b) => data += String.fromCharCode(b), ''); var binary = bytes.reduce((data, b) => data += String.fromCharCode(b), '');
this.src = "data:image/jpeg;base64," + btoa(binary); this.src = "data:image/jpeg;base64," + btoa(binary);
this.$emit('auth', this.src) this.$emit('auth', this.src)
}).finally(() => {
if (!onload) {
this.msg = 'Invalid credentials'
}
}); });
} else {
this.msg = 'Please enter your credentials'
}
} }
}, },
mounted() { mounted() {
this.auth() this.auth('', true)
} }
} }
</script> </script>
<style scoped> <style scoped>
.msg {
position: relative;
padding: .8rem;
background-color: #FFF;
border-radius: .3rem;
text-align: center;
max-width: 150px;
margin: 3em auto 0 auto;
color: orangered;
z-index: -10;
}
.flip-enter-active { .flip-enter-active {
transition: all 0.4s ease; transition: all 0.4s ease;
} }
@@ -93,4 +120,12 @@ export default {
transform: perspective(1000px) rotateY(180deg); transform: perspective(1000px) rotateY(180deg);
opacity: 0; opacity: 0;
} }
.slide-enter-active {
transition: all 0.4s ease;
}
.slide-enter, .slide-leave {
transform: translateY(-100px);
}
</style> </style>

View File

@@ -2,13 +2,15 @@ const express = require('express')
const cookieSession = require('cookie-session') const cookieSession = require('cookie-session')
const app = express() const app = express()
const cors = require('cors') const cors = require('cors')
const https = require('https')
const fs = require('fs')
require('dotenv').config() require('dotenv').config()
app.use(cookieSession({ app.use(cookieSession({
name: 'session', name: 'session',
secret: process.env.SECRET, secret: process.env.SECRET,
maxAge: 24 * 60 * 60 * 1000, // 24 hours maxAge: 24 * 60 * 60 * 1000, // 24 hours
secure: false, secure: process.env.NODE_ENV === 'production',
sameSite: 'none' sameSite: 'none'
})) }))
@@ -41,4 +43,12 @@ app.post('/api/logout', (req, res) => {
} }
}) })
app.listen(process.env.PORT) if (process.env.NODE_ENV === 'production') {
https.createServer({
key: fs.readFileSync(process.env.SSL + '/privkey.pem'),
cert: fs.readFileSync(process.env.SSL + '/cert.pem')
}, app)
.listen(process.env.PORT, () => console.log('Prod server started on ' + process.env.PORT));
} else {
app.listen(process.env.PORT, () => console.log('Dev server started on ' + process.env.PORT));
}