Upload
This commit is contained in:
parent
5cf34df31c
commit
7209b7ee2f
|
@ -1,12 +1,12 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html lang="zh-cn">
|
<html lang="zh-cn" class="h-full bg-gray-100">
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="UTF-8">
|
||||||
<link rel="icon" href="/logo.png">
|
<link rel="icon" href="/logo.png">
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
<title>DormStar</title>
|
<title>DormStar</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body class="h-full">
|
||||||
<div id="app"></div>
|
<div id="app"></div>
|
||||||
<script type="module" src="./src/main.js"></script>
|
<script type="module" src="./src/main.js"></script>
|
||||||
</body>
|
</body>
|
||||||
|
|
|
@ -15,6 +15,7 @@
|
||||||
"vue-router": "^4.2.5"
|
"vue-router": "^4.2.5"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
"@headlessui/vue": "^1.7.16",
|
||||||
"@vitejs/plugin-vue": "^4.4.0",
|
"@vitejs/plugin-vue": "^4.4.0",
|
||||||
"autoprefixer": "^10.4.16",
|
"autoprefixer": "^10.4.16",
|
||||||
"postcss": "^8.4.31",
|
"postcss": "^8.4.31",
|
||||||
|
|
|
@ -15,6 +15,13 @@ const router = createRouter({
|
||||||
{
|
{
|
||||||
path: '/sign/up',
|
path: '/sign/up',
|
||||||
component: () => import('../views/Sign/SignUp.vue'),
|
component: () => import('../views/Sign/SignUp.vue'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: '/sign/reset',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: '/dashboard',
|
||||||
|
component: () => import('../views/Dashboard.vue'),
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
})
|
})
|
||||||
|
|
158
FrontEnd/src/views/Dashboard.vue
Normal file
158
FrontEnd/src/views/Dashboard.vue
Normal file
|
@ -0,0 +1,158 @@
|
||||||
|
<template>
|
||||||
|
<div class="min-h-full">
|
||||||
|
<Disclosure as="nav" class="bg-gray-800" v-slot="{ open }">
|
||||||
|
<div class="mx-auto max-w-7xl px-4 sm:px-6 lg:px-8">
|
||||||
|
<div class="flex h-16 items-center justify-between">
|
||||||
|
<div class="flex items-center">
|
||||||
|
<div class="flex-shrink-0">
|
||||||
|
<img class="h-8 w-8" src="https://tailwindui.com/img/logos/mark.svg?color=indigo&shade=500" alt="Your Company" />
|
||||||
|
</div>
|
||||||
|
<div class="hidden md:block">
|
||||||
|
<div class="ml-10 flex items-baseline space-x-4">
|
||||||
|
<a v-for="item in navigation" :key="item.name" :href="item.href" :class="[item.current ? 'bg-gray-900 text-white' : 'text-gray-300 hover:bg-gray-700 hover:text-white', 'rounded-md px-3 py-2 text-sm font-medium']" :aria-current="item.current ? 'page' : undefined">{{ item.name }}</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hidden md:block">
|
||||||
|
<div class="ml-4 flex items-center md:ml-6">
|
||||||
|
<button type="button" class="relative rounded-full bg-gray-800 p-1 text-gray-400 hover:text-white focus:outline-none focus:ring-2 focus:ring-white focus:ring-offset-2 focus:ring-offset-gray-800">
|
||||||
|
<span class="absolute -inset-1.5" />
|
||||||
|
<span class="sr-only">View notifications</span>
|
||||||
|
<BellIcon class="h-6 w-6" aria-hidden="true" />
|
||||||
|
</button>
|
||||||
|
|
||||||
|
<!-- Profile dropdown -->
|
||||||
|
<Menu as="div" class="relative ml-3">
|
||||||
|
<div>
|
||||||
|
<MenuButton class="relative flex max-w-xs items-center rounded-full bg-gray-800 text-sm focus:outline-none focus:ring-2 focus:ring-white focus:ring-offset-2 focus:ring-offset-gray-800">
|
||||||
|
<span class="absolute -inset-1.5" />
|
||||||
|
<span class="sr-only">打开用户菜单</span>
|
||||||
|
<img class="h-8 w-8 rounded-full" :src="user.imageUrl" alt="" />
|
||||||
|
</MenuButton>
|
||||||
|
</div>
|
||||||
|
<transition enter-active-class="transition ease-out duration-100" enter-from-class="transform opacity-0 scale-95" enter-to-class="transform opacity-100 scale-100" leave-active-class="transition ease-in duration-75" leave-from-class="transform opacity-100 scale-100" leave-to-class="transform opacity-0 scale-95">
|
||||||
|
<MenuItems class="absolute right-0 z-10 mt-2 w-48 origin-top-right rounded-md bg-white py-1 shadow-lg ring-1 ring-black ring-opacity-5 focus:outline-none">
|
||||||
|
<MenuItem v-for="item in userNavigation" :key="item.name" v-slot="{ active }">
|
||||||
|
<a :href="item.href" :class="[active ? 'bg-gray-100' : '', 'block px-4 py-2 text-sm text-gray-700']">{{ item.name }}</a>
|
||||||
|
</MenuItem>
|
||||||
|
</MenuItems>
|
||||||
|
</transition>
|
||||||
|
</Menu>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="-mr-2 flex md:hidden">
|
||||||
|
<!-- Mobile menu button -->
|
||||||
|
<DisclosureButton class="relative inline-flex items-center justify-center rounded-md bg-gray-800 p-2 text-gray-400 hover:bg-gray-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-white focus:ring-offset-2 focus:ring-offset-gray-800">
|
||||||
|
<span class="absolute -inset-0.5" />
|
||||||
|
<span class="sr-only">Open main menu</span>
|
||||||
|
<Bars3Icon v-if="!open" class="block h-6 w-6" aria-hidden="true" />
|
||||||
|
<XMarkIcon v-else class="block h-6 w-6" aria-hidden="true" />
|
||||||
|
</DisclosureButton>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<DisclosurePanel class="md:hidden">
|
||||||
|
<div class="space-y-1 px-2 pb-3 pt-2 sm:px-3">
|
||||||
|
<DisclosureButton v-for="item in navigation" :key="item.name" as="a" :href="item.href" :class="[item.current ? 'bg-gray-900 text-white' : 'text-gray-300 hover:bg-gray-700 hover:text-white', 'block rounded-md px-3 py-2 text-base font-medium']" :aria-current="item.current ? 'page' : undefined">{{ item.name }}</DisclosureButton>
|
||||||
|
</div>
|
||||||
|
<div class="border-t border-gray-700 pb-3 pt-4">
|
||||||
|
<div class="flex items-center px-5">
|
||||||
|
<div class="flex-shrink-0">
|
||||||
|
<img class="h-10 w-10 rounded-full" :src="user.imageUrl" alt="" />
|
||||||
|
</div>
|
||||||
|
<div class="ml-3">
|
||||||
|
<div class="text-base font-medium leading-none text-white">{{ user.name }}</div>
|
||||||
|
<div class="text-sm font-medium leading-none text-gray-400">{{ user.email }}</div>
|
||||||
|
</div>
|
||||||
|
<button type="button" class="relative ml-auto flex-shrink-0 rounded-full bg-gray-800 p-1 text-gray-400 hover:text-white focus:outline-none focus:ring-2 focus:ring-white focus:ring-offset-2 focus:ring-offset-gray-800">
|
||||||
|
<span class="absolute -inset-1.5" />
|
||||||
|
<span class="sr-only">View notifications</span>
|
||||||
|
<BellIcon class="h-6 w-6" aria-hidden="true" />
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
<div class="mt-3 space-y-1 px-2">
|
||||||
|
<DisclosureButton v-for="item in userNavigation" :key="item.name" as="a" :href="item.href" class="block rounded-md px-3 py-2 text-base font-medium text-gray-400 hover:bg-gray-700 hover:text-white">{{ item.name }}</DisclosureButton>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</DisclosurePanel>
|
||||||
|
</Disclosure>
|
||||||
|
|
||||||
|
<header class="bg-white shadow">
|
||||||
|
<div class="mx-auto max-w-7xl px-4 py-6 sm:px-6 lg:px-8">
|
||||||
|
<h1 class="text-3xl font-bold tracking-tight text-gray-900">控制面板</h1>
|
||||||
|
</div>
|
||||||
|
</header>
|
||||||
|
<main>
|
||||||
|
<div class="mx-auto max-w-7xl py-6 sm:px-6 lg:px-8 grid grid-cols-4">
|
||||||
|
<div class="max-w-7xl py-6 sm:px-3 lg:px-4 col-span-1">
|
||||||
|
<div class="block p-6 bg-white border border-gray-200 rounded-lg shadow dark:bg-gray-800 dark:border-gray-700">
|
||||||
|
<h5 class="mb-2 text-2xl font-bold tracking-tight text-gray-900 dark:text-white">宿舍网络状态</h5>
|
||||||
|
<div>获取IP地址:<span class="font-bold">{{ data.ip }}</span></div>
|
||||||
|
<div>是否登录:<span class="font-bold">是</span></div>
|
||||||
|
<div>登陆账号:<span class="font-bold">{{ data.uid }}</span></div>
|
||||||
|
<div>节点信息:<span class="font-bold">{{ data.type }}</span></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="mx-auto max-w-7xl py-6 sm:px-3 lg:px-4 col-span-3">
|
||||||
|
<div class="block p-6 bg-white border border-gray-200 rounded-lg shadow dark:bg-gray-800 dark:border-gray-700">
|
||||||
|
<div v-for="item in items" :key="item.id">
|
||||||
|
{{ item }}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</main>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup>
|
||||||
|
import { Disclosure, DisclosureButton, DisclosurePanel, Menu, MenuButton, MenuItem, MenuItems } from '@headlessui/vue'
|
||||||
|
import { Bars3Icon, BellIcon, XMarkIcon } from '@heroicons/vue/24/outline'
|
||||||
|
|
||||||
|
const user = {
|
||||||
|
name: 'Tom Cook',
|
||||||
|
email: 'tom@example.com',
|
||||||
|
imageUrl:
|
||||||
|
'https://images.unsplash.com/photo-1472099645785-5658abf4ff4e?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=facearea&facepad=2&w=256&h=256&q=80',
|
||||||
|
}
|
||||||
|
const navigation = [
|
||||||
|
{ name: '看板', href: '#', current: true },
|
||||||
|
{ name: '网盘', href: 'http://192.168.5.190:1000/', current: false },
|
||||||
|
]
|
||||||
|
const userNavigation = [
|
||||||
|
{ name: '个人信息', href: '#' },
|
||||||
|
{ name: '设置', href: '#' },
|
||||||
|
{ name: '登出', href: '#' },
|
||||||
|
]
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
import axios from 'axios';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
data: [], // 存储从接口获取的数据
|
||||||
|
};
|
||||||
|
},
|
||||||
|
mounted() {
|
||||||
|
// 在组件挂载后执行获取数据的操作
|
||||||
|
this.getDataFromApi();
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
getDataFromApi() {
|
||||||
|
// 使用 Axios 发送 GET 请求获取 JSON 接口数据
|
||||||
|
axios.get('http://localhost:8080/api/account/info')
|
||||||
|
.then(response => {
|
||||||
|
// 成功获取数据后更新组件的数据
|
||||||
|
this.data = response.data.data;
|
||||||
|
})
|
||||||
|
.catch(error => {
|
||||||
|
// 处理错误
|
||||||
|
console.error('Error fetching data:', error);
|
||||||
|
});
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
</script>
|
|
@ -1,59 +1,67 @@
|
||||||
<template>
|
<template>
|
||||||
<div class="bg-white">
|
<div class="bg-white">
|
||||||
<div class="mx-auto max-w-7xl py-24 sm:px-6 sm:py-32 lg:px-8">
|
<div class="mx-auto max-w-7xl py-24 sm:px-6 sm:py-32 lg:px-8">
|
||||||
<div class="relative isolate overflow-hidden bg-gray-900 px-6 pt-16 shadow-2xl sm:rounded-3xl sm:px-16 md:pt-24 lg:flex lg:gap-x-20 lg:px-24 lg:pt-0">
|
<div
|
||||||
<svg viewBox="0 0 1024 1024" class="absolute left-1/2 top-1/2 -z-10 h-[64rem] w-[64rem] -translate-y-1/2 [mask-image:radial-gradient(closest-side,white,transparent)] sm:left-full sm:-ml-80 lg:left-1/2 lg:ml-0 lg:-translate-x-1/2 lg:translate-y-0" aria-hidden="true">
|
class="relative isolate overflow-hidden bg-gray-900 px-6 pt-16 shadow-2xl sm:rounded-3xl sm:px-16 md:pt-24 lg:flex lg:gap-x-20 lg:px-24 lg:pt-0">
|
||||||
<circle cx="512" cy="512" r="512" fill="url(#759c1415-0410-454c-8f7c-9a820de03641)" fill-opacity="0.7" />
|
<svg viewBox="0 0 1024 1024"
|
||||||
<defs>
|
class="absolute left-1/2 top-1/2 -z-10 h-[64rem] w-[64rem] -translate-y-1/2 [mask-image:radial-gradient(closest-side,white,transparent)] sm:left-full sm:-ml-80 lg:left-1/2 lg:ml-0 lg:-translate-x-1/2 lg:translate-y-0"
|
||||||
<radialGradient id="759c1415-0410-454c-8f7c-9a820de03641">
|
aria-hidden="true">
|
||||||
<stop stop-color="#7775D6" />
|
<circle cx="512" cy="512" r="512" fill="url(#759c1415-0410-454c-8f7c-9a820de03641)" fill-opacity="0.7"/>
|
||||||
<stop offset="1" stop-color="#E935C1" />
|
<defs>
|
||||||
</radialGradient>
|
<radialGradient id="759c1415-0410-454c-8f7c-9a820de03641">
|
||||||
</defs>
|
<stop stop-color="#7775D6"/>
|
||||||
</svg>
|
<stop offset="1" stop-color="#E935C1"/>
|
||||||
<div class="mx-auto max-w-md text-center lg:mx-0 lg:flex-auto lg:py-32 lg:text-left">
|
</radialGradient>
|
||||||
<h2 class="text-3xl font-bold tracking-tight text-white sm:text-4xl">{{ data }}</h2>
|
</defs>
|
||||||
<p class="mt-6 text-lg leading-8 text-gray-300">Ac euismod vel sit maecenas id pellentesque eu sed consectetur. Malesuada adipiscing sagittis vel nulla.</p>
|
</svg>
|
||||||
<div class="mt-10 flex items-center justify-center gap-x-6 lg:justify-start">
|
<div class="mx-auto max-w-md text-center lg:mx-0 lg:flex-auto lg:py-32 lg:text-left">
|
||||||
<a href="#" class="rounded-md bg-white px-3.5 py-2.5 text-sm font-semibold text-gray-900 shadow-sm hover:bg-gray-100 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-white">Get started</a>
|
<h2 class="text-3xl font-bold tracking-tight text-white sm:text-4xl">{{ data.title }}</h2>
|
||||||
<a href="#" class="text-sm font-semibold leading-6 text-white">Learn more <span aria-hidden="true">→</span></a>
|
<p class="mt-6 text-lg leading-8 text-gray-300">{{ data.sub_title }}</p>
|
||||||
</div>
|
<div class="mt-10 flex items-center justify-center gap-x-6 lg:justify-start">
|
||||||
</div>
|
<a href="/sign/in"
|
||||||
<div class="relative mt-16 h-80 lg:mt-8">
|
class="rounded-md bg-white px-3.5 py-2.5 text-sm font-semibold text-gray-900 shadow-sm hover:bg-gray-100 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-white">
|
||||||
<img class="absolute left-0 top-0 w-[57rem] max-w-none rounded-md bg-white/5 ring-1 ring-white/10" src="https://tailwindui.com/img/component-images/dark-project-app-screenshot.png" alt="App screenshot" width="1824" height="1080" />
|
进入中心
|
||||||
</div>
|
</a>
|
||||||
</div>
|
<a href="#" class="text-sm font-semibold leading-6 text-white">了解更多 →</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
<div class="relative mt-16 h-80 lg:mt-8">
|
||||||
|
<img class="absolute left-0 top-0 w-[57rem] max-w-none rounded-md bg-white/5 ring-1 ring-white/10"
|
||||||
<script>
|
src="https://tailwindui.com/img/component-images/dark-project-app-screenshot.png" alt="App screenshot"
|
||||||
import axios from 'axios';
|
width="1824" height="1080"/>
|
||||||
|
</div>
|
||||||
export default {
|
</div>
|
||||||
data() {
|
</div>
|
||||||
return {
|
</div>
|
||||||
message: 'Hello from Vue!',
|
</template>
|
||||||
data: [], // 存储从接口获取的数据
|
|
||||||
};
|
<script>
|
||||||
},
|
import axios from 'axios';
|
||||||
mounted() {
|
|
||||||
// 在组件挂载后执行获取数据的操作
|
export default {
|
||||||
this.getDataFromApi();
|
data() {
|
||||||
},
|
return {
|
||||||
methods: {
|
message: 'Hello from Vue!',
|
||||||
getDataFromApi() {
|
data: [], // 存储从接口获取的数据
|
||||||
// 使用 Axios 发送 GET 请求获取 JSON 接口数据
|
};
|
||||||
axios.get('http://localhost:8080/api/account/info')
|
},
|
||||||
.then(response => {
|
mounted() {
|
||||||
// 成功获取数据后更新组件的数据
|
// 在组件挂载后执行获取数据的操作
|
||||||
this.data = response.data;
|
this.getDataFromApi();
|
||||||
})
|
},
|
||||||
.catch(error => {
|
methods: {
|
||||||
// 处理错误
|
getDataFromApi() {
|
||||||
console.error('Error fetching data:', error);
|
// 使用 Axios 发送 GET 请求获取 JSON 接口数据
|
||||||
});
|
axios.get('http://localhost:8080/api/info/data')
|
||||||
},
|
.then(response => {
|
||||||
},
|
// 成功获取数据后更新组件的数据
|
||||||
};
|
this.data = response.data.data;
|
||||||
</script>
|
})
|
||||||
|
.catch(error => {
|
||||||
|
// 处理错误
|
||||||
|
console.error('Error fetching data:', error);
|
||||||
|
});
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
|
@ -1,11 +1,90 @@
|
||||||
<script setup>
|
<template>
|
||||||
|
<div class="flex min-h-full flex-1 flex-col justify-center px-6 py-12 lg:px-8">
|
||||||
</script>
|
<div class="sm:mx-auto sm:w-full sm:max-w-sm">
|
||||||
|
<img alt="Your Company" class="mx-auto h-10 w-auto"
|
||||||
<template>
|
src="https://tailwindui.com/img/logos/mark.svg?color=indigo&shade=600"/>
|
||||||
|
<h2 class="mt-10 text-center text-2xl font-bold leading-9 tracking-tight text-gray-900">
|
||||||
</template>
|
DormStar - 登录
|
||||||
|
</h2>
|
||||||
<style scoped>
|
</div>
|
||||||
|
|
||||||
</style>
|
<div class="mt-10 sm:mx-auto sm:w-full sm:max-w-sm">
|
||||||
|
<form action="#" class="space-y-6" method="POST">
|
||||||
|
<div>
|
||||||
|
<label class="block text-sm font-medium leading-6 text-gray-900" for="email">邮箱</label>
|
||||||
|
<div class="mt-2">
|
||||||
|
<input id="user" autocomplete="user"
|
||||||
|
class="block w-full rounded-md border-0 py-1.5 text-gray-900 shadow-sm ring-1 ring-inset ring-gray-300 placeholder:text-gray-400 focus:ring-2 focus:ring-inset focus:ring-indigo-600 sm:text-sm sm:leading-6"
|
||||||
|
name="user" required=""
|
||||||
|
type="text"/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<div class="flex items-center justify-between">
|
||||||
|
<label class="block text-sm font-medium leading-6 text-gray-900" for="password">密码</label>
|
||||||
|
<div class="text-sm">
|
||||||
|
<a class="font-semibold text-indigo-600 hover:text-indigo-500" href="/sign/reset">忘记密码</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="mt-2">
|
||||||
|
<input id="password" autocomplete="current-password"
|
||||||
|
class="block w-full rounded-md border-0 py-1.5 text-gray-900 shadow-sm ring-1 ring-inset ring-gray-300 placeholder:text-gray-400 focus:ring-2 focus:ring-inset focus:ring-indigo-600 sm:text-sm sm:leading-6"
|
||||||
|
name="password" required=""
|
||||||
|
type="password"/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<button
|
||||||
|
class="flex w-full justify-center rounded-md bg-indigo-600 px-3 py-1.5 text-sm font-semibold leading-6 text-white shadow-sm hover:bg-indigo-500 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-indigo-600"
|
||||||
|
type="submit">
|
||||||
|
登录
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
|
||||||
|
<p class="mt-10 text-center text-sm text-gray-500">
|
||||||
|
还没有账号?
|
||||||
|
<a class="font-semibold leading-6 text-indigo-600 hover:text-indigo-500" href="#">注册一个!</a>
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
import axios from 'axios';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
data: [], // 存储从接口获取的数据
|
||||||
|
};
|
||||||
|
},
|
||||||
|
mounted() {
|
||||||
|
// 在组件挂载后执行获取数据的操作
|
||||||
|
this.getDataFromApi();
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
getDataFromApi() {
|
||||||
|
// 使用 Axios 发送 GET 请求获取 JSON 接口数据
|
||||||
|
axios.get('http://localhost:8080/api/user/sign/in')
|
||||||
|
.then(response => {
|
||||||
|
// 成功获取数据后更新组件的数据
|
||||||
|
this.data = response.data;
|
||||||
|
if (this.data.output === "SuccessCreate") {
|
||||||
|
// 设置Cookie的过期时间为12小时
|
||||||
|
const expireDate = new Date();
|
||||||
|
expireDate.setTime(expireDate.getTime() + 43200000);
|
||||||
|
// 使用document.cookie创建Cookie
|
||||||
|
document.cookie = `session=${this.data.data}; expires=${expireDate.toUTCString()}; path=/`;
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(error => {
|
||||||
|
// 处理错误
|
||||||
|
console.error('Error fetching data:', error);
|
||||||
|
});
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
</script>
|
|
@ -1,11 +1,107 @@
|
||||||
<script setup>
|
<template>
|
||||||
|
<div class="flex min-h-full flex-1 flex-col justify-center px-6 py-12 lg:px-8">
|
||||||
</script>
|
<div class="sm:mx-auto sm:w-full sm:max-w-sm">
|
||||||
|
<img alt="Your Company" class="mx-auto h-10 w-auto"
|
||||||
<template>
|
src="https://tailwindui.com/img/logos/mark.svg?color=indigo&shade=600"/>
|
||||||
|
<h2 class="mt-10 text-center text-2xl font-bold leading-9 tracking-tight text-gray-900">
|
||||||
</template>
|
DormStar - 注册
|
||||||
|
</h2>
|
||||||
<style scoped>
|
</div>
|
||||||
|
|
||||||
</style>
|
<div class="mt-10 sm:mx-auto sm:w-full sm:max-w-sm">
|
||||||
|
<form action="#" class="space-y-6" method="POST">
|
||||||
|
<div>
|
||||||
|
<label class="block text-sm font-medium leading-6 text-gray-900" for="email">邮箱</label>
|
||||||
|
<div class="mt-2">
|
||||||
|
<input id="user" autocomplete="user"
|
||||||
|
class="block w-full rounded-md border-0 py-1.5 text-gray-900 shadow-sm ring-1 ring-inset ring-gray-300 placeholder:text-gray-400 focus:ring-2 focus:ring-inset focus:ring-indigo-600 sm:text-sm sm:leading-6"
|
||||||
|
name="user" required=""
|
||||||
|
type="text"/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<label class="block text-sm font-medium leading-6 text-gray-900" for="email">昵称</label>
|
||||||
|
<div class="mt-2">
|
||||||
|
<input id="user" autocomplete="user"
|
||||||
|
class="block w-full rounded-md border-0 py-1.5 text-gray-900 shadow-sm ring-1 ring-inset ring-gray-300 placeholder:text-gray-400 focus:ring-2 focus:ring-inset focus:ring-indigo-600 sm:text-sm sm:leading-6"
|
||||||
|
name="user" required=""
|
||||||
|
type="text"/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<label class="block text-sm font-medium leading-6 text-gray-900" for="email">电话</label>
|
||||||
|
<div class="mt-2">
|
||||||
|
<input id="user" autocomplete="user"
|
||||||
|
class="block w-full rounded-md border-0 py-1.5 text-gray-900 shadow-sm ring-1 ring-inset ring-gray-300 placeholder:text-gray-400 focus:ring-2 focus:ring-inset focus:ring-indigo-600 sm:text-sm sm:leading-6"
|
||||||
|
name="user" required=""
|
||||||
|
type="text"/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<div class="flex items-center justify-between">
|
||||||
|
<label class="block text-sm font-medium leading-6 text-gray-900" for="password">密码</label>
|
||||||
|
<div class="text-sm">
|
||||||
|
<a class="font-semibold text-indigo-600 hover:text-indigo-500" href="/sign/reset">忘记密码</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="mt-2">
|
||||||
|
<input id="password" autocomplete="current-password"
|
||||||
|
class="block w-full rounded-md border-0 py-1.5 text-gray-900 shadow-sm ring-1 ring-inset ring-gray-300 placeholder:text-gray-400 focus:ring-2 focus:ring-inset focus:ring-indigo-600 sm:text-sm sm:leading-6"
|
||||||
|
name="password" required=""
|
||||||
|
type="password"/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<button
|
||||||
|
class="flex w-full justify-center rounded-md bg-indigo-600 px-3 py-1.5 text-sm font-semibold leading-6 text-white shadow-sm hover:bg-indigo-500 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-indigo-600"
|
||||||
|
type="submit">
|
||||||
|
注册
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
|
||||||
|
<p class="mt-10 text-center text-sm text-gray-500">
|
||||||
|
我已经有账号了
|
||||||
|
<a class="font-semibold leading-6 text-indigo-600 hover:text-indigo-500" href="/sign/in">登陆!</a>
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
import axios from 'axios';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
data: [], // 存储从接口获取的数据
|
||||||
|
};
|
||||||
|
},
|
||||||
|
mounted() {
|
||||||
|
// 在组件挂载后执行获取数据的操作
|
||||||
|
this.getDataFromApi();
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
getDataFromApi() {
|
||||||
|
// 使用 Axios 发送 GET 请求获取 JSON 接口数据
|
||||||
|
axios.get('http://localhost:8080/api/user/sign/in')
|
||||||
|
.then(response => {
|
||||||
|
// 成功获取数据后更新组件的数据
|
||||||
|
this.data = response.data;
|
||||||
|
if (this.data.output === "SuccessCreate") {
|
||||||
|
// 设置Cookie的过期时间为12小时
|
||||||
|
const expireDate = new Date();
|
||||||
|
expireDate.setTime(expireDate.getTime() + 43200000);
|
||||||
|
// 使用document.cookie创建Cookie
|
||||||
|
document.cookie = `session=${this.data.data}; expires=${expireDate.toUTCString()}; path=/`;
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(error => {
|
||||||
|
// 处理错误
|
||||||
|
console.error('Error fetching data:', error);
|
||||||
|
});
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
</script>
|
|
@ -7,4 +7,5 @@ INSERT INTO ds_info (value, data, commit) VALUES
|
||||||
('sub_title', '我们的宿舍', '网站副标题'),
|
('sub_title', '我们的宿舍', '网站副标题'),
|
||||||
('register', true, '是否允许注册'),
|
('register', true, '是否允许注册'),
|
||||||
('autoLogin', true, '是否允许自动登录'),
|
('autoLogin', true, '是否允许自动登录'),
|
||||||
('schoolLoginAddress', 'http://10.1.99.100:801/', '校园登录IP地址')
|
('schoolLoginAddress', '10.1.99.100', '校园登录IP地址'),
|
||||||
|
('schoolLoginPort', '801', '校园网登录接口端口')
|
|
@ -1,19 +1,19 @@
|
||||||
package com.xlf.dromstarkotlin.config
|
package com.xlf.dromstarkotlin.config
|
||||||
|
|
||||||
import org.springframework.context.annotation.Configuration
|
import org.springframework.context.annotation.Configuration
|
||||||
import org.springframework.web.servlet.config.annotation.CorsRegistry
|
import org.springframework.web.servlet.config.annotation.CorsRegistry
|
||||||
|
|
||||||
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer
|
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer
|
||||||
|
|
||||||
|
|
||||||
@Configuration
|
@Configuration
|
||||||
class CorsConfiguration : WebMvcConfigurer {
|
class CorsConfiguration : WebMvcConfigurer {
|
||||||
override fun addCorsMappings(registry: CorsRegistry) {
|
override fun addCorsMappings(registry: CorsRegistry) {
|
||||||
registry.addMapping("/**") //是否发送Cookie
|
registry.addMapping("/**") //是否发送Cookie
|
||||||
.allowCredentials(true) //放行哪些原始域
|
.allowCredentials(true) //放行哪些原始域
|
||||||
.allowedOriginPatterns("*")
|
.allowedOriginPatterns("*")
|
||||||
.allowedMethods(*arrayOf("GET", "POST", "PUT", "DELETE"))
|
.allowedMethods(*arrayOf("GET", "POST", "PUT", "DELETE"))
|
||||||
.allowedHeaders("*")
|
.allowedHeaders("*")
|
||||||
.exposedHeaders("*")
|
.exposedHeaders("*")
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -23,10 +23,17 @@ class AccountController(
|
||||||
.also { it.find() }
|
.also { it.find() }
|
||||||
val matcherType = Pattern.compile("[a-z]+$").matcher(getMap?.get("uid").toString())
|
val matcherType = Pattern.compile("[a-z]+$").matcher(getMap?.get("uid").toString())
|
||||||
.also { it.find() }
|
.also { it.find() }
|
||||||
hashMap["ip"] = getMap?.get("v46ip")
|
try {
|
||||||
hashMap["time"] = getMap?.get("time")
|
hashMap["ip"] = getMap?.get("v46ip")
|
||||||
hashMap["uid"] = matcherUid.group(0)
|
hashMap["time"] = getMap?.get("time")
|
||||||
hashMap["type"] = matcherType.group(0)
|
hashMap["uid"] = matcherUid.group(0)
|
||||||
|
hashMap["type"] = matcherType.group(0)
|
||||||
|
} catch (e: IllegalStateException) {
|
||||||
|
hashMap["ip"] = getMap?.get("v46ip")
|
||||||
|
hashMap["time"] = null
|
||||||
|
hashMap["uid"] = matcherUid.group(0)
|
||||||
|
hashMap["type"] = null
|
||||||
|
}
|
||||||
return ResultUtil.success(hashMap, httpServletRequest)
|
return ResultUtil.success(hashMap, httpServletRequest)
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -0,0 +1,24 @@
|
||||||
|
package com.xlf.dromstarkotlin.controllers
|
||||||
|
|
||||||
|
import com.frontleaves.general.utils.BaseResponse
|
||||||
|
import com.xlf.dromstarkotlin.services.InfoService
|
||||||
|
import jakarta.servlet.http.HttpServletRequest
|
||||||
|
import org.springframework.http.ResponseEntity
|
||||||
|
import org.springframework.web.bind.annotation.GetMapping
|
||||||
|
import org.springframework.web.bind.annotation.RequestMapping
|
||||||
|
import org.springframework.web.bind.annotation.RestController
|
||||||
|
|
||||||
|
@RestController
|
||||||
|
@RequestMapping("/api/info")
|
||||||
|
class InfoController(
|
||||||
|
val infoService: InfoService
|
||||||
|
) {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取内容
|
||||||
|
*/
|
||||||
|
@GetMapping("/data")
|
||||||
|
fun getWebInfo(httpServletRequest: HttpServletRequest): ResponseEntity<BaseResponse> {
|
||||||
|
return infoService.getWebInfo(httpServletRequest)
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
package com.xlf.dromstarkotlin.controllers
|
||||||
|
|
||||||
|
import com.frontleaves.general.utils.BaseResponse
|
||||||
|
import com.frontleaves.general.utils.ErrorCode
|
||||||
|
import com.frontleaves.general.utils.ResultUtil
|
||||||
|
import com.xlf.dromstarkotlin.services.LogService
|
||||||
|
import jakarta.servlet.http.HttpServletRequest
|
||||||
|
import jakarta.servlet.http.HttpServletResponse
|
||||||
|
import org.springframework.http.ResponseEntity
|
||||||
|
import org.springframework.web.bind.annotation.CookieValue
|
||||||
|
import org.springframework.web.bind.annotation.GetMapping
|
||||||
|
import org.springframework.web.bind.annotation.RequestMapping
|
||||||
|
import org.springframework.web.bind.annotation.RestController
|
||||||
|
|
||||||
|
@RestController
|
||||||
|
@RequestMapping("/api/log")
|
||||||
|
class LogController(
|
||||||
|
val logService: LogService
|
||||||
|
) {
|
||||||
|
|
||||||
|
@GetMapping("/auto-login")
|
||||||
|
fun getAutoLoginLog(
|
||||||
|
@CookieValue("session") token: String?,
|
||||||
|
httpServletRequest: HttpServletRequest,
|
||||||
|
httpServletResponse: HttpServletResponse
|
||||||
|
): ResponseEntity<BaseResponse>? {
|
||||||
|
// token 存在鉴权
|
||||||
|
return if (token != null) {
|
||||||
|
logService.getAutoLoginLog(token, httpServletRequest, httpServletResponse)
|
||||||
|
} else {
|
||||||
|
ResultUtil.error(ErrorCode.TOKEN_NOT_FOUNDED, httpServletRequest)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -7,16 +7,10 @@ import jakarta.servlet.http.Cookie
|
||||||
import jakarta.servlet.http.HttpServletRequest
|
import jakarta.servlet.http.HttpServletRequest
|
||||||
import jakarta.servlet.http.HttpServletResponse
|
import jakarta.servlet.http.HttpServletResponse
|
||||||
import org.springframework.http.ResponseEntity
|
import org.springframework.http.ResponseEntity
|
||||||
import org.springframework.web.bind.annotation.CookieValue
|
import org.springframework.web.bind.annotation.*
|
||||||
import org.springframework.web.bind.annotation.CrossOrigin
|
|
||||||
import org.springframework.web.bind.annotation.GetMapping
|
|
||||||
import org.springframework.web.bind.annotation.RequestMapping
|
|
||||||
import org.springframework.web.bind.annotation.RequestParam
|
|
||||||
import org.springframework.web.bind.annotation.RestController
|
|
||||||
|
|
||||||
@RestController
|
@RestController
|
||||||
@RequestMapping("/api/token")
|
@RequestMapping("/api/token")
|
||||||
@CrossOrigin(origins = ["*"])
|
|
||||||
class TokenController(
|
class TokenController(
|
||||||
private val tokenService: TokenService
|
private val tokenService: TokenService
|
||||||
) {
|
) {
|
||||||
|
@ -25,28 +19,21 @@ class TokenController(
|
||||||
*/
|
*/
|
||||||
@GetMapping("/create")
|
@GetMapping("/create")
|
||||||
fun createToken(
|
fun createToken(
|
||||||
@CookieValue("session") token: String?, httpServletResponse: HttpServletResponse,
|
@CookieValue("session") token: String?,
|
||||||
|
httpServletResponse: HttpServletResponse,
|
||||||
@RequestParam("return") returnLink: String?,
|
@RequestParam("return") returnLink: String?,
|
||||||
httpServletRequest: HttpServletRequest
|
httpServletRequest: HttpServletRequest
|
||||||
): ResponseEntity<BaseResponse> {
|
): ResponseEntity<BaseResponse> {
|
||||||
// 检查 token 是否存在
|
// 检查 token 是否存在
|
||||||
return if (token == null) {
|
return if (token == null) {
|
||||||
val newToken = tokenService.tokenCreate(httpServletRequest)
|
val newToken = tokenService.tokenCreate(httpServletRequest)
|
||||||
httpServletResponse.addCookie(
|
httpServletResponse.addCookie(Cookie("session", newToken).also { it.path = "/" }.also { it.maxAge = 43200 })
|
||||||
Cookie("session", newToken)
|
|
||||||
.also { it.path = "/" }
|
|
||||||
.also { it.maxAge = 43200 }
|
|
||||||
)
|
|
||||||
ResultUtil.redirect("SuccessCreate", "Token创建成功", newToken, returnLink, httpServletRequest)
|
ResultUtil.redirect("SuccessCreate", "Token创建成功", newToken, returnLink, httpServletRequest)
|
||||||
} else {
|
} else {
|
||||||
if (tokenService.tokenVerify(token, httpServletResponse)) {
|
if (tokenService.tokenVerify(token, httpServletResponse)) {
|
||||||
ResultUtil.redirect("StillValid", "Token依旧有效", null, returnLink, httpServletRequest)
|
ResultUtil.redirect("StillValid", "Token依旧有效", null, returnLink, httpServletRequest)
|
||||||
} else {
|
} else {
|
||||||
httpServletResponse.addCookie(
|
httpServletResponse.addCookie(Cookie("session", null).also { it.path = "/" }.also { it.maxAge = 0 })
|
||||||
Cookie("session", null)
|
|
||||||
.also { it.path = "/" }
|
|
||||||
.also { it.maxAge = 0 }
|
|
||||||
)
|
|
||||||
this.createToken(null, httpServletResponse, returnLink, httpServletRequest)
|
this.createToken(null, httpServletResponse, returnLink, httpServletRequest)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -12,12 +12,8 @@ import com.xlf.dromstarkotlin.services.UserService
|
||||||
import jakarta.servlet.http.HttpServletRequest
|
import jakarta.servlet.http.HttpServletRequest
|
||||||
import jakarta.servlet.http.HttpServletResponse
|
import jakarta.servlet.http.HttpServletResponse
|
||||||
import org.springframework.http.ResponseEntity
|
import org.springframework.http.ResponseEntity
|
||||||
import org.springframework.web.bind.annotation.CookieValue
|
import org.springframework.web.bind.annotation.*
|
||||||
import org.springframework.web.bind.annotation.GetMapping
|
import java.util.*
|
||||||
import org.springframework.web.bind.annotation.RequestBody
|
|
||||||
import org.springframework.web.bind.annotation.RequestMapping
|
|
||||||
import org.springframework.web.bind.annotation.RestController
|
|
||||||
import java.util.Date
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 用户控制器
|
* 用户控制器
|
||||||
|
@ -39,7 +35,9 @@ class UserController(
|
||||||
*/
|
*/
|
||||||
@GetMapping("/sign/in")
|
@GetMapping("/sign/in")
|
||||||
fun signIn(
|
fun signIn(
|
||||||
@RequestBody signInVO: SignInVO?, @CookieValue("session") token: String?, httpServletResponse: HttpServletResponse,
|
@RequestBody signInVO: SignInVO?,
|
||||||
|
@CookieValue("session") token: String?,
|
||||||
|
httpServletResponse: HttpServletResponse,
|
||||||
httpServletRequest: HttpServletRequest
|
httpServletRequest: HttpServletRequest
|
||||||
): ResponseEntity<BaseResponse> {
|
): ResponseEntity<BaseResponse> {
|
||||||
// 判断请求体是否为空
|
// 判断请求体是否为空
|
||||||
|
@ -72,7 +70,9 @@ class UserController(
|
||||||
*/
|
*/
|
||||||
@GetMapping("/sign/up")
|
@GetMapping("/sign/up")
|
||||||
fun signUp(
|
fun signUp(
|
||||||
@RequestBody signUpVO: SignUpVO?, @CookieValue("session") token: String?, httpServletResponse: HttpServletResponse,
|
@RequestBody signUpVO: SignUpVO?,
|
||||||
|
@CookieValue("session") token: String?,
|
||||||
|
httpServletResponse: HttpServletResponse,
|
||||||
httpServletRequest: HttpServletRequest
|
httpServletRequest: HttpServletRequest
|
||||||
): ResponseEntity<BaseResponse> {
|
): ResponseEntity<BaseResponse> {
|
||||||
// 检查是否允许注册
|
// 检查是否允许注册
|
||||||
|
@ -103,4 +103,26 @@ class UserController(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取用户信息组件
|
||||||
|
*/
|
||||||
|
fun getUserCurrent(
|
||||||
|
@CookieValue("session") token: String?, httpServletRequest: HttpServletRequest, httpServletResponse: HttpServletResponse
|
||||||
|
): ResponseEntity<BaseResponse> {
|
||||||
|
return if (token!= null) {
|
||||||
|
// 对 token 进行校验
|
||||||
|
if (!tokenService.tokenVerify(token, httpServletResponse)) {
|
||||||
|
// 校验失败
|
||||||
|
BusinessException().backInfo(ErrorCode.TOKEN_VERIFY_FAILED, httpServletRequest)
|
||||||
|
} else {
|
||||||
|
// 获取当前用户信息
|
||||||
|
userService.getUserCurrent(token, httpServletRequest)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// 跳转至创建 Token 页面
|
||||||
|
ResultUtil.redirect("/api/token/create", httpServletRequest)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
|
@ -1,13 +1,13 @@
|
||||||
package com.xlf.dromstarkotlin.controllers
|
package com.xlf.dromstarkotlin.controllers
|
||||||
|
|
||||||
import org.springframework.stereotype.Controller
|
import org.springframework.stereotype.Controller
|
||||||
import org.springframework.web.bind.annotation.PathVariable
|
import org.springframework.web.bind.annotation.PathVariable
|
||||||
import org.springframework.web.bind.annotation.RequestMapping
|
import org.springframework.web.bind.annotation.RequestMapping
|
||||||
|
|
||||||
@Controller
|
@Controller
|
||||||
class ViewController {
|
class ViewController {
|
||||||
@RequestMapping("/{path:[^.]*}")
|
@RequestMapping("/{path:[^.]*}/")
|
||||||
fun forward(@PathVariable path: String): String? {
|
fun forward(@PathVariable path: String): String? {
|
||||||
return "forward:/index.html"
|
return "forward:/index.html"
|
||||||
}
|
}
|
||||||
}
|
}
|
8
src/main/kotlin/com/xlf/dromstarkotlin/entity/InfoDO.kt
Normal file
8
src/main/kotlin/com/xlf/dromstarkotlin/entity/InfoDO.kt
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
package com.xlf.dromstarkotlin.entity
|
||||||
|
|
||||||
|
data class InfoDO (
|
||||||
|
val id: Int,
|
||||||
|
val value: String,
|
||||||
|
val data: String? = null,
|
||||||
|
val commit: String,
|
||||||
|
)
|
|
@ -1,5 +1,6 @@
|
||||||
package com.xlf.dromstarkotlin.mapper
|
package com.xlf.dromstarkotlin.mapper
|
||||||
|
|
||||||
|
import com.xlf.dromstarkotlin.entity.InfoDO
|
||||||
import org.apache.ibatis.annotations.Mapper
|
import org.apache.ibatis.annotations.Mapper
|
||||||
import org.apache.ibatis.annotations.Select
|
import org.apache.ibatis.annotations.Select
|
||||||
|
|
||||||
|
@ -14,4 +15,10 @@ interface InfoMapper {
|
||||||
|
|
||||||
@Select("SELECT * FROM ds_info WHERE value = 'autoLogin'")
|
@Select("SELECT * FROM ds_info WHERE value = 'autoLogin'")
|
||||||
fun autoLogin(): Boolean
|
fun autoLogin(): Boolean
|
||||||
|
|
||||||
|
@Select("SELECT * FROM ds_info WHERE value = 'title'")
|
||||||
|
fun getTitle(): InfoDO
|
||||||
|
|
||||||
|
@Select("SELECT * FROM ds_info WHERE value = 'sub_title'")
|
||||||
|
fun getSubTitle(): InfoDO
|
||||||
}
|
}
|
11
src/main/kotlin/com/xlf/dromstarkotlin/mapper/LogMapper.kt
Normal file
11
src/main/kotlin/com/xlf/dromstarkotlin/mapper/LogMapper.kt
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
package com.xlf.dromstarkotlin.mapper
|
||||||
|
|
||||||
|
import org.apache.ibatis.annotations.Mapper
|
||||||
|
import org.apache.ibatis.annotations.Select
|
||||||
|
|
||||||
|
@Mapper
|
||||||
|
interface LogMapper {
|
||||||
|
|
||||||
|
@Select("SELECT * FROM ds_login_log ORDER BY id DESC LIMIT 50")
|
||||||
|
fun getAutoLoginLog(): String
|
||||||
|
}
|
|
@ -83,7 +83,7 @@ class AccountService(
|
||||||
.build()
|
.build()
|
||||||
try {
|
try {
|
||||||
val response = okHttpClient.newCall(request).execute()
|
val response = okHttpClient.newCall(request).execute()
|
||||||
val matcher = Pattern.compile("dr1003\\(([^)]+)\\)").matcher(response.body!!.string())
|
val matcher = Pattern.compile("dr1002\\(([^)]+)\\)").matcher(response.body!!.string())
|
||||||
matcher.find()
|
matcher.find()
|
||||||
val getResponseBody = Gson().fromJson(matcher.group(1), HashMap::class.java)
|
val getResponseBody = Gson().fromJson(matcher.group(1), HashMap::class.java)
|
||||||
if (getResponseBody["result"] == "1") {
|
if (getResponseBody["result"] == "1") {
|
||||||
|
|
|
@ -0,0 +1,25 @@
|
||||||
|
package com.xlf.dromstarkotlin.services
|
||||||
|
|
||||||
|
import com.frontleaves.general.utils.BaseResponse
|
||||||
|
import com.frontleaves.general.utils.ResultUtil
|
||||||
|
import com.xlf.dromstarkotlin.mapper.InfoMapper
|
||||||
|
import jakarta.servlet.http.HttpServletRequest
|
||||||
|
import org.springframework.http.ResponseEntity
|
||||||
|
import org.springframework.stereotype.Service
|
||||||
|
|
||||||
|
@Service
|
||||||
|
class InfoService(
|
||||||
|
val infoMapper: InfoMapper
|
||||||
|
) {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取内容
|
||||||
|
*/
|
||||||
|
fun getWebInfo(httpServletRequest: HttpServletRequest): ResponseEntity<BaseResponse> {
|
||||||
|
val hashMap = HashMap<String, Any?>()
|
||||||
|
hashMap["title"] = infoMapper.getTitle().data
|
||||||
|
hashMap["sub_title"] = infoMapper.getSubTitle().data
|
||||||
|
return ResultUtil.success(hashMap, httpServletRequest)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,30 @@
|
||||||
|
package com.xlf.dromstarkotlin.services
|
||||||
|
|
||||||
|
import com.frontleaves.general.utils.BaseResponse
|
||||||
|
import com.frontleaves.general.utils.ErrorCode
|
||||||
|
import com.frontleaves.general.utils.ResultUtil
|
||||||
|
import com.xlf.dromstarkotlin.mapper.LogMapper
|
||||||
|
import jakarta.servlet.http.HttpServletRequest
|
||||||
|
import jakarta.servlet.http.HttpServletResponse
|
||||||
|
import org.springframework.http.ResponseEntity
|
||||||
|
import org.springframework.stereotype.Service
|
||||||
|
|
||||||
|
@Service
|
||||||
|
class LogService(
|
||||||
|
val tokenService: TokenService,
|
||||||
|
val logMapper: LogMapper
|
||||||
|
) {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取自动登录日志
|
||||||
|
*/
|
||||||
|
fun getAutoLoginLog(token: String, httpServletRequest: HttpServletRequest, httpServletResponse: HttpServletResponse): ResponseEntity<BaseResponse>? {
|
||||||
|
// token 鉴权
|
||||||
|
return if (tokenService.tokenVerify(token, httpServletResponse)) {
|
||||||
|
// 获取自动登录日志
|
||||||
|
ResultUtil.success(logMapper.getAutoLoginLog(), httpServletRequest)
|
||||||
|
} else {
|
||||||
|
ResultUtil.error(ErrorCode.TOKEN_NOT_FOUNDED, httpServletRequest)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -49,7 +49,7 @@ class ScheduleService(
|
||||||
/**
|
/**
|
||||||
* 登录校园网(5分钟自动检查)
|
* 登录校园网(5分钟自动检查)
|
||||||
*/
|
*/
|
||||||
@Scheduled(fixedDelay = 300000)
|
@Scheduled(fixedDelay = 60000)
|
||||||
fun schoolLogin() {
|
fun schoolLogin() {
|
||||||
if (CacheData.autoLogin) {
|
if (CacheData.autoLogin) {
|
||||||
val calendar = Calendar.getInstance()
|
val calendar = Calendar.getInstance()
|
||||||
|
@ -64,12 +64,13 @@ class ScheduleService(
|
||||||
accountService.regularLogin()
|
accountService.regularLogin()
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// 切换校园网
|
if (accountService.getInformation()?.get("type") != null) {
|
||||||
do {
|
do {
|
||||||
accountService.regularLogout()
|
accountService.regularLogout()
|
||||||
Thread.sleep(5000)
|
Thread.sleep(5000)
|
||||||
} while (accountService.getInformation()?.get("uid") == null)
|
accountService.switchTheCampusNetwork()
|
||||||
accountService.switchTheCampusNetwork()
|
} while (accountService.getInformation()?.get("uid") == null)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (hour in 7 .. 23) {
|
if (hour in 7 .. 23) {
|
||||||
|
@ -80,11 +81,13 @@ class ScheduleService(
|
||||||
}
|
}
|
||||||
} else{
|
} else{
|
||||||
// 切换校园网
|
// 切换校园网
|
||||||
do {
|
if (accountService.getInformation()?.get("type") != null) {
|
||||||
accountService.regularLogout()
|
do {
|
||||||
Thread.sleep(5000)
|
accountService.regularLogout()
|
||||||
} while (accountService.getInformation()?.get("uid") == null)
|
Thread.sleep(5000)
|
||||||
accountService.switchTheCampusNetwork()
|
accountService.switchTheCampusNetwork()
|
||||||
|
} while (accountService.getInformation()?.get("uid") == null)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -81,4 +81,8 @@ class UserService(
|
||||||
return ResultUtil.error(ErrorCode.USER_EXIST, httpServletRequest)
|
return ResultUtil.error(ErrorCode.USER_EXIST, httpServletRequest)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun getUserCurrent(token: String, httpServletRequest: HttpServletRequest): ResponseEntity<BaseResponse> {
|
||||||
|
TODO("Not yet implemented")
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -1,6 +1,6 @@
|
||||||
server:
|
server:
|
||||||
port: 8080
|
port: 8080
|
||||||
spring:
|
spring:
|
||||||
web:
|
web:
|
||||||
resources:
|
resources:
|
||||||
static-locations: classpath:/META-INF/resources/,classpath:/resources/,classpath:/static/,classpath:/public/,classpath:/static/frontend/
|
static-locations: classpath:/META-INF/resources/,classpath:/resources/,classpath:/static/,classpath:/public/,classpath:/static/frontend/
|
Loading…
Reference in New Issue
Block a user