Refatored UserPrecense functionality
This commit is contained in:
parent
9945b58fb1
commit
4928dd3a73
|
@ -7,7 +7,7 @@ import prisma from '../prisma'
|
||||||
import { pubsub, USER_PRESENCE_UPDATED } from '../pubsub'
|
import { pubsub, USER_PRESENCE_UPDATED } from '../pubsub'
|
||||||
|
|
||||||
const DEBOUNCE_TIME_MS = 10000
|
const DEBOUNCE_TIME_MS = 10000
|
||||||
const RECENT_THRESHOLD_IN_MINUTES = 5
|
const RECENT_THRESHOLD_IN_MINUTES = 3
|
||||||
|
|
||||||
let working = false
|
let working = false
|
||||||
|
|
||||||
|
|
|
@ -116,31 +116,33 @@ const Query = {
|
||||||
|
|
||||||
search = search.toLowerCase().trim()
|
search = search.toLowerCase().trim()
|
||||||
|
|
||||||
const userPresences = usersWithWifiDevices
|
const filteredUsers = search
|
||||||
.filter(
|
? usersWithWifiDevices.filter(
|
||||||
user =>
|
user =>
|
||||||
user.displayName.toLowerCase().includes(search) ||
|
user.displayName.toLowerCase().includes(search) ||
|
||||||
user.sAMAccountName.toLowerCase().includes(search) ||
|
user.sAMAccountName.toLowerCase().includes(search) ||
|
||||||
user.wifiDevices.some(
|
user.wifiDevices.some(
|
||||||
device =>
|
device =>
|
||||||
device.apName.toLowerCase().includes(search) ||
|
device.apName.toLowerCase().includes(search) ||
|
||||||
device.ip.startsWith(search)
|
device.ip.startsWith(search)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
.map(user => ({
|
: usersWithWifiDevices
|
||||||
user: {
|
|
||||||
id: user.id,
|
|
||||||
displayName: user.displayName,
|
|
||||||
thumbnailPhoto: user.thumbnailPhoto
|
|
||||||
},
|
|
||||||
wifiDevices: user.wifiDevices
|
|
||||||
}))
|
|
||||||
|
|
||||||
const sortedUserPresences = userPresences.sort((a, b) =>
|
const sortedUsers = filteredUsers.sort((a, b) =>
|
||||||
a.wifiDevices[0].lastSeen > b.wifiDevices[0].lastSeen ? -1 : 1
|
a.wifiDevices[0].lastSeen > b.wifiDevices[0].lastSeen ? -1 : 1
|
||||||
)
|
)
|
||||||
|
|
||||||
return sortedUserPresences.slice(0, 200)
|
return sortedUsers
|
||||||
|
.map(userPresence => ({
|
||||||
|
id: userPresence.id,
|
||||||
|
displayName: userPresence.displayName,
|
||||||
|
thumbnailPhoto: userPresence.thumbnailPhoto,
|
||||||
|
lastSeen: userPresence.wifiDevices[0].lastSeen,
|
||||||
|
status: userPresence.wifiDevices[0].status,
|
||||||
|
apName: userPresence.wifiDevices[0].apName
|
||||||
|
}))
|
||||||
|
.slice(0, 200)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
6
server/src/resolvers/UserPresence.js
Normal file
6
server/src/resolvers/UserPresence.js
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
const UserPresence = {
|
||||||
|
displayName: _ => (_.displayName ? _.displayName.capitalize() : ''),
|
||||||
|
lastSeen: _ => _.lastSeen?.toISOString()
|
||||||
|
}
|
||||||
|
|
||||||
|
export { UserPresence }
|
|
@ -1,9 +1,6 @@
|
||||||
const WifiDevice = {
|
const WifiDevice = {
|
||||||
lastSeen: _ => _.lastSeen?.toISOString(),
|
lastSeen: _ => _.lastSeen?.toISOString(),
|
||||||
firstSeen: _ => _.firstSeen?.toISOString(),
|
firstSeen: _ => _.firstSeen?.toISOString()
|
||||||
isOnline: _ => _.status == 'ONLINE',
|
|
||||||
isRecent: _ => _.status == 'RECENT',
|
|
||||||
isOffline: _ => _.status == 'OFFLINE'
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export { WifiDevice }
|
export { WifiDevice }
|
||||||
|
|
|
@ -3,6 +3,7 @@ import { Mutation } from './Mutation'
|
||||||
import { Subscription } from './Subscriptions'
|
import { Subscription } from './Subscriptions'
|
||||||
|
|
||||||
import { User } from './User'
|
import { User } from './User'
|
||||||
|
import { UserPresence } from './UserPresence'
|
||||||
import { Group } from './Group'
|
import { Group } from './Group'
|
||||||
import { ResetToken } from './ResetToken'
|
import { ResetToken } from './ResetToken'
|
||||||
import { WifiDevice } from './WifiDevice'
|
import { WifiDevice } from './WifiDevice'
|
||||||
|
@ -13,6 +14,7 @@ const resolvers = {
|
||||||
Mutation,
|
Mutation,
|
||||||
Subscription,
|
Subscription,
|
||||||
User,
|
User,
|
||||||
|
UserPresence,
|
||||||
Group,
|
Group,
|
||||||
ResetToken,
|
ResetToken,
|
||||||
WifiDevice,
|
WifiDevice,
|
||||||
|
|
|
@ -167,14 +167,15 @@ const typeDefs = gql`
|
||||||
uptime: String
|
uptime: String
|
||||||
apName: String
|
apName: String
|
||||||
status: Status
|
status: Status
|
||||||
isOnline: Boolean
|
|
||||||
isRecent: Boolean
|
|
||||||
isOffline: Boolean
|
|
||||||
}
|
}
|
||||||
|
|
||||||
type UserPresence {
|
type UserPresence {
|
||||||
user: User!
|
id: ID!
|
||||||
wifiDevices: [WifiDevice!]!
|
displayName: String!
|
||||||
|
thumbnailPhoto: String
|
||||||
|
lastSeen: String!
|
||||||
|
status: Status!
|
||||||
|
apName: String!
|
||||||
}
|
}
|
||||||
|
|
||||||
enum Status {
|
enum Status {
|
||||||
|
|
|
@ -1,139 +0,0 @@
|
||||||
<template>
|
|
||||||
<div v-if="!loading">
|
|
||||||
<transition-group
|
|
||||||
name="scale-transition"
|
|
||||||
tag="div"
|
|
||||||
class="layout row row--dense wrap"
|
|
||||||
mode="out-in"
|
|
||||||
>
|
|
||||||
<v-col
|
|
||||||
v-for="userPresence in userPresences"
|
|
||||||
:key="userPresence.user.id"
|
|
||||||
cols="12"
|
|
||||||
sm="6"
|
|
||||||
md="4"
|
|
||||||
lg="3"
|
|
||||||
>
|
|
||||||
<v-card
|
|
||||||
outlined
|
|
||||||
class="border-highlight light-shadow"
|
|
||||||
:class="{
|
|
||||||
online: userPresence.wifiDevices[0].isOnline,
|
|
||||||
recent: userPresence.wifiDevices[0].isRecent
|
|
||||||
}"
|
|
||||||
>
|
|
||||||
<v-list three-line>
|
|
||||||
<v-list-item>
|
|
||||||
<v-list-item-avatar size="52px" style="overflow: visible">
|
|
||||||
<v-badge
|
|
||||||
:color="
|
|
||||||
userPresence.wifiDevices.some(
|
|
||||||
wifiDevice => wifiDevice.isOnline
|
|
||||||
)
|
|
||||||
? 'green darken-1'
|
|
||||||
: 'grey darken-1'
|
|
||||||
"
|
|
||||||
bottom
|
|
||||||
offset-x="18px"
|
|
||||||
offset-y="18px"
|
|
||||||
>
|
|
||||||
<Avatar :src="userPresence.user.thumbnailPhoto" size="52px" />
|
|
||||||
</v-badge>
|
|
||||||
</v-list-item-avatar>
|
|
||||||
|
|
||||||
<v-list-item-content>
|
|
||||||
<v-list-item-title>
|
|
||||||
{{ userPresence.user.displayName }}
|
|
||||||
</v-list-item-title>
|
|
||||||
|
|
||||||
<template v-if="userPresence.wifiDevices[0].isOnline">
|
|
||||||
<v-list-item-subtitle>
|
|
||||||
<span class="font-weight-medium">On-line</span>
|
|
||||||
</v-list-item-subtitle>
|
|
||||||
<v-list-item-subtitle>
|
|
||||||
Próximo ao AP
|
|
||||||
<span class="font-weight-medium">
|
|
||||||
{{ userPresence.wifiDevices[0].apName }}
|
|
||||||
</span>
|
|
||||||
</v-list-item-subtitle>
|
|
||||||
</template>
|
|
||||||
|
|
||||||
<template v-if="userPresence.wifiDevices[0].isRecent">
|
|
||||||
<v-list-item-subtitle>
|
|
||||||
<span class="font-weight-medium">Visto recentemente</span>
|
|
||||||
</v-list-item-subtitle>
|
|
||||||
<v-list-item-subtitle>
|
|
||||||
Próximo ao AP
|
|
||||||
<span class="font-weight-medium">
|
|
||||||
{{ userPresence.wifiDevices[0].apName }}
|
|
||||||
</span>
|
|
||||||
</v-list-item-subtitle>
|
|
||||||
</template>
|
|
||||||
|
|
||||||
<template v-if="userPresence.wifiDevices[0].isOffline">
|
|
||||||
<v-list-item-subtitle>
|
|
||||||
<span class="font-weight-medium">Off-line</span>
|
|
||||||
</v-list-item-subtitle>
|
|
||||||
<v-list-item-subtitle>
|
|
||||||
<span class="font-weight-medium">
|
|
||||||
Visto {{ userPresence.wifiDevices[0].lastSeen | from }}
|
|
||||||
</span>
|
|
||||||
</v-list-item-subtitle>
|
|
||||||
</template>
|
|
||||||
</v-list-item-content>
|
|
||||||
</v-list-item>
|
|
||||||
</v-list>
|
|
||||||
</v-card>
|
|
||||||
</v-col>
|
|
||||||
</transition-group>
|
|
||||||
</div>
|
|
||||||
<div v-else>
|
|
||||||
<div class="layout row row--dense wrap">
|
|
||||||
<v-col v-for="i in 12" :key="i" cols="12" sm="6" md="4" lg="3">
|
|
||||||
<v-card outlined class="border-highlight light-shadow">
|
|
||||||
<v-list three-line>
|
|
||||||
<v-list-item>
|
|
||||||
<v-list-item-avatar>
|
|
||||||
<v-skeleton-loader type="avatar" />
|
|
||||||
</v-list-item-avatar>
|
|
||||||
<v-list-item-content>
|
|
||||||
<v-skeleton-loader type="paragraph" style="max-width: 300px" />
|
|
||||||
</v-list-item-content>
|
|
||||||
</v-list-item>
|
|
||||||
</v-list>
|
|
||||||
</v-card>
|
|
||||||
</v-col>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</template>
|
|
||||||
|
|
||||||
<script>
|
|
||||||
import Avatar from './Avatar'
|
|
||||||
|
|
||||||
export default {
|
|
||||||
name: 'UserPresenceStatusList',
|
|
||||||
components: { Avatar },
|
|
||||||
props: {
|
|
||||||
userPresences: {
|
|
||||||
type: Array,
|
|
||||||
default: () => []
|
|
||||||
},
|
|
||||||
loading: {
|
|
||||||
type: Boolean,
|
|
||||||
default: false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<style scoped lang="scss">
|
|
||||||
.border-highlight {
|
|
||||||
border-left: 4px solid grey;
|
|
||||||
}
|
|
||||||
.online {
|
|
||||||
border-left-color: #117d4c;
|
|
||||||
}
|
|
||||||
.recent {
|
|
||||||
border-left-color: #ffc107;
|
|
||||||
}
|
|
||||||
</style>
|
|
|
@ -3,7 +3,9 @@
|
||||||
<v-expansion-panel-header>
|
<v-expansion-panel-header>
|
||||||
<v-icon
|
<v-icon
|
||||||
class="shrink mr-2"
|
class="shrink mr-2"
|
||||||
:color="wifiDevice.isOnline ? 'green darken-1' : 'grey lighten-1'"
|
:color="
|
||||||
|
wifiDevice.status == 'ONLINE' ? 'green darken-1' : 'grey lighten-1'
|
||||||
|
"
|
||||||
>
|
>
|
||||||
mdi-cellphone-link
|
mdi-cellphone-link
|
||||||
</v-icon>
|
</v-icon>
|
||||||
|
@ -13,7 +15,7 @@
|
||||||
</v-expansion-panel-header>
|
</v-expansion-panel-header>
|
||||||
<v-expansion-panel-content>
|
<v-expansion-panel-content>
|
||||||
<v-list dense>
|
<v-list dense>
|
||||||
<v-list-item v-if="wifiDevice.isOnline">
|
<v-list-item v-if="wifiDevice.status == 'ONLINE'">
|
||||||
<v-list-item-action>
|
<v-list-item-action>
|
||||||
<v-icon color="green darken-1">mdi-wifi</v-icon>
|
<v-icon color="green darken-1">mdi-wifi</v-icon>
|
||||||
</v-list-item-action>
|
</v-list-item-action>
|
||||||
|
|
|
@ -42,8 +42,8 @@ export default {
|
||||||
lastSeen
|
lastSeen
|
||||||
mac
|
mac
|
||||||
oui
|
oui
|
||||||
isOnline
|
|
||||||
uptime
|
uptime
|
||||||
|
status
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -51,12 +51,113 @@
|
||||||
</v-scale-transition>
|
</v-scale-transition>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<UserPresenceStatusList
|
<transition-group
|
||||||
:user-presences="pagedUserPresences"
|
v-if="
|
||||||
:loading="
|
!$apollo.queries.userPresence.loading && pagedUserPresences.length
|
||||||
$apollo.queries.userPresence.loading && !pagedUserPresences.length
|
|
||||||
"
|
"
|
||||||
/>
|
name="scale-transition"
|
||||||
|
tag="div"
|
||||||
|
class="layout row row--dense wrap"
|
||||||
|
mode="out-in"
|
||||||
|
>
|
||||||
|
<v-col
|
||||||
|
v-for="userPresence in pagedUserPresences"
|
||||||
|
:key="userPresence.id"
|
||||||
|
cols="12"
|
||||||
|
sm="6"
|
||||||
|
md="4"
|
||||||
|
lg="3"
|
||||||
|
>
|
||||||
|
<v-card
|
||||||
|
outlined
|
||||||
|
class="border-highlight light-shadow"
|
||||||
|
:class="{
|
||||||
|
online: userPresence.status == 'ONLINE',
|
||||||
|
recent: userPresence.status == 'RECENT'
|
||||||
|
}"
|
||||||
|
>
|
||||||
|
<v-list three-line>
|
||||||
|
<v-list-item>
|
||||||
|
<v-list-item-avatar size="52px" style="overflow: visible">
|
||||||
|
<v-badge
|
||||||
|
:color="color(userPresence.status)"
|
||||||
|
bottom
|
||||||
|
offset-x="18px"
|
||||||
|
offset-y="18px"
|
||||||
|
>
|
||||||
|
<Avatar :src="userPresence.thumbnailPhoto" size="52px" />
|
||||||
|
</v-badge>
|
||||||
|
</v-list-item-avatar>
|
||||||
|
|
||||||
|
<v-list-item-content>
|
||||||
|
<v-list-item-title>
|
||||||
|
{{ userPresence.displayName }}
|
||||||
|
</v-list-item-title>
|
||||||
|
|
||||||
|
<template v-if="userPresence.status == 'ONLINE'">
|
||||||
|
<v-list-item-subtitle>
|
||||||
|
<span class="font-weight-medium">On-line</span>
|
||||||
|
</v-list-item-subtitle>
|
||||||
|
<v-list-item-subtitle>
|
||||||
|
Próximo ao AP
|
||||||
|
<span class="font-weight-medium">
|
||||||
|
{{ userPresence.apName }}
|
||||||
|
</span>
|
||||||
|
</v-list-item-subtitle>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<template v-if="userPresence.status == 'RECENT'">
|
||||||
|
<v-list-item-subtitle>
|
||||||
|
<span class="font-weight-medium">Visto recentemente</span>
|
||||||
|
</v-list-item-subtitle>
|
||||||
|
<v-list-item-subtitle>
|
||||||
|
Próximo ao AP
|
||||||
|
<span class="font-weight-medium">
|
||||||
|
{{ userPresence.apName }}
|
||||||
|
</span>
|
||||||
|
</v-list-item-subtitle>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<template v-if="userPresence.status == 'OFFLINE'">
|
||||||
|
<v-list-item-subtitle>
|
||||||
|
<span class="font-weight-medium">Off-line</span>
|
||||||
|
</v-list-item-subtitle>
|
||||||
|
<v-list-item-subtitle>
|
||||||
|
<span class="font-weight-medium">
|
||||||
|
Visto
|
||||||
|
{{ userPresence.lastSeen | from }}
|
||||||
|
</span>
|
||||||
|
</v-list-item-subtitle>
|
||||||
|
</template>
|
||||||
|
</v-list-item-content>
|
||||||
|
</v-list-item>
|
||||||
|
</v-list>
|
||||||
|
</v-card>
|
||||||
|
</v-col>
|
||||||
|
</transition-group>
|
||||||
|
|
||||||
|
<div v-else>
|
||||||
|
<div class="layout row row--dense wrap">
|
||||||
|
<v-col v-for="i in 12" :key="i" cols="12" sm="6" md="4" lg="3">
|
||||||
|
<v-card outlined class="border-highlight light-shadow">
|
||||||
|
<v-list three-line>
|
||||||
|
<v-list-item>
|
||||||
|
<v-list-item-avatar>
|
||||||
|
<v-skeleton-loader type="avatar" />
|
||||||
|
</v-list-item-avatar>
|
||||||
|
<v-list-item-content>
|
||||||
|
<v-skeleton-loader
|
||||||
|
type="paragraph"
|
||||||
|
style="max-width: 300px"
|
||||||
|
/>
|
||||||
|
</v-list-item-content>
|
||||||
|
</v-list-item>
|
||||||
|
</v-list>
|
||||||
|
</v-card>
|
||||||
|
</v-col>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<v-alert
|
<v-alert
|
||||||
v-if="!pagedUserPresences.length && search"
|
v-if="!pagedUserPresences.length && search"
|
||||||
icon="mdi-account-search"
|
icon="mdi-account-search"
|
||||||
|
@ -124,11 +225,11 @@
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
import gql from 'graphql-tag'
|
import gql from 'graphql-tag'
|
||||||
import UserPresenceStatusList from '../components/UserPresenceStatusList'
|
import Avatar from '../components/Avatar'
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
name: 'UserPresence',
|
name: 'UserPresence',
|
||||||
components: { UserPresenceStatusList },
|
components: { Avatar },
|
||||||
data: () => {
|
data: () => {
|
||||||
const pageSize = 12
|
const pageSize = 12
|
||||||
return {
|
return {
|
||||||
|
@ -143,20 +244,12 @@ export default {
|
||||||
query: gql`
|
query: gql`
|
||||||
query($search: String = "") {
|
query($search: String = "") {
|
||||||
userPresence(search: $search) {
|
userPresence(search: $search) {
|
||||||
user {
|
id
|
||||||
id
|
displayName
|
||||||
displayName
|
thumbnailPhoto
|
||||||
thumbnailPhoto
|
lastSeen
|
||||||
}
|
status
|
||||||
wifiDevices {
|
apName
|
||||||
apName
|
|
||||||
id
|
|
||||||
lastSeen
|
|
||||||
isOnline
|
|
||||||
isRecent
|
|
||||||
isOffline
|
|
||||||
controller
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
`,
|
`,
|
||||||
|
@ -194,8 +287,27 @@ export default {
|
||||||
pagedUserPresences() {
|
pagedUserPresences() {
|
||||||
return this.userPresence?.slice(0, this.resultSize) || []
|
return this.userPresence?.slice(0, this.resultSize) || []
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
color(status) {
|
||||||
|
return {
|
||||||
|
ONLINE: 'green darken-2',
|
||||||
|
RECENT: 'orange darken-1',
|
||||||
|
OFFLINE: 'grey darken-1'
|
||||||
|
}[status]
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style scoped></style>
|
<style scoped lang="scss">
|
||||||
|
.border-highlight {
|
||||||
|
border-left: 4px solid grey;
|
||||||
|
}
|
||||||
|
.online {
|
||||||
|
border-left-color: green;
|
||||||
|
}
|
||||||
|
.recent {
|
||||||
|
border-left-color: #ffc107;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
|
|
@ -33,7 +33,8 @@
|
||||||
<div v-if="wifiDevices" class="text-center my-4">
|
<div v-if="wifiDevices" class="text-center my-4">
|
||||||
<v-chip color="primary" class="mr-1" dark>
|
<v-chip color="primary" class="mr-1" dark>
|
||||||
{{
|
{{
|
||||||
wifiDevices && wifiDevices.filter(device => device.isOnline).length
|
wifiDevices &&
|
||||||
|
wifiDevices.filter(device => device.status == 'ONLINE').length
|
||||||
}}
|
}}
|
||||||
</v-chip>
|
</v-chip>
|
||||||
online de
|
online de
|
||||||
|
@ -56,7 +57,7 @@
|
||||||
<v-row dense align-content="center" no-gutters>
|
<v-row dense align-content="center" no-gutters>
|
||||||
<v-col class="shrink" align-self="center">
|
<v-col class="shrink" align-self="center">
|
||||||
<v-badge
|
<v-badge
|
||||||
:color="device.isOnline ? 'green' : 'grey'"
|
:color="device.status == 'ONLINE' ? 'green' : 'grey'"
|
||||||
left
|
left
|
||||||
offset-y="16"
|
offset-y="16"
|
||||||
dot
|
dot
|
||||||
|
@ -84,7 +85,7 @@
|
||||||
</v-expansion-panel-header>
|
</v-expansion-panel-header>
|
||||||
<v-expansion-panel-content>
|
<v-expansion-panel-content>
|
||||||
<v-list dense>
|
<v-list dense>
|
||||||
<v-list-item v-if="device.isOnline">
|
<v-list-item v-if="device.status == 'ONLINE'">
|
||||||
<v-list-item-action>
|
<v-list-item-action>
|
||||||
<v-icon color="green darken-1">mdi-wifi</v-icon>
|
<v-icon color="green darken-1">mdi-wifi</v-icon>
|
||||||
</v-list-item-action>
|
</v-list-item-action>
|
||||||
|
@ -234,7 +235,7 @@ export default {
|
||||||
ip
|
ip
|
||||||
uptime
|
uptime
|
||||||
apName
|
apName
|
||||||
isOnline
|
status
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
`
|
`
|
||||||
|
|
|
@ -60,7 +60,7 @@
|
||||||
offset-y="10"
|
offset-y="10"
|
||||||
:content="
|
:content="
|
||||||
user.wifiDevices
|
user.wifiDevices
|
||||||
.filter(wifiDevice => !wifiDevice.isOnline)
|
.filter(wifiDevice => !wifiDevice.status == 'ONLINE')
|
||||||
.length.toString()
|
.length.toString()
|
||||||
"
|
"
|
||||||
>
|
>
|
||||||
|
@ -70,7 +70,7 @@
|
||||||
offset-y="10"
|
offset-y="10"
|
||||||
:content="
|
:content="
|
||||||
user.wifiDevices
|
user.wifiDevices
|
||||||
.filter(wifiDevice => wifiDevice.isOnline)
|
.filter(wifiDevice => wifiDevice.status == 'ONLINE')
|
||||||
.length.toString()
|
.length.toString()
|
||||||
"
|
"
|
||||||
>
|
>
|
||||||
|
@ -87,7 +87,10 @@
|
||||||
>
|
>
|
||||||
<v-expansion-panel-header>
|
<v-expansion-panel-header>
|
||||||
<div>
|
<div>
|
||||||
<v-icon left :color="device.isOnline ? 'green' : ''">
|
<v-icon
|
||||||
|
left
|
||||||
|
:color="device.status == 'ONLINE' ? 'green' : ''"
|
||||||
|
>
|
||||||
mdi-cellphone-wireless
|
mdi-cellphone-wireless
|
||||||
</v-icon>
|
</v-icon>
|
||||||
{{ device.hostname || device.mac }} {{ device.oui }}
|
{{ device.hostname || device.mac }} {{ device.oui }}
|
||||||
|
@ -95,7 +98,7 @@
|
||||||
</v-expansion-panel-header>
|
</v-expansion-panel-header>
|
||||||
<v-expansion-panel-content>
|
<v-expansion-panel-content>
|
||||||
<v-list dense>
|
<v-list dense>
|
||||||
<v-list-item v-if="device.isOnline">
|
<v-list-item v-if="device.status == 'ONLINE'">
|
||||||
<v-list-item-action>
|
<v-list-item-action>
|
||||||
<v-icon color="green darken-1">mdi-wifi</v-icon>
|
<v-icon color="green darken-1">mdi-wifi</v-icon>
|
||||||
</v-list-item-action>
|
</v-list-item-action>
|
||||||
|
@ -214,7 +217,7 @@ export default {
|
||||||
return this.wifiUsers?.map(user => ({
|
return this.wifiUsers?.map(user => ({
|
||||||
...user,
|
...user,
|
||||||
ips: user.wifiDevices.reduce((ips, device) => ` ${device.ip}`, ''),
|
ips: user.wifiDevices.reduce((ips, device) => ` ${device.ip}`, ''),
|
||||||
wifiDevices: user.wifiDevices.sort(a => (a.isOnline ? -1 : 1))
|
wifiDevices: user.wifiDevices.sort(a => (a.status == 'ONLINE' ? -1 : 1))
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -234,7 +237,7 @@ export default {
|
||||||
hostname
|
hostname
|
||||||
firstSeen
|
firstSeen
|
||||||
lastSeen
|
lastSeen
|
||||||
isOnline
|
status
|
||||||
apName
|
apName
|
||||||
essid
|
essid
|
||||||
ip
|
ip
|
||||||
|
|
Loading…
Reference in New Issue
Block a user