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

鸿蒙Socket通信示例(TCP通信)

前言

DevEco Studio版本:4.0.0.600

参考链接:OpenHarmony Socket

效果

TCPSocket

1、bind绑定本地IP地址

private bindTcpSocket() {let localAddress = resolveIP(wifi.getIpInfo().ipAddress)console.info("111111111  localAddress: " + localAddress);//bind本地地址tcpSocket.bind({ address: localAddress }).then(() => {console.info("111111111 绑定Tcp成功");}).catch(err => {console.info("111111111 绑定Tcp失败,原因: " + err);});
}

2、设置tcpSocket的监听

private tcpSocketListener() {tcpSocket.on('connect', () => {this.connectMessage = '已连接'console.info("111111111  监听: 连接成功");});tcpSocket.on('message', (value: {message: ArrayBuffer,remoteInfo: socket.SocketRemoteInfo}) => {this.messageReceive = this.messageReceive + this.resolveArrayBuffer(value.message) + "\n"console.info("111111111  接收服务器的数据: " + this.messageReceive);});tcpSocket.on('close', () => {this.connectMessage = '未连接'console.info("111111111   监听:关闭连接")});
}

3、连接服务器

private tcpSocketConnect() {//开始连接tcpSocket.connect({address: { address: connectAddress.address, port: connectAddress.port, family: connectAddress.family },timeout: 6000}).then(() => {console.info("111111111   tcpSocketConnect:连接成功");let tcpExtraOptions: socket.TCPExtraOptions = {keepAlive: true, //是否保持连接。默认为falseOOBInline: true, //是否为OOB内联。默认为falseTCPNoDelay: true, //TCPSocket连接是否无时延。默认为falsesocketLinger: {on: true,linger: 10}, //socket是否继续逗留。- on:是否逗留(true:逗留;false:不逗留)。- linger:逗留时长,单位毫秒(ms),取值范围为0~65535。当入参on设置为true时,才需要设置。receiveBufferSize: 1000, //接收缓冲区大小(单位:Byte),默认为0sendBufferSize: 1000, //发送缓冲区大小(单位:Byte),默认为0。reuseAddress: true, //是否重用地址。默认为false。socketTimeout: 3000//套接字超时时间,单位毫秒(ms),默认为0。}tcpSocket.setExtraOptions(tcpExtraOptions, (err: BusinessError) => {if (err) {console.log('111111111   setExtraOptions 失败');return;}console.log('111111111  setExtraOptions 成功');});}).catch((error) => {console.info("111111111  tcpSocketConnect 连接失败,原因: " + JSON.stringify(error));})
}

4、发送数据内容

private sendMessage() {tcpSocket.getState().then((data) => {console.info("111111111 连接状态: " + JSON.stringify(data))//已连接if (data.isConnected) {//发送消息tcpSocket.send({ data: `${this.inputContent}\n`, encoding: 'UTF-8' }).then(() => {this.messageReceive = this.messageReceive + "发送:" + this.inputContent + "\n"console.info("111111111  消息发送成功");}).catch((error) => {console.info("111111111  消息发送失败,原因:" + JSON.stringify(error));})} else {console.info("111111111  没有连接");this.connectMessage = '未连接,服务器断了'}})
}

5、结束释放资源

private tcpSocketRelease() {tcpSocket.off("message")tcpSocket.off("connect")tcpSocket.off("close")tcpSocket.close()tcpSocket = null
}

6、UI实现

build() {Column() {TextInput({ placeholder: '请输入用户名', text: '测试数据:Test' }).width('100%').margin({ top: 20, bottom: 20 }).onChange((value: string) => {this.inputContent = value})Button('发送数据').width('100%').margin({ top: 20, bottom: 20 }).onClick(() => {this.sendMessage()})Text() {Span('连接状态:')Span(this.connectMessage).fontColor(Color.Red)}Scroll() {Column() {Text() {Span('内容:\n')Span(this.messageReceive).fontColor(Color.Pink)}}.width('100%').alignItems(HorizontalAlign.Start)}.width("100%").alignSelf(ItemAlign.Start).flexShrink(1).margin({ top: 15 })}.alignItems(HorizontalAlign.Start).padding({ left: 15, right: 15 }).width('100%').height('100%')
}

详细代码

1、Index.ets

import socket from '@ohos.net.socket';
import wifi from '@ohos.wifi';
import { BusinessError } from '@ohos.base';
import { resolveIP } from '../utils/IpUtil';
import util from '@ohos.util';//tcp连接对象
let tcpSocket = socket.constructTCPSocketInstance();//连接服务器的地址和端口
let connectAddress = {address: '10.65.XX.XX', //要通信的 PC地址,CMD--->ipconfig查看family: 1,port: 6666
}@Entry
@Component
struct Index {@State connectMessage: string = '未连接'@State messageReceive: string = ''@State inputContent: string = ''aboutToAppear() {this.tcpSocketListener()this.bindTcpSocket()}onPageShow() {this.tcpSocketConnect()}onPageHide() {this.tcpSocketRelease()}build() {Column() {TextInput({ placeholder: '请输入用户名', text: '测试数据:Test' }).width('100%').margin({ top: 20, bottom: 20 }).onChange((value: string) => {this.inputContent = value})Button('发送数据').width('100%').margin({ top: 20, bottom: 20 }).onClick(() => {this.sendMessage()})Text() {Span('连接状态:')Span(this.connectMessage).fontColor(Color.Red)}Scroll() {Column() {Text() {Span('内容:\n')Span(this.messageReceive).fontColor(Color.Pink)}}.width('100%').alignItems(HorizontalAlign.Start)}.width("100%").alignSelf(ItemAlign.Start).flexShrink(1).margin({ top: 15 })}.alignItems(HorizontalAlign.Start).padding({ left: 15, right: 15 }).width('100%').height('100%')}/*** tcp连接状态和消息监听*/private tcpSocketListener() {tcpSocket.on('connect', () => {this.connectMessage = '已连接'console.info("111111111  监听: 连接成功");});tcpSocket.on('message', (value: {message: ArrayBuffer,remoteInfo: socket.SocketRemoteInfo}) => {this.messageReceive = this.messageReceive + this.resolveArrayBuffer(value.message) + "\n"console.info("111111111  接收服务器的数据: " + this.messageReceive);});tcpSocket.on('close', () => {this.connectMessage = '未连接'console.info("111111111   监听:关闭连接")});}/*** 绑定Tcp本地地址* bind的IP为'localhost'或'127.0.0.1'时,只允许本地回环接口的连接,即服务端和客户端运行在同一台机器上*/private bindTcpSocket() {let localAddress = resolveIP(wifi.getIpInfo().ipAddress)console.info("111111111  localAddress: " + localAddress);//bind本地地址tcpSocket.bind({ address: localAddress }).then(() => {console.info("111111111 绑定Tcp成功");}).catch(err => {console.info("111111111 绑定Tcp失败,原因: " + err);});}/*** 发送消息数据*/private sendMessage() {tcpSocket.getState().then((data) => {console.info("111111111 连接状态: " + JSON.stringify(data))//已连接if (data.isConnected) {//发送消息tcpSocket.send({ data: `${this.inputContent}\n`, encoding: 'UTF-8' }).then(() => {this.messageReceive = this.messageReceive + "发送:" + this.inputContent + "\n"console.info("111111111  消息发送成功");}).catch((error) => {console.info("111111111  消息发送失败,原因:" + JSON.stringify(error));})} else {console.info("111111111  没有连接");this.connectMessage = '未连接,服务器断了'}})}/*** 连接服务器*/private tcpSocketConnect() {//开始连接tcpSocket.connect({address: { address: connectAddress.address, port: connectAddress.port, family: connectAddress.family },timeout: 6000}).then(() => {console.info("111111111   tcpSocketConnect:连接成功");let tcpExtraOptions: socket.TCPExtraOptions = {keepAlive: true, //是否保持连接。默认为falseOOBInline: true, //是否为OOB内联。默认为falseTCPNoDelay: true, //TCPSocket连接是否无时延。默认为falsesocketLinger: {on: true,linger: 10}, //socket是否继续逗留。- on:是否逗留(true:逗留;false:不逗留)。- linger:逗留时长,单位毫秒(ms),取值范围为0~65535。当入参on设置为true时,才需要设置。receiveBufferSize: 1000, //接收缓冲区大小(单位:Byte),默认为0sendBufferSize: 1000, //发送缓冲区大小(单位:Byte),默认为0。reuseAddress: true, //是否重用地址。默认为false。socketTimeout: 3000//套接字超时时间,单位毫秒(ms),默认为0。}tcpSocket.setExtraOptions(tcpExtraOptions, (err: BusinessError) => {if (err) {console.log('111111111   setExtraOptions 失败');return;}console.log('111111111  setExtraOptions 成功');});}).catch((error) => {console.info("111111111  tcpSocketConnect 连接失败,原因: " + JSON.stringify(error));})}/*** 解析ArrayBuffer*/private resolveArrayBuffer(message: ArrayBuffer): string {let view = new Uint8Array(message);let textDecoder = util.TextDecoder.create()let str = textDecoder.decodeWithStream(view);console.info("111111111 message 缓存内容: " + str)return str;}/*** 关闭Socket监听和连接,释放资源*/private tcpSocketRelease() {tcpSocket.off("message")tcpSocket.off("connect")tcpSocket.off("close")tcpSocket.close()tcpSocket = null}
}

2、IpUtil.ets

export function resolveIP(ip: number): string {if (ip < 0 || ip > 0xFFFFFFFF) {throw ('The number is not normal!');}return (ip >>> 24) + '.' + (ip >> 16 & 0xFF) + '.' + (ip >> 8 & 0xFF) + '.' + (ip & 0xFF);
}

3、module.json5配置

因为涉及到网络访问,需要配置网络权限,在module.json5中配置

"requestPermissions": [{"name": "ohos.permission.INTERNET"  //联网},{"name": "ohos.permission.GET_NETWORK_INFO"  //获取网络相关信息},{"name": "ohos.permission.SET_NETWORK_INFO" //设置网络相关信息},{"name": "ohos.permission.GET_WIFI_INFO" //获取wifi相关信息}
]

服务器端Java代码

package org.example;import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;public class SocketService {public static void main(String[] args) {int port = 6666;try {// 创建ServerSocket对象,指定监听的端口号ServerSocket serverSocket = new ServerSocket(port);while (true) {Socket clientSocket = serverSocket.accept();System.out.println("客户端连接: " + clientSocket.getInetAddress().getHostAddress());BufferedReader reader = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));PrintWriter writer = new PrintWriter(clientSocket.getOutputStream(), true);String message;while ((message = reader.readLine()) != null) {System.out.println("从客户端接收到的消息: " + message);writer.println("回复: " + message);}reader.close();writer.close();clientSocket.close();System.out.println("连接断开");}} catch (Exception e) {e.printStackTrace();}}
}

相关文章:

鸿蒙Socket通信示例(TCP通信)

前言 DevEco Studio版本&#xff1a;4.0.0.600 参考链接&#xff1a;OpenHarmony Socket 效果 TCPSocket 1、bind绑定本地IP地址 private bindTcpSocket() {let localAddress resolveIP(wifi.getIpInfo().ipAddress)console.info("111111111 localAddress: " …...

yolov5-v6.0详细解读

yolov5-v6.0详细解读 一、yolov5版本介绍二、网络结构2.1 Backbone特征提取部分2.1.1 ConvBNSiLU模块2.1.2 C3模块2.1.2.1 BottleNeck模块 2.1.3 SPPF模块 2.2 Neck特征融合部分2.2.1 FPN2.2.2 PANet 2.3Head模块 三、目标框回归3.1 yolo标注格式3.2 yolov4目标回归框3.3 yolov…...

FPGA - 单总线协议(one-wire)

1&#xff0c;简介 单总线&#xff08;one-wire&#xff09;是美国 DALLAS 公司推出的外围串行扩展总线技术&#xff0c;与 SPI、I2C 等串行数据通信方式不同&#xff0c;它采用单根信号线&#xff0c;既传输时钟又传输数据&#xff0c;而且数据传输是双向的。它具有节省 I/O口…...

python的函数与类的定义

目录 1.函数 1.函数的定义 2.输入参数与输出参数的类型 3.输入和输出多个参数 1.普通参数 2.含有任意数量的参数 3.关键字参数 4.普通参数与多个参数的结合 2.类 1.类的定义 2.类的实例化 3.继承 1.函数 1.函数的定义 def 函数名(输入参数): 文档字符串 函数体 …...

Parade Series - WebRTC ( < 300 ms Low Latency ) T.B.D

Parade Series - FFMPEG (Stable X64) C:\Conda\parading-cam>ffmpeg -f dshow -i video"Surface Camera Front" -vcodec libx264 -preset:v ultrafast -tune:v zerolatency -an -rtsp_transport tcp -f rtsp://127.0.0.1:8554/cam0801...

【ARM】MDK在programming algorithm界面添加FLM

【更多软件使用问题请点击亿道电子官方网站查询】 1、 文档目标 解决在programming algorithm界面中无法添加想要的Flash编程算法的问题 2、 问题场景 在对于Debug进行Flash Download进行配置的时候&#xff0c;在programming algorithm界面中有对应的Flash编程算法。可以通过…...

springmvc学习笔记1

springmvc学习笔记part1 总概述图创建步骤创建project并在父工程中导入配置类添加为web工程检查maven配置写handller方法写配置类SpringMVC环境搭建项目部署关键步骤总结 具体设置路径设置注解接收参数&#xff08;重点param参数接收路径参数接收json参数接收请求头接收和cooki…...

力扣106 从中序与后续遍历序列构造二叉树

文章目录 题目描述解题思路代码 题目描述 给定两个整数数组 inorder 和 postorder &#xff0c;其中 inorder 是二叉树的中序遍历&#xff0c; postorder 是同一棵树的后序遍历&#xff0c;请你构造并返回这颗 二叉树 。 示例 1: 输入&#xff1a;inorder [9,3,15,20,7], …...

数字逻辑-时序逻辑电路一

一、实验目的 &#xff08;1&#xff09;熟悉触发器的逻辑功能及特性。 &#xff08;2&#xff09;掌握集成D和JK触发器的应用。 &#xff08;3&#xff09;掌握时序逻辑电路的分析和设计方法。 二、实验仪器及材料 三、实验内容及步骤 1、用D触发器&#xff08;74LS74&am…...

web 课程

文章目录 格式图片超链接书签链接表格例子横跨束跨 格式 <br /> <br/> #换行图片 <img> 标签是用于在网页中嵌入图像的 HTML 标签&#xff0c;它有一些属性可以用来控制图像的加载、显示和交互。以下是对 <img> 标签常用属性的详细介绍&#xff1a;…...

工业园区智慧水电设备管控系统

在现代工业园区中&#xff0c;水电设备的管控系统起着至关重要的作用。这些系统不仅仅是简单的机械装置&#xff0c;它们更是一种智慧的结合&#xff0c;为工业生产提供了可靠的保障和高效的管理。让我们一起来探索工业园区智慧水电设备管控系统的奥秘。 我们来看看水电设备的…...

Git之版本回退

文章转载于&#xff1a;https://www.jianshu.com/p/3020740561a8 以前&#xff0c;如果是要去除某一块功能&#xff0c;我都是选择性删除&#xff0c;选择性注释&#xff0c;然后前后逻辑各种查看&#xff0c;各种比较。每一次&#xff0c;改完这些我总感觉心好累啊&#xff01…...

「jQuery系列」jQuery 校验表单(Validate)

文章目录 一、校验表单&#xff08;Validate&#xff09;1. 基本用法2. 验证规则3. 国际化4. 插件扩展 二、Validate常用方法1. 基本验证2. 自定义验证规则3. 远程验证&#xff08;通过 AJAX&#xff09;4. 提交处理&#xff08;submitHandler&#xff09;5. 忽略某些元素的验证…...

【Java设计模式】十九、中介者模式

文章目录 1、中介者模式2、案例3、总结 1、中介者模式 如图&#xff1a; 同事类之间关联较多时&#xff0c;整体出现网状结构&#xff0c;耦合度极高。一个对象一变动&#xff0c;好多对象都得改。若变为右边的星形结构&#xff0c;则一个类的变动&#xff0c;只影响自身与中介…...

这个学习Python的神仙网站,后悔没早点发现

Python 作为时下最流行的编程语言&#xff0c;很多初学者都将它作为自学编程的首选。不管是有编程经验的开发者&#xff0c;还是新手小白&#xff0c;在这个 AIGC 时代&#xff0c; Python 都可以带你探索新世界。 入门 Python 绝非难事&#xff0c;但如何让自己坚持学下去是如…...

牛津大学“领域驱动设计”课程

领域驱动设计&#xff08;“DDD”&#xff09;是一种专注于系统领域而不是技术的软件设计方法。重点是构建共享的心理模型并以尽可能简单的方式在代码中表示该领域模型。数据库存储、框架等技术细节被认为是设计的次要方面。该模块将重点关注 DDD 和一般设计以及相关主题&#…...

Redisson分布式锁解决方案

官方地址 官网: https://redisson.org github: https://github.com/redisson/redisson 基于setnx实现的分布式锁存在的问题 redisson分布式锁原理 不可重入: 利用hash结构记录线程id和重入次数不可重试: 利用信号量和PubSub功能实现等待、唤醒, 获取锁失败的重试机制超时释放…...

linux命令深入研究——cat

cat命令&#xff0c;“猫”&#xff0c;可以理解为瞄一眼文件内容&#xff0c;其中可以用重定向符号对文件进行一些修改&#xff0c;如增加&#xff0c;删除文件内容&#xff0c;其命令参数如-n&#xff0c;-s&#xff0c;-b可以输出带有行号的行 如果想要快速删除文件内容&…...

代码随想录算法训练营第40天|343. 整数拆分、96.不同的二叉搜索树

343. 整数拆分 题目链接&#xff1a;link 文章讲解&#xff1a;link 视频讲解&#xff1a;link 一、做题感受&第一想法 其实第一反应是回溯……但感觉每层的集合都会很繁琐 二、学习文章后收获 1.动态规划思路 动规五要素分析 dp和i的定义&#xff1a;dp[i]指把i拆分后最…...

二叉树算法

递归序 每个节点都能回到3次! 相当于2执行完然后返回了代码会往下走,来到3节点 小总结: 也就是4节点先来到自己一次,不会执行if,先调用自己左边的那个函数,但是是null,直接返回。 这个函数执行完了,就会回到自己,调用自己右边的那个函数,结果又是空,又返回,回到…...

JavaScript 中的 ES|QL:利用 Apache Arrow 工具

作者&#xff1a;来自 Elastic Jeffrey Rengifo 学习如何将 ES|QL 与 JavaScript 的 Apache Arrow 客户端工具一起使用。 想获得 Elastic 认证吗&#xff1f;了解下一期 Elasticsearch Engineer 培训的时间吧&#xff01; Elasticsearch 拥有众多新功能&#xff0c;助你为自己…...

YSYX学习记录(八)

C语言&#xff0c;练习0&#xff1a; 先创建一个文件夹&#xff0c;我用的是物理机&#xff1a; 安装build-essential 练习1&#xff1a; 我注释掉了 #include <stdio.h> 出现下面错误 在你的文本编辑器中打开ex1文件&#xff0c;随机修改或删除一部分&#xff0c;之后…...

全球首个30米分辨率湿地数据集(2000—2022)

数据简介 今天我们分享的数据是全球30米分辨率湿地数据集&#xff0c;包含8种湿地亚类&#xff0c;该数据以0.5X0.5的瓦片存储&#xff0c;我们整理了所有属于中国的瓦片名称与其对应省份&#xff0c;方便大家研究使用。 该数据集作为全球首个30米分辨率、覆盖2000–2022年时间…...

Nginx server_name 配置说明

Nginx 是一个高性能的反向代理和负载均衡服务器&#xff0c;其核心配置之一是 server 块中的 server_name 指令。server_name 决定了 Nginx 如何根据客户端请求的 Host 头匹配对应的虚拟主机&#xff08;Virtual Host&#xff09;。 1. 简介 Nginx 使用 server_name 指令来确定…...

【android bluetooth 框架分析 04】【bt-framework 层详解 1】【BluetoothProperties介绍】

1. BluetoothProperties介绍 libsysprop/srcs/android/sysprop/BluetoothProperties.sysprop BluetoothProperties.sysprop 是 Android AOSP 中的一种 系统属性定义文件&#xff08;System Property Definition File&#xff09;&#xff0c;用于声明和管理 Bluetooth 模块相…...

【Zephyr 系列 10】实战项目:打造一个蓝牙传感器终端 + 网关系统(完整架构与全栈实现)

🧠关键词:Zephyr、BLE、终端、网关、广播、连接、传感器、数据采集、低功耗、系统集成 📌目标读者:希望基于 Zephyr 构建 BLE 系统架构、实现终端与网关协作、具备产品交付能力的开发者 📊篇幅字数:约 5200 字 ✨ 项目总览 在物联网实际项目中,**“终端 + 网关”**是…...

PL0语法,分析器实现!

简介 PL/0 是一种简单的编程语言,通常用于教学编译原理。它的语法结构清晰,功能包括常量定义、变量声明、过程(子程序)定义以及基本的控制结构(如条件语句和循环语句)。 PL/0 语法规范 PL/0 是一种教学用的小型编程语言,由 Niklaus Wirth 设计,用于展示编译原理的核…...

ios苹果系统,js 滑动屏幕、锚定无效

现象&#xff1a;window.addEventListener监听touch无效&#xff0c;划不动屏幕&#xff0c;但是代码逻辑都有执行到。 scrollIntoView也无效。 原因&#xff1a;这是因为 iOS 的触摸事件处理机制和 touch-action: none 的设置有关。ios有太多得交互动作&#xff0c;从而会影响…...

Python Ovito统计金刚石结构数量

大家好,我是小马老师。 本文介绍python ovito方法统计金刚石结构的方法。 Ovito Identify diamond structure命令可以识别和统计金刚石结构,但是无法直接输出结构的变化情况。 本文使用python调用ovito包的方法,可以持续统计各步的金刚石结构,具体代码如下: from ovito…...

NPOI Excel用OLE对象的形式插入文件附件以及插入图片

static void Main(string[] args) {XlsWithObjData();Console.WriteLine("输出完成"); }static void XlsWithObjData() {// 创建工作簿和单元格,只有HSSFWorkbook,XSSFWorkbook不可以HSSFWorkbook workbook new HSSFWorkbook();HSSFSheet sheet (HSSFSheet)workboo…...