• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# UDMF开发指导 (C/C++)
2<!--Kit: ArkData-->
3<!--Subsystem: DistributedDataManager-->
4<!--Owner: @jcwen-->
5<!--Designer: @junathuawei1; @zph000-->
6<!--Tester: @lj_liujing; @yippo; @logic42-->
7<!--Adviser: @ge-yafang-->
8
9
10## 场景介绍
11
12统一数据管理框架(UDMF):提供了数据跨应用、跨设备交互标准,定义了跨应用、跨设备数据交互过程中的数据语言,提升数据交互效率。提供安全、标准化数据流通通路,支持不同级别的数据访问权限与生命周期管理策略,实现高效的数据跨应用、跨设备共享。
13
14
15## 基本概念
16
17- **标准化数据类型**:Uniform Type Descriptor,简称UTD。主要针对同一种数据类型,提供统一定义,即标准数据类型描述符,定义了包括标识数据类型的ID、类型归属关系等相关信息,用于解决OpenHarmony系统中的类型模糊问题。一般用于过滤或者识别某一种数据类型的场景,比如文件预览、文件分享等。
18
19- **标准化数据结构**:Unified Data Structure,简称UDS。主要针对部分标准化数据类型定义了统一的数据内容结构,并明确了对应的描述信息。应用间使用标准化数据结构进行数据交互后,将遵从统一的解析标准,可有效减少适配相关的工作量。一般用于跨应用跨设备间的数据交互,比如拖拽。
20
21- **统一数据记录**:Unified Record,对UDMF支持的数据内容的抽象定义,例如一条文本记录、一条图片记录等。
22
23- **统一数据对象**:Unified Data,用于封装一组数据记录Unified Record。
24
25- **统一数据提供者**:Unified Data Provider,配置到统一数据记录中,用来提供UDS数据。通常用于数据的延迟发送场景,让UDS数据在数据使用方从统一数据记录中实际获取时才发生数据的转移。
26
27
28## 约束限制
29
30- UDMF支持批量数据记录的分组管理,每个分组整体大小不超过200MB,其中PlainText、Hyperlink、HTML内单个属性值数据上限20MB。
31- 向统一数据记录中添加用户自定义数据时,所添加的数据大小不超过100MB。
32- 向UDMF数据库中写入数据时,定义的唯一标识符的内存大小不小于512字节。
33
34
35
36## 接口说明
37
38详细的接口说明请参考[UDMF接口文档](../reference/apis-arkdata/capi-udmf.md)。
39
40| 接口名称                                                     | 描述                                                        |
41| ------------------------------------------------------------ | ----------------------------------------------------------- |
42| OH_Utd* OH_Utd_Create(const char* typeId)                    | 创建一个指向统一数据类型描述符OH_Utd的指针。                |
43| void OH_Utd_Destroy(OH_Utd* pThis)                           | 销毁指向统一数据类型描述符OH_Utd的指针。                    |
44| const char** OH_Utd_GetTypesByFilenameExtension(const char* extension, unsigned int* count) | 通过文件后缀名获取标准化数据类型ID。                        |
45| const char** OH_Utd_GetTypesByMimeType(const char* mimeType, unsigned int* count) | 通过MIME类型获取标准化数据类型ID。                          |
46| bool OH_Utd_Equals(OH_Utd* utd1, OH_Utd* utd2)               | 判断两种标准化数据类型是否相等。                            |
47| void OH_Utd_DestroyStringList(const char** list, unsigned int count) | 销毁字符串列表数据。                                        |
48| OH_UdsHyperlink* OH_UdsHyperlink_Create()                    | 创建一个指向标准化数据结构超链接类型OH_UdsHyperlink的指针。 |
49| void OH_UdsHyperlink_Destroy(OH_UdsHyperlink* pThis)         | 销毁指向标准化数据结构超链接类型OH_UdsHyperlink的指针。     |
50| const char* OH_UdsHyperlink_GetType(OH_UdsHyperlink* pThis)  | 获取OH_UdsHyperlink中的标准化数据类型ID。                   |
51| const char* OH_UdsHyperlink_GetUrl(OH_UdsHyperlink* pThis)   | 获取OH_UdsHyperlink中的链接URL。                            |
52| const char* OH_UdsHyperlink_GetDescription(OH_UdsHyperlink* pThis) | 获取OH_UdsHyperlink中的链接内容描述。                       |
53| int OH_UdsHyperlink_SetUrl(OH_UdsHyperlink* pThis, const char* url) | 设置OH_UdsHyperlink中的链接URL。                            |
54| int OH_UdsHyperlink_SetDescription(OH_UdsHyperlink* pThis, const char* description) | 设置OH_UdsHyperlink中的链接内容描述。                       |
55| OH_UdmfData* OH_UdmfData_Create()                            | 创建一个指向统一数据对象OH_UdmfData的指针。                 |
56| void OH_UdmfData_Destroy(OH_UdmfData* pThis)                 | 销毁指向统一数据对象OH_UdmfData的指针。                     |
57| int OH_UdmfData_AddRecord(OH_UdmfData* pThis, OH_UdmfRecord* record) | 向OH_UdmfData中增加一条OH_UdmfRecord数据记录。              |
58| bool OH_UdmfData_HasType(OH_UdmfData* pThis, const char* type) | 判断统一数据对象OH_UdmfData是否存在指定类型。               |
59| OH_UdmfRecord** OH_UdmfData_GetRecords(OH_UdmfData* pThis, unsigned int* count) | 获取OH_UdmfData中全部的数据记录。                           |
60| OH_UdmfRecord* OH_UdmfRecord_Create()                        | 创建一个指向统一数据记录OH_UdmfRecord的指针。               |
61| void OH_UdmfRecord_Destroy(OH_UdmfRecord* pThis)             | 销毁指向统一数据记录OH_UdmfRecord的指针。                   |
62| int OH_UdmfRecord_AddHyperlink(OH_UdmfRecord* pThis, OH_UdsHyperlink* hyperlink) | 向OH_UdmfRecord添加超链接类型数据。                         |
63| char** OH_UdmfRecord_GetTypes(OH_UdmfRecord* pThis, unsigned int* count) | 获取OH_UdmfRecord中全部的数据类型。                         |
64| int OH_UdmfRecord_GetHyperlink(OH_UdmfRecord* pThis, OH_UdsHyperlink* hyperlink) | 获取OH_UdmfRecord中超链接类型数据。                         |
65| int OH_Udmf_GetUnifiedData(const char* key, Udmf_Intention intention, OH_UdmfData* unifiedData) | 从UDMF数据库中获取数据。                                    |
66| int OH_Udmf_SetUnifiedData(Udmf_Intention intention, OH_UdmfData* unifiedData, char* key, unsigned int keyLen) | 向UDMF数据库中写入数据。                                    |
67| OH_UdmfRecordProvider* OH_UdmfRecordProvider_Create()        | 创建一个指向统一数据提供者的指针。                          |
68| int OH_UdmfRecordProvider_Destroy(OH_UdmfRecordProvider* provider) | 销毁指向统一数据提供者OH_UdmfRecordProvider的指针。 |
69| int OH_UdmfRecordProvider_SetData(OH_UdmfRecordProvider* provider, void* context, const OH_UdmfRecordProvider_GetData callback, const UdmfData_Finalize finalize) | 设置统一数据提供者的回调函数。                              |
70| int OH_UdmfRecord_SetProvider(OH_UdmfRecord* pThis, const char* const* types, unsigned int count, OH_UdmfRecordProvider* provider) | 将统一数据提供者配置到OH_UdmfRecord中。                     |
71
72
73## 添加动态链接库
74
75CMakeLists.txt中添加以下lib。
76
77```txt
78libudmf.so
79```
80
81## 引用头文件
82
83```c
84#include <cstdio>
85#include <cstring>
86#include <database/udmf/utd.h>
87#include <database/udmf/uds.h>
88#include <database/udmf/udmf.h>
89#include <database/udmf/udmf_meta.h>
90#include <database/udmf/udmf_err_code.h>
91```
92## 通过不同方式获取纯文本类型数据
93
94下面以获取纯文本数据的查询场景为例,说明如何使用UTD。
951. 通过后缀名“.txt”获取UTD的typeId。
962. 通过MIME类型“text/plain”获取UTD的typeId。
973. 使用以上两个步骤获取到的typeId创建UTD实例对象。
984. 比较UTD实例对象是否相等。
995. 使用结束后,删除上述步骤中产生的指针。
100
101```c
102// 1. 通过文件后缀名获取纯文本类型的UTD的typeId
103unsigned int typeIds1Count = 0;
104const char** typeIds1 = OH_Utd_GetTypesByFilenameExtension(".txt", &typeIds1Count);
105printf("the count of typeIds1 is %u", typeIds1Count);
106// 2. 通过MIME类型获取typeId
107unsigned int typeIds2Count = 0;
108const char** typeIds2 = OH_Utd_GetTypesByMimeType("text/plain", &typeIds2Count);
109printf("the count of typeIds2 is %u", typeIds2Count);
110// 3. 使用以上两个步骤获取到的typeId创建UTD实例对象。
111OH_Utd* utd1 = OH_Utd_Create(typeIds1[0]);
112OH_Utd* utd2 = OH_Utd_Create(typeIds2[0]);
113// 4. 比较两种方式获取到的typeId对应的UTD是否相同
114bool isEquals = OH_Utd_Equals(utd1, utd2);
115if (isEquals) {
116    printf("utd1 == utd2");
117} else {
118    printf("utd1 != utd2");
119}
120// 5. 销毁OH_Utd_GetTypesByFilenameExtension与OH_Utd_GetFilenameExtensions函数获取到的指针,同时销毁UTD指针
121OH_Utd_DestroyStringList(typeIds1, typeIds1Count);
122OH_Utd_DestroyStringList(typeIds2, typeIds2Count);
123OH_Utd_Destroy(utd1);
124OH_Utd_Destroy(utd2);
125```
126
127## 使用UDMF发送UDS数据
128
129下面以发送超链接hyperlink类型数据场景为例,说明如何使用UDS与UDMF。
1301. 创建超链接hyperlink数据的UDS数据结构。
1312. 设置hyperlink中的URL和描述信息。
1323. 将hyperlink数据放入数据记录OH_UdmfRecord中。
1334. 将数据记录OH_UdmfRecord添加到统一数据OH_UdmfData中。
1345. 保存以上数据至数据库中,得到返回的key值。
1356. 使用结束后,删除上述步骤中产生的指针。
136
137```c
138// 1. 创建超链接hyperlink数据的UDS数据结构。
139OH_UdsHyperlink* hyperlink = OH_UdsHyperlink_Create();
140// 2. 设置hyperlink中的URL和描述信息。
141if (OH_UdsHyperlink_SetUrl(hyperlink, "www.demo.com") != Udmf_ErrCode::UDMF_E_OK) {
142    printf("Hyperlink set url error!");
143}
144if (OH_UdsHyperlink_SetDescription(hyperlink, "This is the description.") != Udmf_ErrCode::UDMF_E_OK) {
145    printf("Hyperlink set description error!");
146}
147// 3. 创建OH_UdmfRecord对象,并向OH_UdmfRecord中添加超链接类型数据。
148OH_UdmfRecord* record = OH_UdmfRecord_Create();
149if (OH_UdmfRecord_AddHyperlink(record, hyperlink) != Udmf_ErrCode::UDMF_E_OK) {
150    printf("Add hyperlink to record error!");
151}
152// 4. 创建OH_UdmfData对象,并向OH_UdmfData中添加OH_UdmfRecord。
153OH_UdmfData* data = OH_UdmfData_Create();
154if (OH_UdmfData_AddRecord(data, record) != Udmf_ErrCode::UDMF_E_OK) {
155    printf("Add record to data error!");
156}
157// 5. 构建数据,将数据写入数据库中,得到返回的key值。
158char key[UDMF_KEY_BUFFER_LEN] = {0};
159if (OH_Udmf_SetUnifiedData(Udmf_Intention::UDMF_INTENTION_DRAG, data, key, sizeof(key)) != Udmf_ErrCode::UDMF_E_OK) {
160    printf("Set data error!");
161}
162printf("key = %s", key);
163// 6. 使用完成后销毁指针。
164OH_UdsHyperlink_Destroy(hyperlink);
165OH_UdmfRecord_Destroy(record);
166OH_UdmfData_Destroy(data);
167```
168
169## 使用UDMF接收UDS数据
170
171下面继续以获取超链接hyperlink类型数据场景为例,说明如何使用UDS与UDMF。
1721. 创建统一数据OH_UdmfData,用来承载数据库中读取的数据。
1732. 通过key值从数据库中获取到数据。
1743. 判断数据中是否有hyperlink类型的数据。
1754. 获取OH_UdmfData中的数据记录,并从数据记录中获取hyperlink数据。
1765. 读取hyperlink数据中的各项信息。
1776. 使用结束后,删除上述步骤中产生的指针。
178
179```c
180// 1. 创建统一数据OH_UdmfData。
181OH_UdmfData* readData = OH_UdmfData_Create();
182// 此处key为示例,不可直接使用,其值应与OH_Udmf_SetUnifiedData接口中获取到的key值保持一致。
183char key[] = {"udmf://Drag/com.ohos.test/0123456789"};
184// 2. 通过key值从数据库中获取到数据。
185if (OH_Udmf_GetUnifiedData(key, Udmf_Intention::UDMF_INTENTION_DRAG, readData) != Udmf_ErrCode::UDMF_E_OK) {
186    printf("Failed to get data.");
187    return;
188}
189// 3. 判断OH_UdmfData是否有对应的类型。
190if (!OH_UdmfData_HasType(readData, UDMF_META_HYPERLINK)) {
191    printf("There is no hyperlink type in data.");
192    return;
193}
194// 4. 获取数据记录和hyperlink数据。
195unsigned int recordsCount = 0;
196OH_UdmfRecord** records = OH_UdmfData_GetRecords(readData, &recordsCount);
197printf("the count of records count is %u", recordsCount);
198// 创建hyperlink的UDS,用来承载record中读取出来的hyperlink数据。
199OH_UdsHyperlink* hyperlink = OH_UdsHyperlink_Create();
200// 获取records中的元素。
201for (int i = 0; i < recordsCount; i++) {
202    // 获取OH_UdmfRecord类型列表。
203    unsigned int recordTypeIdCount = 0;
204    char** typeIdsFromRecord = OH_UdmfRecord_GetTypes(records[i], &recordTypeIdCount);
205    for (unsigned int j = 0; j < recordTypeIdCount; j++) {
206        // 从OH_UdmfRecord中获取超链接类型数据。
207        if (strcmp(typeIdsFromRecord[j], UDMF_META_HYPERLINK) == 0) {
208            // 获取hyperlink数据。
209            if (OH_UdmfRecord_GetHyperlink(records[i], hyperlink) != Udmf_ErrCode::UDMF_E_OK) {
210                printf("Fail get hyperlink from record!");
211            }
212        }
213    }
214}
215// 5. 读取OH_UdsHyperlink中的各项信息。
216printf("The hyperlink type id is : %s", OH_UdsHyperlink_GetType(hyperlink));
217printf("The hyperlink url is : %s", OH_UdsHyperlink_GetUrl(hyperlink));
218printf("The hyperlink description is : %s", OH_UdsHyperlink_GetDescription(hyperlink));
219// 6. 销毁指针。
220OH_UdsHyperlink_Destroy(hyperlink);
221OH_UdmfData_Destroy(readData);
222```
223
224## 使用UDMF延迟发送UDS数据
225
226### 定义UDS数据提供函数
227
228下面以超链接hyperlink类型数据场景为例,说明如何定义一个提供UDS数据的回调函数。
2291. 定义OH_UdmfRecordProvider的数据提供函数。
2302. 在数据提供函数中,创建hyperlink类型的UDS数据结构。
2313. 设置hyperlink中的URL和描述信息。
2324. 定义OH_UdmfRecordProvider实例注销回调函数。
233
234```c
235// 为了代码可读性,代码中省略了各个步骤操作结果的校验,实际开发中需要确认每次调用的成功。
236// 1. 获取数据时触发的提供UDS数据的回调函数。
237static void* GetDataCallback(void* context, const char* type) {
238    if (strcmp(type, UDMF_META_PLAIN_TEXT)) {
239        // 2. 创建超链接hyperlink数据的UDS数据结构。
240        OH_UdsHyperlink* hyperlink = OH_UdsHyperlink_Create();
241        // 3. 设置hyperlink中的URL和描述信息。
242        OH_UdsHyperlink_SetUrl(hyperlink, "www.demo.com");
243        OH_UdsHyperlink_SetDescription(hyperlink, "This is the description.");
244        return hyperlink;
245    }
246    return nullptr;
247}
248// 4. OH_UdmfRecordProvider销毁时触发的回调函数。
249static void ProviderFinalizeCallback(void* context) { printf("OH_UdmfRecordProvider finalize."); }
250```
251
252### 延迟发送UDS数据
253
254下面以延迟发送超链接hyperlink类型数据场景为例,说明如何使用OH_UdmfRecordProvider与UDMF。需要注意,此步骤完成后超链接类型数据并未真正写入数据库,只有当数据使用者从OH_UdmfRecord中获取OH_UdsHyperlink时,才会触发上文定义的`GetDataCallback`数据提供函数,从中得到数据。
255
2561. 创建一个OH_UdmfRecordProvider,并设置它的数据提供函数和销毁时的回调函数。
2572. 创建一个OH_UdmfRecord对象,并将OH_UdmfRecordProvider配置到其中。
2583. 创建一个OH_UdmfData对象,并向OH_UdmfData中添加OH_UdmfRecord。
2594. 构建数据,将数据写入数据库中,得到返回的Key值。
2605. 使用结束后,删除上述步骤中产生的指针。
261
262```c
263// 为了代码可读性,代码中省略了各个步骤操作结果的校验,实际开发中需要确认每次调用的成功。
264// 1. 创建一个统一数据提供者,并配置它提供数据、销毁时的两个回调函数。
265OH_UdmfRecordProvider* provider = OH_UdmfRecordProvider_Create();
266OH_UdmfRecordProvider_SetData(provider, (void* )provider, GetDataCallback, ProviderFinalizeCallback);
267
268// 2. 创建一个OH_UdmfRecord对象,并将OH_UdmfRecordProvider配置到其中。
269OH_UdmfRecord* record = OH_UdmfRecord_Create();
270const char* types[1] = {UDMF_META_HYPERLINK};
271OH_UdmfRecord_SetProvider(record, types, 1, provider);
272
273// 3. 创建OH_UdmfData对象,并向OH_UdmfData中添加OH_UdmfRecord。
274OH_UdmfData* data = OH_UdmfData_Create();
275OH_UdmfData_AddRecord(data, record);
276
277// 4. 构建数据,将数据写入数据库中,得到返回的Key值。
278char key[UDMF_KEY_BUFFER_LEN] = {0};
279OH_Udmf_SetUnifiedData(Udmf_Intention::UDMF_INTENTION_DRAG, data, key, sizeof(key));
280printf("key = %s", key);
281
282// 5. 使用完成后销毁指针。
283OH_UdmfRecordProvider_Destroy(provider);
284OH_UdmfRecord_Destroy(record);
285OH_UdmfData_Destroy(data);
286```