Skip to content

Commit

Permalink
[auth] Add CAs to the connection for pkipkcs12
Browse files Browse the repository at this point in the history
  • Loading branch information
elpaso committed Oct 13, 2017
1 parent 7cb908a commit 7b7dad0
Show file tree
Hide file tree
Showing 4 changed files with 173 additions and 71 deletions.
47 changes: 47 additions & 0 deletions src/auth/pkipkcs12/qgsauthpkcs12edit.cpp
Expand Up @@ -36,6 +36,9 @@ QgsAuthPkcs12Edit::QgsAuthPkcs12Edit( QWidget *parent )
connect( lePkcs12KeyPass, &QLineEdit::textChanged, this, &QgsAuthPkcs12Edit::lePkcs12KeyPass_textChanged );
connect( chkPkcs12PassShow, &QCheckBox::stateChanged, this, &QgsAuthPkcs12Edit::chkPkcs12PassShow_stateChanged );
connect( btnPkcs12Bundle, &QToolButton::clicked, this, &QgsAuthPkcs12Edit::btnPkcs12Bundle_clicked );
lblCas->hide();
twCas->hide();
cbAddCas->hide();
}

bool QgsAuthPkcs12Edit::validateConfig()
Expand Down Expand Up @@ -108,14 +111,22 @@ bool QgsAuthPkcs12Edit::validateConfig()
tr( "%1 thru %2" ).arg( startdate.toString(), enddate.toString() ),
( bundlevalid ? Valid : Invalid ) );

bool showCas( bundlevalid && populateCas() );
lblCas->setVisible( showCas );
twCas->setVisible( showCas );
cbAddCas->setVisible( showCas );

return validityChange( bundlevalid );
}



QgsStringMap QgsAuthPkcs12Edit::configMap() const
{
QgsStringMap config;
config.insert( QStringLiteral( "bundlepath" ), lePkcs12Bundle->text() );
config.insert( QStringLiteral( "bundlepass" ), lePkcs12KeyPass->text() );
config.insert( QStringLiteral( "addcas" ), cbAddCas->isChecked() ? QStringLiteral( "true" ) : QStringLiteral( "false" ) );

return config;
}
Expand All @@ -127,6 +138,7 @@ void QgsAuthPkcs12Edit::loadConfig( const QgsStringMap &configmap )
mConfigMap = configmap;
lePkcs12Bundle->setText( configmap.value( QStringLiteral( "bundlepath" ) ) );
lePkcs12KeyPass->setText( configmap.value( QStringLiteral( "bundlepass" ) ) );
cbAddCas->setChecked( configmap.value( QStringLiteral( "addcas" ), QStringLiteral( "false " ) ) == QStringLiteral( "true" ) );

validateConfig();
}
Expand Down Expand Up @@ -218,3 +230,38 @@ bool QgsAuthPkcs12Edit::validityChange( bool curvalid )
}
return curvalid;
}

bool QgsAuthPkcs12Edit::populateCas()
{
twCas->clear();
const QList<QSslCertificate> cas( QgsAuthCertUtils::pkcs12BundleCas( lePkcs12Bundle->text(), lePkcs12KeyPass->text() ) );
if ( cas.isEmpty() )
{
return false;
}

QTreeWidgetItem *prevItem( nullptr );
QList<QSslCertificate>::const_iterator it( cas.constEnd() );
while ( it != cas.constBegin() )
{
--it;
const QSslCertificate cert = static_cast<QSslCertificate>( *it );
QTreeWidgetItem *item;

if ( prevItem && cert.issuerInfo( QSslCertificate::SubjectInfo::CommonName ).contains( prevItem->text( 0 ) ) )
{
item = new QTreeWidgetItem( QStringList( cert.subjectInfo( QSslCertificate::SubjectInfo::CommonName ) ) );
prevItem->addChild( item );
}
else
{
item = new QTreeWidgetItem( twCas, QStringList( cert.subjectInfo( QSslCertificate::SubjectInfo::CommonName ) ) );
}
item->setIcon( 0, QgsApplication::getThemeIcon( QStringLiteral( "/mIconCertificate.svg" ) ) );
item->setToolTip( 0, tr( "<ul><li>Serial #: %1</li><li>Expiry date: %2</li></ul>" ).arg( cert.serialNumber( ), cert.expiryDate().toString( Qt::TextDate ) ) );
prevItem = item;
}
twCas->expandAll();

return true;
}
2 changes: 2 additions & 0 deletions src/auth/pkipkcs12/qgsauthpkcs12edit.h
Expand Up @@ -64,6 +64,8 @@ class QgsAuthPkcs12Edit : public QgsAuthMethodEdit, private Ui::QgsAuthPkcs12Edi
private:
bool validityChange( bool curvalid );

bool populateCas( );

QgsStringMap mConfigMap;
bool mValid = 0;
};
Expand Down
168 changes: 99 additions & 69 deletions src/auth/pkipkcs12/qgsauthpkcs12edit.ui
Expand Up @@ -6,8 +6,8 @@
<rect>
<x>0</x>
<y>0</y>
<width>400</width>
<height>300</height>
<width>365</width>
<height>224</height>
</rect>
</property>
<layout class="QGridLayout" name="gridLayout">
Expand All @@ -23,69 +23,52 @@
<property name="bottomMargin">
<number>6</number>
</property>
<item row="1" column="1">
<layout class="QHBoxLayout" name="horizontalLayout_6">
<item>
<widget class="QLineEdit" name="lePkcs12KeyPass">
<property name="echoMode">
<enum>QLineEdit::Password</enum>
</property>
<property name="placeholderText">
<string>Optional passphrase</string>
</property>
</widget>
</item>
<item>
<widget class="QCheckBox" name="chkPkcs12PassShow">
<property name="sizePolicy">
<sizepolicy hsizetype="Maximum" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="text">
<string>Show</string>
</property>
</widget>
</item>
</layout>
</item>
<item row="0" column="1">
<layout class="QGridLayout" name="gridLayout_5">
<property name="spacing">
<number>0</number>
</property>
<item row="0" column="0">
<widget class="QLineEdit" name="lePkcs12Bundle">
<property name="readOnly">
<bool>true</bool>
</property>
<property name="placeholderText">
<string>Required</string>
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QToolButton" name="btnPkcs12Bundle">
<property name="text">
<string>…</string>
</property>
<property name="popupMode">
<enum>QToolButton::InstantPopup</enum>
</property>
</widget>
</item>
<item row="1" column="0" colspan="2">
<widget class="QLineEdit" name="lePkcs12Msg">
<property name="styleSheet">
<string notr="true">background-color: rgba(255, 255, 255, 0);</string>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
</layout>
<widget class="QLineEdit" name="lePkcs12Bundle">
<property name="readOnly">
<bool>true</bool>
</property>
<property name="placeholderText">
<string>Required</string>
</property>
</widget>
</item>
<item row="3" column="0">
<widget class="QLabel" name="lblPkcs12Key">
<property name="sizePolicy">
<sizepolicy hsizetype="Maximum" vsizetype="Preferred">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="text">
<string>Key</string>
</property>
</widget>
</item>
<item row="2" column="1">
<widget class="QTreeWidget" name="twCas">
<property name="editTriggers">
<set>QAbstractItemView::NoEditTriggers</set>
</property>
<property name="selectionMode">
<enum>QAbstractItemView::NoSelection</enum>
</property>
<property name="rootIsDecorated">
<bool>true</bool>
</property>
<property name="columnCount">
<number>1</number>
</property>
<attribute name="headerVisible">
<bool>false</bool>
</attribute>
<column>
<property name="text">
<string notr="true">1</string>
</property>
</column>
</widget>
</item>
<item row="0" column="0">
<widget class="QLabel" name="lblPkcs12Bundle">
Expand All @@ -100,20 +83,40 @@
</property>
</widget>
</item>
<item row="1" column="0">
<widget class="QLabel" name="lblPkcs12Key">
<item row="3" column="2">
<widget class="QCheckBox" name="chkPkcs12PassShow">
<property name="sizePolicy">
<sizepolicy hsizetype="Maximum" vsizetype="Preferred">
<sizepolicy hsizetype="Maximum" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="text">
<string>Key</string>
<string>Show</string>
</property>
</widget>
</item>
<item row="2" column="1">
<item row="0" column="2">
<widget class="QToolButton" name="btnPkcs12Bundle">
<property name="text">
<string>…</string>
</property>
<property name="popupMode">
<enum>QToolButton::InstantPopup</enum>
</property>
</widget>
</item>
<item row="3" column="1">
<widget class="QLineEdit" name="lePkcs12KeyPass">
<property name="echoMode">
<enum>QLineEdit::Password</enum>
</property>
<property name="placeholderText">
<string>Optional passphrase</string>
</property>
</widget>
</item>
<item row="4" column="1">
<spacer name="verticalSpacer">
<property name="orientation">
<enum>Qt::Vertical</enum>
Expand All @@ -126,6 +129,33 @@
</property>
</spacer>
</item>
<item row="1" column="1">
<widget class="QLineEdit" name="lePkcs12Msg">
<property name="styleSheet">
<string notr="true">background-color: rgba(255, 255, 255, 0);</string>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item row="2" column="2">
<widget class="QCheckBox" name="cbAddCas">
<property name="toolTip">
<string>Add bundle CAs to the connection</string>
</property>
<property name="text">
<string>Add</string>
</property>
</widget>
</item>
<item row="2" column="0">
<widget class="QLabel" name="lblCas">
<property name="text">
<string>CAs</string>
</property>
</widget>
</item>
</layout>
</widget>
<resources/>
Expand Down
27 changes: 25 additions & 2 deletions src/auth/pkipkcs12/qgsauthpkcs12method.cpp
Expand Up @@ -101,6 +101,13 @@ bool QgsAuthPkcs12Method::updateNetworkRequest( QNetworkRequest &request, const
sslConfig.setLocalCertificate( pkibundle->clientCert() );
sslConfig.setPrivateKey( pkibundle->clientCertKey() );

if ( pkibundle->config().config( QStringLiteral( "addcas" ), QStringLiteral( "false" ) ) == QStringLiteral( "true" ) )
{
QList<QSslCertificate> cas;
cas = QgsAuthCertUtils::casMerge( QgsAuthManager::instance()->getTrustedCaCerts(), pkibundle->caChain() );
sslConfig.setCaCertificates( cas );
}

request.setSslConfiguration( sslConfig );

return true;
Expand Down Expand Up @@ -141,10 +148,23 @@ bool QgsAuthPkcs12Method::updateDataSourceUriItems( QStringList &connectionItems
return false;
}

// add extra CAs in the bundle
QList<QSslCertificate> cas;

if ( pkibundle->config().config( QStringLiteral( "addcas" ), QStringLiteral( "false" ) ) == QStringLiteral( "true" ) )
{
cas = QgsAuthCertUtils::casMerge( QgsAuthManager::instance()->getTrustedCaCerts(), pkibundle->caChain() );
}
else
{
cas = QgsAuthManager::instance()->getTrustedCaCerts();
}

// save CAs to temp file
QString caFilePath = QgsAuthCertUtils::pemTextToTempFile(
pkiTempFileBase.arg( QUuid::createUuid().toString() ),
QgsAuthManager::instance()->getTrustedCaCertsPemText() );
QgsAuthCertUtils::certsToPemText( cas ) );

if ( caFilePath.isEmpty() )
{
return false;
Expand Down Expand Up @@ -272,7 +292,10 @@ QgsPkiConfigBundle *QgsAuthPkcs12Method::getPkiConfigBundle( const QString &auth
return bundle;
}

bundle = new QgsPkiConfigBundle( mconfig, clientcert, clientkey );
bundle = new QgsPkiConfigBundle( mconfig, clientcert, clientkey,
QgsAuthCertUtils::pkcs12BundleCas(
mconfig.config( QStringLiteral( "bundlepath" ) ),
mconfig.config( QStringLiteral( "bundlepass" ) ) ) );

locker.unlock();
// cache bundle
Expand Down

0 comments on commit 7b7dad0

Please sign in to comment.