当前位置: 首页 > news >正文

桂林论坛网七星区seo月薪

桂林论坛网七星区,seo月薪,苏州市高新区建设局网站,最好的app制作公司本篇使用Vue2开发前端,Go语言开发服务端,使用nginx代理部署实现登录页面及其校验功能。 目录 1.部署结构 2.Vue2前端 2.1代码结构 2.1源码 3.Go后台服务 3.2代码结构 3.2 源码 3.3单测效果 4.nginx 5.运行效果 6.问题总结 1.部署结构 2.Vue2…

   本篇使用Vue2开发前端,Go语言开发服务端,使用nginx代理部署实现登录页面及其校验功能。

目录

1.部署结构

2.Vue2前端

2.1代码结构

2.1源码

3.Go后台服务

3.2代码结构

3.2 源码

3.3单测效果

4.nginx

5.运行效果

6.问题总结


1.部署结构

 

2.Vue2前端

2.1代码结构

2.1源码

index.html

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1.0">
    <title>demo</title>
  </head>
  <body>
    <div id="myapp"></div>
    <!-- built files will be auto injected -->
  </body>
</html>

src/App.vue

<template>
<div>
<router-view></router-view>
</div>
</template>

src/assets/css/reset.css

/* http://meyerweb.com/eric/tools/css/reset/ 
   v2.0 | 20110126
   License: none (public domain)
*/

html, body, div, span, applet, object, iframe,
h1, h2, h3, h4, h5, h6, p, blockquote, pre,
a, abbr, acronym, address, big, cite, code,
del, dfn, em, img, ins, kbd, q, s, samp,
small, strike, strong, sub, sup, tt, var,
b, u, i, center,
dl, dt, dd, ol, ul, li,
fieldset, form, label, legend,
table, caption, tbody, tfoot, thead, tr, th, td,
article, aside, canvas, details, embed, 
figure, figcaption, footer, header, hgroup, 
menu, nav, output, ruby, section, summary,
time, mark, audio, video {
    margin: 0;
    padding: 0;
    border: 0;
    font-size: 100%;
    font: inherit;
    vertical-align: baseline;
}
/* HTML5 display-role reset for older browsers */
article, aside, details, figcaption, figure, 
footer, header, hgroup, menu, nav, section {
    display: block;
}
body {
    line-height: 1;
}
ol, ul {
    list-style: none;
}
blockquote, q {
    quotes: none;
}
blockquote:before, blockquote:after,
q:before, q:after {
    content: '';
    content: none;
}
table {
    border-collapse: collapse;
    border-spacing: 0;
}

src/components/Home.vue

<template>
<div id="YYYYYYYYYYY" class="hello">
<button @click="goLogin">登录</button>
<el-button type="primary">你好</el-button>
<el-button type="info">你好</el-button>
<el-button type="danger">你好</el-button>
<el-button type="success">你好</el-button>
<el-tag> fsfsd dsd dsfv</el-tag>
<i class="fa fa-user"></i>
<i class="fa fa-users"></i>
</div>
</template>

<style lang="scss">
    .hello {
        background: yello;
        .el-button {
            color: red;
        }
    }
@import url('../assets/css/reset.css')
</style>


<script>
export default {
  methods: {
    goLogin () {
      this.$router.push('/login')
    }
  }
}
</script>

src/components/Login.vue

<template>
  <div class="login">
    <el-card class="box-card">
        <div slot="header" class="clearfix">
            <span>业务后台管理系统</span>
        </div>

        <el-form label-width="100px" :model="form" ref="form" :rules='rules'>
            <el-form-item label="用户名" prop='username'>
                <el-input v-model="form.username"></el-input>
            </el-form-item>
            <el-form-item label="密码" prop='password'>
                <el-input type='password' v-model="form.password"></el-input>
            </el-form-item>
            <el-form-item>
                <el-button type='primary' @click="login('form')">登录</el-button>
            </el-form-item>
        </el-form>
    </el-card>
  </div>
</template>

/*
原生AJAX和Axios在使用上存在一定的区别。Axios可以支持多种方式,包括浏览器环境、node环境,而AJAX则只能在浏览器环境中使用。
Axios还支持多种请求方式,包括GET、POST、PUT、DELETE等;而AJAX只能支持GET和POST方式发送请求。此外,Axios还可以拦截请求和响应。
*/

<script>

//登录验证的封装
import {nameRule, passRule} from '../utils/validate.js'

import {setToken} from '@/utils/dealtoken.js'

export default {
  data () {
    return {
        form: {
            username: "",
            password: ""
        },
        rules: {
            username: [{validator: nameRule, required: true, trigger: "blur"}],
            password: [{validator: passRule, required: true, trigger: "blur"}]
        }
    }
  },
  methods: {
    login(form) {
        this.$refs[form].validate((valid) => {
            if (valid) {
                console.log(this.form)
                //this.$router.push('/home')
                //解决axios post请求 404  OPTIONS问题
                const posthead = {
                    headers: {
                    'Content-Type': 'text/plain;charset=utf-8',
                    },
                    //withCredentials: 'same-origin'
                }
                this.axios.post('http://localhost:8282/login', JSON.stringify(this.form), posthead).then(res => {
                    console.log(res)
                    if (res.status === 200) {
                        //localStorage.setItem('username', res.data.username)
                        setToken('username', res.data.username)
                        this.$message({message: res.data, type: 'success'})
                        this.$router.push('/home')
                        console.log("post mid")
                    }
                })
            } else {
                console.error(this.form)
            }
        })
    }
  }
}
</script>

<style lang='scss'>
    .login {
        width: 100%;
        height: 100%;
        position: absolute;
        background: #409EFF;
        .box-card {
            width: 450px;
            margin: 200px auto;
            .el-card_header {
                font-size: 34px;
            }
            .el-button {
                width: 100%;
            }
        }
    }
</style>

src/main.js

import Vue from 'vue'
import App from './App'
import 'font-awesome/css/font-awesome.min.css'
import axios from 'axios'
import router from './router'

// 挂载到原型就可以全局使用
Vue.prototype.axios = axios

import ElementUI from 'element-ui'
import 'element-ui/lib/theme-chalk/index.css'
Vue.use(ElementUI)


new Vue({
  router,
  render: h => h(App)
}).$mount('#myapp')

src/router/index.js

import Vue from 'vue'
import Home from '@/components/Home'
import VueRouter from 'vue-router'

Vue.use(VueRouter)

const routes = [
  { path: '/', redirect: '/login', component: () => import('@/components/Login') },
  { path: '/login', name: 'Login', component: () => import('@/components/Login') },
  { path: '/home', component: Home },
  { path: '*', component: Home }
]


export default new VueRouter({
  mode: 'history',
  routes: routes
})


src/utils/validate.js

// Token的封装 Token存放在localStorage
export function setToken(tokenkey, token) {
    return localStorage.setItem(tokenkey, token)
}

export function getToken(tokenkey) {
    return localStorage.getItem(tokenkey)
}

export function removeToken(tokenkey) {
    return localStorage.removeItem(tokenkey)
}

src/utils/dealtoken.js

//用户名匹配
export function nameRule (rule, value, callback) {
    let reg = /(^[a-zA-Z0-9]{4,10}$)/;
    if (value === "") {
        callback(new Error("请输入用户名"));
    } else if (!reg.test(value)) {
        callback(new Error("请输入4-10用户名"));
    } else {
        callback();
    }
}

//密码匹配
export function passRule (rule, value, callback) {
    let pass = /^\S*(?=\S{6,12})(?=\S*\d)(?=\S*[A-Z])(?=\S*[a-z])(?=\S*[!@#$%^&*? ])\S*$/;
    if (value === "") {
        callback(new Error("请输入密码"));
    } else if (!pass.test(value)) {
        callback(new Error("请输入6-12位密码需要包含大小写和数字及特殊字符"));
    } else {
        callback();
    }
}

plugins/element.js

import Vue from 'vue'
import { Button, Tag } from 'element-ui'

Vue.use(Button)
Vue.use(Tag)

3.Go后台服务

3.2代码结构

3.2 源码

controller/login.go

package controller

import (
    "encoding/json"
    "fmt"
    "io/ioutil"
    "net/http"
    "path/filepath"

    "github.com/gin-gonic/gin"
)

// post  http://127.0.0.1:8181/login
// axios.post 和 post json处理
func LoginPost(ctx *gin.Context) {
    version := ctx.DefaultQuery("version", "V1.0.0.1")

    //前端使用axios直接传递form时,axios会默认使用json,必须使用下面方式获取json数据,解析后再使用
    data, _ := ioutil.ReadAll(ctx.Request.Body)
    type UserInfo struct {
        Username string
        Password string
    }
    var u UserInfo
    err := json.Unmarshal(data, &u)
    if err != nil {
        fmt.Println(err)
    }
    username := u.Username
    password := u.Password

    fmt.Println("login info:: ", version, username, password)

    /*
        ctx.Header("Access-Control-Allow-Origin", "*")

            ctx.Header("Access-Control-Allow-Headers", "Content-Type,AccessToken,X-CSRF-Token, Authorization, Token")
            ctx.Header("Access-Control-Allow-Credentials", "true")
            ctx.Header("Access-Control-Allow-Methods", "POST, GET, OPTIONS, PUT, DELETE")
            ctx.Header("content-type", "application/json;charset=UTF-8")

            ctx.Writer.Header().Set("Access-Control-Max-Age", "86400")
            ctx.Writer.Header().Set("Access-Control-Allow-Methods", "*")
            ctx.Writer.Header().Set("Access-Control-Allow-Headers", "*")
            ctx.Writer.Header().Set("Access-Control-Expose-Headers", "*")
            ctx.Writer.Header().Set("Access-Control-Allow-Credentials", "true")
    */

    if username == "123456" && password == "1234abcdE@" {
        ctx.String(http.StatusOK, "登录成功")
    } else {
        ctx.String(http.StatusNotFound, "用户名或密码错误")
    }
}

// http://127.0.0.1:8181/formlogin
// form表单提交处理 application/x-www-form-urlencoded
func FormLoginPost(ctx *gin.Context) {

    //第一种
    username := ctx.PostForm("username")
    password := ctx.PostForm("password")

    //第二种
    /*
        username := ctx.DefaultPostForm("username", "somebody")
        password := ctx.DefaultPostForm("password", "***")
    */

    //第三种
    /*
        username, ok := ctx.GetPostForm("username")
        if !ok {
            username = "取不到的话"
        }
        password, ok := ctx.GetPostForm("password")
        if !ok {
            password = "***"
        }
    */

    fmt.Println("FormLoginPost :: ", username, password)
    /*
        ctx.HTML(http.StatusOK, "home.html", gin.H{
            "Name":     username,
            "Password": password,
        })
    */
    ctx.JSON(http.StatusOK, gin.H{
        "Name":     username,
        "Password": password,
    })

    if username == "123456" && password == "1234abcdE@" {
        ctx.String(http.StatusOK, "登录成功")
    } else {
        ctx.String(http.StatusNotFound, "用户名或密码错误")
    }
}

// form表单提交文件上传处理 multipart/form-data
func UploadFile(ctx *gin.Context) {
    file, _ := ctx.FormFile("uploadfile")
    fmt.Println(file.Filename)
    file_path := "upload/" + filepath.Base(file.Filename)
    fmt.Println(file_path)
    ctx.SaveUploadedFile(file, file_path)
    ctx.String(http.StatusOK, "上传成功")
}

server.go

package main

import (
    "main/controller"
    "net/http"

    "github.com/gin-contrib/cors"
    "github.com/gin-gonic/gin"
)

/*
// 错误: server.go:4:2: package main/controller is not in GOROOT (/home/tiger/go/go/src/main/controller)
go mod init main

//错误: server.go:7:2: no required module provides package github.com/gin-gonic/gin; to add it:
go get github.com/gin-gonic/gin

//处理跨域框架
go get github.com/gin-contrib/cors
*/

/*
当客户端(尤其是基于 Web 的客户端)想要访问 API 时,服务器会决定允许哪些客户端发送请求。这是通过使用称为 CORS 来完成的,它代表跨源资源共享。
跨域资源共享 (CORS) 是一种机制,允许从提供第一个资源的域之外的另一个域请求网页上的受限资源。
*/

func CrosHandler() gin.HandlerFunc {
    return func(context *gin.Context) {
        context.Writer.Header().Set("Access-Control-Allow-Origin", "*")
        context.Header("Access-Control-Allow-Origin", "*") // 设置允许访问所有域
        context.Header("Access-Control-Allow-Methods", "POST,GET,OPTIONS,PUT,DELETE,UPDATE")
        context.Header("Access-Control-Allow-Headers", "Authorization, Content-Length, X-CSRF-Token, Token,session,X_Requested_With,Accept, Origin, Host, Connection, Accept-Encoding, Accept-Language,DNT, X-CustomHeader, Keep-Alive, User-Agent, X-Requested-With, If-Modified-Since, Cache-Control, Content-Type, Pragma,token,openid,opentoken")
        context.Header("Access-Control-Expose-Headers", "Content-Length, Access-Control-Allow-Origin, Access-Control-Allow-Headers,Cache-Control,Content-Language,Content-Type,Expires,Last-Modified,Pragma,FooBar")
        context.Header("Access-Control-Max-Age", "172800")
        context.Header("Access-Control-Allow-Credentials", "true")
        context.Set("content-type", "application/json") //设置返回格式是json
        //处理请求
        context.Next()
    }
}

// http://127.0.0.1:8181/ping
// http://127.0.0.1:8181/index
func main() {
    r := gin.Default()

    // 设置全局跨域访问
    //r.Use(CrosHandler())

    //cors处理跨域
    r.Use(cors.Default())

    // 返回一个json数据
    r.GET("/ping", func(c *gin.Context) {
        c.JSON(200, gin.H{
            "message": "pong",
            "num":     888,
        })
    })

    // 返回一个html页面
    r.LoadHTMLGlob("templates/*")
    r.GET("/index", func(c *gin.Context) {
        c.HTML(http.StatusOK, "index.html", nil)
    })

    r.POST("/login", controller.LoginPost)
    r.POST("/formlogin", controller.FormLoginPost)
    r.POST("/upload", controller.UploadFile)

    //r.Run()  // <===> r.Run(":8080")  监听并在 0.0.0.0:8080 上启动服务
    r.Run(":8181")
}

templates/home.html

欢迎进入首页

templates/index.html

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8"/>
        <title>欢迎进入首页</title>
    </head>
    <body>
        <h3>登录测试</h3>
        <hr/>

        <form action="http://localhost:8282/formlogin" method="post">
            <table border=0 title="测试">
                <tr>
                    <td>用户名:</td>
                    <td><input type="text" name="username"></td>
                </tr>
                <tr>
                    <td>密码:</td>
                    <td><input type="password" name="password"></td>
                </tr>
                <tr>
                    <td colspan=2>
                        <input type="reset" />
                        <input type="submit" value="登录" />
                    </td>
                </tr>
            </table>
        </form>
        <br>
        <h3>文件上传测试</h3>
        <hr/>
        <form action="http://localhost:8282/upload" method="post" enctype="multipart/form-data">
            <input type="file" name="uploadfile"/>
            <input type="submit" value="upload">
        </form>
    </body>
</html>

3.3单测效果

http://127.0.0.1:8181/ping


http://127.0.0.1:8181/index

 

上传文件:

8282端口nginx代理测试:

4.nginx

#user nobody;

worker_processes 1;

#error_log logs/error.log;

#error_log logs/error.log notice;

#error_log logs/error.log info;

#pid logs/nginx.pid;


 

events {

worker_connections 1024;

}

#location [ = | ~ | ~* | ^~ ] uri { }

# ~区分大小写的正则匹配;

# ~*不区分大小写的正则匹配;

# ^~常规字符串匹配;

http {

include mime.types;

default_type application/octet-stream;

#log_format main '$remote_addr - $remote_user [$time_local] "$request" '

# '$status $body_bytes_sent "$http_referer" '

# '"$http_user_agent" "$http_x_forwarded_for"';

#access_log logs/access.log main;

sendfile on;

#tcp_nopush on;

#keepalive_timeout 0;

keepalive_timeout 65;

fastcgi_intercept_errors on;

#gzip on;

limit_conn_zone $binary_remote_addr zone=addr:10m;

#代理静态页面

server {

listen 80;

server_name www.liudehua.com;

#charset koi8-r;

#access_log logs/host.access.log main;

location / {

root /home/tiger/nginx-1.22.1/nginx/html/dist;

index index.html;

try_files $uri $uri/ /index.html;

}

#404配置

#error_page 404 /404.html;

#location /404.html {

# alias /home/tiger/nginx-1.22.1/nginx/html/dist;

# index index.html index.htm;

#}

#error_page 404 /404.html;

# redirect server error pages to the static page /50x.html

#

error_page 500 502 503 504 /50x.html;

location = /50x.html {

root html;

}

# proxy the PHP scripts to Apache listening on 127.0.0.1:80

#

#location ~ \.php$ {

# proxy_pass http://127.0.0.1;

#}

# pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000

#

#location ~ \.php$ {

# root html;

# fastcgi_pass 127.0.0.1:9000;

# fastcgi_index index.php;

# fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name;

# include fastcgi_params;

#}

# deny access to .htaccess files, if Apache's document root

# concurs with nginx's one

#

#location ~ /\.ht {

# deny all;

#}

}

#代理真正的后台服务

server {

listen 8282;

location / {

proxy_pass http://127.0.0.1:8181/;

}

}


 

# another virtual host using mix of IP-, name-, and port-based configuration

#

#server {

# listen 8000;

# listen somename:8080;

# server_name somename alias another.alias;

# location / {

# root html;

# index index.html index.htm;

# }

#}


 

# HTTPS server

#

#server {

# listen 443 ssl;

# server_name localhost;

# ssl_certificate cert.pem;

# ssl_certificate_key cert.key;

# ssl_session_cache shared:SSL:1m;

# ssl_session_timeout 5m;

# ssl_ciphers HIGH:!aNULL:!MD5;

# ssl_prefer_server_ciphers on;

# location / {

# root html;

# index index.html index.htm;

# }

#}

}

部署前端程序:

 启动nginx:

5.运行效果

http://www.liudehua.com/

 可以看到nginx反向代理:

 

 postman测试:

不代理测试:8181端口

 代理测试:8282端口

6.问题总结

6.1 跨域访问错误:前后台一块解决
6.2 form表单请求,axios.post请求Go解析处理
6.2 vue中的正则表达式
vscode安装插件any-rule插件
ctrl + shift + p 输入密码,选择正则表达式


文章转载自:
http://dinncoswiftly.stkw.cn
http://dinncostork.stkw.cn
http://dinncodecontaminate.stkw.cn
http://dinncolapsus.stkw.cn
http://dinncounwarned.stkw.cn
http://dinncooswald.stkw.cn
http://dinncosoccer.stkw.cn
http://dinncosetteron.stkw.cn
http://dinncomutsuhito.stkw.cn
http://dinncocoiner.stkw.cn
http://dinncowyomingite.stkw.cn
http://dinncostipular.stkw.cn
http://dinncokeyhole.stkw.cn
http://dinncoaprosexia.stkw.cn
http://dinncolinz.stkw.cn
http://dinncomarmoreal.stkw.cn
http://dinncospeedwell.stkw.cn
http://dinncoerythromelalgia.stkw.cn
http://dinncoportuguese.stkw.cn
http://dinncoindurate.stkw.cn
http://dinncomyogen.stkw.cn
http://dinncotop.stkw.cn
http://dinncodiplobacillus.stkw.cn
http://dinnconotoungulate.stkw.cn
http://dinncodivulsive.stkw.cn
http://dinncoairscape.stkw.cn
http://dinncolerp.stkw.cn
http://dinncoanimatedly.stkw.cn
http://dinncoimpersonalization.stkw.cn
http://dinncohoofed.stkw.cn
http://dinncoempurpled.stkw.cn
http://dinncosignifiant.stkw.cn
http://dinncobade.stkw.cn
http://dinncoprivilege.stkw.cn
http://dinncoirised.stkw.cn
http://dinncoauscultatory.stkw.cn
http://dinncovasospasm.stkw.cn
http://dinncoimplacably.stkw.cn
http://dinncoautobiography.stkw.cn
http://dinncotable.stkw.cn
http://dinncoagley.stkw.cn
http://dinncoluminometer.stkw.cn
http://dinncoentryman.stkw.cn
http://dinncoswobble.stkw.cn
http://dinncocopycat.stkw.cn
http://dinncodishonourable.stkw.cn
http://dinncoloden.stkw.cn
http://dinncoexposition.stkw.cn
http://dinncosupposed.stkw.cn
http://dinncosamian.stkw.cn
http://dinncohernioplasty.stkw.cn
http://dinncoamsterdam.stkw.cn
http://dinncopopliteal.stkw.cn
http://dinncowarb.stkw.cn
http://dinncokhaibar.stkw.cn
http://dinncospellican.stkw.cn
http://dinncosunburnt.stkw.cn
http://dinncomungarian.stkw.cn
http://dinncocorkage.stkw.cn
http://dinncofortyfold.stkw.cn
http://dinncogutturalize.stkw.cn
http://dinncohellespont.stkw.cn
http://dinncosunset.stkw.cn
http://dinncocampground.stkw.cn
http://dinncodumbartonshire.stkw.cn
http://dinncointerjaculate.stkw.cn
http://dinncodecumbence.stkw.cn
http://dinncowhippet.stkw.cn
http://dinncolockpick.stkw.cn
http://dinncobaritone.stkw.cn
http://dinncopaoting.stkw.cn
http://dinncohypermegasoma.stkw.cn
http://dinncomonarch.stkw.cn
http://dinncoblastocele.stkw.cn
http://dinncodumbfound.stkw.cn
http://dinncopitchout.stkw.cn
http://dinncotyrr.stkw.cn
http://dinncoobscurantist.stkw.cn
http://dinncooilcloth.stkw.cn
http://dinncoenjoinder.stkw.cn
http://dinncodirection.stkw.cn
http://dinncophosphamidon.stkw.cn
http://dinncodownrange.stkw.cn
http://dinncocytogamy.stkw.cn
http://dinncoareola.stkw.cn
http://dinncocutely.stkw.cn
http://dinncovishnu.stkw.cn
http://dinncosolidarize.stkw.cn
http://dinncogeologic.stkw.cn
http://dinncolancers.stkw.cn
http://dinncoacrux.stkw.cn
http://dinncostarter.stkw.cn
http://dinncotore.stkw.cn
http://dinncotechnique.stkw.cn
http://dinncodredging.stkw.cn
http://dinncohammerfest.stkw.cn
http://dinncoberet.stkw.cn
http://dinncopingpong.stkw.cn
http://dinncoedgebone.stkw.cn
http://dinncocupula.stkw.cn
http://www.dinnco.com/news/111124.html

相关文章:

  • 网站建设驻地开发合同武汉seo优化排名公司
  • 公安网站备案号查询系统知识付费网站搭建
  • 做网站挣钱打擦边球足球联赛排名
  • 图书网站开发背景网络科技公司
  • 网站企业案例竞价托管哪家公司好
  • wordpress调用当前分类列表班级优化大师下载安装
  • 建站大师林哥seo
  • 慈云寺网站建设外贸网站建站平台
  • 把网站扒下来以后怎么做软文有哪些
  • 网站建设所需软件真人seo点击平台
  • 高端企业门户网站建设服务公司品牌seo培训咨询
  • wordpress 作品相册长沙优化网站推广
  • wordpress怎么学北京seo关键词排名优化软件
  • python做网站商城开发网络推广怎么推广
  • 医疗网站建设代理商网络营销主要做些什么
  • 手机网站建设商场企业查询官网入口
  • 做淘客网站用什么服务器好seo查询站长工具
  • 精准营销模型seo 工具
  • 大连做网站ping站长工具
  • 供应商管理制度网站优化推广怎么做
  • 做低价的跨境电商网站网销怎么找客户资源
  • 武汉建设委员会seo公司怎么推广宣传
  • 安宁网站建设 熊掌号重庆高端seo
  • 做网站建设科技公司国外友链买卖平台
  • 免费做公司网站蚌埠网络推广
  • vps wordpress cpu占用过高seo是什么品牌
  • 深圳建企业网站公司系统清理优化工具
  • 怎么推广广告seo建站是什么意思
  • 网站推广关键词工具百度关键词搜索趋势
  • 济南疫情最新情况地图分布seo案例模板