1 | // SPDX-FileCopyrightText: 2021 Carl Schwan <carlschwan@kde.org> |
2 | // |
3 | // SPDX-License-Identifier: LGPL-2.1-or-later |
4 | |
5 | #pragma once |
6 | |
7 | #include <Quotient/converters.h> |
8 | |
9 | #include <array> |
10 | |
11 | namespace Quotient { |
12 | /** |
13 | * JSON Web Key object as specified in |
14 | * https://spec.matrix.org/unstable/client-server-api/#extensions-to-mroommessage-msgtypes |
15 | * The only currently relevant member is `k`, the rest needs to be set to the defaults specified in the spec. |
16 | */ |
17 | struct JWK |
18 | { |
19 | Q_GADGET |
20 | Q_PROPERTY(QString kty MEMBER kty CONSTANT) |
21 | Q_PROPERTY(QStringList keyOps MEMBER keyOps CONSTANT) |
22 | Q_PROPERTY(QString alg MEMBER alg CONSTANT) |
23 | Q_PROPERTY(QString k MEMBER k CONSTANT) |
24 | Q_PROPERTY(bool ext MEMBER ext CONSTANT) |
25 | |
26 | public: |
27 | QString kty; |
28 | QStringList keyOps; |
29 | QString alg; |
30 | QString k; |
31 | bool ext; |
32 | }; |
33 | |
34 | struct QUOTIENT_API EncryptedFileMetadata { |
35 | Q_GADGET |
36 | Q_PROPERTY(QUrl url MEMBER url CONSTANT) |
37 | Q_PROPERTY(JWK key MEMBER key CONSTANT) |
38 | Q_PROPERTY(QString iv MEMBER iv CONSTANT) |
39 | Q_PROPERTY(QHash<QString, QString> hashes MEMBER hashes CONSTANT) |
40 | Q_PROPERTY(QString v MEMBER v CONSTANT) |
41 | Q_PROPERTY(bool isValid READ isValid CONSTANT) |
42 | |
43 | public: |
44 | QUrl url; |
45 | JWK key; |
46 | QString iv; |
47 | QHash<QString, QString> hashes; |
48 | QString v; |
49 | |
50 | bool isValid() const { return url.isValid(); } |
51 | }; |
52 | |
53 | #ifdef Quotient_E2EE_ENABLED |
54 | QUOTIENT_API std::pair<EncryptedFileMetadata, QByteArray> encryptFile( |
55 | const QByteArray& plainText); |
56 | QUOTIENT_API QByteArray decryptFile(const QByteArray& ciphertext, |
57 | const EncryptedFileMetadata& metadata); |
58 | #endif |
59 | |
60 | template <> |
61 | struct QUOTIENT_API JsonObjectConverter<EncryptedFileMetadata> { |
62 | static void dumpTo(QJsonObject& jo, const EncryptedFileMetadata& pod); |
63 | static void fillFrom(const QJsonObject& jo, EncryptedFileMetadata& pod); |
64 | }; |
65 | |
66 | template <> |
67 | struct QUOTIENT_API JsonObjectConverter<JWK> { |
68 | static void dumpTo(QJsonObject& jo, const JWK& pod); |
69 | static void fillFrom(const QJsonObject& jo, JWK& pod); |
70 | }; |
71 | |
72 | using FileSourceInfo = std::variant<QUrl, EncryptedFileMetadata>; |
73 | |
74 | QUOTIENT_API QUrl getUrlFromSourceInfo(const FileSourceInfo& fsi); |
75 | |
76 | QUOTIENT_API void setUrlInSourceInfo(FileSourceInfo& fsi, const QUrl& newUrl); |
77 | |
78 | // The way FileSourceInfo is stored in JSON requires an extra parameter so |
79 | // the original template is not applicable |
80 | template <> |
81 | void fillJson(QJsonObject&, const FileSourceInfo&) = delete; |
82 | |
83 | //! \brief Export FileSourceInfo to a JSON object |
84 | //! |
85 | //! Depending on what is stored inside FileSourceInfo, this function will insert |
86 | //! - a key-to-string pair where key is taken from jsonKeys[0] and the string |
87 | //! is the URL, if FileSourceInfo stores a QUrl; |
88 | //! - a key-to-object mapping where key is taken from jsonKeys[1] and the object |
89 | //! is the result of converting EncryptedFileMetadata to JSON, |
90 | //! if FileSourceInfo stores EncryptedFileMetadata |
91 | QUOTIENT_API void fillJson(QJsonObject& jo, |
92 | const std::array<QLatin1String, 2>& jsonKeys, |
93 | const FileSourceInfo& fsi); |
94 | |
95 | namespace FileMetadataMap { |
96 | QUOTIENT_API void add(const QString& roomId, |
97 | const QString& eventId, |
98 | const EncryptedFileMetadata& fileMetadata); |
99 | QUOTIENT_API void remove(const QString& roomId, |
100 | const QString& eventId); |
101 | |
102 | //! \brief Obtain file source information across connections, thread-safely |
103 | //! \return the previously saved EncryptedFileMetadata object, or an invalid |
104 | //! (default-constructed) object in case of unsuccessful lookup |
105 | QUOTIENT_API EncryptedFileMetadata lookup(const QString& roomId, |
106 | const QString& eventId); |
107 | } |
108 | |
109 | } // namespace Quotient |
110 | |