Всем привет, я Брат Фу, мастер технического УП.
Как технический программист, при использовании сообществ, форумов или различных сервисов искусственного интеллекта я часто вижу такое приглашение: «Используйте официальную учетную запись WeChat, чтобы отсканировать QR-код для входа». Это связано с тем, что помимо входа в систему этот метод входа также может позволить пользователям накапливать данные в официальной учетной записи и получать повышение от официальной учетной записи в будущем, что, можно сказать, убивает двух зайцев одним выстрелом. Итак, как это делается? 🤔
Брат Фу, позвольте мне сначала привести вам пример такого входа в систему, чтобы каждый мог ознакомиться с этим бизнес-сценарием.
Посредством такого отображения эффекта страницы мы можем примерно знать, что непрерывное обнаружение пользовательских страниц с помощью checkScan требует использования уникального значения идентификатора. Когда пользователь сканирует код с помощью WeChat, уникальное значение идентификатора может быть получено и сохранено через официальную учетную запись WeChat, и создается связь между уникальным идентификатором и токеном. Затем, когда checkScan просканирует и обнаружит, что на сервере есть такое сопоставление, токен можно будет получить и сохранить в браузере, что позволит пользователю успешно войти в систему.
Процесс такой, как же обрабатывается конкретная реализация кода? Далее брат Фу расскажет вам, как реализовать этот план.
В конце статьи мы предоставляем метод скидки «Planet: Coders Club Lock»🧧, чтобы присоединиться.,и этот курсизкодовый адрес。Демонстрационный адрес проекта:https://gaga.plus - 8 практических проектов
Процесс входа в систему при сканировании кода WeChat в основном состоит из четырех частей: пользователя, браузера, внутренней службы и официальной учетной записи. Сначала мы можем понять всю взаимосвязь вызовов с помощью блок-схемы UML.
При таком понимании процесса далее мы можем посмотреть, как реализуется код.
Нет необходимости подавать заявку на официальное аккаунт может завершить тест, как в песочнице
Наконец, это QR-код, сканируемый пользователем.
Брат Фу усыновил его здесь DDD На основе структуры инженерной модели мы разработали сервер входа в систему с кодом сканирования общедоступной учетной записи. если ты прав DDD Если вы еще не знакомы с ним, вы можете прочитать серию, написанную Братом Фу. DDD Учебник "Ява"; Краткое руководство》-> bugstack.cn -> дорожная книга
Прочитав документы официального сайта WeChat, мы можем узнать, что для получения QR-кода для сканирования и входа в систему необходимо выполнить три шага;
public interface IWeixinApiService {
/**
* получать Access token
* документ:<a href="https://developers.weixin.qq.com/doc/offiaccount/Basic_Information/Get_access_token.html">Get_access_token</a>
*
* @param grantType получатьaccess_tokenзаполнятьclient_credential * @param appId Сертификат только для сторонних пользователей
* @param appSecret Сертификат только для сторонних пользователейключ,Прямо сейчасappsecret
* @return результат ответа
*/
@GET("cgi-bin/token")
Call<WeixinTokenResponseDTO> getToken(
@Query("grant_type") String grantType,
@Query("appid") String appId,
@Query("secret") String appSecret
);
/**
* получать Реквизиты для входа ticket
* документ:<a href="https://developers.weixin.qq.com/doc/offiaccount/Account_Management/Generating_a_Parametric_QR_Code.html">Generating_a_Parametric_QR_Code</a>
* <a href="https://mp.weixin.qq.com/cgi-bin/showqrcode?ticket=TICKET">Передняя часть на основесертификат Показать QR-код</a>
*
* @param accessToken getToken получатьиз token информация
* @param weixinQrCodeRequestDTO Объект входного параметра
* @return результат ответа
*/
@POST("cgi-bin/qrcode/create")
Call<WeixinQrCodeResponseDTO> createQrCode(@Query("access_token") String accessToken, @Body WeixinQrCodeRequestDTO weixinQrCodeRequestDTO);
}
@Slf4j
@Configuration
public class Retrofit2Config {
private static final String BASE_URL = "https://api.weixin.qq.com/";
@Bean
public Retrofit retrofit() {
return new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(JacksonConverterFactory.create())
.build();
}
@Bean
public IWeixinApiService weixinApiService(Retrofit retrofit) {
return retrofit.create(IWeixinApiService.class);
}
}
интерфейс:https://mp.weixin.qq.com/cgi-bin/showqrcode?ticket=TICKET
Исходный код:cn.bugstack.xfg.dev.tech.trigger.http.LoginController
@Slf4j
@RestController()
@CrossOrigin("*")
@RequestMapping("/api/v1/login/")
public class LoginController {
@Resource
private ILoginService loginService;
@RequestMapping(value = "weixin_qrcode_ticket", method = RequestMethod.GET)
public Response<String> weixinQrCodeTicket() {
try {
String qrCodeTicket = loginService.createQrCodeTicket();
log.info("Сгенерировать Вичат Сканируйте код, чтобы войти ticket {}", qrCodeTicket);
return Response.<String>builder()
.code(Constants.ResponseCode.SUCCESS.getCode())
.info(Constants.ResponseCode.SUCCESS.getInfo())
.data(qrCodeTicket)
.build();
} catch (Exception e) {
log.info("Сгенерировать Вичат Сканируйте код, чтобы войти ticket неудача", e);
return Response.<String>builder()
.code(Constants.ResponseCode.UN_ERROR.getCode())
.info(Constants.ResponseCode.UN_ERROR.getInfo())
.build();
}
}
@RequestMapping(value = "check_login", method = RequestMethod.GET)
public Response<String> checkLogin(@RequestParam String ticket) {
try {
String openidToken = loginService.checkLogin(ticket);
log.info("Результаты сканирования Авторизоваться ticket:{} openidToken:{}", ticket, openidToken);
if (StringUtils.isNotBlank(openidToken)) {
return Response.<String>builder()
.code(Constants.ResponseCode.SUCCESS.getCode())
.info(Constants.ResponseCode.SUCCESS.getInfo())
.data(openidToken)
.build();
} else {
return Response.<String>builder()
.code(Constants.ResponseCode.NO_LOGIN.getCode())
.info(Constants.ResponseCode.NO_LOGIN.getInfo())
.build();
}
} catch (Exception e) {
log.info("Результаты сканирования Авторизоватьсянеудача ticket:{}", ticket);
return Response.<String>builder()
.code(Constants.ResponseCode.UN_ERROR.getCode())
.info(Constants.ResponseCode.UN_ERROR.getInfo())
.build();
}
}
}
Разработать два интерфейса;
/api/v1/login/weixin_qrcode_ticket
- получать Вичат ticket сертификат/api/v1/login/check_login
- Проверка ротационного обучения АвторизоватьсяПрежде всего, пока процесс разработки общедоступной учетной записи завершен, необходимо осуществить стыковку общедоступной учетной записи. Такая стыковка означает, что вы самостоятельно разрабатываете программу стыковки согласно официальным документам аккаунта и настраиваете ее под официальную платформу аккаунта.
Как показано на рисунке, это то, что вы увидите после входа в официальную платформу тестирования учетной записи WeChat и добавления конфигурации интерфейса и безопасного доменного имени JS.
QR-код номера теста
,Таким образом, вы можете увидеть тестинформация。Исходный код:cn.bugstack.xfg.dev.tech.trigger.http.WeixinPortalController
@Slf4j
@RestController()
@CrossOrigin("*")
@RequestMapping("/api/v1/weixin/portal/")
public class WeixinPortalController {
@Value("${weixin.config.originalid}")
private String originalid;
@Resource
private Cache<String, String> openidToken;
/**
* Проверка подписи, жесткое кодирование token b8b6 - Измените по мере необходимости
*/
@GetMapping(value = "receive", produces = "text/plain;charset=utf-8")
public String validate(@RequestParam(value = "signature", required = false) String signature,
@RequestParam(value = "timestamp", required = false) String timestamp,
@RequestParam(value = "nonce", required = false) String nonce,
@RequestParam(value = "echostr", required = false) String echostr) {
try {
log.info("Вичат Официальный начать проверку информации аккаунта [{}, {}, {}, {}]", signature, timestamp, nonce, echostr);
if (StringUtils.isAnyBlank(signature, timestamp, nonce, echostr)) {
throw new IllegalArgumentException("Параметр просить недопустим, пожалуйста, проверьте!");
}
boolean check = SignatureUtil.check("b8b6", signature, timestamp, nonce);
log.info("Вичат Официальный Информация для проверки аккаунта заполнена. check:{}", check);
if (!check) {
return null;
}
return echostr;
} catch (Exception e) {
log.error("Вичат Официальный аккаунт Проверкаинформациянеудача [{}, {}, {}, {}]", signature, timestamp, nonce, echostr, e);
return null;
}
}
/**
* Обратный звонок, получить Официальный сообщение аккаунта [Сканировать Авторизоваться, вы получите сообщение]
*/
@PostMapping(value = "receive", produces = "application/xml; charset=UTF-8")
public String post(@RequestBody String requestBody,
@RequestParam("signature") String signature,
@RequestParam("timestamp") String timestamp,
@RequestParam("nonce") String nonce,
@RequestParam("openid") String openid,
@RequestParam(name = "encrypt_type", required = false) String encType,
@RequestParam(name = "msg_signature", required = false) String msgSignature) {
try {
log.info("Получить Вичат Официальный аккаунтинформацияпросить{}начинать {}", openid, requestBody);
// преобразование сообщений
MessageTextEntity message = XmlUtil.xmlToBean(requestBody, MessageTextEntity.class);
// Сканируйте код, чтобы введите【Тип сообщения】
if ("event".equals(message.getMsgType()) && "SCAN".equals(message.getEvent())) {
// Могут быть созданы реальные бизнес-сценарии jwt из token Позвольте фронтенду хранить
openidToken.put(message.getTicket(), openid);
return buildMessageTextEntity(openid, "Авторизоватьсяуспех"); }
log.info("Получить Вичат Официальный аккаунтинформацияпросить{}Заканчивать {}", openid, requestBody);
return buildMessageTextEntity(openid, «Чтобы проверить этот случай, спросите Сканируйте код, чтобы войти!");
} catch (Exception e) {
log.error("Получить Вичат Официальный аккаунтинформацияпросить{}неудача {}", openid, requestBody, e);
return "";
}
}
private String buildMessageTextEntity(String openid, String content) {
MessageTextEntity res = new MessageTextEntity();
// Официальный аккаунтраспространятьизID res.setFromUserName(originalid);
res.setToUserName(openid);
res.setCreateTime(String.valueOf(System.currentTimeMillis() / 1000L));
res.setMsgType("text");
res.setContent(content);
return XmlUtil.beanToXml(res);
}
}
http://xfg-studio.natapp1.cc/api/v1/weixin/portal/receive
Вам необходимо заменить ваше изпроникновение в адрес доменного имени интранета.openidToken.put(message.getTicket(), openid);
Фактический бизнес-сценарий будет преобразован в Авторизоватьсяиз. jwt token данные.если ты не 8091 Порт, можно изменить на другой
. ____ _ __ _ _
/\\ / ___'_ __ _ _(_)_ __ __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
\\/ ___)| |_)| | | | | || (_| | ) ) ) )
' |____| .__|_| |_|_| |_\__, | / / / /
=========|_|==============|___/=/_/_/_/
:: Spring Boot :: (v2.7.12)
24-02-25.17:13:00.372 [main ] INFO EndpointLinksResolver - Exposing 1 endpoint(s) beneath base path '/actuator'
24-02-25.17:13:00.405 [main ] INFO Http11NioProtocol - Starting ProtocolHandler ["http-nio-8091"]
24-02-25.17:13:00.440 [main ] INFO TomcatWebServer - Tomcat started on port(s): 8091 (http) with context path ''
24-02-25.17:13:00.461 [main ] INFO Application - Started Application in 4.268 seconds (JVM running for 4.941)
./natapp запускать
Интерфейс доступа: http://xfg-studio.natapp1.cc/api/v1/login/weixin_qrcode_ticket — нужно заменить на свой адрес.
Интерфейс доступа: http://xfg-studio.natapp1.cc/api/v1/login/check_login — нужно заменить на свой адрес.
Используйте WeChat для сканирования QR-кода и просмотра журналов сервера и подсказок мобильного телефона.
24-02-25.17:25:09.096 [http-nio-8091-exec-3] INFO LoginController - генерировать Вичат Сканируйте код, чтобы войти ticket gQHN7zwAAAAAAAAAAS5odHRwOi8vd2VpeGluLnFxLmNvbS9xLzAycTRMbnB4TDBjckcxT043cjFCMWoAAgR1B9tlAwQ8AAAA
24-02-25.17:25:18.793 [http-nio-8091-exec-5] INFO WeixinPortalController - Получить Вичат Официальный аккаунтинформацияпроситьor0Ab6ivwmypESVp_bYuk92T6SvUначинать <xml><ToUserName><![CDATA[gh_e067c267e056]]></ToUserName>
<FromUserName><![CDATA[or0Ab6ivwmypESVp_bYuk92T6SvU]]></FromUserName>
<CreateTime>1708853118</CreateTime>
<MsgType><![CDATA[event]]></MsgType>
<Event><![CDATA[SCAN]]></Event>
<EventKey><![CDATA[100601]]></EventKey>
<Ticket><![CDATA[gQHN7zwAAAAAAAAAAS5odHRwOi8vd2VpeGluLnFxLmNvbS9xLzAycTRMbnB4TDBjckcxT043cjFCMWoAAgR1B9tlAwQ8AAAA]]></Ticket>
</xml>