dynamic loaded chat and PWA

chatInformations
adb 4 years ago
parent fd4fff2a78
commit 451b30c3f2

@ -27,7 +27,7 @@ wss.on('connection', (ws, req) => {
console.log(`${req.socket.remoteAddress} connected`) console.log(`${req.socket.remoteAddress} connected`)
ws.on('message', msgJSON => { ws.on('message', msgJSON => {
let msg = JSON.parse(msgJSON) let msg = JSON.parse(msgJSON)
console.log(`${req.socket.remoteAddress} => ${msgJSON}`) console.log(`${req.socket.remoteAddress} (${thisuser}) => ${msgJSON}`)
if (msg.type === 'message') if (msg.type === 'message')
if (thisuser === ""){ if (thisuser === ""){
ws.send(JSON.stringify({type: "error", content: "please login before writing"})) ws.send(JSON.stringify({type: "error", content: "please login before writing"}))
@ -37,23 +37,26 @@ wss.on('connection', (ws, req) => {
else{ else{
msg.content.user = thisuser msg.content.user = thisuser
msg.content.text = msg.content.text.replace(/</g, "&lt").replace(/>/g, "&gt").replace(/\n/g, "<br>") msg.content.text = msg.content.text.replace(/</g, "&lt").replace(/>/g, "&gt").replace(/\n/g, "<br>")
wss.clients.forEach(client => { wss.clients.forEach(client => client.send(JSON.stringify(msg)))
if (client !== ws) client.send(JSON.stringify(msg))})
} }
else if (msg.type === 'login' && msg.content.user !== ""){ else if (msg.type === 'login' && msg.content.user !== ""){
if (msg.content.user >= 20) ws.send(JSON.stringify({type: "error", content: "username is too long"})) if (msg.content.user.length >= 20) ws.send(JSON.stringify({type: "error", content: "username is too long"}))
else if (function(){ else if (msg.content.user === "you" || user.indexOf(msg.content.user) !== -1)
for (let i = 0; i < user.length; i++) if (user[i] === msg.content.user) return true ws.send(JSON.stringify({type: "error", content: "username already exist"}))
return false
}() === true) ws.send(JSON.stringify({type: "error", content: "username already exist"}))
else{ else{
thisuser = msg.content.user thisuser = msg.content.user
user.push(msg.content.user) user.push(msg.content.user)
ws.send('{"type":"route","path":"/chat"}') ws.send('{"type":"route","path":"/chat"}')
ws.send(JSON.stringify({type: "info", username: thisuser}))
wss.clients.forEach(client => wss.clients.forEach(client =>
client.send(JSON.stringify({type: "room", name: "open chat", user: user}))) client.send(JSON.stringify({type: "room", name: "open chat", user: user})))
} }
} }
}) })
ws.on('close', () => {
user.splice(user.indexOf(thisuser), 1);
console.log(`${req.socket.remoteAddress} (${thisuser}) closed`)
})
ws.send(JSON.stringify({type: "info", time: Date.now(), content: "connected"})) ws.send(JSON.stringify({type: "info", time: Date.now(), content: "connected"}))
}) })

@ -3,6 +3,10 @@
<head> <head>
<meta charset="utf-8" /> <meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge"/> <meta http-equiv="X-UA-Compatible" content="IE=edge"/>
<!-- PWA support -->
<link rel="manifest" href="./manifest.json"/>
<meta name="theme-color" content="#2F3BA2"/>
<meta name="description" content="open chat"/>
<meta name='viewport' content='width=device-width, initial-scale=1, maximum-scale=1, user-scalable=0'/> <meta name='viewport' content='width=device-width, initial-scale=1, maximum-scale=1, user-scalable=0'/>
<link rel="icon" href="<%= BASE_URL %>favicon.ico"/> <link rel="icon" href="<%= BASE_URL %>favicon.ico"/>
<title><%= htmlWebpackPlugin.options.title %></title> <title><%= htmlWebpackPlugin.options.title %></title>

@ -0,0 +1,9 @@
{
"name": "open chat",
"short_name": "open chat",
"start_url": "/",
"display": "standalone",
"background_color": "#14181b",
"theme_color": "#00BCD4",
"orientation": "portrait-primary"
}

@ -32,5 +32,6 @@ export default {
background-color: #42b983; background-color: #42b983;
border-radius: 1rem 1rem 1rem 0; border-radius: 1rem 1rem 1rem 0;
text-align: left; text-align: left;
word-break: break-word;
} }
</style> </style>

@ -22,16 +22,6 @@ export default {
if (this.msg.content.text !== "") { if (this.msg.content.text !== "") {
this.msg.time = Date.now() this.msg.time = Date.now()
main.methods.sendWebSocket(this.msg) main.methods.sendWebSocket(this.msg)
//just for now, ik it's dirty
document.getElementById('messages').innerHTML +=
`<div class="messageContainer" data-v-032da2b2="">
<div class="message" data-v-032da2b2="">
${this.msg.content.text
.replace(/</g, "&lt")
.replace(/>/g, "&gt")
.replace(/\n/g, "<br>")}
</div>
</div>`;
this.msg.content.text = "" this.msg.content.text = ""
document.getElementById("messagesContainer").style.height = "calc(100% - 7rem)" document.getElementById("messagesContainer").style.height = "calc(100% - 7rem)"
document.getElementById("newMessageInput").style.height = "1.25rem" document.getElementById("newMessageInput").style.height = "1.25rem"
@ -54,9 +44,11 @@ export default {
type: "message", type: "message",
time: Date.now(), time: Date.now(),
content: { content: {
user: "you",
text: "" text: ""
} }
} },
chatroom: main.data().chatroom
} }
} }
} }

@ -6,8 +6,8 @@
</router-link> </router-link>
<icon class="smallIcon" id="picTop" ic="./sym/supervisor_account-24px.svg" /> <icon class="smallIcon" id="picTop" ic="./sym/supervisor_account-24px.svg" />
<div id="container"> <div id="container">
<div id="chatName">{{roomInfo.name}}</div> <div id="chatName">{{chatroom.name}}</div>
<div id="users">{{roomInfo.user.length}} members</div> <div id="users">{{chatroom.user.length}} members</div>
</div> </div>
<icon class="smallIcon" id="icon-menu" ic="./sym/menu-24px.svg" /> <icon class="smallIcon" id="icon-menu" ic="./sym/menu-24px.svg" />
</div> </div>
@ -15,6 +15,7 @@
</template> </template>
<script> <script>
import icon from '@/components/icon.vue'; import icon from '@/components/icon.vue';
import main from '@/main.js';
export default { export default {
name: "topBanner", name: "topBanner",
@ -23,10 +24,7 @@ export default {
}, },
data(){ data(){
return { return {
roomInfo: { chatroom: main.data().chatroom
name: "open chat",
user: []
}
} }
} }
} }
@ -37,7 +35,7 @@ export default {
width: 100%; width: 100%;
height: 3rem; height: 3rem;
background-color: #1d1d1d; background-color: #1d1d1d;
box-shadow: 0 3px 10px #111; box-shadow: 0 0px 5px #111;
} }
.smallIcon{ .smallIcon{
top: 0.25rem; top: 0.25rem;

@ -27,12 +27,12 @@ const router = new VueRouter({
] ]
}) })
new Vue({ let chatroom = {
el: '#app', name: "open chat",
router, user: [],
template: '<App/>', username: "you",
components: {App} messages: []
}).$mount('#app') };
export default { export default {
mounted() { mounted() {
@ -40,10 +40,7 @@ export default {
}, },
data(){ data(){
return { return {
roomInfo: { chatroom: chatroom
name: "open chat",
user: []
}
} }
}, },
methods: { methods: {
@ -63,9 +60,22 @@ export default {
} }
} }
new Vue({
el: '#app',
router,
template: '<App/>',
components: {App},
data(){
return {
chatroom: chatroom
}
}
}).$mount('#app')
const wsurl = 'ws://127.0.0.1:8090' const wsurl = 'ws://127.0.0.1:8090'
const socket = new WebSocket(wsurl) //const wsurl = 'wss://chat.adb.sh:8080'
const socket = new WebSocket(wsurl)
function element(id){ return document.getElementById(id)} function element(id){ return document.getElementById(id)}
socket.onopen = () => { socket.onopen = () => {
@ -86,16 +96,11 @@ socket.onmessage = (e) => {
if (msg.type === 'error') show_error(msg.content) if (msg.type === 'error') show_error(msg.content)
else if (msg.type === 'route') router.push({path: msg.path}) else if (msg.type === 'route') router.push({path: msg.path})
else if (msg.type === 'room'){ else if (msg.type === 'room'){
this.roomInfo.user = msg.user chatroom.user = msg.user
} }
else if (msg.type === "info") chatroom.username = msg.username
else if (msg.type === 'message'){ else if (msg.type === 'message'){
//just for now, ik it's dirty chatroom.messages.push(msg)
element('messages').innerHTML +=
`<div class="messageContainer" data-v-a1576e28="">
<div class="message" data-v-a1576e28="">
${msg.content.text}
</div>
</div>`;
let msgContainer = document.getElementById("messagesContainer") let msgContainer = document.getElementById("messagesContainer")
if (msgContainer.scrollHeight < msgContainer.scrollTop + 1000) msgContainer.scrollTo(0, msgContainer.scrollHeight) if (msgContainer.scrollHeight < msgContainer.scrollTop + 1000) msgContainer.scrollTo(0, msgContainer.scrollHeight)
} }

@ -2,9 +2,15 @@
<div> <div>
<div ref="msgContainer" id="messagesContainer" class="messagesContainer"> <div ref="msgContainer" id="messagesContainer" class="messagesContainer">
<div id="messages" class="messages"> <div id="messages" class="messages">
<p style="margin-left: 1rem; font-style: italic;">You entered the chat</p> <p style="text-align: center; font-style: italic;">you entered the chat</p>
<message style="display: none;" /> <div v-for="(message, i) in chatroom.messages" :key="message.time">
<messageReceive style="display: none;" /> <div v-if="message.content.user !== chatroom.username && function(){
return i===0 || chatroom.messages[i-1].content.user!==message.content.user;}()"
style="margin-left: 2rem; margin-top: 1rem">{{message.content.user}}
</div>
<messageReceive v-if="message.content.user !== chatroom.username" :msg=message.content.text />
<message v-if="message.content.user === chatroom.username" :msg=message.content.text />
</div>
</div> </div>
</div> </div>
<newMessage /> <newMessage />
@ -16,7 +22,8 @@
import message from '@/components/message.vue'; import message from '@/components/message.vue';
import messageReceive from '@/components/messageReceive.vue'; import messageReceive from '@/components/messageReceive.vue';
import newMessage from '@/components/newMessage.vue'; import newMessage from '@/components/newMessage.vue';
import topBanner from "@/components/topBanner"; import topBanner from '@/components/topBanner.vue';
import main from '@/main.js';
export default { export default {
name: 'chat', name: 'chat',
@ -25,6 +32,11 @@ export default {
messageReceive, messageReceive,
newMessage, newMessage,
topBanner topBanner
},
data(){
return {
chatroom: main.data().chatroom
}
} }
} }
</script> </script>

Loading…
Cancel
Save