Allow changing alias
diff --git a/src/addcontactpanel.cpp b/src/addcontactpanel.cpp
index 9d332a7..80675ea 100644
--- a/src/addcontactpanel.cpp
+++ b/src/addcontactpanel.cpp
@@ -36,8 +36,10 @@
this, SLOT(onCancelClicked()));
connect(ui->searchButton, SIGNAL(clicked()),
this, SLOT(onSearchClicked()));
- connect(&*m_contactManager, SIGNAL(contactFetched(const EndorseCertificate&>)),
- this, SLOT(selfEndorseCertificateFetched(const EndorseCertificate&>)));
+ connect(ui->addButton, SIGNAL(clicked()),
+ this, SLOT(onAddClicked()));
+ connect(&*m_contactManager, SIGNAL(contactFetched(const EndorseCertificate&)),
+ this, SLOT(selfEndorseCertificateFetched(const EndorseCertificate&)));
connect(&*m_contactManager, SIGNAL(contactFetchFailed(const ndn::Name&)),
this, SLOT(selfEndorseCertificateFetchFailed(const ndn::Name&)));
}
@@ -55,6 +57,9 @@
void
AddContactPanel::onSearchClicked()
{
+ ui->infoView->clear();
+ for(int i = ui->infoView->rowCount() - 1; i >= 0 ; i--)
+ ui->infoView->removeRow(i);
QString inputIdentity = ui->contactInput->text();
m_searchIdentity = Name(inputIdentity.toUtf8().constData());
@@ -64,12 +69,30 @@
void
AddContactPanel::onAddClicked()
{
+ ContactItem contactItem(*m_currentEndorseCertificate);
+ m_contactManager->getContactStorage()->addNormalContact(contactItem);
+ emit newContactAdded();
+ this->close();
}
void
AddContactPanel::selfEndorseCertificateFetched(const EndorseCertificate& endorseCertificate)
{
- _LOG_DEBUG("CALLED");
+ m_currentEndorseCertificate = Ptr<EndorseCertificate>(new EndorseCertificate(endorseCertificate));
+ const Profile& profile = endorseCertificate.getProfileData()->getProfile();
+ ui->infoView->setColumnCount(3);
+ Profile::const_iterator it = profile.begin();
+ int rowCount = 0;
+ for(; it != profile.end(); it++)
+ {
+ ui->infoView->insertRow(rowCount);
+ QTableWidgetItem *type = new QTableWidgetItem(QString::fromUtf8(it->first.c_str()));
+ ui->infoView->setItem(rowCount, 0, type);
+ string valueString(it->second.buf(), it->second.size());
+ QTableWidgetItem *value = new QTableWidgetItem(QString::fromUtf8(valueString.c_str()));
+ ui->infoView->setItem(rowCount, 1, value);
+ rowCount++;
+ }
}
void
diff --git a/src/addcontactpanel.h b/src/addcontactpanel.h
index f6776c0..1536464 100644
--- a/src/addcontactpanel.h
+++ b/src/addcontactpanel.h
@@ -17,6 +17,7 @@
#ifndef Q_MOC_RUN
#include "endorse-certificate.h"
+#include "profile.h"
#include "contact-manager.h"
#endif
@@ -54,11 +55,16 @@
void
selfEndorseCertificateFetchFailed(const ndn::Name& identity);
+signals:
+ void
+ newContactAdded();
+
private:
Ui::AddContactPanel *ui;
ndn::Name m_searchIdentity;
ndn::Ptr<ContactManager> m_contactManager;
WarningDialog* m_warningDialog;
+ ndn::Ptr<EndorseCertificate> m_currentEndorseCertificate;
};
#endif // ADDCONTACTPANEL_H
diff --git a/src/addcontactpanel.ui b/src/addcontactpanel.ui
index 99fd5e9..7974593 100644
--- a/src/addcontactpanel.ui
+++ b/src/addcontactpanel.ui
@@ -60,7 +60,11 @@
</layout>
</item>
<item>
- <widget class="QTableWidget" name="infoView"/>
+ <widget class="QTableWidget" name="infoView">
+ <attribute name="horizontalHeaderStretchLastSection">
+ <bool>true</bool>
+ </attribute>
+ </widget>
</item>
<item>
<layout class="QHBoxLayout" name="buttonLayout">
diff --git a/src/contact-item.cpp b/src/contact-item.cpp
index 08f4fa6..c14b328 100644
--- a/src/contact-item.cpp
+++ b/src/contact-item.cpp
@@ -13,10 +13,14 @@
#include <ndn.cxx/fields/signature-sha256-with-rsa.h>
+#include "logging.h"
+
using namespace std;
using namespace ndn;
using namespace ndn::security;
+INIT_LOGGER("ContactItem");
+
ContactItem::ContactItem(const EndorseCertificate& selfEndorseCertificate,
const string& alias)
: m_selfEndorseCertificate(selfEndorseCertificate)
@@ -24,8 +28,31 @@
Name endorsedkeyName = selfEndorseCertificate.getPublicKeyName();
Ptr<const signature::Sha256WithRsa> endorseSig = boost::dynamic_pointer_cast<const signature::Sha256WithRsa>(selfEndorseCertificate.getSignature());
const Name& signingKeyName = endorseSig->getKeyLocator().getKeyName();
+
+ int i = 0;
+ int j = -1;
+ string keyString("KEY");
+ string idString("ID-CERT");
+ for(; i < signingKeyName.size(); i++)
+ {
+ if(keyString == signingKeyName.get(i).toUri())
+ j = i;
+ if(idString == signingKeyName.get(i).toUri())
+ break;
+ }
- if(endorsedkeyName != signingKeyName)
+ if(i >= signingKeyName.size() || j < 0)
+ throw LnException("Wrong name!");
+
+ Name subName = signingKeyName.getSubName(0, j);
+ subName.append(signingKeyName.getSubName(j+1, i-j-1));
+
+
+
+ // _LOG_DEBUG("endorsedkeyName " << endorsedkeyName.toUri());
+ // _LOG_DEBUG("subKeyName " << subName.toUri());
+
+ if(endorsedkeyName != subName)
throw LnException("not a self-claimed");
m_namespace = endorsedkeyName.getSubName(0, endorsedkeyName.size() - 1);
diff --git a/src/contact-manager.cpp b/src/contact-manager.cpp
index 01168a0..9b7d7a3 100644
--- a/src/contact-manager.cpp
+++ b/src/contact-manager.cpp
@@ -157,6 +157,20 @@
}
}
+vector<Ptr<ContactItem> >
+ContactManager::getContactItemList()
+{
+ vector<Ptr<ContactItem> > result;
+
+ vector<Ptr<ContactItem> > ncList = m_contactStorage->getAllNormalContacts();
+ vector<Ptr<TrustedContact> > tcList = m_contactStorage->getAllTrustedContacts();
+
+ result.insert(result.end(), tcList.begin(), tcList.end());
+ result.insert(result.end(), ncList.begin(), ncList.end());
+
+ return result;
+}
+
Ptr<EndorseCertificate>
ContactManager::getSignedSelfEndorseCertificate(const Name& identity,
const Profile& profile)
@@ -203,6 +217,11 @@
if(security::PolicyManager::verifySignature(*plainData, ksk))
{
+ // Profile profile = selfEndorseCertificate->getProfileData()->getProfile();
+ // Profile::const_iterator it = profile.getEntries().begin();
+ // it++;
+ // _LOG_DEBUG("Entry Size: " << it->first);
+
emit contactFetched (*selfEndorseCertificate);
}
else
diff --git a/src/contact-manager.h b/src/contact-manager.h
index 42fd847..666cf9b 100644
--- a/src/contact-manager.h
+++ b/src/contact-manager.h
@@ -17,6 +17,7 @@
#include "contact-storage.h"
#include "dns-storage.h"
#include "endorse-certificate.h"
+#include "profile.h"
#include <ndn.cxx/wrapper/wrapper.h>
#endif
@@ -38,6 +39,9 @@
void
updateProfileData(const ndn::Name& identity);
+ std::vector<ndn::Ptr<ContactItem> >
+ getContactItemList();
+
inline ndn::Ptr<ContactStorage>
getContactStorage()
{ return m_contactStorage; }
@@ -75,7 +79,7 @@
signals:
void
- contactFetched(const EndorseCertificate& selfEndorseCertificate);
+ contactFetched(const EndorseCertificate& endorseCertificate);
void
contactFetchFailed(const ndn::Name& identity);
diff --git a/src/contact-storage.cpp b/src/contact-storage.cpp
index 5c6dc31..24c322e 100644
--- a/src/contact-storage.cpp
+++ b/src/contact-storage.cpp
@@ -200,14 +200,16 @@
Ptr<Profile>
ContactStorage::getSelfProfile(const Name& identity)
{
+ _LOG_DEBUG("getSelfProfile " << identity.toUri());
sqlite3_stmt *stmt;
Ptr<Profile> profile = Ptr<Profile>(new Profile(identity));
- sqlite3_prepare_v2(m_db, "SELECT profile_type, profile_value FROM SelfProfile WHERE profile_identity=", -1, &stmt, 0);
+ sqlite3_prepare_v2(m_db, "SELECT profile_type, profile_value FROM SelfProfile WHERE profile_identity=?", -1, &stmt, 0);
sqlite3_bind_text(stmt, 1, identity.toUri().c_str(), identity.toUri().size(), SQLITE_TRANSIENT);
-
- while( sqlite3_step (stmt) == SQLITE_ROW)
+
+ while(sqlite3_step (stmt) == SQLITE_ROW)
{
+ _LOG_DEBUG("entry");
string profileType(reinterpret_cast<const char *>(sqlite3_column_text(stmt, 0)), sqlite3_column_bytes (stmt, 0));
Blob profileValue(reinterpret_cast<const char *>(sqlite3_column_text(stmt, 1)), sqlite3_column_bytes (stmt, 1));
@@ -260,9 +262,35 @@
sqlite3_bind_text(stmt, 3, selfCertificateBlob->buf(), selfCertificateBlob->size(), SQLITE_TRANSIENT);
int res = sqlite3_step (stmt);
+ // _LOG_DEBUG("res " << res);
sqlite3_finalize (stmt);
}
+void
+ContactStorage::updateAlias(const ndn::Name& identity, std::string alias)
+{
+ if(doesNormalContactExist(identity))
+ {
+ sqlite3_stmt *stmt;
+ sqlite3_prepare_v2 (m_db, "UPDATE NormalContact SET contact_alias=? WHERE contact_namespace=?", -1, &stmt, 0);
+ sqlite3_bind_text(stmt, 1, alias.c_str(), alias.size(), SQLITE_TRANSIENT);
+ sqlite3_bind_text(stmt, 2, identity.toUri().c_str(), identity.toUri().size (), SQLITE_TRANSIENT);
+ int res = sqlite3_step (stmt);
+ sqlite3_finalize (stmt);
+ return;
+ }
+ if(doesTrustedContactExist(identity))
+ {
+ sqlite3_stmt *stmt;
+ sqlite3_prepare_v2 (m_db, "UPDATE TrustedContact SET contact_alias=? WHERE contact_namespace=?", -1, &stmt, 0);
+ sqlite3_bind_text(stmt, 1, alias.c_str(), alias.size(), SQLITE_TRANSIENT);
+ sqlite3_bind_text(stmt, 2, identity.toUri().c_str(), identity.toUri().size (), SQLITE_TRANSIENT);
+ int res = sqlite3_step (stmt);
+ sqlite3_finalize (stmt);
+ return;
+ }
+}
+
bool
ContactStorage::doesContactExist(const Name& name, bool normal)
{
diff --git a/src/contact-storage.h b/src/contact-storage.h
index 3275c40..e08790e 100644
--- a/src/contact-storage.h
+++ b/src/contact-storage.h
@@ -40,6 +40,9 @@
void
addNormalContact(const ContactItem& contactItem);
+ void
+ updateAlias(const ndn::Name& identity, std::string alias);
+
std::vector<ndn::Ptr<TrustedContact> >
getAllTrustedContacts() const;
diff --git a/src/contactpanel.cpp b/src/contactpanel.cpp
index abfbb08..5128105 100644
--- a/src/contactpanel.cpp
+++ b/src/contactpanel.cpp
@@ -25,6 +25,7 @@
namespace fs = boost::filesystem;
using namespace ndn;
+using namespace std;
INIT_LOGGER("ContactPanel");
@@ -34,6 +35,9 @@
, m_contactManager(contactManager)
, m_contactListModel(new QStringListModel)
, m_addContactPanel(new AddContactPanel(contactManager))
+ , m_setAliasDialog(new SetAliasDialog(contactManager))
+ , m_menuInvite(new QAction("&Invite", this))
+ , m_menuAlias(new QAction("&Set Alias", this))
{
ui->setupUi(this);
@@ -46,21 +50,28 @@
m_profileEditor = new ProfileEditor(m_contactManager);
- QStringList contactNameList;
- contactNameList << "Alex" << "Wentao" << "Yingdi";
-
- m_contactListModel->setStringList(contactNameList);
+ refreshContactList();
ui->ContactList->setModel(m_contactListModel);
QItemSelectionModel* selectionModel = ui->ContactList->selectionModel();
connect(selectionModel, SIGNAL(selectionChanged(const QItemSelection &, const QItemSelection &)),
this, SLOT(updateSelection(const QItemSelection &, const QItemSelection &)));
+ connect(ui->ContactList, SIGNAL(customContextMenuRequested(const QPoint&)),
+ this, SLOT(showContextMenu(const QPoint&)));
connect(ui->EditProfileButton, SIGNAL(clicked()),
this, SLOT(openProfileEditor()));
connect(ui->AddContactButton, SIGNAL(clicked()),
this, SLOT(openAddContactPanel()));
+
+ connect(m_addContactPanel, SIGNAL(newContactAdded()),
+ this, SLOT(refreshContactList()));
+ connect(m_setAliasDialog, SIGNAL(aliasChanged()),
+ this, SLOT(refreshContactList()));
+
+
+
}
ContactPanel::~ContactPanel()
@@ -69,6 +80,8 @@
delete m_contactListModel;
delete m_profileEditor;
delete m_addContactPanel;
+
+ delete m_menuInvite;
}
void
@@ -77,7 +90,25 @@
{
QModelIndexList items = selected.indexes();
QString text = m_contactListModel->data(items.first(), Qt::DisplayRole).toString();
- ui->NameData->setText(text);
+ string alias = text.toUtf8().constData();
+
+ m_currentSelectedContact = alias;
+
+ int i = 0;
+ for(; i < m_contactList.size(); i++)
+ {
+ if(alias == m_contactList[i]->getAlias())
+ break;
+ }
+
+ QString name = QString::fromUtf8(m_contactList[i]->getName().c_str());
+ QString institution = QString::fromUtf8(m_contactList[i]->getInstitution().c_str());
+ QString nameSpace = QString::fromUtf8(m_contactList[i]->getNameSpace().toUri().c_str());
+ ui->NameData->setText(name);
+ ui->NameSpaceData->setText(nameSpace);
+ ui->InstitutionData->setText(institution);
+
+ // _LOG_DEBUG("current Alias: " << m_currentSelectedContact);
}
void
@@ -88,6 +119,36 @@
ContactPanel::openAddContactPanel()
{ m_addContactPanel->show(); }
+void
+ContactPanel::refreshContactList()
+{
+ m_contactList = m_contactManager->getContactItemList();
+ QStringList contactNameList;
+ for(int i = 0; i < m_contactList.size(); i++)
+ contactNameList << QString::fromUtf8(m_contactList[i]->getAlias().c_str());
+
+ m_contactListModel->setStringList(contactNameList);
+}
+
+void
+ContactPanel::showContextMenu(const QPoint& pos)
+{
+ QMenu menu(ui->ContactList);
+ menu.addAction(m_menuInvite);
+ menu.addAction(m_menuAlias);
+ connect(m_menuAlias, SIGNAL(triggered()),
+ this, SLOT(openSetAliasDialog()));
+ menu.exec(ui->ContactList->mapToGlobal(pos));
+
+}
+
+void
+ContactPanel::openSetAliasDialog()
+{
+ m_setAliasDialog->setTargetIdentity(m_currentSelectedContact);
+ m_setAliasDialog->show();
+}
+
#if WAF
#include "contactpanel.moc"
#include "contactpanel.cpp.moc"
diff --git a/src/contactpanel.h b/src/contactpanel.h
index 5e20ee5..54c586b 100644
--- a/src/contactpanel.h
+++ b/src/contactpanel.h
@@ -14,9 +14,11 @@
#include <QDialog>
#include <QStringListModel>
#include <QtSql/QSqlDatabase>
+#include <QMenu>
#include "profileeditor.h"
#include "addcontactpanel.h"
+#include "setaliasdialog.h"
#ifndef Q_MOC_RUN
#include "contact-manager.h"
@@ -45,12 +47,29 @@
void
openAddContactPanel();
+ void
+ openSetAliasDialog();
+
+ void
+ refreshContactList();
+
+ void
+ showContextMenu(const QPoint& pos);
+
private:
Ui::ContactPanel *ui;
ndn::Ptr<ContactManager> m_contactManager;
QStringListModel* m_contactListModel;
ProfileEditor* m_profileEditor;
AddContactPanel* m_addContactPanel;
+ SetAliasDialog* m_setAliasDialog;
+ QAction* m_menuInvite;
+ QAction* m_menuAlias;
+
+
+ std::vector<ndn::Ptr<ContactItem> > m_contactList;
+
+ std::string m_currentSelectedContact;
};
#endif // CONTACTPANEL_H
diff --git a/src/contactpanel.ui b/src/contactpanel.ui
index 442fdae..6819ad0 100644
--- a/src/contactpanel.ui
+++ b/src/contactpanel.ui
@@ -43,7 +43,7 @@
<item>
<widget class="QListView" name="ContactList">
<property name="contextMenuPolicy">
- <enum>Qt::DefaultContextMenu</enum>
+ <enum>Qt::CustomContextMenu</enum>
</property>
<property name="acceptDrops">
<bool>false</bool>
diff --git a/src/profile.h b/src/profile.h
index 0f5a5cc..5c9ce24 100644
--- a/src/profile.h
+++ b/src/profile.h
@@ -65,6 +65,10 @@
static ndn::Ptr<Profile>
fromDerBlob(const ndn::Blob& derBlob);
+ inline const std::map<std::string, ndn::Blob>&
+ getEntries() const
+ { return m_entries; }
+
protected:
ndn::Name m_identityName;
std::map<std::string, ndn::Blob> m_entries;
diff --git a/src/setaliasdialog.cpp b/src/setaliasdialog.cpp
new file mode 100644
index 0000000..38e70d9
--- /dev/null
+++ b/src/setaliasdialog.cpp
@@ -0,0 +1,68 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
+/*
+ * Copyright (c) 2013, Regents of the University of California
+ * Yingdi Yu
+ *
+ * BSD license, See the LICENSE file for more information
+ *
+ * Author: Yingdi Yu <yingdi@cs.ucla.edu>
+ */
+
+#include "setaliasdialog.h"
+#include "ui_setaliasdialog.h"
+
+
+using namespace ndn;
+using namespace std;
+
+SetAliasDialog::SetAliasDialog(Ptr<ContactManager> contactManager,
+ QWidget *parent)
+ : QDialog(parent)
+ , ui(new Ui::SetAliasDialog)
+ , m_contactManager(contactManager)
+{
+ ui->setupUi(this);
+
+ connect(ui->okButton, SIGNAL(clicked()),
+ this, SLOT(onOkClicked()));
+ connect(ui->cancelButton, SIGNAL(clicked()),
+ this, SLOT(onCancelClicked()));
+}
+
+SetAliasDialog::~SetAliasDialog()
+{
+ delete ui;
+}
+
+void
+SetAliasDialog::onOkClicked()
+{
+ QString text = ui->aliasInput->text();
+ string alias = text.toUtf8().constData();
+
+ m_contactManager->getContactStorage()->updateAlias(Name(m_target), alias);
+
+ emit aliasChanged();
+
+ this->close();
+}
+
+void
+SetAliasDialog::onCancelClicked()
+{ this->close(); }
+
+void
+SetAliasDialog::setTargetIdentity(const string& name)
+{
+ m_target = name;
+ string msg("Set alias for ");
+ msg.append(name).append(":");
+ ui->introLabel->setText(QString::fromUtf8(msg.c_str()));
+ ui->aliasInput->clear();
+}
+
+
+#if WAF
+#include "setaliasdialog.moc"
+#include "setaliasdialog.cpp.moc"
+#endif
diff --git a/src/setaliasdialog.h b/src/setaliasdialog.h
new file mode 100644
index 0000000..1e24963
--- /dev/null
+++ b/src/setaliasdialog.h
@@ -0,0 +1,53 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
+/*
+ * Copyright (c) 2013, Regents of the University of California
+ * Yingdi Yu
+ *
+ * BSD license, See the LICENSE file for more information
+ *
+ * Author: Yingdi Yu <yingdi@cs.ucla.edu>
+ */
+
+#ifndef SETALIASDIALOG_H
+#define SETALIASDIALOG_H
+
+#include <QDialog>
+
+#ifndef Q_MOC_RUN
+#include "contact-manager.h"
+#endif
+
+namespace Ui {
+class SetAliasDialog;
+}
+
+class SetAliasDialog : public QDialog
+{
+ Q_OBJECT
+
+public:
+ explicit SetAliasDialog(ndn::Ptr<ContactManager> contactManager,
+ QWidget *parent = 0);
+ ~SetAliasDialog();
+
+ void
+ setTargetIdentity(const std::string& name);
+
+signals:
+ void
+ aliasChanged();
+
+private slots:
+ void
+ onOkClicked();
+
+ void
+ onCancelClicked();
+
+private:
+ Ui::SetAliasDialog *ui;
+ ndn::Ptr<ContactManager> m_contactManager;
+ std::string m_target;
+};
+
+#endif // SETALIASDIALOG_H
diff --git a/src/setaliasdialog.ui b/src/setaliasdialog.ui
new file mode 100644
index 0000000..3beeb3a
--- /dev/null
+++ b/src/setaliasdialog.ui
@@ -0,0 +1,71 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>SetAliasDialog</class>
+ <widget class="QDialog" name="SetAliasDialog">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>300</width>
+ <height>150</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Dialog</string>
+ </property>
+ <widget class="QLineEdit" name="aliasInput">
+ <property name="geometry">
+ <rect>
+ <x>20</x>
+ <y>60</y>
+ <width>260</width>
+ <height>21</height>
+ </rect>
+ </property>
+ </widget>
+ <widget class="QPushButton" name="okButton">
+ <property name="geometry">
+ <rect>
+ <x>180</x>
+ <y>100</y>
+ <width>100</width>
+ <height>32</height>
+ </rect>
+ </property>
+ <property name="text">
+ <string>OK</string>
+ </property>
+ </widget>
+ <widget class="QPushButton" name="cancelButton">
+ <property name="geometry">
+ <rect>
+ <x>20</x>
+ <y>100</y>
+ <width>100</width>
+ <height>32</height>
+ </rect>
+ </property>
+ <property name="text">
+ <string>Cancel</string>
+ </property>
+ </widget>
+ <widget class="QLabel" name="introLabel">
+ <property name="geometry">
+ <rect>
+ <x>20</x>
+ <y>20</y>
+ <width>260</width>
+ <height>30</height>
+ </rect>
+ </property>
+ <property name="text">
+ <string>TextLabel</string>
+ </property>
+ <property name="alignment">
+ <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set>
+ </property>
+ </widget>
+ </widget>
+ <resources/>
+ <connections/>
+</ui>