From 3b07121f08f84e645b17e79f841d91905a94dd2b Mon Sep 17 00:00:00 2001 From: Jakub Date: Wed, 30 Mar 2022 14:45:51 +0200 Subject: [PATCH 1/6] Other: temporary disable mac build --- .gitlab-ci.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index a9172a5..e254298 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -172,7 +172,6 @@ build-darwin-qa: extends: .build-darwin-base only: - web - - branches script: - BUILD_TAGS="build_qa" make build artifacts: From 5b20b6a3d0e0488fe37a87a733b82c3de6b5c0b0 Mon Sep 17 00:00:00 2001 From: Jakub Date: Wed, 30 Mar 2022 14:34:58 +0200 Subject: [PATCH 2/6] GODT-1537: Manual in-app update mechanism. --- doc/updates.md | 103 ++++++++++++++++++ internal/frontend/qml/Bridge.qml | 2 +- internal/frontend/qml/Bridge_test.qml | 17 ++- internal/frontend/qml/MainWindow.qml | 1 + internal/frontend/qml/NotificationPopups.qml | 4 + .../qml/Notifications/Notifications.qml | 9 +- internal/frontend/qt/frontend.go | 2 +- internal/frontend/qt/frontend_updates.go | 35 +++++- internal/frontend/qt/qml_backend.go | 8 ++ 9 files changed, 173 insertions(+), 8 deletions(-) create mode 100644 doc/updates.md diff --git a/doc/updates.md b/doc/updates.md new file mode 100644 index 0000000..e63116f --- /dev/null +++ b/doc/updates.md @@ -0,0 +1,103 @@ +# Update mechanism of Bridge + +There are mulitple options how to change version of application: +* Automatic in-app update +* Manual in-app update +* Manual install + +In-app update ends with restarting bridge into new version. Automatic in-app +update is downloading, verifying and installing the new version immediatelly +without user confirmation. For manual in-app update user needs to confirm first. +Update is done from special update file published on website. + +The manual installation requires user to download, verify and install manually +using installer for given OS. + +The bridge is installed and executed differently for given OS: + +* Windows and Linux apps are using launcher mechanism: + * There is system protected installation path which is created on first + install. It contains bridge exe and launcher exe. When users starts + bridge the launcher is executed first. It will check update path compare + version with installed one. The newer version then is then executed. + * Update mechanism means to replace files in update folder which is located + in user space. + +* macOS app does not use launcher + * No launcher, only one executable + * In-App udpate replaces the bridge files in installation path directly + + +```mermaid +flowchart LR + subgraph Frontend + U[User requests
version check] + ManIns((Notify user about
manual install
is needed)) + R((Notify user
about restart)) + ManUp((Notify user about
manual update)) + NF((Notify user about
force update)) + + ManUp -->|Install| InstFront[Install] + InstFront -->|Ok| R + InstFront -->|Error| ManIns + + U --> CheckFront[Check online] + CheckFront -->|Ok| IAFront{Is new version
and applicable?} + CheckFront -->|Error| ManIns + + IAFront -->|No| Latest((Notify user
has latest version)) + IAFront -->|Yes| CanInstall{Can update?} + CanInstall -->|No| ManIns + CanInstall -->|Yes| NotifOrInstall{Is automatic
update enabled?} + NotifOrInstall -->|Manual| ManUp + end + + + subgraph Backend + W[Wait for next check] + + W --> Check[Check online] + + Check --> NV{Has new
version?} + Check -->|Error| W + NV -->|No new version| W + IA{Is install
applicable?} + NV -->|New version
available| IA + IA -->|Local rollout
not enough| W + IA -->|Yes| AU{Is automatic\nupdate enabled?} + + AU -->|Yes| CanUp{Can update?} + CanUp -->|No| ManIns + + CanUp -->|Yes| Ins[Install] + Ins -->|Error| ManIns + Ins -->|Ok| R + + AU -->|No| ManUp + ManUp -->|Ignore| W + + + F[Force update] + F --> NF + end + + ManIns --> Web[Open web page] + NF --> Web + ManUp --> Web + R --> Re[Restart] + NF --> Q[Quit bridge] + NotifOrInstall -->|Automatic| W +``` + + +The non-trivial is to combine the update with setting change: +* turn off/on automatic in-app updates +* change from stable to beta or back + +_TODO fill flow chart details_ + + +We are not support downgrade functionality. Only some circumstances can lead to +downgrading the app version. + +_TODO fill flow chart details_ diff --git a/internal/frontend/qml/Bridge.qml b/internal/frontend/qml/Bridge.qml index 110afb6..7deb44c 100644 --- a/internal/frontend/qml/Bridge.qml +++ b/internal/frontend/qml/Bridge.qml @@ -133,7 +133,7 @@ QtObject { return Qt.point(_x, _y) } - // fir to the right + // fit to the right _x = iconRect.right if (isInInterval(_x, screenRect.left, screenRect.right - width)) { // position preferebly in the vertical center but bound to the screen rect diff --git a/internal/frontend/qml/Bridge_test.qml b/internal/frontend/qml/Bridge_test.qml index b704038..187b020 100644 --- a/internal/frontend/qml/Bridge_test.qml +++ b/internal/frontend/qml/Bridge_test.qml @@ -729,6 +729,9 @@ Window { console.log("check updates") } signal checkUpdatesFinished() + function installUpdate() { + console.log("manuall install update triggered") + } property bool isDiskCacheEnabled: true @@ -748,7 +751,19 @@ Window { property bool isAutomaticUpdateOn : true function toggleAutomaticUpdate(makeItActive) { console.debug("-> silent updates", makeItActive, root.isAutomaticUpdateOn) - root.isAutomaticUpdateOn = makeItActive + var callback = function () { + root.isAutomaticUpdateOn = makeItActive; + console.debug("-> CHANGED silent updates", makeItActive, root.isAutomaticUpdateOn) + } + atimer.onTriggered.connect(callback) + atimer.restart() + } + + Timer { + id: atimer + interval: 2000 + running: false + repeat: false } property bool isAutostartOn : true // Example of settings with loading state diff --git a/internal/frontend/qml/MainWindow.qml b/internal/frontend/qml/MainWindow.qml index 7ad1e42..02d1c52 100644 --- a/internal/frontend/qml/MainWindow.qml +++ b/internal/frontend/qml/MainWindow.qml @@ -182,6 +182,7 @@ ApplicationWindow { colorScheme: root.colorScheme notifications: root.notifications mainWindow: root + backend: root.backend } function showLocalCacheSettings() { contentWrapper.showLocalCacheSettings() } diff --git a/internal/frontend/qml/NotificationPopups.qml b/internal/frontend/qml/NotificationPopups.qml index 0e7dab1..35d7df0 100644 --- a/internal/frontend/qml/NotificationPopups.qml +++ b/internal/frontend/qml/NotificationPopups.qml @@ -25,6 +25,7 @@ import Notifications 1.0 Item { id: root + property var backend property ColorScheme colorScheme property var notifications @@ -51,8 +52,11 @@ Item { notification: root.notifications.updateManualReady Switch { + id:autoUpdate colorScheme: root.colorScheme text: qsTr("Update automatically in the future") + checked: root.backend.isAutomaticUpdateOn + onClicked: root.backend.toggleAutomaticUpdate(autoUpdate.checked) } } diff --git a/internal/frontend/qml/Notifications/Notifications.qml b/internal/frontend/qml/Notifications/Notifications.qml index 36ee23c..2dc366d 100644 --- a/internal/frontend/qml/Notifications/Notifications.qml +++ b/internal/frontend/qml/Notifications/Notifications.qml @@ -166,8 +166,9 @@ QtObject { } property Notification updateManualError: Notification { - description: qsTr("Bridge couldn’t update") - brief: description + title: qsTr("Bridge couldn’t update") + brief: title + description: qsTr("Please follow manual installation in order to update Bridge.") icon: "./icons/ic-exclamation-circle-filled.svg" type: Notification.NotificationType.Warning group: Notifications.Group.Update @@ -192,7 +193,7 @@ QtObject { text: qsTr("Remind me later") onTriggered: { - root.updateManualReady.active = false + root.updateManualError.active = false } } ] @@ -273,7 +274,7 @@ QtObject { onTriggered: { root.backend.quit() - root.updateForce.active = false + root.updateForceError.active = false } } ] diff --git a/internal/frontend/qt/frontend.go b/internal/frontend/qt/frontend.go index 0383d1c..bbfc966 100644 --- a/internal/frontend/qt/frontend.go +++ b/internal/frontend/qt/frontend.go @@ -153,7 +153,7 @@ func (f *FrontendQt) NotifySilentUpdateInstalled() { } func (f *FrontendQt) NotifySilentUpdateError(err error) { - f.log.WithError(err).Warn("Update failed, asking for manual.") + f.log.WithError(err).Warn("In-app update failed, asking for manual.") f.qml.UpdateManualError() } diff --git a/internal/frontend/qt/frontend_updates.go b/internal/frontend/qt/frontend_updates.go index 90bb16a..3c48f1a 100644 --- a/internal/frontend/qt/frontend_updates.go +++ b/internal/frontend/qt/frontend_updates.go @@ -25,6 +25,7 @@ import ( "github.com/ProtonMail/proton-bridge/internal/config/settings" "github.com/ProtonMail/proton-bridge/internal/updater" + "github.com/pkg/errors" ) var checkingUpdates = sync.Mutex{} @@ -62,9 +63,18 @@ func (f *FrontendQt) checkUpdatesAndNotify(isRequestFromUser bool) { if !f.updater.CanInstall(f.newVersionInfo) { f.log.Debug("A manual update is required") - f.qml.UpdateManualReady(f.newVersionInfo.Version.String()) + f.qml.UpdateManualError() + return + } + + if f.settings.GetBool(settings.AutoUpdateKey) { + // NOOP will update eventually return } + + if isRequestFromUser { + f.qml.UpdateManualReady(f.newVersionInfo.Version.String()) + } } func (f *FrontendQt) updateForce() { @@ -113,3 +123,26 @@ func (f *FrontendQt) toggleBeta(makeItEnabled bool) { // Immediately check the updates to set the correct landing page link. f.checkUpdates() } + +func (f *FrontendQt) installUpdate() { + checkingUpdates.Lock() + defer checkingUpdates.Unlock() + + if !f.updater.CanInstall(f.newVersionInfo) { + f.log.Warning("Skipping update installation, current version too old") + f.qml.UpdateManualError() + return + } + + if err := f.updater.InstallUpdate(f.newVersionInfo); err != nil { + if errors.Cause(err) == updater.ErrDownloadVerify { + f.log.WithError(err).Warning("Skipping update installation due to temporary error") + } else { + f.log.WithError(err).Error("The update couldn't be installed") + f.qml.UpdateManualError() + } + return + } + + f.qml.UpdateSilentRestartNeeded() +} diff --git a/internal/frontend/qt/qml_backend.go b/internal/frontend/qt/qml_backend.go index a9c7ac2..23292b7 100644 --- a/internal/frontend/qt/qml_backend.go +++ b/internal/frontend/qt/qml_backend.go @@ -81,6 +81,7 @@ type QMLBackend struct { _ func() `signal:"updateIsLatestVersion"` _ func() `slot:"checkUpdates"` _ func() `signal:"checkUpdatesFinished"` + _ func() `slot:"installUpdate"` _ bool `property:"isDiskCacheEnabled"` _ core.QUrl `property:"diskCachePath"` @@ -213,6 +214,13 @@ func (q *QMLBackend) setup(f *FrontendQt) { }() }) + q.ConnectInstallUpdate(func() { + go func() { + defer f.panicHandler.HandlePanic() + f.installUpdate() + }() + }) + f.setIsDiskCacheEnabled() f.setDiskCachePath() q.ConnectChangeLocalCache(func(e bool, d *core.QUrl) { From c32a1068983e5762d42153ab083d9093d527e243 Mon Sep 17 00:00:00 2001 From: Jakub Date: Fri, 18 Mar 2022 15:25:02 +0100 Subject: [PATCH 3/6] GODT-1525: Add keybase/go-keychain/secretservice as new keychain helper. --- go.mod | 4 +- go.sum | 4 + pkg/keychain/helper_dbus_linux.go | 220 ++++++++++++++++++++++++++++++ pkg/keychain/helper_linux.go | 15 +- 4 files changed, 240 insertions(+), 3 deletions(-) create mode 100644 pkg/keychain/helper_dbus_linux.go diff --git a/go.mod b/go.mod index 19aca58..59b283c 100644 --- a/go.mod +++ b/go.mod @@ -43,12 +43,13 @@ require ( github.com/flynn-archive/go-shlex v0.0.0-20150515145356-3f9db97f8568 // indirect github.com/getsentry/sentry-go v0.12.0 github.com/go-resty/resty/v2 v2.6.0 + github.com/godbus/dbus v4.1.0+incompatible github.com/golang/mock v1.4.4 github.com/google/go-cmp v0.5.5 github.com/google/uuid v1.1.1 github.com/hashicorp/go-multierror v1.1.0 github.com/jaytaylor/html2text v0.0.0-20200412013138-3577fbdbcff7 - github.com/keybase/go-keychain v0.0.0-20211119201326-e02f34051621 + github.com/keybase/go-keychain v0.0.0 github.com/kr/text v0.2.0 // indirect github.com/logrusorgru/aurora v2.0.3+incompatible github.com/mattn/go-runewidth v0.0.9 // indirect @@ -79,4 +80,5 @@ replace ( github.com/emersion/go-imap => github.com/ProtonMail/go-imap v0.0.0-20201228133358-4db68cea0cac github.com/emersion/go-message => github.com/ProtonMail/go-message v0.0.0-20210611055058-fabeff2ec753 github.com/jameskeane/bcrypt => github.com/ProtonMail/bcrypt v0.0.0-20210511135022-227b4adcab57 + github.com/keybase/go-keychain => github.com/cuthix/go-keychain v0.0.0-20220405075754-31e7cee908fe ) diff --git a/go.sum b/go.sum index e12c82f..f32cf0e 100644 --- a/go.sum +++ b/go.sum @@ -102,6 +102,8 @@ github.com/cucumber/godog v0.12.1/go.mod h1:u6SD7IXC49dLpPN35kal0oYEjsXZWee4pW6T github.com/cucumber/messages-go/v16 v16.0.0/go.mod h1:EJcyR5Mm5ZuDsKJnT2N9KRnBK30BGjtYotDKpwQ0v6g= github.com/cucumber/messages-go/v16 v16.0.1 h1:fvkpwsLgnIm0qugftrw2YwNlio+ABe2Iu94Ap8GMYIY= github.com/cucumber/messages-go/v16 v16.0.1/go.mod h1:EJcyR5Mm5ZuDsKJnT2N9KRnBK30BGjtYotDKpwQ0v6g= +github.com/cuthix/go-keychain v0.0.0-20220405075754-31e7cee908fe h1:KRj3wdvA9yE92prNmOjS7x5DOqoyjxqdE30qnrmTasc= +github.com/cuthix/go-keychain v0.0.0-20220405075754-31e7cee908fe/go.mod h1:ZoZU1fnBy3mOLWr3Pg+Y2+nTKtu6ypDte2kZg9HvSwY= github.com/danieljoos/wincred v1.1.0 h1:3RNcEpBg4IhIChZdFRSdlQt1QjCp1sMAPIrOnm7Yf8g= github.com/danieljoos/wincred v1.1.0/go.mod h1:XYlo+eRTsVA9aHGp7NGjFkPla4m+DCL7hqDjlFjiygg= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -164,6 +166,8 @@ github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/me github.com/gobwas/httphead v0.0.0-20180130184737-2c6c146eadee/go.mod h1:L0fX3K22YWvt/FAX9NnzrNzcI4wNYi9Yku4O0LKYflo= github.com/gobwas/pool v0.2.0/go.mod h1:q8bcK0KcYlCgd9e7WYLm9LpyS+YeLd8JVDW6WezmKEw= github.com/gobwas/ws v1.0.2/go.mod h1:szmBTxLgaFppYjEmNtny/v3w89xOydFnnZMcgRRu/EM= +github.com/godbus/dbus v4.1.0+incompatible h1:WqqLRTsQic3apZUK9qC5sGNfXthmPXzUZ7nQPrNITa4= +github.com/godbus/dbus v4.1.0+incompatible/go.mod h1:/YcGZj5zSblfDWMMoOzV4fas9FZnQYTkDnsGvmh2Grw= github.com/gofrs/uuid v4.0.0+incompatible h1:1SD/1F5pU8p29ybwgQSwpQk+mwdRrXCYuPhW6m+TnJw= github.com/gofrs/uuid v4.0.0+incompatible/go.mod h1:b2aQJv3Z4Fp6yNu3cdSllBxTCLRxnplIgP/c0N/04lM= github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ= diff --git a/pkg/keychain/helper_dbus_linux.go b/pkg/keychain/helper_dbus_linux.go new file mode 100644 index 0000000..ffc4a84 --- /dev/null +++ b/pkg/keychain/helper_dbus_linux.go @@ -0,0 +1,220 @@ +// Copyright (c) 2022 Proton Technologies AG +// +// This file is part of ProtonMail Bridge. +// +// ProtonMail Bridge is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// ProtonMail Bridge is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with ProtonMail Bridge. If not, see . + +package keychain + +import ( + "strings" + + "github.com/docker/docker-credential-helpers/credentials" + "github.com/godbus/dbus" + "github.com/keybase/go-keychain/secretservice" +) + +const ( + serverAtt = "server" + labelAtt = "label" + usernameAtt = "username" + + defaulDomain = "protonmail/bridge/users/" + defaultLabel = "Docker Credentials" +) + +func getSession() (*secretservice.SecretService, *secretservice.Session, error) { + service, err := secretservice.NewService() + if err != nil { + return nil, nil, err + } + + session, err := service.OpenSession(secretservice.AuthenticationDHAES) + if err != nil { + return nil, nil, err + } + + return service, session, nil +} + +func handleTimeout(f func() error) error { + err := f() + if err == secretservice.ErrPromptTimedOut { + return f() + } + return err +} + +func getItems(service *secretservice.SecretService, attributes map[string]string) ([]dbus.ObjectPath, error) { + if err := unlock(service); err != nil { + return nil, err + } + + var items []dbus.ObjectPath + err := handleTimeout(func() error { + var err error + items, err = service.SearchCollection( + secretservice.DefaultCollection, + attributes, + ) + return err + }) + if err != nil { + return nil, err + } + + return items, err +} + +func unlock(service *secretservice.SecretService) error { + return handleTimeout(func() error { + return service.Unlock([]dbus.ObjectPath{secretservice.DefaultCollection}) + }) +} + +// SecretServiceDBusHelper is wrapper around keybase/go-keychain/secretservice +// library. +type SecretServiceDBusHelper struct{} + +// Add appends credentials to the store. +func (s *SecretServiceDBusHelper) Add(creds *credentials.Credentials) error { + service, session, err := getSession() + if err != nil { + return err + } + defer service.CloseSession(session) + + if err := unlock(service); err != nil { + return err + } + + secret, err := session.NewSecret([]byte(creds.Secret)) + if err != nil { + return err + } + + attributes := map[string]string{ + usernameAtt: creds.Username, + serverAtt: creds.ServerURL, + labelAtt: defaultLabel, + "xdg:schema": "io.docker.Credentials", + "docker_cli": "1", + } + + return handleTimeout(func() error { + _, err = service.CreateItem( + secretservice.DefaultCollection, + secretservice.NewSecretProperties(creds.ServerURL, attributes), + secret, + secretservice.ReplaceBehaviorReplace, + ) + + return err + }) +} + +// Delete removes credentials from the store. +func (s *SecretServiceDBusHelper) Delete(serverURL string) error { + service, session, err := getSession() + if err != nil { + return err + } + defer service.CloseSession(session) + + items, err := getItems(service, map[string]string{ + labelAtt: defaultLabel, + serverAtt: serverURL, + }) + + if len(items) == 0 || err != nil { + return err + } + + return handleTimeout(func() error { + return service.DeleteItem(items[0]) + }) +} + +// Get retrieves credentials from the store. +// It returns username and secret as strings. +func (s *SecretServiceDBusHelper) Get(serverURL string) (string, string, error) { + service, session, err := getSession() + if err != nil { + return "", "", err + } + defer service.CloseSession(session) + + if err := unlock(service); err != nil { + return "", "", err + } + + items, err := getItems(service, map[string]string{ + labelAtt: defaultLabel, + serverAtt: serverURL, + }) + + if len(items) == 0 || err != nil { + return "", "", err + } + + item := items[0] + + attributes, err := service.GetAttributes(item) + if err != nil { + return "", "", err + } + + var secretPlaintext []byte + err = handleTimeout(func() error { + var err error + secretPlaintext, err = service.GetSecret(item, *session) + return err + }) + if err != nil { + return "", "", err + } + + return attributes[usernameAtt], string(secretPlaintext), nil +} + +// List returns the stored serverURLs and their associated usernames. +func (s *SecretServiceDBusHelper) List() (map[string]string, error) { + userIDByURL := make(map[string]string) + + service, session, err := getSession() + if err != nil { + return nil, err + } + defer service.CloseSession(session) + + items, err := getItems(service, map[string]string{labelAtt: defaultLabel}) + if err != nil { + return nil, err + } + + for _, it := range items { + attributes, err := service.GetAttributes(it) + if err != nil { + return nil, err + } + + if !strings.HasPrefix(attributes[serverAtt], defaulDomain) { + continue + } + + userIDByURL[attributes[serverAtt]] = attributes[usernameAtt] + } + + return userIDByURL, nil +} diff --git a/pkg/keychain/helper_linux.go b/pkg/keychain/helper_linux.go index 53b4c65..2a517ae 100644 --- a/pkg/keychain/helper_linux.go +++ b/pkg/keychain/helper_linux.go @@ -28,13 +28,18 @@ import ( ) const ( - Pass = "pass-app" - SecretService = "secret-service" + Pass = "pass-app" + SecretService = "secret-service" + SecretServiceDBus = "secret-service-dbus" ) func init() { // nolint[noinit] Helpers = make(map[string]helperConstructor) + if isUsable(newDBusHelper("")) { + Helpers[SecretServiceDBus] = newDBusHelper + } + if _, err := exec.LookPath("gnome-keyring"); err == nil && isUsable(newSecretServiceHelper("")) { Helpers[SecretService] = newSecretServiceHelper } @@ -43,6 +48,8 @@ func init() { // nolint[noinit] Helpers[Pass] = newPassHelper } + defaultHelper = SecretServiceDBus + // If Pass is available, use it by default. // Otherwise, if SecretService is available, use it by default. if _, ok := Helpers[Pass]; ok { @@ -52,6 +59,10 @@ func init() { // nolint[noinit] } } +func newDBusHelper(string) (credentials.Helper, error) { + return &SecretServiceDBusHelper{}, nil +} + func newPassHelper(string) (credentials.Helper, error) { return &pass.Pass{}, nil } From de586e5f12c765c7e35c01533fc7bf91e4a6f0d1 Mon Sep 17 00:00:00 2001 From: Jakub Date: Thu, 31 Mar 2022 10:54:14 +0200 Subject: [PATCH 4/6] GODT-1527: Change bug report description. --- .gitlab-ci.yml | 1 + Makefile | 2 +- internal/frontend/qml/BugReportView.qml | 11 +---------- internal/store/cooldown_test.go | 2 +- pkg/parallel/parallel_test.go | 2 +- 5 files changed, 5 insertions(+), 13 deletions(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index e254298..a9172a5 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -172,6 +172,7 @@ build-darwin-qa: extends: .build-darwin-base only: - web + - branches script: - BUILD_TAGS="build_qa" make build artifacts: diff --git a/Makefile b/Makefile index 049798c..29e94d6 100644 --- a/Makefile +++ b/Makefile @@ -85,7 +85,7 @@ hasher: ${TGZ_TARGET}: ${DEPLOY_DIR}/${TARGET_OS} rm -f $@ - cd ${DEPLOY_DIR}/${TARGET_OS} && tar czf ../../../../$@ . + cd ${DEPLOY_DIR}/${TARGET_OS} && tar -czf ../../../../$@ . ${DEPLOY_DIR}/linux: ${EXE_TARGET} cp -pf ./internal/frontend/share/${SRC_SVG} ${DEPLOY_DIR}/linux/logo.svg diff --git a/internal/frontend/qml/BugReportView.qml b/internal/frontend/qml/BugReportView.qml index a29c9d1..d5db875 100644 --- a/internal/frontend/qml/BugReportView.qml +++ b/internal/frontend/qml/BugReportView.qml @@ -127,19 +127,10 @@ SettingsView { } TextEdit { - text: { - var address = "bridge@protonmail.com" - var mailTo = `${address}` - return "" +qsTr( - "These reports are not end-to-end encrypted. In case of sensitive information, contact us at %1." - ).arg(mailTo) - } - onLinkActivated: Qt.openUrlExternally(link) - textFormat: Text.RichText + text: qsTr("Reports are not end-to-end encrypted, please do not send any sensitive information.") readOnly: true - Layout.fillWidth: true color: root.colorScheme.text_weak font.family: ProtonStyle.font_family diff --git a/internal/store/cooldown_test.go b/internal/store/cooldown_test.go index 88fa27f..eb96090 100644 --- a/internal/store/cooldown_test.go +++ b/internal/store/cooldown_test.go @@ -127,6 +127,6 @@ func TestCooldownNotSooner(t *testing.T) { assert.True(t, testCooldown.isTooSoon()) // After given wait time it shouldn't be soon anymore. - time.Sleep(waitTime / 2) + time.Sleep(waitTime/2 + time.Millisecond) assert.False(t, testCooldown.isTooSoon()) } diff --git a/pkg/parallel/parallel_test.go b/pkg/parallel/parallel_test.go index 628a5dc..67805ed 100644 --- a/pkg/parallel/parallel_test.go +++ b/pkg/parallel/parallel_test.go @@ -34,7 +34,7 @@ var ( wantOutput = []int{1, 2, 3, 4, 5, 6, 7, 8, 9, 10} testProcessSleep = 100 // ms runParallelTimeOverhead = 150 // ms - windowsCIExtra = 250 // ms - estimated experimentally + windowsCIExtra = 500 // ms - estimated experimentally ) func TestParallel(t *testing.T) { From c94d839fbba5bd1667f55816d388533ebb12757b Mon Sep 17 00:00:00 2001 From: Jakub Date: Wed, 6 Apr 2022 11:22:32 +0200 Subject: [PATCH 5/6] Other: debug mac CI --- .gitlab-ci.yml | 2 -- .gitmodules | 0 Makefile | 2 +- 3 files changed, 1 insertion(+), 3 deletions(-) delete mode 100644 .gitmodules diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index a9172a5..434c4c8 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -147,8 +147,6 @@ build-linux-qa: .build-darwin-base: extends: .build-base before_script: - - eval $(ssh-agent -s) - - echo "$SSH_PRIVATE_KEY" | tr -d '\r' | ssh-add - > /dev/null - export PATH=/usr/local/bin:$PATH - export PATH=/usr/local/opt/git/bin:$PATH - export PATH=/usr/local/opt/make/libexec/gnubin:$PATH diff --git a/.gitmodules b/.gitmodules deleted file mode 100644 index e69de29..0000000 diff --git a/Makefile b/Makefile index 29e94d6..2e91f3e 100644 --- a/Makefile +++ b/Makefile @@ -85,7 +85,7 @@ hasher: ${TGZ_TARGET}: ${DEPLOY_DIR}/${TARGET_OS} rm -f $@ - cd ${DEPLOY_DIR}/${TARGET_OS} && tar -czf ../../../../$@ . + cd ${DEPLOY_DIR}/${TARGET_OS} && tar -czvf ../../../../$@ . ${DEPLOY_DIR}/linux: ${EXE_TARGET} cp -pf ./internal/frontend/share/${SRC_SVG} ${DEPLOY_DIR}/linux/logo.svg From 51eb2c42cdb82051e8b24ba02e009ec0b9f0241c Mon Sep 17 00:00:00 2001 From: Jakub Date: Fri, 8 Apr 2022 07:34:19 +0200 Subject: [PATCH 6/6] Other: Bridge London 2.1.3 --- Changelog.md | 12 ++++++++++++ Makefile | 2 +- test/Makefile | 2 +- 3 files changed, 14 insertions(+), 2 deletions(-) diff --git a/Changelog.md b/Changelog.md index 12c6b6d..1a0a53a 100644 --- a/Changelog.md +++ b/Changelog.md @@ -2,6 +2,18 @@ Changelog [format](http://keepachangelog.com/en/1.0.0/) +## [Bridge 2.1.3] London + +## Added +GODT-1525: Add keybase/go-keychain/secretservice as new keychain helper. + +## Changed +GODT-1527: Change bug report description. + +## Fixed +GODT-1537: Manual in-app update mechanism. + + ## [Bridge 2.1.2] London ## Added diff --git a/Makefile b/Makefile index 2e91f3e..727ffaa 100644 --- a/Makefile +++ b/Makefile @@ -10,7 +10,7 @@ TARGET_OS?=${GOOS} .PHONY: build build-nogui build-launcher versioner hasher # Keep version hardcoded so app build works also without Git repository. -BRIDGE_APP_VERSION?=2.1.2+git +BRIDGE_APP_VERSION?=2.1.3+git APP_VERSION:=${BRIDGE_APP_VERSION} SRC_ICO:=logo.ico SRC_ICNS:=Bridge.icns diff --git a/test/Makefile b/test/Makefile index fd52323..45649d1 100644 --- a/test/Makefile +++ b/test/Makefile @@ -1,7 +1,7 @@ .PHONY: check-go check-godog install-godog test test-bridge test-live test-live-bridge test-stage test-debug test-live-debug bench export GO111MODULE=on -export BRIDGE_VERSION:=2.1.2+integrationtests +export BRIDGE_VERSION:=2.1.3+integrationtests export VERBOSITY?=fatal export TEST_DATA=testdata