diff --git a/damus/Models/NoteContent.swift b/damus/Models/NoteContent.swift index 08c9210d..8a4e4971 100644 --- a/damus/Models/NoteContent.swift +++ b/damus/Models/NoteContent.swift @@ -191,6 +191,7 @@ func reduce_text_block(ind: Int, hide_text_index: Int, txt: String) -> String { func invoice_str(_ invoice: Invoice) -> CompatibleText { var attributedString = AttributedString(stringLiteral: abbrev_identifier(invoice.string)) + attributedString.link = URL(string: "damus:lightning:\(invoice.string)") attributedString.foregroundColor = DamusColors.purple return CompatibleText(attributed: attributedString) diff --git a/damus/Models/URLHandler.swift b/damus/Models/URLHandler.swift index 03198d8f..4feec53d 100644 --- a/damus/Models/URLHandler.swift +++ b/damus/Models/URLHandler.swift @@ -43,6 +43,18 @@ struct DamusURLHandler { return .route(.Script(script: model)) case .purple(let purple_url): return await damus_state.purple.handle(purple_url: purple_url) + case .invoice(let invoice): + if damus_state.settings.show_wallet_selector { + return .sheet(.select_wallet(invoice: invoice.string)) + } else { + do { + try open_with_wallet(wallet: damus_state.settings.default_wallet.model, invoice: invoice.string) + return .no_action + } + catch { + return .sheet(.select_wallet(invoice: invoice.string)) + } + } case nil: break } @@ -91,6 +103,11 @@ struct DamusURLHandler { return .filter(filt) case .script(let script): return .script(script) + case .invoice(let bolt11): + if let invoice = decode_bolt11(bolt11) { + return .invoice(invoice) + } + return nil } return nil } @@ -103,5 +120,6 @@ struct DamusURLHandler { case wallet_connect(WalletConnectURL) case script([UInt8]) case purple(DamusPurpleURL) + case invoice(Invoice) } } diff --git a/damus/Nostr/NostrLink.swift b/damus/Nostr/NostrLink.swift index 16074429..6fd74e0e 100644 --- a/damus/Nostr/NostrLink.swift +++ b/damus/Nostr/NostrLink.swift @@ -12,6 +12,7 @@ enum NostrLink: Equatable { case ref(RefId) case filter(NostrFilter) case script([UInt8]) + case invoice(String) } func encode_pubkey_uri(_ pubkey: Pubkey) -> String { @@ -93,8 +94,15 @@ func decode_nostr_uri(_ s: String) -> NostrLink? { return } - if parts.count >= 2 && parts[0] == "t" { - return .filter(NostrFilter(hashtag: [parts[1].lowercased()])) + if parts.count >= 2 { + switch parts[0] { + case "t": + return .filter(NostrFilter(hashtag: [parts[1].lowercased()])) + case "lightning": + return .invoice(parts[1]) + default: + break + } } guard parts.count == 1 else { diff --git a/damusTests/NoteContentViewTests.swift b/damusTests/NoteContentViewTests.swift index 73bd9375..484c5cdd 100644 --- a/damusTests/NoteContentViewTests.swift +++ b/damusTests/NoteContentViewTests.swift @@ -84,6 +84,7 @@ class NoteContentViewTests: XCTestCase { XCTAssertEqual(runArray.count, 3) XCTAssertTrue(runArray[0].description.contains("Donations appreciated: ")) XCTAssertTrue(runArray[1].description.contains("lnbc100n:qpsql29r")) + XCTAssertEqual(runArray[1].link?.absoluteString, "damus:lightning:\(invoiceString)") XCTAssertTrue(runArray[2].description.contains(" Pura Vida")) } @@ -281,6 +282,7 @@ class NoteContentViewTests: XCTestCase { XCTAssertEqual(runArray.count, 4) XCTAssertTrue(runArray[0].description.contains("Donations appreciated: ")) XCTAssertTrue(runArray[1].description.contains("lnbc100n:qpsql29r")) + XCTAssertEqual(runArray[1].link?.absoluteString, "damus:lightning:\(invoiceString)") XCTAssertTrue(runArray[2].description.contains(" Pura Vida")) XCTAssertTrue(runArray[3].description.contains("https://damus.io/nothidden.png")) XCTAssertEqual(runArray[3].link?.absoluteString, "https://damus.io/nothidden.png")