当前位置: 首页 > news >正文

todo: 使用融云imserve做登录(android)

使用融云做登录注册思路

  • 注册界面需要name, email, password
  • 考虑到融云注册用户的post格式
POST http://api.rong-api.com/user/getToken.json?userId=1690544550qqcom&name=Ironman
  • 这里的userId可以使用用户的email,但是要截断@. 符号,即1690544550@qq.com -> 1690544550qqcom, 融云不让我传完整的邮箱地址,这里可能要考虑到奇怪的邮箱地址,如fuckerfucker@fucker.edu.cn,我不确定截断后的是fuckerfuckerfuckereducn能不能还原成邮箱地址
  • 注册的name传入post 参数的name
  • 融云注册返回格式
{"code": 200,"userId": "1690544550qqcom","token": "测试"
}
  • 那android注册界面需要检查返回的response的code==200token!=null, 如果ok,注册用户成功
  • 登录界面需要email和password, 这里可能还要考虑到自己搭建服务后端来存取用户基本信息(email, password)
  • 但是查到融云一条api是关于查询用户信息的
POST http://api.rong-api.com/user/info.json?userId=1690544550qqcom

接口返回

{"code": 200,"userName": "Ironman","userPortrait": "http://abc.com/myportrait.jpg","createTime": "2025-03-05 11:46:49"
}
  • 现在考虑怎么校验密码那一块, 校验密码能不能本地校验,就是注册的时候拿到email和password存到手机本地数据库,到登录时,需要用userId请求融云用户信息,检查code==200, 密码就比对本地数据库的email, password一对,好像相对繁琐了
  • 登录成功后跳转界面
  • 完啦,注册的页面还要考虑到验证邮箱地址正确,就是发邮箱验证码,这不知道怎么入手

todo实现以上思路

1. 使用go语言简单搭建一个邮箱验证码服务,邮箱服务来自qq邮箱

  • 后端地址: https://gitee.com/EEPPEE_admin/dont-want-to-write-code-anymore/tree/master/send_code_to_mail
  • 配置自己的qqmail 授权码还有自己的发送邮箱地址
  • 提供接口
### 发送验证码,这里的email是从adnroid客户端注册用户获取
POST http://localhost:8080/send-code?email=1876056356@qq.com
### 验证验证码, 738702 是验证码,有发送验证码获取,随机的,这里的email是从adnroid客户端注册用户获取
POST http://localhost:8080/verify-code?email=1876056356@qq.com&code=6271

2. 搭建data层调式邮箱验证码

  • 先启动后端go run main.go
  • 创建data/network/EmailVerifyCodeApiService.kt

// Base url:https://7f498cbc.r7.cpolar.top
interface EmailVerifyCodeApiService {@POST("send-code")fun sendVerificationCode(@Query("email") email: String): Call<VerifyCodeResponse>@POST("verify-code")fun verifyEmailCode(@Query("email") email: String,@Query("code") code: String): Call<VerifyCodeResponse>}// 邮箱验证码的返回
data class VerifyCodeResponse(val message: String
)object EmailVerifyCodeApiClient {// todo: 这个base url随时变动,根据你的cpolar地址来private const val BASE_URL = "https://7f498cbc.r7.cpolar.top"private var apiService: EmailVerifyCodeApiService? = nullval emailVerifyCodeApiService: EmailVerifyCodeApiService?get() {if (apiService == null) {val client: OkHttpClient = OkHttpClient.Builder().build()val retrofit = Retrofit.Builder().baseUrl(BASE_URL).client(client).addConverterFactory(GsonConverterFactory.create()).build()apiService = retrofit.create(EmailVerifyCodeApiService::class.java)}return apiService}
}
  • 测试点击发送邮件事件(这个简单界面代码就不给出了,就一个按钮,一个EditText,使用viewbinding)
 binding.sendBtn.setOnClickListener {val email = binding.emailEt.text.toString().trim()// todo: 处理发送邮箱验证码val apiService = EmailVerifyCodeApiClient.emailVerifyCodeApiServiceval call = apiService?.sendVerificationCode(email)call!!.enqueue(object : retrofit2.Callback<VerifyCodeResponse> {override fun onResponse(call: Call<VerifyCodeResponse>,response: Response<VerifyCodeResponse>) {Log.d("注册", response.body().toString())Log.d("注册", "发送邮箱验证码成功")}override fun onFailure(call: Call<VerifyCodeResponse>, t: Throwable) {Log.d("注册", "发送验证码失败")}})}
  • 测试邮箱验证码发送通过

3. 调试融云api

  • 创建data/network/RongCloudApiService.kt
// todo: 构建融云api服务, 接口里面的方法可以是suspend和普通函数
/*
普通函数 vs. suspend 函数
普通函数:
使用回调(Callback)或 Call 对象来处理异步请求。
适用于传统的异步编程模型。
代码相对复杂,需要处理回调和线程切换。
suspend 函数:
使用 Kotlin 协程来处理异步请求。
代码更简洁,更接近同步编程风格。
需要结合 CoroutineScope 或其他协程工具来调用。
示例代码*/
interface RongCloudApiService {@FormUrlEncoded@POST("user/getToken.json")fun getToken(// 这是x-form形式@Field("userId") userId: String, // todo: required@Field("name") name: String = "",@Field("portraitUri") portraitUri: String = ""): Call<GetTokenResponse>//    @POST("user/info.json")
//     fun getRongCloudUserInfo(
//        @Query("userId") userId: String
//    ): Response<RongCloudUserInfo>@FormUrlEncoded@POST("user/info.json")fun getUserInfo(@Field("userId") userId: String,): Call<UserInfoResponse>}// user/getToken.json接口的返回
data class GetTokenResponse(val code: Int,val userId: String,val token: String?
)// user/info.json接口的返回
data class UserInfoResponse(val code: Int,val userName: String,val userPortrait: String?,val createTime: String
)object RongCloudApiClient {// 要求不能明文传输,改成httpsprivate const val BASE_URL = "https://api.rong-api.com/"private const val APP_KEY = "你自己的"private const val NONCE = "1442907399"private const val TIMESTAMP = "1741092643"private const val SIGNATURE = "你自己的"private var apiService: RongCloudApiService? = null// todo: 获取实例方法val rongIMApiService: RongCloudApiService?get() {if (apiService == null) {val client: OkHttpClient = OkHttpClient.Builder().addInterceptor(Interceptor { chain ->val originalRequest: Request = chain.request()val newRequest: Request = originalRequest.newBuilder().header("App-Key", APP_KEY).header("Nonce", NONCE).header("Timestamp", TIMESTAMP).header("Signature", SIGNATURE).header("Content-Type", "application/x-www-form-urlencoded").build()chain.proceed(newRequest)}).build()val retrofit = Retrofit.Builder().baseUrl(BASE_URL).client(client).addConverterFactory(GsonConverterFactory.create()).build()apiService = retrofit.create(RongCloudApiService::class.java)}return apiService}
}
  • 调试代码,点击一个注册按钮,观察Logcat
  binding.registerBtn.setOnClickListener {val email = binding.emailEt.text.toString().trim()Log.d("注册", email)val name = binding.nameEt.text.toString().trim()Log.d("注册", name)val password = binding.passwordEt.text.toString().trim()Log.d("注册", password)val mailVerifyCode = binding.mailVerifycodeEt.text.toString().trim()Log.d("注册", mailVerifyCode)if (name.isEmpty() || email.isEmpty() || password.isEmpty() || mailVerifyCode.isEmpty()) {Toast.makeText(this, "请填充完整信息", Toast.LENGTH_SHORT).show()return@setOnClickListener}// email 处理成 userIdval processedEmailAsUserId = EmailUtil.convertEmailToRongCloudId(email)Log.d("注册", processedEmailAsUserId)// todo 取到接口实例val apiService = RongCloudApiClient.rongIMApiService// todo 调用api serviceval call = apiService?.getToken(processedEmailAsUserId,name)// todo call 进入队列call!!.enqueue(object : retrofit2.Callback<GetTokenResponse> {override fun onResponse(call: Call<GetTokenResponse>,response: retrofit2.Response<GetTokenResponse>) {Log.d("注册", response.body().toString())//RongCloudTokenResponse(code=200, userId=13266263124qqcom, token=Seq1kNg6Uft4UOBPzi2gGqh30okEsnM0kPAf6ohCvgf1vll6L9v54A==@ptfq.cn.rongnav.com;ptfq.cn.rongcfg.com)}override fun onFailure(call: Call<GetTokenResponse>, t: Throwable) {Log.d("注册", "获取token失败")}})// todo new call 进入队列val newcall = apiService?.getUserInfo(processedEmailAsUserId)newcall!!.enqueue(object : retrofit2.Callback<UserInfoResponse> {override fun onResponse(call: Call<UserInfoResponse>,response: Response<UserInfoResponse>) {Log.d("注册", response.body().toString())// UserInfoResponse(code=200, userName=好, userPortrait=http://abc.com/myportrait.jpg, createTime=2025-03-05 16:51:19)}override fun onFailure(call: Call<UserInfoResponse>, t: Throwable) {Log.d("注册", "获取用户信息失败")}})}

todo还要考虑谷歌和facebook登录情况

相关文章:

todo: 使用融云imserve做登录(android)

使用融云做登录注册思路 注册界面需要name, email, password考虑到融云注册用户的post格式 POST http://api.rong-api.com/user/getToken.json?userId1690544550qqcom&nameIronman这里的userId可以使用用户的email&#xff0c;但是要截断和 . 符号&#xff0c;即1690544…...

Mac OS升级后变慢了,如何恢复老系统?

我的一台Mac Air闲置很久了&#xff0c;原因是某次系统升级后用着会卡&#xff0c;有差不多10年没用了。今天想试着恢复一下出厂系统&#xff0c;目前看这条路可以走通。记录如下&#xff1a; 1、去哪里下载旧版系统&#xff1f; https://support.apple.com/zh-cn/102662 2、…...

cursor使用经验分享(java后端服务开发向)

前言 cursor是一款基于vscode&#xff0c;并集成AI能力的代码编辑器&#xff0c;其功能包括但不限于代码生成及补全、AI对话&#xff08;能够直接将代码环境作为上下文&#xff09;、即时应用建议等等&#xff0c;是一款面向未来的代码编辑器。 对于vscode&#xff0c;最先想…...

初次使用 IDE 搭配 Lombok 注解的配置

前言 在 Java 开发的漫漫征程中&#xff0c;我们总会遇到各种提升效率的工具。Lombok 便是其中一款能让代码编写变得更加简洁高效的神奇库。它通过注解的方式&#xff0c;巧妙地在编译阶段为我们生成那些繁琐的样板代码&#xff0c;比如 getter、setter、构造函数等。然而&…...

vue 安装依赖npm install过程中报错npm ERR! cb() never called!

解决办法&#xff1a; 步骤 1&#xff1a;清理 npm 缓存 npm cache clean --force rm -rf node_modules package-lock.json 步骤 2&#xff1a;一个第三方 npm 工具包&#xff0c;功能是 自动重试失败的 npm install 操作&#xff0c;适用于网络不稳定或依赖源不可靠的场景 …...

android接入rocketmq

一 前言 RocketMQ 作为一个功能强大的消息队列系统&#xff0c;不仅支持基本的消息发布与订阅&#xff0c;还提供了顺序消息、延时消息、事务消息等高级功能&#xff0c;适应了复杂的分布式系统需求。其高可用性架构、多副本机制、完善的运维管理工具&#xff0c;以及安全控制…...

libilibi项目优化(1)使用Redis实现缓存

第一版 获取视频信息使用旁路缓存 当视频信息存在缓存中时&#xff08;命中&#xff09;&#xff0c;直接从缓存中获取。不存在缓存中时&#xff0c;先从数据库中查出对应的信息&#xff0c;写入缓存后再放回数据。 //获取视频详细信息RequestMapping("/getVideoInfo&q…...

The Rust Programming Language 学习 (二)

通用编程概念 变量和可变性 默认情况下变量是不可变的&#xff08;immutable&#xff09;,不过你也可以选择让变量是可变的&#xff08;mutable&#xff09;. 变量的遮蔽 你可以声明和前面变量具有相同名称的新变量,说这个是第一个变量被第二个变量遮蔽&#xff08;shadow&…...

http链接转成https的链接的几种方法

以下是一个将HTTP链接转换为HTTPS的JavaScript函数&#xff0c;处理了多种常见输入情况&#xff1a; function convertToHttps(url) {if (typeof url ! string) return url;// 移除首尾空格并处理空字符串const trimmedUrl url.trim();if (!trimmedUrl) return https://;// 替…...

STM32——串口通信 UART

一、基础配置 Universal Asynchronous Receiver Transmitter 异步&#xff0c;串行&#xff0c;全双工 TTL电平 &#xff1a;高电平1 低电平0 帧格式&#xff1a; 起始位1bit 数据位8bit 校验位1bit 终止位1bit NVIC Settings一栏使能接受中断。 之前有设置LCD&#xff0c;…...

mybatis日期格式与字符串不匹配bug

异常特征&#xff1a;java.lang.IllegalArgumentException: invalid comparison: java.time.LocalDateTime and java.lang.String ### Error updating database. Cause: java.lang.IllegalArgumentException: invalid comparison: java.time.LocalDateTime and java.lang.Str…...

文献分享: ConstBERT固定数目向量编码文档

&#x1f602;图放这了&#xff0c;大道至简的 idea \text{idea} idea不愧是 ECIR \text{ECIR} ECIR &#x1f449;原论文 1. ConstBERT \textbf{1. ConstBERT} 1. ConstBERT的原理 1️⃣模型的改进点&#xff1a;相较于 ColBERT \text{ColBERT} ColBERT为每个 Token \text{Tok…...

学习记录-用例设计编写

黑马测试视频记录 目录 一、 软件测试流程 二、测试用例编写格式 1、等价类法 2、边界值分析法 3、 判定表法 4、场景法​编辑 5、错误推荐法 一、 软件测试流程 二、测试用例编写格式 1、等价类法 2、边界值分析法 3、 判定表法 4、场景法 5、错误推荐法 时间紧任务重…...

学习工具的一天之(burp)

第一呢一定是先下载 【Java环境】&#xff1a;Java Downloads | Oracle 下来是burp的下载 Download Burp Suite Community Edition - PortSwigger 【下载方法二】关注的一个博主 【BurpSuite 安装激活使用详细上手教程 web安全测试工具】https://www.bilibili.com/video/BV…...

el-tree右键节点动态位置展示菜单;el-tree的节点图片动态根据节点属性color改变背景色;加遮罩层(opacity)

一、el-tree右键节点动态位置展示菜单 关键:@node-contextmenu="handleRightClick"与@node-click=“handleNodeClick” <div class="content"><el-tabs class="tabs" @tab-click="handleClick" v-model="Modal"…...

K8s 1.27.1 实战系列(一)准备工作

一、主机规划与硬件要求 1、节点数量 至少需要 3 台服务器(1 台 Master 节点,2 台 Worker 节点)。本地测试可缩容:若仅用于测试,可缩减为 1 个 Master 和 1 个 Worker,但需注意稳定性风险。2、硬件配置 ​Master 节点:建议 2 核 CPU、8GB 内存、80GB 硬盘。​Worker 节…...

说一下SpringBoot3新特新和JDK17新特性

JDK1.8&#xff08;Java8&#xff09;新特性 stream流式编程 流处理 Stream API 提供了对集合数据进行操作的一种高效、简洁的方式。它支持顺序和并行的聚合操作 如&#xff1a;过滤&#xff08;filter&#xff09;、排序&#xff08;sort&#xff09;、映射&#xff08;map&…...

Linux系统服务安全检测手记

一&#xff1a;服务器ip暴露ip和端口的安全问题 服务器IP和端口暴露在外网中确实存在一定的安全风险&#xff0c;以下是几个主要的安全问题及相应的缓解措施&#xff1a; ### 主要安全问题 1. **直接攻击**&#xff1a; - 暴露的IP地址和开放的端口可能成为黑客直接攻击的…...

鸿蒙与DeepSeek深度整合:构建下一代智能操作系统生态

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到网站。 https://www.captainbed.cn/north 目录 技术融合背景与价值鸿蒙分布式架构解析DeepSeek技术体系剖析核心整合架构设计智能调度系统实现…...

[创业之路-329]:华为铁三角实施的步骤

一、通用过程 华为铁三角实施的步骤主要包括以下几个关键阶段&#xff1a; 1、明确角色与职责 确定铁三角成员&#xff1a;组建由客户经理&#xff08;AR&#xff09;、解决方案经理&#xff08;SR&#xff09;和交付经理&#xff08;FR&#xff09;组成的铁三角团队。制定岗…...

3个步骤在Docker容器中运行本地Windows ISO镜像:从配置到优化

3个步骤在Docker容器中运行本地Windows ISO镜像&#xff1a;从配置到优化 【免费下载链接】windows Windows inside a Docker container. 项目地址: https://gitcode.com/GitHub_Trending/wi/windows 问题导入&#xff1a;为什么需要本地ISO镜像&#xff1f; 在使用Doc…...

从抓包实战出发:用Wireshark解密HTTP请求背后的TCP三次握手与挥手

从抓包实战出发&#xff1a;用Wireshark解密HTTP请求背后的TCP三次握手与挥手 当我们在浏览器中输入一个网址按下回车时&#xff0c;屏幕背后正上演着一场精密的协议芭蕾。作为开发者&#xff0c;你是否曾好奇&#xff1a;那些教科书上的TCP三次握手理论&#xff0c;在真实网络…...

P1122 最大子树和

题目描述 小明对数学饱有兴趣&#xff0c;并且是个勤奋好学的学生&#xff0c;总是在课后留在教室向老师请教一些问题。一天他早晨骑车去上课&#xff0c;路上见到一个老伯正在修剪花花草草&#xff0c;顿时想到了一个有关修剪花卉的问题。于是当日课后&#xff0c;小明就向老…...

采购管理系统:为企业实现降本增效、强化供应链韧性

在数字化浪潮下&#xff0c;采购管理已从传统的成本中心演变为企业的战略职能和价值引擎。选择一款合适的采购管理软件&#xff0c;对于企业实现降本增效、强化供应链韧性、赋能战略决策至关重要。本文将为您盘点市场上主流的五款采购管理软件&#xff0c;深入剖析其核心能力。…...

Llama-3.2V-11B-cot部署教程:双卡4090一键启动视觉推理工具

Llama-3.2V-11B-cot部署教程&#xff1a;双卡4090一键启动视觉推理工具 1. 项目概述 Llama-3.2V-11B-cot是基于Meta多模态大模型开发的高性能视觉推理工具&#xff0c;专为双卡4090环境优化。它解决了传统大模型部署复杂、视觉权重加载失败等痛点&#xff0c;让普通用户也能轻…...

飞书文档全流程备份终极方案:从手动操作到自动化管理的完美转型

飞书文档全流程备份终极方案&#xff1a;从手动操作到自动化管理的完美转型 【免费下载链接】feishu-doc-export 项目地址: https://gitcode.com/gh_mirrors/fe/feishu-doc-export 价值定位&#xff1a;破解企业文档管理的三大核心痛点 &#x1f4ca; 在数字化办公日益…...

Go语言HTTP服务开发:从标准库到框架

Go语言HTTP服务开发&#xff1a;从标准库到框架 作为一个写了十几年代码的Go后端老兵&#xff0c;我在HTTP服务开发上踩过不少坑。今天就来分享一下Go语言HTTP服务开发的实践经验&#xff0c;从标准库到框架。 一、标准库net/http 1. 基本用法 package mainimport ("fmt&q…...

告别虚拟机!在Windows 11上零配置搭建Masm汇编实验环境(保姆级图文教程)

在Windows 11上零配置搭建Masm汇编实验环境&#xff1a;从入门到实战 对于计算机专业的学生和开发者来说&#xff0c;汇编语言是理解计算机底层工作原理的重要工具。然而&#xff0c;传统的汇编环境搭建往往需要复杂的配置步骤或依赖虚拟机&#xff0c;这给初学者带来了不小的门…...

VideoAgentTrek-ScreenFilter快速部署:基于Docker与ComfyUI的可视化工作流搭建

VideoAgentTrek-ScreenFilter快速部署&#xff1a;基于Docker与ComfyUI的可视化工作流搭建 你是不是也对那些能自动处理视频、实现智能过滤的AI模型感到好奇&#xff0c;但又觉得命令行操作太复杂&#xff0c;参数调整像在猜谜&#xff1f;别担心&#xff0c;今天我们就来聊聊…...

Uvicorn源码中的中介者模式:组件通信与解耦设计

Uvicorn源码中的中介者模式&#xff1a;组件通信与解耦设计 【免费下载链接】uvicorn An ASGI web server, for Python. &#x1f984; 项目地址: https://gitcode.com/GitHub_Trending/uv/uvicorn Uvicorn作为Python生态中流行的ASGI web服务器&#xff0c;其内部架构巧…...