go开源webssh终端源码main.go分析

1.地址:  

https://github.com/Jrohy/webssh.git

2.添加中文注释地址:

https://github.com/tonyimax/webssh_cn.git

main.go分析

主包名:main

package main //主包名

依赖包加载

//导入依赖包
import ("embed"                       //可执行文件资源嵌入"flag"                        //标志变量"fmt"                         //格式化"github.com/gin-contrib/gzip" //压缩库"github.com/gin-gonic/gin"    //网页框架"io/fs"                       //文件系统"net/http"                    //http通信"os"                          //系统信息"strconv"                     //字符串转换"strings"                     //字符串"time"                        //时间"webssh/controller"           //websocket通信
)
在可执行文件中嵌入文件夹dist
//go:embed web/dist/*

访问集成文件夹文件系统

var f embed.FS //集成文件集合,取go:embed中文件夹中文件与文件夹列表
变量声明
var (//整形标志声明,用于储存整形指针port = flag.Int("p", //标志名5032,     //标志值"服务运行端口") //标志描述v        = flag.Bool("v", false, "显示版本号")authInfo = flag.String("a", "", "开启账号密码登录验证, '-a user:pass'的格式传参")//普通变量声明timeout    int    //连接超时savePass   bool   //保存密码version    string //版本号buildDate  string //编译时间goVersion  string //go版本号gitVersion string //git版本号username   string //用户名password   string //密码
)

初始化函数分析

func init() {}

初始化变量为标志

//初始化timeout变量为标志flag.IntVar(&timeout, //标志指针"t",              //标志名120,              //标志值"ssh连接超时时间(min)") //标志描述//初始化savePass变量为标志flag.BoolVar(&savePass, //标志指针"s",       //标志名true,      //标志值"保存ssh密码") //标志描述flag.StringVar(&version,"ver","v1.0.0","程序版本号")flag.StringVar(&goVersion,"gover","v1.22","go版本号")flag.StringVar(&gitVersion,"gitver","2.45.2","git版本号")flag.StringVar(&buildDate,"d",time.Now().String(),"编译日期")

操作环境变量

//查找环境变量savePassif envVal, ok := os.LookupEnv("savePass"); ok {//转换环境变量值为Bool值if b, err := strconv.ParseBool(envVal); err == nil {savePass = b //如果环境变量有值保存到savePass}}//读取环境变量用户验证信息if envVal, ok := os.LookupEnv("authInfo"); ok {*authInfo = envVal}//读取环境变量通信端口信息if envVal, ok := os.LookupEnv("port"); ok {//转换为整数if b, err := strconv.Atoi(envVal); err == nil {*port = b}}//必须在标志定义之后及程序访问之前调用flag.Parse()

参数检测

//如果有-v参数,显示版本号信息if *v {fmt.Printf("Version: %s\n\n", version)fmt.Printf("BuildDate: %s\n\n", buildDate)fmt.Printf("GoVersion: %s\n\n", goVersion)fmt.Printf("GitVersion: %s\n\n", gitVersion)os.Exit(0)}

用户名与密码参数分割 (-a user:pass'的格式传参)

if *authInfo != "" {//分割用户名与密码accountInfo := strings.Split(*authInfo, ":")//非空判断if len(accountInfo) != 2 ||accountInfo[0] == "" ||accountInfo[1] == "" {fmt.Println("请按'user:pass'的格式来传参或设置环境变量, 且账号密码都不能为空!")os.Exit(0)}//保存用户名与密码username, password = accountInfo[0], accountInfo[1]}

静态路由函数分析

func staticRouter(router *gin.Engine) {}

创建用户键值对

//创建账户mapaccountList := map[string]string{username: password,}

授权并写页面

//授权路由//传入用户列表{用户:密码}authorized := router.Group("/", gin.BasicAuth(accountList))authorized.GET("", func(c *gin.Context) {//读取主页面indexHTML, _ := f.ReadFile("web/dist/" + "index.html")//向上下文写入主页面c.Writer.Write(indexHTML)})

http操作静态资源

staticFs, _ := fs.Sub(f, "web/dist/static")
router.StaticFS("/static", http.FS(staticFs))

main主函数分析

func main() {}

设置http服务参数并启用路由

//取web引擎实例server := gin.Default()//设置可信代理server.SetTrustedProxies(nil)//使用压缩中间件,支持资源压缩功能server.Use(gzip.Gzip(gzip.DefaultCompression))//启动路由staticRouter(server)

HTTP服务操作:

//HTTP服务操作//GET操作,连接终端websocketserver.GET("/term", func(c *gin.Context) {//调用终端websocketcontroller.TermWs(c, time.Duration(timeout)*time.Minute)})//GET操作,SSH服务检测server.GET("/check", func(c *gin.Context) {//检测SSH服务responseBody := controller.CheckSSH(c)//保存连接密码responseBody.Data = map[string]interface{}{"savePass": savePass,}//渲染JSON数据及HTTP状态码给客户端c.JSON(200, responseBody)})

文件资源操作:

//文件资源操作file := server.Group("/file"){//请求文件列表file.GET("/list", func(c *gin.Context) {c.JSON(200, controller.FileList(c))})//下载文件file.GET("/download", func(c *gin.Context) {controller.DownloadFile(c)})//上传文件file.POST("/upload", func(c *gin.Context) {c.JSON(200, controller.UploadFile(c))})//上传/下载进度处理file.GET("/progress", func(c *gin.Context) {controller.UploadProgressWs(c)})}

启动HTTP服务

//启动HTTP服务server.Run(fmt.Sprintf(":%d", *port))

启动成功输出 如下日志:

[GIN-debug] [WARNING] Creating an Engine instance with the Logger and Recovery middleware already attached.[GIN-debug] [WARNING] Running in "debug" mode. Switch to "release" mode in production.- using env:	export GIN_MODE=release- using code:	gin.SetMode(gin.ReleaseMode)[GIN-debug] GET    /                         --> main.staticRouter.func2 (4 handlers)
[GIN-debug] GET    /static/*filepath         --> github.com/gin-gonic/gin.(*RouterGroup).createStaticHandler.func1 (4 handlers)
[GIN-debug] HEAD   /static/*filepath         --> github.com/gin-gonic/gin.(*RouterGroup).createStaticHandler.func1 (4 handlers)
[GIN-debug] GET    /term                     --> main.main.func1 (4 handlers)
[GIN-debug] GET    /check                    --> main.main.func2 (4 handlers)
[GIN-debug] GET    /file/list                --> main.main.func3 (4 handlers)
[GIN-debug] GET    /file/download            --> main.main.func4 (4 handlers)
[GIN-debug] POST   /file/upload              --> main.main.func5 (4 handlers)
[GIN-debug] GET    /file/progress            --> main.main.func6 (4 handlers)
[GIN-debug] Listening and serving HTTP on :5032

main.go

package main //主包名
//导入依赖包
import ("embed"                       //可执行文件资源嵌入"flag"                        //标志变量"fmt"                         //格式化"github.com/gin-contrib/gzip" //压缩库"github.com/gin-gonic/gin"    //网页框架"io/fs"                       //文件系统"net/http"                    //http通信"os"                          //系统信息"strconv"                     //字符串转换"strings"                     //字符串"time"                        //时间"webssh/controller"           //websocket通信
)// 在可执行文件中嵌入文件夹dist
//
//go:embed web/dist/*
var f embed.FS //集成文件集合,取go:embed中文件夹中文件与文件夹列表
// 变量声明
var (//整形标志声明,用于储存整形指针port = flag.Int("p", //标志名5032,     //标志值"服务运行端口") //标志描述v        = flag.Bool("v", false, "显示版本号")authInfo = flag.String("a", "", "开启账号密码登录验证, '-a user:pass'的格式传参")//普通变量声明timeout    int    //连接超时savePass   bool   //保存密码version    string //版本号buildDate  string //编译时间goVersion  string //go版本号gitVersion string //git版本号username   string //用户名password   string //密码
)// 初始化
func init() {//初始化timeout变量为标志flag.IntVar(&timeout, //标志指针"t",              //标志名120,              //标志值"ssh连接超时时间(min)") //标志描述//初始化savePass变量为标志flag.BoolVar(&savePass, //标志指针"s",       //标志名true,      //标志值"保存ssh密码") //标志描述flag.StringVar(&version,"ver","v1.0.0","程序版本号")flag.StringVar(&goVersion,"gover","v1.22","go版本号")flag.StringVar(&gitVersion,"gitver","2.45.2","git版本号")flag.StringVar(&buildDate,"d",time.Now().String(),"编译日期")//查找环境变量savePassif envVal, ok := os.LookupEnv("savePass"); ok {//转换环境变量值为Bool值if b, err := strconv.ParseBool(envVal); err == nil {savePass = b //如果环境变量有值保存到savePass}}//读取环境变量用户验证信息if envVal, ok := os.LookupEnv("authInfo"); ok {*authInfo = envVal}//读取环境变量通信端口信息if envVal, ok := os.LookupEnv("port"); ok {//转换为整数if b, err := strconv.Atoi(envVal); err == nil {*port = b}}//必须在标志定义之后及程序访问之前调用flag.Parse()//如果有-v参数,显示版本号信息if *v {fmt.Printf("Version: %s\n\n", version)fmt.Printf("BuildDate: %s\n\n", buildDate)fmt.Printf("GoVersion: %s\n\n", goVersion)fmt.Printf("GitVersion: %s\n\n", gitVersion)os.Exit(0)}if *authInfo != "" {//分割用户名与密码accountInfo := strings.Split(*authInfo, ":")//非空判断if len(accountInfo) != 2 ||accountInfo[0] == "" ||accountInfo[1] == "" {fmt.Println("请按'user:pass'的格式来传参或设置环境变量, 且账号密码都不能为空!")os.Exit(0)}//保存用户名与密码username, password = accountInfo[0], accountInfo[1]}
}// 启动静态路由
func staticRouter(router *gin.Engine) {//如果密码不为空if password != "" {//创建账户mapaccountList := map[string]string{username: password,}//授权路由//传入用户列表{用户:密码}authorized := router.Group("/", gin.BasicAuth(accountList))authorized.GET("", func(c *gin.Context) {//读取主页面indexHTML, _ := f.ReadFile("web/dist/" + "index.html")//向上下文写入主页面c.Writer.Write(indexHTML)})} else {router.GET("/", func(c *gin.Context) {indexHTML, _ := f.ReadFile("web/dist/" + "index.html")c.Writer.Write(indexHTML)})}//http操作静态资源staticFs, _ := fs.Sub(f, "web/dist/static")router.StaticFS("/static", http.FS(staticFs))
}func main() {//取web引擎实例server := gin.Default()//设置可信代理server.SetTrustedProxies(nil)//使用压缩中间件,支持资源压缩功能server.Use(gzip.Gzip(gzip.DefaultCompression))//启动路由staticRouter(server)//HTTP服务操作//GET操作,连接终端websocketserver.GET("/term", func(c *gin.Context) {//调用终端websocketcontroller.TermWs(c, time.Duration(timeout)*time.Minute)})//GET操作,SSH服务检测server.GET("/check", func(c *gin.Context) {//检测SSH服务responseBody := controller.CheckSSH(c)//保存连接密码responseBody.Data = map[string]interface{}{"savePass": savePass,}//渲染JSON数据及HTTP状态码给客户端c.JSON(200, responseBody)})//文件资源操作file := server.Group("/file"){//请求文件列表file.GET("/list", func(c *gin.Context) {c.JSON(200, controller.FileList(c))})//下载文件file.GET("/download", func(c *gin.Context) {controller.DownloadFile(c)})//上传文件file.POST("/upload", func(c *gin.Context) {c.JSON(200, controller.UploadFile(c))})//上传/下载进度处理file.GET("/progress", func(c *gin.Context) {controller.UploadProgressWs(c)})}//启动HTTP服务server.Run(fmt.Sprintf(":%d", *port))
}

 

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

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

相关文章

申请SSL证书 SSL是如何保护网站安全的

随着互联网的不断发展,网络安全问题日益凸显,特别是在数据传输和存储方面。为了保护网站和用户的数据安全,SSL(安全套接层)技术应运而生,成为了保护网站安全的重要工具。本文将详细介绍SSL如何保护网站安全…

星光云720全景VR系统源码

星光云720全景VR系统源码 系统体验地址项目介绍JDK版本后端主要依赖前端框架前端node 版本用户端框架介绍技术选型依赖全景内容简介系统图片部分功能截图系统体验地址 系统体验地址 VR全景系统体验地址 账号:18175760278 密码:12345678 项目介绍 JDK版…

C语言_指针初阶(进阶还在更新中)

指针是什么 指针是内存中一个最小单元的编号,也就是地址平时口语中说的指针,通常指的是指针变量,是用来存放内存地址的变量指针就是地址,口语中说的指针通常指的是指针变量。我们可以通过&(取地址操作符&#xff…

WSL——忘记root密码(Ubuntu)

1、问题描述 Windows下的WSL(Ubuntu)忘记了root密码,无法使用管理员权限。 2、解决方法 关闭 Ubuntu 窗口。打开 Windows 的 Powershell 或 cmd, 以 root 默认登陆 WSL。 wsl -u root 修改对应用户密码。 # xxx为要修改密码的用…

2024年第十四届APMCM亚太地区大学生数学建模竞赛

C 题 基于量子计算的物流配送问题 随着电子商务的迅猛发展,电商平台对物流配送的需求日益增长。为了确保货物能够按时、高效地送达消费者手中,电商平台与第三方物流公司建立了紧密的合作关系。然而,面对大量的货物和多样的目的地&#xff0c…

女性经济崛起,天润融通用客户感知挖掘市场潜力

每逢一年一度的国际妇女节,“女性”话题都会被郑重地讨论。 从消费市场上来说,最近几年女性群体正在拥有越来越大的影响力,甚至出现了“她经济”这样的专属词汇在最近几年被市场反复讨论。 毫无疑问,女性消费群体的崛起已经成为…

EXTI寄存器,AFIO的简洁,EXTI配置的流程

一,AFIO简介 AFIO是Alternate Function Input/Output 的缩写,表示复用功能IO,主要用于实现IO端口的复用功能以及外部中断的控制 STM32外设有很多I/O以及内置外设(如12C,ADC,ISP,USART等)。为节省引出管脚的…

科普文:Linux服务器性能调优概叙

概叙 Java web应用性能分析之服务端慢和优化概叙_cpu飙高java-CSDN博客 Java web应用性能分析之【CPU飙升分析概述】_web页面性能分析cpu占满是因为死循环,还是循环过多-CSDN博客 在我们的软件服务中,软件部署的服务器,一般都是linux服务器&#xff0c…

Hadoop-11-MapReduce JOIN 操作的Java实现 Driver Mapper Reducer具体实现逻辑 模拟SQL进行联表操作

章节内容 上一节我们完成了: MapReduce的介绍Hadoop序列化介绍Mapper编写规范Reducer编写规范Driver编写规范WordCount功能开发WordCount本地测试 背景介绍 这里是三台公网云服务器,每台 2C4G,搭建一个Hadoop的学习环境,供我学…

实验六 SQL数据查询—单表查询

题目 打开ecommerce数据库,用SQL语句完成下列各项查询要求: 查询每位员工的员工编号empno、员工姓名empname、联系电话telephone和所在部门名称depname查询已下订单的商品的orderno、memname、proname、qty、totalmoney信息查询会员订单总金额超过2000的…

vue-org-tree搜索到对应项高亮展开

效果图&#xff1a; 代码&#xff1a; <template><div class"AllTree"><el-form :inline"true" :model"formInline" class"demo-form-inline"><el-form-item><el-input v-model"formInline.user&quo…

11-阿里云服务器 ECS-FileZilla的文件传输

FileZilla的下载与安装以及简单使用(有图解超简单)-CSDN博客 Windows下 FileZilla客户端下载与安装 官方下载地址:https://www.filezilla.cn/download 绿色版我们可以理解为免安装版本,而安装版本则是需要运行Setup的引导程序,最大的区别就是会不会生成注册表。 filezi…

2024/07/04

1、梳理笔记(原创) 2、终端输入一个日期&#xff0c;判断是这一年的第几天 scanf("%d-%d-%d",&y,&m,&d); 闰年2月29天&#xff0c;平年2月28天 #include<stdio.h> int main(int argc, char const *argv[]) {int y0,m0,d0;printf("please ente…

OpenCV基础(2)

目录 滤波处理 均值滤波 基本原理 函数用法 程序示例 高斯滤波 基本原理 函数用法 程序示例 中值滤波 基本原理 函数用法 程序示例 形态学 腐蚀 膨胀 通用形态学函数 前言&#xff1a;本部分是上一篇文章的延续&#xff0c;前面部分请查看&#xff1a;OpenCV…

航模插头篇

一、常见的电池插头&#xff08;电调端 是公头 电池端 是母头&#xff09; 电池总是被插的 1.XT60头 过流大 安全系数高 难插拔 2.T插 插拔轻松 过流比较小 容易发烫 电调端 是公头 电池端 是母头 3.香蕉头插孔 过流够 插拔轻松 但 容易插反 爆炸 4.TX90(和XT60差…

命令行升级ubuntu版本过程中出现的grub问题 解决

1、问题描述 使用命令行升级ubuntu18到20版本后&#xff0c;系统提示重启&#xff0c;使用reboot命令重启后&#xff0c;不显示服务器ip&#xff0c;或是显示但无法ssh远程连接服务器了&#xff0c;使用屏幕连接服务器后发现出现grub问题。 2、问题经过 命令行输入如下升级u…

腾讯云函数部署环境[使用函数URL]

使用函数URL 之前使用的是网关API,最近腾讯云的网关API说要关闭了,所以没有办法这里改成函数URL,使用后发现只要不是在浏览器直接访问的情况,函数URL都可以满足! 这里结合腾讯云函数node.js返回自动带反斜杠这篇文章来做说明,比如这里的URL如下: 结合文章腾讯云函数node.js返…

Altium Designer专业PCB设计软件下载安装 Altium Designer安装包下载获取

在电子设计的广袤领域中&#xff0c;PCB设计无疑占据着重要的地位。而Altium Designer作为一款业界领先的电子设计自动化软件&#xff0c;其提供的先进布局工具&#xff0c;无疑为设计师们打开了一扇通往高效、精确设计的大门。 在PCB设计的核心环节——布局中&#xff0c;Alti…

初出茅庐的小李博客之C语言文件操作

C语言文件操作 在C语言中&#xff0c;文件操作主要是通过标准库函数来实现的。 今天有时间就来学习下一些常用的文件操作函数&#xff1a; C 语言提供了一个 FILE 数据结构&#xff0c;记录了操作一个文件所需要的信息。该结构定义在头文件stdio.h&#xff0c;所有文件操作函…