Ring Daemon
Loading...
Searching...
No Matches
jamiaccount.h
Go to the documentation of this file.
1/*
2 * Copyright (C) 2004-2026 Savoir-faire Linux Inc.
3 *
4 * This program is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation, either version 3 of the License, or
7 * (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <https://www.gnu.org/licenses/>.
16 */
17#pragma once
18
19#include "def.h"
20#ifdef HAVE_CONFIG_H
21#include "config.h"
22#endif
23
24#include "sip/sipaccountbase.h"
27#include "data_transfer.h"
28#include "uri.h"
29#include "jamiaccount_config.h"
30
31#include "noncopyable.h"
32#include "gitserver.h"
33#include "channel_handler.h"
34#include "conversation_module.h"
35#include "sync_module.h"
37#include "namedirectory.h"
38
39#include <dhtnet/diffie-hellman.h>
40#include <dhtnet/tls_session.h>
41#include <dhtnet/multiplexed_socket.h>
42#include <dhtnet/certstore.h>
43#include <dhtnet/connectionmanager.h>
44#include <dhtnet/upnp/mapping.h>
45#include <dhtnet/ip_utils.h>
46#include <dhtnet/fileutils.h>
47
48#include <opendht/dhtrunner.h>
49#include <opendht/default_types.h>
50#include <opendht/dht_proxy_server.h>
51
52#include <pjsip/sip_types.h>
53#include <json/json.h>
54
55#include <chrono>
56#include <functional>
57#include <future>
58#include <list>
59#include <map>
60#include <optional>
61#include <vector>
62#include <filesystem>
63#include <shared_mutex>
64
65namespace dev {
66template<unsigned N>
67class FixedHash;
68using h160 = FixedHash<20>;
69using Address = h160;
70} // namespace dev
71
72namespace jami {
73
74class IceTransport;
75struct Contact;
76struct AccountArchive;
78class AccountManager;
79struct AccountInfo;
80class SipTransport;
82class SyncModule;
83class PresenceManager;
84
85using SipConnectionKey = std::pair<std::string /* uri */, DeviceId>;
86
87static constexpr const char MIME_TYPE_IM_COMPOSING[] {"application/im-iscomposing+xml"};
88
93{
94public:
95 constexpr static auto ACCOUNT_TYPE = ACCOUNT_TYPE_JAMI;
96 constexpr static const std::pair<uint16_t, uint16_t> DHT_PORT_RANGE {4000, 8888};
97 constexpr static int ICE_STREAMS_COUNT {1};
98 constexpr static int ICE_COMP_COUNT_PER_STREAM {1};
99
100 std::string_view getAccountType() const override { return ACCOUNT_TYPE; }
101
102 std::shared_ptr<JamiAccount> shared() { return std::static_pointer_cast<JamiAccount>(shared_from_this()); }
103 std::shared_ptr<JamiAccount const> shared() const
104 {
105 return std::static_pointer_cast<JamiAccount const>(shared_from_this());
106 }
107 std::weak_ptr<JamiAccount> weak() { return std::static_pointer_cast<JamiAccount>(shared_from_this()); }
108 std::weak_ptr<JamiAccount const> weak() const
109 {
110 return std::static_pointer_cast<JamiAccount const>(shared_from_this());
111 }
112
113 const JamiAccountConfig& config() const { return *static_cast<const JamiAccountConfig*>(&Account::config()); }
114
116 {
117 auto* conf = static_cast<JamiAccountConfig*>(config_.get());
118 return std::move(conf->credentials);
119 }
120
121 void loadConfig() override;
122
127 JamiAccount(const std::string& accountId);
128
130
135 virtual std::map<std::string, std::string> getVolatileAccountDetails() const override;
136
138 {
139 return std::make_unique<JamiAccountConfig>(getAccountID(), idPath_);
140 }
141
148 void trackBuddyPresence(const std::string& buddy_id, bool track);
149
156 std::map<std::string, bool> getTrackedBuddyPresence() const;
157
158 void setActiveCodecs(const std::vector<unsigned>& list) override;
159
163 void doRegister() override;
164
168 void doUnregister(bool forceShutdownConnections = false) override;
169
174 void setRegistrationState(RegistrationState state, int detail_code = 0, const std::string& detail_str = {}) override;
175
185 std::string getFromUri() const override;
186
195 std::string getToUri(const std::string& username) const override;
196
205 std::string getServerUri() const { return ""; };
206
207 void setIsComposing(const std::string& conversationUri, bool isWriting) override;
208
209 bool setMessageDisplayed(const std::string& conversationUri, const std::string& messageId, int status) override;
210
215 std::string getContactHeader(const std::shared_ptr<SipTransport>& sipTransport);
216
217 /* Returns true if the username and/or hostname match this account */
218 MatchRank matches(std::string_view username, std::string_view hostname) const override;
219
230 std::shared_ptr<Call> newOutgoingCall(std::string_view toUrl,
231 const std::vector<libjami::MediaMap>& mediaList) override;
232
240 std::shared_ptr<SIPCall> newIncomingCall(const std::string& from,
241 const std::vector<libjami::MediaMap>& mediaList,
242 const std::shared_ptr<SipTransport>& sipTr = {}) override;
243
244 void onTextMessage(const std::string& id,
245 const std::string& from,
246 const std::shared_ptr<dht::crypto::Certificate>& peerCert,
247 const std::map<std::string, std::string>& payloads) override;
248 void loadConversation(const std::string& convId);
249
250 virtual bool isTlsEnabled() const override { return true; }
251 bool isSrtpEnabled() const override { return true; }
252
253 bool setCertificateStatus(const std::string& cert_id, dhtnet::tls::TrustStore::PermissionStatus status);
254 bool setCertificateStatus(const std::shared_ptr<crypto::Certificate>& cert,
255 dhtnet::tls::TrustStore::PermissionStatus status,
256 bool local = true);
257 std::vector<std::string> getCertificatesByStatus(dhtnet::tls::TrustStore::PermissionStatus status);
258
259 bool findCertificate(const std::string& id);
260 bool findCertificate(const dht::InfoHash& h,
261 std::function<void(const std::shared_ptr<dht::crypto::Certificate>&)>&& cb = {});
262 bool findCertificate(const dht::PkId& h,
263 std::function<void(const std::shared_ptr<dht::crypto::Certificate>&)>&& cb = {});
264
265 /* contact requests */
266 std::vector<std::map<std::string, std::string>> getTrustRequests() const;
267 // Note: includeConversation used for compatibility test. Do not change
268 bool acceptTrustRequest(const std::string& from, bool includeConversation = true);
269 bool discardTrustRequest(const std::string& from);
270 void declineConversationRequest(const std::string& conversationId);
271
276 void addContact(const std::string& uri, bool confirmed = false);
277 void removeContact(const std::string& uri, bool banned = true);
278 std::vector<std::map<std::string, std::string>> getContacts(bool includeRemoved = false) const;
279
283 std::map<std::string, std::string> getContactDetails(const std::string& uri) const;
284 std::optional<Contact> getContactInfo(const std::string& uri) const;
285
286 void sendTrustRequest(const std::string& to, const std::vector<uint8_t>& payload);
287 void sendMessage(const std::string& to,
288 const std::string& deviceId,
289 const std::map<std::string, std::string>& payloads,
290 uint64_t id,
291 bool retryOnTimeout = true,
292 bool onlyConnected = false) override;
293
294 uint64_t sendTextMessage(const std::string& to,
295 const std::string& deviceId,
296 const std::map<std::string, std::string>& payloads,
298 bool onlyConnected = false) override;
299 void sendInstantMessage(const std::string& convId, const std::map<std::string, std::string>& msg);
300
304 dhtnet::IceTransportOptions getIceOptions() const override;
305 void getIceOptions(std::function<void(dhtnet::IceTransportOptions&&)> cb) const;
306 dhtnet::IpAddr getPublishedIpAddress(uint16_t family = PF_UNSPEC) const override;
307
308 /* Devices - existing device */
317 int32_t addDevice(const std::string& uriProvided);
320 /* Devices - new device */
321 bool provideAccountAuthentication(const std::string& credentialsFromUser, const std::string& scheme);
322
330 bool exportArchive(const std::string& destinationPath,
331 std::string_view scheme = {},
332 const std::string& password = {});
333 bool revokeDevice(const std::string& device, std::string_view scheme = {}, const std::string& password = {});
334 std::map<std::string, std::string> getKnownDevices() const;
335
336 bool isPasswordValid(const std::string& password);
337 std::vector<uint8_t> getPasswordKey(const std::string& password);
338
339 bool changeArchivePassword(const std::string& password_old, const std::string& password_new);
340
341 void connectivityChanged() override;
342
343 // overloaded methods
344 void flush() override;
345
346 void lookupName(const std::string& name);
347 void lookupAddress(const std::string& address);
348 void registerName(const std::string& name, const std::string& scheme, const std::string& password);
349 bool searchUser(const std::string& nameQuery);
350
354 bool isMessageTreated(dht::Value::Id id);
355
356 std::shared_ptr<dht::DhtRunner> dht() { return dht_; }
357
358 const dht::crypto::Identity& identity() const { return id_; }
359
360 PresenceManager* presenceManager() const { return presenceManager_.get(); }
361
362 void forEachDevice(const dht::InfoHash& to,
363 std::function<void(const std::shared_ptr<dht::crypto::PublicKey>&)>&& op,
364 std::function<void(bool)>&& end = {});
365
366 bool setPushNotificationToken(const std::string& pushDeviceToken = "") override;
367 bool setPushNotificationTopic(const std::string& topic) override;
368 bool setPushNotificationConfig(const std::map<std::string, std::string>& data) override;
369
373 void pushNotificationReceived(const std::string& from, const std::map<std::string, std::string>& data);
374
375 std::string getUserUri() const override;
376
381 std::vector<libjami::Message> getLastMessages(const uint64_t& base_timestamp) override;
382
386 void startAccountPublish();
387
392
393 void saveConfig() const override;
394
395 inline void editConfig(std::function<void(JamiAccountConfig& conf)>&& edit)
396 {
397 Account::editConfig([&](AccountConfig& conf) { edit(*static_cast<JamiAccountConfig*>(&conf)); });
398 }
399
403 std::map<std::string, std::string> getNearbyPeers() const override;
404
405 void sendProfileToPeers();
406
413 void updateProfile(const std::string& displayName,
414 const std::string& avatar,
415 const std::string& fileType,
416 int32_t flag) override;
417
418#ifdef LIBJAMI_TEST
419 dhtnet::ConnectionManager& connectionManager() { return *connectionManager_; }
420
426
427 void publishPresence(bool newValue) { publishPresence_ = newValue; }
428#endif
429
434 void shutdownConnections();
435
436 std::string_view currentDeviceId() const;
437
438 // Received a new commit notification
439
440 bool handleMessage(const std::shared_ptr<dht::crypto::Certificate>& cert,
441 const std::string& from,
442 const std::pair<std::string, std::string>& message) override;
443
444 void monitor();
445 // conversationId optional
446 std::vector<std::map<std::string, std::string>> getConnectionList(const std::string& conversationId = "");
447 std::vector<std::map<std::string, std::string>> getConversationConnectivity(const std::string& conversationId);
448 std::vector<std::map<std::string, std::string>> getConversationTrackedMembers(const std::string& conversationId);
449 std::vector<std::map<std::string, std::string>> getChannelList(const std::string& connectionId);
450
451 // File transfer
452 void sendFile(const std::string& conversationId,
453 const std::filesystem::path& path,
454 const std::string& name,
455 const std::string& replyTo);
456
457 void transferFile(const std::string& conversationId,
458 const std::string& path,
459 const std::string& deviceId,
460 const std::string& fileId,
461 const std::string& interactionId,
462 size_t start = 0,
463 size_t end = 0,
464 const std::string& sha3Sum = "",
466 std::function<void()> onFinished = {});
467
468 void askForFileChannel(const std::string& conversationId,
469 const std::string& deviceId,
470 const std::string& interactionId,
471 const std::string& fileId,
472 size_t start = 0,
473 size_t end = 0);
474
475 void askForProfile(const std::string& conversationId, const std::string& deviceId, const std::string& memberUri);
476
482 std::shared_ptr<TransferManager> dataTransfer(const std::string& id = "");
483
490 ConversationModule* convModule(bool noCreation = false);
491 SyncModule* syncModule();
492
499 // Note: when swarm will be merged, this can be moved in transferManager
500 bool needToSendProfile(const std::string& peerUri, const std::string& deviceId, const std::string& sha3Sum);
507 void sendProfile(const std::string& convId, const std::string& peerUri, const std::string& deviceId);
513 void sendProfile(const std::string& peerUri, const std::string& deviceId);
518 void clearProfileCache(const std::string& peerUri);
519
520 std::filesystem::path profilePath() const;
521
522 const std::shared_ptr<AccountManager>& accountManager() { return accountManager_; }
523
524 bool sha3SumVerify() const;
525
533 bool setValidity(std::string_view scheme, const std::string& pwd, const dht::InfoHash& id, int64_t validity);
537 void forceReloadAccount();
538
539 void reloadContacts();
540
545 void unlinkConversations(const std::set<std::string>& removedConv);
546
547 bool isValidAccountDevice(const dht::crypto::Certificate& cert) const;
548
554 void handleIncomingConversationCall(const std::string& callId, const std::string& destination);
555
561 bool isMobile() const { return config().proxyEnabled and not config().deviceKey.empty(); }
562
563#ifdef LIBJAMI_TEST
564 std::map<Uri::Scheme, std::unique_ptr<ChannelHandlerInterface>>& channelHandlers() { return channelHandlers_; };
565#endif
566
567 dhtnet::tls::CertificateStore& certStore() const { return *certStore_; }
573 bool isConnectedWith(const DeviceId& deviceId) const;
574
579 void sendPresenceNote(const std::string& note);
580
581private:
583
584 using clock = std::chrono::system_clock;
585 using time_point = clock::time_point;
586
590 struct PendingCall;
591 struct PendingMessage;
592 struct DiscoveredPeer;
593 class SendMessageContext;
594
595 inline std::string getProxyConfigKey() const
596 {
597 const auto& conf = config();
598 return dht::InfoHash::get(conf.proxyServer + conf.proxyListUrl).toString();
599 }
600
601 void scheduleAccountReady() const;
602 AccountManager::OnChangeCallback setupAccountCallbacks();
603
604 void onContactAdded(const std::string& uri, bool confirmed);
605 void onContactRemoved(const std::string& uri, bool banned);
606 void onIncomingTrustRequest(const std::string& uri,
607 const std::string& conversationId,
608 const std::vector<uint8_t>& payload,
609 time_t received);
610 void onKnownDevicesChanged(const std::map<DeviceId, KnownDevice>& devices);
611 void onConversationRequestAccepted(const std::string& conversationId, const std::string& deviceId);
612 void onContactConfirmed(const std::string& uri, const std::string& convFromReq);
613
614 void conversationNeedsSyncing(std::shared_ptr<SyncMsg>&& syncMsg);
615 uint64_t conversationSendMessage(const std::string& uri,
616 const DeviceId& device,
617 const std::map<std::string, std::string>& msg,
618 uint64_t token = 0);
619 void onConversationNeedSocket(const std::string& convId,
620 const std::string& deviceId,
621 ChannelCb&& cb,
622 const std::string& type);
623 void onConversationNeedSwarmSocket(const std::string& convId,
624 const std::string& deviceId,
625 ChannelCb&& cb,
626 const std::string& type);
627 void conversationOneToOneReceive(const std::string& convId, const std::string& from);
628
629 std::unique_ptr<AccountManager::AccountCredentials> buildAccountCredentials(
630 const JamiAccountConfig& conf,
631 const dht::crypto::Identity& id,
632 const std::string& archive_password_scheme,
633 const std::string& archive_password,
634 const std::string& archive_path,
635 bool& migrating,
636 bool& hasPassword);
637
638 void onAuthenticationSuccess(bool migrating,
639 bool hasPassword,
640 const AccountInfo& info,
641 const std::map<std::string, std::string>& configMap,
642 std::string&& receipt,
643 std::vector<uint8_t>&& receiptSignature);
644
645 static void onAuthenticationError(const std::weak_ptr<JamiAccount>& w,
646 bool hadIdentity,
647 bool migrating,
648 std::string accountId,
650 const std::string& message);
651
652 void onPeerConnected(const std::string& peerId, bool connected);
653
654 void doRegister_();
655
656 void lookupRegisteredName(const std::string& regName, const NameDirectory::Response& response);
657 dht::DhtRunner::Config initDhtConfig(const JamiAccountConfig& conf);
658 dht::DhtRunner::Context initDhtContext();
659 void onAccountDeviceFound(const std::shared_ptr<dht::crypto::Certificate>& crt);
660 void onAccountDeviceAnnounced();
661 bool onICERequest(const DeviceId& deviceId);
662 bool onChannelRequest(const std::shared_ptr<dht::crypto::Certificate>& cert, const std::string& name);
663 void onConnectionReady(const DeviceId& deviceId,
664 const std::string& name,
665 std::shared_ptr<dhtnet::ChannelSocket> channel);
666
667 const dht::ValueType USER_PROFILE_TYPE = {9, "User profile", std::chrono::hours(24 * 7)};
668
669 void startOutgoingCall(const std::shared_ptr<SIPCall>& call, const std::string& toUri);
670
671 void onConnectedOutgoingCall(const std::shared_ptr<SIPCall>& call, const std::string& to_id, dhtnet::IpAddr target);
672
678 bool SIPStartCall(SIPCall& call, const dhtnet::IpAddr& target);
679
683 void onTrackedBuddyOffline(const std::string&);
684
688 void onTrackedBuddyOnline(const std::string&);
689
693 void registerAsyncOps();
697 void onPortMappingAdded(uint16_t port_used, bool success);
698 void forEachPendingCall(const DeviceId& deviceId, const std::function<void(const std::shared_ptr<SIPCall>&)>& cb);
699
700 void loadAccount(const std::string& archive_password_scheme = {},
701 const std::string& archive_password = {},
702 const std::string& archive_path = {});
703
704 std::vector<std::string> loadBootstrap() const;
705
706 static std::pair<std::string, std::string> saveIdentity(const dht::crypto::Identity& id,
707 const std::filesystem::path& path,
708 const std::string& name);
709
710 void replyToIncomingIceMsg(const std::shared_ptr<SIPCall>&,
711 const std::shared_ptr<IceTransport>&,
712 const std::shared_ptr<IceTransport>&,
713 const dht::IceCandidates&,
714 const std::shared_ptr<dht::crypto::Certificate>& from_cert,
715 const dht::InfoHash& from);
716
717 void loadCachedUrl(const std::string& url,
718 const std::filesystem::path& cachePath,
719 const std::chrono::seconds& cacheDuration,
720 const std::function<void(const dht::http::Response& response)>& cb);
721
722 std::string getDhtProxyServer(const std::string& serverList);
723 void loadCachedProxyServer(std::function<void(const std::string&)> cb);
724
725 void newOutgoingCallHelper(const std::shared_ptr<SIPCall>& call, const Uri& uri);
726 std::shared_ptr<SIPCall> newSwarmOutgoingCallHelper(const Uri& uri, const std::vector<libjami::MediaMap>& mediaList);
727 std::shared_ptr<SIPCall> createSubCall(const std::shared_ptr<SIPCall>& mainCall);
728
729 std::filesystem::path cachePath_ {};
730 std::filesystem::path dataPath_ {};
731
732 mutable std::mutex registeredNameMutex_;
733 std::string registeredName_;
734
735 bool setRegisteredName(const std::string& name)
736 {
737 std::lock_guard<std::mutex> lock(registeredNameMutex_);
738 if (registeredName_ != name) {
739 registeredName_ = name;
740 return true;
741 }
742 return false;
743 }
744 std::string getRegisteredName() const
745 {
746 std::lock_guard<std::mutex> lock(registeredNameMutex_);
747 return registeredName_;
748 }
749
750 std::shared_ptr<dht::Logger> logger_;
751 std::shared_ptr<dhtnet::tls::CertificateStore> certStore_;
752
753 std::shared_ptr<dht::DhtRunner> dht_ {};
754 std::shared_ptr<AccountManager> accountManager_;
755 dht::crypto::Identity id_ {};
756
757 std::shared_ptr<dht::DhtProxyServer> dhtProxyServer_;
758
759 mutable std::mutex messageMutex_ {};
760 std::map<dht::Value::Id, PendingMessage> sentMessages_;
761 dhtnet::fileutils::IdList treatedMessages_;
762
763 /* tracked buddies presence */
764 std::unique_ptr<PresenceManager> presenceManager_;
765 uint64_t presenceListenerToken_ {0};
766
767 std::atomic_int syncCnt_ {0};
768
774 in_port_t dhtPortUsed()
775 {
776 return (upnpCtrl_ and dhtUpnpMapping_.isValid()) ? dhtUpnpMapping_.getExternalPort() : config().dhtPort;
777 }
778
779 /* Current UPNP mapping */
780 dhtnet::upnp::Mapping dhtUpnpMapping_ {dhtnet::upnp::PortType::UDP};
781
785 std::string proxyServerCached_ {};
786
790 pjsip_host_port via_addr_ {};
791
792 pjsip_transport* via_tp_ {nullptr};
793
797 mutable std::shared_mutex connManagerMtx_ {};
798 std::unique_ptr<dhtnet::ConnectionManager> connectionManager_;
799
800 virtual void updateUpnpController() override;
801
802 std::mutex discoveryMapMtx_;
803 std::shared_ptr<dht::PeerDiscovery> peerDiscovery_;
804 std::map<dht::InfoHash, DiscoveredPeer> discoveredPeers_;
805 std::map<std::string, std::string> discoveredPeerMap_;
806
807 std::set<std::shared_ptr<dht::http::Request>> requests_;
808
809 mutable std::mutex sipConnsMtx_ {};
810 struct SipConnection
811 {
812 std::shared_ptr<SipTransport> transport;
813 // Needs to keep track of that channel to access underlying ICE
814 // information, as the SipTransport use a generic transport
815 std::shared_ptr<dhtnet::ChannelSocket> channel;
816 };
817 // NOTE: here we use a vector to avoid race conditions. In fact the contact
818 // can ask for a SIP channel when we are creating a new SIP Channel with this
819 // peer too.
820 std::map<SipConnectionKey, std::vector<SipConnection>> sipConns_;
821
822 std::mutex pendingCallsMutex_;
823 std::map<DeviceId, std::vector<std::shared_ptr<SIPCall>>> pendingCalls_;
824
825 std::mutex onConnectionClosedMtx_ {};
826 std::map<DeviceId, std::function<void(const DeviceId&, bool)>> onConnectionClosed_ {};
833 void callConnectionClosed(const DeviceId& deviceId, bool eraseDummy);
834
843 void requestSIPConnection(const std::string& peerId,
844 const DeviceId& deviceId,
845 const std::string& connectionType,
846 bool forceNewConnection = false,
847 const std::shared_ptr<SIPCall>& pc = {});
854 void cacheSIPConnection(std::shared_ptr<dhtnet::ChannelSocket>&& channel,
855 const std::string& peerId,
856 const DeviceId& deviceId);
863 void shutdownSIPConnection(const std::shared_ptr<dhtnet::ChannelSocket>& channel,
864 const std::string& peerId,
865 const DeviceId& deviceId);
866
867 void requestMessageConnection(const std::string& peerId,
868 const DeviceId& deviceId,
869 const std::string& connectionType);
870
871 // File transfers
872 std::mutex transfersMtx_ {};
873 std::set<std::string> incomingFileTransfers_ {};
874
875 void onMessageSent(
876 const std::string& to, uint64_t id, const std::string& deviceId, bool success, bool onlyConnected, bool retry);
877
878 std::mutex gitServersMtx_ {};
879 std::map<dht::Value::Id, std::unique_ptr<GitServer>> gitServers_ {};
880
882 std::shared_ptr<TransferManager> nonSwarmTransferManager_;
883
884 std::atomic_bool deviceAnnounced_ {false};
885 std::atomic_bool noSha3sumVerification_ {false};
886
887 bool publishPresence_ {true};
888
889 std::map<Uri::Scheme, std::unique_ptr<ChannelHandlerInterface>> channelHandlers_ {};
890
891 std::unique_ptr<ConversationModule> convModule_;
892 std::mutex moduleMtx_;
893 std::unique_ptr<SyncModule> syncModule_;
894
895 std::mutex rdvMtx_;
896
897 int dhtBoundPort_ {0};
898
899 void initConnectionManager();
900
901 enum class PresenceState : int { DISCONNECTED = 0, AVAILABLE, CONNECTED };
902 std::map<std::string, PresenceState> presenceState_;
903 mutable std::mutex presenceStateMtx_;
904 std::string presenceNote_;
905};
906
907static inline std::ostream&
908operator<<(std::ostream& os, const JamiAccount& acc)
909{
910 os << "[Account " << acc.getAccountID() << "] ";
911 return os;
912}
913
914} // namespace jami
ContactList::OnChangeCallback OnChangeCallback
const std::string & getAccountID() const
Get the account ID.
Definition account.h:149
std::filesystem::path idPath_
path to account
Definition account.h:482
std::unique_ptr< AccountConfig > config_
Definition account.h:437
void editConfig(std::function< void(AccountConfig &config)> &&edit)
Definition account.h:116
const AccountConfig & config() const
Definition account.h:108
std::shared_ptr< dhtnet::upnp::Controller > upnpCtrl_
Definition account.h:493
Ring Account is build on top of SIPAccountBase and uses DHT to handle call connectivity.
Definition jamiaccount.h:93
dhtnet::IpAddr getPublishedIpAddress(uint16_t family=PF_UNSPEC) const override
void askForFileChannel(const std::string &conversationId, const std::string &deviceId, const std::string &interactionId, const std::string &fileId, size_t start=0, size_t end=0)
void forceReloadAccount()
Try to reload the account to force the identity to be updated.
std::optional< Contact > getContactInfo(const std::string &uri) const
void sendTrustRequest(const std::string &to, const std::vector< uint8_t > &payload)
bool isConnectedWith(const DeviceId &deviceId) const
Check if a Device is connected.
void addContact(const std::string &uri, bool confirmed=false)
Add contact to the account contact list.
static constexpr int ICE_STREAMS_COUNT
Definition jamiaccount.h:97
std::shared_ptr< Call > newOutgoingCall(std::string_view toUrl, const std::vector< libjami::MediaMap > &mediaList) override
Create outgoing SIPCall.
std::vector< std::map< std::string, std::string > > getConversationTrackedMembers(const std::string &conversationId)
bool needToSendProfile(const std::string &peerUri, const std::string &deviceId, const std::string &sha3Sum)
Check (via the cache) if we need to send our profile to a specific device.
std::vector< std::map< std::string, std::string > > getConnectionList(const std::string &conversationId="")
bool provideAccountAuthentication(const std::string &credentialsFromUser, const std::string &scheme)
void sendPresenceNote(const std::string &note)
Send a presence note.
const JamiAccountConfig & config() const
std::map< std::string, std::string > getKnownDevices() const
void startAccountDiscovery()
Start Discovery the Jami Account from the Network.
std::vector< std::map< std::string, std::string > > getChannelList(const std::string &connectionId)
PresenceManager * presenceManager() const
~JamiAccount() noexcept
void lookupAddress(const std::string &address)
bool discardTrustRequest(const std::string &from)
void declineConversationRequest(const std::string &conversationId)
void doRegister() override
Connect to the DHT.
std::string getContactHeader(const std::shared_ptr< SipTransport > &sipTransport)
Get the contact header for.
void unlinkConversations(const std::set< std::string > &removedConv)
Make sure appdata/contacts.yml contains correct information.
bool isSrtpEnabled() const override
static constexpr int ICE_COMP_COUNT_PER_STREAM
Definition jamiaccount.h:98
void sendProfile(const std::string &peerUri, const std::string &deviceId)
Send profile via cached SIP connection.
std::vector< std::string > getCertificatesByStatus(dhtnet::tls::TrustStore::PermissionStatus status)
void setRegistrationState(RegistrationState state, int detail_code=0, const std::string &detail_str={}) override
Set the registration state of the specified link.
void sendFile(const std::string &conversationId, const std::filesystem::path &path, const std::string &name, const std::string &replyTo)
bool setPushNotificationConfig(const std::map< std::string, std::string > &data) override
void pushNotificationReceived(const std::string &from, const std::map< std::string, std::string > &data)
To be called by clients with relevant data when a push notification is received.
std::shared_ptr< dht::DhtRunner > dht()
JamiAccountConfig::Credentials consumeConfigCredentials()
std::shared_ptr< SIPCall > newIncomingCall(const std::string &from, const std::vector< libjami::MediaMap > &mediaList, const std::shared_ptr< SipTransport > &sipTr={}) override
Create incoming SIPCall.
bool changeArchivePassword(const std::string &password_old, const std::string &password_new)
std::shared_ptr< TransferManager > dataTransfer(const std::string &id="")
Retrieve linked transfer manager.
std::map< std::string, std::string > getNearbyPeers() const override
Get current discovered peers account id and display name.
std::vector< std::map< std::string, std::string > > getConversationConnectivity(const std::string &conversationId)
bool exportArchive(const std::string &destinationPath, std::string_view scheme={}, const std::string &password={})
Export the archive to a file.
dhtnet::IceTransportOptions getIceOptions() const override
Create and return ICE options.
std::string getToUri(const std::string &username) const override
This method adds the correct scheme, hostname and append the ;transport= parameter at the end of the ...
void askForProfile(const std::string &conversationId, const std::string &deviceId, const std::string &memberUri)
void startAccountPublish()
Start Publish the Jami Account onto the Network.
void shutdownConnections()
This should be called before flushing the account.
static constexpr const std::pair< uint16_t, uint16_t > DHT_PORT_RANGE
Definition jamiaccount.h:96
bool setMessageDisplayed(const std::string &conversationUri, const std::string &messageId, int status) override
virtual bool isTlsEnabled() const override
Determine if TLS is enabled for this account.
void registerName(const std::string &name, const std::string &scheme, const std::string &password)
SyncModule * syncModule()
std::vector< std::map< std::string, std::string > > getContacts(bool includeRemoved=false) const
void flush() override
This method is called to request removal of possible account traces on the system,...
std::shared_ptr< JamiAccount > shared()
const std::shared_ptr< AccountManager > & accountManager()
bool isMessageTreated(dht::Value::Id id)
MatchRank matches(std::string_view username, std::string_view hostname) const override
std::string getUserUri() const override
void doUnregister(bool forceShutdownConnections=false) override
Disconnect from the DHT.
bool acceptTrustRequest(const std::string &from, bool includeConversation=true)
bool cancelAddDevice(uint32_t op_token)
void sendProfile(const std::string &convId, const std::string &peerUri, const std::string &deviceId)
Send Profile via cached SIP connection.
std::string getFromUri() const override
ConversationModule * convModule(bool noCreation=false)
Used to get the instance of the ConversationModule class which is responsible for managing conversati...
bool revokeDevice(const std::string &device, std::string_view scheme={}, const std::string &password={})
bool isValidAccountDevice(const dht::crypto::Certificate &cert) const
std::filesystem::path profilePath() const
bool searchUser(const std::string &nameQuery)
const dht::crypto::Identity & identity() const
void sendInstantMessage(const std::string &convId, const std::map< std::string, std::string > &msg)
bool findCertificate(const std::string &id)
bool isPasswordValid(const std::string &password)
std::string getServerUri() const
In the current version, "srv" uri is obtained in the preformated way: hostname:port.
void connectivityChanged() override
Inform the account that the network status has changed.
bool handleMessage(const std::shared_ptr< dht::crypto::Certificate > &cert, const std::string &from, const std::pair< std::string, std::string > &message) override
void transferFile(const std::string &conversationId, const std::string &path, const std::string &deviceId, const std::string &fileId, const std::string &interactionId, size_t start=0, size_t end=0, const std::string &sha3Sum="", uint64_t lastWriteTime=0, std::function< void()> onFinished={})
std::string_view getAccountType() const override
void handleIncomingConversationCall(const std::string &callId, const std::string &destination)
Join incoming call to hosted conference.
std::vector< libjami::Message > getLastMessages(const uint64_t &base_timestamp) override
Get last messages (should be used to retrieve messages when launching the client)
std::map< std::string, bool > getTrackedBuddyPresence() const
Tells for each tracked account id if it has been seen online so far in the last DeviceAnnouncement::T...
bool setValidity(std::string_view scheme, const std::string &pwd, const dht::InfoHash &id, int64_t validity)
Change certificate's validity period.
void updateProfile(const std::string &displayName, const std::string &avatar, const std::string &fileType, int32_t flag) override
Update the profile vcard and send it to peers.
bool setPushNotificationToken(const std::string &pushDeviceToken="") override
bool confirmAddDevice(uint32_t op_token)
void editConfig(std::function< void(JamiAccountConfig &conf)> &&edit)
void removeContact(const std::string &uri, bool banned=true)
bool isMobile() const
The DRT component is composed on some special nodes, that are usually present but not connected.
bool sha3SumVerify() const
int32_t addDevice(const std::string &uriProvided)
Initiates the process of adding a new device to this account.
void sendMessage(const std::string &to, const std::string &deviceId, const std::map< std::string, std::string > &payloads, uint64_t id, bool retryOnTimeout=true, bool onlyConnected=false) override
bool setPushNotificationTopic(const std::string &topic) override
void saveConfig() const override
void setIsComposing(const std::string &conversationUri, bool isWriting) override
std::vector< std::map< std::string, std::string > > getTrustRequests() const
void forEachDevice(const dht::InfoHash &to, std::function< void(const std::shared_ptr< dht::crypto::PublicKey > &)> &&op, std::function< void(bool)> &&end={})
void loadConversation(const std::string &convId)
std::unique_ptr< AccountConfig > buildConfig() const override
bool setCertificateStatus(const std::string &cert_id, dhtnet::tls::TrustStore::PermissionStatus status)
std::weak_ptr< JamiAccount > weak()
void onTextMessage(const std::string &id, const std::string &from, const std::shared_ptr< dht::crypto::Certificate > &peerCert, const std::map< std::string, std::string > &payloads) override
void setActiveCodecs(const std::vector< unsigned > &list) override
Update both the codec order structure and the codec string used for SDP offer and configuration respe...
void clearProfileCache(const std::string &peerUri)
Clear sent profiles (because of a removed contact or new trust request)
static constexpr auto ACCOUNT_TYPE
Definition jamiaccount.h:95
void loadConfig() override
Load the settings in this account.
uint64_t sendTextMessage(const std::string &to, const std::string &deviceId, const std::map< std::string, std::string > &payloads, uint64_t refreshToken=0, bool onlyConnected=false) override
If supported, send a text message from this account.
void lookupName(const std::string &name)
std::weak_ptr< JamiAccount const > weak() const
std::shared_ptr< JamiAccount const > shared() const
std::vector< uint8_t > getPasswordKey(const std::string &password)
std::string_view currentDeviceId() const
std::map< std::string, std::string > getContactDetails(const std::string &uri) const
Obtain details about one account contact in serializable form.
virtual std::map< std::string, std::string > getVolatileAccountDetails() const override
Retrieve volatile details such as recent registration errors.
dhtnet::tls::CertificateStore & certStore() const
void trackBuddyPresence(const std::string &buddy_id, bool track)
Adds an account id to the list of accounts to track on the DHT for buddy presence.
Definition Address.h:25
FixedHash< 20 > h160
Definition FixedHash.h:469
h160 Address
An Ethereum address: 20 bytes.
Definition Address.h:29
dht::PkId DeviceId
std::pair< std::string, DeviceId > SipConnectionKey
Definition jamiaccount.h:85
void emitSignal(Args... args)
Definition jami_signal.h:64
static constexpr const char MIME_TYPE_IM_COMPOSING[]
Definition jamiaccount.h:87
RegistrationState
Contains all the Registration states for an account can be in.
static constexpr std::string_view ACCOUNT_TYPE_JAMI
std::function< bool(const std::shared_ptr< dhtnet::ChannelSocket > &)> ChannelCb
std::chrono::steady_clock clock
Definition conference.h:181
static std::ostream & operator<<(std::ostream &os, const Account &acc)
Definition account.h:512
Simple macro to hide class' copy constructor and assignment operator.
#define NON_COPYABLE(ClassName)
Definition noncopyable.h:30
std::string deviceKey
Device push notification token.