目录
一 阿里云配置
1.购买验证码2.0服务
https://yundun.console.aliyun.com/spm=a2c4g.11186623.0.0.755e6061CmsJB3&p=captcha#/
2.构建场景,
购买服务后进入控制台,点击控制台左侧的控制管理,进入控制管理界面之后选择构建新的场景
构建相应的场景
创建成功之后就是
在这里一定有同学很纠结客户端的web和h5如何选择,网页的话一般是选择web
二 构建react前端
1.插入阿里的js
<script type="text/javascript" charset="utf-8" src="https://o.alicdn.com/captcha-frontend/aliyunCaptcha/AliyunCaptcha.js"></script>
直接加入到你react的index.html文件里
2.下载demo包
大家看着阿里的实例都是纯原生的如何加到react里有点懵逼,我也蒙蔽,所以在阿里云文档最下面有一个react的案例,下载下来,解压打开
3.代码拷贝
下载下来打开,里面有两个demo,分为弹出和嵌入的,已经封装好了两个组件,将自己选择好的组件的index.js复制到自己项目里(创建一个.js文件就好,然后导入到自己需要用到的页面里)
4.修改代码
现在要修改两个地方:你的场景ID和身份标 (都在你的验证码控制台里)
5.修改组件的的return,
大家肯定希望使用自己的登录或者注册...按钮来触发人机验证,所以return这里需要修改,将其改成如下,
剩下这一个是用来显示验证的div(嵌入式)
将登入的id进行修改绑定,改成'captcha-button'
此时点击登录按钮已经可以弹出人机验证了只不过没有向后端发送响应的请求,所以对错都可通过
三 java(springboot)构建服务端
1.在阿里平台创建AccessKey
创建子用户
赋予AliyunYundunAFSFullAccess权限 不然后面回报403的错误
2.导入相关的sdk(我感觉就是pom文件里的依赖)
验证码服务端智能验证示例代码_验证码_示例中心-阿里云OpenAPI开发者门户
进入这个网址后下载工程案例
将工程里pom文件里的依赖复制一份到自己的pom文件中去
<dependency>
<groupId>com.aliyun</groupId>
<artifactId>captcha20230305</artifactId>
<version>1.1.2</version>
</dependency>
<dependency>
<groupId>com.aliyun</groupId>
<artifactId>tea-openapi</artifactId>
<version>0.3.1</version>
</dependency>
<dependency>
<groupId>com.aliyun</groupId>
<artifactId>tea</artifactId>
<version>1.1.14</version>
</dependency>
3.在springboot的yml文件中加入相关配置
(可以不加直接赋值也可以,如果是大点的项目的话,我建议加)
aliyun:
accessKeyId: (创建子用户是可以看一次,一定要下载csv文件保存到本地)
accessKeySecret: (同上)
sceneId: (你的场景id)
4.创建一个类,AliAfsInfo
(可以不创建,从yml文件中直接读也可以)
import lombok.Data;
import org.springframework.stereotype.Component;
import org.springframework.beans.factory.annotation.Value;
@Component
@Data
public class AliAfsInfo {
@Value("${aliyun.accessKeyId}")
private String AccessKeyId;
@Value("${aliyun.accessKeySecret}")
private String AccessKeySecret;
@Value("${aliyun.sceneId}")
private String SceneId;
}
5. code 返回类R 接口
public interface ResultCode {
Integer SUCCESS = 200;
Integer ERROR = 500;
}
import lombok.Data;
import java.util.HashMap;
import java.util.Map;
@Data
public class R {
private Boolean success; //返回的成功或者失败的标识符
private Integer code; //返回的状态码
private String message; //提示信息
private Map<String, Object> data = new HashMap<String, Object>(); //数据
//把构造方法私有
private R() {}
//成功的静态方法
public static R ok(){
R r=new R();
r.setSuccess(true);
r.setCode(ResultCode.SUCCESS);
r.setMessage("成功");
return r;
}
//失败的静态方法
public static R error(){
R r=new R();
r.setSuccess(false);
r.setCode(ResultCode.ERROR);
r.setMessage("失败");
return r;
}
//使用下面四个方法,方面以后使用链式编程
// R.ok().success(true)
// r.message("ok).data("item",list)
public R success(Boolean success){
this.setSuccess(success);
return this; //当前对象 R.success(true).message("操作成功").code().data()
}
public R message(String message){
this.setMessage(message);
return this;
}
public R code(Integer code){
this.setCode(code);
return this;
}
public R data(String key, Object value){
this.data.put(key, value);
return this;
}
public R data(Map<String, Object> map){
this.setData(map);
return this;
}
}
import com.lfl.springsecuritydemo01.service.AuthenticationService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import com.lfl.springsecuritydemo01.result.R;
import java.util.Map;
@RestController
@RequestMapping("/sys")
@CrossOrigin
public class AuthenticationController {
@Autowired
private AuthenticationService authenticationService;
@PostMapping("/afsCheck")
public R afsCheck(@RequestBody Map<String,String> map) throws Exception {
String captchaVerifyParam = map.get("captchaVerifyParam");
return authenticationService.afsCheck(captchaVerifyParam);
}
}
6.服务实现
import com.lfl.springsecuritydemo01.result.R;
public interface AuthenticationService {
R afsCheck(String captchaVerifyParam) throws Exception;
}
import com.alibaba.fastjson.JSONObject;
import com.aliyun.captcha20230305.models.VerifyIntelligentCaptchaRequest;
import com.aliyun.captcha20230305.models.VerifyIntelligentCaptchaResponse;
import com.aliyun.dysmsapi20170525.models.SendSmsResponse;
import com.aliyun.tea.TeaException;
import com.aliyun.teaopenapi.models.Config;
import com.lfl.springsecuritydemo01.domain.vo.AliAfsInfo;
import com.lfl.springsecuritydemo01.result.R;
import com.lfl.springsecuritydemo01.service.AuthenticationService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import java.util.HashMap;
import java.util.Map;
import java.util.Random;
import java.util.concurrent.TimeUnit;
@Service
public class AuthenticationServiceImpl implements AuthenticationService {
@Autowired
private AliAfsInfo aliAfs;
@Override
public R afsCheck(String captchaVerifyParam) throws Exception {
// ====================== 1. 初始化配置 ======================
Config config = new Config();
// 设置您的AccessKey ID 和 AccessKey Secret。
// getEnvProperty只是个示例方法,需要您自己实现AccessKey ID 和 AccessKey Secret安全的获取方式。
config.accessKeyId = aliAfs.getAccessKeyId();
config.accessKeySecret = aliAfs.getAccessKeySecret();
//设置请求地址 国内调用地址 captcha.cn-shanghai.aliyuncs.com 新加坡调用地址 xxxxx.captcha-open-southeast.aliyuncs.com (xxx为用户身份标)
config.endpoint = "captcha.cn-shanghai.aliyuncs.com";
// 设置连接超时为5000毫秒
config.connectTimeout = 5000;
// 设置读超时为5000毫秒
config.readTimeout = 5000;
// ====================== 2. 初始化客户端(实际生产代码中建议复用client) ======================
com.aliyun.captcha20230305.Client client = new com.aliyun.captcha20230305.Client(config);
// 创建APi请求
VerifyIntelligentCaptchaRequest request = new VerifyIntelligentCaptchaRequest();
// 本次验证的场景ID,建议传入,防止前端被篡改场景
request.sceneId = aliAfs.getSceneId();
// 前端传来的验证参数 CaptchaVerifyParam
request.captchaVerifyParam = captchaVerifyParam;
// ====================== 3. 发起请求) ======================
Boolean captchaVerifyResult = false;
try {
VerifyIntelligentCaptchaResponse resp = client.verifyIntelligentCaptcha(request);
System.out.println(resp.toString());
// 建议使用您系统中的日志组件,打印返回
// 获取验证码验证结果(请注意判空),将结果返回给前端。出现异常建议认为验证通过,优先保证业务可用,然后尽快排查异常原因。
captchaVerifyResult = resp.body.result.verifyResult;
System.out.println(captchaVerifyResult);
// 原因code
String captchaVerifyCode = resp.body.result.verifyCode;
} catch (TeaException error) {
// 建议使用您系统中的日志组件,打印异常
// 出现异常建议认为验证通过,优先保证业务可用,然后尽快排查异常原因。
captchaVerifyResult = true;
} catch (Exception _error) {
TeaException error = new TeaException(_error.getMessage(), _error);
// 建议使用您系统中的日志组件,打印异常
// 出现异常建议认为验证通过,优先保证业务可用,然后尽快排查异常原因。
captchaVerifyResult = true;
}
if(captchaVerifyResult){
return R.ok().message("验证成功");
}
return R.error().message("验证失败");
}
}
四 修改前端 向后端发起请求(在咱们复制进来的js文件里)
const captchaVerifyCallback = async (captchaVerifyParam) => {
// 1.向后端发起业务请求,获取验证码验证结果和业务结果
let res = false;
console.log("验证");
const result = await fetch('http://localhost:8000/sys/afsCheck',{
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
captchaVerifyParam: captchaVerifyParam, // 验证码参数
})
}).then(res => res.json())
.then(data => {
console.log(data);
if (data.code === 200) {
console.log('验证通过');
res = true;
}
})
return {
captchaResult: res, // 验证码验证是否通过,boolean类型,必选
bizResult: true, // 业务验证是否通过,boolean类型,可选;若为无业务验证结果的场景,bizResult可以为空
}
//console.log(captchaVerifyParam);
}
现在如下人机功能成功实现
人机认证实现时候,如果认证通过则会有后续相关的操作可以在如下地方修改,比如修改全局变量等操作