From be125538c6e9c17a923c9dbe1e4cca9962b0ed39 Mon Sep 17 00:00:00 2001
From: yaowanxin <3588231647@qq.com>
Date: 星期一, 08 九月 2025 10:17:53 +0800
Subject: [PATCH] Merge remote-tracking branch 'origin/dev' into ywx
---
src/views/collaborativeApproval/planTemplate/index.vue | 750 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 750 insertions(+), 0 deletions(-)
diff --git a/src/views/collaborativeApproval/planTemplate/index.vue b/src/views/collaborativeApproval/planTemplate/index.vue
new file mode 100644
index 0000000..f46a203
--- /dev/null
+++ b/src/views/collaborativeApproval/planTemplate/index.vue
@@ -0,0 +1,750 @@
+<template>
+ <div class="app-container">
+ <!-- 椤堕儴鎿嶄綔鏍� -->
+ <div class="header-actions">
+ <div class="left-actions">
+ <el-select v-model="currentLevel" placeholder="閫夋嫨璁″垝绾у埆" style="width: 150px" @change="handleLevelChange">
+ <el-option label="涓汉璁″垝" value="personal" />
+ <el-option label="灏忕粍璁″垝" value="group" />
+ <el-option label="閮ㄩ棬璁″垝" value="department" />
+ <el-option label="鍏徃璁″垝" value="company" />
+ </el-select>
+ <el-select v-model="currentPeriod" placeholder="閫夋嫨鏃堕棿鍛ㄦ湡" style="width: 120px; margin-left: 10px" @change="handlePeriodChange">
+ <el-option label="鍛ㄨ鍒�" value="week" />
+ <el-option label="鏈堣鍒�" value="month" />
+ <el-option label="骞磋鍒�" value="year" />
+ </el-select>
+ <el-date-picker
+ v-model="currentDate"
+ :type="datePickerType"
+ placeholder="閫夋嫨鏃ユ湡"
+ style="width: 180px; margin-left: 10px"
+ @change="handleDateChange"
+ />
+ </div>
+ <div class="right-actions">
+ <el-button type="primary" @click="handleAddPlan">鏂板璁″垝</el-button>
+ <el-button @click="handleExport">瀵煎嚭璁″垝</el-button>
+ <el-button @click="handleShare">鍏变韩璁″垝</el-button>
+ </div>
+ </div>
+
+ <!-- 璁″垝姒傝鍗$墖 -->
+ <div class="overview-cards">
+ <el-row :gutter="20">
+ <el-col :span="6">
+ <el-card class="overview-card">
+ <div class="card-content">
+ <div class="card-icon personal">
+ <el-icon><User /></el-icon>
+ </div>
+ <div class="card-info">
+ <div class="card-title">涓汉璁″垝</div>
+ <div class="card-number">{{ overviewData.personal.total }}</div>
+ <div class="card-progress">
+ <el-progress :percentage="overviewData.personal.completion" :stroke-width="6" />
+ </div>
+ </div>
+ </div>
+ </el-card>
+ </el-col>
+ <el-col :span="6">
+ <el-card class="overview-card">
+ <div class="card-content">
+ <div class="card-icon group">
+ <el-icon><UserFilled /></el-icon>
+ </div>
+ <div class="card-info">
+ <div class="card-title">灏忕粍璁″垝</div>
+ <div class="card-number">{{ overviewData.group.total }}</div>
+ <div class="card-progress">
+ <el-progress :percentage="overviewData.group.completion" :stroke-width="6" />
+ </div>
+ </div>
+ </div>
+ </el-card>
+ </el-col>
+ <el-col :span="6">
+ <el-card class="overview-card">
+ <div class="card-content">
+ <div class="card-icon department">
+ <el-icon><OfficeBuilding /></el-icon>
+ </div>
+ <div class="card-info">
+ <div class="card-title">閮ㄩ棬璁″垝</div>
+ <div class="card-number">{{ overviewData.department.total }}</div>
+ <div class="card-progress">
+ <el-progress :percentage="overviewData.department.completion" :stroke-width="6" />
+ </div>
+ </div>
+ </div>
+ </el-card>
+ </el-col>
+ <el-col :span="6">
+ <el-card class="overview-card">
+ <div class="card-content">
+ <div class="card-icon company">
+ <el-icon><House /></el-icon>
+ </div>
+ <div class="card-info">
+ <div class="card-title">鍏徃璁″垝</div>
+ <div class="card-number">{{ overviewData.company.total }}</div>
+ <div class="card-progress">
+ <el-progress :percentage="overviewData.company.completion" :stroke-width="6" />
+ </div>
+ </div>
+ </div>
+ </el-card>
+ </el-col>
+ </el-row>
+ </div>
+
+ <!-- 璁″垝鍒楄〃 -->
+ <div class="plan-content">
+ <el-card>
+ <template #header>
+ <div class="card-header">
+ <span>{{ getCurrentLevelText() }} - {{ getCurrentPeriodText() }}</span>
+ <div>
+ <el-button size="small" @click="handleRefresh">鍒锋柊</el-button>
+ <el-button size="small" @click="handleFilter">绛涢��</el-button>
+ </div>
+ </div>
+ </template>
+
+ <div class="plan-list">
+ <div v-for="plan in planList" :key="plan.id" class="plan-item">
+ <div class="plan-header">
+ <div class="plan-title">
+ <el-tag :type="getPriorityType(plan.priority)" size="small">{{ getPriorityText(plan.priority) }}</el-tag>
+ <span class="title-text">{{ plan.title }}</span>
+ </div>
+ <div class="plan-actions">
+ <el-button size="small" @click="handleEditPlan(plan)">缂栬緫</el-button>
+ <el-button size="small" @click="handleViewDetail(plan)">璇︽儏</el-button>
+ <el-dropdown @command="handleMoreAction">
+ <el-button size="small">
+ 鏇村<el-icon class="el-icon--right"><ArrowDown /></el-icon>
+ </el-button>
+ <template #dropdown>
+ <el-dropdown-menu>
+ <el-dropdown-item command="share">鍏变韩</el-dropdown-item>
+ <el-dropdown-item command="copy">澶嶅埗</el-dropdown-item>
+ <el-dropdown-item command="delete" divided>鍒犻櫎</el-dropdown-item>
+ </el-dropdown-menu>
+ </template>
+ </el-dropdown>
+ </div>
+ </div>
+
+ <div class="plan-content">
+ <div class="plan-description">{{ plan.description }}</div>
+ <div class="plan-meta">
+ <div class="meta-item">
+ <el-icon><Calendar /></el-icon>
+ <span>{{ plan.startDate }} - {{ plan.endDate }}</span>
+ </div>
+ <div class="meta-item">
+ <el-icon><User /></el-icon>
+ <span>{{ plan.assignee }}</span>
+ </div>
+ <div class="meta-item">
+ <el-icon><Clock /></el-icon>
+ <span>杩涘害: {{ plan.progress }}%</span>
+ </div>
+ <div class="meta-item">
+ <el-icon><Flag /></el-icon>
+ <span>{{ getStatusText(plan.status) }}</span>
+ </div>
+ </div>
+
+ <div class="plan-progress">
+ <el-progress
+ :percentage="plan.progress"
+ :color="getProgressColor(plan.progress)"
+ :stroke-width="8"
+ />
+ </div>
+
+ <div class="plan-tags">
+ <el-tag v-for="tag in plan.tags" :key="tag" size="small" style="margin-right: 5px">
+ {{ tag }}
+ </el-tag>
+ </div>
+ </div>
+ </div>
+ </div>
+ </el-card>
+ </div>
+
+ <!-- 鏂板/缂栬緫璁″垝瀵硅瘽妗� -->
+ <el-dialog
+ v-model="planDialogVisible"
+ :title="dialogTitle"
+ width="600px"
+ @close="handleDialogClose"
+ >
+ <el-form :model="planForm" :rules="planRules" ref="planFormRef" label-width="100px">
+ <el-form-item label="璁″垝鏍囬" prop="title">
+ <el-input v-model="planForm.title" placeholder="璇疯緭鍏ヨ鍒掓爣棰�" />
+ </el-form-item>
+ <el-form-item label="璁″垝鎻忚堪" prop="description">
+ <el-input
+ v-model="planForm.description"
+ type="textarea"
+ :rows="3"
+ placeholder="璇疯緭鍏ヨ鍒掓弿杩�"
+ />
+ </el-form-item>
+ <el-form-item label="璁″垝绾у埆" prop="level">
+ <el-select v-model="planForm.level" placeholder="閫夋嫨璁″垝绾у埆" style="width: 100%">
+ <el-option label="涓汉璁″垝" value="personal" />
+ <el-option label="灏忕粍璁″垝" value="group" />
+ <el-option label="閮ㄩ棬璁″垝" value="department" />
+ <el-option label="鍏徃璁″垝" value="company" />
+ </el-select>
+ </el-form-item>
+ <el-form-item label="鏃堕棿鍛ㄦ湡" prop="period">
+ <el-select v-model="planForm.period" placeholder="閫夋嫨鏃堕棿鍛ㄦ湡" style="width: 100%">
+ <el-option label="鍛ㄨ鍒�" value="week" />
+ <el-option label="鏈堣鍒�" value="month" />
+ <el-option label="骞磋鍒�" value="year" />
+ </el-select>
+ </el-form-item>
+ <el-form-item label="寮�濮嬫椂闂�" prop="startDate">
+ <el-date-picker
+ v-model="planForm.startDate"
+ type="date"
+ placeholder="閫夋嫨寮�濮嬫椂闂�"
+ style="width: 100%"
+ />
+ </el-form-item>
+ <el-form-item label="缁撴潫鏃堕棿" prop="endDate">
+ <el-date-picker
+ v-model="planForm.endDate"
+ type="date"
+ placeholder="閫夋嫨缁撴潫鏃堕棿"
+ style="width: 100%"
+ />
+ </el-form-item>
+ <el-form-item label="璐熻矗浜�" prop="assignee">
+ <el-input v-model="planForm.assignee" placeholder="璇疯緭鍏ヨ礋璐d汉" />
+ </el-form-item>
+ <el-form-item label="浼樺厛绾�" prop="priority">
+ <el-select v-model="planForm.priority" placeholder="閫夋嫨浼樺厛绾�" style="width: 100%">
+ <el-option label="楂�" value="high" />
+ <el-option label="涓�" value="medium" />
+ <el-option label="浣�" value="low" />
+ </el-select>
+ </el-form-item>
+ <el-form-item label="鏍囩">
+ <el-input v-model="planForm.tags" placeholder="璇疯緭鍏ユ爣绛撅紝鐢ㄩ�楀彿鍒嗛殧" />
+ </el-form-item>
+ </el-form>
+ <template #footer>
+ <span class="dialog-footer">
+ <el-button @click="planDialogVisible = false">鍙栨秷</el-button>
+ <el-button type="primary" @click="handleSavePlan">淇濆瓨</el-button>
+ </span>
+ </template>
+ </el-dialog>
+ </div>
+</template>
+
+<script setup>
+import { ref, reactive, computed, onMounted } from 'vue'
+import { ElMessage, ElMessageBox } from 'element-plus'
+import {
+ User,
+ UserFilled,
+ OfficeBuilding,
+ House,
+ Calendar,
+ Clock,
+ Flag,
+ ArrowDown
+} from '@element-plus/icons-vue'
+
+// 鍝嶅簲寮忔暟鎹�
+const currentLevel = ref('personal')
+const currentPeriod = ref('week')
+const currentDate = ref(new Date())
+const planDialogVisible = ref(false)
+const dialogTitle = ref('鏂板璁″垝')
+const planFormRef = ref()
+
+// 琛ㄥ崟鏁版嵁
+const planForm = reactive({
+ title: '',
+ description: '',
+ level: 'personal',
+ period: 'week',
+ startDate: '',
+ endDate: '',
+ assignee: '',
+ priority: 'medium',
+ tags: ''
+})
+
+// 琛ㄥ崟楠岃瘉瑙勫垯
+const planRules = {
+ title: [{ required: true, message: '璇疯緭鍏ヨ鍒掓爣棰�', trigger: 'blur' }],
+ description: [{ required: true, message: '璇疯緭鍏ヨ鍒掓弿杩�', trigger: 'blur' }],
+ level: [{ required: true, message: '璇烽�夋嫨璁″垝绾у埆', trigger: 'change' }],
+ period: [{ required: true, message: '璇烽�夋嫨鏃堕棿鍛ㄦ湡', trigger: 'change' }],
+ startDate: [{ required: true, message: '璇烽�夋嫨寮�濮嬫椂闂�', trigger: 'change' }],
+ endDate: [{ required: true, message: '璇烽�夋嫨缁撴潫鏃堕棿', trigger: 'change' }],
+ assignee: [{ required: true, message: '璇疯緭鍏ヨ礋璐d汉', trigger: 'blur' }],
+ priority: [{ required: true, message: '璇烽�夋嫨浼樺厛绾�', trigger: 'change' }]
+}
+
+// 姒傝鏁版嵁
+const overviewData = reactive({
+ personal: { total: 12, completion: 75 },
+ group: { total: 8, completion: 60 },
+ department: { total: 15, completion: 45 },
+ company: { total: 6, completion: 30 }
+})
+
+// 璁″垝鍒楄〃鏁版嵁
+const planList = ref([
+ {
+ id: 1,
+ title: '浜у搧闇�姹傚垎鏋�',
+ description: '瀵规柊浜у搧杩涜璇︾粏鐨勯渶姹傚垎鏋愬拰甯傚満璋冪爺锛屽埗瀹氫骇鍝佽鍒掓柟妗�',
+ level: 'personal',
+ period: 'week',
+ startDate: '2025-01-15',
+ endDate: '2025-01-21',
+ assignee: '闄堝織寮�',
+ priority: 'high',
+ status: 'in_progress',
+ progress: 80,
+ tags: ['浜у搧', '鍒嗘瀽', '璋冪爺']
+ },
+ {
+ id: 2,
+ title: '鎶�鏈灦鏋勮璁�',
+ description: '璁捐绯荤粺鎶�鏈灦鏋勶紝鍖呮嫭鏁版嵁搴撹璁°�佹帴鍙h璁$瓑',
+ level: 'group',
+ period: 'month',
+ startDate: '2025-01-01',
+ endDate: '2025-01-31',
+ assignee: '鍒橀泤濠�',
+ priority: 'high',
+ status: 'completed',
+ progress: 100,
+ tags: ['鎶�鏈�', '鏋舵瀯', '璁捐']
+ },
+ {
+ id: 3,
+ title: '甯傚満鎺ㄥ箍璁″垝',
+ description: '鍒跺畾骞村害甯傚満鎺ㄥ箍绛栫暐鍜岃惀閿�璁″垝',
+ level: 'department',
+ period: 'year',
+ startDate: '2025-01-01',
+ endDate: '2025-12-31',
+ assignee: '鐜嬪缓鍥�',
+ priority: 'medium',
+ status: 'not_started',
+ progress: 0,
+ tags: ['甯傚満', '鎺ㄥ箍', '钀ラ攢']
+ },
+ {
+ id: 4,
+ title: '鍥㈤槦寤鸿娲诲姩',
+ description: '缁勭粐鍥㈤槦寤鸿娲诲姩锛屾彁鍗囧洟闃熷嚌鑱氬姏鍜屽崗浣滄晥鐜�',
+ level: 'company',
+ period: 'month',
+ startDate: '2025-01-15',
+ endDate: '2025-02-15',
+ assignee: '璧典附鍗�',
+ priority: 'low',
+ status: 'in_progress',
+ progress: 30,
+ tags: ['鍥㈤槦', '寤鸿', '娲诲姩']
+ }
+])
+
+// 璁$畻灞炴��
+const datePickerType = computed(() => {
+ switch (currentPeriod.value) {
+ case 'week':
+ return 'week'
+ case 'month':
+ return 'month'
+ case 'year':
+ return 'year'
+ default:
+ return 'date'
+ }
+})
+
+// 鏂规硶
+const handleLevelChange = (value) => {
+ console.log('璁″垝绾у埆鍙樻洿:', value)
+ // 杩欓噷鍙互鏍规嵁绾у埆绛涢�夋暟鎹�
+}
+
+const handlePeriodChange = (value) => {
+ console.log('鏃堕棿鍛ㄦ湡鍙樻洿:', value)
+ // 杩欓噷鍙互鏍规嵁鍛ㄦ湡绛涢�夋暟鎹�
+}
+
+const handleDateChange = (value) => {
+ console.log('鏃ユ湡鍙樻洿:', value)
+ // 杩欓噷鍙互鏍规嵁鏃ユ湡绛涢�夋暟鎹�
+}
+
+const handleAddPlan = () => {
+ dialogTitle.value = '鏂板璁″垝'
+ planDialogVisible.value = true
+ // 閲嶇疆琛ㄥ崟
+ Object.keys(planForm).forEach(key => {
+ planForm[key] = ''
+ })
+ planForm.level = 'personal'
+ planForm.period = 'week'
+ planForm.priority = 'medium'
+}
+
+const handleEditPlan = (plan) => {
+ dialogTitle.value = '缂栬緫璁″垝'
+ planDialogVisible.value = true
+ // 濉厖琛ㄥ崟鏁版嵁
+ Object.keys(planForm).forEach(key => {
+ if (key === 'tags') {
+ planForm[key] = plan[key].join(', ')
+ } else {
+ planForm[key] = plan[key]
+ }
+ })
+}
+
+const handleViewDetail = (plan) => {
+ ElMessage.info(`鏌ョ湅璁″垝璇︽儏: ${plan.title}`)
+}
+
+const handleMoreAction = (command) => {
+ switch (command) {
+ case 'share':
+ ElMessage.success('璁″垝宸插叡浜�')
+ break
+ case 'copy':
+ ElMessage.success('璁″垝宸插鍒�')
+ break
+ case 'delete':
+ ElMessageBox.confirm('纭畾瑕佸垹闄よ繖涓鍒掑悧锛�', '鎻愮ず', {
+ confirmButtonText: '纭畾',
+ cancelButtonText: '鍙栨秷',
+ type: 'warning'
+ }).then(() => {
+ ElMessage.success('璁″垝宸插垹闄�')
+ })
+ break
+ }
+}
+
+const handleSavePlan = async () => {
+ try {
+ await planFormRef.value.validate()
+ ElMessage.success('璁″垝淇濆瓨鎴愬姛')
+ planDialogVisible.value = false
+ } catch (error) {
+ console.log('琛ㄥ崟楠岃瘉澶辫触:', error)
+ }
+}
+
+const handleDialogClose = () => {
+ planFormRef.value?.resetFields()
+}
+
+const handleRefresh = () => {
+ ElMessage.success('鏁版嵁宸插埛鏂�')
+}
+
+const handleFilter = () => {
+ ElMessage.info('鎵撳紑绛涢�夐潰鏉�')
+}
+
+const handleExport = () => {
+ ElMessage.success('璁″垝宸插鍑�')
+}
+
+const handleShare = () => {
+ ElMessage.success('璁″垝宸插叡浜�')
+}
+
+const getCurrentLevelText = () => {
+ const levelMap = {
+ personal: '涓汉璁″垝',
+ group: '灏忕粍璁″垝',
+ department: '閮ㄩ棬璁″垝',
+ company: '鍏徃璁″垝'
+ }
+ return levelMap[currentLevel.value] || '涓汉璁″垝'
+}
+
+const getCurrentPeriodText = () => {
+ const periodMap = {
+ week: '鍛ㄨ鍒�',
+ month: '鏈堣鍒�',
+ year: '骞磋鍒�'
+ }
+ return periodMap[currentPeriod.value] || '鍛ㄨ鍒�'
+}
+
+const getPriorityType = (priority) => {
+ const typeMap = {
+ high: 'danger',
+ medium: 'warning',
+ low: 'info'
+ }
+ return typeMap[priority] || 'info'
+}
+
+const getPriorityText = (priority) => {
+ const textMap = {
+ high: '楂�',
+ medium: '涓�',
+ low: '浣�'
+ }
+ return textMap[priority] || '涓�'
+}
+
+const getStatusText = (status) => {
+ const statusMap = {
+ not_started: '鏈紑濮�',
+ in_progress: '杩涜涓�',
+ completed: '宸插畬鎴�',
+ paused: '宸叉殏鍋�'
+ }
+ return statusMap[status] || '鏈煡'
+}
+
+const getProgressColor = (progress) => {
+ if (progress >= 80) return '#67C23A'
+ if (progress >= 50) return '#E6A23C'
+ return '#F56C6C'
+}
+
+onMounted(() => {
+ console.log('澶氱骇璁″垝妯℃澘椤甸潰宸插姞杞�')
+})
+</script>
+
+<style scoped>
+.app-container {
+ padding: 20px;
+ background-color: #f5f5f5;
+ min-height: 100vh;
+}
+
+.header-actions {
+ display: flex;
+ justify-content: space-between;
+ align-items: center;
+ margin-bottom: 20px;
+ background: white;
+ padding: 20px;
+ box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
+}
+
+.left-actions {
+ display: flex;
+ align-items: center;
+}
+
+.right-actions {
+ display: flex;
+ gap: 10px;
+}
+
+.overview-cards {
+ margin-bottom: 20px;
+}
+
+.overview-card {
+ height: 120px;
+}
+
+.card-content {
+ display: flex;
+ align-items: center;
+ height: 100%;
+}
+
+.card-icon {
+ width: 60px;
+ height: 60px;
+ border-radius: 50%;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ margin-right: 15px;
+ font-size: 24px;
+ color: white;
+}
+
+.card-icon.personal {
+ background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
+}
+
+.card-icon.group {
+ background: linear-gradient(135deg, #f093fb 0%, #f5576c 100%);
+}
+
+.card-icon.department {
+ background: linear-gradient(135deg, #4facfe 0%, #00f2fe 100%);
+}
+
+.card-icon.company {
+ background: linear-gradient(135deg, #43e97b 0%, #38f9d7 100%);
+}
+
+.card-info {
+ flex: 1;
+}
+
+.card-title {
+ font-size: 14px;
+ color: #666;
+ margin-bottom: 5px;
+}
+
+.card-number {
+ font-size: 24px;
+ font-weight: bold;
+ color: #333;
+ margin-bottom: 10px;
+}
+
+.card-progress {
+ width: 100%;
+}
+
+.plan-content {
+ background: white;
+ border-radius: 8px;
+ overflow: hidden;
+}
+
+.card-header {
+ display: flex;
+ justify-content: space-between;
+ align-items: center;
+ font-weight: bold;
+ color: #333;
+}
+
+.header-actions {
+ display: flex;
+ gap: 10px;
+}
+
+.plan-list {
+ padding: 20px 0;
+}
+
+.plan-item {
+ border: 1px solid #e4e7ed;
+ border-radius: 8px;
+ margin-bottom: 15px;
+ padding: 20px;
+ transition: all 0.3s ease;
+}
+
+.plan-item:hover {
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.1);
+ transform: translateY(-2px);
+}
+
+.plan-header {
+ display: flex;
+ justify-content: space-between;
+ align-items: center;
+ margin-bottom: 15px;
+}
+
+.plan-title {
+ display: flex;
+ align-items: center;
+ gap: 10px;
+}
+
+.title-text {
+ font-size: 16px;
+ font-weight: bold;
+ color: #333;
+}
+
+.plan-actions {
+ display: flex;
+ gap: 10px;
+}
+
+.plan-content {
+ margin-bottom: 15px;
+}
+
+.plan-description {
+ color: #666;
+ margin-bottom: 15px;
+ line-height: 1.6;
+}
+
+.plan-meta {
+ display: flex;
+ flex-wrap: wrap;
+ gap: 20px;
+ margin-bottom: 15px;
+}
+
+.meta-item {
+ display: flex;
+ align-items: center;
+ gap: 5px;
+ color: #666;
+ font-size: 14px;
+}
+
+.plan-progress {
+ margin-bottom: 15px;
+}
+
+.plan-tags {
+ display: flex;
+ flex-wrap: wrap;
+ gap: 5px;
+}
+
+.dialog-footer {
+ display: flex;
+ justify-content: flex-end;
+ gap: 10px;
+}
+
+/* 鍝嶅簲寮忚璁� */
+@media (max-width: 768px) {
+ .header-actions {
+ flex-direction: column;
+ gap: 15px;
+ }
+
+ .left-actions {
+ flex-wrap: wrap;
+ gap: 10px;
+ }
+
+ .plan-meta {
+ flex-direction: column;
+ gap: 10px;
+ }
+
+ .plan-header {
+ flex-direction: column;
+ align-items: flex-start;
+ gap: 10px;
+ }
+}
+</style>
--
Gitblit v1.9.3