From 911a56b56c4f9ec5d0c4f1fd15189102bc97fcdb Mon Sep 17 00:00:00 2001 From: Jaakko Keränen Date: Fri, 21 May 2021 08:30:39 +0300 Subject: Added identity exporting Exporting an identity will display it in a new tab in PEM encoded format, where it can be saved or copied. IssueID #236 --- src/ui/documentwidget.c | 81 +++++++++++++++++++++++++++++++------------------ src/ui/documentwidget.h | 1 + src/ui/root.c | 5 +-- src/ui/sidebarwidget.c | 32 ++++++++++++++----- 4 files changed, 78 insertions(+), 41 deletions(-) (limited to 'src/ui') diff --git a/src/ui/documentwidget.c b/src/ui/documentwidget.c index 452e5508..337e2a03 100644 --- a/src/ui/documentwidget.c +++ b/src/ui/documentwidget.c @@ -976,7 +976,7 @@ iBool isPinned_DocumentWidget_(const iDocumentWidget *d) { static void showOrHidePinningIndicator_DocumentWidget_(iDocumentWidget *d) { iWidget *w = as_Widget(d); - showCollapsed_Widget(findChild_Widget(root_Widget(as_Widget(d)), "document.pinned"), + showCollapsed_Widget(findChild_Widget(root_Widget(w), "document.pinned"), isPinned_DocumentWidget_(d)); } @@ -1214,7 +1214,9 @@ static void updateDocument_DocumentWidget_(iDocumentWidget *d, const iGmResponse setRange_String(&d->sourceMime, param); } else if (startsWith_Rangecc(param, "text/") || - equal_Rangecc(param, "application/json")) { + equal_Rangecc(param, "application/json") || + equal_Rangecc(param, "application/x-pem-file") || + equal_Rangecc(param, "application/pem-certificate-chain")) { docFormat = plainText_GmDocumentFormat; setRange_String(&d->sourceMime, param); } @@ -1383,37 +1385,42 @@ static void cacheDocumentGlyphs_DocumentWidget_(const iDocumentWidget *d) { } } +static void updateFromCachedResponse_DocumentWidget_(iDocumentWidget *d, float normScrollY, + const iGmResponse *resp) { + setLinkNumberMode_DocumentWidget_(d, iFalse); + clear_ObjectList(d->media); + delete_Gempub(d->sourceGempub); + d->sourceGempub = NULL; + reset_GmDocument(d->doc); + resetWideRuns_DocumentWidget_(d); + d->state = fetching_RequestState; + /* Do the fetch. */ { + d->initNormScrollY = normScrollY; + /* Use the cached response data. */ + updateTrust_DocumentWidget_(d, resp); + d->sourceTime = resp->when; + d->sourceStatus = success_GmStatusCode; + format_String(&d->sourceHeader, cstr_Lang("pageinfo.header.cached")); + set_Block(&d->sourceContent, &resp->body); + updateDocument_DocumentWidget_(d, resp, iTrue); + postProcessRequestContent_DocumentWidget_(d, iTrue); + } + d->state = ready_RequestState; + init_Anim(&d->altTextOpacity, 0); + reset_SmoothScroll(&d->scrollY); + init_Anim(&d->scrollY.pos, d->initNormScrollY * size_GmDocument(d->doc).y); + updateSideOpacity_DocumentWidget_(d, iFalse); + updateVisible_DocumentWidget_(d); + moveSpan_SmoothScroll(&d->scrollY, 0, 0); /* clamp position to new max */ + cacheDocumentGlyphs_DocumentWidget_(d); + d->drawBufs->flags |= updateTimestampBuf_DrawBufsFlag | updateSideBuf_DrawBufsFlag; + postCommandf_Root(as_Widget(d)->root, "document.changed doc:%p url:%s", d, cstr_String(d->mod.url)); +} + static iBool updateFromHistory_DocumentWidget_(iDocumentWidget *d) { const iRecentUrl *recent = findUrl_History(d->mod.history, d->mod.url); if (recent && recent->cachedResponse) { - const iGmResponse *resp = recent->cachedResponse; - clear_ObjectList(d->media); - delete_Gempub(d->sourceGempub); - d->sourceGempub = NULL; - reset_GmDocument(d->doc); - resetWideRuns_DocumentWidget_(d); - d->state = fetching_RequestState; - /* Do the fetch. */ { - d->initNormScrollY = recent->normScrollY; - /* Use the cached response data. */ - updateTrust_DocumentWidget_(d, resp); - d->sourceTime = resp->when; - d->sourceStatus = success_GmStatusCode; - format_String(&d->sourceHeader, cstr_Lang("pageinfo.header.cached")); - set_Block(&d->sourceContent, &resp->body); - updateDocument_DocumentWidget_(d, resp, iTrue); - postProcessRequestContent_DocumentWidget_(d, iTrue); - } - d->state = ready_RequestState; - init_Anim(&d->altTextOpacity, 0); - reset_SmoothScroll(&d->scrollY); - init_Anim(&d->scrollY.pos, d->initNormScrollY * size_GmDocument(d->doc).y); - updateSideOpacity_DocumentWidget_(d, iFalse); - updateVisible_DocumentWidget_(d); - moveSpan_SmoothScroll(&d->scrollY, 0, 0); /* clamp position to new max */ - cacheDocumentGlyphs_DocumentWidget_(d); - d->drawBufs->flags |= updateTimestampBuf_DrawBufsFlag | updateSideBuf_DrawBufsFlag; - postCommandf_Root(as_Widget(d)->root, "document.changed doc:%p url:%s", d, cstr_String(d->mod.url)); + updateFromCachedResponse_DocumentWidget_(d, recent->normScrollY, recent->cachedResponse); return iTrue; } else if (!isEmpty_String(d->mod.url)) { @@ -4413,6 +4420,20 @@ void setUrlFromCache_DocumentWidget(iDocumentWidget *d, const iString *url, iBoo } } +void setUrlAndSource_DocumentWidget(iDocumentWidget *d, const iString *url, const iString *mime, + const iBlock *source) { + setLinkNumberMode_DocumentWidget_(d, iFalse); + set_String(d->mod.url, url); + parseUser_DocumentWidget_(d); + iGmResponse *resp = new_GmResponse(); + resp->statusCode = success_GmStatusCode; + initCurrent_Time(&resp->when); + set_String(&resp->meta, mime); + set_Block(&resp->body, source); + updateFromCachedResponse_DocumentWidget_(d, 0, resp); + delete_GmResponse(resp); +} + iDocumentWidget *duplicate_DocumentWidget(const iDocumentWidget *orig) { iDocumentWidget *d = new_DocumentWidget(); delete_History(d->mod.history); diff --git a/src/ui/documentwidget.h b/src/ui/documentwidget.h index 12603437..c038f981 100644 --- a/src/ui/documentwidget.h +++ b/src/ui/documentwidget.h @@ -47,6 +47,7 @@ int documentWidth_DocumentWidget (const iDocumentWidget *); void setUrl_DocumentWidget (iDocumentWidget *, const iString *url); void setUrlFromCache_DocumentWidget (iDocumentWidget *, const iString *url, iBool isFromCache); +void setUrlAndSource_DocumentWidget (iDocumentWidget *, const iString *url, const iString *mime, const iBlock *source); void setInitialScroll_DocumentWidget (iDocumentWidget *, float normScrollY); /* set after content received */ void setRedirectCount_DocumentWidget (iDocumentWidget *, int count); void setSource_DocumentWidget (iDocumentWidget *, const iString *sourceText); diff --git a/src/ui/root.c b/src/ui/root.c index 1698a5d4..9a089992 100644 --- a/src/ui/root.c +++ b/src/ui/root.c @@ -438,10 +438,7 @@ static void updateNavBarIdentity_(iWidget *navBar) { setFlags_Widget(tool, selected_WidgetFlag, ident != NULL); /* Update menu. */ iLabelWidget *idItem = child_Widget(findChild_Widget(button, "menu"), 0); - iString *subjectName = ident ? collect_String(subject_TlsCertificate(ident->cert)) : NULL; - if (subjectName && startsWith_String(subjectName, "CN = ")) { - remove_Block(&subjectName->chars, 0, 5); - } + const iString *subjectName = ident ? name_GmIdentity(ident) : NULL; setTextCStr_LabelWidget( idItem, subjectName ? format_CStr(uiTextAction_ColorEscape "%s", cstr_String(subjectName)) diff --git a/src/ui/sidebarwidget.c b/src/ui/sidebarwidget.c index 556ae951..f9bdbf67 100644 --- a/src/ui/sidebarwidget.c +++ b/src/ui/sidebarwidget.c @@ -169,9 +169,10 @@ static void updateContextMenu_SidebarWidget_(iSidebarWidget *d) { { "---", 0, 0, NULL }, { edit_Icon " ${menu.edit.notes}", 0, 0, "ident.edit" }, { "${ident.fingerprint}", 0, 0, "ident.fingerprint" }, + { export_Icon " ${ident.export}", 0, 0, "ident.export" }, { "---", 0, 0, NULL }, { delete_Icon " " uiTextCaution_ColorEscape "${ident.delete}", 0, 0, "ident.delete confirm:1" }, - }, 8); + }, 9); /* Used URLs. */ const iGmIdentity *ident = menuIdentity_SidebarWidget_(d); if (ident) { @@ -440,10 +441,7 @@ static void updateItems_SidebarWidget_(iSidebarWidget *d) { iSidebarItem *item = new_SidebarItem(); item->id = (uint32_t) index_PtrArrayConstIterator(&i); item->icon = 0x1f464; /* person */ - set_String(&item->label, collect_String(subject_TlsCertificate(ident->cert))); - if (startsWith_String(&item->label, "CN = ")) { - remove_Block(&item->label.chars, 0, 5); - } + set_String(&item->label, name_GmIdentity(ident)); iDate until; validUntil_TlsCertificate(ident->cert, &until); const iBool isActive = isUsedOn_GmIdentity(ident, tabUrl); @@ -480,11 +478,11 @@ static void updateItems_SidebarWidget_(iSidebarWidget *d) { addActionButton_SidebarWidget_(d, add_Icon " ${sidebar.action.ident.new}", "ident.new", 0); addActionButton_SidebarWidget_(d, "${sidebar.action.ident.import}", "ident.import", 0); } + /* const iMenuItem menuItems[] = { { person_Icon " ${ident.use}", 0, 0, "ident.use arg:1" }, { close_Icon " ${ident.stopuse}", 0, 0, "ident.use arg:0" }, { close_Icon " ${ident.stopuse.all}", 0, 0, "ident.use arg:0 clear:1" }, - { "${ident.showuse}", 0, 0, "ident.showuse" }, { "---", 0, 0, NULL }, { edit_Icon " ${menu.edit.notes}", 0, 0, "ident.edit" }, { "${ident.fingerprint}", 0, 0, "ident.fingerprint" }, @@ -494,6 +492,7 @@ static void updateItems_SidebarWidget_(iSidebarWidget *d) { { delete_Icon " " uiTextCaution_ColorEscape "${ident.delete}", 0, 0, "ident.delete confirm:1" }, }; d->menu = makeMenu_Widget(as_Widget(d), menuItems, iElemCount(menuItems)); + */ break; } default: @@ -792,6 +791,9 @@ static void itemClicked_SidebarWidget_(iSidebarWidget *d, iSidebarItem *item, si } case identities_SidebarMode: { d->contextItem = item; + if (d->contextIndex != iInvalidPos) { + invalidateItem_ListWidget(d->list, d->contextIndex); + } d->contextIndex = itemIndex; if (itemIndex < numItems_ListWidget(d->list)) { updateContextMenu_SidebarWidget_(d); @@ -1277,6 +1279,20 @@ static iBool processEvent_SidebarWidget_(iSidebarWidget *d, const SDL_Event *ev) } return iTrue; } + else if (isCommand_Widget(w, ev, "ident.export")) { + const iGmIdentity *ident = menuIdentity_SidebarWidget_(d); + if (ident) { + iString *pem = collect_String(pem_TlsCertificate(ident->cert)); + append_String(pem, collect_String(privateKeyPem_TlsCertificate(ident->cert))); + iDocumentWidget *expTab = newTab_App(NULL, iTrue); + setUrlAndSource_DocumentWidget( + expTab, + collectNewFormat_String("file:%s.pem", cstr_String(name_GmIdentity(ident))), + collectNewCStr_String("text/plain"), + utf8_String(pem)); + } + return iTrue; + } else if (isCommand_Widget(w, ev, "ident.setnotes")) { iGmIdentity *ident = pointerLabel_Command(cmd, "ident"); if (ident) { @@ -1385,7 +1401,7 @@ static iBool processEvent_SidebarWidget_(iSidebarWidget *d, const SDL_Event *ev) d->contextIndex = iInvalidPos; } } - if (d->menu && ev->type == SDL_MOUSEBUTTONDOWN) { + if ((d->menu || d->mode == identities_SidebarMode )&& ev->type == SDL_MOUSEBUTTONDOWN) { if (ev->button.button == SDL_BUTTON_RIGHT) { d->contextItem = NULL; if (!isVisible_Widget(d->menu)) { @@ -1457,11 +1473,13 @@ static iBool processEvent_SidebarWidget_(iSidebarWidget *d, const SDL_Event *ev) (!cmdClear && cmdUse && isUsedOn_GmIdentity(ident, docUrl)) || (!cmdClear && !cmdUse && !isUsedOn_GmIdentity(ident, docUrl))); } + /* else if (equal_Command(cmdItem, "ident.showuse")) { setFlags_Widget(as_Widget(menuItem), disabled_WidgetFlag, !isUsed_GmIdentity(ident)); } + */ } } } -- cgit v1.2.3