1 /*
2 * Copyright (C) 2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15 #include "convert_utils.h"
16 #include "pasteboard_hilog.h"
17 namespace OHOS {
18 namespace MiscServices {
19 using UnifiedRecord = UDMF::UnifiedRecord;
20 using UnifiedData = UDMF::UnifiedData;
21 using UnifiedDataProperties = UDMF::UnifiedDataProperties;
22 using UDType = UDMF::UDType;
23 using ShareOptions = UDMF::ShareOptions;
24
Convert(const UnifiedData & unifiedData)25 std::shared_ptr<PasteData> ConvertUtils::Convert(const UnifiedData &unifiedData)
26 {
27 auto pasteData = std::make_shared<PasteData>(Convert(unifiedData.GetRecords()));
28 pasteData->SetProperty(ConvertProperty(unifiedData.GetProperties(), unifiedData));
29 return pasteData;
30 }
31
Convert(const PasteData & pasteData)32 std::shared_ptr<UnifiedData> ConvertUtils::Convert(const PasteData &pasteData)
33 {
34 auto unifiedData = std::make_shared<UnifiedData>();
35 unifiedData->SetRecords(Convert(pasteData.AllRecords()));
36 unifiedData->SetProperties(ConvertProperty(pasteData.GetProperty()));
37 unifiedData->SetDataId(pasteData.GetDataId());
38 return unifiedData;
39 }
40
Convert(const std::vector<std::shared_ptr<PasteDataRecord>> & records)41 std::vector<std::shared_ptr<UnifiedRecord>> ConvertUtils::Convert(
42 const std::vector<std::shared_ptr<PasteDataRecord>> &records)
43 {
44 std::vector<std::shared_ptr<UnifiedRecord>> unifiedRecords;
45 for (auto const &record : records) {
46 unifiedRecords.emplace_back(Convert(record));
47 }
48 return unifiedRecords;
49 }
50
Convert(const std::vector<std::shared_ptr<UnifiedRecord>> & records)51 std::vector<std::shared_ptr<PasteDataRecord>> ConvertUtils::Convert(
52 const std::vector<std::shared_ptr<UnifiedRecord>> &records)
53 {
54 std::vector<std::shared_ptr<PasteDataRecord>> pasteboardRecords;
55 for (auto const &record : records) {
56 pasteboardRecords.emplace_back(Convert(record));
57 }
58 return pasteboardRecords;
59 }
60
Convert(std::shared_ptr<PasteDataRecord> record)61 std::shared_ptr<UnifiedRecord> ConvertUtils::Convert(std::shared_ptr<PasteDataRecord> record)
62 {
63 PASTEBOARD_CHECK_AND_RETURN_RET_LOGE(record != nullptr, nullptr, PASTEBOARD_MODULE_CLIENT,
64 "paste record is nullptr");
65 std::shared_ptr<UnifiedRecord> udmfRecord = std::make_shared<UnifiedRecord>();
66 auto entries = Convert(record->GetEntries(), record);
67 if (entries->empty()) {
68 PASTEBOARD_HILOGW(PASTEBOARD_MODULE_CLIENT, "entries is nullptr");
69 auto udmfValue = record->GetUDMFValue();
70 if (udmfValue) {
71 auto utdId = CommonUtils::Convert2UtdId(record->GetUDType(), record->GetMimeType());
72 udmfRecord->AddEntry(utdId, std::move(*udmfValue));
73 }
74 return udmfRecord;
75 }
76 for (auto &udmfEntry : *entries) {
77 udmfRecord->AddEntry(udmfEntry.first, std::move(udmfEntry.second));
78 }
79 udmfRecord->SetChannelName(CHANNEL_NAME);
80 udmfRecord->SetDataId(record->GetDataId());
81 udmfRecord->SetRecordId(record->GetRecordId());
82 return udmfRecord;
83 }
84
Convert(std::shared_ptr<UnifiedRecord> record)85 std::shared_ptr<PasteDataRecord> ConvertUtils::Convert(std::shared_ptr<UnifiedRecord> record)
86 {
87 PASTEBOARD_CHECK_AND_RETURN_RET_LOGE(record != nullptr, nullptr, PASTEBOARD_MODULE_CLIENT,
88 "udmfRecord is nullptr");
89 std::shared_ptr<PasteDataRecord> pbRecord = std::make_shared<PasteDataRecord>();
90 auto utdId = record->GetUtdId();
91 pbRecord->AddEntry(utdId, std::make_shared<PasteDataEntry>(utdId, record->GetOriginValue()));
92 for (auto const &entry : Convert(record->GetEntries())) {
93 if (entry == nullptr) {
94 PASTEBOARD_HILOGW(PASTEBOARD_MODULE_CLIENT, "entry is empty");
95 continue;
96 }
97 if (utdId == entry->GetUtdId()) {
98 continue;
99 }
100 pbRecord->AddEntry(entry->GetUtdId(), entry);
101 }
102 pbRecord->SetDataId(record->GetDataId());
103 pbRecord->SetRecordId(record->GetRecordId());
104 if (record->GetEntryGetter() != nullptr) {
105 pbRecord->SetDelayRecordFlag(true);
106 }
107 return pbRecord;
108 }
109
Convert(const std::shared_ptr<std::map<std::string,UDMF::ValueType>> & entries)110 std::vector<std::shared_ptr<PasteDataEntry>> ConvertUtils::Convert(
111 const std::shared_ptr<std::map<std::string, UDMF::ValueType>> &entries)
112 {
113 std::vector<std::shared_ptr<PasteDataEntry>> pbEntries;
114 PASTEBOARD_CHECK_AND_RETURN_RET_LOGE(entries != nullptr, pbEntries, PASTEBOARD_MODULE_CLIENT,
115 "pbEntries is empty");
116 for (auto const &[utdId, value] : *entries) {
117 pbEntries.emplace_back(std::make_shared<PasteDataEntry>(utdId, value));
118 }
119 return pbEntries;
120 }
121
Convert(const std::shared_ptr<PasteDataEntry> & entry,std::shared_ptr<PasteDataRecord> record)122 UDMF::ValueType ConvertUtils::Convert(const std::shared_ptr<PasteDataEntry>& entry,
123 std::shared_ptr<PasteDataRecord> record)
124 {
125 PASTEBOARD_CHECK_AND_RETURN_RET_LOGE(entry != nullptr, nullptr, PASTEBOARD_MODULE_CLIENT,
126 "entry is null, convert failed.");
127 auto utdId = entry->GetUtdId();
128 auto value = entry->GetValue();
129 if (std::holds_alternative<std::monostate>(value) || std::holds_alternative<std::shared_ptr<Object>>(value)) {
130 if (std::holds_alternative<std::shared_ptr<Object>>(value) && CommonUtils::IsFileUri(utdId) &&
131 record->GetUri() != nullptr) {
132 auto object = std::get<std::shared_ptr<Object>>(value);
133 object->value_[UDMF::FILE_URI_PARAM] = record->GetUri()->ToString();
134 }
135 return value;
136 }
137 auto mimeType = entry->GetMimeType();
138 auto object = std::make_shared<UDMF::Object>();
139 if (mimeType == MIMETYPE_TEXT_PLAIN) {
140 object->value_[UDMF::UNIFORM_DATA_TYPE] = utdId;
141 if (std::holds_alternative<std::string>(value)) {
142 object->value_[UDMF::CONTENT] = std::get<std::string>(value);
143 }
144 } else if (mimeType == MIMETYPE_TEXT_HTML) {
145 object->value_[UDMF::UNIFORM_DATA_TYPE] = utdId;
146 if (std::holds_alternative<std::string>(value)) {
147 object->value_[UDMF::HTML_CONTENT] = std::get<std::string>(value);
148 }
149 } else if (mimeType == MIMETYPE_TEXT_URI) {
150 object->value_[UDMF::UNIFORM_DATA_TYPE] = utdId;
151 if (std::holds_alternative<std::string>(value) && record->GetUri() != nullptr) {
152 object->value_[UDMF::FILE_URI_PARAM] = record->GetUri()->ToString();
153 }
154 } else if (mimeType == MIMETYPE_PIXELMAP) {
155 object->value_[UDMF::UNIFORM_DATA_TYPE] = utdId;
156 if (std::holds_alternative<std::shared_ptr<OHOS::Media::PixelMap>>(value)) {
157 object->value_[UDMF::PIXEL_MAP] = std::get<std::shared_ptr<OHOS::Media::PixelMap>>(value);
158 }
159 } else if (mimeType == MIMETYPE_TEXT_WANT) {
160 PASTEBOARD_HILOGW(PASTEBOARD_MODULE_CLIENT, "mimeType is want, udmf not support");
161 } else {
162 object->value_[UDMF::UNIFORM_DATA_TYPE] = utdId;
163 if (std::holds_alternative<std::vector<uint8_t>>(value)) {
164 auto arrayBuffer = std::get<std::vector<uint8_t>>(value);
165 object->value_[UDMF::ARRAY_BUFFER] = arrayBuffer;
166 object->value_[UDMF::ARRAY_BUFFER_LENGTH] = static_cast<int64_t>(arrayBuffer.size());
167 }
168 }
169 return object;
170 }
171
Convert(const std::vector<std::shared_ptr<PasteDataEntry>> & entries,std::shared_ptr<PasteDataRecord> record)172 std::shared_ptr<std::vector<std::pair<std::string, UDMF::ValueType>>> ConvertUtils::Convert(
173 const std::vector<std::shared_ptr<PasteDataEntry>> &entries, std::shared_ptr<PasteDataRecord> record)
174 {
175 std::map<std::string, UDMF::ValueType> udmfEntryMap;
176 std::vector<std::pair<std::string, UDMF::ValueType>> udmfEntries;
177 std::vector<std::string> entryUtdIds;
178 for (auto const &entry : entries) {
179 if (entry == nullptr) {
180 continue;
181 }
182 if (udmfEntryMap.find(entry->GetUtdId()) == udmfEntryMap.end()) {
183 entryUtdIds.emplace_back(entry->GetUtdId());
184 }
185 udmfEntryMap.insert_or_assign(entry->GetUtdId(), Convert(entry, record));
186 }
187 for (auto const &utdId : entryUtdIds) {
188 auto item = udmfEntryMap.find(utdId);
189 if (item != udmfEntryMap.end()) {
190 udmfEntries.emplace_back(std::pair<std::string, UDMF::ValueType>(item->first, item->second));
191 }
192 }
193 return std::make_shared<std::vector<std::pair<std::string, UDMF::ValueType>>>(udmfEntries);
194 }
195
UdmfOptions2PbOption(ShareOptions udmfOptions)196 ShareOption ConvertUtils::UdmfOptions2PbOption(ShareOptions udmfOptions)
197 {
198 ShareOption pbOption = CrossDevice;
199 switch (udmfOptions) {
200 case UDMF::IN_APP:
201 pbOption = InApp;
202 break;
203 case UDMF::CROSS_APP:
204 pbOption = LocalDevice;
205 break;
206 case UDMF::CROSS_DEVICE:
207 pbOption = CrossDevice;
208 break;
209 default:
210 break;
211 }
212 return pbOption;
213 }
214
PbOption2UdmfOptions(ShareOption pbOption)215 ShareOptions ConvertUtils::PbOption2UdmfOptions(ShareOption pbOption)
216 {
217 ShareOptions udmfOptions = UDMF::CROSS_DEVICE;
218 switch (pbOption) {
219 case InApp:
220 udmfOptions = UDMF::IN_APP;
221 break;
222 case LocalDevice:
223 udmfOptions = UDMF::CROSS_APP;
224 break;
225 case CrossDevice:
226 udmfOptions = UDMF::CROSS_DEVICE;
227 break;
228 default:
229 break;
230 }
231 return udmfOptions;
232 }
233
ConvertProperty(const std::shared_ptr<UnifiedDataProperties> & properties,const UnifiedData & unifiedData)234 PasteDataProperty ConvertUtils::ConvertProperty(
235 const std::shared_ptr<UnifiedDataProperties> &properties, const UnifiedData &unifiedData)
236 {
237 if (!properties) {
238 return {};
239 }
240 PasteDataProperty pasteDataProperty;
241 pasteDataProperty.shareOption = UdmfOptions2PbOption(properties->shareOptions);
242 pasteDataProperty.additions = properties->extras;
243 pasteDataProperty.timestamp = properties->timestamp;
244 pasteDataProperty.tag = properties->tag;
245 auto utdIds = unifiedData.GetTypesLabels();
246 pasteDataProperty.mimeTypes = Convert(utdIds);
247 pasteDataProperty.isRemote = properties->isRemote;
248 return PasteDataProperty(pasteDataProperty);
249 }
250
ConvertProperty(const PasteDataProperty & properties)251 std::shared_ptr<UnifiedDataProperties> ConvertUtils::ConvertProperty(const PasteDataProperty &properties)
252 {
253 auto unifiedDataProperties = std::make_shared<UnifiedDataProperties>();
254 unifiedDataProperties->shareOptions = PbOption2UdmfOptions(properties.shareOption);
255 unifiedDataProperties->extras = properties.additions;
256 unifiedDataProperties->timestamp = properties.timestamp;
257 unifiedDataProperties->tag = properties.tag;
258 unifiedDataProperties->isRemote = properties.isRemote;
259 return unifiedDataProperties;
260 }
261
Convert(const std::vector<std::string> & utdIds)262 std::vector<std::string> ConvertUtils::Convert(const std::vector<std::string> &utdIds)
263 {
264 std::vector<std::string> types;
265 for (const auto &utdId : utdIds) {
266 types.push_back(CommonUtils::Convert2MimeType(utdId));
267 }
268 return types;
269 }
270 } // namespace MiscServices
271 } // namespace OHOS