<template>
  <div class="system-pwconfig-container">
    <el-card shadow="hover">
      <template #header>
        <div class="card-header">
          <span>密码策略配置</span>
        </div>
      </template>
      <el-form :model="ruleForm" ref="formRef" :rules="rules" label-width="180px" style="max-width: 800px;">
        <el-form-item label="启用密码策略" prop="enabled">
          <el-switch v-model="ruleForm.enabled" />
        </el-form-item>

        <el-form-item label="最小密码长度" prop="minLength">
          <el-input-number v-model="ruleForm.minLength" :min="4" :max="32" placeholder="请输入最小密码长度" />
          <span class="ml10 text-muted">位</span>
        </el-form-item>

        <el-form-item label="最大密码长度" prop="maxLength">
          <el-input-number v-model="ruleForm.maxLength" :min="4" :max="128" placeholder="请输入最大密码长度" />
          <span class="ml10 text-muted">位</span>
        </el-form-item>

        <el-form-item label="必须包含大写字母" prop="requireUppercase">
          <el-switch v-model="ruleForm.requireUppercase" />
        </el-form-item>

        <el-form-item label="必须包含小写字母" prop="requireLowercase">
          <el-switch v-model="ruleForm.requireLowercase" />
        </el-form-item>

        <el-form-item label="必须包含数字" prop="requireDigit">
          <el-switch v-model="ruleForm.requireDigit" />
        </el-form-item>

        <el-form-item label="必须包含特殊字符" prop="requireSpecialChar">
          <el-switch v-model="ruleForm.requireSpecialChar" />
          <div class="text-muted mt5" style="font-size: 12px;">特殊字符包括：!@#$%^&*()_+-=[]{}|;:,.<>?</div>
        </el-form-item>

        <el-form-item label="密码过期天数" prop="expireDays">
          <el-input-number v-model="ruleForm.expireDays" :min="0" :max="365" placeholder="请输入密码过期天数" />
          <span class="ml10 text-muted">天（0表示永不过期）</span>
        </el-form-item>

        <el-form-item label="禁止重复使用次数" prop="historyLimit">
          <el-input-number v-model="ruleForm.historyLimit" :min="0" :max="24" placeholder="请输入禁止重复使用次数" />
          <span class="ml10 text-muted">次（0表示不限制）</span>
        </el-form-item>

        <el-form-item label="登录失败锁定次数" prop="maxRetryCount">
          <el-input-number v-model="ruleForm.maxRetryCount" :min="0" :max="10" placeholder="请输入登录失败锁定次数" />
          <span class="ml10 text-muted">次（0表示不锁定）</span>
        </el-form-item>

        <el-form-item label="锁定时长" prop="lockTimeMinutes">
          <el-input-number v-model="ruleForm.lockTimeMinutes" :min="1" :max="1440" placeholder="请输入锁定时长" />
          <span class="ml10 text-muted">分钟</span>
        </el-form-item>

        <el-form-item label="备注" prop="remark">
          <el-input v-model="ruleForm.remark" type="textarea" :rows="3" placeholder="请输入备注" />
        </el-form-item>

        <el-form-item>
          <el-button type="primary" @click="onSubmit" :loading="loading">保存配置</el-button>
          <el-button @click="resetForm">重置</el-button>
        </el-form-item>
      </el-form>
    </el-card>
  </div>
</template>

<script lang="ts">
import { reactive, toRefs, defineComponent, ref, onMounted, unref } from 'vue';
import { ElMessage, FormInstance, FormRules } from 'element-plus';
import { getPwConfig, savePwConfig } from "/@/api/system/pwconfig";

interface RuleFormState {
  enabled: boolean;
  minLength: number;
  maxLength: number;
  requireUppercase: boolean;
  requireLowercase: boolean;
  requireDigit: boolean;
  requireSpecialChar: boolean;
  expireDays: number;
  historyLimit: number;
  maxRetryCount: number;
  lockTimeMinutes: number;
  remark: string;
}

interface PwConfigState {
  ruleForm: RuleFormState;
  rules: FormRules;
  loading: boolean;
}

export default defineComponent({
  name: 'systemPwConfig',
  setup() {
    const formRef = ref<FormInstance>();
    const state = reactive<PwConfigState>({
      loading: false,
      ruleForm: {
        enabled: false,
        minLength: 8,
        maxLength: 32,
        requireUppercase: false,
        requireLowercase: true,
        requireDigit: true,
        requireSpecialChar: false,
        expireDays: 90,
        historyLimit: 5,
        maxRetryCount: 5,
        lockTimeMinutes: 30,
        remark: '',
      },
      rules: {
        minLength: [
          { required: true, message: '请输入最小密码长度', trigger: 'blur' }
        ],
        maxLength: [
          { required: true, message: '请输入最大密码长度', trigger: 'blur' }
        ],
        expireDays: [
          { required: true, message: '请输入密码过期天数', trigger: 'blur' }
        ],
        historyLimit: [
          { required: true, message: '请输入禁止重复使用次数', trigger: 'blur' }
        ],
        maxRetryCount: [
          { required: true, message: '请输入登录失败锁定次数', trigger: 'blur' }
        ],
        lockTimeMinutes: [
          { required: true, message: '请输入锁定时长', trigger: 'blur' }
        ],
      }
    });

    // 获取配置
    const loadConfig = async () => {
      try {
        const res: any = await getPwConfig();
        if (res.code === 0 && res.data) {
          state.ruleForm = {
            ...state.ruleForm,
            ...res.data,
          };
        }
      } catch {
        // 错误由全局拦截器处理
      }
    };

    // 重置表单
    const resetForm = () => {
      loadConfig();
    };

    // 保存配置
    const onSubmit = async () => {
      const formWrap = unref(formRef);
      if (!formWrap) return;

      await formWrap.validate(async (valid: boolean) => {
        if (valid) {
          // 验证最小长度不大于最大长度
          if (state.ruleForm.minLength > state.ruleForm.maxLength) {
            ElMessage.error('最小密码长度不能大于最大密码长度');
            return;
          }

          state.loading = true;
          try {
            await savePwConfig(state.ruleForm);
            ElMessage.success('保存成功');
          } finally {
            state.loading = false;
          }
        }
      });
    };

    // 页面加载时
    onMounted(() => {
      loadConfig();
    });

    return {
      formRef,
      onSubmit,
      resetForm,
      ...toRefs(state),
    };
  },
});
</script>

<style scoped lang="scss">
.text-muted {
  color: var(--el-text-color-placeholder);
}

.card-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
}

.system-pwconfig-container {
  :deep(.el-card__body) {
    padding-top: 30px;
  }
}
</style>
