wordpress站群搭建6外部库的引入和测试

news2024/12/26 21:46:05

wordpress站群搭建6wordpress外部库的引入和测试

本次目标我们主要讲解引入wordpress外部库并测试。

我们将一些外部库和工具包放入到pkg项目,方便其他项目引用。

1.安装go-wordpress库

进入到pkg项目

go get github.com/robbiet480/go-wordpress

2.编写工具类

我们在添加station的时候,在之前的代码中我们有几个todo,现在我们将这几个todo进行处理。

// todo 校验wordpress账号密码

// todo 加密密码

// todo 自动获取服务器ip

pkg包下创建 wordpressutil目录,创建wordpressutil.go文件,编写 创建客户端和测试账号密码方法。

wordpressutil.go

package wordpressutil

import (
	"context"
	"fmt"

	"github.com/robbiet480/go-wordpress"
)

// 创建wordpress客户端
func Client(DomainName string, Username string, Password string) (client *wordpress.Client, err error) {
	Url := fmt.Sprintf("%s/wp-json", DomainName)
	tp := wordpress.BasicAuthTransport{
		Username: Username,
		Password: Password,
	}
	// create wp-api client
	client, err = wordpress.NewClient(Url, tp.Client())
	if err != nil {
		return nil, err
	}
	return client, nil
}

// 测试账号是否正确
func Test(DomainName string, Username string, Password string) error {
	client, err := Client(DomainName, Username, Password)
	if err != nil {
		return err
	}
	_, r, err := client.Users.Me(context.Background(), nil)
	if err != nil {
		return err
	}
	if r.StatusCode != 200 {
		return fmt.Errorf("账号验证失败")
	}
	return nil
}

3.编写测试类

编写完工具方法后我们需要对接方法进行测试。

测试之前我们需要先准备到wordpress账号密码

wordpressutil.go同级目录创建 wordpressutil_test.go文件。

测试类需要引入testing包,测试方法以Test开头,参数为*testing.T。下面是一个Test函数的典型定义

import "testing"
func Test_test(t *testing.T) {

}

wordpressutil_test.go

package wordpressutil

import (
	"context"
	"fmt"
	"net/http"
	"testing"

	"github.com/robbiet480/go-wordpress"
)

func getClient() (client *wordpress.Client, err error) {
	client, err = Client("https://xxx.com/wp-json/", "admin", "xxx")
	if err != nil {
		return nil, err
	}
	return client, nil
}

// 测试Client函数
func Test_getClient(t *testing.T) {
	client, err := getClient()
	if err != nil {
		fmt.Println(err.Error())
	}
	media, resp, _ := client.Media.List(context.Background(), nil)
	if resp != nil && resp.StatusCode != http.StatusOK {
		t.Errorf("Expected 200 OK, got %v", resp.Status)
	}
	if len(media) < 1 {
		t.Fatalf("Should not return empty comments")
	}
	fmt.Println(media)
}

// 测试Test函数
func Test12(t *testing.T) {
	err := Test("https://www.xxxxx.com/wp-json/", "gxx", "xxx")
	if err != nil {
		fmt.Println(err.Error())
	}
}

// 测试Create_User函数
func Test_Create_User(t *testing.T) {
	client, err := getClient()
	if err != nil {
		fmt.Println(err.Error())
	}
	user, _, err := client.Users.Create(context.Background(), &wordpress.User{Username: "test", Email: "test@test.com"})
	if err != nil {
		fmt.Println(err.Error())
	}
	fmt.Println(user)
}

如果你使用vscode在测试函数旁边有个测试按钮,直接进行测试。其他的ide也是类型的操作。
test
右键点击有更多操作下拉.
debug

测试完成后们就可以在业务代码中使用了。使用时把 pkg/wordpressutilimport即可使用

4.编写其他工具类

有了上面的流程我们在引入下其他的工具类。由于涉及到密码所以我们存入数据库时需要进行加密,因此需要编写一个加密解密工具。

pkg包下创建 encryption目录,创建encryption.go文件

encryption.go

package encryption

import (
	"crypto/aes"
	"crypto/cipher"
	"crypto/rand"
	"crypto/sha256"
	"encoding/base64"
	"fmt"
	"io"
)

// AES加密函数
func AESEncrypt(plainText, key string) (string, error) {
	// 创建 AES 加密器
	block, err := aes.NewCipher(createHash(key))
	if err != nil {
		return "", err
	}

	// 使用 GCM 模式
	gcm, err := cipher.NewGCM(block)
	if err != nil {
		return "", err
	}

	// 创建 nonce
	nonce := make([]byte, gcm.NonceSize())
	if _, err = io.ReadFull(rand.Reader, nonce); err != nil {
		return "", err
	}

	// 加密数据
	cipherText := gcm.Seal(nonce, nonce, []byte(plainText), nil)
	return base64.StdEncoding.EncodeToString(cipherText), nil
}

// AES解密函数
func AESDecrypt(cipherText, key string) (string, error) {
	// 将密文解码
	data, err := base64.StdEncoding.DecodeString(cipherText)
	if err != nil {
		return "", err
	}

	// 创建 AES 解密器
	block, err := aes.NewCipher(createHash(key))
	if err != nil {
		return "", err
	}

	// 使用 GCM 模式
	gcm, err := cipher.NewGCM(block)
	if err != nil {
		return "", err
	}

	nonceSize := gcm.NonceSize()
	if len(data) < nonceSize {
		return "", fmt.Errorf("ciphertext too short")
	}
	// 解密
	nonce, cipherTextByte := data[:nonceSize], data[nonceSize:]
	plainText, err := gcm.Open(nil, nonce, cipherTextByte, nil)
	if err != nil {
		return "", err
	}

	return string(plainText), nil
}

// 创建哈希函数
func createHash(key string) []byte {
	hash := sha256.New()
	hash.Write([]byte(key))
	return hash.Sum(nil)[:32] // AES-256 密钥需要32字节
}

encryption_test.go

package encryption

import (
	"testing"
)

func TestEncryption(t *testing.T) {
	res, err := AESEncrypt("hello", "12345678")
	if err != nil {
		t.Error(err)
	}
	t.Log(res)
	t.Log("---------------------")
	res, err = AESDecrypt(res, "12345678")
	if err != nil {
		t.Error(err)
	}
	t.Log(res)
}

同样的方式进行测试
test
iputil.go

package iputil

import (
	"errors"
	"net"
	"net/http"
	"net/url"
	"strings"
)

func GetIP(r *http.Request) (string, error) {
	ip := r.Header.Get("X-Forwarded-For")
	for _, i := range strings.Split(ip, ",") {
		if net.ParseIP(i) != nil {
			return i, nil
		}
	}

	ip, _, err := net.SplitHostPort(r.RemoteAddr)
	if err != nil {
		return "", err
	}

	if net.ParseIP(ip) != nil {
		return ip, nil
	}

	return "", errors.New("no valid ip found")
}

// 获取域名ip
func GetDomainIP(domain string) (string, error) {
	domain, err := extractDomain(domain)
	if err != nil {
		return "", err
	}
	ips, err := net.LookupIP(domain)
	if err != nil {
		return "", err
	}

	for _, ip := range ips {
		return ip.String(), err
	}
	return "", errors.New("no valid ip found")
}

// 提取域名
func extractDomain(u string) (string, error) {
	if strings.Contains(u, "http") {
		parsedUrl, err := url.Parse(u)
		if err != nil {
			return "", err
		}
		return parsedUrl.Hostname(), nil
	}
	return u, nil
}

我们同样进行测试,这里就不直接复制出,大家可以自行测试练习。

5.业务代码调用

编写完工具类后,我们对之前业务代码中的todo 逻辑进行补全。

addstationlogic.go中我们在之前的todo处进行逻辑处理

addstationlogic.go

func (l *AddStationLogic) AddStation(in *types.StationInfo) (resp *types.StationInfoResp, err error) {
	//校验wordpress 账号密码
	err = wordpressutil.Test(in.DomainName, in.UserName, in.PassWord)
	if err != nil {
		return nil, err
	}
	// 加密密码
	pw, err := encryption.AESEncrypt(in.PassWord, l.svcCtx.Config.Secret.AESSecret)
	if err != nil {
		return nil, err
	}

	info := &station.StationInfo{
		Id:           in.Id,
		DomainName:   in.DomainName,
		DomainYear:   in.DomainYear,
		GoogleWeight: in.GoogleWeight,
		Type:         in.Type,
		Industry:     in.Industry,
		UserName:     in.UserName,
		PassWord:     pw,
		ArticlesNum:  in.ArticlesNum,
		Ip:           in.Ip,
	}
	// 自动获取服务器ip
	if info.Ip == "" {
		ip, _ := iputil.GetDomainIP(info.DomainName)
		info.Ip = ip
	}
	// 后的代码省略了
}

这样我们完成了外部公共库的引入和使用。

完整代码查询 6wordpress外部库的引入和测试 代码分支 。

5.总结

引入公共库,工具类时,我们可以对其进行测试。测试使用testing,通过测试我们可以快速验证工具能力。测试做的完善可以大大减少我们bug量。

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

22 交换机双工模式

交换机双工模式 一、双工模式 &#xff08;一&#xff09;单工、半双工、全双 ​ 单工&#xff1a; ​ 只有一个信道&#xff0c;传输方向只能是单向的 ​ 半双工&#xff1a; ​ 只有一个信道&#xff0c;在同一时刻&#xff0c;只能是单向传输 ​ 全双工&#xff1a; …

【JavaEE】深入MyBatis:动态SQL操作与实战项目实现指南

目录 MyBatis的进阶操作动态SQL<if>标签<trim>标签<where>标签<set>标签<foreach>标签<include>标签 练习表白墙数据准备引⼊MyBatis 和 MySQL驱动依赖配置MySQL账号密码编写后端代码测试 图书管理系统数据库表设计引⼊MyBatis 和MySQL 驱…

阿里QuickBI实战

目录 引言数据采集、数据治理、数据分析举例资金在经济社会的流通性 概述数据分析的常见问题数据分析的痛点 QuickBI 产品架构图主功能链路数据建模与数据分析的关系使用场景1、搭建报表看板&#xff1a;仪表盘2、中国式报表工具&#xff1a;电子表格3、企业CXO驾驶舱&#xff…

网络工程3(子网通信,为什么要使用mac和ip)

文章目录 一. 子网如何通讯1. 子网内部通信2. 子网外部通信 二. 交换机和路由器的连接三. 为什么不只使用mac地址或ip地址进行网络通信1. 首先要明确的是&#xff0c;不管是只用mac或只用ip通信 四. 子网设备如何获得ip五. 不同网段的主机无法直接通信的原因 一. 子网如何通讯 …

GAMES101——作业7 路径追踪 (含提高:多线程,微平面理论)

任务 castRay(const Ray ray, int depth)in Scene.cpp: 在其中实现 Path Tracing 算法 可能用到的函数有&#xff1a; intersect(const Ray ray)in Scene.cpp: 求一条光线与场景的交点 sampleLight(Intersection pos, float pdf) in Scene.cpp: 在场景的所有光源上按面积…

用 CWE API 减轻软件产品中的安全风险

1. CWE REST API 推出的目的 8 月 8 号&#xff0c;CWE™ 计划推出了“CWE REST API”。 CWE™计划由美国网络安全与基础设施安全局(Cybersecurity & Infrastructure Security Agency(CISA))资助的国土安全系统工程与发展研究所(Homeland Security Systems Engineering a…

AutoSAR SecOC小小科普

目录 1.为什么要提SecOC 2.SecOC基本原理 2.1 参与到MAC计算的数据有哪些 2.2 新鲜度值如何管理 3.SecOC与各模块关联关系 1.为什么要提SecOC 在车载网络技术里&#xff0c;大家基本都是从CAN开始入门。在CAN DBC里&#xff0c;我们总能看到有些报文除了自带有效payload外…

AWS 消息队列服务 SQS

AWS 消息队列服务 SQS 引言什么是 SQSSQS 访问策略 Access Policy示例&#xff1a;如何为 DataLake Subscription 配置 SQS 引言 应用系统需要处理海量数据&#xff0c;数据发送方和数据消费方是通过什么方式来无缝集成消费数据的&#xff0c;AWS 提供 SQS 消息队列服务来解决…

42000 Star图标工具Mermaid!

Mermaid&#xff1a;用文本构建图表世界 - 精选真开源&#xff0c;释放新价值。 概览 Mermaid.js 是一个创新的开源工具&#xff0c;专为简化图表创建流程而设计。它通过一种简洁的文本描述语言&#xff0c;使得用户能够快速地生成流程图、序列图、甘特图等图表&#xff0c;而…

【威锋网-注册安全分析报告-无验证方式导致安全隐患】

前言 由于网站注册入口容易被黑客攻击&#xff0c;存在如下安全问题&#xff1a; 1. 暴力破解密码&#xff0c;造成用户信息泄露 2. 短信盗刷的安全问题&#xff0c;影响业务及导致用户投诉 3. 带来经济损失&#xff0c;尤其是后付费客户&#xff0c;风险巨大&#xff0c;造…

JavaEE过滤器的创建与使用过滤器的使用场景

过滤器 Filter也称之为过滤器&#xff0c;过滤器是javaEE规范肿定义的一种技术,可以让请求到达目标servlet之前,先进入到过滤器中,在过滤器中统一进行一些拦截处理,当处理完成后,可以继续向后执行,到达目标servlet,如果配置了多个过滤器,也可以进入下一个过滤器 创建过滤器 创…

一键更换Linux优质的软件源和docker源 —— 筑梦之路

一个非常牛逼的开源项目&#xff1a;https://github.com/SuperManito/LinuxMirrors.git LinuxMirrors 使换源更简单 - LinuxMirrors 支持的操作系统 系统名称适配版本Debian8.0 ~ 13Ubuntu14.04 ~ 24Kali Linux2.0 ~ 2024Linux Mint19.0 ~ 21 / LMDE 6DeepinallArmbianallP…

Redis7基础篇(一)

redis十大数据类型 目录 redis十大数据类型 redis键key 数据类型命令 redis字符串string 分布式锁 ​编辑 ​编辑​编辑应用场景 ​编辑​编辑 reids列表list 应用场景 redis哈希hash 应用场景 redis集合set 应用场景 redis有序集合zset&#xff08;sorted set集…

【设计模式】观察者模式和订阅发布模式

观察者模式 观察者模式包含观察目标和观察者两类对象。一个目标可以有任意数目的与之相依赖的观察者。一旦观察目标的状态发生改变&#xff0c;所有的观察者都将得到通知。 当一个对象的状态发生改变时&#xff0c;所有依赖于它的对象都得到通知并被自动更新&#xff0c;解决…

《机器学习》逻辑回归 梯度下降、混淆矩阵、随机种子、正则化惩罚 No.6

一、混淆矩阵 1、什么是混淆矩阵&#xff1f; 混淆矩阵是用于评估分类模型在不同类别上的预测准确性的工具。它提供了模型预测结果与真实结果之间的对应关系&#xff0c;帮助我们分析和理解模型的分类性能。 假设&#xff0c;要对15个人预测是否患病&#xff0c;使用1表示患病…

生产环境中MapReduce的最佳实践

目录 MapReduce跑的慢的原因 MapReduce常用调优参数 1. MapTask相关参数 2. ReduceTask相关参数 3. 总体调优参数 4. 其他重要参数 调优策略 MapReduce数据倾斜问题 1. 数据预处理 2. 自定义Partitioner 3. 调整Reduce任务数 4. 小文件问题处理 5. 二次排序 6. 使用…

【python与java的区别-03(集合、字典)】

一、Set python: 集合&#xff08;set&#xff09;是一个无序的不重复元素序列。 集合中的元素不会重复&#xff0c;并且可以进行交集、并集、差集等常见的集合操作。 可以使用大括号 { } 创建集合&#xff0c;元素之间用逗号 , 分隔&#xff0c; 或者也可以使用 set() 函数…

【解释器模式】设计模式系列:构建动态语言解释器与复杂表达式处理(深入理解并实现)

文章目录 深入理解并实现解释器模式1. 引言1.1 解释器模式的定义1.2 模式的主要优点和缺点1.3 适用场景1.4 实际应用案例简介 2. 解释器模式的基本概念2.1 模式的核心思想2.2 模式的角色2.3 模式的动态行为分析 3. 解释器模式的工作原理3.1 如何构建表达式树3.2 如何通过递归遍…

可达鸭举牌网页版本在线生成源码html5

源码介绍 可达鸭举牌网页版本&#xff0c;在线生成源码&#xff0c;点击分享即可制作DIY自己的举牌文字网页&#xff0c;需要GIF动图的自行用GIF图片录制工具录制下来。 PS:上传到服务器运行或者本地nginx运行&#xff0c;不要双击index.html&#xff0c;如果本地双击HTML&…

【3】AT32F437 OpenHarmony轻量系统第一个程序:点灯

在搭建好AT32F437 OpenHarmony 轻量系统之后&#xff0c;当然要尝试点一下灯了。 编写点灯程序 笔者在适配OpenHarmony轻量系统的时候&#xff0c;只对源码的device和vendor目录进行了修改&#xff0c;AT32的app目录笔者放置在了vendor/tree/master/artery/AT-START-F437/app…