Gpt微信小程序搭建的前后端流程 - 后端基础框架的搭建(三)
Gpt微信小程序搭建的前后端流程 - 后端基础框架的搭建(三)
Gpt微信小程序 只需要几个API,API上一小节也有讲到。直接用 gin 或者 beego 简单搭web服务器就够了。我们这里还用 go-micro微服务 去搭建,主要也是为了学以致用,把之前go-micro系列播客衔接上,以及后续好的横纵向扩展。
整体的代码框架:

pkg通用库中用到的db数据库,redis和mq队列,大部分都是前面go-micro系列有用到的。internal内部的微服务目录也是在之前go-micro单个微服务目录格式上调整。
这里主要看配置解析, 配置解析用得是toml库, github.com/BurntSushi/toml
pkg目录

配置的代码解析,用一个接口(基类) IConfig
pkg/config/config.go
type IConfig interface {//服务名AppName() string//运行模式AppEnv() string//日志的定义LogFilePath() stringLogMaxAge() intLogMaxSize() intLogBackUpNum() int//mysql关系型数据库SchemeConfig() map[string]*SchemeConfig//redisRedisConfig() map[string]*RedisConfig//rabbitmqAmqpConfig() map[string]*AmqpConfig
}// log日志库基本配置
type LogConfig struct {Type string `yaml:"Type",toml:"Type"`LogDir string `yaml:"LogDir",toml:"LogDir"`LogName string `yaml:"LogName",toml:"LogName"`LogMaxAge int `yaml:"LogMaxAge",toml:"LogMaxAge"` // 日志的过期时间,单位为天LogMaxSize int `yaml:"LogMaxSize",toml:"LogMaxSize"` // 日志文件的最大LogBackUpNum int `yaml:"LogBackUpNum",toml:"LogBackUpNum"` // 日志文件最多保留个数}// 服务配置
type Config struct {ConfPath string //配置路径AppPath string //项目路径Scheme map[string]*SchemeConfig `yaml:"Scheme",toml:"Scheme"`Redis map[string]*RedisConfig `yaml:"Redis",toml:"Redis"`Amqp map[string]*AmqpConfig `yaml:"Amqp",toml:"Amqp"`Log *LogConfig `yaml:"Log",toml:"Log"`
}// App 的基本配置
type AppBaseConfig struct {AppName string `yaml:"AppName",toml:"AppName"`Env string `yaml:"Env",toml:"Env"`Version string `yaml:"Version",toml:"Version"` // 版本
}type AppConfig struct {ConfigApp AppBaseConfig
}
pkg/config/scheme.go
// 关系型数据库的配置
type SchemeConfig struct {// mysql pgsqlDriver string `yaml:"Driver",toml:"Driver"`Dsn string `yaml:"Dsn",toml:"Dsn"`// 建立最大的连接数MaxOpenConns int `yaml:"MaxOpenConns",toml:"MaxOpenConns"`// 最大的空闲连接数MaxIdleConns int `yaml:"MaxIdleConns",toml:"MaxIdleConns"`// 一条连接存活的最长时间ConnMaxLifeTime int `yaml:"ConnMaxLifeTime",toml:"ConnMaxLifeTime"`
}
pkg/config/redis.go
// redis配置
type RedisConfig struct {Addr string `yaml:"Addr",toml:"Addr"` // host:portPassword string `yaml:"Password",toml:"Password"`MaxConnNum int `yaml:"MaxConnNum",toml:"MaxConnNum"`InitConnNum int `yaml:"InitConnNum",toml:"InitConnNum"`IdleTimeout int `yaml:"IdleTimeout",toml:"IdleTimeout"`PingStep int `yaml:"PingStep",toml:"PingStep"`RetryTimes int `yaml:"RetryTimes",toml:"RetryTimes"`
}
pkg/config/amqp.go
// rabbitmq
type AmqpConfig struct {Addr string `toml:"Addr"`Port int `toml:"Port"`User string `toml:"User"`Pwd string `toml:"Pwd"`MaxConnection int `toml:"MaxConnection"`MaxChannel int `toml:"MaxChannel"`VirtualHost string `toml:"VirtualHost"`Type int `toml:"Type"`
}
对应的toml配置格式:
config/test_service/app.toml
[App]AppName = "test_service"Version = "1.0"Env = "dev"[Log]Type = "log" # 默认是log, 可以是redis, kafka获取是其他的,如果是其他的请在 log中实现LogDir = "/log"LogName = "error_log.log"LogMaxAge = 7 # 单位 day,日志最多可以保存多长时间。只有 Type 为File时才会有效LogMaxSize = 10 # 文件大小(M),10MLogBackUpNum = 10 # 文件保留最多个数[Scheme]# 放置数据库连接信息[Scheme.base]Driver = "mysql"Dsn = "root:root@tcp(127.0.0.1:3306)/test?charset=utf8mb4&parseTime=true"MaxOpenConns = 60MaxIdleConns = 20ConnMaxLifeTime = 1200[Redis][Redis.base]Addr = "127.0.0.1:6379"Password = "11111111"MaxConnNum = 20InitConnNum = 1IdleTimeout = 7200 #最大idle时间PingStep = 10 #两次ping之间间隔RetryTimes = 3 #获取连接重试次数[Amqp][Amqp.publish]Addr = "127.0.0.1"Port = 5672User = "guest"Pwd = "guest"MaxConnection = 4VirtualHost = "/"Type = 1 # 1生产者;2消费者[Amqp.consume]Addr = "127.0.0.1"Port = 5672User = "guest"Pwd = "guest"MaxConnection = 10MaxChannel = 10VirtualHost = "/"Type = 2 # 1生产者;2消费者
最后的配置解析
pkg/config/parse.go
// 解析配置
func ParseConfig() {verifyConf()toml.DecodeFile(Conf.ConfPath, Conf)
}func verifyConf() {if fl, err := os.Stat(Conf.ConfPath); err != nil {if os.IsNotExist(err) {fmt.Println(Conf.ConfPath)fmt.Printf("config file %s not exists", Conf.ConfPath)os.Exit(0)}} else {fl.Mode().Perm()}
}// 获取项目当前路径
func getRunPath() string {rst, err := os.Getwd()if err != nil {return ""}return rst
}
这里,通用log日志库,mysql,redis,rabbitmq的配置解析和初始代码就好了,接下来就是微服务的初始化调用和启动了。
微服务目录

微服务初始化代码, init.go和elog.go
internal/test_service/init.go
// 服务
type EmicroService struct {Server micro.ServiceHost stringPort uintAddr string
}// 服务的自定义配置
type ServerConfig struct {ServerLog map[string]*config.LogConfig
}// 服务内部配置
type Conf struct {Config *config.AppConfig //pkg通用配置ServerConfig *ServerConfig
}// 服务操作对象
var Service *EmicroService// 日志库操作对象,对pkg的日志再封装
var Logger *zap.Logger// 服务内部配置操作对象
var Config *Conffunc init() {Service = NewService()Config = NewConfig()
}func NewService() *EmicroService {service := new(EmicroService)return service
}func NewConfig() *Conf {return new(Conf)
}// 初始化
func Init(confPath string) {//指定配置文件路径config.Conf.ConfPath = confPath//解析配置config.ParseConfig()// 处理日志文件路径和日志等级config.Conf.Log.LogDir = config.Conf.GetAppPath() + config.Conf.Log.LogDir + "/" + config.Conf.AppName()// 默认日志等级为errorvar level stringif config.Conf.AppEnv() == "dev" {level = "debug"} else {level = "error"}// 初始化通用日志库logObj.LoggerInit(config.Conf, level)Logger = logObj.Logger()// 初始数据库,Redis等database.Init(config.Conf)// 解析服务内部自定义配置Config.Config = config.Configer()var serverConf = new(ServerConfig)serverConfPath := Config.Config.GetAppPath() + "/internal/test_service/config/server.toml"toml.DecodeFile(serverConfPath, serverConf)Config.ServerConfig = serverConf// 初始化自定义的loginitServerLog(level)
}
internal/test_service/elog.go
// 服务自定义的log日志库操作对象
var ServerLogger map[string]*zap.Logger
var logLevel string// 初始化自定义的log
func initServerLog(level string){ServerLogger = make(map[string]*zap.Logger, len(Config.ServerConfig.ServerLog))logLevel = levelfor logName, logInfo := range Config.ServerConfig.ServerLog{logInfo.LogDir = config.Conf.AppPath + logInfo.LogDir + string(os.PathSeparator) +logNamelog, err := newServerLog(logInfo)if err != nil{panic("init server log err:" + err.Error())}ServerLogger[logName] = log}
}func newServerLog(logInfo *config.LogConfig) (*zap.Logger, error){var console boolif Config.Config.AppEnv() == "dev" {console = true}else{console = false}logInfo.LogName = getLogFilename()return logObj.CreateLogger(logLevel, console, logInfo)
}func getLogFilename() string {currentTime := time.Now()return currentTime.Format("2006-01-02") + ".log"
}
启动代码在internal/test_service/server/server.go,跟之前go-micro系列播客的微服务启动一样,这里不再列明。
启动脚本: cmd/test_service/main.go
package mainimport("emicro-go-base/internal/test_service/server"
)func main() {server.RunTestService(":8080", "../../config/test_service/app.toml")
}
后端基础的框架就大概这样,一些太细的细节代码就没全贴出来了,后续具体实现API章节会再继续贴。
最后
可以先体验如下的微信小程序,该专栏系列都是参考小柠AI智能聊天来展开,小程序整体的gpt交互直接,界面也容易,对我们上手仿照在实现方面也比较友好。
体验方式:
- 微信小程序直接搜小柠AI智能聊天
- 扫码下图

相关文章:
Gpt微信小程序搭建的前后端流程 - 后端基础框架的搭建(三)
Gpt微信小程序搭建的前后端流程 - 后端基础框架的搭建(三) Gpt微信小程序 只需要几个API,API上一小节也有讲到。直接用 gin 或者 beego 简单搭web服务器就够了。我们这里还用 go-micro微服务 去搭建,主要也是为了学以致用,把之前go-micro系列…...
jstat(JVM Statistics Monitoring Tool):虚拟机统计信息监视工具
jstat(JVM Statistics Monitoring Tool):虚拟机统计信息监视工具 用于监视虚拟机各种运行状态信息的命令行工具。 它可以显示本地或者远程虚拟机进程中的类加载、内存、垃圾收集、即时编译等运行时数据,在没有GUI图形界面、只提…...
【ARM】Day6 cotex-A7核UART总线实验
cotex-A7核UART总线实验 1. 键盘输入一个字符‘a’,串口工具显示‘b’ 2. 键盘输入一个字符串"nihao",串口工具显示“nihao” uart.h #ifndef __UART4_H__ #define __UART4_H__#include "stm32mp1xx_rcc.h" #include "stm3…...
HTTPS代理搭建技巧分享
今天我们来分享一下如何搭建一个能够实现中间人 检测和防护的HTTPS代理。保护我们的网络通信安全是至关重要的,让我们一起学习如何构建一个安全可靠的HTTPS代理吧! 什么是中间人 ? 首先,让我们来了解一下什么是中间人 。中间人 是…...
第四章:树形结构的关联式容器(map+set)
系列文章目录 文章目录 系列文章目录前言1、关联式容器与序列式容器1.1 键值对 2、set的介绍3、multiset的介绍3.1 接口count与容器multiset 4、map的介绍4.1 接口insert4.2 operator[]和at 5、multimap的介绍 前言 根据应用场景的不桶,STL总共实现了两种不同结构的…...
SpringBoot +Vue3 简单的前后端交互
前端:Vue3 创建项目: npm create vuelatest > cd <your-project-name> > npm install > npm run dev 项目结构图如下: 1、查看入口文件内容:main.js 代码如下: import ./assets/main.css impor…...
【Android】Mobile-Security-Framework-MobSF Manifest 静态扫描规则
前言 移动安全框架(MobSF)是一个自动化的一体化移动应用程序(Android/iOS/Windows)测试、恶意软件分析和安全评估框架,能够执行静态和动态分析。MobSF支持移动应用程序二进制文件(APK、XAPK、IPA和APPX&am…...
【C++】初谈迭代器
文章目录 前言一、什么是迭代器二、迭代器的分类三、迭代器的用法总结 前言 迭代器是一种可以访问和遍历容器中元素的对象,它类似于指针,但是具有更多的功能和灵活性。本文将介绍C迭代器的基本概念、分类、用法和注意事项。 一、什么是迭代器 迭代器&a…...
PL端案例开发手册
目 录 前 言 1 工程编译、程序加载方法 1.1 工程编译 1.2 程序加载 2 led-flash 2.1 案例说明 2.2 操作说明 2.3 关键代码 更多帮助 前 言 本文主要介绍PL端案例的使用说明,适用开发环境:Windows 7/10 64bit、Xilinx Unified 20…...
华为OD-整数对最小和
题目描述 给定两个整数数组array1、array2,数组元素按升序排列。假设从array1、array2中分别取出一个元素可构成一对元素,现在需要取出k对元素,并对取出的所有元素求和,计算和的最小值 代码实现 # coding:utf-8 class Solution:…...
Ubuntu 22LTS 配置静态IP
可行方法,需界面配置 转载自:哔哩哔哩链接地址 命令行配置:待补充...
【Python】Python爬虫:网络数据的提取利器
随着互联网的快速发展,网络数据已经成为了一项重要的资源。如何从海量的网络数据中提取出我们需要的信息,就成为了各个行业都需要解决的问题。而Python爬虫,就是解决这个问题的利器。 首先,让我们了解一下什么是Python爬虫。Pyth…...
20.图的遍历
目录 一. 深度优先遍历 二. 广度优先遍历 图的遍历算法和二叉树不同的是,图中可能存在回路,且图的任一顶点都可能与其它顶点相通,在访问完某个顶点之后可能会沿着某些边又回到了曾经访问过的顶点。为了避免重复访问,我们的解决思…...
ARM DIY(一)电源、SD卡座、SOC 调试
文章目录 前言加热台焊接热风枪吹焊电烙铁补焊电源调试SD 卡座调试DRAM 电路调试串口电路调试SOC 调试成品 前言 之前打样的几块 ARM 板,一直放着没去焊接。今天再次看到,决定把它焊起来。 加热台焊接 为了提高焊接效率,先使用加热台焊接…...
数学建模知识之小白入门篇
数学建模知识--小白入门篇 一、数学模型的定义二、建立数学模型的方法和步骤1. 模型准备2. 模型假设3. 模型构成4. 模型求解5. 模型分析 三、数模竞赛出题的指导思想四、竞赛中的常见题型1. 实际问题背景2.若干假设条件3.要求回答的问题 五、提交一篇论文…...
【日常积累】Linux下ftp服务安装
概述 FTP是一种在互联网中进行文件传输的协议,基于客户端/服务器模式,默认使用20、21号端口,其中端口20用于进行数据传输,端口21用于接受客户端发出的相关FTP命令与参数。FTP服务器普遍部署于内网中,具有容易搭建、方…...
确定了,TikTok将于9月12日正式关闭美国半闭环
外媒报道称,TikTok已对其官网的常见问题页面进行了更新。消息显示,其在美国和英国市场运营的半封闭模式将于9月12日正式结束,并将全力推进TikTok闭环小店业务。尽管我们早在本月初就获悉了这一消息,但实际得知后仍不免有些感慨。曾…...
ATFX汇评:英国7月零售销售年率大降,GBPUSD仍未升破1.3000
ATFX汇评:7月季调后零售销售年率,最新值-3.2%,前值-1.6%,降幅扩大;7月季调后核心零售销售年率,最新值-3.4%,前值-1.6%,降幅扩大。零售销售综合衡量除服务业外包括所有主要从事零售业…...
CTFhub-sqli注入-Referer注入
在最后添加 Referer: (注意 R 大写, Referer后面是 :,Content-Length: 与 Referer: 之间没有空行) 1 2 3 1 union select 1,database() -1 union select 1,database() -1 union select 1,group_concat(table_name)from information_sche…...
【案例】登录注册
<template><div class"loginhome"><Header :butShow"butShow"></Header><div class"formdiv"><div style"text-align:center;padding:10px;"><h3>你好登录账号{{ stauts 3? 注册:登录 }}…...
[2025CVPR]DeepVideo-R1:基于难度感知回归GRPO的视频强化微调框架详解
突破视频大语言模型推理瓶颈,在多个视频基准上实现SOTA性能 一、核心问题与创新亮点 1.1 GRPO在视频任务中的两大挑战 安全措施依赖问题 GRPO使用min和clip函数限制策略更新幅度,导致: 梯度抑制:当新旧策略差异过大时梯度消失收敛困难:策略无法充分优化# 传统GRPO的梯…...
零门槛NAS搭建:WinNAS如何让普通电脑秒变私有云?
一、核心优势:专为Windows用户设计的极简NAS WinNAS由深圳耘想存储科技开发,是一款收费低廉但功能全面的Windows NAS工具,主打“无学习成本部署” 。与其他NAS软件相比,其优势在于: 无需硬件改造:将任意W…...
ubuntu搭建nfs服务centos挂载访问
在Ubuntu上设置NFS服务器 在Ubuntu上,你可以使用apt包管理器来安装NFS服务器。打开终端并运行: sudo apt update sudo apt install nfs-kernel-server创建共享目录 创建一个目录用于共享,例如/shared: sudo mkdir /shared sud…...
服务器硬防的应用场景都有哪些?
服务器硬防是指一种通过硬件设备层面的安全措施来防御服务器系统受到网络攻击的方式,避免服务器受到各种恶意攻击和网络威胁,那么,服务器硬防通常都会应用在哪些场景当中呢? 硬防服务器中一般会配备入侵检测系统和预防系统&#x…...
大数据学习(132)-HIve数据分析
🍋🍋大数据学习🍋🍋 🔥系列专栏: 👑哲学语录: 用力所能及,改变世界。 💖如果觉得博主的文章还不错的话,请点赞👍收藏⭐️留言Ǵ…...
【数据分析】R版IntelliGenes用于生物标志物发现的可解释机器学习
禁止商业或二改转载,仅供自学使用,侵权必究,如需截取部分内容请后台联系作者! 文章目录 介绍流程步骤1. 输入数据2. 特征选择3. 模型训练4. I-Genes 评分计算5. 输出结果 IntelliGenesR 安装包1. 特征选择2. 模型训练和评估3. I-Genes 评分计…...
Yolov8 目标检测蒸馏学习记录
yolov8系列模型蒸馏基本流程,代码下载:这里本人提交了一个demo:djdll/Yolov8_Distillation: Yolov8轻量化_蒸馏代码实现 在轻量化模型设计中,**知识蒸馏(Knowledge Distillation)**被广泛应用,作为提升模型…...
A2A JS SDK 完整教程:快速入门指南
目录 什么是 A2A JS SDK?A2A JS 安装与设置A2A JS 核心概念创建你的第一个 A2A JS 代理A2A JS 服务端开发A2A JS 客户端使用A2A JS 高级特性A2A JS 最佳实践A2A JS 故障排除 什么是 A2A JS SDK? A2A JS SDK 是一个专为 JavaScript/TypeScript 开发者设计的强大库ÿ…...
在 Spring Boot 项目里,MYSQL中json类型字段使用
前言: 因为程序特殊需求导致,需要mysql数据库存储json类型数据,因此记录一下使用流程 1.java实体中新增字段 private List<User> users 2.增加mybatis-plus注解 TableField(typeHandler FastjsonTypeHandler.class) private Lis…...
MyBatis中关于缓存的理解
MyBatis缓存 MyBatis系统当中默认定义两级缓存:一级缓存、二级缓存 默认情况下,只有一级缓存开启(sqlSession级别的缓存)二级缓存需要手动开启配置,需要局域namespace级别的缓存 一级缓存(本地缓存&#…...
