user-operate-drawer.vue 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166
  1. <script setup lang="ts">
  2. import { computed, ref, watch } from 'vue';
  3. import { enableStatusOptions, userGenderOptions } from '@/constants/business';
  4. import { fetchGetAllRoles } from '@/service/api';
  5. import { useFormRules, useNaiveForm } from '@/hooks/common/form';
  6. import { $t } from '@/locales';
  7. defineOptions({
  8. name: 'UserOperateDrawer'
  9. });
  10. interface Props {
  11. /** the type of operation */
  12. operateType: NaiveUI.TableOperateType;
  13. /** the edit row data */
  14. rowData?: Api.SystemManage.User | null;
  15. }
  16. const props = defineProps<Props>();
  17. interface Emits {
  18. (e: 'submitted'): void;
  19. }
  20. const emit = defineEmits<Emits>();
  21. const visible = defineModel<boolean>('visible', {
  22. default: false
  23. });
  24. const { formRef, validate, restoreValidation } = useNaiveForm();
  25. const { defaultRequiredRule } = useFormRules();
  26. const title = computed(() => {
  27. const titles: Record<NaiveUI.TableOperateType, string> = {
  28. add: $t('page.manage.user.addUser'),
  29. edit: $t('page.manage.user.editUser')
  30. };
  31. return titles[props.operateType];
  32. });
  33. type Model = Pick<
  34. Api.SystemManage.User,
  35. 'userName' | 'userGender' | 'nickName' | 'userPhone' | 'userEmail' | 'userRoles' | 'status'
  36. >;
  37. const model = ref(createDefaultModel());
  38. function createDefaultModel(): Model {
  39. return {
  40. userName: '',
  41. userGender: null,
  42. nickName: '',
  43. userPhone: '',
  44. userEmail: '',
  45. userRoles: [],
  46. status: null
  47. };
  48. }
  49. type RuleKey = Extract<keyof Model, 'userName' | 'status'>;
  50. const rules: Record<RuleKey, App.Global.FormRule> = {
  51. userName: defaultRequiredRule,
  52. status: defaultRequiredRule
  53. };
  54. /** the enabled role options */
  55. const roleOptions = ref<CommonType.Option<string>[]>([]);
  56. async function getRoleOptions() {
  57. const { error, data } = await fetchGetAllRoles();
  58. if (!error) {
  59. const options = data.map(item => ({
  60. label: item.roleName,
  61. value: item.roleCode
  62. }));
  63. // the mock data does not have the roleCode, so fill it
  64. // if the real request, remove the following code
  65. const userRoleOptions = model.value.userRoles.map(item => ({
  66. label: item,
  67. value: item
  68. }));
  69. // end
  70. roleOptions.value = [...userRoleOptions, ...options];
  71. }
  72. }
  73. function handleInitModel() {
  74. model.value = createDefaultModel();
  75. if (props.operateType === 'edit' && props.rowData) {
  76. Object.assign(model.value, props.rowData);
  77. }
  78. }
  79. function closeDrawer() {
  80. visible.value = false;
  81. }
  82. async function handleSubmit() {
  83. await validate();
  84. // request
  85. window.$message?.success($t('common.updateSuccess'));
  86. closeDrawer();
  87. emit('submitted');
  88. }
  89. watch(visible, () => {
  90. if (visible.value) {
  91. handleInitModel();
  92. restoreValidation();
  93. getRoleOptions();
  94. }
  95. });
  96. </script>
  97. <template>
  98. <NDrawer v-model:show="visible" display-directive="show" :width="360">
  99. <NDrawerContent :title="title" :native-scrollbar="false" closable>
  100. <NForm ref="formRef" :model="model" :rules="rules">
  101. <NFormItem :label="$t('page.manage.user.userName')" path="userName">
  102. <NInput v-model:value="model.userName" :placeholder="$t('page.manage.user.form.userName')" />
  103. </NFormItem>
  104. <NFormItem :label="$t('page.manage.user.userGender')" path="userGender">
  105. <NRadioGroup v-model:value="model.userGender">
  106. <NRadio v-for="item in userGenderOptions" :key="item.value" :value="item.value" :label="$t(item.label)" />
  107. </NRadioGroup>
  108. </NFormItem>
  109. <NFormItem :label="$t('page.manage.user.nickName')" path="nickName">
  110. <NInput v-model:value="model.nickName" :placeholder="$t('page.manage.user.form.nickName')" />
  111. </NFormItem>
  112. <NFormItem :label="$t('page.manage.user.userPhone')" path="userPhone">
  113. <NInput v-model:value="model.userPhone" :placeholder="$t('page.manage.user.form.userPhone')" />
  114. </NFormItem>
  115. <NFormItem :label="$t('page.manage.user.userEmail')" path="email">
  116. <NInput v-model:value="model.userEmail" :placeholder="$t('page.manage.user.form.userEmail')" />
  117. </NFormItem>
  118. <NFormItem :label="$t('page.manage.user.userStatus')" path="status">
  119. <NRadioGroup v-model:value="model.status">
  120. <NRadio v-for="item in enableStatusOptions" :key="item.value" :value="item.value" :label="$t(item.label)" />
  121. </NRadioGroup>
  122. </NFormItem>
  123. <NFormItem :label="$t('page.manage.user.userRole')" path="roles">
  124. <NSelect
  125. v-model:value="model.userRoles"
  126. multiple
  127. :options="roleOptions"
  128. :placeholder="$t('page.manage.user.form.userRole')"
  129. />
  130. </NFormItem>
  131. </NForm>
  132. <template #footer>
  133. <NSpace :size="16">
  134. <NButton @click="closeDrawer">{{ $t('common.cancel') }}</NButton>
  135. <NButton type="primary" @click="handleSubmit">{{ $t('common.confirm') }}</NButton>
  136. </NSpace>
  137. </template>
  138. </NDrawerContent>
  139. </NDrawer>
  140. </template>
  141. <style scoped></style>