1
0
mirror of https://github.com/1Panel-dev/1Panel.git synced 2025-01-19 16:29:17 +08:00

feat: 增加设置默认网站功能

This commit is contained in:
zhengkunwang223 2023-01-03 16:56:36 +08:00 committed by zhengkunwang223
parent 6d290f6a73
commit 869f552cf8
16 changed files with 189 additions and 26 deletions

View File

@ -2,7 +2,7 @@
"formFields": [ "formFields": [
{ {
"type": "password", "type": "password",
"labelZh": "Root用户密码", "labelZh": "root用户密码",
"labelEn": "RootPassword", "labelEn": "RootPassword",
"required": true, "required": true,
"default": "random", "default": "random",

View File

@ -2,7 +2,7 @@
"formFields": [ "formFields": [
{ {
"type": "password", "type": "password",
"labelZh": "Root用户密码", "labelZh": "root用户密码",
"labelEn": "RootPassword", "labelEn": "RootPassword",
"required": true, "required": true,
"default": "random", "default": "random",

View File

@ -26,6 +26,15 @@ func (b *BaseApi) PageWebsite(c *gin.Context) {
}) })
} }
func (b *BaseApi) GetWebsites(c *gin.Context) {
websites, err := websiteService.GetWebsites()
if err != nil {
helper.ErrorWithDetail(c, constant.CodeErrInternalServer, constant.ErrTypeInternalServer, err)
return
}
helper.SuccessWithData(c, websites)
}
func (b *BaseApi) GetWebsiteOptions(c *gin.Context) { func (b *BaseApi) GetWebsiteOptions(c *gin.Context) {
websites, err := websiteService.GetWebsiteOptions() websites, err := websiteService.GetWebsiteOptions()
if err != nil { if err != nil {
@ -334,3 +343,16 @@ func (b *BaseApi) OpWebsiteLog(c *gin.Context) {
} }
helper.SuccessWithData(c, res) helper.SuccessWithData(c, res)
} }
func (b *BaseApi) ChangeDefaultServer(c *gin.Context) {
var req request.WebsiteDefaultUpdate
if err := c.ShouldBindJSON(&req); err != nil {
helper.ErrorWithDetail(c, constant.CodeErrBadRequest, constant.ErrTypeInvalidParams, err)
return
}
if err := websiteService.ChangeDefaultServer(req.ID); err != nil {
helper.ErrorWithDetail(c, constant.CodeErrInternalServer, constant.ErrTypeInternalServer, err)
return
}
helper.SuccessWithData(c, nil)
}

View File

@ -122,3 +122,7 @@ type WebsiteLogReq struct {
Operate string `json:"operate" validate:"required"` Operate string `json:"operate" validate:"required"`
LogType string `json:"logType" validate:"required"` LogType string `json:"logType" validate:"required"`
} }
type WebsiteDefaultUpdate struct {
ID uint `json:"id" validate:"required"`
}

View File

@ -18,6 +18,7 @@ type Website struct {
Proxy string `gorm:"type:varchar(128);not null" json:"proxy"` Proxy string `gorm:"type:varchar(128);not null" json:"proxy"`
ErrorLog bool `json:"errorLog"` ErrorLog bool `json:"errorLog"`
AccessLog bool `json:"accessLog"` AccessLog bool `json:"accessLog"`
DefaultServer bool `json:"defaultServer"`
Domains []WebsiteDomain `json:"domains"` Domains []WebsiteDomain `json:"domains"`
WebsiteSSL WebsiteSSL `json:"webSiteSSL"` WebsiteSSL WebsiteSSL `json:"webSiteSSL"`
} }

View File

@ -14,6 +14,7 @@ type IWebsiteRepo interface {
WithAlias(alias string) DBOption WithAlias(alias string) DBOption
WithWebsiteSSLID(sslId uint) DBOption WithWebsiteSSLID(sslId uint) DBOption
WithGroupID(groupId uint) DBOption WithGroupID(groupId uint) DBOption
WithDefaultServer() DBOption
Page(page, size int, opts ...DBOption) (int64, []model.Website, error) Page(page, size int, opts ...DBOption) (int64, []model.Website, error)
List(opts ...DBOption) ([]model.Website, error) List(opts ...DBOption) ([]model.Website, error)
GetFirst(opts ...DBOption) (model.Website, error) GetFirst(opts ...DBOption) (model.Website, error)
@ -60,6 +61,12 @@ func (w *WebsiteRepo) WithGroupID(groupId uint) DBOption {
} }
} }
func (w *WebsiteRepo) WithDefaultServer() DBOption {
return func(db *gorm.DB) *gorm.DB {
return db.Where("default_server = 1")
}
}
func (w *WebsiteRepo) Page(page, size int, opts ...DBOption) (int64, []model.Website, error) { func (w *WebsiteRepo) Page(page, size int, opts ...DBOption) (int64, []model.Website, error) {
var websites []model.Website var websites []model.Website
db := getDb(opts...).Model(&model.Website{}) db := getDb(opts...).Model(&model.Website{})

View File

@ -29,6 +29,7 @@ type WebsiteService struct {
type IWebsiteService interface { type IWebsiteService interface {
PageWebsite(req request.WebsiteSearch) (int64, []response.WebsiteDTO, error) PageWebsite(req request.WebsiteSearch) (int64, []response.WebsiteDTO, error)
GetWebsites() ([]response.WebsiteDTO, error)
CreateWebsite(create request.WebsiteCreate) error CreateWebsite(create request.WebsiteCreate) error
OpWebsite(req request.WebsiteOp) error OpWebsite(req request.WebsiteOp) error
GetWebsiteOptions() ([]string, error) GetWebsiteOptions() ([]string, error)
@ -81,6 +82,20 @@ func (w WebsiteService) PageWebsite(req request.WebsiteSearch) (int64, []respons
return total, websiteDTOs, nil return total, websiteDTOs, nil
} }
func (w WebsiteService) GetWebsites() ([]response.WebsiteDTO, error) {
var websiteDTOs []response.WebsiteDTO
websites, err := websiteRepo.List()
if err != nil {
return nil, err
}
for _, web := range websites {
websiteDTOs = append(websiteDTOs, response.WebsiteDTO{
Website: web,
})
}
return websiteDTOs, nil
}
func (w WebsiteService) CreateWebsite(create request.WebsiteCreate) error { func (w WebsiteService) CreateWebsite(create request.WebsiteCreate) error {
if exist, _ := websiteRepo.GetBy(websiteRepo.WithDomain(create.PrimaryDomain)); len(exist) > 0 { if exist, _ := websiteRepo.GetBy(websiteRepo.WithDomain(create.PrimaryDomain)); len(exist) > 0 {
return buserr.New(constant.ErrNameIsExist) return buserr.New(constant.ErrNameIsExist)
@ -777,3 +792,25 @@ func (w WebsiteService) OpWebsiteLog(req request.WebsiteLogReq) (*response.Websi
} }
return res, nil return res, nil
} }
func (w WebsiteService) ChangeDefaultServer(id uint) error {
defaultWebsite, _ := websiteRepo.GetFirst(websiteRepo.WithDefaultServer())
if defaultWebsite.ID > 0 {
if err := updateNginxConfig(constant.NginxScopeServer, []dto.NginxParam{{Name: "listen", Params: []string{"80"}}}, &defaultWebsite); err != nil {
return err
}
defaultWebsite.DefaultServer = false
if err := websiteRepo.Save(context.Background(), &defaultWebsite); err != nil {
return err
}
}
website, err := websiteRepo.GetFirst(commonRepo.WithByID(id))
if err != nil {
return err
}
if err := updateNginxConfig(constant.NginxScopeServer, []dto.NginxParam{{Name: "listen", Params: []string{"80", "default_server"}}}, &website); err != nil {
return err
}
website.DefaultServer = true
return websiteRepo.Save(context.Background(), &website)
}

View File

@ -314,10 +314,10 @@ func applySSL(website model.Website, websiteSSL model.WebsiteSSL, req request.We
server.RemoveListenByBind("80") server.RemoveListenByBind("80")
server.RemoveDirective("if", []string{"($scheme"}) server.RemoveDirective("if", []string{"($scheme"})
case constant.HTTPToHTTPS: case constant.HTTPToHTTPS:
server.UpdateListen("80", false) server.UpdateListen("80", website.DefaultServer)
server.AddHTTP2HTTPS() server.AddHTTP2HTTPS()
case constant.HTTPAlso: case constant.HTTPAlso:
server.UpdateListen("80", false) server.UpdateListen("80", website.DefaultServer)
server.RemoveDirective("if", []string{"($scheme"}) server.RemoveDirective("if", []string{"($scheme"})
} }

View File

@ -16,6 +16,7 @@ func (a *WebsiteRouter) InitWebsiteRouter(Router *gin.RouterGroup) {
baseApi := v1.ApiGroupApp.BaseApi baseApi := v1.ApiGroupApp.BaseApi
{ {
groupRouter.POST("/search", baseApi.PageWebsite) groupRouter.POST("/search", baseApi.PageWebsite)
groupRouter.GET("/list", baseApi.GetWebsites)
groupRouter.POST("", baseApi.CreateWebsite) groupRouter.POST("", baseApi.CreateWebsite)
groupRouter.POST("/operate", baseApi.OpWebsite) groupRouter.POST("/operate", baseApi.OpWebsite)
groupRouter.POST("/log", baseApi.OpWebsiteLog) groupRouter.POST("/log", baseApi.OpWebsiteLog)
@ -40,5 +41,6 @@ func (a *WebsiteRouter) InitWebsiteRouter(Router *gin.RouterGroup) {
groupRouter.POST("/waf/config", baseApi.GetWebsiteWafConfig) groupRouter.POST("/waf/config", baseApi.GetWebsiteWafConfig)
groupRouter.POST("/waf/update", baseApi.UpdateWebsiteWafConfig) groupRouter.POST("/waf/update", baseApi.UpdateWebsiteWafConfig)
groupRouter.POST("/nginx/update", baseApi.UpdateWebsiteNginxConfig) groupRouter.POST("/nginx/update", baseApi.UpdateWebsiteNginxConfig)
groupRouter.POST("/default/server", baseApi.ChangeDefaultServer)
} }
} }

View File

@ -32,23 +32,6 @@ func (b *Block) FindDirectives(directiveName string) []IDirective {
return directives return directives
} }
//func (b *Block) UpdateDirectives(directiveName string, directive Directive) {
// directives := b.GetDirectives()
// index := -1
// for i, dir := range directives {
// if dir.GetName() == directiveName {
// index = i
// break
// }
// }
// if index > -1 {
// directives[index] = &directive
// } else {
// directives = append(directives, &directive)
// }
// b.Directives = directives
//}
func (b *Block) UpdateDirective(key string, params []string) { func (b *Block) UpdateDirective(key string, params []string) {
if key == "" || len(params) == 0 { if key == "" || len(params) == 0 {
return return

View File

@ -73,6 +73,19 @@ func (s *Server) UpdateDirective(key string, params []string) {
if key == "" || len(params) == 0 { if key == "" || len(params) == 0 {
return return
} }
if key == "listen" {
defaultServer := false
if len(params) > 1 && params[1] == "default_server" {
defaultServer = true
}
if len(params) > 2 {
s.UpdateListen(params[0], defaultServer, params[2:]...)
} else {
s.UpdateListen(params[0], defaultServer)
}
return
}
directives := s.Directives directives := s.Directives
index := -1 index := -1
for i, dir := range directives { for i, dir := range directives {

View File

@ -11,6 +11,7 @@ export namespace Website {
appInstallId?: number; appInstallId?: number;
webSiteGroupId: number; webSiteGroupId: number;
otherDomains: string; otherDomains: string;
defaultServer: boolean;
appinstall?: NewAppInstall; appinstall?: NewAppInstall;
webSiteSSL: SSL; webSiteSSL: SSL;
} }
@ -271,4 +272,8 @@ export namespace Website {
id: number; id: number;
content: string; content: string;
} }
export interface DefaultServerUpdate {
id: number;
}
} }

View File

@ -7,6 +7,10 @@ export const SearchWebsites = (req: Website.WebSiteSearch) => {
return http.post<ResPage<Website.Website>>(`/websites/search`, req); return http.post<ResPage<Website.Website>>(`/websites/search`, req);
}; };
export const ListWebsites = () => {
return http.get<Website.WebsiteDTO>(`/websites/list`);
};
export const CreateWebsite = (req: Website.WebSiteCreateReq) => { export const CreateWebsite = (req: Website.WebSiteCreateReq) => {
return http.post<any>(`/websites`, req); return http.post<any>(`/websites`, req);
}; };
@ -174,3 +178,7 @@ export const UpdateWafEnable = (req: Website.WafUpdate) => {
export const UpdateNginxFile = (req: Website.NginxUpdate) => { export const UpdateNginxFile = (req: Website.NginxUpdate) => {
return http.post<any>(`/websites/nginx/update`, req); return http.post<any>(`/websites/nginx/update`, req);
}; };
export const ChangeDefaultServer = (req: Website.DefaultServerUpdate) => {
return http.post<any>(`/websites/default/server`, req);
};

View File

@ -959,6 +959,8 @@ export default {
nextYear: '一年后', nextYear: '一年后',
allGroup: '所有分组', allGroup: '所有分组',
noLog: '当前没有日志...', noLog: '当前没有日志...',
defaulServer: '默认网站',
noDefaulServer: '当前没有默认网站',
}, },
nginx: { nginx: {
serverNamesHashBucketSizeHelper: '服务器名字的hash表大小', serverNamesHashBucketSizeHelper: '服务器名字的hash表大小',

View File

@ -0,0 +1,70 @@
<template>
<el-dialog
v-model="open"
:title="$t('website.defaulServer')"
width="20%"
@close="handleClose"
:close-on-click-modal="false"
>
<div style="text-align: center">
<el-select v-model="defaultId">
<el-option :value="0" :key="-1" :label="$t('website.noDefaulServer')"></el-option>
<el-option
v-for="(website, key) in websites"
:key="key"
:value="website.id"
:label="website.primaryDomain"
></el-option>
</el-select>
</div>
<template #footer>
<span class="dialog-footer">
<el-button @click="handleClose" :disabled="loading">{{ $t('commons.button.cancel') }}</el-button>
<el-button type="primary" @click="submit()" :disabled="loading">
{{ $t('commons.button.confirm') }}
</el-button>
</span>
</template>
</el-dialog>
</template>
<script lang="ts" setup>
import { Website } from '@/api/interface/Website';
import { ChangeDefaultServer, ListWebsites } from '@/api/modules/website';
import i18n from '@/lang';
import { ElMessage } from 'element-plus';
import { ref } from 'vue';
let open = ref(false);
let websites = ref<any>();
let defaultId = ref(-1);
let loading = ref(false);
const acceptParams = () => {
defaultId.value = 0;
get();
open.value = true;
};
const handleClose = () => {
open.value = false;
};
const get = async () => {
const res = await ListWebsites();
websites.value = res.data;
websites.value.forEach((website: Website.WebsiteDTO) => {
if (website.defaultServer) {
defaultId.value = website.id;
}
});
};
const submit = () => {
ChangeDefaultServer({ id: defaultId.value }).then(() => {
ElMessage.success(i18n.global.t('commons.msg.updateSuccess'));
handleClose();
});
};
defineExpose({ acceptParams });
</script>

View File

@ -16,6 +16,9 @@
<el-button type="primary" plain @click="openGroup"> <el-button type="primary" plain @click="openGroup">
{{ $t('website.group') }} {{ $t('website.group') }}
</el-button> </el-button>
<el-button type="primary" plain @click="openDefault">
{{ $t('website.defaulServer') }}
</el-button>
</el-col> </el-col>
<el-col :span="14"> <el-col :span="14">
<div style="float: right"> <div style="float: right">
@ -120,6 +123,7 @@
<WebSiteGroup ref="groupRef"></WebSiteGroup> <WebSiteGroup ref="groupRef"></WebSiteGroup>
<UploadDialog ref="uploadRef" /> <UploadDialog ref="uploadRef" />
<BackupRecords ref="dialogBackupRef" /> <BackupRecords ref="dialogBackupRef" />
<DefaultServer ref="defaultRef" />
</LayoutContent> </LayoutContent>
</div> </div>
<div v-if="nginxIsExist"> <div v-if="nginxIsExist">
@ -127,7 +131,6 @@
<span style="font-size: 14px">{{ $t('commons.service.serviceNotStarted', ['OpenResty']) }}</span> <span style="font-size: 14px">{{ $t('commons.service.serviceNotStarted', ['OpenResty']) }}</span>
</el-card> </el-card>
</div> </div>
<el-card v-if="openNginxConfig"> <el-card v-if="openNginxConfig">
<NginxConfig :containerName="containerName" :status="nginxStatus"></NginxConfig> <NginxConfig :containerName="containerName" :status="nginxStatus"></NginxConfig>
</el-card> </el-card>
@ -138,6 +141,7 @@
import LayoutContent from '@/layout/layout-content.vue'; import LayoutContent from '@/layout/layout-content.vue';
import BackupRecords from '@/views/website/website/backup/index.vue'; import BackupRecords from '@/views/website/website/backup/index.vue';
import UploadDialog from '@/views/website/website/upload/index.vue'; import UploadDialog from '@/views/website/website/upload/index.vue';
import DefaultServer from '@/views/website/website/default/index.vue';
import ComplexTable from '@/components/complex-table/index.vue'; import ComplexTable from '@/components/complex-table/index.vue';
import { onMounted, reactive, ref } from '@vue/runtime-core'; import { onMounted, reactive, ref } from '@vue/runtime-core';
import CreateWebSite from './create/index.vue'; import CreateWebSite from './create/index.vue';
@ -181,25 +185,26 @@ let nginxStatus = ref('');
let installPath = ref(''); let installPath = ref('');
const uploadRef = ref(); const uploadRef = ref();
const dialogBackupRef = ref(); const dialogBackupRef = ref();
const defaultRef = ref();
const data = ref(); const data = ref();
let dateRefs: Map<number, any> = new Map(); let dateRefs: Map<number, any> = new Map();
let groups = ref<Website.Group[]>([]); let groups = ref<Website.Group[]>([]);
const paginationConfig = reactive({ const paginationConfig = reactive({
currentPage: 1, currentPage: 1,
pageSize: 20, pageSize: 15,
total: 0, total: 0,
}); });
let req = reactive({ let req = reactive({
name: '', name: '',
page: paginationConfig.currentPage, page: 1,
pageSize: paginationConfig.pageSize, pageSize: 15,
websiteGroupId: 0, websiteGroupId: 0,
}); });
const search = async () => { const search = async () => {
req.page = paginationConfig.currentPage; req.page = paginationConfig.currentPage;
req.pageSize = paginationConfig.currentPage; req.pageSize = paginationConfig.pageSize;
SearchWebsites(req).then((res) => { SearchWebsites(req).then((res) => {
data.value = res.data.items; data.value = res.data.items;
paginationConfig.total = res.data.total; paginationConfig.total = res.data.total;
@ -330,6 +335,10 @@ const openGroup = () => {
groupRef.value.acceptParams(); groupRef.value.acceptParams();
}; };
const openDefault = () => {
defaultRef.value.acceptParams();
};
const checkExist = (data: App.CheckInstalled) => { const checkExist = (data: App.CheckInstalled) => {
nginxIsExist.value = data.isExist; nginxIsExist.value = data.isExist;
containerName.value = data.containerName; containerName.value = data.containerName;