[9/10/1400] All APIs since 7/10/1400 are done
This commit is contained in:
parent
f34605b9a2
commit
732054d95b
File diff suppressed because it is too large
Load Diff
|
|
@ -50,6 +50,7 @@
|
|||
"vue-good-table": "2.21.0",
|
||||
"vue-i18n": "8.22.2",
|
||||
"vue-jstree": "^2.1.6",
|
||||
"vue-number-animation": "^1.1.1",
|
||||
"vue-perfect-scrollbar": "0.2.1",
|
||||
"vue-persian-datetime-picker": "^2.10.1",
|
||||
"vue-prism-component": "1.1.1",
|
||||
|
|
|
|||
|
|
@ -13,9 +13,10 @@ Example:
|
|||
<b-button v-b-modal:modal-charge-user>Charge User</b-button>
|
||||
|
||||
Props:
|
||||
Name Type Description
|
||||
------- ------- -------------------------------------------------------------
|
||||
user-id Number the id of the user you want to charge his/her account
|
||||
Name Type Description
|
||||
--------- ------- -------------------------------------------------------------
|
||||
user-id Number the id of the user you want to charge his/her account
|
||||
table-ref ? a reference to the table engine which must be refershed e.g. v-bind:xtable="this.$refs.MyTable"
|
||||
|
||||
-->
|
||||
|
||||
|
|
@ -32,7 +33,7 @@ user-id Number the id of the user you want to charge his/her account
|
|||
>
|
||||
<div class="d-flex align-items-center" style="column-gap: 0.5rem;">
|
||||
<span>$</span>
|
||||
<b-form-input v-bind:value="Payload_D.amount" />
|
||||
<b-form-input v-bind:value="Payload_D.amount" v-on:input="HandleInputChanged" />
|
||||
</div>
|
||||
</b-modal>
|
||||
|
||||
|
|
@ -58,6 +59,11 @@ export default {
|
|||
type: Number,
|
||||
required: true,
|
||||
},
|
||||
tableRef: {
|
||||
type: Object,
|
||||
required: false,
|
||||
default: undefined,
|
||||
},
|
||||
},
|
||||
|
||||
components: {
|
||||
|
|
@ -78,10 +84,12 @@ export default {
|
|||
methods: {
|
||||
async HandleChargeButtonClicked()
|
||||
{
|
||||
this.Payload_D.amount = parseInt(this.Payload_D.amount)
|
||||
this.$store.commit('app/toggle_full_page_overlay')
|
||||
try
|
||||
{
|
||||
let { data } = await axios.post(`https://api.ira-lex.com/administrator/user/${this.userId}/charge/`, this.Payload_D)
|
||||
if( this.tableRef !== undefined ) this.tableRef.fetch()
|
||||
this.$store.commit('app/toggle_full_page_overlay')
|
||||
this.$bvModal.show('modal-success')
|
||||
}
|
||||
|
|
@ -92,6 +100,11 @@ export default {
|
|||
Log('ERROR::AXIOS::COMPONENTS/UI/CHARGE_USER_MODAL.VUE>CHARGE_USER_MODAL', e)
|
||||
}
|
||||
},
|
||||
|
||||
HandleInputChanged(e)
|
||||
{
|
||||
this.Payload_D.amount = e
|
||||
},
|
||||
},
|
||||
}
|
||||
</script>
|
||||
|
|
|
|||
|
|
@ -38,6 +38,10 @@ import Antd from 'ant-design-vue'
|
|||
import 'ant-design-vue/dist/antd.css'
|
||||
Vue.use(Antd)
|
||||
|
||||
// Vue Number Animation
|
||||
import VueNumber from 'vue-number-animation'
|
||||
Vue.use(VueNumber)
|
||||
|
||||
// Feather font icon - For form-wizard
|
||||
// * Shall remove it if not using font-icons of feather-icons - For form-wizard
|
||||
require('@core/assets/fonts/feather/iconfont.css') // For form-wizard
|
||||
|
|
|
|||
|
|
@ -0,0 +1,65 @@
|
|||
/*******************************************************************************
|
||||
* Core *
|
||||
* Contains various javascript utilities. *
|
||||
* *
|
||||
* Table of Contents: *
|
||||
* - Number Thousand Separator *
|
||||
* - Logging *
|
||||
*******************************************************************************/
|
||||
|
||||
/*
|
||||
|-----------------------------------------------------------------------
|
||||
| Number Thousand Separator
|
||||
|-----------------------------------------------------------------------
|
||||
|
|
||||
| A function which takes a number and a character and returns a string
|
||||
| containing that number with the given character as thousands
|
||||
| separators.
|
||||
|
|
||||
*/
|
||||
export function SeparateNumberByThousands(Num, Separator = ',')
|
||||
{
|
||||
return Num.toString().replace(/\B(?=(\d{3})+(?!\d))/g, Separator)
|
||||
|
||||
// P.S: Thanks Github Copilot for saving me numerous hours of stackoverflowing 🙂
|
||||
}
|
||||
|
||||
/*
|
||||
|-----------------------------------------------------------------------
|
||||
| Format Bytes
|
||||
|-----------------------------------------------------------------------
|
||||
|
|
||||
| Converts bytes to the equivalent kilobytes, megabytes, gigabytes, etc.
|
||||
|
|
||||
*/
|
||||
export function FormatBytes(Bytes, Decimals = 2)
|
||||
{
|
||||
if( Bytes === 0 ) return '0 Bytes'
|
||||
|
||||
const K = 1024
|
||||
const Dm = (Decimals < 0) ? 0 : Decimals
|
||||
const Sizes = ['Bytes', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB']
|
||||
|
||||
const I = Math.floor(Math.log(Bytes) / Math.log(K))
|
||||
|
||||
return parseFloat((Bytes / Math.pow(K, I)).toFixed(Dm)) + ' ' + Sizes[I]
|
||||
}
|
||||
|
||||
/*
|
||||
|-----------------------------------------------------------------------
|
||||
| Logging
|
||||
|-----------------------------------------------------------------------
|
||||
|
|
||||
| Logs a message to the browser console.
|
||||
| This function is provided to abstract all your logging calls, so you
|
||||
| can change the style of all of them at once. It is useful to make the
|
||||
| logs of your application look different so you can find them easier
|
||||
| when there are hundreds of logs in the console.
|
||||
|
|
||||
*/
|
||||
export function Log(Message, Data = '')
|
||||
{
|
||||
console.log(`%c ${Message} `, 'background:black; color:#bada55; font-family:"PxPlus ToshibaSat 9x16"; font-size: 13px;')
|
||||
if( Data !== '' )
|
||||
console.log(Data)
|
||||
}
|
||||
|
|
@ -3,18 +3,240 @@
|
|||
<h3>Dashboard</h3>
|
||||
|
||||
<b-card>
|
||||
<b-card-title>Users Information</b-card-title>
|
||||
<b-row>
|
||||
<b-col sm="4" style="text-align: center;">
|
||||
<number
|
||||
style="font-weight: bold; font-size: 5rem; color: #7367f0;"
|
||||
v-bind:from="0"
|
||||
v-bind:to="UserAccountsCount_D"
|
||||
v-bind:duration="2"
|
||||
v-bind:delay="1"
|
||||
/>
|
||||
<p style="font-size: 1.1rem;">User Accounts</p>
|
||||
</b-col>
|
||||
<b-col sm="4" style="text-align: center;">
|
||||
<number
|
||||
style="font-weight: bold; font-size: 5rem; color: #7367f0;"
|
||||
v-bind:from="0"
|
||||
v-bind:to="FirmAccountsCount_D"
|
||||
v-bind:duration="2"
|
||||
v-bind:delay="1"
|
||||
/>
|
||||
<p style="font-size: 1.1rem;">Firm Accounts</p>
|
||||
</b-col>
|
||||
<b-col sm="4" style="text-align: center;">
|
||||
<number
|
||||
style="font-weight: bold; font-size: 5rem; color: #7367f0;"
|
||||
v-bind:from="0"
|
||||
v-bind:to="TotalAccountsCount_D"
|
||||
v-bind:duration="2"
|
||||
v-bind:delay="1"
|
||||
/>
|
||||
<p style="font-size: 1.1rem;">Total Accounts</p>
|
||||
</b-col>
|
||||
</b-row>
|
||||
|
||||
<br>
|
||||
<br>
|
||||
|
||||
<b-card-title>Hardware Information</b-card-title>
|
||||
<b-row class="justify-content-center">
|
||||
<b-col sm="3">
|
||||
<vue-apex-charts
|
||||
type="donut"
|
||||
height="350"
|
||||
v-bind:options="DiskChartData_D.options"
|
||||
v-bind:series="DiskChartData_D.series"
|
||||
/>
|
||||
</b-col>
|
||||
<b-col sm="3">
|
||||
<vue-apex-charts
|
||||
type="donut"
|
||||
height="350"
|
||||
v-bind:options="RAMChartData_D.options"
|
||||
v-bind:series="RAMChartData_D.series"
|
||||
/>
|
||||
</b-col>
|
||||
<b-col sm="3">
|
||||
<vue-apex-charts
|
||||
type="donut"
|
||||
height="350"
|
||||
v-bind:options="CPUChartData_D.options"
|
||||
v-bind:series="CPUChartData_D.series"
|
||||
/>
|
||||
</b-col>
|
||||
<!-- <b-col sm="3">
|
||||
<number
|
||||
style="font-weight: bold; font-size: 5rem; color: #7367f0;"
|
||||
v-bind:from="0"
|
||||
v-bind:to="HardwareInfo_D.cpu.count"
|
||||
v-bind:duration="2"
|
||||
v-bind:delay="1"
|
||||
/>
|
||||
<p style="font-size: 1.1rem;">CPU Cores</p>
|
||||
</b-col> -->
|
||||
<!-- <div class="d-flex flex-column align-items-center">
|
||||
</div> -->
|
||||
</b-row>
|
||||
</b-card>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { BCard } from 'bootstrap-vue'
|
||||
import { BRow, BCol, BCard, BCardTitle } from 'bootstrap-vue'
|
||||
import { Log, FormatBytes } from '@/modules/core'
|
||||
import axios from '@/axios'
|
||||
import VueApexCharts from 'vue-apexcharts'
|
||||
|
||||
export default {
|
||||
name: 'DashboardView',
|
||||
|
||||
components: {
|
||||
BRow,
|
||||
BCol,
|
||||
BCard,
|
||||
BCardTitle,
|
||||
VueApexCharts,
|
||||
},
|
||||
|
||||
data() {
|
||||
return {
|
||||
TotalAccountsCount_D: 0,
|
||||
UserAccountsCount_D: 0,
|
||||
FirmAccountsCount_D: 0,
|
||||
HardwareInfo_D: undefined,
|
||||
DiskChartData_D: {
|
||||
series: [],
|
||||
options: {
|
||||
labels: [ 'Used', 'Free' ],
|
||||
plotOptions: {
|
||||
pie: {
|
||||
donut: {
|
||||
labels: {
|
||||
show: true,
|
||||
total: {
|
||||
show: true,
|
||||
label: 'Disk',
|
||||
formatter: () => '',
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
},
|
||||
RAMChartData_D: {
|
||||
series: [],
|
||||
options: {
|
||||
labels: [ 'Used', 'Free' ],
|
||||
plotOptions: {
|
||||
pie: {
|
||||
donut: {
|
||||
labels: {
|
||||
show: true,
|
||||
total: {
|
||||
show: true,
|
||||
label: 'RAM',
|
||||
formatter: () => '',
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
},
|
||||
CPUChartData_D: {
|
||||
series: [],
|
||||
options: {
|
||||
labels: [ 'Involved', 'Free' ],
|
||||
plotOptions: {
|
||||
pie: {
|
||||
donut: {
|
||||
labels: {
|
||||
show: true,
|
||||
total: {
|
||||
show: true,
|
||||
label: 'CPU',
|
||||
formatter: (val) =>'',
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
},
|
||||
|
||||
async created()
|
||||
{
|
||||
// -----------------------------------------------------------------
|
||||
// Get Hardware Info
|
||||
// -----------------------------------------------------------------
|
||||
try
|
||||
{
|
||||
const { data } = await axios.post('administrator/hardware/')
|
||||
this.HardwareInfo_D = data
|
||||
Log('Hardware', data)
|
||||
// this.DiskChartData_D.options.plotOptions.pie.donut.labels.total.label = FormatBytes(data.disk.total)
|
||||
this.DiskChartData_D.series.push(data.disk.used)
|
||||
this.DiskChartData_D.series.push(data.disk.free)
|
||||
this.RAMChartData_D.series.push(data.ram.used)
|
||||
this.RAMChartData_D.series.push(data.ram.available)
|
||||
this.CPUChartData_D.series.push(data.cpu.percent)
|
||||
this.CPUChartData_D.series.push(100 - data.cpu.percent)
|
||||
}
|
||||
catch (e)
|
||||
{
|
||||
Log('ERROR::AXIOS::VIEWS/MISC/DASHBOARD>MOUNTED>GET_HARDWARE_INFO', e)
|
||||
}
|
||||
},
|
||||
|
||||
async mounted()
|
||||
{
|
||||
// -----------------------------------------------------------------
|
||||
// Get Number of Users
|
||||
// -----------------------------------------------------------------
|
||||
try
|
||||
{
|
||||
const { data } = await axios.post('administrator/user/query/', {
|
||||
query: [{ field: 'is_main', condition: '=', value: false }]
|
||||
})
|
||||
this.UserAccountsCount_D = data.query.total
|
||||
}
|
||||
catch (e)
|
||||
{
|
||||
Log('ERROR::AXIOS::VIEWS/MISC/DASHBOARD>MOUNTED>GET_NUMBER_OF_USERS', e)
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------
|
||||
// Get Number of Firms
|
||||
// -----------------------------------------------------------------
|
||||
try
|
||||
{
|
||||
const { data } = await axios.post('administrator/user/query/', {
|
||||
query: [{ field: 'is_main', condition: '=', value: true }]
|
||||
})
|
||||
this.FirmAccountsCount_D = data.query.total
|
||||
}
|
||||
catch (e)
|
||||
{
|
||||
Log('ERROR::AXIOS::VIEWS/MISC/DASHBOARD>MOUNTED>GET_NUMBER_OF_FIRMS', e)
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------
|
||||
// Get Number of Accounts
|
||||
// -----------------------------------------------------------------
|
||||
try
|
||||
{
|
||||
const { data } = await axios.post('administrator/user/query/')
|
||||
this.TotalAccountsCount_D = data.query.total
|
||||
}
|
||||
catch (e)
|
||||
{
|
||||
Log('ERROR::AXIOS::VIEWS/MISC/DASHBOARD>MOUNTED>GET_NUMBER_OF_ACCOUNTS', e)
|
||||
}
|
||||
},
|
||||
}
|
||||
</script>
|
||||
|
|
|
|||
|
|
@ -54,6 +54,29 @@
|
|||
v-on:selectedRows="SelectedRows_D"
|
||||
v-bind:options="TableOptions_D"
|
||||
>
|
||||
<span slot="firm" slot-scope="text, record">
|
||||
<svg v-if="text.record.is_main" style="width: 24px; height: 24px" viewBox="0 0 24 24">
|
||||
<path fill="currentColor" d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z" />
|
||||
</svg>
|
||||
<svg v-else style="width: 24px; height: 24px" viewBox="0 0 24 24">
|
||||
<path fill="currentColor" d="M19,6.41L17.59,5L12,10.59L6.41,5L5,6.41L10.59,12L5,17.59L6.41,19L12,13.41L17.59,19L19,17.59L13.41,12L19,6.41Z" />
|
||||
</svg>
|
||||
</span>
|
||||
|
||||
<span slot="charge" slot-scope="text, record">
|
||||
<span v-if="text.record.subscription">${{ SeparateNumberByThousands(text.record.subscription.charge) }}</span>
|
||||
<!-- <span v-if="text.record.subscription">$ {{ text.record.subscription.charge }}</span> -->
|
||||
<span v-else>$0</span>
|
||||
</span>
|
||||
|
||||
<span slot="total_uploaded_size" slot-scope="text, record">
|
||||
<span>{{ FormatBytes(text.record.total_uploaded_size) }}</span>
|
||||
</span>
|
||||
|
||||
<span slot="total_firm_uploaded_size" slot-scope="text, record">
|
||||
<span>{{ FormatBytes(text.record.total_firm_uploaded_size) }}</span>
|
||||
</span>
|
||||
|
||||
<span slot="action" slot-scope="text, record">
|
||||
<b-button
|
||||
v-if="text.record.is_main"
|
||||
|
|
@ -65,21 +88,12 @@
|
|||
Charge
|
||||
</b-button>
|
||||
</span>
|
||||
|
||||
<span slot="firm" slot-scope="text, record">
|
||||
<svg v-if="text.record.is_main" style="width: 24px; height: 24px" viewBox="0 0 24 24">
|
||||
<path fill="currentColor" d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z" />
|
||||
</svg>
|
||||
<svg v-else style="width: 24px; height: 24px" viewBox="0 0 24 24">
|
||||
<path fill="currentColor" d="M19,6.41L17.59,5L12,10.59L6.41,5L5,6.41L10.59,12L5,17.59L6.41,19L12,13.41L17.59,19L19,17.59L13.41,12L19,6.41Z" />
|
||||
</svg>
|
||||
</span>
|
||||
</XTable>
|
||||
</div>
|
||||
</b-card>
|
||||
|
||||
<AddUserModal type="user" v-on:submit="HandleNewUserAdded()" />
|
||||
<ChargeUserModal v-bind:user-id="IdOfUserToCharge_D" v-on:submit="HandleUserCharged()" />
|
||||
<ChargeUserModal v-bind:user-id="IdOfUserToCharge_D" v-bind:table-ref="$refs.users" v-on:submit="HandleUserCharged()" />
|
||||
</div>
|
||||
</template>
|
||||
|
||||
|
|
@ -92,6 +106,7 @@ import ChargeUserModal from '@/components/ui/ChargeUserModal'
|
|||
import * as TableCol from "./userTbl"
|
||||
import XTable from "@/components/x-table/XTable"
|
||||
import axios from '@/axios'
|
||||
import { SeparateNumberByThousands, FormatBytes } from '@/modules/core'
|
||||
// import CoreMixin from '@/mixins/index'
|
||||
|
||||
const InnerColumns = [
|
||||
|
|
@ -149,6 +164,16 @@ export default {
|
|||
},
|
||||
|
||||
methods: {
|
||||
SeparateNumberByThousands(Num)
|
||||
{
|
||||
return SeparateNumberByThousands(Num)
|
||||
},
|
||||
|
||||
FormatBytes(Bytes)
|
||||
{
|
||||
return FormatBytes(Bytes)
|
||||
},
|
||||
|
||||
HandleNewUserAdded()
|
||||
{
|
||||
this.Users_D.push(2)
|
||||
|
|
@ -166,7 +191,6 @@ export default {
|
|||
|
||||
ApplyFilters()
|
||||
{
|
||||
console.log('FETCH')
|
||||
this.$refs.users.query.query = [
|
||||
]
|
||||
if( this.Query_D.IsMain )
|
||||
|
|
@ -175,7 +199,6 @@ export default {
|
|||
condition: '=',
|
||||
value: this.Query_D.IsMain,
|
||||
})
|
||||
console.log(this.$refs.users.query.query)
|
||||
this.$refs.users.fetch()
|
||||
},
|
||||
},
|
||||
|
|
@ -184,6 +207,12 @@ export default {
|
|||
{
|
||||
this.Model_D = TableCol.default
|
||||
},
|
||||
|
||||
async mounted()
|
||||
{
|
||||
const { data } = await axios.post('administrator/user/query/')
|
||||
console.log('users: ', data)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
|||
|
|
@ -5,9 +5,10 @@ tbl.add(new Xtc('first_name', 'First Name'))
|
|||
tbl.add(new Xtc('last_name', 'Last Name'))
|
||||
tbl.add(new Xtc('email_address', 'Email'))
|
||||
tbl.add(new Xtc('is_main', 'Firm').renderSlot('firm'))
|
||||
// tbl.add(new Xtc('user_type', 'User Type'))
|
||||
// tbl.add(new Xtc('birthday', 'Birthday'))
|
||||
// tbl.add(new Xtc('status', 'Status'))
|
||||
tbl.add(new Xtc('subscription.charge', 'Charge').renderSlot('charge'))
|
||||
tbl.add(new Xtc('total_uploaded_size', 'Uploaded Size').renderSlot('total_uploaded_size'))
|
||||
tbl.add(new Xtc('total_firm_uploaded_size', 'Firm Uploaded Size').renderSlot('total_firm_uploaded_size'))
|
||||
tbl.add(new Xtc('action', 'Action').noSort().renderSlot('action'))
|
||||
|
||||
|
||||
export default tbl
|
||||
12
yarn.lock
12
yarn.lock
|
|
@ -4718,6 +4718,11 @@ graceful-fs@^4.1.11, graceful-fs@^4.1.15, graceful-fs@^4.1.2, graceful-fs@^4.1.6
|
|||
resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.8.tgz#e412b8d33f5e006593cbd3cee6df9f2cebbe802a"
|
||||
integrity sha512-qkIilPUYcNhJpd33n0GBXTB1MMPp14TxEsEs0pTrsSVucApsYzW5V+Q8Qxhik6KU3evy+qkAAowTByymK0avdg==
|
||||
|
||||
gsap@^3.6.0:
|
||||
version "3.9.1"
|
||||
resolved "https://registry.yarnpkg.com/gsap/-/gsap-3.9.1.tgz#d4c7443540497afee9ddc0824fd0180224e33360"
|
||||
integrity sha512-JSGVYoC6da4pIjdF/yxFU6Rz8OojOIDkbooveZlfNg0+JIoFoRruyfWAEi6R/gUeNcuOiTqUIb0gi1nCNrHf8w==
|
||||
|
||||
gzip-size@^5.0.0:
|
||||
version "5.1.1"
|
||||
resolved "https://registry.yarnpkg.com/gzip-size/-/gzip-size-5.1.1.tgz#cb9bee692f87c0612b232840a873904e4c135274"
|
||||
|
|
@ -9423,6 +9428,13 @@ vue-loader@^15.9.2:
|
|||
vue-hot-reload-api "^2.3.0"
|
||||
vue-style-loader "^4.1.0"
|
||||
|
||||
vue-number-animation@^1.1.1:
|
||||
version "1.1.1"
|
||||
resolved "https://registry.yarnpkg.com/vue-number-animation/-/vue-number-animation-1.1.1.tgz#785d35b8cbd349919265fb98ced566c388d5753b"
|
||||
integrity sha512-xSYZZ50dbfQa0MPtDMECCkPSe6jDU56gPIBRXzfu9G/lFaCMzWyMokRQiHHK3/H/2WXdWGwnuZjpdphurtAHAg==
|
||||
dependencies:
|
||||
gsap "^3.6.0"
|
||||
|
||||
vue-perfect-scrollbar@0.2.1:
|
||||
version "0.2.1"
|
||||
resolved "https://registry.yarnpkg.com/vue-perfect-scrollbar/-/vue-perfect-scrollbar-0.2.1.tgz#2fecab975512f7c8c37e1610dee48faf46d649f3"
|
||||
|
|
|
|||
Loading…
Reference in New Issue