+ // Do a trivial test of constructing a phantom invoice
+ Result_InvoiceSignOrCreationErrorZ phantom_invoice = UtilMethods.create_phantom_invoice(
+ Option_u64Z.some(42000),
+ new byte[32], // TODO: This needs to be an option/null, not interpreting all-0s as None
+ "Phantom Invoice", 7200,
+ new PhantomRouteHints[]{ peer2.chan_manager.get_phantom_route_hints() },
+ peer2.entropy_source,
+ PhantomKeysManager.of(peer2.key_seed, 42, 42, new byte[32]).as_NodeSigner(),
+ peer2.logger, Currency.LDKCurrency_Bitcoin, Option_u16Z.none(),
+ System.currentTimeMillis() / 1000);
+ assert phantom_invoice.is_ok();
+ RouteHint[] hints = ((Result_InvoiceSignOrCreationErrorZ.Result_InvoiceSignOrCreationErrorZ_OK)phantom_invoice).res.route_hints();
+ assert hints.length == 1;
+ RouteHintHop[] val = hints[0].get_a();
+ assert hints[0].get_a().length == 1; // Our one channel is public so we should just have a single-hop hint
+
+ if (!use_invoice_payer) {
+ byte[] payment_hash = ((Result_InvoiceSignOrCreationErrorZ.Result_InvoiceSignOrCreationErrorZ_OK) invoice).res.payment_hash();
+ byte[] payment_secret = ((Result_InvoiceSignOrCreationErrorZ.Result_InvoiceSignOrCreationErrorZ_OK) invoice).res.payment_secret();
+ byte[] dest_node_id = ((Result_InvoiceSignOrCreationErrorZ.Result_InvoiceSignOrCreationErrorZ_OK) invoice).res.recover_payee_pub_key();
+ assert Arrays.equals(dest_node_id, peer2.node_id);
+ InvoiceFeatures invoice_features = ((Result_InvoiceSignOrCreationErrorZ.Result_InvoiceSignOrCreationErrorZ_OK) invoice).res.features();
+ RouteHint[] route_hints = ((Result_InvoiceSignOrCreationErrorZ.Result_InvoiceSignOrCreationErrorZ_OK) invoice).res.route_hints();
+
+ PaymentParameters payee = PaymentParameters.of(peer2.node_id, invoice_features, Hints.clear(route_hints), Option_u64Z.none(), 6*24*14, (byte)1, (byte)2, new long[0], 42);
+ RouteParameters route_params = RouteParameters.of(payee, 10000000);
+ Result_RouteLightningErrorZ route_res = UtilMethods.find_route(
+ peer1.chan_manager.get_our_node_id(), route_params, peer1.net_graph,
+ peer1_chans, peer1.logger, ProbabilisticScorer.of(ProbabilisticScoringParameters.with_default(), peer1.net_graph, peer1.logger).as_Score(), new byte[32]);
+ assert route_res instanceof Result_RouteLightningErrorZ.Result_RouteLightningErrorZ_OK;
+ Route route = ((Result_RouteLightningErrorZ.Result_RouteLightningErrorZ_OK) route_res).res;
+ assert route.get_paths().length == 1;
+ assert route.get_paths()[0].get_hops().length == 1;
+ assert route.get_paths()[0].final_value_msat() == 10000000;
+
+ byte[] payment_id = new byte[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31 };
+ Result_NonePaymentSendFailureZ payment_res = peer1.chan_manager.send_payment_with_route(route, payment_hash, RecipientOnionFields.secret_only(payment_secret), payment_id);
+ assert payment_res instanceof Result_NonePaymentSendFailureZ.Result_NonePaymentSendFailureZ_OK;
+
+ RouteHop[] hops = new RouteHop[1];
+ byte[] hop_pubkey = new byte[33];
+ hop_pubkey[0] = 3;
+ hop_pubkey[1] = 42;
+ NodeFeatures node_features = NodeFeatures.empty();
+ ChannelFeatures channel_features = ChannelFeatures.empty();
+ hops[0] = RouteHop.of(hop_pubkey, node_features, 42, channel_features, 100, 0);
+ Path[] paths = new Path[1];
+ paths[0] = Path.of(hops, null);
+ Route r2 = Route.of(paths, payee);
+ payment_res = peer1.chan_manager.send_payment_with_route(r2, payment_hash, RecipientOnionFields.secret_only(payment_secret), payment_id);
+ assert payment_res instanceof Result_NonePaymentSendFailureZ.Result_NonePaymentSendFailureZ_Err;