feat(quartz): NIP-BC sign_psbt over NIP-55 external signer (Phase B)
Wires the NIP-55 Android external-signer contract for sign_psbt, so
NostrSignerExternal.signPsbt is real instead of a stub.
- CommandType.SIGN_PSBT ("sign_psbt") — also available in NIP-55 `perms`
lists, since Permission wraps CommandType directly.
- SignPsbtResult result type.
- SignPsbtQuery (background ContentResolver) + SignPsbtRequest /
SignPsbtResponse (foreground Intent), modeled on the derive_key
string-in/string-out shape: the PSBT hex rides the `nostrsigner:` URI,
the signed (not finalized) PSBT comes back in the `result` field.
- BackgroundRequestHandler.signPsbt / ForegroundRequestHandler.signPsbt.
- NostrSignerExternal.signPsbt now runs the background-then-foreground
query. Signer apps that predate sign_psbt reply with no `result`, which
surfaces as CouldNotPerformException — the send dialog shows it as a
failure ("update your signer").
NIP-46 (NostrSignerRemote) still throws UnsupportedMethodException — the
bunker-side command isn't standardized yet.
This commit is contained in:
@@ -150,7 +150,7 @@ Lightning fast path. Two minimal hooks:
|
|||||||
| **C** | Receive + display: `OnchainSection` in `WalletScreen` (address + live balance), Esplora sync, `LocalCache.consume(OnchainZapEvent)`, `updateZapTotal` fold-in, kind-list edits in all 7 in-scope filter files | **Shipped** |
|
| **C** | Receive + display: `OnchainSection` in `WalletScreen` (address + live balance), Esplora sync, `LocalCache.consume(OnchainZapEvent)`, `updateZapTotal` fold-in, kind-list edits in all 7 in-scope filter files | **Shipped** |
|
||||||
| **A.2** | Quartz foundation (send side): BIP-174 PSBT codec, BIP-341 sighash, `OnchainZapBuilder`, `signPsbt` on the `NostrSigner` hierarchy. All crypto validated against BIP-341 wallet test vectors (31 tests). | **Shipped** |
|
| **A.2** | Quartz foundation (send side): BIP-174 PSBT codec, BIP-341 sighash, `OnchainZapBuilder`, `signPsbt` on the `NostrSigner` hierarchy. All crypto validated against BIP-341 wallet test vectors (31 tests). | **Shipped** |
|
||||||
| **D** | Send flow: `OnchainZapSender` orchestrator, `Account.sendOnchainZap`, `OnchainZapSendDialog`, "Send" button on the wallet `OnchainSection`. | **Shipped** |
|
| **D** | Send flow: `OnchainZapSender` orchestrator, `Account.sendOnchainZap`, `OnchainZapSendDialog`, "Send" button on the wallet `OnchainSection`. | **Shipped** |
|
||||||
| **B** | NIP-55 `sign_psbt` intent contract + `NostrSignerExternal.signPsbt`. Broken until Amber ships matching support — surface "update your signer" in the UI. | Pending |
|
| **B** | NIP-55 `sign_psbt` Intent + ContentResolver contract, wired through `NostrSignerExternal.signPsbt`. Works once the external signer app (Amber etc.) ships `sign_psbt` support — older signers reply with no `result`, surfaced as a send failure. | **Shipped** |
|
||||||
|
|
||||||
### Phase A.2 — shipped
|
### Phase A.2 — shipped
|
||||||
|
|
||||||
@@ -179,15 +179,27 @@ Lightning fast path. Two minimal hooks:
|
|||||||
estimates, comment; runs the send and shows progress + result.
|
estimates, comment; runs the send and shows progress + result.
|
||||||
- `OnchainSection`: "Send" button on the wallet-screen Bitcoin card.
|
- `OnchainSection`: "Send" button on the wallet-screen Bitcoin card.
|
||||||
|
|
||||||
|
### Phase B — shipped
|
||||||
|
|
||||||
|
- `CommandType.SIGN_PSBT` (`sign_psbt`) — also usable in NIP-55 `perms` lists
|
||||||
|
via `Permission`, which wraps `CommandType` directly.
|
||||||
|
- `SignPsbtResult` result type; `SignPsbtQuery` (background ContentResolver),
|
||||||
|
`SignPsbtRequest` / `SignPsbtResponse` (foreground Intent), mirroring the
|
||||||
|
`derive_key` string-in/string-out shape — the PSBT hex rides the
|
||||||
|
`nostrsigner:` URI, the signed PSBT comes back in `result`.
|
||||||
|
- `BackgroundRequestHandler.signPsbt` / `ForegroundRequestHandler.signPsbt`;
|
||||||
|
`NostrSignerExternal.signPsbt` now does the real background-then-foreground
|
||||||
|
query instead of throwing. External signers that predate `sign_psbt` reply
|
||||||
|
with no `result` → `CouldNotPerformException`, surfaced by the send dialog.
|
||||||
|
|
||||||
### What's still pending
|
### What's still pending
|
||||||
|
|
||||||
1. **Phase B — NIP-55 `sign_psbt` Intent.** The Android external-signer Intent
|
1. **Note-zap-menu entry point.** `OnchainZapSendDialog` already accepts
|
||||||
contract for PSBT signing, plus `NostrSignerExternal.signPsbt`. Blocked on
|
|
||||||
Amber shipping support; until then external-signer accounts hit
|
|
||||||
`UnsupportedMethodException` (the send dialog surfaces it as a failure).
|
|
||||||
2. **Note-zap-menu entry point.** `OnchainZapSendDialog` already accepts
|
|
||||||
`recipientPubKey` + `zappedEvent`; wiring an "Onchain" option into the
|
`recipientPubKey` + `zappedEvent`; wiring an "Onchain" option into the
|
||||||
existing `ZapAmountChoicePopup` is the remaining UI hook for event zaps.
|
existing `ZapAmountChoicePopup` is the remaining UI hook for event zaps.
|
||||||
|
2. **NIP-46 `sign_psbt`.** `NostrSignerRemote.signPsbt` still throws
|
||||||
|
`UnsupportedMethodException` — the bunker-side command is not standardized
|
||||||
|
yet.
|
||||||
|
|
||||||
## Risks / open questions
|
## Risks / open questions
|
||||||
|
|
||||||
|
|||||||
+2
@@ -31,6 +31,7 @@ enum class CommandType(
|
|||||||
GET_PUBLIC_KEY("get_public_key"),
|
GET_PUBLIC_KEY("get_public_key"),
|
||||||
DECRYPT_ZAP_EVENT("decrypt_zap_event"),
|
DECRYPT_ZAP_EVENT("decrypt_zap_event"),
|
||||||
DERIVE_KEY("derive_key"),
|
DERIVE_KEY("derive_key"),
|
||||||
|
SIGN_PSBT("sign_psbt"),
|
||||||
;
|
;
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
@@ -44,6 +45,7 @@ enum class CommandType(
|
|||||||
GET_PUBLIC_KEY.code -> GET_PUBLIC_KEY
|
GET_PUBLIC_KEY.code -> GET_PUBLIC_KEY
|
||||||
DECRYPT_ZAP_EVENT.code -> DECRYPT_ZAP_EVENT
|
DECRYPT_ZAP_EVENT.code -> DECRYPT_ZAP_EVENT
|
||||||
DERIVE_KEY.code -> DERIVE_KEY
|
DERIVE_KEY.code -> DERIVE_KEY
|
||||||
|
SIGN_PSBT.code -> SIGN_PSBT
|
||||||
else -> null
|
else -> null
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+4
@@ -89,3 +89,7 @@ data class ZapEventDecryptionResult(
|
|||||||
data class DerivationResult(
|
data class DerivationResult(
|
||||||
val newPrivKey: HexKey,
|
val newPrivKey: HexKey,
|
||||||
) : IResult
|
) : IResult
|
||||||
|
|
||||||
|
data class SignPsbtResult(
|
||||||
|
val signedPsbtHex: String,
|
||||||
|
) : IResult
|
||||||
|
|||||||
+59
@@ -0,0 +1,59 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2025 Vitor Pamplona
|
||||||
|
*
|
||||||
|
* Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||||
|
* this software and associated documentation files (the "Software"), to deal in
|
||||||
|
* the Software without restriction, including without limitation the rights to use,
|
||||||
|
* copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the
|
||||||
|
* Software, and to permit persons to whom the Software is furnished to do so,
|
||||||
|
* subject to the following conditions:
|
||||||
|
*
|
||||||
|
* The above copyright notice and this permission notice shall be included in all
|
||||||
|
* copies or substantial portions of the Software.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
||||||
|
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
||||||
|
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
|
||||||
|
* AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||||
|
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
*/
|
||||||
|
package com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries
|
||||||
|
|
||||||
|
import android.content.ContentResolver
|
||||||
|
import androidx.core.net.toUri
|
||||||
|
import com.vitorpamplona.quartz.nip01Core.core.HexKey
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.CommandType
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignPsbtResult
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignerResult
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.utils.getStringByName
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.utils.query
|
||||||
|
|
||||||
|
/**
|
||||||
|
* NIP-BC `sign_psbt` background (ContentResolver) query.
|
||||||
|
*
|
||||||
|
* Passes the unsigned/partially-signed PSBT (lowercase hex) to the external
|
||||||
|
* signer app and expects the updated PSBT back in the `result` column. The
|
||||||
|
* signer signs each input whose `tapInternalKey` matches the user's pubkey;
|
||||||
|
* it does NOT finalize the PSBT.
|
||||||
|
*/
|
||||||
|
class SignPsbtQuery(
|
||||||
|
val loggedInUser: HexKey,
|
||||||
|
val packageName: String,
|
||||||
|
val contentResolver: ContentResolver,
|
||||||
|
) {
|
||||||
|
val uri = "content://$packageName.${CommandType.SIGN_PSBT}".toUri()
|
||||||
|
|
||||||
|
fun query(psbtHex: String): SignerResult<SignPsbtResult> =
|
||||||
|
contentResolver.query(
|
||||||
|
uri,
|
||||||
|
arrayOf(psbtHex, loggedInUser),
|
||||||
|
) { cursor ->
|
||||||
|
val signedPsbtHex = cursor.getStringByName("result")
|
||||||
|
if (!signedPsbtHex.isNullOrBlank()) {
|
||||||
|
SignerResult.RequestAddressed.Successful(SignPsbtResult(signedPsbtHex))
|
||||||
|
} else {
|
||||||
|
SignerResult.RequestAddressed.ReceivedButCouldNotPerform()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+48
@@ -0,0 +1,48 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2025 Vitor Pamplona
|
||||||
|
*
|
||||||
|
* Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||||
|
* this software and associated documentation files (the "Software"), to deal in
|
||||||
|
* the Software without restriction, including without limitation the rights to use,
|
||||||
|
* copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the
|
||||||
|
* Software, and to permit persons to whom the Software is furnished to do so,
|
||||||
|
* subject to the following conditions:
|
||||||
|
*
|
||||||
|
* The above copyright notice and this permission notice shall be included in all
|
||||||
|
* copies or substantial portions of the Software.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
||||||
|
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
||||||
|
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
|
||||||
|
* AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||||
|
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
*/
|
||||||
|
package com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests
|
||||||
|
|
||||||
|
import android.content.Intent
|
||||||
|
import androidx.core.net.toUri
|
||||||
|
import com.vitorpamplona.quartz.nip01Core.core.HexKey
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.CommandType
|
||||||
|
|
||||||
|
/**
|
||||||
|
* NIP-BC `sign_psbt` foreground Intent request.
|
||||||
|
*
|
||||||
|
* Carries the PSBT (lowercase hex) as the `nostrsigner:` URI data so the
|
||||||
|
* signer app can display the inputs/outputs to the user for confirmation.
|
||||||
|
*/
|
||||||
|
class SignPsbtRequest {
|
||||||
|
companion object {
|
||||||
|
fun assemble(
|
||||||
|
psbtHex: String,
|
||||||
|
loggedInUser: HexKey,
|
||||||
|
packageName: String,
|
||||||
|
): Intent {
|
||||||
|
val intent = Intent(Intent.ACTION_VIEW, "nostrsigner:$psbtHex".toUri())
|
||||||
|
intent.`package` = packageName
|
||||||
|
intent.putExtra("type", CommandType.SIGN_PSBT.code)
|
||||||
|
intent.putExtra("current_user", loggedInUser)
|
||||||
|
return intent
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+50
@@ -0,0 +1,50 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2025 Vitor Pamplona
|
||||||
|
*
|
||||||
|
* Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||||
|
* this software and associated documentation files (the "Software"), to deal in
|
||||||
|
* the Software without restriction, including without limitation the rights to use,
|
||||||
|
* copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the
|
||||||
|
* Software, and to permit persons to whom the Software is furnished to do so,
|
||||||
|
* subject to the following conditions:
|
||||||
|
*
|
||||||
|
* The above copyright notice and this permission notice shall be included in all
|
||||||
|
* copies or substantial portions of the Software.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
||||||
|
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
||||||
|
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
|
||||||
|
* AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||||
|
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
*/
|
||||||
|
package com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses
|
||||||
|
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignPsbtResult
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignerResult
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.results.IntentResult
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parses the external signer's `sign_psbt` Intent reply. The `result` field
|
||||||
|
* carries the updated (signed, not finalized) PSBT as lowercase hex.
|
||||||
|
*/
|
||||||
|
class SignPsbtResponse {
|
||||||
|
companion object {
|
||||||
|
fun assemble(signedPsbtHex: String): IntentResult =
|
||||||
|
IntentResult(
|
||||||
|
result = signedPsbtHex,
|
||||||
|
)
|
||||||
|
|
||||||
|
fun parse(intent: IntentResult): SignerResult.RequestAddressed<SignPsbtResult> {
|
||||||
|
if (intent.rejected == true) {
|
||||||
|
return SignerResult.RequestAddressed.ManuallyRejected()
|
||||||
|
}
|
||||||
|
val signedPsbtHex = intent.result
|
||||||
|
return if (!signedPsbtHex.isNullOrBlank()) {
|
||||||
|
SignerResult.RequestAddressed.Successful(SignPsbtResult(signedPsbtHex))
|
||||||
|
} else {
|
||||||
|
SignerResult.RequestAddressed.ReceivedButCouldNotPerform()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+17
-9
@@ -30,6 +30,7 @@ import com.vitorpamplona.quartz.nip01Core.signers.SignerExceptions
|
|||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.DecryptionResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.DecryptionResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.DerivationResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.DerivationResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.EncryptionResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.EncryptionResult
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignPsbtResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignerResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignerResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.ZapEventDecryptionResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.ZapEventDecryptionResult
|
||||||
@@ -175,16 +176,23 @@ class NostrSignerExternal(
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* NIP-BC `sign_psbt` over NIP-55. The Android external-signer Intent
|
* NIP-BC `sign_psbt` over NIP-55. Sends the PSBT (lowercase hex) to the
|
||||||
* contract for PSBT signing is not implemented yet (Phase B); Amber and
|
* external signer app, which signs each input whose `tapInternalKey`
|
||||||
* other signer apps must also ship support before this can work. Until
|
* matches the user's pubkey and returns the updated (not finalized) PSBT.
|
||||||
* then, callers should fall back to other signer kinds or surface an
|
*
|
||||||
* "update your signer" message.
|
* Signer apps that predate `sign_psbt` support reply with no `result`,
|
||||||
|
* which surfaces here as [SignerExceptions.CouldNotPerformException] —
|
||||||
|
* callers should treat that as "update your signer".
|
||||||
*/
|
*/
|
||||||
override suspend fun signPsbt(psbtHex: String): String =
|
override suspend fun signPsbt(psbtHex: String): String {
|
||||||
throw SignerExceptions.UnsupportedMethodException(
|
val result = backgroundQuery.signPsbt(psbtHex) ?: foregroundQuery.signPsbt(psbtHex)
|
||||||
"This external signer does not support sign_psbt yet",
|
|
||||||
)
|
if (result is SignerResult.RequestAddressed.Successful<SignPsbtResult>) {
|
||||||
|
return result.result.signedPsbtHex
|
||||||
|
}
|
||||||
|
|
||||||
|
throw convertExceptions("Could not sign PSBT", result)
|
||||||
|
}
|
||||||
|
|
||||||
// always ready
|
// always ready
|
||||||
override fun hasForegroundSupport() = hasForegroundActivity()
|
override fun hasForegroundSupport() = hasForegroundActivity()
|
||||||
|
|||||||
+5
@@ -27,6 +27,7 @@ import com.vitorpamplona.quartz.nip55AndroidSigner.api.DecryptionResult
|
|||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.DerivationResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.DerivationResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.EncryptionResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.EncryptionResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.PubKeyResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.PubKeyResult
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignPsbtResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignerResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.SignerResult
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.ZapEventDecryptionResult
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.ZapEventDecryptionResult
|
||||||
@@ -37,6 +38,7 @@ import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.Nip04D
|
|||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.Nip04EncryptQuery
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.Nip04EncryptQuery
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.Nip44DecryptQuery
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.Nip44DecryptQuery
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.Nip44EncryptQuery
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.Nip44EncryptQuery
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.SignPsbtQuery
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.SignQuery
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.background.queries.SignQuery
|
||||||
import com.vitorpamplona.quartz.nip57Zaps.LnZapRequestEvent
|
import com.vitorpamplona.quartz.nip57Zaps.LnZapRequestEvent
|
||||||
|
|
||||||
@@ -53,6 +55,7 @@ class BackgroundRequestHandler(
|
|||||||
val nip44Decrypt = Nip44DecryptQuery(loggedInUser, packageName, contentResolver)
|
val nip44Decrypt = Nip44DecryptQuery(loggedInUser, packageName, contentResolver)
|
||||||
val decryptZap = DecryptZapQuery(loggedInUser, packageName, contentResolver)
|
val decryptZap = DecryptZapQuery(loggedInUser, packageName, contentResolver)
|
||||||
val deriveKey = DeriveKeyQuery(loggedInUser, packageName, contentResolver)
|
val deriveKey = DeriveKeyQuery(loggedInUser, packageName, contentResolver)
|
||||||
|
val signPsbt = SignPsbtQuery(loggedInUser, packageName, contentResolver)
|
||||||
|
|
||||||
fun login() = login.query() as? SignerResult.RequestAddressed<PubKeyResult>
|
fun login() = login.query() as? SignerResult.RequestAddressed<PubKeyResult>
|
||||||
|
|
||||||
@@ -81,4 +84,6 @@ class BackgroundRequestHandler(
|
|||||||
fun decryptZapEvent(event: LnZapRequestEvent) = decryptZap.query(event) as? SignerResult.RequestAddressed<ZapEventDecryptionResult>
|
fun decryptZapEvent(event: LnZapRequestEvent) = decryptZap.query(event) as? SignerResult.RequestAddressed<ZapEventDecryptionResult>
|
||||||
|
|
||||||
fun deriveKey(nonce: HexKey) = deriveKey.query(nonce) as? SignerResult.RequestAddressed<DerivationResult>
|
fun deriveKey(nonce: HexKey) = deriveKey.query(nonce) as? SignerResult.RequestAddressed<DerivationResult>
|
||||||
|
|
||||||
|
fun signPsbt(psbtHex: String) = signPsbt.query(psbtHex) as? SignerResult.RequestAddressed<SignPsbtResult>
|
||||||
}
|
}
|
||||||
|
|||||||
+8
@@ -29,6 +29,7 @@ import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.reques
|
|||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.Nip04EncryptRequest
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.Nip04EncryptRequest
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.Nip44DecryptRequest
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.Nip44DecryptRequest
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.Nip44EncryptRequest
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.Nip44EncryptRequest
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.SignPsbtRequest
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.SignRequest
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.requests.SignRequest
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.DecryptZapResponse
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.DecryptZapResponse
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.DeriveKeyResponse
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.DeriveKeyResponse
|
||||||
@@ -36,6 +37,7 @@ import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.respon
|
|||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.Nip04EncryptResponse
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.Nip04EncryptResponse
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.Nip44DecryptResponse
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.Nip44DecryptResponse
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.Nip44EncryptResponse
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.Nip44EncryptResponse
|
||||||
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.SignPsbtResponse
|
||||||
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.SignResponse
|
import com.vitorpamplona.quartz.nip55AndroidSigner.api.foreground.intents.responses.SignResponse
|
||||||
import com.vitorpamplona.quartz.nip57Zaps.LnZapRequestEvent
|
import com.vitorpamplona.quartz.nip57Zaps.LnZapRequestEvent
|
||||||
|
|
||||||
@@ -95,4 +97,10 @@ class ForegroundRequestHandler(
|
|||||||
requestIntentBuilder = { DeriveKeyRequest.assemble(nonce, loggedInUser, packageName) },
|
requestIntentBuilder = { DeriveKeyRequest.assemble(nonce, loggedInUser, packageName) },
|
||||||
parser = DeriveKeyResponse::parse,
|
parser = DeriveKeyResponse::parse,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
suspend fun signPsbt(psbtHex: String) =
|
||||||
|
launcher.launchWaitAndParse(
|
||||||
|
requestIntentBuilder = { SignPsbtRequest.assemble(psbtHex, loggedInUser, packageName) },
|
||||||
|
parser = SignPsbtResponse::parse,
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user