k8s部署gin-vue-admin框架、gitlab-ci、jenkins pipeline 、CICD

测试环境使用的jenkins
正式环境使用的gitlab-ci

测试环境

  1. 创建yaml文件
apiVersion: v1
kind: ConfigMap
metadata:name: dtk-go-tiktok-admin-configlabels:app.kubernetes.io/name: dtk-go-tiktok-adminapp.kubernetes.io/business: infrastructureapp.kubernetes.io/runtime: golangapp.kubernetes.io/tier: backendapp.kubernetes.io/environment: testapp.kubernetes.io/managed-by: yong.xd
data:config.yaml: |max-age: 0show-line: truelog-in-console: true---
apiVersion: v1
kind: ConfigMap
metadata:name: dtk-vue-tiktok-admin-configlabels:app.kubernetes.io/name: dtk-go-tiktok-adminapp.kubernetes.io/business: infrastructureapp.kubernetes.io/runtime: golangapp.kubernetes.io/tier: frontapp.kubernetes.io/environment: testapp.kubernetes.io/managed-by: yong.xd
data:default.conf: |server{listen       80 default_server;server_name  _;access_log   /dev/stdout;error_log    /dev/stdout;root         /opt/app/dist/;location / {try_files $uri $uri/ /index.html;}location /api {proxy_set_header Host $http_host;proxy_set_header  X-Real-IP $remote_addr;proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;proxy_set_header X-Forwarded-Proto $scheme;rewrite ^/api/(.*)$ /$1 break;  #重写add_header 'dtk-debug' 'api';#一个deployment2个pod是网络资源是共享的,所以可以直接代理proxy_pass http://127.0.0.1:8888; # 设置代理服务器的协议和地址}location /api/swagger/index.html {proxy_pass http://127.0.0.1:8888/swagger/index.html;}location /health {access_log off;return 200;}}---
apiVersion: apps/v1
kind: Deployment
metadata:name: dtk-go-tiktok-adminlabels:app.kubernetes.io/name: dtk-go-tiktok-adminapp.kubernetes.io/business: infrastructureapp.kubernetes.io/runtime: golangapp.kubernetes.io/tier: backendapp.kubernetes.io/environment: testapp.kubernetes.io/managed-by: yong.xd
spec:replicas: 1selector:matchLabels:app.kubernetes.io/name: dtk-go-tiktok-adminapp.kubernetes.io/business: infrastructureapp.kubernetes.io/runtime: golangapp.kubernetes.io/tier: backendapp.kubernetes.io/environment: testapp.kubernetes.io/managed-by: yong.xdtemplate:metadata:labels:app.kubernetes.io/name: dtk-go-tiktok-adminapp.kubernetes.io/business: infrastructureapp.kubernetes.io/runtime: golangapp.kubernetes.io/tier: backendapp.kubernetes.io/environment: testapp.kubernetes.io/managed-by: yong.xdspec:imagePullSecrets:- name: aliyun-regcredserviceAccountName: defaultsecurityContext:dnsPolicy: NonednsConfig:nameservers:- 172.31.74.196searches:- test1.svc.cluster.local- svc.cluster.local- cluster.localcontainers:- name: golangsecurityContext:runAsUser: 0image: "registry.buydance.com/dataoke-test/dtk-go-tiktok-admin-golang:latest"volumeMounts:- name: configmountPath: /opt/app/conf/ports:- name: httpcontainerPort: 8888protocol: TCPlivenessProbe:httpGet:path: /healthport: 8888initialDelaySeconds: 5periodSeconds: 20timeoutSeconds: 3readinessProbe:httpGet:path: /healthport: 8888initialDelaySeconds: 5periodSeconds: 10timeoutSeconds: 3resources:requests:cpu: 1mmemory: 20Mi- name: nginxsecurityContext:image: "registry.buydance.com/dataoke-test/dtk-go-tiktok-admin-nginx:latest"volumeMounts:- name: ng-configmountPath: /etc/nginx/conf.d/ports:- name: httpcontainerPort: 80protocol: TCPlivenessProbe:httpGet:path: /healthport: 80periodSeconds: 5readinessProbe:httpGet:path: /healthport: 80periodSeconds: 5resources:requests:cpu: 1mmemory: 64Milimits:cpu: 200mmemory: 256Mivolumes:- name: ng-configconfigMap:name: dtk-vue-tiktok-admin-config- name: configconfigMap:name: dtk-go-tiktok-admin-config
---
apiVersion: v1
kind: Service
metadata:name: dtk-go-tiktok-admin
spec:ports:- port: 80targetPort: 80protocol: TCPname: nginx- port: 8888targetPort: 8888protocol: TCPname: golangselector:app.kubernetes.io/name: dtk-go-tiktok-adminapp.kubernetes.io/business: infrastructureapp.kubernetes.io/runtime: golangapp.kubernetes.io/tier: backendapp.kubernetes.io/environment: testapp.kubernetes.io/managed-by: yong.xd
  1. 启动服务
kubectl apply -f ./ -n test1
  1. 配置jenkins
#!/usr/bin/env groovy
import groovy.json.JsonOutputString gitRepositryURL = 'https://test.com/dtk-go-tiktok-admin.git'
String dockerRegistry = 'test.com'
String dockerRegistryURL = 'https://test.com'
String dockerRegistryNameSpace = 'dataoke-test'
#dockerfile路径
String kubeManifestsRepo = '/home/jenkins/repo/dtk-kubernetes-test/app'
Map dockerFiles = ["nginx":"Dockerfile.test.nginx", "golang":"Dockerfile.test.golang"]
Map dockerImages = [:]
boolean notify = falseString jobBaseName = env.JOB_NAME[4..-1]
String jobK8sName = jobBaseName.replaceAll('_', "-") Map commitInfo = [:]
Map buildInfo = [:]commitInfo.projectName = gitRepositryURL.replaceFirst(/^.*\/([^\/]+?).git$/, '$1') 
commitInfo.gitRepositryURL = gitRepositryURL
buildInfo.buildId = currentBuild.id@NonCPS
def newSh(String cmd) {def script = '#!/bin/sh +x\n' << cmdresult = sh(returnStdout: true, script: script.toString())return result
}pipeline {agent anyoptions {buildDiscarder logRotator(artifactDaysToKeepStr: '', artifactNumToKeepStr: '', daysToKeepStr: '10', numToKeepStr: '10')}parameters {choice( name: 'PENV',choices: ['dev1','dev2','test1','test2', 'test3', 'test4','test5','test6','test7','huise',
'huise4','huise3'], description: '选择发布环境,默认发布至dev1测试环境')gitParameter(name: 'GIT_BRANCH', type: 'PT_BRANCH_TAG',branchFilter: 'origin/(.*)',defaultValue: 'master',selectedValue: 'DEFAULT',sortMode: 'DESCENDING_SMART',quickFilterEnabled: true, description: 'Select your branch or tag.')booleanParam(name: 'force', defaultValue: false, description: '代码重复强制发版')}stages {stage('预处理') {steps {script {def now = new Date()buildInfo.buildDate = now.format("yy-MM-dd HH:mm", TimeZone.getTimeZone('UTC'))def causes = currentBuild.getBuildCauses()buildInfo.buildUser = causes[0]['userName']userList = readYaml(file:'/etc/jenkins/users.yaml')if (!(PENV in userList.env.dev ) && !(buildInfo.buildUser in userList.user.allow)) {error(message: "开发只能发布环境到${userList.env.dev.join(',')}")			}buildInfo.gitBranch = GIT_BRANCHbuildInfo.publishEnv = PENVcurrentBuild.description = "k8s环境: ${PENV} 构建人:${buildInfo.buildUser} 分支: ${GIT_BRANCH}"newSh("check.py -u ${buildInfo.buildUser} -e ${PENV}")}}}stage('同步代码仓库') {steps {script {def scmVars = checkout([$class: 'GitSCM', branches: [[name: "${GIT_BRANCH}"]], extensions: [[$class: 'CheckoutOption', timeout: 20], [$class: 'CloneOption', depth: 1]], userRemoteConfigs: [[credentialsId: "5411496d-3606-4855-ab9c-2e4453cd2880", url: "${gitRepositryURL}"]]])commitInfo.gitCommit = scmVars.GIT_COMMITcommitInfo.gitBranch = GIT_BRANCHcommitInfo.xiangmu_name = env.JOB_BASE_NAMEcommitInfo.commitDate = newSh('git log --pretty=format:"%ci" -1')commitInfo.cmmitMessage = newSh('git log --pretty=format:"%s" -1')String gitDiff = newSh('git diff HEAD^ HEAD')def committer = [:]committer.name = newSh('git log --pretty=format:"%cn" -1')committer.email =  newSh('git log --pretty=format:"%ce" -1')commitInfo.committer = committerString consoleStdout = "\n\n---------SYNCHRONIZE GIT REPOSITORY---------\nGit repo sync successfully.\n\n" + JsonOutput.prettyPrint(JsonOutput.toJson(commitInfo))println(consoleStdout)consoleStdout = "\n\n---------CHANGE LOGS---------\nGit diff:\n\n" + gitDiffprintln(consoleStdout)getDatabaseConnection(type: 'GLOBAL') {def sqlString="select commit_seccec from jenkins_commit.jenkins_jilu where xm_name = ? and env = ?"def params=[commitInfo.xiangmu_name,PENV]def rest_null = sql sql:sqlString,parameters:paramsif (rest_null.size() == 0){def sqlString2="insert  into  jenkins_commit.jenkins_jilu(xm_name,env,commit_seccec)   values(?,?,?)"def params2=[commitInfo.xiangmu_name,PENV,commitInfo.gitCommit]sql sql:sqlString2,parameters:params2println("mysql插入数据")}if (rest_null.size() >= 1) {def Map rest = rest_null.get(0)if (rest.get("commit_seccec") == commitInfo.gitCommit && force == "false"){currentBuild.description = "k8s环境: ${PENV} 构建人:${buildInfo.buildUser} 分支: ${GIT_BRANCH} 构建失败: 代码重复不发版"println("代码没有变化不做发版")error "上一个版本和现在正在发的版本一致,不做发版"}}}}}}stage('构建') {		agent {docker { image 'registry.buydance.com/dataoke-test/golang:1.19'args '--user root -v /data/jenkins_build_cache/.cache:/.cache'args '--user root -v /data/lib/go:/go'reuseNode true}	}steps {script {env.STAGE = "goujian"def now = new Date()String buildDate = now.format("yy-MM-dd HH:mm", TimeZone.getTimeZone('UTC'))sh (script: '#!/bin/sh +x\n' + '''cd ./servermkdir -p .cacheexport GO111MODULE=onexport GOPROXY=https://goproxy.cn,directexport GOPRIVATE="gitlab.buydance.com/*"export CGO_ENABLED=0go mod  tidygo build -o main''')def files = findFiles(glob: '**/main')String artifactPath = files[0].pathString sha1Checksum = sha1(file: artifactPath)String sha256Checksum = sha256(file: artifactPath)consoleStdout = "\n\n---------BUILD RESULTS---------\nBuild info generated successfully.\n\n" + JsonOutput.prettyPrint(JsonOutput.toJson(buildInfo))println(consoleStdout)}	}}stage('构建vue') {		agent {docker { image 'node:14.19.3-alpine3.15'args '--user root -v /data/jenkins_build_cache/.cache:${HOME}/.cache'args '--user root -v /data/lib/composer:/root/.composer'reuseNode true}	}steps {script {sh """cd ./webnpm config set puppeteer_download_host=https://npm.taobao.org/mirrorsnpm i --registry=https://registry.npm.taobao.orgnpm run build"""consoleStdout = "\n\n---------BUILD RESULTS---------\nBuild info generated successfully.\n\n" + JsonOutput.prettyPrint(JsonOutput.toJson(buildInfo))println(consoleStdout)}	}}stage('Docker') {steps {script {env.STAGE = "DOCKERFIEL"//	docker.withRegistry(dockerRegistryURL, '8f1a40fa-3258-4717-825c-a9f87299916d') {docker.withRegistry(dockerRegistryURL) {String dockerFile = kubeManifestsRepo + '/' + jobBaseName + '/' + 'Dockerfile.test.nginx'if (!fileExists(dockerFile)) {dockerFile = kubeManifestsRepo + '/' + jobK8sName + '/' + 'Dockerfile.test.nginx'}String dockerRepository = dockerRegistry + '/' + dockerRegistryNameSpace + '/' + jobK8sName + '-' + 'nginx'def customImage = docker.build(dockerRepository, "-f ${dockerFile} .")customImage.push(commitInfo.gitCommit)customImage.push('latest')dockerImages.nginx = dockerRepository + ':' + commitInfo.gitCommitdockerFile = kubeManifestsRepo + '/' + jobBaseName + '/' + 'Dockerfile.test.golang'if (!fileExists(dockerFile)) {dockerFile = kubeManifestsRepo + '/' + jobK8sName + '/' + 'Dockerfile.test.golang'}dockerRepository = dockerRegistry + '/' + dockerRegistryNameSpace + '/' + jobK8sName + '-' + 'golang'customImage = docker.build(dockerRepository, "-f ${dockerFile} .")customImage.push(commitInfo.gitCommit)customImage.push('latest')dockerImages."golang" = dockerRepository + ':' + commitInfo.gitCommit}}}}stage('部署') {steps {script {env.STAGE = "bushu"dockerImages.each { k, v -> newSh("kubectl -n ${PENV} set image deployment/${jobK8sName} ${k}=${v}")newSh("kubectl -n ${PENV} rollout status deployment/${jobK8sName} --timeout=2m")}String content = "![screenshot](https://comquent.de/wp-content/uploads/CQ-Pipeline-Kurs.png)\n\n### Jenkins Pipeline\n>**构建信息**:\n>- 构建项目: ${jobBaseName}\n>- 构建id: ${currentBuild.number}\n>- 构建人: ${buildInfo.buildUser}\n>- 构建分支: ${GIT_BRANCH}\n>- 发布环境: ${PENV}\n>**版本信息**:\n>- commit_hash: ${commitInfo.gitCommit}\n>- commit_date: ${commitInfo.commitDate}\n>- commit_message: ${commitInfo.cmmitMessage}\n>- committer: ${commitInfo.committer.name}"	def workflowMessage = ["msgtype": "actionCard","actionCard":["title":"构建信息","text":content,"btnOrientation": "0","btns": [["title": "详细信息","actionURL": "https://k8sjenkins.haojiequ.com/blue/organizations/jenkins/k8s_dtk_go_app_api/detail/k8s_dtk_go_app_api/${currentBuild.number}/pipeline"],["title": "日志监控","actionURL": "http://k8skibana.haou.com/app/kibana#/discover?_g=()&_a=(columns:!(_source),index:'18d51920-96c3-11eb-811f-1383c86a1d0',interval:auto,query:(language:kuery,query:''),sort:!(!('@timestamp',desc)))"],]]]	String workflowMessageJSON = JsonOutput.toJson(workflowMessage)timeout(unit: 'SECONDS', time: 30) {newSh("curl 'https://oapi.dingtalk.com/robot/send?access_token=9e91f6860736ff69e7f6f986179e154e497b70e26fd749c' -s -H 'Content-Type: application/json' -d '${workflowMessageJSON}'")}}}}stage("commit入库"){steps {script{getDatabaseConnection(type: 'GLOBAL') {def sqlString3="update jenkins_commit.jenkins_jilu set commit_seccec=?    where xm_name=? and env=?;"def params3=[commitInfo.gitCommit,commitInfo.xiangmu_name,PENV]sql sql:sqlString3,parameters:params3}}}}}post {failure {script{if (STAGE == "goujian") {println("----> goujian失败")}if (STAGE == "bushu") {println("----> bushu失败")		   }if (STAGE == "DOCKERFIEL") {println("----> DOCKERFIEL失败")}}}}
}
  1. 配置nginx
upstream  dtk-vue-tiktok-admin  {server dtk-go-tiktok-admin  weight=1 max_fails=0 fail_timeout=0s;keepalive 20;
}server {
listen  80;
listen      443 ssl;
server_name test.com;
access_log  /var/log/nginx/dtest.com.access.log json;
error_log   /var/log/nginx/dtest.com.error.log;
ssl_certificate     conf.d/dtkcert/test.com.pem;
ssl_certificate_key conf.d/dtkcert/test.com.key;
more_set_headers 'Access-Control-Allow-Headers: Cookie,DNT,X-CSRF-Token,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Authorization,Auth-token';
more_set_headers 'Access-Control-Allow-Origin: *';
more_set_headers 'Access-Control-Allow-Methods: GET, POST, OPTIONS, PUT';
more_set_headers 'Access-Control-Allow-Credentials: true';
default_type     'text/html';
set $backend 'dtk-vue-tiktok-admin';include  public/deny.conf;
location / {proxy_pass http://$backend;
}location ~ /\.ht {deny  all;
}
}
  1. jenkins机器上的dockerfile
[root@k8s-jenkins dtk-go-tiktok-admin]# cat Dockerfile.test.golang
FROM test.com/dataoke-test/alpine:3.12-CST as test
WORKDIR /opt/app
COPY  $CI_PROJECT_DIR/server/main /opt/app/main
CMD ["/opt/app/main", "-c", "/opt/app/conf/config.yaml"][root@k8s-jenkins dtk-go-tiktok-admin]# cat Dockerfile.test.nginx
FROM test.com/dataoke-test/openresty:base
WORKDIR /opt/app/dist/
COPY --chown=nobody:nobody web/dist /opt/app/dist

线上环境配置

  1. yaml其它都一样除了svc,因为svc需要绑定slb地址
apiVersion: v1
kind: Service
metadata:name: dtk-go-tiktok-adminannotations:#开启slb使用service.beta.kubernetes.io/alibaba-cloud-loadbalancer-force-override-listeners: "true"#slb地址service.beta.kubernetes.io/alibaba-cloud-loadbalancer-id: lb-2ze1hpcomc#    service.beta.kubernetes.io/alibaba-cloud-loadbalancer-protocol-port: "http:9090"service.beta.kubernetes.io/alibaba-cloud-loadbalancer-scheduler: "wrr"namespace: default
spec:type: LoadBalancerexternalTrafficPolicy: Localports:- port: 16107  #slb端口targetPort: 80 #pod服务端口protocol: TCPselector:app.kubernetes.io/name: dtk-go-tiktok-adminapp.kubernetes.io/business: infrastructureapp.kubernetes.io/runtime: golangapp.kubernetes.io/tier: backendapp.kubernetes.io/environment: prodapp.kubernetes.io/managed-by: yong.xd
  1. 启动
cat .gitlab-ci.ymlstages:- build- package- docker- deploy- notifybuild:stage: buildimage: test.com/dataoke-prod/golang:1.19-with-repo-certcache:key:files:- go.modpaths:- .cache/pkgartifacts:expire_in: 20 minsuntracked: falsepaths:- $CI_PROJECT_DIR/server/mainscript:- mkdir -p .cache- cd ./server - export GOPATH="$CI_PROJECT_DIR/.cache"- go env -w GO111MODULE=on - go env -w GOPROXY=https://goproxy.cn,direct - go env -w GOPRIVATE=gitlab.buydance.com - go env -w CGO_ENABLED=0- go build -o mainonly:- tagspackage:stage: packageimage: test.com/dataoke-prod/node:14.19.3-alpine3.15script:- cd ./web- npm config set puppeteer_download_host=https://npm.taobao.org/mirrors- npm i --registry=https://registry.npm.taobao.org- npm run buildcache:key:files:- package.jsonpaths:- node_modulesartifacts:name: "dist"untracked: falseexpire_in: 5 minspaths:- $CI_PROJECT_DIR/web/distonly:- tagsdocker:stage: dockerimage: test.com/dataoke-prod/kaniko-executor:debugscript:- mkdir -p /kaniko/.docker- echo "${DOCKER_AUTH_CONFIG}" > /kaniko/.docker/config.json- /kaniko/executor --context $CI_PROJECT_DIR --dockerfile $CI_PROJECT_DIR/Dockerfile.prod.nginx --destination test.aliyuncs.com/dataoke-prod/`echo ${CI_PROJECT_NAME} |sed 's@_@-@g'`-nginx:${CI_COMMIT_SHORT_SHA} --destination test.aliyuncs.com/dataoke-prod/`echo ${CI_PROJECT_NAME} |sed 's@_@-@g'`-nginx:latest- /kaniko/executor --context $CI_PROJECT_DIR --dockerfile $CI_PROJECT_DIR/Dockerfile.prod.golang --destination test.aliyuncs.com/dataoke-prod/`echo ${CI_PROJECT_NAME} |sed 's@_@-@g'`-golang:${CI_COMMIT_SHORT_SHA} --destination test.aliyuncs.com/dataoke-prod/`echo ${CI_PROJECT_NAME} |sed 's@_@-@g'`-golang:latestonly:- tagsdeploy:stage: deployimage: test.com/dataoke-prod/kubectl:1.18.1variables:GIT_STRATEGY: noneK8S_NAME_SPACE: defaultscript:- mkdir -p $HOME/.kube- echo "$KUBERNETES_SECRET" >> "$HOME/.kube/config"- kubectl version- kubectl get deployments.apps -n ${K8S_NAME_SPACE}- kubectl -n ${K8S_NAME_SPACE} set image deployment/`echo ${CI_PROJECT_NAME} |sed 's@_@-@g'` nginx=test.aliyuncs.com/dataoke-prod/`echo ${CI_PROJECT_NAME} |sed 's@_@-@g'`-nginx:${CI_COMMIT_SHORT_SHA} golang=test.aliyuncs.com/dataoke-prod/`echo ${CI_PROJECT_NAME} |sed 's@_@-@g'`-golang:${CI_COMMIT_SHORT_SHA} --record- kubectl rollout status deployment/`echo ${CI_PROJECT_NAME} |sed 's@_@-@g'`only:- tagsnotifyFailWeChat:stage: notifyimage: test.aliyuncs.com/dataoke-prod/curl-image:v1script:- curl 'https://oapi.dingtalk.com/robot/send?access_token=6147ec1eb7d8b9bd5cd1b15f1c' -H 'Content-Type:application/json' -d "{\"msgtype\":\"text\",\"text\":{\"content\":\"$CI_PROJECT_NAME项目构建失败\n>本次构建由:$GITLAB_USER_NAME 触发\n>项目名称:$CI_PROJECT_NAME\n>提交号:$CI_COMMIT_SHA\n>提交日志:$CI_COMMIT_MESSAGE\n>构建分支:$CI_COMMIT_BRANCH\n>流水线地址:[$CI_PIPELINE_URL]($CI_PIPELINE_URL)\"}}"only:- tagswhen: on_failure# 构建成功时的通知消息
notifySuccessWeChat:stage: notifyimage: test.aliyuncs.com/dataoke-prod/curl-image:v1script:- curl 'https://oapi.dingtalk.com/robot/send?access_token=d6147ec1eb7d8b9bd5cd1b15f1c' -H 'Content-Type:application/json' -d "{\"msgtype\":\"text\",\"text\":{\"content\":\"$CI_PROJECT_NAME项目构建成功\n>本次构建由:$GITLAB_USER_NAME 触发\n>项目名称:$CI_PROJECT_NAME\n>提交号:$CI_COMMIT_SHA\n>提交日志:$CI_COMMIT_MESSAGE\n>构建分支:$CI_COMMIT_BRANCH\n>流水线地址:[$CI_PIPELINE_URL]($CI_PIPELINE_URL)\"}}"only:- tagswhen: on_success
  1. 配置dockerfile
cat  Dockerfile.prod.golangFROM test.aliyuncs.com/dataoke-prod/alpine:3.12-CST as prod
WORKDIR /opt/app
COPY  $CI_PROJECT_DIR/server/main /opt/app/main
CMD ["/opt/app/main", "-c", "/opt/app/conf/config.yaml"]cat Dockerfile.prod.nginxFROM test.aliyuncs.com/dataoke-prod/openresty:base
WORKDIR /opt/app/dist/
COPY --chown=nobody:nobody web/dist /opt/app/dist
  1. 配置nginx
upstream  dtk-go-tiktok-admin {
#svc内网ip
server 192.168.10.123:16107  weight=1 max_fails=0 fail_timeout=0s;
keepalive 20;
}server {
listen  80;
listen      443 ssl;
server_name test.com;
access_log  /var/log/nginx/dtest.com.access.log json;
error_log   /var/log/nginx/dtest.com.error.log;
ssl_certificate     conf.d/dtkcert/test.com.pem;
ssl_certificate_key conf.d/dtkcert/test.com.key;more_set_headers 'Access-Control-Allow-Headers: Cookie,DNT,X-CSRF-Token,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Authorization,Auth-token';
more_set_headers 'Access-Control-Allow-Origin: *';
more_set_headers 'Access-Control-Allow-Methods: GET, POST, OPTIONS, PUT';
more_set_headers 'Access-Control-Allow-Credentials: true';
default_type     'text/html';
set $backend 'dtk-vue-tiktok-admin';include  public/deny.conf;
location / {
proxy_pass http://$backend;
}location ~ /\.ht {
deny  all;
}
}
  1. 结果图
    微信截图_20230928142620.png
    微信截图_20230928142639.png

微信截图_20230928142705.png
微信截图_20230928142657.png
微信截图_20230928142557.png
微信截图_20230928142535.png

原文

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/144618.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Windows系统利用cpolar内网穿透搭建Zblog博客网站并实现公网访问内网!

文章目录 1. 前言2. Z-blog网站搭建2.1 XAMPP环境设置2.2 Z-blog安装2.3 Z-blog网页测试2.4 Cpolar安装和注册 3. 本地网页发布3.1. Cpolar云端设置3.2 Cpolar本地设置 4. 公网访问测试5. 结语 1. 前言 想要成为一个合格的技术宅或程序员&#xff0c;自己搭建网站制作网页是绕…

What is a UDP Flood Attack?

用户数据报协议 &#xff08;UDP&#xff09; 是计算机网络中使用的无连接、不可靠的协议。它在互联网协议 &#xff08;IP&#xff09; 的传输层上运行&#xff0c;并提供跨网络的快速、高效的数据传输。与TCP&#xff08;其更可靠的对应物&#xff09;不同&#xff0c;UDP不提…

GitHub配置SSH key

GitHub配置SSH key Git配置信息并生成密钥 设置用户名和密码 设置用户名 git config --global user.name "用户名" 设置邮箱 git confir --global user.email "邮箱" 生成密钥 ssh-keygen -t rsa -C "邮箱" 查看密钥 到密钥所保存的位置 复…

ubuntu与win之间共享文件夹

ubuntu上设置共享文件夹 第一步&#xff1a;点击【设置】或【虚拟机弹窗下面的【设置】选项】 第二步&#xff1a;进入【虚拟机设置】页面&#xff0c;点击【选项】如下图所示 第三步&#xff1a;启用共享文件&#xff1a;点击【总是启用】第四步&#xff1a;添加共享文件&…

uni-app:canvas-绘制图形4(获取画布宽高,根据画布宽高进行图形绘制)

效果 代码 var width ; var height ; const query uni.createSelectorQuery(); //获取宽度 query.select(#firstCanvas).fields({ size: true }, (res) > { width res.width; height res.height; }).exec(); console.log(宽度width); console.log(高…

国庆day1

发送数据 #include<myhead.h>//消息结构体 typedef struct {long msgtype; //消息类型char data[1024]; //消息正文 }Msg_ds;#define SIZE sizeof(Msg_ds)-sizeof(long) //正文大小 int main(int argc, const char *argv[]) {//1、创建key值key_t ke…

五、接口测试工具:Postman

Postman是一款接口调试工具&#xff0c;是一款免费的可视化软件&#xff0c;同时支持各种操作系统平台&#xff0c;是测试接口的首选工具。 官网下载&#xff1a; https://www.postman.com/downloads/ 工作面板 简易的get请求 简易的post请求 案例&#xff1a;请求百度地图…

Unity实现设计模式——中介者模式

Unity实现设计模式——中介者模式 用一个中介者对象来封装一系列的对象交互&#xff0c;中介者使各对象不需要显示地相互引用&#xff0c;从而使其松散耦合&#xff0c;而且可以独立地改变它们之间的交互。 这里使用一个生活中的例子来介绍中介者模式&#xff0c;比如当我们在…

使用Python爬虫抓取网站资源的方法

Python爬虫是一种自动化程序&#xff0c;用于从互联网上获取数据。使用Python爬虫可以轻松地抓取网站上的各种资源&#xff0c;例如文本、图片、视频等。在本文中&#xff0c;我们将介绍如何使用Python爬虫抓取网站资源。 安装Python 在使用Python爬虫之前&#xff0c;需要先安…

【SSL】用Certbot生成免费HTTPS证书

1. 实验背景 服务器&#xff1a;CentOS7.x 示例域名&#xff1a; www.example.com 域名对应的web站点目录&#xff1a; /usr/local/openresty/nginx/html 2. 安装docker # yum -y install yum-utils# yum-config-manager --add-repo https://download.docker.com/linux/ce…

矢量图形编辑软件illustrator 2023 mac软件特点

illustrator 2023 mac是一款矢量图形编辑软件&#xff0c;用于创建和编辑排版、图标、标志、插图和其他类型的矢量图形。 illustrator mac软件特点 矢量图形&#xff1a;illustrator创建的图形是矢量图形&#xff0c;可以无限放大而不失真&#xff0c;这与像素图形编辑软件&am…

国庆周《Linux学习第三课》

国庆周《Linux学习第三课》 国庆周《Linux学习第二课》_IHOPEDREAM的博客-CSDN博客 总结 用户的管理 增加一个用户 删除一个用户 修改一个用户 查看一个用户 用户组的管理 增加一个组 删除一个组 修改一个组 查看一个组 将用户成员增加到该组中去 移除组的成员 1 用户

【深度学习实验】卷积神经网络(六):卷积神经网络模型(VGG)训练、评价

目录 一、实验介绍 二、实验环境 1. 配置虚拟环境 2. 库版本介绍 三、实验内容 0. 导入必要的工具包 1. 构建数据集&#xff08;CIFAR10Dataset&#xff09; a. read_csv_labels&#xff08;&#xff09; b. CIFAR10Dataset 2. 构建模型&#xff08;FeedForward&…

python监控ES索引数量变化

文章目录 1, datafram根据相同的key聚合2, 数据合并&#xff1a;获取采集10,20,30分钟es索引数据脚本测试验证 1, datafram根据相同的key聚合 # 创建df1 > json {key:A, value:1 } {key:B, value:2 } data1 {key: [A, B], value: [1, 2]} df1 pd.DataFrame(data1)# 创建d…

rhel8 网络操作学习

一、查询dns服务器地址汇总 1.查询dns服务器地址&#xff1a; &#xff08;1&#xff09;方法一&#xff1a;执行命令 cat /etc/resolv.conf 执行结果如下&#xff1a; nameserver后面就是dns服务器的ip地址。 &#xff08;2&#xff09;方法2&#xff1a;查看/etc/syscon…

蓝海彤翔亮相2023新疆网络文化节重点项目“新疆动漫节”

9月22日上午&#xff0c;2023新疆网络文化节重点项目“新疆动漫节”&#xff08;以下简称“2023新疆动漫节”&#xff09;在克拉玛依科学技术馆隆重开幕&#xff0c;蓝海彤翔作为国内知名的文化科技产业集团应邀参与此次活动&#xff0c;并在美好新疆e起向未来动漫展映区设置展…

【C++数据结构】二叉树搜索树【完整版】

目录 一、二叉搜索树的定义 二、二叉搜索树的实现&#xff1a; 1、树节点的创建--BSTreeNode 2、二叉搜索树的基本框架--BSTree 3、插入节点--Insert 4、中序遍历--InOrder 5、 查找--Find 6、 删除--erase 完整代码&#xff1a; 三、二叉搜索树的应用 1、key的模型 &a…

工具学习--easyexcel-3.x 使用--写入基本使用,自定义转换--动态表头以及宽设置-

写在前面&#xff1a; easyexcel是alibaba开发简单导出未excel的工具。使用的情况还是比较多的。 文章目录 依赖导入写Excel快速入门对象设置ExcelProperty设置列属性ExcelIgnore 忽视列宽、行高格式转换时间格式化数字格式化自定义格式化 合并单元格其他更加个性化需求动态表…

【Java 进阶篇】MySQL多表关系详解

MySQL是一种常用的关系型数据库管理系统&#xff0c;它允许我们创建多个表格&#xff0c;并通过各种方式将这些表格联系在一起。在实际的数据库设计和应用中&#xff0c;多表关系是非常常见的&#xff0c;它能够更好地组织和管理数据&#xff0c;实现数据的复杂查询和分析。本文…

react+IntersectionObserver实现页面丝滑帧动画

实现效果&#xff1a; 加入帧动画前&#xff1a; 普通的静态页面 加入帧动画后&#xff1a; 可以看到&#xff0c;加入帧动画后&#xff0c;页面效果还是比较丝滑的。 技术实现 加入animation动画类 先用 **scss **定义三种动画类&#xff1a; .withAnimation {.fade1 {ani…