blob: a63f9f9dfa71f390587209ef170acbeafe1b6c2c [file] [log] [blame]
Yingdi Yu9e0dc292013-10-10 11:39:45 -07001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
2/*
3 * Copyright (c) 2013, Regents of the University of California
4 * Yingdi Yu
5 *
6 * BSD license, See the LICENSE file for more information
7 *
8 * Author: Yingdi Yu <yingdi@cs.ucla.edu>
9 */
10
Yingdi Yudef90612013-10-09 22:34:42 -070011#include "contactpanel.h"
12#include "ui_contactpanel.h"
13
Yingdi Yu01a942b2013-10-10 15:00:58 -070014
15#include <QStringList>
16#include <QItemSelectionModel>
17#include <QModelIndex>
Yingdi Yu0a6b6c52013-10-15 17:54:00 -070018#include <QDir>
Yingdi Yu8dacdf22013-11-05 23:06:43 -080019#include <QtSql/QSqlRecord>
20#include <QtSql/QSqlField>
21#include <QtSql/QSqlError>
Yingdi Yu01a942b2013-10-10 15:00:58 -070022
Yingdi Yu0a6b6c52013-10-15 17:54:00 -070023#ifndef Q_MOC_RUN
Yingdi Yu53eb8a72013-10-23 11:50:51 -070024#include <ndn.cxx/security/keychain.h>
Yingdi Yu53eb8a72013-10-23 11:50:51 -070025#include <ndn.cxx/security/identity/identity-manager.h>
Yingdi Yu100267f2013-10-21 15:01:40 -070026#include <ndn.cxx/common.h>
Yingdi Yu0a6b6c52013-10-15 17:54:00 -070027#include <boost/filesystem.hpp>
Yingdi Yu53eb8a72013-10-23 11:50:51 -070028#include <boost/random/random_device.hpp>
29#include <boost/random/uniform_int_distribution.hpp>
Yingdi Yu42f66462013-10-31 17:38:22 -070030#include "panel-policy-manager.h"
Yingdi Yu0a6b6c52013-10-15 17:54:00 -070031#include "logging.h"
32#include "exception.h"
33#endif
34
35namespace fs = boost::filesystem;
36using namespace ndn;
Yingdi Yu53eb8a72013-10-23 11:50:51 -070037
Yingdi Yu79c25a22013-10-21 13:38:38 -070038using namespace std;
Yingdi Yu0a6b6c52013-10-15 17:54:00 -070039
40INIT_LOGGER("ContactPanel");
41
Yingdi Yu53eb8a72013-10-23 11:50:51 -070042Q_DECLARE_METATYPE(ndn::security::IdentityCertificate)
Yingdi Yu42f66462013-10-31 17:38:22 -070043Q_DECLARE_METATYPE(ChronosInvitation)
Yingdi Yu53eb8a72013-10-23 11:50:51 -070044
Yingdi Yub29f78c2013-11-09 20:12:31 -080045ContactPanel::ContactPanel(QWidget *parent)
Yingdi Yua50c3252013-11-03 15:05:26 -080046 : QDialog(parent)
47 , ui(new Ui::ContactPanel)
Yingdi Yub29f78c2013-11-09 20:12:31 -080048 , m_warningDialog(new WarningDialog)
Yingdi Yua50c3252013-11-03 15:05:26 -080049 , m_contactListModel(new QStringListModel)
50 , m_startChatDialog(new StartChatDialog)
51 , m_invitationDialog(new InvitationDialog)
52 , m_settingDialog(new SettingDialog)
Yingdi Yudef90612013-10-09 22:34:42 -070053{
Yingdi Yu53eb8a72013-10-23 11:50:51 -070054 qRegisterMetaType<ndn::security::IdentityCertificate>("IdentityCertificate");
Yingdi Yu42f66462013-10-31 17:38:22 -070055 qRegisterMetaType<ChronosInvitation>("ChronosInvitation");
Yingdi Yu0a6b6c52013-10-15 17:54:00 -070056
Yingdi Yu42372442013-11-06 18:43:31 -080057 createAction();
58
Yingdi Yub29f78c2013-11-09 20:12:31 -080059 m_contactManager = Ptr<ContactManager>::Create();
Yingdi Yub35b8652013-11-07 11:32:40 -080060
Yingdi Yub29f78c2013-11-09 20:12:31 -080061 connect(&*m_contactManager, SIGNAL(noNdnConnection(const QString&)),
62 this, SLOT(showError(const QString&)));
63
64 m_contactManager->setWrapper();
65
Yingdi Yub35b8652013-11-07 11:32:40 -080066 openDB();
Yingdi Yu42372442013-11-06 18:43:31 -080067
Yingdi Yuc4d08d22013-10-23 23:07:29 -070068 refreshContactList();
Yingdi Yu01a942b2013-10-10 15:00:58 -070069
Yingdi Yuc4d08d22013-10-23 23:07:29 -070070 setKeychain();
Yingdi Yu42372442013-11-06 18:43:31 -080071
72 m_defaultIdentity = m_keychain->getDefaultIdentity();
Yingdi Yu908f8412013-11-09 00:03:26 -080073 m_contactManager->setDefaultIdentity(m_defaultIdentity);
Yingdi Yu42372442013-11-06 18:43:31 -080074 m_nickName = m_defaultIdentity.get(-1).toUri();
75 m_settingDialog->setIdentity(m_defaultIdentity.toUri(), m_nickName);
76
Yingdi Yub35b8652013-11-07 11:32:40 -080077 m_profileEditor = new ProfileEditor(m_contactManager);
78 m_profileEditor->setCurrentIdentity(m_defaultIdentity);
79
Yingdi Yub29f78c2013-11-09 20:12:31 -080080 m_addContactPanel = new AddContactPanel(m_contactManager);
81 m_browseContactDialog = new BrowseContactDialog(m_contactManager);
82 m_setAliasDialog = new SetAliasDialog(m_contactManager);
Yingdi Yub35b8652013-11-07 11:32:40 -080083
84 ui->setupUi(this);
85
Yingdi Yub29f78c2013-11-09 20:12:31 -080086 try{
87 m_handler = Ptr<Wrapper>(new Wrapper(m_keychain));
88 }catch(ndn::Error::ndnOperation& e){
89 showError(QString::fromStdString("Cannot conect to ndnd!\n Have you started your ndnd?"));
90 }
91
Yingdi Yu42372442013-11-06 18:43:31 -080092
Yingdi Yuc4d08d22013-10-23 23:07:29 -070093 setLocalPrefix();
Yingdi Yu53eb8a72013-10-23 11:50:51 -070094
Yingdi Yuc4d08d22013-10-23 23:07:29 -070095 setInvitationListener();
Yingdi Yu42372442013-11-06 18:43:31 -080096
Yingdi Yu8dacdf22013-11-05 23:06:43 -080097 collectEndorsement();
Yingdi Yuc4d08d22013-10-23 23:07:29 -070098
99 ui->ContactList->setModel(m_contactListModel);
100
Yingdi Yuc26af3c2013-10-17 17:03:46 -0700101
Yingdi Yu42372442013-11-06 18:43:31 -0800102 connect(ui->ContactList->selectionModel(), SIGNAL(selectionChanged(const QItemSelection &, const QItemSelection &)),
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700103 this, SLOT(updateSelection(const QItemSelection &, const QItemSelection &)));
Yingdi Yu01a942b2013-10-10 15:00:58 -0700104
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700105 connect(ui->ContactList, SIGNAL(customContextMenuRequested(const QPoint&)),
106 this, SLOT(showContextMenu(const QPoint&)));
Yingdi Yud59b5932013-10-16 13:16:49 -0700107
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700108 connect(ui->EditProfileButton, SIGNAL(clicked()),
109 this, SLOT(openProfileEditor()));
Yingdi Yud59b5932013-10-16 13:16:49 -0700110
Yingdi Yu908f8412013-11-09 00:03:26 -0800111 // connect(ui->AddContactButton, SIGNAL(clicked()),
112 // this, SLOT(openAddContactPanel()));
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700113 connect(ui->AddContactButton, SIGNAL(clicked()),
Yingdi Yu908f8412013-11-09 00:03:26 -0800114 this, SLOT(openBrowseContactDialog()));
115
116 connect(this, SIGNAL(refreshCertDirectory()),
117 m_browseContactDialog, SLOT(refreshList()));
118
119 connect(ui->DeleteContactButton, SIGNAL(clicked()),
120 this, SLOT(removeContactButton()));
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700121
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700122 connect(ui->settingButton, SIGNAL(clicked()),
123 this, SLOT(openSettingDialog()));
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700124
Yingdi Yu908f8412013-11-09 00:03:26 -0800125 connect(m_browseContactDialog, SIGNAL(newContactAdded()),
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700126 this, SLOT(refreshContactList()));
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700127 connect(m_setAliasDialog, SIGNAL(aliasChanged()),
128 this, SLOT(refreshContactList()));
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700129
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700130 connect(m_startChatDialog, SIGNAL(chatroomConfirmed(const QString&, const QString&, bool)),
131 this, SLOT(startChatroom(const QString&, const QString&, bool)));
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700132
Yingdi Yu42f66462013-10-31 17:38:22 -0700133 connect(m_invitationDialog, SIGNAL(invitationAccepted(const ChronosInvitation&, const ndn::security::IdentityCertificate&)),
134 this, SLOT(acceptInvitation(const ChronosInvitation&, const ndn::security::IdentityCertificate&)));
135 connect(m_invitationDialog, SIGNAL(invitationRejected(const ChronosInvitation&)),
136 this, SLOT(rejectInvitation(const ChronosInvitation&)));
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700137
Yingdi Yu42372442013-11-06 18:43:31 -0800138 connect(m_settingDialog, SIGNAL(identitySet(const QString&, const QString&)),
139 this, SLOT(updateDefaultIdentity(const QString&, const QString&)));
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700140
141 connect(this, SIGNAL(newInvitationReady()),
142 this, SLOT(openInvitationDialog()));
Yingdi Yu100267f2013-10-21 15:01:40 -0700143
Yingdi Yua50c3252013-11-03 15:05:26 -0800144 connect(ui->isIntroducer, SIGNAL(stateChanged(int)),
145 this, SLOT(isIntroducerChanged(int)));
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800146
147 connect(ui->addScope, SIGNAL(clicked()),
148 this, SLOT(addScopeClicked()));
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800149 connect(ui->deleteScope, SIGNAL(clicked()),
150 this, SLOT(deleteScopeClicked()));
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800151 connect(ui->saveButton, SIGNAL(clicked()),
152 this, SLOT(saveScopeClicked()));
153
154 connect(ui->endorseButton, SIGNAL(clicked()),
155 this, SLOT(endorseButtonClicked()));
Yingdi Yudef90612013-10-09 22:34:42 -0700156}
157
158ContactPanel::~ContactPanel()
159{
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700160 delete ui;
161 delete m_contactListModel;
Yingdi Yu42372442013-11-06 18:43:31 -0800162 delete m_startChatDialog;
163 delete m_invitationDialog;
164 delete m_settingDialog;
165
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700166 delete m_profileEditor;
167 delete m_addContactPanel;
Yingdi Yu908f8412013-11-09 00:03:26 -0800168 delete m_browseContactDialog;
Yingdi Yu42372442013-11-06 18:43:31 -0800169 delete m_setAliasDialog;
170
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800171 delete m_trustScopeModel;
172 delete m_endorseDataModel;
Yingdi Yu42372442013-11-06 18:43:31 -0800173 delete m_endorseComboBoxDelegate;
Yingdi Yu79c25a22013-10-21 13:38:38 -0700174
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700175 delete m_menuInvite;
Yingdi Yu42372442013-11-06 18:43:31 -0800176 delete m_menuAlias;
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700177
178 map<Name, ChatDialog*>::iterator it = m_chatDialogs.begin();
179 for(; it != m_chatDialogs.end(); it++)
180 delete it->second;
Yingdi Yudef90612013-10-09 22:34:42 -0700181}
Yingdi Yu9e0dc292013-10-10 11:39:45 -0700182
Yingdi Yu01a942b2013-10-10 15:00:58 -0700183void
Yingdi Yu42372442013-11-06 18:43:31 -0800184ContactPanel::createAction()
185{
186 m_menuInvite = new QAction("&Chat", this);
187 m_menuAlias = new QAction("&Set Alias", this);
188}
189
190void
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700191ContactPanel::openDB()
192{
193 QSqlDatabase db = QSqlDatabase::addDatabase("QSQLITE");
194 QString path = (QDir::home().path());
195 path.append(QDir::separator()).append(".chronos").append(QDir::separator()).append("chronos.db");
196 db.setDatabaseName(path);
197 bool ok = db.open();
Yingdi Yu42372442013-11-06 18:43:31 -0800198 _LOG_DEBUG("DB opened: " << std::boolalpha << ok );
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800199
200 m_trustScopeModel = new QSqlTableModel;
201 m_endorseDataModel = new QSqlTableModel;
202 m_endorseComboBoxDelegate = new EndorseComboBoxDelegate;
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700203}
204
205void
206ContactPanel::setKeychain()
207{
Yingdi Yued8cfc42013-11-01 17:37:51 -0700208 m_panelPolicyManager = Ptr<PanelPolicyManager>::Create();
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700209
210 vector<Ptr<ContactItem> >::const_iterator it = m_contactList.begin();
211 for(; it != m_contactList.end(); it++)
Yingdi Yub35b8652013-11-07 11:32:40 -0800212 {
213 m_panelPolicyManager->addTrustAnchor((*it)->getSelfEndorseCertificate());
214 }
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700215
Yingdi Yued8cfc42013-11-01 17:37:51 -0700216 m_keychain = Ptr<security::Keychain>(new security::Keychain(Ptr<security::IdentityManager>::Create(),
217 m_panelPolicyManager,
218 NULL));
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700219}
220
221void
222ContactPanel::setLocalPrefix()
223{
224 Ptr<Interest> interest = Ptr<Interest>(new Interest(Name("/local/ndn/prefix")));
225 interest->setChildSelector(Interest::CHILD_RIGHT);
226
227 Ptr<Closure> closure = Ptr<Closure>(new Closure(boost::bind(&ContactPanel::onLocalPrefixVerified,
228 this,
229 _1),
230 boost::bind(&ContactPanel::onLocalPrefixTimeout,
231 this,
232 _1,
233 _2),
234 boost::bind(&ContactPanel::onLocalPrefixVerified,
235 this,
236 _1)));
237
238 m_handler->sendInterest(interest, closure);
239}
240
241void
242ContactPanel::onLocalPrefixVerified(Ptr<Data> data)
243{
244 string originPrefix(data->content().buf(), data->content().size());
245 string prefix = QString::fromStdString (originPrefix).trimmed ().toUtf8().constData();
246 string randomSuffix = getRandomString();
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700247 m_localPrefix = Name(prefix);
248}
249
250void
251ContactPanel::onLocalPrefixTimeout(Ptr<Closure> closure, Ptr<Interest> interest)
Yingdi Yu42f66462013-10-31 17:38:22 -0700252{
253 string randomSuffix = getRandomString();
254 m_localPrefix = Name("/private/local");
Yingdi Yu42f66462013-10-31 17:38:22 -0700255}
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700256
257void
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700258ContactPanel::setInvitationListener()
259{
Yingdi Yu42372442013-11-06 18:43:31 -0800260 m_inviteListenPrefix = Name("/ndn/broadcast/chronos/invitation");
261 m_inviteListenPrefix.append(m_defaultIdentity);
262 _LOG_DEBUG("Listening for invitation on prefix: " << m_inviteListenPrefix.toUri());
263 m_handler->setInterestFilter (m_inviteListenPrefix,
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700264 boost::bind(&ContactPanel::onInvitation,
265 this,
266 _1));
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700267}
268
269void
270ContactPanel::onInvitation(Ptr<Interest> interest)
271{
Yingdi Yu42372442013-11-06 18:43:31 -0800272 _LOG_DEBUG("Receive invitation!" << interest->getName().toUri());
Yingdi Yub35b8652013-11-07 11:32:40 -0800273
274 Ptr<ChronosInvitation> invitation = NULL;
275 try{
276 invitation = Ptr<ChronosInvitation>(new ChronosInvitation(interest->getName()));
277 }catch(exception& e){
278 _LOG_ERROR("Exception: " << e.what());
279 return;
280 }
281
Yingdi Yu42372442013-11-06 18:43:31 -0800282 Name chatroomName("/ndn/broadcast/chronos");
283 chatroomName.append(invitation->getChatroom());
284 map<Name, ChatDialog*>::iterator it = m_chatDialogs.find(chatroomName);
285 if(it != m_chatDialogs.end())
286 {
Yingdi Yub35b8652013-11-07 11:32:40 -0800287 _LOG_ERROR("Exisiting chatroom!");
Yingdi Yu42372442013-11-06 18:43:31 -0800288 return;
289 }
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700290
Yingdi Yued8cfc42013-11-01 17:37:51 -0700291 Ptr<Interest> newInterest = Ptr<Interest>(new Interest(invitation->getInviterCertificateName()));
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700292 Ptr<Closure> closure = Ptr<Closure>(new Closure(boost::bind(&ContactPanel::onInvitationCertVerified,
293 this,
294 _1,
Yingdi Yued8cfc42013-11-01 17:37:51 -0700295 invitation),
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700296 boost::bind(&ContactPanel::onTimeout,
297 this,
298 _1,
299 _2),
300 boost::bind(&ContactPanel::onUnverified,
301 this,
302 _1)));
303 m_handler->sendInterest(newInterest, closure);
304}
305
306void
Yingdi Yu42372442013-11-06 18:43:31 -0800307ContactPanel::onInvitationCertVerified(Ptr<Data> data,
308 Ptr<ChronosInvitation> invitation)
309{
310 using namespace ndn::security;
311 Ptr<IdentityCertificate> certificate = Ptr<IdentityCertificate>(new IdentityCertificate(*data));
312
313 if(PolicyManager::verifySignature(invitation->getSignedBlob(), invitation->getSignatureBits(), certificate->getPublicKeyInfo()))
314 {
315 Name keyName = certificate->getPublicKeyName();
316 Name inviterNameSpace = keyName.getPrefix(keyName.size() - 1);
317 popChatInvitation(invitation, inviterNameSpace, certificate);
318 }
319}
320
321void
322ContactPanel::onUnverified(Ptr<Data> data)
323{}
324
325void
326ContactPanel::onTimeout(Ptr<Closure> closure, Ptr<Interest> interest)
327{}
328
329void
330ContactPanel::popChatInvitation(Ptr<ChronosInvitation> invitation,
331 const Name& inviterNameSpace,
332 Ptr<security::IdentityCertificate> certificate)
333{
334 string alias;
335 vector<Ptr<ContactItem> >::iterator it = m_contactList.begin();
336 for(; it != m_contactList.end(); it++)
337 if((*it)->getNameSpace() == inviterNameSpace)
338 alias = (*it)->getAlias();
339
340 if(it != m_contactList.end())
341 return;
342
343 m_invitationDialog->setInvitation(alias, invitation, certificate);
344 emit newInvitationReady();
345}
346
347void
348ContactPanel::collectEndorsement()
349{
350 m_collectStatus = Ptr<vector<bool> >::Create();
351 m_collectStatus->assign(m_contactList.size(), false);
352
353 vector<Ptr<ContactItem> >::iterator it = m_contactList.begin();
354 int count = 0;
355 for(; it != m_contactList.end(); it++, count++)
356 {
357 Name interestName = (*it)->getNameSpace();
358 interestName.append("DNS").append(m_defaultIdentity).append("ENDORSEE");
359 Ptr<Interest> interest = Ptr<Interest>(new Interest(interestName));
360 interest->setChildSelector(Interest::CHILD_RIGHT);
361 interest->setInterestLifetime(1);
362
363 Ptr<Closure> closure = Ptr<Closure>(new Closure(boost::bind(&ContactPanel::onDnsEndorseeVerified,
364 this,
365 _1,
366 count),
367 boost::bind(&ContactPanel::onDnsEndorseeTimeout,
368 this,
369 _1,
370 _2,
371 count),
372 boost::bind(&ContactPanel::onDnsEndorseeUnverified,
373 this,
374 _1,
375 count)));
376
377 m_handler->sendInterest(interest, closure);
378 }
379}
380
381void
382ContactPanel::onDnsEndorseeVerified(Ptr<Data> data, int count)
383{
384 Ptr<Blob> contentBlob = Ptr<Blob>(new Blob(data->content().buf(), data->content().size()));
385 Ptr<Data> endorseData = Data::decodeFromWire(contentBlob);
386 EndorseCertificate endorseCertificate(*endorseData);
387
388 m_contactManager->getContactStorage()->updateCollectEndorse(endorseCertificate);
389
390 updateCollectStatus(count);
391}
392
393void
394ContactPanel::onDnsEndorseeTimeout(Ptr<Closure> closure, Ptr<Interest> interest, int count)
395{ updateCollectStatus(count); }
396
397void
398ContactPanel::onDnsEndorseeUnverified(Ptr<Data> data, int count)
399{ updateCollectStatus(count); }
400
401void
402ContactPanel::updateCollectStatus(int count)
403{
404 m_collectStatus->at(count) = true;
405 vector<bool>::const_iterator it = m_collectStatus->begin();
406 for(; it != m_collectStatus->end(); it++)
407 if(*it == false)
408 return;
409
410 m_contactManager->publishEndorsedDataInDns(m_defaultIdentity);
411}
412
413static std::string chars("qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM0123456789");
414
415string
416ContactPanel::getRandomString()
417{
418 string randStr;
419 boost::random::random_device rng;
420 boost::random::uniform_int_distribution<> index_dist(0, chars.size() - 1);
421 for (int i = 0; i < 10; i ++)
422 {
423 randStr += chars[index_dist(rng)];
424 }
425 return randStr;
426}
427
428void
Yingdi Yub29f78c2013-11-09 20:12:31 -0800429ContactPanel::showError(const QString& msg){
430 QMessageBox::critical(this, tr("Chronos"), msg, QMessageBox::Ok);
431 exit(1);
432}
433
434void
Yingdi Yu01a942b2013-10-10 15:00:58 -0700435ContactPanel::updateSelection(const QItemSelection &selected,
436 const QItemSelection &deselected)
437{
438 QModelIndexList items = selected.indexes();
439 QString text = m_contactListModel->data(items.first(), Qt::DisplayRole).toString();
Yingdi Yu42372442013-11-06 18:43:31 -0800440 string alias = text.toStdString();
Yingdi Yu79c25a22013-10-21 13:38:38 -0700441
Yingdi Yu79c25a22013-10-21 13:38:38 -0700442 int i = 0;
443 for(; i < m_contactList.size(); i++)
444 {
445 if(alias == m_contactList[i]->getAlias())
446 break;
447 }
448
Yingdi Yua50c3252013-11-03 15:05:26 -0800449 m_currentSelectedContact = m_contactList[i];
Yingdi Yua0594092013-11-06 22:07:38 -0800450 ui->NameData->setText(QString::fromStdString(m_currentSelectedContact->getName()));
451 ui->NameSpaceData->setText(QString::fromStdString(m_currentSelectedContact->getNameSpace().toUri()));
452 ui->InstitutionData->setText(QString::fromStdString(m_currentSelectedContact->getInstitution()));
Yingdi Yu100267f2013-10-21 15:01:40 -0700453
Yingdi Yua50c3252013-11-03 15:05:26 -0800454 if(m_currentSelectedContact->isIntroducer())
455 {
456 ui->isIntroducer->setChecked(true);
457 ui->addScope->setEnabled(true);
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800458 ui->deleteScope->setEnabled(true);
459 ui->trustScopeList->setEnabled(true);
460
461 string filter("contact_namespace = '");
462 filter.append(m_currentSelectedContact->getNameSpace().toUri()).append("'");
463
464 m_trustScopeModel->setEditStrategy(QSqlTableModel::OnManualSubmit);
465 m_trustScopeModel->setTable("TrustScope");
466 m_trustScopeModel->setFilter(filter.c_str());
467 m_trustScopeModel->select();
468 m_trustScopeModel->setHeaderData(0, Qt::Horizontal, QObject::tr("ID"));
469 m_trustScopeModel->setHeaderData(1, Qt::Horizontal, QObject::tr("Contact"));
470 m_trustScopeModel->setHeaderData(2, Qt::Horizontal, QObject::tr("TrustScope"));
471
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800472 ui->trustScopeList->setModel(m_trustScopeModel);
473 ui->trustScopeList->setColumnHidden(0, true);
474 ui->trustScopeList->setColumnHidden(1, true);
475 ui->trustScopeList->show();
Yingdi Yua50c3252013-11-03 15:05:26 -0800476 }
477 else
478 {
479 ui->isIntroducer->setChecked(false);
480 ui->addScope->setEnabled(false);
481 ui->deleteScope->setEnabled(false);
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800482
483 string filter("contact_namespace = '");
484 filter.append(m_currentSelectedContact->getNameSpace().toUri()).append("'");
485
486 m_trustScopeModel->setEditStrategy(QSqlTableModel::OnManualSubmit);
487 m_trustScopeModel->setTable("TrustScope");
488 m_trustScopeModel->setFilter(filter.c_str());
489 m_trustScopeModel->select();
490 m_trustScopeModel->setHeaderData(0, Qt::Horizontal, QObject::tr("ID"));
491 m_trustScopeModel->setHeaderData(1, Qt::Horizontal, QObject::tr("Contact"));
492 m_trustScopeModel->setHeaderData(2, Qt::Horizontal, QObject::tr("TrustScope"));
493
494 ui->trustScopeList->setModel(m_trustScopeModel);
495 ui->trustScopeList->setColumnHidden(0, true);
496 ui->trustScopeList->setColumnHidden(1, true);
497 ui->trustScopeList->show();
498
499 ui->trustScopeList->setEnabled(false);
Yingdi Yua50c3252013-11-03 15:05:26 -0800500 }
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800501
502 string filter("profile_identity = '");
503 filter.append(m_currentSelectedContact->getNameSpace().toUri()).append("'");
504
505 m_endorseDataModel->setEditStrategy(QSqlTableModel::OnManualSubmit);
506 m_endorseDataModel->setTable("ContactProfile");
507 m_endorseDataModel->setFilter(filter.c_str());
508 m_endorseDataModel->select();
509
510 m_endorseDataModel->setHeaderData(0, Qt::Horizontal, QObject::tr("Identity"));
511 m_endorseDataModel->setHeaderData(1, Qt::Horizontal, QObject::tr("Type"));
512 m_endorseDataModel->setHeaderData(2, Qt::Horizontal, QObject::tr("Value"));
513 m_endorseDataModel->setHeaderData(3, Qt::Horizontal, QObject::tr("Endorse"));
514
515 ui->endorseList->setModel(m_endorseDataModel);
516 ui->endorseList->setColumnHidden(0, true);
517 ui->endorseList->resizeColumnToContents(1);
518 ui->endorseList->resizeColumnToContents(2);
519 ui->endorseList->setItemDelegateForColumn(3, m_endorseComboBoxDelegate);
520 ui->endorseList->show();
Yingdi Yu01a942b2013-10-10 15:00:58 -0700521}
Yingdi Yu9e0dc292013-10-10 11:39:45 -0700522
Yingdi Yu0a6b6c52013-10-15 17:54:00 -0700523void
Yingdi Yu42372442013-11-06 18:43:31 -0800524ContactPanel::updateDefaultIdentity(const QString& identity, const QString& nickName)
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700525{
Yingdi Yu42372442013-11-06 18:43:31 -0800526 m_defaultIdentity = Name(identity.toStdString());
Yingdi Yub35b8652013-11-07 11:32:40 -0800527 m_profileEditor->setCurrentIdentity(m_defaultIdentity);
Yingdi Yu42372442013-11-06 18:43:31 -0800528 m_nickName = nickName.toStdString();
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700529 m_handler->clearInterestFilter(m_inviteListenPrefix);
Yingdi Yu908f8412013-11-09 00:03:26 -0800530 m_contactManager->setDefaultIdentity(m_defaultIdentity);
Yingdi Yu42372442013-11-06 18:43:31 -0800531 setInvitationListener();
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800532 collectEndorsement();
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700533}
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700534
535void
Yingdi Yu0a6b6c52013-10-15 17:54:00 -0700536ContactPanel::openProfileEditor()
Yingdi Yud59b5932013-10-16 13:16:49 -0700537{ m_profileEditor->show(); }
Yingdi Yu0a6b6c52013-10-15 17:54:00 -0700538
Yingdi Yud59b5932013-10-16 13:16:49 -0700539void
540ContactPanel::openAddContactPanel()
541{ m_addContactPanel->show(); }
Yingdi Yu0a6b6c52013-10-15 17:54:00 -0700542
Yingdi Yu79c25a22013-10-21 13:38:38 -0700543void
Yingdi Yu908f8412013-11-09 00:03:26 -0800544ContactPanel::openBrowseContactDialog()
545{
546 m_browseContactDialog->show();
547 emit refreshCertDirectory();
548}
549
550void
551ContactPanel::removeContactButton()
552{
553 QItemSelectionModel* selectionModel = ui->ContactList->selectionModel();
554 QModelIndexList selectedList = selectionModel->selectedIndexes();
555 QModelIndexList::iterator it = selectedList.begin();
556 for(; it != selectedList.end(); it++)
557 {
558 string alias = m_contactListModel->data(*it, Qt::DisplayRole).toString().toStdString();
559 vector<Ptr<ContactItem> >::iterator contactIt = m_contactList.begin();
560 for(; contactIt != m_contactList.end(); contactIt++)
561 {
562 if((*contactIt)->getAlias() == alias)
563 {
564 m_contactManager->getContactStorage()->removeContact((*contactIt)->getNameSpace());
565 m_contactList.erase(contactIt);
566 break;
567 }
568 }
569 }
570 refreshContactList();
571}
572
573void
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700574ContactPanel::openInvitationDialog()
575{ m_invitationDialog->show(); }
576
577void
Yingdi Yu79c25a22013-10-21 13:38:38 -0700578ContactPanel::refreshContactList()
579{
580 m_contactList = m_contactManager->getContactItemList();
581 QStringList contactNameList;
582 for(int i = 0; i < m_contactList.size(); i++)
Yingdi Yua0594092013-11-06 22:07:38 -0800583 contactNameList << QString::fromStdString(m_contactList[i]->getAlias());
Yingdi Yu79c25a22013-10-21 13:38:38 -0700584
585 m_contactListModel->setStringList(contactNameList);
586}
587
588void
589ContactPanel::showContextMenu(const QPoint& pos)
590{
591 QMenu menu(ui->ContactList);
592 menu.addAction(m_menuInvite);
Yingdi Yu100267f2013-10-21 15:01:40 -0700593 connect(m_menuInvite, SIGNAL(triggered()),
594 this, SLOT(openStartChatDialog()));
Yingdi Yua0594092013-11-06 22:07:38 -0800595 menu.addSeparator();
Yingdi Yu79c25a22013-10-21 13:38:38 -0700596 menu.addAction(m_menuAlias);
597 connect(m_menuAlias, SIGNAL(triggered()),
598 this, SLOT(openSetAliasDialog()));
599 menu.exec(ui->ContactList->mapToGlobal(pos));
600
601}
602
603void
604ContactPanel::openSetAliasDialog()
605{
Yingdi Yua50c3252013-11-03 15:05:26 -0800606 m_setAliasDialog->setTargetIdentity(m_currentSelectedContact->getNameSpace().toUri());
Yingdi Yu79c25a22013-10-21 13:38:38 -0700607 m_setAliasDialog->show();
608}
609
Yingdi Yu100267f2013-10-21 15:01:40 -0700610void
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700611ContactPanel::openSettingDialog()
612{
Yingdi Yu42372442013-11-06 18:43:31 -0800613 m_settingDialog->setIdentity(m_defaultIdentity.toUri(), m_nickName);
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700614 m_settingDialog->show();
615}
616
617void
Yingdi Yu100267f2013-10-21 15:01:40 -0700618ContactPanel::openStartChatDialog()
619{
Yingdi Yu100267f2013-10-21 15:01:40 -0700620 Name chatroom("/ndn/broadcast/chronos");
Yingdi Yu42f66462013-10-31 17:38:22 -0700621 chatroom.append(string("chatroom-") + getRandomString());
Yingdi Yu100267f2013-10-21 15:01:40 -0700622
Yingdi Yua50c3252013-11-03 15:05:26 -0800623 m_startChatDialog->setInvitee(m_currentSelectedContact->getNameSpace().toUri(), chatroom.toUri());
Yingdi Yu100267f2013-10-21 15:01:40 -0700624 m_startChatDialog->show();
625}
626
Yingdi Yu42f66462013-10-31 17:38:22 -0700627// For inviter
Yingdi Yu100267f2013-10-21 15:01:40 -0700628void
629ContactPanel::startChatroom(const QString& chatroom, const QString& invitee, bool isIntroducer)
630{
Yingdi Yu42f66462013-10-31 17:38:22 -0700631 Name chatroomName(chatroom.toUtf8().constData());
Yingdi Yu6a5b9f62013-11-06 23:00:21 -0800632
633 Name inviteeNamespace(invitee.toStdString());
634 Ptr<ContactItem> inviteeItem = m_contactManager->getContact(inviteeNamespace);
635
Yingdi Yuc90deb12013-11-06 18:51:19 -0800636 ChatDialog* chatDialog = new ChatDialog(m_contactManager, chatroomName, m_localPrefix, m_defaultIdentity, m_nickName);
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700637 m_chatDialogs.insert(pair <Name, ChatDialog*> (chatroomName, chatDialog));
Yingdi Yu42372442013-11-06 18:43:31 -0800638
639 connect(chatDialog, SIGNAL(closeChatDialog(const ndn::Name&)),
640 this, SLOT(removeChatDialog(const ndn::Name&)));
Yingdi Yub29f78c2013-11-09 20:12:31 -0800641 connect(chatDialog, SIGNAL(noNdnConnection(const QString&)),
642 this, SLOT(showError(const QString&)));
Yingdi Yu42372442013-11-06 18:43:31 -0800643
Yingdi Yuc90deb12013-11-06 18:51:19 -0800644 // send invitation
Yingdi Yu42f66462013-10-31 17:38:22 -0700645 chatDialog->sendInvitation(inviteeItem, isIntroducer);
Yingdi Yuc4d08d22013-10-23 23:07:29 -0700646
647 chatDialog->show();
Yingdi Yu100267f2013-10-21 15:01:40 -0700648}
649
Yingdi Yu42f66462013-10-31 17:38:22 -0700650// For Invitee
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700651void
Yingdi Yu42f66462013-10-31 17:38:22 -0700652ContactPanel::startChatroom2(const ChronosInvitation& invitation,
653 const security::IdentityCertificate& identityCertificate)
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700654{
Yingdi Yu6a5b9f62013-11-06 23:00:21 -0800655 Ptr<ContactItem> inviterItem = m_contactManager->getContact(invitation.getInviterNameSpace());
656
Yingdi Yu42f66462013-10-31 17:38:22 -0700657 Name chatroomName("/ndn/broadcast/chronos");
658 chatroomName.append(invitation.getChatroom());
Yingdi Yu6a5b9f62013-11-06 23:00:21 -0800659
Yingdi Yuc90deb12013-11-06 18:51:19 -0800660 ChatDialog* chatDialog = new ChatDialog(m_contactManager, chatroomName, m_localPrefix, m_defaultIdentity, m_nickName, true);
Yingdi Yua0594092013-11-06 22:07:38 -0800661
Yingdi Yu42372442013-11-06 18:43:31 -0800662 connect(chatDialog, SIGNAL(closeChatDialog(const ndn::Name&)),
663 this, SLOT(removeChatDialog(const ndn::Name&)));
Yingdi Yub29f78c2013-11-09 20:12:31 -0800664 connect(chatDialog, SIGNAL(noNdnConnection(const QString&)),
665 this, SLOT(showError(const QString&)));
Yingdi Yu42f66462013-10-31 17:38:22 -0700666
Yingdi Yuc90deb12013-11-06 18:51:19 -0800667 chatDialog->addChatDataRule(invitation.getInviterPrefix(), identityCertificate, true);
Yingdi Yua0594092013-11-06 22:07:38 -0800668 chatDialog->publishIntroCert(identityCertificate, true);
Yingdi Yu42f66462013-10-31 17:38:22 -0700669
Yingdi Yu42f66462013-10-31 17:38:22 -0700670 chatDialog->addTrustAnchor(inviterItem->getSelfEndorseCertificate());
671
672 m_chatDialogs.insert(pair <Name, ChatDialog*> (chatroomName, chatDialog));
673
674 chatDialog->show();
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700675}
676
677void
Yingdi Yu42f66462013-10-31 17:38:22 -0700678ContactPanel::acceptInvitation(const ChronosInvitation& invitation,
679 const security::IdentityCertificate& identityCertificate)
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700680{
681 string prefix = m_localPrefix.toUri();
Yingdi Yu42f66462013-10-31 17:38:22 -0700682 m_handler->publishDataByIdentity (invitation.getInterestName(), prefix);
Yingdi Yu42f66462013-10-31 17:38:22 -0700683 startChatroom2(invitation, identityCertificate);
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700684}
685
686void
Yingdi Yu42f66462013-10-31 17:38:22 -0700687ContactPanel::rejectInvitation(const ChronosInvitation& invitation)
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700688{
Yingdi Yu97936352013-11-08 14:13:42 -0800689 string empty("nack");
Yingdi Yu42f66462013-10-31 17:38:22 -0700690 m_handler->publishDataByIdentity (invitation.getInterestName(), empty);
Yingdi Yu53eb8a72013-10-23 11:50:51 -0700691}
692
Yingdi Yua50c3252013-11-03 15:05:26 -0800693void
694ContactPanel::isIntroducerChanged(int state)
695{
696 if(state == Qt::Checked)
697 {
698 ui->addScope->setEnabled(true);
699 ui->deleteScope->setEnabled(true);
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800700 ui->trustScopeList->setEnabled(true);
701
702 string filter("contact_namespace = '");
703 filter.append(m_currentSelectedContact->getNameSpace().toUri()).append("'");
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800704
705 m_trustScopeModel->setEditStrategy(QSqlTableModel::OnManualSubmit);
706 m_trustScopeModel->setTable("TrustScope");
707 m_trustScopeModel->setFilter(filter.c_str());
708 m_trustScopeModel->select();
709 m_trustScopeModel->setHeaderData(0, Qt::Horizontal, QObject::tr("ID"));
710 m_trustScopeModel->setHeaderData(1, Qt::Horizontal, QObject::tr("Contact"));
711 m_trustScopeModel->setHeaderData(2, Qt::Horizontal, QObject::tr("TrustScope"));
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800712
713 ui->trustScopeList->setModel(m_trustScopeModel);
714 ui->trustScopeList->setColumnHidden(0, true);
715 ui->trustScopeList->setColumnHidden(1, true);
716 ui->trustScopeList->show();
717
718 m_currentSelectedContact->setIsIntroducer(true);
Yingdi Yua50c3252013-11-03 15:05:26 -0800719 }
720 else
721 {
Yingdi Yua50c3252013-11-03 15:05:26 -0800722 ui->addScope->setEnabled(false);
723 ui->deleteScope->setEnabled(false);
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800724
725 string filter("contact_namespace = '");
726 filter.append(m_currentSelectedContact->getNameSpace().toUri()).append("'");
727
728 m_trustScopeModel->setEditStrategy(QSqlTableModel::OnManualSubmit);
729 m_trustScopeModel->setTable("TrustScope");
730 m_trustScopeModel->setFilter(filter.c_str());
731 m_trustScopeModel->select();
732 m_trustScopeModel->setHeaderData(0, Qt::Horizontal, QObject::tr("ID"));
733 m_trustScopeModel->setHeaderData(1, Qt::Horizontal, QObject::tr("Contact"));
734 m_trustScopeModel->setHeaderData(2, Qt::Horizontal, QObject::tr("TrustScope"));
735
736 ui->trustScopeList->setModel(m_trustScopeModel);
737 ui->trustScopeList->setColumnHidden(0, true);
738 ui->trustScopeList->setColumnHidden(1, true);
739 ui->trustScopeList->show();
740
741 ui->trustScopeList->setEnabled(false);
742
743 m_currentSelectedContact->setIsIntroducer(false);
Yingdi Yua50c3252013-11-03 15:05:26 -0800744 }
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800745 m_contactManager->getContactStorage()->updateIsIntroducer(m_currentSelectedContact->getNameSpace(), m_currentSelectedContact->isIntroducer());
746}
747
748void
749ContactPanel::addScopeClicked()
750{
751 int rowCount = m_trustScopeModel->rowCount();
752 QSqlRecord record;
753 QSqlField identityField("contact_namespace", QVariant::String);
754 record.append(identityField);
755 record.setValue("contact_namespace", QString(m_currentSelectedContact->getNameSpace().toUri().c_str()));
756 m_trustScopeModel->insertRow(rowCount);
757 m_trustScopeModel->setRecord(rowCount, record);
758}
759
760void
761ContactPanel::deleteScopeClicked()
762{
763 QItemSelectionModel* selectionModel = ui->trustScopeList->selectionModel();
764 QModelIndexList indexList = selectionModel->selectedIndexes();
765
766 int i = indexList.size() - 1;
767 for(; i >= 0; i--)
768 m_trustScopeModel->removeRow(indexList[i].row());
769
770 m_trustScopeModel->submitAll();
771}
772
773void
774ContactPanel::saveScopeClicked()
Yingdi Yua0594092013-11-06 22:07:38 -0800775{ m_trustScopeModel->submitAll(); }
Yingdi Yu8dacdf22013-11-05 23:06:43 -0800776
777void
778ContactPanel::endorseButtonClicked()
779{
780 m_endorseDataModel->submitAll();
781 m_contactManager->updateEndorseCertificate(m_currentSelectedContact->getNameSpace(), m_defaultIdentity);
Yingdi Yua50c3252013-11-03 15:05:26 -0800782}
Yingdi Yu100267f2013-10-21 15:01:40 -0700783
Yingdi Yu42372442013-11-06 18:43:31 -0800784void
785ContactPanel::removeChatDialog(const ndn::Name& chatroomName)
786{
787 map<Name, ChatDialog*>::iterator it = m_chatDialogs.find(chatroomName);
Yingdi Yua0594092013-11-06 22:07:38 -0800788
789 ChatDialog* deletedChat = NULL;
Yingdi Yu42372442013-11-06 18:43:31 -0800790 if(it != m_chatDialogs.end())
791 {
Yingdi Yu42372442013-11-06 18:43:31 -0800792 deletedChat = it->second;
793 m_chatDialogs.erase(it);
794 }
Yingdi Yua0594092013-11-06 22:07:38 -0800795 if (deletedChat != NULL)
796 delete deletedChat;
Yingdi Yu42372442013-11-06 18:43:31 -0800797}
798
Yingdi Yu9e0dc292013-10-10 11:39:45 -0700799#if WAF
800#include "contactpanel.moc"
801#include "contactpanel.cpp.moc"
802#endif