diff options
author | Kitsune Ral <Kitsune-Ral@users.sf.net> | 2018-08-25 22:40:15 +0900 |
---|---|---|
committer | Kitsune Ral <Kitsune-Ral@users.sf.net> | 2018-08-25 22:40:15 +0900 |
commit | d9ff200ff62fb7f5b6b51082dc3979d5454a1bec (patch) | |
tree | 16f33987a6e98646b462d22ca9f69884a9e01ee6 | |
parent | e507ca582b1b243ee4422a4a3e0b11b28697cb16 (diff) | |
download | libquotient-d9ff200ff62fb7f5b6b51082dc3979d5454a1bec.tar.gz libquotient-d9ff200ff62fb7f5b6b51082dc3979d5454a1bec.zip |
Update to the recent CS API (watch out for breakage)
Breaking changes:
* guest_can_join is no more a thing - neither in Connection::createRoom, nor even in CreateRoomJob (it turned out that Synapse didn't really process this flag);
* LoginJob has changed its list of arguments. If you use Connection to do logins (and you really should), you shouldn't be affected.
* GetPublicRoomsJob now returns PublicRoomsResponse instead of providing all the response parts within the job
Watch other changes in the diff.
25 files changed, 627 insertions, 240 deletions
diff --git a/lib/connection.cpp b/lib/connection.cpp index 017180c4..8d55460d 100644 --- a/lib/connection.cpp +++ b/lib/connection.cpp @@ -217,8 +217,9 @@ void Connection::doConnectToServer(const QString& user, const QString& password, const QString& deviceId) { auto loginJob = callApi<LoginJob>(QStringLiteral("m.login.password"), - user, /*medium*/ "", /*address*/ "", password, /*token*/ "", - deviceId, initialDeviceName); + UserIdentifier { QStringLiteral("m.id.user"), + {{ QStringLiteral("user"), user }} }, + password, /*token*/ "", deviceId, initialDeviceName); connect(loginJob, &BaseJob::success, this, [this, loginJob] { d->connectWithToken(loginJob->userId(), loginJob->accessToken(), @@ -505,19 +506,17 @@ DownloadFileJob* Connection::downloadFile(const QUrl& url, CreateRoomJob* Connection::createRoom(RoomVisibility visibility, const QString& alias, const QString& name, const QString& topic, - const QStringList& invites, const QString& presetName, - bool isDirect, bool guestsCanJoin, + QStringList invites, const QString& presetName, bool isDirect, const QVector<CreateRoomJob::StateEvent>& initialState, const QVector<CreateRoomJob::Invite3pid>& invite3pids, const QJsonObject& creationContent) { - // FIXME: switch to using QStringList instead of const QStringList& in 0.4 - auto filteredInvites = invites; - filteredInvites.removeOne(d->userId); // The creator is by definition in the room + invites.removeOne(d->userId); // The creator is by definition in the room auto job = callApi<CreateRoomJob>( - visibility == PublishRoom ? "public" : "private", alias, name, - topic, filteredInvites, invite3pids, creationContent, initialState, - presetName, isDirect, guestsCanJoin); + visibility == PublishRoom ? QStringLiteral("public") + : QStringLiteral("private"), + alias, name, topic, invites, invite3pids, QString(/*TODO: #233*/), + creationContent, initialState, presetName, isDirect); connect(job, &BaseJob::success, this, [this,job] { emit createdRoom(provideRoom(job->roomId(), JoinState::Join)); }); diff --git a/lib/connection.h b/lib/connection.h index 9b253711..ea7c62c0 100644 --- a/lib/connection.h +++ b/lib/connection.h @@ -375,8 +375,8 @@ namespace QMatrixClient */ CreateRoomJob* createRoom(RoomVisibility visibility, const QString& alias, const QString& name, const QString& topic, - const QStringList& invites, const QString& presetName = {}, - bool isDirect = false, bool guestsCanJoin = false, + QStringList invites, const QString& presetName = {}, + bool isDirect = false, const QVector<CreateRoomJob::StateEvent>& initialState = {}, const QVector<CreateRoomJob::Invite3pid>& invite3pids = {}, const QJsonObject& creationContent = {}); diff --git a/lib/csapi/administrative_contact.cpp b/lib/csapi/administrative_contact.cpp index 682a6f05..bcbba5b5 100644 --- a/lib/csapi/administrative_contact.cpp +++ b/lib/csapi/administrative_contact.cpp @@ -93,17 +93,31 @@ Post3PIDsJob::Post3PIDsJob(const ThreePidCredentials& threePidCreds, bool bind) setRequestData(_data); } -QUrl RequestTokenTo3PIDJob::makeRequestUrl(QUrl baseUrl) +QUrl RequestTokenTo3PIDEmailJob::makeRequestUrl(QUrl baseUrl) { return BaseJob::makeRequestUrl(std::move(baseUrl), basePath % "/account/3pid/email/requestToken"); } -static const auto RequestTokenTo3PIDJobName = QStringLiteral("RequestTokenTo3PIDJob"); +static const auto RequestTokenTo3PIDEmailJobName = QStringLiteral("RequestTokenTo3PIDEmailJob"); -RequestTokenTo3PIDJob::RequestTokenTo3PIDJob() - : BaseJob(HttpVerb::Post, RequestTokenTo3PIDJobName, +RequestTokenTo3PIDEmailJob::RequestTokenTo3PIDEmailJob() + : BaseJob(HttpVerb::Post, RequestTokenTo3PIDEmailJobName, basePath % "/account/3pid/email/requestToken", false) { } +QUrl RequestTokenTo3PIDMSISDNJob::makeRequestUrl(QUrl baseUrl) +{ + return BaseJob::makeRequestUrl(std::move(baseUrl), + basePath % "/account/3pid/msisdn/requestToken"); +} + +static const auto RequestTokenTo3PIDMSISDNJobName = QStringLiteral("RequestTokenTo3PIDMSISDNJob"); + +RequestTokenTo3PIDMSISDNJob::RequestTokenTo3PIDMSISDNJob() + : BaseJob(HttpVerb::Post, RequestTokenTo3PIDMSISDNJobName, + basePath % "/account/3pid/msisdn/requestToken", false) +{ +} + diff --git a/lib/csapi/administrative_contact.h b/lib/csapi/administrative_contact.h index decf7e3c..112b81cc 100644 --- a/lib/csapi/administrative_contact.h +++ b/lib/csapi/administrative_contact.h @@ -118,15 +118,38 @@ namespace QMatrixClient /// validation tokens when adding an email address to an account. This API's /// parameters and response is identical to that of the HS API /// |/register/email/requestToken|_ endpoint. - class RequestTokenTo3PIDJob : public BaseJob + class RequestTokenTo3PIDEmailJob : public BaseJob { public: - explicit RequestTokenTo3PIDJob(); + explicit RequestTokenTo3PIDEmailJob(); /*! Construct a URL without creating a full-fledged job object * * This function can be used when a URL for - * RequestTokenTo3PIDJob is necessary but the job + * RequestTokenTo3PIDEmailJob is necessary but the job + * itself isn't. + */ + static QUrl makeRequestUrl(QUrl baseUrl); + + }; + + /// Requests a validation token be sent to the given email address for the purpose of adding a phone number to an account. + /// + /// Proxies the identity server API ``validate/msisdn/requestToken``, but + /// first checks that the given phone number is **not** already associated + /// with an account on this Home Server. This API should be used to request + /// validation tokens when adding a phone number to an account. This API's + /// parameters and response is identical to that of the HS API + /// |/register/msisdn/requestToken|_ endpoint. + class RequestTokenTo3PIDMSISDNJob : public BaseJob + { + public: + explicit RequestTokenTo3PIDMSISDNJob(); + + /*! Construct a URL without creating a full-fledged job object + * + * This function can be used when a URL for + * RequestTokenTo3PIDMSISDNJob is necessary but the job * itself isn't. */ static QUrl makeRequestUrl(QUrl baseUrl); diff --git a/lib/csapi/create_room.cpp b/lib/csapi/create_room.cpp index 534f8fdd..068b567f 100644 --- a/lib/csapi/create_room.cpp +++ b/lib/csapi/create_room.cpp @@ -43,7 +43,7 @@ class CreateRoomJob::Private static const auto CreateRoomJobName = QStringLiteral("CreateRoomJob"); -CreateRoomJob::CreateRoomJob(const QString& visibility, const QString& roomAliasName, const QString& name, const QString& topic, const QStringList& invite, const QVector<Invite3pid>& invite3pid, const QJsonObject& creationContent, const QVector<StateEvent>& initialState, const QString& preset, bool isDirect, bool guestCanJoin) +CreateRoomJob::CreateRoomJob(const QString& visibility, const QString& roomAliasName, const QString& name, const QString& topic, const QStringList& invite, const QVector<Invite3pid>& invite3pid, const QString& roomVersion, const QJsonObject& creationContent, const QVector<StateEvent>& initialState, const QString& preset, bool isDirect, const QJsonObject& powerLevelContentOverride) : BaseJob(HttpVerb::Post, CreateRoomJobName, basePath % "/createRoom") , d(new Private) @@ -55,11 +55,12 @@ CreateRoomJob::CreateRoomJob(const QString& visibility, const QString& roomAlias addParam<IfNotEmpty>(_data, QStringLiteral("topic"), topic); addParam<IfNotEmpty>(_data, QStringLiteral("invite"), invite); addParam<IfNotEmpty>(_data, QStringLiteral("invite_3pid"), invite3pid); + addParam<IfNotEmpty>(_data, QStringLiteral("room_version"), roomVersion); addParam<IfNotEmpty>(_data, QStringLiteral("creation_content"), creationContent); addParam<IfNotEmpty>(_data, QStringLiteral("initial_state"), initialState); addParam<IfNotEmpty>(_data, QStringLiteral("preset"), preset); addParam<IfNotEmpty>(_data, QStringLiteral("is_direct"), isDirect); - addParam<IfNotEmpty>(_data, QStringLiteral("guest_can_join"), guestCanJoin); + addParam<IfNotEmpty>(_data, QStringLiteral("power_level_content_override"), powerLevelContentOverride); setRequestData(_data); } @@ -73,6 +74,9 @@ const QString& CreateRoomJob::roomId() const BaseJob::Status CreateRoomJob::parseJson(const QJsonDocument& data) { auto json = data.object(); + if (!json.contains("room_id"_ls)) + return { JsonParseError, + "The key 'room_id' not found in the response" }; d->roomId = fromJson<QString>(json.value("room_id"_ls)); return Success; } diff --git a/lib/csapi/create_room.h b/lib/csapi/create_room.h index 79ea2385..60579a83 100644 --- a/lib/csapi/create_room.h +++ b/lib/csapi/create_room.h @@ -23,16 +23,20 @@ namespace QMatrixClient /// apply the events implied by the request in the following order: /// /// 0. A default ``m.room.power_levels`` event, giving the room creator - /// (and not other members) permission to send state events. + /// (and not other members) permission to send state events. Overridden + /// by the ``power_level_content_override`` parameter. /// - /// 1. Events set by the ``preset``. + /// 1. Events set by the ``preset``. Currently these are the ``m.room.join_rules``, + /// ``m.room.history_visibility``, and ``m.room.guest_access`` state events. /// /// 2. Events listed in ``initial_state``, in the order that they are /// listed. /// - /// 3. Events implied by ``name`` and ``topic``. + /// 3. Events implied by ``name`` and ``topic`` (``m.room.name`` and ``m.room.topic`` + /// state events). /// - /// 4. Invite events implied by ``invite`` and ``invite_3pid``. + /// 4. Invite events implied by ``invite`` and ``invite_3pid`` (``m.room.member`` with + /// ``membership: invite`` and ``m.room.third_party_invite``). /// /// The available presets do the following with respect to room state: /// @@ -43,6 +47,10 @@ namespace QMatrixClient /// ``trusted_private_chat`` ``invite`` ``shared`` ``can_join`` All invitees are given the same power level as the room creator. /// ``public_chat`` ``public`` ``shared`` ``forbidden`` /// ======================== ============== ====================== ================ ========= + /// + /// The server will create a ``m.room.create`` event in the room with the + /// requesting user as the creator, alongside other keys provided in the + /// ``creation_content``. class CreateRoomJob : public BaseJob { public: @@ -55,16 +63,20 @@ namespace QMatrixClient /// apply the events implied by the request in the following order: /// /// 0. A default ``m.room.power_levels`` event, giving the room creator - /// (and not other members) permission to send state events. + /// (and not other members) permission to send state events. Overridden + /// by the ``power_level_content_override`` parameter. /// - /// 1. Events set by the ``preset``. + /// 1. Events set by the ``preset``. Currently these are the ``m.room.join_rules``, + /// ``m.room.history_visibility``, and ``m.room.guest_access`` state events. /// /// 2. Events listed in ``initial_state``, in the order that they are /// listed. /// - /// 3. Events implied by ``name`` and ``topic``. + /// 3. Events implied by ``name`` and ``topic`` (``m.room.name`` and ``m.room.topic`` + /// state events). /// - /// 4. Invite events implied by ``invite`` and ``invite_3pid``. + /// 4. Invite events implied by ``invite`` and ``invite_3pid`` (``m.room.member`` with + /// ``membership: invite`` and ``m.room.third_party_invite``). /// /// The available presets do the following with respect to room state: /// @@ -75,6 +87,10 @@ namespace QMatrixClient /// ``trusted_private_chat`` ``invite`` ``shared`` ``can_join`` All invitees are given the same power level as the room creator. /// ``public_chat`` ``public`` ``shared`` ``forbidden`` /// ======================== ============== ====================== ================ ========= + /// + /// The server will create a ``m.room.create`` event in the room with the + /// requesting user as the creator, alongside other keys provided in the + /// ``creation_content``. struct Invite3pid { /// The hostname+port of the identity server which should be used for third party identifier lookups. @@ -92,16 +108,20 @@ namespace QMatrixClient /// apply the events implied by the request in the following order: /// /// 0. A default ``m.room.power_levels`` event, giving the room creator - /// (and not other members) permission to send state events. + /// (and not other members) permission to send state events. Overridden + /// by the ``power_level_content_override`` parameter. /// - /// 1. Events set by the ``preset``. + /// 1. Events set by the ``preset``. Currently these are the ``m.room.join_rules``, + /// ``m.room.history_visibility``, and ``m.room.guest_access`` state events. /// /// 2. Events listed in ``initial_state``, in the order that they are /// listed. /// - /// 3. Events implied by ``name`` and ``topic``. + /// 3. Events implied by ``name`` and ``topic`` (``m.room.name`` and ``m.room.topic`` + /// state events). /// - /// 4. Invite events implied by ``invite`` and ``invite_3pid``. + /// 4. Invite events implied by ``invite`` and ``invite_3pid`` (``m.room.member`` with + /// ``membership: invite`` and ``m.room.third_party_invite``). /// /// The available presets do the following with respect to room state: /// @@ -112,6 +132,10 @@ namespace QMatrixClient /// ``trusted_private_chat`` ``invite`` ``shared`` ``can_join`` All invitees are given the same power level as the room creator. /// ``public_chat`` ``public`` ``shared`` ``forbidden`` /// ======================== ============== ====================== ================ ========= + /// + /// The server will create a ``m.room.create`` event in the room with the + /// requesting user as the creator, alongside other keys provided in the + /// ``creation_content``. struct StateEvent { /// The type of event to send. @@ -139,6 +163,9 @@ namespace QMatrixClient * created the room. For example, if this was set to "foo" and * sent to the homeserver "example.com" the complete room alias * would be ``#foo:example.com``. + * + * The complete room alias will become the canonical alias for + * the room. * \param name * If this is included, an ``m.room.name`` event will be sent * into the room to indicate the name of the room. See Room @@ -153,11 +180,16 @@ namespace QMatrixClient * \param invite3pid * A list of objects representing third party IDs to invite into * the room. + * \param roomVersion + * The room version to set for the room. If not provided, the homeserver is + * to use its configured default. If provided, the homeserver will return a + * 400 error with the errcode ``M_UNSUPPORTED_ROOM_VERSION`` if it does not + * support the room version. * \param creationContent - * Extra keys to be added to the content of the ``m.room.create``. - * The server will clobber the following keys: ``creator``. Future - * versions of the specification may allow the server to clobber - * other keys. + * Extra keys, such as ``m.federate``, to be added to the content + * of the `m.room.create`_ event. The server will clobber the following + * keys: ``creator``, ``room_version``. Future versions of the specification + * may allow the server to clobber other keys. * \param initialState * A list of state events to set in the new room. This allows * the user to override the default state events set in the new @@ -169,14 +201,22 @@ namespace QMatrixClient * \param preset * Convenience parameter for setting various default state events * based on a preset. + * + * If unspecified, the server should use the ``visibility`` to determine + * which preset to use. A visbility of ``public`` equates to a preset of + * ``public_chat`` and ``private`` visibility equates to a preset of + * ``private_chat``. * \param isDirect * This flag makes the server set the ``is_direct`` flag on the * ``m.room.member`` events sent to the users in ``invite`` and * ``invite_3pid``. See `Direct Messaging`_ for more information. - * \param guestCanJoin - * Allows guests to join the room. See `Guest Access`_ for more information. + * \param powerLevelContentOverride + * The power level content to override in the default power level + * event. This object is applied on top of the generated `m.room.power_levels`_ + * event content prior to it being sent to the room. Defaults to + * overriding nothing. */ - explicit CreateRoomJob(const QString& visibility = {}, const QString& roomAliasName = {}, const QString& name = {}, const QString& topic = {}, const QStringList& invite = {}, const QVector<Invite3pid>& invite3pid = {}, const QJsonObject& creationContent = {}, const QVector<StateEvent>& initialState = {}, const QString& preset = {}, bool isDirect = false, bool guestCanJoin = false); + explicit CreateRoomJob(const QString& visibility = {}, const QString& roomAliasName = {}, const QString& name = {}, const QString& topic = {}, const QStringList& invite = {}, const QVector<Invite3pid>& invite3pid = {}, const QString& roomVersion = {}, const QJsonObject& creationContent = {}, const QVector<StateEvent>& initialState = {}, const QString& preset = {}, bool isDirect = false, const QJsonObject& powerLevelContentOverride = {}); ~CreateRoomJob() override; // Result properties diff --git a/lib/csapi/definitions/auth_data.h b/lib/csapi/definitions/auth_data.h index 0ad72b87..dce55396 100644 --- a/lib/csapi/definitions/auth_data.h +++ b/lib/csapi/definitions/auth_data.h @@ -6,6 +6,8 @@ #include "converters.h" +#include <QtCore/QJsonObject> +#include <QtCore/QHash> namespace QMatrixClient { diff --git a/lib/csapi/definitions/public_rooms_response.cpp b/lib/csapi/definitions/public_rooms_response.cpp new file mode 100644 index 00000000..7cdf16af --- /dev/null +++ b/lib/csapi/definitions/public_rooms_response.cpp @@ -0,0 +1,75 @@ +/****************************************************************************** + * THIS FILE IS GENERATED - ANY EDITS WILL BE OVERWRITTEN + */ + +#include "public_rooms_response.h" + +using namespace QMatrixClient; + +QJsonObject QMatrixClient::toJson(const PublicRoomsChunk& pod) +{ + QJsonObject _json; + addParam<IfNotEmpty>(_json, QStringLiteral("aliases"), pod.aliases); + addParam<IfNotEmpty>(_json, QStringLiteral("canonical_alias"), pod.canonicalAlias); + addParam<IfNotEmpty>(_json, QStringLiteral("name"), pod.name); + addParam<>(_json, QStringLiteral("num_joined_members"), pod.numJoinedMembers); + addParam<>(_json, QStringLiteral("room_id"), pod.roomId); + addParam<IfNotEmpty>(_json, QStringLiteral("topic"), pod.topic); + addParam<>(_json, QStringLiteral("world_readable"), pod.worldReadable); + addParam<>(_json, QStringLiteral("guest_can_join"), pod.guestCanJoin); + addParam<IfNotEmpty>(_json, QStringLiteral("avatar_url"), pod.avatarUrl); + return _json; +} + +PublicRoomsChunk FromJson<PublicRoomsChunk>::operator()(const QJsonValue& jv) +{ + const auto& _json = jv.toObject(); + PublicRoomsChunk result; + result.aliases = + fromJson<QStringList>(_json.value("aliases"_ls)); + result.canonicalAlias = + fromJson<QString>(_json.value("canonical_alias"_ls)); + result.name = + fromJson<QString>(_json.value("name"_ls)); + result.numJoinedMembers = + fromJson<qint64>(_json.value("num_joined_members"_ls)); + result.roomId = + fromJson<QString>(_json.value("room_id"_ls)); + result.topic = + fromJson<QString>(_json.value("topic"_ls)); + result.worldReadable = + fromJson<bool>(_json.value("world_readable"_ls)); + result.guestCanJoin = + fromJson<bool>(_json.value("guest_can_join"_ls)); + result.avatarUrl = + fromJson<QString>(_json.value("avatar_url"_ls)); + + return result; +} + +QJsonObject QMatrixClient::toJson(const PublicRoomsResponse& pod) +{ + QJsonObject _json; + addParam<>(_json, QStringLiteral("chunk"), pod.chunk); + addParam<IfNotEmpty>(_json, QStringLiteral("next_batch"), pod.nextBatch); + addParam<IfNotEmpty>(_json, QStringLiteral("prev_batch"), pod.prevBatch); + addParam<IfNotEmpty>(_json, QStringLiteral("total_room_count_estimate"), pod.totalRoomCountEstimate); + return _json; +} + +PublicRoomsResponse FromJson<PublicRoomsResponse>::operator()(const QJsonValue& jv) +{ + const auto& _json = jv.toObject(); + PublicRoomsResponse result; + result.chunk = + fromJson<QVector<PublicRoomsChunk>>(_json.value("chunk"_ls)); + result.nextBatch = + fromJson<QString>(_json.value("next_batch"_ls)); + result.prevBatch = + fromJson<QString>(_json.value("prev_batch"_ls)); + result.totalRoomCountEstimate = + fromJson<qint64>(_json.value("total_room_count_estimate"_ls)); + + return result; +} + diff --git a/lib/csapi/definitions/public_rooms_response.h b/lib/csapi/definitions/public_rooms_response.h new file mode 100644 index 00000000..eea4bc5e --- /dev/null +++ b/lib/csapi/definitions/public_rooms_response.h @@ -0,0 +1,72 @@ +/****************************************************************************** + * THIS FILE IS GENERATED - ANY EDITS WILL BE OVERWRITTEN + */ + +#pragma once + +#include "converters.h" + +#include <QtCore/QVector> +#include "converters.h" + +namespace QMatrixClient +{ + // Data structures + + struct PublicRoomsChunk + { + /// Aliases of the room. May be empty. + QStringList aliases; + /// The canonical alias of the room, if any. + QString canonicalAlias; + /// The name of the room, if any. + QString name; + /// The number of members joined to the room. + qint64 numJoinedMembers; + /// The ID of the room. + QString roomId; + /// The topic of the room, if any. + QString topic; + /// Whether the room may be viewed by guest users without joining. + bool worldReadable; + /// Whether guest users may join the room and participate in it. + /// If they can, they will be subject to ordinary power level + /// rules like any other user. + bool guestCanJoin; + /// The URL for the room's avatar, if one is set. + QString avatarUrl; + }; + + QJsonObject toJson(const PublicRoomsChunk& pod); + + template <> struct FromJson<PublicRoomsChunk> + { + PublicRoomsChunk operator()(const QJsonValue& jv); + }; + + /// A list of the rooms on the server. + struct PublicRoomsResponse + { + /// A paginated chunk of public rooms. + QVector<PublicRoomsChunk> chunk; + /// A pagination token for the response. The absence of this token + /// means there are no more results to fetch and the client should + /// stop paginating. + QString nextBatch; + /// A pagination token that allows fetching previous results. The + /// absence of this token means there are no results before this + /// batch, i.e. this is the first batch. + QString prevBatch; + /// An estimate on the total number of public rooms, if the + /// server has an estimate. + Omittable<qint64> totalRoomCountEstimate; + }; + + QJsonObject toJson(const PublicRoomsResponse& pod); + + template <> struct FromJson<PublicRoomsResponse> + { + PublicRoomsResponse operator()(const QJsonValue& jv); + }; + +} // namespace QMatrixClient diff --git a/lib/csapi/definitions/push_rule.cpp b/lib/csapi/definitions/push_rule.cpp index 1ee57945..833135ec 100644 --- a/lib/csapi/definitions/push_rule.cpp +++ b/lib/csapi/definitions/push_rule.cpp @@ -6,24 +6,6 @@ using namespace QMatrixClient; -QJsonObject QMatrixClient::toJson(const SetTweakAction& pod) -{ - QJsonObject _json = toJson(pod.additionalProperties); - addParam<>(_json, QStringLiteral("set_tweak"), pod.setTweak); - return _json; -} - -SetTweakAction FromJson<SetTweakAction>::operator()(const QJsonValue& jv) -{ - auto _json = jv.toObject(); - SetTweakAction result; - result.setTweak = - fromJson<QString>(_json.take("set_tweak"_ls)); - - result.additionalProperties = fromJson<QVariantHash>(_json); - return result; -} - QJsonObject QMatrixClient::toJson(const PushRule& pod) { QJsonObject _json; diff --git a/lib/csapi/definitions/push_rule.h b/lib/csapi/definitions/push_rule.h index 6959e9d1..c6542aa6 100644 --- a/lib/csapi/definitions/push_rule.h +++ b/lib/csapi/definitions/push_rule.h @@ -7,38 +7,15 @@ #include "converters.h" #include "csapi/definitions/push_condition.h" +#include "converters.h" #include <QtCore/QVector> #include <QtCore/QVariant> -#include "converters.h" +#include <QtCore/QJsonObject> namespace QMatrixClient { // Data structures - /// Specifies an entry to the 'tweaks' dictionary sent in - /// the notification request to the Push Gateway. - /// Tweak parameters, if any, are provided as additional - /// key-value pairs in this structure. - struct SetTweakAction - { - /// The tweak type. Two predefined types are `sound` - /// and `highlight`; client applications and Push Gateways - /// may agree on additional tweak types. - QString setTweak; - /// Specifies an entry to the 'tweaks' dictionary sent in - /// the notification request to the Push Gateway. - /// Tweak parameters, if any, are provided as additional - /// key-value pairs in this structure. - QVariantHash additionalProperties; - }; - - QJsonObject toJson(const SetTweakAction& pod); - - template <> struct FromJson<SetTweakAction> - { - SetTweakAction operator()(const QJsonValue& jv); - }; - struct PushRule { /// The actions to perform when this rule is matched. diff --git a/lib/csapi/definitions/user_identifier.cpp b/lib/csapi/definitions/user_identifier.cpp new file mode 100644 index 00000000..3d3acaba --- /dev/null +++ b/lib/csapi/definitions/user_identifier.cpp @@ -0,0 +1,26 @@ +/****************************************************************************** + * THIS FILE IS GENERATED - ANY EDITS WILL BE OVERWRITTEN + */ + +#include "user_identifier.h" + +using namespace QMatrixClient; + +QJsonObject QMatrixClient::toJson(const UserIdentifier& pod) +{ + QJsonObject _json = toJson(pod.additionalProperties); + addParam<>(_json, QStringLiteral("type"), pod.type); + return _json; +} + +UserIdentifier FromJson<UserIdentifier>::operator()(const QJsonValue& jv) +{ + auto _json = jv.toObject(); + UserIdentifier result; + result.type = + fromJson<QString>(_json.take("type"_ls)); + + result.additionalProperties = fromJson<QVariantHash>(_json); + return result; +} + diff --git a/lib/csapi/definitions/user_identifier.h b/lib/csapi/definitions/user_identifier.h new file mode 100644 index 00000000..edc254d3 --- /dev/null +++ b/lib/csapi/definitions/user_identifier.h @@ -0,0 +1,31 @@ +/****************************************************************************** + * THIS FILE IS GENERATED - ANY EDITS WILL BE OVERWRITTEN + */ + +#pragma once + +#include "converters.h" + +#include <QtCore/QVariant> + +namespace QMatrixClient +{ + // Data structures + + /// Identification information for a user + struct UserIdentifier + { + /// The type of identification. See `Identifier types`_ for supported values and additional property descriptions. + QString type; + /// Identification information for a user + QVariantHash additionalProperties; + }; + + QJsonObject toJson(const UserIdentifier& pod); + + template <> struct FromJson<UserIdentifier> + { + UserIdentifier operator()(const QJsonValue& jv); + }; + +} // namespace QMatrixClient diff --git a/lib/csapi/list_public_rooms.cpp b/lib/csapi/list_public_rooms.cpp index c34af34c..1a5b9203 100644 --- a/lib/csapi/list_public_rooms.cpp +++ b/lib/csapi/list_public_rooms.cpp @@ -58,47 +58,10 @@ SetRoomVisibilityOnDirectoryJob::SetRoomVisibilityOnDirectoryJob(const QString& setRequestData(_data); } -namespace QMatrixClient -{ - // Converters - - template <> struct FromJson<GetPublicRoomsJob::PublicRoomsChunk> - { - GetPublicRoomsJob::PublicRoomsChunk operator()(const QJsonValue& jv) - { - const auto& _json = jv.toObject(); - GetPublicRoomsJob::PublicRoomsChunk result; - result.aliases = - fromJson<QStringList>(_json.value("aliases"_ls)); - result.canonicalAlias = - fromJson<QString>(_json.value("canonical_alias"_ls)); - result.name = - fromJson<QString>(_json.value("name"_ls)); - result.numJoinedMembers = - fromJson<qint64>(_json.value("num_joined_members"_ls)); - result.roomId = - fromJson<QString>(_json.value("room_id"_ls)); - result.topic = - fromJson<QString>(_json.value("topic"_ls)); - result.worldReadable = - fromJson<bool>(_json.value("world_readable"_ls)); - result.guestCanJoin = - fromJson<bool>(_json.value("guest_can_join"_ls)); - result.avatarUrl = - fromJson<QString>(_json.value("avatar_url"_ls)); - - return result; - } - }; -} // namespace QMatrixClient - class GetPublicRoomsJob::Private { public: - QVector<PublicRoomsChunk> chunk; - QString nextBatch; - QString prevBatch; - Omittable<qint64> totalRoomCountEstimate; + PublicRoomsResponse data; }; BaseJob::Query queryToGetPublicRooms(Omittable<int> limit, const QString& since, const QString& server) @@ -130,36 +93,18 @@ GetPublicRoomsJob::GetPublicRoomsJob(Omittable<int> limit, const QString& since, GetPublicRoomsJob::~GetPublicRoomsJob() = default; -const QVector<GetPublicRoomsJob::PublicRoomsChunk>& GetPublicRoomsJob::chunk() const +const PublicRoomsResponse& GetPublicRoomsJob::data() const { - return d->chunk; -} - -const QString& GetPublicRoomsJob::nextBatch() const -{ - return d->nextBatch; -} - -const QString& GetPublicRoomsJob::prevBatch() const -{ - return d->prevBatch; -} - -Omittable<qint64> GetPublicRoomsJob::totalRoomCountEstimate() const -{ - return d->totalRoomCountEstimate; + return d->data; } BaseJob::Status GetPublicRoomsJob::parseJson(const QJsonDocument& data) { auto json = data.object(); - if (!json.contains("chunk"_ls)) + if (!json.contains("data"_ls)) return { JsonParseError, - "The key 'chunk' not found in the response" }; - d->chunk = fromJson<QVector<PublicRoomsChunk>>(json.value("chunk"_ls)); - d->nextBatch = fromJson<QString>(json.value("next_batch"_ls)); - d->prevBatch = fromJson<QString>(json.value("prev_batch"_ls)); - d->totalRoomCountEstimate = fromJson<qint64>(json.value("total_room_count_estimate"_ls)); + "The key 'data' not found in the response" }; + d->data = fromJson<PublicRoomsResponse>(json.value("data"_ls)); return Success; } diff --git a/lib/csapi/list_public_rooms.h b/lib/csapi/list_public_rooms.h index e955f8e5..b2697c8c 100644 --- a/lib/csapi/list_public_rooms.h +++ b/lib/csapi/list_public_rooms.h @@ -7,6 +7,7 @@ #include "jobs/basejob.h" #include <QtCore/QVector> +#include "csapi/definitions/public_rooms_response.h" #include "converters.h" namespace QMatrixClient @@ -78,38 +79,6 @@ namespace QMatrixClient class GetPublicRoomsJob : public BaseJob { public: - // Inner data structures - - /// Lists the public rooms on the server. - /// - /// This API returns paginated responses. The rooms are ordered by the number - /// of joined members, with the largest rooms first. - struct PublicRoomsChunk - { - /// Aliases of the room. May be empty. - QStringList aliases; - /// The canonical alias of the room, if any. - QString canonicalAlias; - /// The name of the room, if any. - QString name; - /// The number of members joined to the room. - qint64 numJoinedMembers; - /// The ID of the room. - QString roomId; - /// The topic of the room, if any. - QString topic; - /// Whether the room may be viewed by guest users without joining. - bool worldReadable; - /// Whether guest users may join the room and participate in it. - /// If they can, they will be subject to ordinary power level - /// rules like any other user. - bool guestCanJoin; - /// The URL for the room's avatar, if one is set. - QString avatarUrl; - }; - - // Construction/destruction - /*! Lists the public rooms on the server. * \param limit * Limit the number of results returned. @@ -136,19 +105,8 @@ namespace QMatrixClient // Result properties - /// A paginated chunk of public rooms. - const QVector<PublicRoomsChunk>& chunk() const; - /// A pagination token for the response. The absence of this token - /// means there are no more results to fetch and the client should - /// stop paginating. - const QString& nextBatch() const; - /// A pagination token that allows fetching previous results. The - /// absence of this token means there are no results before this - /// batch, i.e. this is the first batch. - const QString& prevBatch() const; - /// An estimate on the total number of public rooms, if the - /// server has an estimate. - Omittable<qint64> totalRoomCountEstimate() const; + /// A list of the rooms on the server. + const PublicRoomsResponse& data() const; protected: Status parseJson(const QJsonDocument& data) override; diff --git a/lib/csapi/login.cpp b/lib/csapi/login.cpp index 3956a1c4..363b6037 100644 --- a/lib/csapi/login.cpp +++ b/lib/csapi/login.cpp @@ -76,20 +76,21 @@ class LoginJob::Private static const auto LoginJobName = QStringLiteral("LoginJob"); -LoginJob::LoginJob(const QString& type, const QString& user, const QString& medium, const QString& address, const QString& password, const QString& token, const QString& deviceId, const QString& initialDeviceDisplayName) +LoginJob::LoginJob(const QString& type, const Omittable<UserIdentifier>& identifier, const QString& password, const QString& token, const QString& deviceId, const QString& initialDeviceDisplayName, const QString& user, const QString& medium, const QString& address) : BaseJob(HttpVerb::Post, LoginJobName, basePath % "/login", false) , d(new Private) { QJsonObject _data; addParam<>(_data, QStringLiteral("type"), type); - addParam<IfNotEmpty>(_data, QStringLiteral("user"), user); - addParam<IfNotEmpty>(_data, QStringLiteral("medium"), medium); - addParam<IfNotEmpty>(_data, QStringLiteral("address"), address); + addParam<IfNotEmpty>(_data, QStringLiteral("identifier"), identifier); addParam<IfNotEmpty>(_data, QStringLiteral("password"), password); addParam<IfNotEmpty>(_data, QStringLiteral("token"), token); addParam<IfNotEmpty>(_data, QStringLiteral("device_id"), deviceId); addParam<IfNotEmpty>(_data, QStringLiteral("initial_device_display_name"), initialDeviceDisplayName); + addParam<IfNotEmpty>(_data, QStringLiteral("user"), user); + addParam<IfNotEmpty>(_data, QStringLiteral("medium"), medium); + addParam<IfNotEmpty>(_data, QStringLiteral("address"), address); setRequestData(_data); } diff --git a/lib/csapi/login.h b/lib/csapi/login.h index 57113813..6b35cb85 100644 --- a/lib/csapi/login.h +++ b/lib/csapi/login.h @@ -6,8 +6,9 @@ #include "jobs/basejob.h" -#include "converters.h" #include <QtCore/QVector> +#include "csapi/definitions/user_identifier.h" +#include "converters.h" namespace QMatrixClient { @@ -76,12 +77,8 @@ namespace QMatrixClient /*! Authenticates the user. * \param type * The login type being used. - * \param user - * The fully qualified user ID or just local part of the user ID, to log in. - * \param medium - * When logging in using a third party identifier, the medium of the identifier. Must be 'email'. - * \param address - * Third party identifier for the user. + * \param identifier + * Identification information for the user. * \param password * Required when ``type`` is ``m.login.password``. The user's * password. @@ -94,8 +91,14 @@ namespace QMatrixClient * \param initialDeviceDisplayName * A display name to assign to the newly-created device. Ignored * if ``device_id`` corresponds to a known device. + * \param user + * The fully qualified user ID or just local part of the user ID, to log in. Deprecated in favour of ``identifier``. + * \param medium + * When logging in using a third party identifier, the medium of the identifier. Must be 'email'. Deprecated in favour of ``identifier``. + * \param address + * Third party identifier for the user. Deprecated in favour of ``identifier``. */ - explicit LoginJob(const QString& type, const QString& user = {}, const QString& medium = {}, const QString& address = {}, const QString& password = {}, const QString& token = {}, const QString& deviceId = {}, const QString& initialDeviceDisplayName = {}); + explicit LoginJob(const QString& type, const Omittable<UserIdentifier>& identifier = none, const QString& password = {}, const QString& token = {}, const QString& deviceId = {}, const QString& initialDeviceDisplayName = {}, const QString& user = {}, const QString& medium = {}, const QString& address = {}); ~LoginJob() override; // Result properties diff --git a/lib/csapi/openid.cpp b/lib/csapi/openid.cpp new file mode 100644 index 00000000..2547f0c8 --- /dev/null +++ b/lib/csapi/openid.cpp @@ -0,0 +1,77 @@ +/****************************************************************************** + * THIS FILE IS GENERATED - ANY EDITS WILL BE OVERWRITTEN + */ + +#include "openid.h" + +#include "converters.h" + +#include <QtCore/QStringBuilder> + +using namespace QMatrixClient; + +static const auto basePath = QStringLiteral("/_matrix/client/r0"); + +class RequestOpenIdTokenJob::Private +{ + public: + QString accessToken; + QString tokenType; + QString matrixServerName; + int expiresIn; +}; + +static const auto RequestOpenIdTokenJobName = QStringLiteral("RequestOpenIdTokenJob"); + +RequestOpenIdTokenJob::RequestOpenIdTokenJob(const QString& userId, const QJsonObject& body) + : BaseJob(HttpVerb::Post, RequestOpenIdTokenJobName, + basePath % "/user/" % userId % "/openid/request_token") + , d(new Private) +{ + setRequestData(Data(toJson(body))); +} + +RequestOpenIdTokenJob::~RequestOpenIdTokenJob() = default; + +const QString& RequestOpenIdTokenJob::accessToken() const +{ + return d->accessToken; +} + +const QString& RequestOpenIdTokenJob::tokenType() const +{ + return d->tokenType; +} + +const QString& RequestOpenIdTokenJob::matrixServerName() const +{ + return d->matrixServerName; +} + +int RequestOpenIdTokenJob::expiresIn() const +{ + return d->expiresIn; +} + +BaseJob::Status RequestOpenIdTokenJob::parseJson(const QJsonDocument& data) +{ + auto json = data.object(); + if (!json.contains("access_token"_ls)) + return { JsonParseError, + "The key 'access_token' not found in the response" }; + d->accessToken = fromJson<QString>(json.value("access_token"_ls)); + if (!json.contains("token_type"_ls)) + return { JsonParseError, + "The key 'token_type' not found in the response" }; + d->tokenType = fromJson<QString>(json.value("token_type"_ls)); + if (!json.contains("matrix_server_name"_ls)) + return { JsonParseError, + "The key 'matrix_server_name' not found in the response" }; + d->matrixServerName = fromJson<QString>(json.value("matrix_server_name"_ls)); + if (!json.contains("expires_in"_ls)) + return { JsonParseError, + "The key 'expires_in' not found in the response" }; + d->expiresIn = fromJson<int>(json.value("expires_in"_ls)); + return Success; +} + diff --git a/lib/csapi/openid.h b/lib/csapi/openid.h new file mode 100644 index 00000000..0dbad7eb --- /dev/null +++ b/lib/csapi/openid.h @@ -0,0 +1,61 @@ +/****************************************************************************** + * THIS FILE IS GENERATED - ANY EDITS WILL BE OVERWRITTEN + */ + +#pragma once + +#include "jobs/basejob.h" + +#include "converters.h" +#include <QtCore/QJsonObject> + +namespace QMatrixClient +{ + // Operations + + /// Get an OpenID token object to verify the requester's identity. + /// + /// Gets an OpenID token object that the requester may supply to another + /// service to verify their identity in Matrix. The generated token is only + /// valid for exchanging for user information from the federation API for + /// OpenID. + /// + /// The access token generated is only valid for the OpenID API. It cannot + /// be used to request another OpenID access token or call ``/sync``, for + /// example. + class RequestOpenIdTokenJob : public BaseJob + { + public: + /*! Get an OpenID token object to verify the requester's identity. + * \param userId + * The user to request and OpenID token for. Should be the user who + * is authenticated for the request. + * \param body + * An empty object. Reserved for future expansion. + */ + explicit RequestOpenIdTokenJob(const QString& userId, const QJsonObject& body = {}); + ~RequestOpenIdTokenJob() override; + + // Result properties + + /// An access token the consumer may use to verify the identity of + /// the person who generated the token. This is given to the federation + /// API ``GET /openid/userinfo``. + const QString& accessToken() const; + /// The string ``Bearer``. + const QString& tokenType() const; + /// The homeserver domain the consumer should use when attempting to + /// verify the user's identity. + const QString& matrixServerName() const; + /// The number of seconds before this token expires and a new one must + /// be generated. + int expiresIn() const; + + protected: + Status parseJson(const QJsonDocument& data) override; + + private: + class Private; + QScopedPointer<Private> d; + }; +} // namespace QMatrixClient diff --git a/lib/csapi/pusher.cpp b/lib/csapi/pusher.cpp index feecdbc7..531970b3 100644 --- a/lib/csapi/pusher.cpp +++ b/lib/csapi/pusher.cpp @@ -24,6 +24,8 @@ namespace QMatrixClient GetPushersJob::PusherData result; result.url = fromJson<QString>(_json.value("url"_ls)); + result.format = + fromJson<QString>(_json.value("format"_ls)); return result; } @@ -100,6 +102,7 @@ namespace QMatrixClient { QJsonObject _json; addParam<IfNotEmpty>(_json, QStringLiteral("url"), pod.url); + addParam<IfNotEmpty>(_json, QStringLiteral("format"), pod.format); return _json; } } // namespace QMatrixClient diff --git a/lib/csapi/pusher.h b/lib/csapi/pusher.h index 2d192669..52717cd1 100644 --- a/lib/csapi/pusher.h +++ b/lib/csapi/pusher.h @@ -15,7 +15,7 @@ namespace QMatrixClient /// Gets the current pushers for the authenticated user /// - /// Gets all currently active pushers for the authenticated user + /// Gets all currently active pushers for the authenticated user. class GetPushersJob : public BaseJob { public: @@ -28,12 +28,15 @@ namespace QMatrixClient /// Required if ``kind`` is ``http``. The URL to use to send /// notifications to. QString url; + /// The format to use when sending notifications to the Push + /// Gateway. + QString format; }; - /// Gets all currently active pushers for the authenticated user + /// Gets all currently active pushers for the authenticated user. struct Pusher { - /// This is a unique identifier for this pusher. See `/set` for + /// This is a unique identifier for this pusher. See ``/set`` for /// more detail. /// Max length, 512 bytes. QString pushkey; @@ -57,7 +60,7 @@ namespace QMatrixClient QString lang; /// A dictionary of information for the pusher implementation /// itself. - Omittable<PusherData> data; + PusherData data; }; // Construction/destruction @@ -103,8 +106,15 @@ namespace QMatrixClient struct PusherData { /// Required if ``kind`` is ``http``. The URL to use to send - /// notifications to. + /// notifications to. MUST be an HTTPS URL with a path of + /// ``/_matrix/push/v1/notify``. QString url; + /// The format to send notifications in to Push Gateways if the + /// ``kind`` is ``http``. The details about what fields the + /// homeserver should send to the push gateway are defined in the + /// `Push Gateway Specification`_. Currently the only format + /// available is 'event_id_only'. + QString format; }; // Construction/destruction @@ -117,14 +127,20 @@ namespace QMatrixClient * for APNS or the Registration ID for GCM. If your notification * client has no such concept, use any unique identifier. * Max length, 512 bytes. + * + * If the ``kind`` is ``"email"``, this is the email address to + * send notifications to. * \param kind * The kind of pusher to configure. ``"http"`` makes a pusher that - * sends HTTP pokes. ``null`` deletes the pusher. + * sends HTTP pokes. ``"email"`` makes a pusher that emails the + * user with unread notifications. ``null`` deletes the pusher. * \param appId * This is a reverse-DNS style identifier for the application. * It is recommended that this end with the platform, such that * different platform versions get different app identifiers. * Max length, 64 chars. + * + * If the ``kind`` is ``"email"``, this is ``"m.email"``. * \param appDisplayName * A string that will allow the user to identify what application * owns this pusher. @@ -133,7 +149,7 @@ namespace QMatrixClient * this pusher. * \param lang * The preferred language for receiving notifications (e.g. 'en' - * or 'en-US') + * or 'en-US'). * \param data * A dictionary of information for the pusher implementation * itself. If ``kind`` is ``http``, this should contain ``url`` diff --git a/lib/csapi/registration.cpp b/lib/csapi/registration.cpp index c0a35917..bdfa4606 100644 --- a/lib/csapi/registration.cpp +++ b/lib/csapi/registration.cpp @@ -79,10 +79,10 @@ BaseJob::Status RegisterJob::parseJson(const QJsonDocument& data) return Success; } -static const auto RequestTokenToRegisterJobName = QStringLiteral("RequestTokenToRegisterJob"); +static const auto RequestTokenToRegisterEmailJobName = QStringLiteral("RequestTokenToRegisterEmailJob"); -RequestTokenToRegisterJob::RequestTokenToRegisterJob(const QString& clientSecret, const QString& email, int sendAttempt, const QString& idServer) - : BaseJob(HttpVerb::Post, RequestTokenToRegisterJobName, +RequestTokenToRegisterEmailJob::RequestTokenToRegisterEmailJob(const QString& clientSecret, const QString& email, int sendAttempt, const QString& idServer) + : BaseJob(HttpVerb::Post, RequestTokenToRegisterEmailJobName, basePath % "/register/email/requestToken", false) { QJsonObject _data; @@ -93,6 +93,21 @@ RequestTokenToRegisterJob::RequestTokenToRegisterJob(const QString& clientSecret setRequestData(_data); } +static const auto RequestTokenToRegisterMSISDNJobName = QStringLiteral("RequestTokenToRegisterMSISDNJob"); + +RequestTokenToRegisterMSISDNJob::RequestTokenToRegisterMSISDNJob(const QString& clientSecret, const QString& country, const QString& phoneNumber, double sendAttempt, const QString& idServer) + : BaseJob(HttpVerb::Post, RequestTokenToRegisterMSISDNJobName, + basePath % "/register/msisdn/requestToken", false) +{ + QJsonObject _data; + addParam<IfNotEmpty>(_data, QStringLiteral("id_server"), idServer); + addParam<>(_data, QStringLiteral("client_secret"), clientSecret); + addParam<>(_data, QStringLiteral("country"), country); + addParam<>(_data, QStringLiteral("phone_number"), phoneNumber); + addParam<>(_data, QStringLiteral("send_attempt"), sendAttempt); + setRequestData(_data); +} + static const auto ChangePasswordJobName = QStringLiteral("ChangePasswordJob"); ChangePasswordJob::ChangePasswordJob(const QString& newPassword, const Omittable<AuthenticationData>& auth) @@ -105,20 +120,34 @@ ChangePasswordJob::ChangePasswordJob(const QString& newPassword, const Omittable setRequestData(_data); } -QUrl RequestTokenToResetPasswordJob::makeRequestUrl(QUrl baseUrl) +QUrl RequestTokenToResetPasswordEmailJob::makeRequestUrl(QUrl baseUrl) { return BaseJob::makeRequestUrl(std::move(baseUrl), basePath % "/account/password/email/requestToken"); } -static const auto RequestTokenToResetPasswordJobName = QStringLiteral("RequestTokenToResetPasswordJob"); +static const auto RequestTokenToResetPasswordEmailJobName = QStringLiteral("RequestTokenToResetPasswordEmailJob"); -RequestTokenToResetPasswordJob::RequestTokenToResetPasswordJob() - : BaseJob(HttpVerb::Post, RequestTokenToResetPasswordJobName, +RequestTokenToResetPasswordEmailJob::RequestTokenToResetPasswordEmailJob() + : BaseJob(HttpVerb::Post, RequestTokenToResetPasswordEmailJobName, basePath % "/account/password/email/requestToken", false) { } +QUrl RequestTokenToResetPasswordMSISDNJob::makeRequestUrl(QUrl baseUrl) +{ + return BaseJob::makeRequestUrl(std::move(baseUrl), + basePath % "/account/password/msisdn/requestToken"); +} + +static const auto RequestTokenToResetPasswordMSISDNJobName = QStringLiteral("RequestTokenToResetPasswordMSISDNJob"); + +RequestTokenToResetPasswordMSISDNJob::RequestTokenToResetPasswordMSISDNJob() + : BaseJob(HttpVerb::Post, RequestTokenToResetPasswordMSISDNJobName, + basePath % "/account/password/msisdn/requestToken", false) +{ +} + static const auto DeactivateAccountJobName = QStringLiteral("DeactivateAccountJob"); DeactivateAccountJob::DeactivateAccountJob(const Omittable<AuthenticationData>& auth) diff --git a/lib/csapi/registration.h b/lib/csapi/registration.h index 0709f71b..cc60b692 100644 --- a/lib/csapi/registration.h +++ b/lib/csapi/registration.h @@ -111,11 +111,9 @@ namespace QMatrixClient /// /// Proxies the identity server API ``validate/email/requestToken``, but /// first checks that the given email address is not already associated - /// with an account on this Home Server. Note that, for consistency, - /// this API takes JSON objects, though the Identity Server API takes - /// ``x-www-form-urlencoded`` parameters. See the Identity Server API for + /// with an account on this Home Server. See the Identity Server API for /// further information. - class RequestTokenToRegisterJob : public BaseJob + class RequestTokenToRegisterEmailJob : public BaseJob { public: /*! Requests a validation token be sent to the given email address for the purpose of registering an account @@ -128,7 +126,32 @@ namespace QMatrixClient * \param idServer * The ID server to send the onward request to as a hostname with an appended colon and port number if the port is not the default. */ - explicit RequestTokenToRegisterJob(const QString& clientSecret, const QString& email, int sendAttempt, const QString& idServer = {}); + explicit RequestTokenToRegisterEmailJob(const QString& clientSecret, const QString& email, int sendAttempt, const QString& idServer = {}); + }; + + /// Requests a validation token be sent to the given phone number for the purpose of registering an account + /// + /// Proxies the identity server API ``validate/msisdn/requestToken``, but + /// first checks that the given phone number is not already associated + /// with an account on this Home Server. See the Identity Server API for + /// further information. + class RequestTokenToRegisterMSISDNJob : public BaseJob + { + public: + /*! Requests a validation token be sent to the given phone number for the purpose of registering an account + * \param clientSecret + * Client-generated secret string used to protect this session. + * \param country + * The two-letter uppercase ISO country code that the number in + * ``phone_number`` should be parsed as if it were dialled from. + * \param phoneNumber + * The phone number. + * \param sendAttempt + * Used to distinguish protocol level retries from requests to re-send the SMS message. + * \param idServer + * The ID server to send the onward request to as a hostname with an appended colon and port number if the port is not the default. + */ + explicit RequestTokenToRegisterMSISDNJob(const QString& clientSecret, const QString& country, const QString& phoneNumber, double sendAttempt, const QString& idServer = {}); }; /// Changes a user's password. @@ -170,15 +193,46 @@ namespace QMatrixClient /// .. |/register/email/requestToken| replace:: ``/register/email/requestToken`` /// /// .. _/register/email/requestToken: #post-matrix-client-r0-register-email-requesttoken - class RequestTokenToResetPasswordJob : public BaseJob + class RequestTokenToResetPasswordEmailJob : public BaseJob + { + public: + explicit RequestTokenToResetPasswordEmailJob(); + + /*! Construct a URL without creating a full-fledged job object + * + * This function can be used when a URL for + * RequestTokenToResetPasswordEmailJob is necessary but the job + * itself isn't. + */ + static QUrl makeRequestUrl(QUrl baseUrl); + + }; + + /// Requests a validation token be sent to the given phone number for the purpose of resetting a user's password. + /// + /// Proxies the identity server API ``validate/msisdn/requestToken``, but + /// first checks that the given phone number **is** associated with an account + /// on this Home Server. This API should be used to request + /// validation tokens when authenticating for the + /// `account/password` endpoint. This API's parameters and response are + /// identical to that of the HS API |/register/msisdn/requestToken|_ except that + /// `M_THREEPID_NOT_FOUND` may be returned if no account matching the + /// given email address could be found. The server may instead send an + /// SMS message to the given address prompting the user to create an account. + /// `M_THREEPID_IN_USE` may not be returned. + /// + /// .. |/register/msisdn/requestToken| replace:: ``/register/msisdn/requestToken`` + /// + /// .. _/register/msisdn/requestToken: #post-matrix-client-r0-register-email-requesttoken + class RequestTokenToResetPasswordMSISDNJob : public BaseJob { public: - explicit RequestTokenToResetPasswordJob(); + explicit RequestTokenToResetPasswordMSISDNJob(); /*! Construct a URL without creating a full-fledged job object * * This function can be used when a URL for - * RequestTokenToResetPasswordJob is necessary but the job + * RequestTokenToResetPasswordMSISDNJob is necessary but the job * itself isn't. */ static QUrl makeRequestUrl(QUrl baseUrl); diff --git a/lib/csapi/third_party_lookup.cpp b/lib/csapi/third_party_lookup.cpp index 45ccb7c3..406e6d34 100644 --- a/lib/csapi/third_party_lookup.cpp +++ b/lib/csapi/third_party_lookup.cpp @@ -28,7 +28,7 @@ static const auto GetProtocolsJobName = QStringLiteral("GetProtocolsJob"); GetProtocolsJob::GetProtocolsJob() : BaseJob(HttpVerb::Get, GetProtocolsJobName, - basePath % "/thirdparty/protocols", false) + basePath % "/thirdparty/protocols") , d(new Private) { } @@ -66,7 +66,7 @@ static const auto GetProtocolMetadataJobName = QStringLiteral("GetProtocolMetada GetProtocolMetadataJob::GetProtocolMetadataJob(const QString& protocol) : BaseJob(HttpVerb::Get, GetProtocolMetadataJobName, - basePath % "/thirdparty/protocol/" % protocol, false) + basePath % "/thirdparty/protocol/" % protocol) , d(new Private) { } @@ -113,8 +113,7 @@ static const auto QueryLocationByProtocolJobName = QStringLiteral("QueryLocation QueryLocationByProtocolJob::QueryLocationByProtocolJob(const QString& protocol, const QString& searchFields) : BaseJob(HttpVerb::Get, QueryLocationByProtocolJobName, basePath % "/thirdparty/location/" % protocol, - queryToQueryLocationByProtocol(searchFields), - {}, false) + queryToQueryLocationByProtocol(searchFields)) , d(new Private) { } @@ -142,14 +141,14 @@ class QueryUserByProtocolJob::Private QVector<ThirdPartyUser> data; }; -BaseJob::Query queryToQueryUserByProtocol(const QJsonObject& fields) +BaseJob::Query queryToQueryUserByProtocol(const QString& fields) { BaseJob::Query _q; - addParam<IfNotEmpty>(_q, QStringLiteral("fields"), fields); + addParam<IfNotEmpty>(_q, QStringLiteral("fields..."), fields); return _q; } -QUrl QueryUserByProtocolJob::makeRequestUrl(QUrl baseUrl, const QString& protocol, const QJsonObject& fields) +QUrl QueryUserByProtocolJob::makeRequestUrl(QUrl baseUrl, const QString& protocol, const QString& fields) { return BaseJob::makeRequestUrl(std::move(baseUrl), basePath % "/thirdparty/user/" % protocol, @@ -158,11 +157,10 @@ QUrl QueryUserByProtocolJob::makeRequestUrl(QUrl baseUrl, const QString& protoco static const auto QueryUserByProtocolJobName = QStringLiteral("QueryUserByProtocolJob"); -QueryUserByProtocolJob::QueryUserByProtocolJob(const QString& protocol, const QJsonObject& fields) +QueryUserByProtocolJob::QueryUserByProtocolJob(const QString& protocol, const QString& fields) : BaseJob(HttpVerb::Get, QueryUserByProtocolJobName, basePath % "/thirdparty/user/" % protocol, - queryToQueryUserByProtocol(fields), - {}, false) + queryToQueryUserByProtocol(fields)) , d(new Private) { } @@ -209,8 +207,7 @@ static const auto QueryLocationByAliasJobName = QStringLiteral("QueryLocationByA QueryLocationByAliasJob::QueryLocationByAliasJob(const QString& alias) : BaseJob(HttpVerb::Get, QueryLocationByAliasJobName, basePath % "/thirdparty/location", - queryToQueryLocationByAlias(alias), - {}, false) + queryToQueryLocationByAlias(alias)) , d(new Private) { } @@ -257,8 +254,7 @@ static const auto QueryUserByIDJobName = QStringLiteral("QueryUserByIDJob"); QueryUserByIDJob::QueryUserByIDJob(const QString& userid) : BaseJob(HttpVerb::Get, QueryUserByIDJobName, basePath % "/thirdparty/user", - queryToQueryUserByID(userid), - {}, false) + queryToQueryUserByID(userid)) , d(new Private) { } diff --git a/lib/csapi/third_party_lookup.h b/lib/csapi/third_party_lookup.h index a431b87a..03d607a8 100644 --- a/lib/csapi/third_party_lookup.h +++ b/lib/csapi/third_party_lookup.h @@ -7,7 +7,6 @@ #include "jobs/basejob.h" #include "csapi/../application-service/definitions/user.h" -#include <QtCore/QJsonObject> #include "csapi/../application-service/definitions/location.h" #include <QtCore/QHash> #include <QtCore/QVector> @@ -144,7 +143,7 @@ namespace QMatrixClient * \param fields * One or more custom fields that are passed to the AS to help identify the user. */ - explicit QueryUserByProtocolJob(const QString& protocol, const QJsonObject& fields = {}); + explicit QueryUserByProtocolJob(const QString& protocol, const QString& fields = {}); /*! Construct a URL without creating a full-fledged job object * @@ -152,7 +151,7 @@ namespace QMatrixClient * QueryUserByProtocolJob is necessary but the job * itself isn't. */ - static QUrl makeRequestUrl(QUrl baseUrl, const QString& protocol, const QJsonObject& fields = {}); + static QUrl makeRequestUrl(QUrl baseUrl, const QString& protocol, const QString& fields = {}); ~QueryUserByProtocolJob() override; |