Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 11 additions & 8 deletions frontend/src/pages/team/Home/components/DashboardSection.vue
Original file line number Diff line number Diff line change
@@ -1,14 +1,17 @@
<template>
<div class="ff-box" :data-el="`dashboard-section-${type}`">
<div class="ff-box-header">
<span v-if="$slots.icon" class="icon">
<slot name="icon" />
</span>
<h3 v-if="title" class="ff-box-title">
<span>
{{ title }}
<div class="flex items-center gap-2">
<span v-if="$slots.icon" class="icon">
<slot name="icon" />
</span>
</h3>
<h3 v-if="title" class="ff-box-title">
<span>
{{ title }}
</span>
</h3>
</div>
<slot name="actions" />
</div>
<div class="ff-box-content flex flex-col flex-1 overflow-auto">
<slot />
Expand Down Expand Up @@ -44,8 +47,8 @@ export default {

.ff-box-header {
display: flex;
justify-content: space-between;
align-items: center;
gap: 10px;
margin-bottom: 10px;

.ff-box-title {
Expand Down
83 changes: 76 additions & 7 deletions frontend/src/pages/team/Home/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,21 @@
/>
</div>

<template #actions>
<ff-button
v-ff-tooltip:left="!hasPermission('project:create') && 'Your role does not allow creating new instances. Contact a team admin to change your role.'"
data-action="create-project"
kind="secondary"
:to="{name: 'CreateInstance'}"
:disabled="!hasPermission('project:create')"
>
<template #icon-left>
<PlusIcon class="ff-icon" />
</template>
Add Instance
</ff-button>
</template>

<RecentlyModifiedInstances :total-instances="totalInstances" @delete-instance="openDeleteInstanceForm" />
</DashboardSection>

Expand All @@ -57,6 +72,21 @@
/>
</div>

<template #actions>
<ff-button
v-ff-tooltip:left="!hasPermission('device:create') && 'Your role does not allow creating new remote instances. Contact a team admin to change your role.'"
data-action="create-project"
kind="secondary"
:disabled="!hasPermission('device:create')"
@click="showCreateDeviceDialog"
>
<template #icon-left>
<PlusIcon class="ff-icon" />
</template>
Add Instance
</ff-button>
</template>

<RecentlyModifiedDevices :total-devices="totalDevices" />
</DashboardSection>
</section>
Expand All @@ -78,21 +108,41 @@
</transition>
</div>
</ff-page>
<TeamDeviceCreateDialog
v-if="team && modals.addDevice"
ref="teamDeviceCreateDialog"
:team="team"
:teamDeviceCount="totalDevices"
@device-created="deviceCreated"
@close="modals.addDevice = false"
>
<template #description>
<p v-if="!featuresCheck?.isHostedInstancesEnabledForTeam && tours.firstDevice">
Describe your new Remote Instance here, e.g. "Raspberry Pi", "Allen-Bradley PLC", etc.
</p>
<p v-else>
Remote Instances are managed using the <a href="https://flowfuse.com/docs/user/devices/" target="_blank">FlowFuse Device Agent</a>. The agent will need to be setup on the hardware where you want your Remote Instance to run.
</p>
</template>
</TeamDeviceCreateDialog>
<DeviceCredentialsDialog ref="deviceCredentialsDialog" />
</template>

<script>
import { ChipIcon, DatabaseIcon } from '@heroicons/vue/outline'
import { ChipIcon, DatabaseIcon, PlusIcon } from '@heroicons/vue/outline'

import { mapGetters } from 'vuex'
import { mapGetters, mapState } from 'vuex'

import TeamAPI from '../../../api/team.js'
import AuditLog from '../../../components/audit-log/AuditLog.vue'

import ProjectsIcon from '../../../components/icons/Projects.js'
import InstanceStat from '../../../components/tiles/InstanceCounter.vue'
import { useInstanceStates } from '../../../composables/InstanceStates.js'
import usePermissions from '../../../composables/Permissions.js'
import Alerts from '../../../services/alerts.js'
import ConfirmInstanceDeleteDialog from '../../instance/Settings/dialogs/ConfirmInstanceDeleteDialog.vue'
import DeviceCredentialsDialog from '../Devices/dialogs/DeviceCredentialsDialog.vue'
import TeamDeviceCreateDialog from '../Devices/dialogs/TeamDeviceCreateDialog.vue'

import DashboardSection from './components/DashboardSection.vue'
import RecentlyModifiedDevices from './components/RecentlyModifiedDevices.vue'
Expand All @@ -101,6 +151,7 @@ import RecentlyModifiedInstances from './components/RecentlyModifiedInstances.vu
export default {
name: 'TeamHome',
components: {
DeviceCredentialsDialog,
ConfirmInstanceDeleteDialog,
InstanceStat,
RecentlyModifiedInstances,
Expand All @@ -109,14 +160,18 @@ export default {
ChipIcon,
ProjectsIcon,
DatabaseIcon,
RecentlyModifiedDevices
PlusIcon,
RecentlyModifiedDevices,
TeamDeviceCreateDialog
},
setup () {
const { groupBySimplifiedStates, statesMap: instanceStatesMap } = useInstanceStates()

const { hasPermission } = usePermissions()
return {
groupBySimplifiedStates,
instanceStatesMap
instanceStatesMap,
hasPermission
}
},
data () {
Expand All @@ -127,11 +182,15 @@ export default {
instanceStateCounts: {},
deviceStateCounts: {},
isDeleteInstanceDialogOpen: false,
devices: []
devices: [],
modals: {
addDevice: false
}
}
},
computed: {
...mapGetters('account', ['team', 'pendingTeamChange']),
...mapState('ux/tours', ['tours']),
...mapGetters('account', ['team', 'pendingTeamChange', 'featuresCheck']),
instanceStats () {
return this.groupBySimplifiedStates(this.instanceStateCounts)
},
Expand Down Expand Up @@ -205,6 +264,16 @@ export default {
this.isDeleteInstanceDialogOpen = false
// get the new number of instances which triggers a recently modified instances list refresh
this.getInstanceStateCounts()
},
showCreateDeviceDialog () {
this.modals.addDevice = true
this.$nextTick(() => {
this.$refs.teamDeviceCreateDialog.show(null, null, null, true)
})
},
deviceCreated (device) {
// navigate to the new Remote Instance
this.$refs.deviceCredentialsDialog.show(device)
}
}
}
Expand Down
Loading