1
0
mirror of https://github.com/bitwarden/browser synced 2026-02-07 12:13:45 +00:00

PM-22476: Show config UI while enabling Bitwarden (#15149)

* Show config ui while enabling Bitwarden

* locals

* Added Localizable strings

* Changed the linebreakmode

* Removed swedish locals
This commit is contained in:
Anders Åberg
2025-07-01 16:41:59 +02:00
committed by GitHub
parent cd4f5fbdb9
commit f74f9add1b
5 changed files with 88 additions and 64 deletions

View File

@@ -8,63 +8,56 @@
<objects>
<customObject id="-2" userLabel="File's Owner" customClass="CredentialProviderViewController" customModule="autofill_extension" customModuleProvider="target">
<connections>
<outlet property="logoImageView" destination="logoImageView" id="logoImageViewOutlet"/>
<outlet property="statusLabel" destination="statusLabel" id="statusLabelOutlet"/>
<outlet property="view" destination="1" id="2"/>
</connections>
</customObject>
<customObject id="-1" userLabel="First Responder" customClass="FirstResponder"/>
<customObject id="-3" userLabel="Application" customClass="NSObject"/>
<customView hidden="YES" translatesAutoresizingMaskIntoConstraints="NO" id="1">
<rect key="frame" x="0.0" y="0.0" width="378" height="94"/>
<rect key="frame" x="0.0" y="0.0" width="400" height="120"/>
<subviews>
<button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="1uM-r7-H1c">
<rect key="frame" x="184" y="3" width="191" height="32"/>
<buttonCell key="cell" type="push" title="Return Example Password" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="2l4-PO-we5">
<behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
<font key="font" metaFont="system"/>
<string key="keyEquivalent">D</string>
<modifierMask key="keyEquivalentModifierMask" command="YES"/>
</buttonCell>
<connections>
<action selector="passwordSelected:" target="-2" id="yic-EC-GGk"/>
</connections>
</button>
<button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="NVE-vN-dkz">
<rect key="frame" x="114" y="3" width="76" height="32"/>
<buttonCell key="cell" type="push" title="Cancel" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="6Up-t3-mwm">
<behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
<font key="font" metaFont="system"/>
<string key="keyEquivalent" base64-UTF8="YES">
Gw
</string>
</buttonCell>
<constraints>
<constraint firstAttribute="width" relation="greaterThanOrEqual" constant="60" id="cP1-hK-9ZX"/>
</constraints>
<connections>
<action selector="cancel:" target="-2" id="Qav-AK-DGt"/>
</connections>
</button>
<textField verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="aNc-0i-CWK">
<rect key="frame" x="112" y="63" width="154" height="16"/>
<textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" alignment="left" title="autofill-extension hello" id="0xp-rC-2gr">
<font key="font" metaFont="systemBold"/>
<color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
<color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
</textFieldCell>
</textField>
<stackView distribution="fill" orientation="horizontal" alignment="centerY" spacing="20" horizontalStackHuggingPriority="249.99998474121094" verticalStackHuggingPriority="249.99998474121094" detachesHiddenViews="YES" translatesAutoresizingMaskIntoConstraints="NO" id="configStackView">
<rect key="frame" x="89" y="35" width="223" height="50"/>
<subviews>
<imageView horizontalHuggingPriority="251" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="logoImageView">
<rect key="frame" x="0.0" y="0.0" width="50" height="50"/>
<constraints>
<constraint firstAttribute="height" constant="50" id="logoImageHeight"/>
<constraint firstAttribute="width" constant="50" id="logoImageWidth"/>
</constraints>
<imageCell key="cell" refusesFirstResponder="YES" alignment="left" imageScaling="proportionallyUpOrDown" image="bitwarden-icon" id="logoImageCell"/>
</imageView>
<textField horizontalHuggingPriority="251" verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="statusLabel">
<rect key="frame" x="68" y="16" width="157" height="19"/>
<textFieldCell key="cell" sendsActionOnEndEditing="YES" alignment="left" title="Enabling Bitwarden..." id="statusLabelCell">
<font key="font" metaFont="system" size="16"/>
<color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
<color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
</textFieldCell>
</textField>
</subviews>
<visibilityPriorities>
<integer value="1000"/>
<integer value="1000"/>
</visibilityPriorities>
<customSpacing>
<real value="3.4028234663852886e+38"/>
<real value="3.4028234663852886e+38"/>
</customSpacing>
</stackView>
</subviews>
<constraints>
<constraint firstItem="1uM-r7-H1c" firstAttribute="leading" secondItem="NVE-vN-dkz" secondAttribute="trailing" constant="8" id="1UO-J1-LbJ"/>
<constraint firstItem="NVE-vN-dkz" firstAttribute="leading" relation="greaterThanOrEqual" secondItem="1" secondAttribute="leading" constant="20" symbolic="YES" id="3N9-qo-UfS"/>
<constraint firstAttribute="bottom" secondItem="1uM-r7-H1c" secondAttribute="bottom" constant="10" id="4wH-De-nMF"/>
<constraint firstItem="NVE-vN-dkz" firstAttribute="firstBaseline" secondItem="aNc-0i-CWK" secondAttribute="baseline" constant="50" id="Dpq-cK-cPE"/>
<constraint firstAttribute="bottom" secondItem="NVE-vN-dkz" secondAttribute="bottom" constant="10" id="USG-Gg-of3"/>
<constraint firstItem="1uM-r7-H1c" firstAttribute="leading" secondItem="NVE-vN-dkz" secondAttribute="trailing" constant="8" id="a8N-vS-Ew9"/>
<constraint firstAttribute="trailing" secondItem="1uM-r7-H1c" secondAttribute="trailing" constant="10" id="qfT-cw-QQ2"/>
<constraint firstAttribute="centerX" secondItem="aNc-0i-CWK" secondAttribute="centerX" id="uV3-Wn-RA3"/>
<constraint firstItem="aNc-0i-CWK" firstAttribute="top" secondItem="1" secondAttribute="top" constant="15" id="vpR-tf-ebx"/>
<constraint firstItem="configStackView" firstAttribute="centerX" secondItem="1" secondAttribute="centerX" id="stackCenterX"/>
<constraint firstItem="configStackView" firstAttribute="centerY" secondItem="1" secondAttribute="centerY" id="stackCenterY"/>
<constraint firstItem="configStackView" firstAttribute="leading" relation="greaterThanOrEqual" secondItem="1" secondAttribute="leading" constant="20" id="stackLeading"/>
<constraint firstAttribute="trailing" relation="greaterThanOrEqual" secondItem="configStackView" secondAttribute="trailing" constant="20" id="stackTrailing"/>
</constraints>
<point key="canvasLocation" x="162" y="146"/>
<point key="canvasLocation" x="200" y="60"/>
</customView>
</objects>
<resources>
<image name="bitwarden-icon" width="64" height="64"/>
</resources>
</document>

View File

@@ -8,9 +8,12 @@
import AuthenticationServices
import os
class CredentialProviderViewController: ASCredentialProviderViewController {
let logger: Logger
@IBOutlet weak var statusLabel: NSTextField!
// There is something a bit strange about the initialization/deinitialization in this class.
// Sometimes deinit won't be called after a request has successfully finished,
// which would leave this class hanging in memory and the IPC connection open.
@@ -108,7 +111,7 @@ class CredentialProviderViewController: ASCredentialProviderViewController {
logger.log("[autofill-extension] initializing extension")
super.init(nibName: nil, bundle: nil)
super.init(nibName: "CredentialProviderViewController", bundle: nil)
// Setup connection monitoring now that self is available
setupConnectionMonitoring()
@@ -126,16 +129,6 @@ class CredentialProviderViewController: ASCredentialProviderViewController {
connectionMonitorTimer = nil
}
@IBAction func cancel(_ sender: AnyObject?) {
self.extensionContext.cancelRequest(withError: NSError(domain: ASExtensionErrorDomain, code: ASExtensionError.userCanceled.rawValue))
}
@IBAction func passwordSelected(_ sender: AnyObject?) {
let passwordCredential = ASPasswordCredential(user: "j_appleseed", password: "apple1234")
self.extensionContext.completeRequest(withSelectedCredential: passwordCredential, completionHandler: nil)
}
private func getWindowPosition() -> Position {
let frame = self.view.window?.frame ?? .zero
let screenHeight = NSScreen.main?.frame.height ?? 0
@@ -155,16 +148,27 @@ class CredentialProviderViewController: ASCredentialProviderViewController {
return Position(x: positionX, y: positionY)
}
override func loadView() {
let view = NSView()
// Hide the native window since we only need the IPC connection
view.isHidden = true
self.view = view
override func viewDidLoad() {
super.viewDidLoad()
// Initially hide the view
self.view.isHidden = true
}
override func prepareInterfaceForExtensionConfiguration() {
// Show the configuration UI
self.view.isHidden = false
// Set the localized message
statusLabel.stringValue = NSLocalizedString("autofillConfigurationMessage", comment: "Message shown when Bitwarden is enabled in system settings")
// Send the native status request
client.sendNativeStatus(key: "request-sync", value: "")
self.extensionContext.completeExtensionConfigurationRequest()
// Complete the configuration after 2 seconds
DispatchQueue.main.asyncAfter(deadline: .now() + 2.0) { [weak self] in
self?.extensionContext.completeExtensionConfigurationRequest()
}
}
override func provideCredentialWithoutUserInteraction(for credentialRequest: any ASCredentialRequest) {

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.2 KiB

View File

@@ -0,0 +1,2 @@
/* Message shown during passkey configuration */
"autofillConfigurationMessage" = "Enabling Bitwarden...";

View File

@@ -9,6 +9,8 @@
/* Begin PBXBuildFile section */
3368DB392C654B8100896B75 /* BitwardenMacosProviderFFI.xcframework in Frameworks */ = {isa = PBXBuildFile; fileRef = 3368DB382C654B8100896B75 /* BitwardenMacosProviderFFI.xcframework */; };
3368DB3B2C654F3800896B75 /* BitwardenMacosProvider.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3368DB3A2C654F3800896B75 /* BitwardenMacosProvider.swift */; };
9AE299092DF9D82E00AAE454 /* bitwarden-icon.png in Resources */ = {isa = PBXBuildFile; fileRef = 9AE299082DF9D82E00AAE454 /* bitwarden-icon.png */; };
9AE299122DFB57A200AAE454 /* Localizable.strings in Resources */ = {isa = PBXBuildFile; fileRef = 9AE2990D2DFB57A200AAE454 /* Localizable.strings */; };
E1DF713F2B342F6900F29026 /* AuthenticationServices.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E1DF713E2B342F6900F29026 /* AuthenticationServices.framework */; };
E1DF71422B342F6900F29026 /* CredentialProviderViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = E1DF71412B342F6900F29026 /* CredentialProviderViewController.swift */; };
E1DF71452B342F6900F29026 /* CredentialProviderViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = E1DF71432B342F6900F29026 /* CredentialProviderViewController.xib */; };
@@ -18,6 +20,8 @@
3368DB382C654B8100896B75 /* BitwardenMacosProviderFFI.xcframework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.xcframework; name = BitwardenMacosProviderFFI.xcframework; path = ../desktop_native/macos_provider/BitwardenMacosProviderFFI.xcframework; sourceTree = "<group>"; };
3368DB3A2C654F3800896B75 /* BitwardenMacosProvider.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BitwardenMacosProvider.swift; sourceTree = "<group>"; };
968ED08A2C52A47200FFFEE6 /* ReleaseAppStore.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = ReleaseAppStore.xcconfig; sourceTree = "<group>"; };
9AE299082DF9D82E00AAE454 /* bitwarden-icon.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "bitwarden-icon.png"; sourceTree = "<group>"; };
9AE2990C2DFB57A200AAE454 /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = Localizable.strings; sourceTree = "<group>"; };
D83832AB2D67B9AE003FB9F8 /* Debug.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = Debug.xcconfig; sourceTree = "<group>"; };
D83832AD2D67B9D0003FB9F8 /* ReleaseDeveloper.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = ReleaseDeveloper.xcconfig; sourceTree = "<group>"; };
E1DF713C2B342F6900F29026 /* autofill-extension.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "autofill-extension.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
@@ -41,6 +45,14 @@
/* End PBXFrameworksBuildPhase section */
/* Begin PBXGroup section */
9AE2990E2DFB57A200AAE454 /* en.lproj */ = {
isa = PBXGroup;
children = (
9AE2990D2DFB57A200AAE454 /* Localizable.strings */,
);
path = en.lproj;
sourceTree = "<group>";
};
E1DF711D2B342E2800F29026 = {
isa = PBXGroup;
children = (
@@ -73,6 +85,8 @@
E1DF71402B342F6900F29026 /* autofill-extension */ = {
isa = PBXGroup;
children = (
9AE2990E2DFB57A200AAE454 /* en.lproj */,
9AE299082DF9D82E00AAE454 /* bitwarden-icon.png */,
3368DB3A2C654F3800896B75 /* BitwardenMacosProvider.swift */,
E1DF71412B342F6900F29026 /* CredentialProviderViewController.swift */,
E1DF71432B342F6900F29026 /* CredentialProviderViewController.xib */,
@@ -124,6 +138,7 @@
knownRegions = (
en,
Base,
sv,
);
mainGroup = E1DF711D2B342E2800F29026;
productRefGroup = E1DF71272B342E2800F29026 /* Products */;
@@ -141,6 +156,8 @@
buildActionMask = 2147483647;
files = (
E1DF71452B342F6900F29026 /* CredentialProviderViewController.xib in Resources */,
9AE299122DFB57A200AAE454 /* Localizable.strings in Resources */,
9AE299092DF9D82E00AAE454 /* bitwarden-icon.png in Resources */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@@ -159,6 +176,14 @@
/* End PBXSourcesBuildPhase section */
/* Begin PBXVariantGroup section */
9AE2990D2DFB57A200AAE454 /* Localizable.strings */ = {
isa = PBXVariantGroup;
children = (
9AE2990C2DFB57A200AAE454 /* en */,
);
name = Localizable.strings;
sourceTree = "<group>";
};
E1DF71432B342F6900F29026 /* CredentialProviderViewController.xib */ = {
isa = PBXVariantGroup;
children = (